Call grails 3 domain in groovy script - grails

I have a groovy script, created with grails create-script.
How can I import domain class from my grails app, like
dep p = new User(name: 'Karl')
p.save()
If I try this I get unable to resolve class User.
Thanks for help.

Related

Incapable of running unit tests because of CREATE INDEX and CREATE CONSTRAINT

I've developed a module for Neo4j using Graphaware package. As a part of my module, I want to make sure that some indices and/or constraints are present in the database. To this end, I use BaseTxDrivenModule.initialize method to run a couple of Cypher statements:
#Override
public void initialize(GraphDatabaseService database)
{
database.execute("CREATE CONSTRAINT ON (n:`Label`) ASSERT n.`id` IS UNIQUE;");
database.execute("CREATE INDEX ON n:`Label2`(`id`) IS UNIQUE;");
}
These statements run successfully in production when I deploy the module in a server instance of Neo4j. But when I want to run the unit tests, as a part of build process, the execution hangs and never finishes. And when I omit the initialize method, it goes on without any error.
The worst part is that I have to build the package like: mvn package -Dmaven.test.skip=true or it won't build anything.
So my question is, why? And how can I fix this problem?
Here's a sample project demonstrating the issue:
https://github.com/ziadloo/test_neo4j_module
Just clone it and run mvn package and you'll see that the tests never finish.
There is no guarantee that the Runtime is started during your test, you'll have to assert it by invoking the waitUntilStarted method.
#Before
public void setUp() {
database = new TestGraphDatabaseFactory()
.newImpermanentDatabaseBuilder()
.loadPropertiesFromFile(this.getClass().getClassLoader().getResource("neo4j-module.conf").getPath())
.newGraphDatabase();
getRuntime(database).waitUntilStarted();
registerShutdownHook(database);
}
I would suggest you take a look at some test cases in the neo4j-uuid module for eg.

Grails 3 run-script - Script execution error: No transactionManager

I'm trying to use the run-script command with one of my services in Grails 3.
I have all my services marked with the #Transactional tag. I made a "standalone" groovy file in the folder src/main/groovy that declares one of the services and wants to call a method on it.
My stand-alone groovy file declares a dataSource and sets it like this:
def dataSource = new OracleDataSource(URL: 'jdbc:oracle:thin:#localhost:1521:local', user: 'test', password: '');
I can verify it works within the stand-alone groovy file by doing this:
sql = new Sql(dataSource);
sql.eachRow("SELECT COUNT(*) AS MYCOUNT FROM MYTABLE") {
myCount = it."MYCOUNT";
}
and it works fine.
I then pass the dataSource to my service class as a param. Note that when I run my Grails app as a "normal" Grails app, I don't need to do this, as the service "already knows" how to initialize the dataSource property that it has. But when running my stand-alone groovy file with "grails run-script" and wanting to use the service, I do this:
applicationFunctionService.setSession(dataSource);
But then afterwards when I call a method on my service that involves doing an SQL/database-interaction, it throws this error (when using grails run-script)
Script execution error: No transactionManager was specified. Using #Transactional or #Rollback requires a valid configured transaction manager. If you are running in a unit test ensure the test has been properly configured and that you run the test suite not an individual test method.
:runScript FAILED
Note that my intention is not to do a test per say... I actually want to have a "stand-alone" groovy file that invokes my Grails service within the Grails-context. I'd also like to leave the service as-is with the #Transactional tag. Though I wouldn't mind "turning #Transaction off" within the context of my stand-alone groovy class, if that's possible.
Is there a way to deal with this error?

Grails fails to realize Domain class

I'm using Grails 3.1.4, I've created some domain object and written unit test.
Tests are executed fine on my computer.
Tests on my computer
But on the other developpers computers and on the continous integration platform, tests fail with exception :
java.lang.IllegalStateException: Either class [ ] is not a domain class or GORM has not been initialized correctly or has already been shutdown. If you are unit testing your entities using the mocking APIs
at org.grails.datastore.gorm.GormEnhancer.stateException(GormEnhancer.groovy:159)
at org.grails.datastore.gorm.GormEnhancer.findValidationApi(GormEnhancer.groovy:173)
at org.grails.datastore.gorm.GormValidateable$Trait$Helper.currentGormValidationApi(GormValidateable.groovy:120)
at org.grails.datastore.gorm.GormValidateable$Trait$Helper.validate(GormValidateable.groovy:87)
at com.cscinfo.platform.constraint.CascadeValidationConstraint.validateValue(CascadeValidationConstraint.groovy:43)
at com.cscinfo.platform.constraint.CascadeValidationConstraint.processValidateWithVetoing_closure1(CascadeValidationConstraint.groovy:29)
at groovy.lang.Closure.call(Closure.java:426)
at com.cscinfo.platform.constraint.CascadeValidationConstraint.processValidateWithVetoing(CascadeValidationConstraint.groovy:28)
at grails.validation.AbstractVetoingConstraint.validateWithVetoing(AbstractVetoingConstraint.java:33)
at grails.validation.ConstrainedProperty.validate(ConstrainedProperty.java:967)
at org.grails.validation.GrailsDomainClassValidator.validatePropertyWithConstraint(GrailsDomainClassValidator.java:211)
at org.grails.validation.GrailsDomainClassValidator.validate(GrailsDomainClassValidator.java:81)
at org.grails.datastore.gorm.GormValidationApi.doValidate(GormValidationApi.groovy:89)
at org.grails.datastore.gorm.GormValidationApi.validate(GormValidationApi.groovy:161)
at org.grails.datastore.gorm.GormValidateable$Trait$Helper.validate(GormValidateable.groovy:87)
at api.mails.MailSpec.Test la validation d'un mail incorrect 2(MailSpec.groovy:66)
It seems that GORM can't get my domain object.
I can't reproduce the bug on my computer.
Any help or documentation will be appreciated.
Thanks !
The problem was some oject in my Unit test were not mocked.
I put an array of object in my #Mock annotation and now, it works on my continuous integration platform.
#TestFor(SMTPMailerService)
#Mock([Mail, DestinataireMail, PieceJointeMail])
class SMTPMailerServiceSpec extends Specification {
Hope it will help someone !

Grails GORM in Spring tool suite

The following artical code works in 'grails console'. But when I try to run it in STS its giving compile error for the domain class.
http://timsporcic.github.io/GORM-Recipes/
Is it possible to run in STS, I want to test to GORM methods before using it in contolers. even console command from STS is not working.
trying to run like this:
class Test {
static main(args) {
new BootStrap().init()
println Person.get(1)
}
}
thanks
Run as > Groovy Script will not work. grails console works different, because you have you application fully initialized (same for run-app and test-app).
If you want to test your BootStrap class I suggest you to create one integration test. This will also ensure that, if you change your class, the logic still works.

Grails shell not seeing domain objects

I'm a grails newbie (and a groovy newbie), and I'm working through some grails tutorials. As a new user, the grails shell is a really useful little tool for me, but I can't figure out how to make it see my classes and objects. Here's what I'm trying:
% grails create-app test
% cd test
% grails create-domain-class com.test.TestObj
% grails shell
groovy:000> new TestObj()
ERROR org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed, groovysh_evaluate: 2: unable to resolve class TestObj
I was under the impression that the grails shell could see all of the controllers, services, and domain objects. What's up with this? Do I need to do something else here?
I tried one other thing:
groovy:000> foo = new com.test.TestObj();
===> com.test.TestObj : null
groovy:000> foo.save
ERROR groovy.lang.MissingPropertyException: No such property: save for class: com.test.TestObj
What am I doing wrong?
EDIT: Okay, I saw the answers about using the full name and also using .save() instead of .save. But what about this one?
groovy:000> new com.test.TestObj().save()
ERROR org.hibernate.HibernateException: No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here
What'd I do wrong this time?
I second Burt's advice to use the console instead of the shell. Regarding the exception:
groovy:000> new com.test.TestObj().save()
ERROR org.hibernate.HibernateException: No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here
Can you try explicitly running this code with a transaction:
import com.test.TestObj
TestObj.withTransaction{ status ->
TestObj().save()
}
You need the package since it's possible (but not a good idea) to have two domain classes with the same name in different packages.
For the 2nd session it should be foo.save(), not foo.save.
I prefer the console, it's a lot easier to work with. Run 'grails console' and the Swing app will start. It's a little different from the regular Groovy console in that it's got an implicit 'ctx' variable available which is the Spring application context. You can use that to access services and other Spring beans via "ctx.getBean('fooService')"
you will have to import com.test.TestObj or reference it by new com.test.TestObj() as you have shown.
Note that 'save' is not a propery but a dynamic method that Grails decorates the domain class with at runtime.
groovy:000> foo = new com.test.TestObj();
===> com.test.TestObj : null
groovy:000> foo.save()
===> com.test.TestObj : 2
groovy:000>

Resources