Defining a unique constraint with multiple datasources in Grails 2.0 - grails

Let's suppose I define a domain class named Client in several datasources and create a unique constraint on the field "name" :
class Client {
static mapping = {
datasources(['ds1', 'ds2'])
}
String name
static constraints = {
name unique: true
}
}
The unique constraint will be applied across all the datasources, i.e. if I create a Client in the datasource ds1 with the name "client1", then I can't create a client with the same name in the datasource ds2.
I would like the field "name" to be unique for a given datasource, not across all datasources, the same way it is possible to define the field "name" to be unique for the given value(s) of one or several other field(s). In fact, it was the way it worked by default with the Datasources plugin before Grails 2.0. Do you know how to do that ?

If that's how it's working, it's a bug. Please create an issue at http://jira.grails.org/browse/GRAILS

Related

How can I update my existing database table using domain class in grails 3.3.0?

I would like to add new column in my existed table using domain class but it is not happening. if I use create-drop in application.yml file then it works but at the same time I lost my data. I needed to keep the data as well as I needed to add new column by updating domain class property in grails 3.3.0 and SQL Server 2012
package com.alumni
class Student
{
String studentId
String studentName
String age
static constraints = {
}
}
Database is not updating with column address
It's unclear from your code snippet, but it sounds like you're trying to add
String address
Note that columns are made NOT NULL by default, so if data exists in the table, it's attempting to add a non-nullable column, with null data on every row, so the column will fail to create. You need to allow this column to be nullable in the constraints block as well
static constraints = {
address(nullable: true)
}
If you add that, the column should create successfully.

GORM creating tables with base class name instead concrete class name

I Have the following domains in my gorm package:
Domain.groovy
package gorm
class Domain {
String createdBy
static constraints = {
}
static mapping = {
tablePerHierarchy true
}
}
User.groovy
package gorm
class User extends Domain {
String name
static constraints = {
}
}
I want a table named user with the fields of the base class domain, but instead GROM generate a table whit this specification
create table domain
(
id bigint auto_increment
primary key,
version bigint not null,
created_by varchar(255) not null,
class varchar(255) not null,
name varchar(255) null
)
I'm using mysql driver with grails 2.5.6.
It generates the table with the name as domain because you are using tablePerHierarchy true in your mapping.
Basically, you will get one table where you can set different discriminators for the subclasses.
See here for more information on inheritance strategies: http://docs.grails.org/2.5.x/guide/single.html#GORM
(scroll down to: 7.2.3 Inheritance in GORM)
If you simply want schema-export to generate your table with the name as user, then you would need to add the following to your mapping block in the Domain class:
table 'user'
so the entire mapping block would look like:
static mapping = {
table 'user'
tablePerHierarchy true
}
However, this may not make sense to name the table user if you have other classes extend from Domain.
(and if you don't plan to have other classes extend from Domain, then just add your fields into your User domain).
If you want to generate two tables (Domain and User), then set tablePerHierachy false.
Here is a great write-up with examples that may help you decide which way you want to go for your project:
https://sysgears.com/articles/advanced-gorm-features-inheritance-embedded-data-maps-and-lists-storing/
As a side note: I'm not keen on the name Domain for a domain class; it is too generic and may get confusing when you are talking about the specific Domain class vs domain classes. At least name it BaseDomain.

grails elasticsearch only indexed one instance out of many

I am using the elasticsearch grails plugin for the first time, and when I set the config bulkIndexOnStartup = true, it indexed several of the domain classes correctly, but for a couple of others it seemed to only index one instance out of many, even though I saw 99 distinct instances in the database.
When I tried to specifically index the instances by calling
elasticSearchService.index( anInstance )
it would just delete the old entry and add a new one, so at the end there was still only one instance in elasticsearch. Is there an "indexAllDistinct" setting somewhere? How does it decide to add a new entry or replace an existing entry?
I also noticed that on the instances that were indexed correctly, the _id fields all had numeric values, but on the incorrectly indexed instance, the _id field was "null".
EDIT: I found that the incorrectly indexed classes have the "id" mapping name set to a different field. How can I tell elasticsearch that the "id" has a different name for these classes?
For grails domain classes that map the default "id" to another name, I had to add a transient "id" for elasticsearch. For example:
class LogEntry {
Integer logId // replaces default id
...
static mapping = {
id name: 'logId', column: 'LOG_ID'
...
}
static transients = ['id'] // for elasticsearch
def getId(){
return logId
}
}

grails validation when fetching rows

Is it possible to fetch a default value in grails if a column is null? If I were to represent following query via grails domain object then how could I achieve it:
SELECT IFNULL(empsalary,0.00) from Employee;
Domain object:
class Employee{
Integer id,
Float empsalary
static constraints = {
id unique: true, blank:false
empsalary nullable:true
}
}
making empsalary nullable false isn't an option due to existing data
validator on empsalary seems to work when inserting rows but not while data fetch
we can consider writing say getEmpSalary() method on domain and perform check there but there are several other fields we need to do this so trying to avoid massive code changes
If you want a default value to come out of the database without having to code anything into your classes, I suggest you update every row where it is null and set it to 0 in the database. If data is getting inserted from another application and that application is allowing a null value, put a 'DEFAULT 0' on your database column.
Grails also offers an "afterLoad" event which is run when a domain object gets loaded from the database. See the documentation here: http://grails.org/doc/2.3.7/guide/GORM.html.
I think you can do this with HQL:
def salary = Employee.executeQuery('SELECT COALESCE(empsalary, 0.0) FROM Employee')[0]
See this SO Question.
Please try setting Float empsalary = 0.0 in your domain object.

How to change primary key column in grails?

I have a domain class having an Integer variable 'code'. my requirement is to make 'code', primary key column for that domain and also auto increment and to remove the default 'id' column from the table created for that doamin.thnks
use this :
static mapping = {
id name: 'code'
}
more informations here :
http://grails.org/doc/2.0.x/ref/Database%20Mapping/id.html
Domain classes in Grails by default dictate the way they are mapped to the database using sensible defaults. You can customize these with the ORM Mapping DSL.
Customizes the way the identifier for a domain class is generated with id.
See the Grails documentation for id.
static mapping = {
id column: 'code', type: 'integer'
}

Resources