Category Archives: Subversion

IntelliJ: Handling SVN Global Ignore List

PROBLEM

Every time we check out a project from SVN for the first time, we always have to remember to set the SVN ignore list in IntelliJ.

SOLUTION

NOTE: We only need to perform these steps just once per development machine.

To do so, we configure the SVN global ignore list and have IntelliJ to conform to that rule.

  • In Mac, go to IntelliJ IDEA -> Preferences. In Windows, go to File -> Settings.
  • In the preference dialog, go to Version Control -> Subversion.
  • Check Use system default Subversion configuration directory.
  • Note down Subversion configuration directory.
  • Close preference dialog.
  • Open [SVN_CONFIG_DIR]/config in a text editor.
  • Scroll to the [miscellany] section that looks something like this:-

    ...
    [miscellany]
    ### Set global-ignores to a set of whitespace-delimited globs
    ### which Subversion will ignore in its 'status' output, and
    ### while importing or adding files and directories.
    ### '*' matches leading dots, e.g. '*.rej' matches '.foo.rej'.
    # global-ignores = *.o *.lo *.la *.al .libs *.so *.so.[0-9]* *.a *.pyc *.pyo
    #   *.rej *~ #*# .#* .*.swp .DS_Store 
    ### Set log-encoding to the default encoding for log messages
    # log-encoding = latin1
    ...
    

  • Uncomment global-ignores statement by removing #:-

    ...
    [miscellany]
    ### Set global-ignores to a set of whitespace-delimited globs
    ### which Subversion will ignore in its 'status' output, and
    ### while importing or adding files and directories.
    ### '*' matches leading dots, e.g. '*.rej' matches '.foo.rej'.
    global-ignores = *.o *.lo *.la *.al .libs *.so *.so.[0-9]* *.a *.pyc *.pyo
       *.rej *~ #*# .#* .*.swp .DS_Store
    ### Set log-encoding to the default encoding for log messages
    # log-encoding = latin1
    ...
    

  • Add the following patterns:-

    ...
    [miscellany]
    ### Set global-ignores to a set of whitespace-delimited globs
    ### which Subversion will ignore in its 'status' output, and
    ### while importing or adding files and directories.
    ### '*' matches leading dots, e.g. '*.rej' matches '.foo.rej'.
    global-ignores = *.o *.lo *.la *.al .libs *.so *.so.[0-9]* *.a *.pyc *.pyo
       *.rej *~ #*# .#* .*.swp .DS_Store
       .idea target .git .classpath .project .settings *.iml *.log *.bak *.class *.jar *.war *.ear 
       node_modules pom.xml.versionsBackup
    ### Set log-encoding to the default encoding for log messages
    # log-encoding = latin1
    ...
    

  • Save and close this config file.

Now, all the unnecessary files will not appear under “Changes” section in IntelliJ and they will not be committed into SVN.

IntelliJ: Configuring SVN Ignored Files

OVERVIEW

Whenever we share a project in SVN or checks out a project from SVN, we have to perform a one-time configuration on the project to ignore selected files from being committed into SVN. That said, this configuration will only work if the files are not already in SVN.

PROBLEM

Let’s assume we have a Maven project that contains an EAR module and a WAR module:-

EpicApp
├── .idea
│   └── ...
├── EpicApp.iml
├── epicapp-ear
│   ├── epicapp-ear.iml
│   ├── pom.xml
│   └── src
│       └── ...
├── epicapp-war
│   ├── epicapp-war.iml
│   ├── pom.xml
│   └── src
│       └── ...
└── pom.xml

IntelliJ generates .idea folder and *.iml files to store our project settings and module configuration.

When we run mvn clean compile, the target folders are created:-

EpicApp
├── .idea
│   └── ...
├── EpicApp.iml
├── epicapp-ear
│   ├── epicapp-ear.iml
│   ├── pom.xml
│   ├── src
│   │   └── ...
│   └── target
│       └── ...
├── epicapp-war
│   ├── epicapp-war.iml
│   ├── pom.xml
│   ├── src
│   │   └── ...
│   └── target
│       └── ...
├── pom.xml
└── target # Depending on how the root pom.xml is configured, this folder may or may not appear.
    └── ...

If we look at the overall project structure, there are tons of generated files that are not created by us:-

EpicApp
├── .idea
│   └── ...
├── EpicApp.iml
├── epicapp-ear
│   ├── epicapp-ear.iml
│   ├── pom.xml
│   ├── src
│   │   └── ...
│   └── target
│       └── ...
├── epicapp-war
│   ├── epicapp-war.iml
│   ├── pom.xml
│   ├── src
│   │   └── ...
│   └── target
│       └── ...
├── pom.xml
└── target # Depending on how the root pom.xml is configured, this folder may or may not appear.
    └── ...

First, we definitely want to ignore target folders from being committed into SVN.

Now, regarding whether to ignore .idea folder and *.iml files, there are two camps out there:-

  • Camp PINK will commit the IntelliJ generated files into SVN so that the project configuration is shared among team members.
  • Camp BLUE will NOT commit files that are not created by them.

What’s my take? I’m with Camp BLUE because I don’t like pink in the first place. In the past, I tend to commit all IntelliJ generated files into SVN. However, it was a nightmare working in a team environment because every team member kept overwriting these files from one other, resulting endless SVN conflicts. Since we encourage folks to only commit the files they modify (or create), I see no absolute reason to commit these IntelliJ generated files. We saw more cons than pros based on our past experience.

SOLUTION 1: Add Ignored Files Using IntelliJ

Based on the example above, there are 5 things we need to ignore:-

  • epicapp-ear/target/ directory
  • epicapp-war/target/ directory
  • target/ directory
  • .idea/ directory
  • *.iml files

So, in IntelliJ…

  1. Select “Changes” tab at the bottom.
  2. Select “Local” subtab.
  3. Click on “Configure Ignored Files” button.
    "Changes" tab
  4. In “Configure Ignored Files” dialog, click on the “+” button.
  5. Add the ignored file (or directory).
    "Configure Ignored Files" dialog

  6. Repeat step 4 and 5 until all ignored files are added.

SOLUTION 2: Add Ignored Files Directly in .idea/workspace.xml

If you have quite a few files and directories to ignore, the above solution can be rather tedious.

So, an alternative solution is to “hack” .idea/workspace.xml by entering all the ignored paths under “ChangeListManager” component:-

<?xml version="1.0" encoding="UTF-8"?>
<project>
    <component name="ChangeListManager">
        ...
        <ignored path="epicapp-war/target/" />
        <ignored path="epicapp-ear/target/" />
        <ignored path=".idea/" />
        <ignored path=".settings/" />
        <ignored path="target/" />
        <ignored path=".DS_Store" />
        <ignored path=".classpath" />
        <ignored path=".project" />
        <ignored mask="*.iws" />
        <ignored mask="*~" />
        <ignored mask="*.bak" />
        <ignored mask="*.log" />
        <ignored mask="*.iml" />
    </component>
    ...
</project>

In this example, we ignore all target folders, all IntelliJ generated files, all Eclipse generated files, all OS-specific generated files and some useless files.

When we save .idea/workspace.xml, IntelliJ immediately detects a change made to this file (because it is intelligent) and it will prompt us to reload the project. Once reloaded, the “Configure Ignored Files” dialog will reflect the changes made.