Mercurial, MercurialEclipse, TortoiseHg and SSH Server with Win7

There is problem with the Usercredentials passed by MercurialEclipse to a remote SSH repository. There are two ways to fix this issue, one is to authenticate with a public/private keypair and the use of TortoisePlink/PuttyPlink, the other way is to install openSSh on the Windows machine with cygwin and the openSSH package.

I decided to use the public/private Key authentication with Plink because it’s more comfortable in conjunction with Pageant because you only need to give your password only once, despite if youre using Tortoise or Eclipse. Here is the HowTo:

1. Set up the public/private key authentication as described in the Post here.

### To get TortoiseHg working: ###
2. Find out the path to TortoisePlink.exe. It should be located in your TortoiseHg install directory
3. Locate the path to your private key file (.ppk)
4. To tell TortoiseHg and MercurialEclipse to connect with ssh and the public/private keypair you need to add a config value in
the mercurial.ini. Edit it via TortoiseHg -> File -> Settings -> Edit File and add the following lines
[ui]
username = dwasser
ssh=”C:\Programme\TortoiseHg\TortoisePlink.exe” -ssh -agent -i “C:\Dev\Putty\dwasser.ppk”

Here is a screenshot of the EditFile dialog (be careful, use the String above it contains the -agent property which means that Pageant should be used)

Sometimes there is some trouble with the Windowspath to TortoisePlink.exe. If so, extend your Path Variable to the
Tortoise directory and set the ssh value in the mercurial.ini to:
ssh=TortoisePlink.exe -ssh -agent -i “C:\Dev\Putty\dwasser.ppk”

This is important, because this configuration will be used by TortoiseHg

    and

MercurialEclipse. It tells the Applications to use TortoisePlink as “ssh bridge”.
If you want to use cygwin with openSSH, install it, add the folder cygwin/bin to the PATH variable
of Windows and use the following configuration instead : ssh = C:\yourpathto\cygwin\bin\ssh

5. Now all Actions should work. For example you should be able to clone a repository by clicking
File -> clone and enter an Url in this way ssh://dwasser@192.168.103.64//sources//myproj . Don’t forget to mask the slashes!!

### To get MercurialEclipse working: ###
6. Nothing special here, just create a new Project of type mercurial and enter the URL. Also use an Url of this type: ssh://dwasser@192.168.103.64//sources//myproj

log4j doesn’t refresh Loglevels correctly

I don’t know whether it is a log4j (JBoss 1.2.14) problem or a bug in the Jboss Log4jService URLWatchTimerTask (from JBoss 4.3.0.GA) which i use on my server to refresh the log4j configuration automatically after a change. When I try to  set a higher log level by a base package name, it doesn’t work if formerly a lower log level was set explicit for a class.

Here is an example:

First my machine is configured like this (snip of log4j.xml):

<!-- limit my code-->
<category name="de.koelnerwasser">
 <priority value="INFO" />
</category>
<!-- log a class explicit -->
<category name="de.koelnerwasser.testclass">
 <priority value="DEBUG" />
</category>

Until now everything is fine – all info messages and the debug messages of testclass are logged.  When i change the log4j.xml like this:

<!-- limit my code-->
<category name="de.koelnerwasser">
 <priority value="ERROR" />
</category>

.. and deploy the file to my server, the log4j framework will be reconfigured by the URLWatchTimerTask.

Now only error will be logged and – this is curious: Debug Messages of my testclass . The old loglevel DEBUG will not be overwritten by the ERROR level.  I think this is a little bug of log4j or the Jboss URLWatchTimerTask, i will analyse the code and add a defect to Jboss or Apache.

PortletStateHolder in the JBoss PortletBridge and ConcurrentModificationException

Today I run again into my old problem with the PortletStateHolder. While he is under fire he throws a lot of ConcurrentModificationExceptions.

Here is one of these Exceptions:

Caused by: java.util.ConcurrentModificationException
at java.util.LinkedHashMap$LinkedHashIterator.nextEntry(LinkedHashMap.java:373)
at java.util.LinkedHashMap$KeyIterator.next(LinkedHashMap.java:384)
at de.koelnerwasser.portlet.bridge.MyPortletStateHolder
         .removeSessionStates(MyPortletStateHolder.javaa:198)

Because I synchronized every write access to the class variable “states” eg.:

public void addWindowState(StateId stateId, PortletWindowState state) {
  // prevent concurrent access
  synchronized (states) {
    states.put(stateId, state);
  }
 }

I wonder about the exceptions.  So I investigated the read access to “states” in the “getWindowState()” method:

public PortletWindowState getWindowState(StateId stateId) {
 PortletWindowState state = null;
  if (null != stateId) {
   state = states.get(stateId);
  }
  return state;
 }

I found that states.get() calls a put on the org.apache.commons.collections.LRUMap. Here is the code:

public Object get(Object key)
{
  if(!containsKey(key))
  {
    return null;
  } else {
    Object value = remove(key);
    super.put(key, value);
    return value;
  }

The put() call causes the ConcurrentModificationException. The solution is to synchronize every call on the state LRUMap.