Thursday, July 11, 2013

Shiro with Spring: Remember Me - Custom Cipher Key

Recently was working with Shiro apache security library. Nice library with good inbuilt methods like “Remember Me” function.
You just need to set the value at the time of login and it will take care of rest. There is a small caveat, this functionality uses a hardcoded AES key to encrypt the user name. More information here: http://shiro.apache.org/configuration.html#Configuration-ByteArrayValues

As the article rightly mentioned you can specify your own key in the shiro configuration ini file. Ok, I did the same but in my project we were using Spring to configure Shiro so instead of specifying the key in shiro.ini, I specified it in my properties file, which was read by the spring config file. Sample code: In spring config file:

<bean id="securityManager"  class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="realm" ref="myRealm"/>
<property name="subjectFactory" ref="mySubjectFactory"/>
<property name="rememberMeManager.cipherKey">
<value>Your Key</value>
</property>
</bean>

All worked fine, the key was picked up but my test cases started failing. 

Downloaded the source for Shiro, debugged the flow and found that Key picked properly, also getting read in the AbstractRememberMeManager. After lots of wasted hours, found that there was exception from a Java class while encrypting user name. (invalid key length) . Come on I was using the same code to generate the key as mentioned in the comments of default cipher key.
(More wasted hours)
Finally did something basic, provided the default shiro cipher key in the properties file and again error. That made one thing clear – There was some issue in how the key was read/set.
(why I didn't find that while debugging, because the key is actually set as byte array and me being proficient only in English and Hindi couldn't notice the difference in byte representation :))
Ok, now where is it getting corrupted. Downloaded the spring libs’ code and found that the key received by the shiro class was getting corrupted in the spring code itself. On further investigation found that instead of using Base64.decode, spring was converting the key (which was encoded to string with Base64) to bytes directly (but of-course).
Looks like while reading from Shiro.ini file this is taken care of by shiro, but when using spring, one needs to make sure that key is set in the security manager after getting decoded to byte using Base64 only.

Huff, problem found, solution was much simpler. (no you cannot use spring's ByteArrayPropertyEditor it again does not use Base64)

Create a custom property editor.
1) Create a java class:

import java.beans.PropertyEditorSupport;
import com.ibm.xml.crypto.util.Base64;
public class BytesPropertyEditor extends PropertyEditorSupport {
    public void setAsText(String text) throws IllegalArgumentException {
        byte[] bytes = Base64.decode(text);
        setValue(bytes);
    }
}

2) Add following in your spring config:
<bean id="customEditorConfigure2"
    class="org.springframework.beans.factory.config.CustomEditorConfigurer">
    <property name="customEditors">
        <map>
            <entry key="byte[]">
                <bean class="com.amit.BytesPropertyEditor">
                </bean>
            </entry>
        </map>
    </property>
</bean>
And you are done. Happy remembering me... *_^

Wednesday, July 3, 2013

How I broke my Linux (RHEL) and fixed it

Few months back I moved to RHEL Linux and managed to crash the OS by doing seemingly safe things. Here I am sharing my experience with other users so that they don't end up wasting time like me.
What I did
Installed XFCE and then uninstalled it
Why
I was hoping it to be better than gnome in terms of user experience. Later found its actually minimalistic desktop mainly for low end systems.
What happen
System failed to boot. Failsafe boot option also didn't work.
How I fixed
Reinstalled Gnome desktop by booting to RHEL command
  1. Boot to Red Hat command line (steps in 'how to' below)
  2. Ensure the network is working (steps in 'how to' below)
  3. Reinstall gnome by giving command
              Yum groupinstall “GNOME Desktop Environment”

Should you try it
You can of course try XFCE but if you uninstall make sure to install Gnome Desktop again before any sort of reboot. I haven't tried this but based on my experience this should prevent the OS crash on next reboot.

Below are few ‘how to' which might be useful in case of system crash:
How To 1: How to boot RHEL to command prompt (not the grub menu)
1. Boot/reboot machine
2. At blue Red Hat screen press any key to enter the boot loader
3. Press 'e' to edit the most recent boot command
4. Use the arrow keys to select the line that starts with "kernel"
5. Press 'e' to edit the kernel command
6. Append 'S' to the end of the line. There should be a space before the previous end of the line (probably 'quiet') and the 'S'. Capitalization matters.
7. Hit Enter to commit the change
8. Hit 'b' to boot
9. When it is done booting you will be at a command prompt. Type 'help' for list of available commands

How To 2: How to connect network in the command line mode
Once you get the command line it's of no use if you have to install something and you are not on network. To start network (assuming that whatever you did to crash your system, it didn't mess up your network settings)
dhclient eth0

Note:
  1. I am pretty sure that other people might be having similar inputs so feel free to put in the comments.
  2. The reason/solutions mentioned are based on my search on internet, in case someone has anything to correct/add, please feel free to point out.

Monday, July 1, 2013

Lotes Notes tip: Upgrade notes database version

If you are using lotus notes and upgrading from past versions, chances are you might be using an old database version, most probably will be 43. Notes database version should be 51 assuming you are at 8.5.3 or above

To Check: Application -> Properties -> i and look for ODS version  

1) How to fix: Add following in the notes.ini
NSF_UpdateODS=1
CREATE_R85_DATABASES=1

2) Do a compact on the database (Application -> Properties) . To compact all the databases, simply fire compact -c from command prompt from your notes directory. (Looks like -c option to convert is necessary, for me the GUI option didnt work for archive files which were not store in the notes/data directory. To convert those I used compact -c )

Result:
  1. More compact database.
  2. Better speed
  3. Ability to use newer features of the new db version