Failure publishing Play modules

Today i found interesting module for my Play application on git-hub.
Unfortunately it was not published on modules repository (I didn’t know the reason).
So i forked it and made some changes (i hope that it was an improvement).
Then i wanted to use it in my app so i wanted to publish it in play modules repository.
And this is what i found about sharing modules in play repository for 1.2.4 version:

Share module in Play

“First you need to have an OpenID.
Then you have to send module registration request on the Google Group.
Then you can release your module
And then log in to module repository and upload the generated package”

Damm, now i know why creator of this module didn’t share it at first place. More detailed instruction available here http://www.playframework.org/documentation/1.2.4/modules

Share gem in ruby
Compare all of this tasks to rubygems one line way of publishing your gem:

gem push foo-1.0.0.gem

Grails spring-security-ui plugin and Bad credentials exception

The spring-security-ui plugin provides CRUD screens and user management workflows out of the box for spring security implementation. The most important is that it’s fully customizable. Together with spring-security-core plugin its gives you full implementation of security stack. Instalation is very simple but you have to consider one thing.

For example to install plugin with brand new app run:

grails create-app sample
grails install-plugin spring-security-core
grails s2-quickstart com.sample User Role

grails install-plugin mail
grails install-plugin jquery
grails install-plugin jquery-ui
grails install-plugin famfamfam

grails install-plugin spring-security-ui

grails run-app

And that’s it. You have CRUD flow for user management and login, register, forgot password functionalty.
Only problem is that you cannot login with registered users. Read along to see why.

Password encoding catch

Plugin have generated all classes for us but one thing you have to change manually.
Classes generated by spring-security-core plugins already have encodePassword executed before insert.
For example in User it looks like this:

	def beforeInsert() {
		encodePassword()
	}
	def beforeUpdate() {
		if (isDirty('password')) {
			encodePassword()
		}
	}
	protected void encodePassword() {
		password = springSecurityService.encodePassword(password)
	}

After you install spring-security-ui you may find that you cannot login using created users. You will receive error about bad credentials: org.springframework.security.BadCredentialsException: Bad credentials

The problem is that while registering new users controller generated by springsecurity.ui is encoding user password second time.
So you end up having password encoded twice. Password is encoded in controller and in User domain object.
You can remove encoding in domain object but this is not prefered because then you will have to remember to encode password when creating
User objects in BootStrap or anywhere else besides UserController.

Solution

Solution is to disable encoding in springsecurity.ui controllers by setting property in Config.groovy:

grails.plugins.springsecurity.ui.encodePassword = false

Other things to configure

There are also other things generated by plugin you may want to customize.
For example RegisterController and its views assume that your User domain class has an email field. If You don’t have smtp server then registration will fail. Be sure to rework the workflow (using the s2ui-override script) if you don’t want an email confirmation step.

grails s2ui-override register com.sample

Otherwise add an email field to User domain class and configure mail plugin.

You probably will need to change generated pages like register/index.gsp too get rid of email functionality. View register/index.gsp assumes that sendEmail model property is set to true after sucessfull registering user.

Run single Spock test in Grails

When using Spock framework together with Intellij Idea 11 I found very annoying that when I try to run single test all test in spec are executed.
First I thought that this is Idea issue but it turned out to be Grails problem.

The thing is that You can only run whole spec from Grails command line:

grails test-app unit:spock SomeControllerSpec

New Feature request to fix this: http://jira.grails.org/browse/GPSPOCK-3

Workaround

There is a annotation you can use as a workaround to run only one test:

@IgnoreRest
def "should test something"() {
...
}

You can put this on test you are working on to prevent all other test in spec from running.
Don’t forget to remove it when You finish.

Unit testing with Spock in Intellij Idea

Recently i have stared to learn Grails for my new project. For unit testing I use Spock. Unfortuantelly it turns out that test classes generated from Grails are using Junit by default.
Untill I find way to make Grails generate test with Spock template I have created file templates and live templates for Idea for generating test classes and test methods for Spock.

Spock Contoller Test File Template

#if (${PACKAGE_NAME} != "")package ${PACKAGE_NAME};#end

import grails.plugin.spock.ExtendedControllerSpec

#parse("File Header.java")
class ${NAME} extends ExtendedControllerSpec{

}

Spock Unit Test File Template

#if (${PACKAGE_NAME} != "")package ${PACKAGE_NAME};#end

import grails.plugin.spock.UnitSpec

#parse("File Header.java")
class ${NAME} extends UnitSpec{

}

Live template for given-when-then test method

def "$NAME$"(){
    given:
    $END$

    when:

    then:
}

Live template for expect-where test method

def "$NAME$"(){
    expect:
    $END$

    where:
    
}