Grails error: No such property: it for class: - grails

Below is my code.
Here I am getting an error which is 'No such property: it for class: emp.EmployeeController'.
I think I am doing something wrong here.
Any advice??
def list ={
def id=params.id
def results
String employee="SELECT empName, empDate, empNo from employee where empId='id'"
String referrer="SELECT empName, empDate, empNo from referer where empId='id'"
def employeeInstanceList = new ArrayList<Employee>()
Sql sql = new Sql(dataSource)
def joining=null
joining = sql.rows( "select joining from employee_dates")
if (joining!=null)
results = sql.eachRow(employee)
employeeInstanceList=getCalculatedEmployeeData(results)
/*{
def employee = new Employee()
employee.setempName it.empName
employee.setEmpNo it.empNo
employee.setEmpDate it.EmpDate
employeeInstanceList.add employee
}*/
else
results = sql.rows (currentDaySql)
employeeInstanceList=getCalculatedEmployeeData(results)
/*{
def employee = new Employee()
employee.setempName it.empName
employee.setEmpNo it.empNo
employee.setEmpDate it.EmpDate
employeeInstanceList.add employee }*/
}
[employeeInstanceList: [employeeInstanceList: employeeInstanceTotal: Employee.count()]
}
def getCalculatedImpactData(def results){
def employee = new Employee()
employee.setempName it.empName
employee.setEmpNo it.empNo
employee.setEmpDate it.EmpDate
employeeInstanceList.add employee }*/
return [employeeInstanceList: employeeInstanceList]
}
Thanks,
Meghana

i would second leebutts answer... but just a pointer, the usage of the it keyword is usually confined to closures... so instead of doing this in java:
List l = [];
for (Iterator i = l.iterator(); i.hasNext(); ) {
...do something adressing List l at position i...
}
you could do this in groovy / grails:
list.each { it ->
...do something with each object in the list (it)...
}
but you should really read up on groovy closures at http://groovy.codehaus.org/Closures

There is so much wrong with that code, I don't know where to start...
But to avoid getting more down votes I have tried :)
I tried to copy your code into an IDE and try and work out what you are trying to achieve but couldn't.
This is as close as I could get it:
def list = {
def id = parmas.id
def results
String employee = "SELECT empName, empDate, empNo from employe"
def employeeInstanceList
Sql sql = new Sql(dataSource)
def joining = sql.rows("select joining from employee_dates")
if (joining != null) {
results = sql.eachRow(employee)
employeeInstanceList = getCalculatedEmployeeData(results)
}
else {
results = sql.rows(currentDaySql)
employeeInstanceList = getCalculatedEmployeeData(results)
}
[employeeInstanceList: employeeInstanceList, employeeInstanceTotal: Employee.count()]
}
def getCalculatedImpactData(def results) {
def employeeInstanceList = new ArrayList<Employee>()
results.each { it ->
def employee = new Employee()
employee.empName = it.empName
employee.empNo = it.empNo
employee.empDate = it.EmpDate
employeeInstanceList.add(employee)
}
return employeeInstanceList
}
but it is still referring to a variable currentDaySql which doesn't exist and I'm not sure what you're trying to do with the 'joining' result.
You really need to read up on Groovy basics.

The block of code where the error occurs is probably:
def getCalculatedImpactData(def results){
def employee = new Employee()
employee.setempName it.empName
employee.setEmpNo it.empNo
employee.setEmpDate it.EmpDate
employeeInstanceList.add employee
return [employeeInstanceList: employeeInstanceList]
}
it is not defined anywhere (hint: the compilation error told you this). Like Sebastian said, it is typically used in closures; what you've defined here is a function. Presumably you wanted to use results (or something) instead of it here.
I'm assuming that some of the things in your code (e.g. comment opening/closing) weren't in there and were added between when you saw the error and when you posted the code. Otherwise you'd get other errors.

Related

executeUpdate query not working on grails spock test

Now willing to do integration test as below but problem is that
MerchantTier.executeUpdate('update MerchantTier..........'),
here update does not working
but if I make update with
def merchant = MerchantTier.get(params.id.toLong())
merchant.setValue(merchantTierVal)
instead of execute update it works
Is there is any prolem with executeUpdate Query?
def merchantTier
def setup() {
merchantTier = new MerchantTier(
startTier: tier,
endTier: tier,
value: 2.02).save(flush: true)
}
void "for given merchantTierId update merchantTier"(){
setup:
params = [id:merchantTier.id,tierVal:2]
when:
testData = updateIndividualSuperResellerTier(params)
then:"return data"
merchantTier.value==params.tierVal
}
def updateIndividualSuperResellerTier(params) {
def merchantTierVal = 0
if (params.tierVal) {
merchantTierVal = params.tierVal.toDouble()
}
def merchantTier = MerchantTier.get(params.id.toLong())
def updateMerchantTier = MerchantTier.executeUpdate('update MerchantTier mt set mt.value=:mrValue where mt.id=:mtId', [mrValue: merchantTierVal, mtId: params.id.toLong()])
}
There seems to be no problem with executeUpdate, the problem here could be, that executeUpdate did not return an object, it just return the number of rows updated so updateMerchantTier doesnot contain updatedObject.
Also you should again fetch the object as it is updated by executeUpdate in your void "for given merchantTierId update merchantTier"() then: statement
then:"return data"
merchantTier.value==params.tierVal
here merchantTier is still an old object hence will not be having value equal to params.tierVal
in your other case you are using setter explicitly to set the property and hence it passed your Integration test.
def merchant = MerchantTier.get(params.id.toLong())
merchant.setValue(merchantTierVal)
hope this helps. Thanks

How can I pass a class to Groovy's Eval binding?

I'm doing some gross stuff, like using Groovy's metaClass and Eval to dynamically assign properties to an object from an XML import:
class ObjectBuilder {
def assignProp(String propName, String propValue) {
Eval.x(this, "x.metaClass.${propName} = '${propValue}'")
}
}
def h = new ObjectBuilder()
h.assignProp('name', 'Henson')
println(h.name)
What I'd like to do though, is be able instantiate another copy of the class inside itself:
Eval.x(this, "x.metaClass.${ObjName} = new ObjectBuilder()")
But I can't, because I think the class isn't passed to the binding. Is there another solution?
A couple of solutions:
Expando
You may try working with a bunch of Expandos:
h = new Expando()
h.last = new Expando()
h.last.name = 'tech'
assert h.last.name == 'tech'
Metaclass the object directly
xml = '''
<person>
<name>john</name>
<surname>doe</surname>
<age>41</age>
<location>St Louis, MO</location>
</person>
'''
class Person {
def name, surname, location, age
}
root = new XmlParser().parseText xml
person = new Person(root.children().collectEntries { [it.name(), it.text()] })
person.metaClass.getFullname = { "$delegate.name $delegate.surname" }
assert person.fullname == "john doe"
person.metaClass.likes = "chicken with lemon"
assert person.likes == "chicken with lemon"
Maps
map = [:]
map.last = [:]
map.last.name = 'Tech'
assert map.last.name == 'Tech'
Passing a newly instantiated object then assigning it with Eval seems to work:
class ObjectBuilder {
def assignProp(String propName, String propValue) {
Eval.x(this, "x.metaClass.${propName} = '${propValue}'")
}
def nestObj(String objName) {
Eval.xy(this, new ObjectBuilder(), "x.metaClass.${objName} = y")
}
}
ObjectBuilder h = new ObjectBuilder()
h.assignProp('name', 'Henson')
h.nestObj('last')
h.last.assignProp('name', 'Tech')
println h.name + ' ' + h.last.name

how to grails find withCriteria or condition

String query='test'
def user = User.withCriteria {
ilike('firstName', '%'+query+'%')
or {ilike('lastName', '%'+query+'%')}
or {ilike('email', '%'+query+'%')}
}
above is the sample code i need to find those object if any one of three of these field( firstName lastName email ) contains query string
thnks
Try joining the conditions inside one or
or {
ilike('firstName', '%'+query+'%'),
ilike('lastName', '%'+query+'%'),
ilike('email', '%'+query+'%')
}
You can also turn on SQL debugging to see how your queries get built.
You can do in this way
String query='test'
def crit = User.createCriteria()
def user = User.list{
or{
ilike('firstName', '%'+query+'%')
ilike('lastName', '%'+query+'%')
ilike('email', '%'+query+'%')
}
maxResults(1000)
order("firstName")
}

How to save multiple rows of data by looping through an array or a map?

Class Buyer {
String name
static constraints = {
}
}
Class Order {
String ref
static belongsTo = [buyer:Buyer]
static constraints = {
buyer(nullable:false)
}
}
In OrderController.groovy
...
def someAction = {
//working
def data1 = ["buyer.id": 2, "ref": "xyz"]
def ord = new Order(data1);
ord.save();
def data2 = ["buyer.id": 2, "ref": "234xyz"]
def ord2 = new Order(data2);
ord2.save();
//But in a loop - its not working
def items = ['abc', 'def', 'ghi', 'jkl']
def data2 = [:]
for(e in items) {
data2 = ["buyer.id": 2, "ref" : e.value] //keeping buyer id same
def ord = new Order(data2);
ord.save();
data2 = [:] //just emptying it?
}
}
As you would notice in "working" above, if I am able to save multiple rows by copy pasting and definging new maps but If I try to loop through an array, it doesnt work. Any ideas how do I save data by looping through an array or a map?
Any questions, please let know
Thanks
First, I'm not sure about ["buyer.id": 2, "ref" : e.value], I think it should be [buyer: Buyer.get(2), ref : e.value].
Second, I would recommend using cascading save to do the task. You can try something like this(You need to define a static hasMany = [orders: Order] relation in Buyer for Buyer-Order relationship.
Buyer b = new Buyer(name: "foo")
for(e in items) {
def ord = new Order(ref: e.value);
b.addToOrders(ord)
}
b.save(flush:true)
You should just be able to do:
def someAction = {
def items = ['abc', 'def', 'ghi', 'jkl']
items.each { item ->
def ord = new Order( [ 'buyer.id':2, ref:item ] )
ord.save()
}
}
What errors (if any) are you getting?
Also, why are you doing e.value? This will get you an array of Character rather than a String (which is what your first working example is using)

Need help in transforming this SQL statement to GORM

select
b.security_type,
b.symbol,
b.security_description,
b.trade_date_qty as 'axys_qty',
c.trade_date_qty as 'fidelity_qty',
c.trade_date_qty - b.trade_date_qty as 'qty_diff',
b.cost_basis as 'axys_cost',
c.cost_basis as 'fidelity_cost',
c.cost_basis - b.cost_basis as 'cost_diff'
from
account a
inner join advent_position b on a.fixed_account_number = b.account_number
inner join fidelity_position c on a.fixed_account_number = c.account_number and b.symbol = c.symbol
where
b.account_number = '636296651'
Basically, I have the ff. domains: Account, AdventPosition, FidelityPosition. I haven't set the relationship yet. I'm just wondering if there's a way to replicate the logic above using Criteria or HQL. Forgive me, I'm still new to Grails.
Thank you for any leads on this.
It'd be something close to this:
String hql = '''
select
b.securityType,
b.symbol,
b.securityDescription,
b.tradeDateQty,
c.tradeDateQty,
c.tradeDateQty - b.tradeDateQty,
b.costBasis,
c.costBasis,
c.costBasis - b.costBasis
from
Account a, AdventPosition b, FidelityPosition c
where
a.fixedAccountNumber = b.accountNumber
and a.fixedAccountNumber = c.accountNumber
and b.symbol = c.symbol
and b.accountNumber = :accountNumber
'''
def accountNumber = '636296651'
def results = Account.executeQuery(hql, [accountNumber: accountNumber])
The results will be an ArrayList of Object[], so you can iterate it with something like
for (row in results) {
def securityType = row[0]
def symbol = row[1]
def securityDescription = row[2]
def axys_qty = row[3]
def fidelity_qty = row[4]
def qty_diff = row[5]
def axys_cost = row[6]
def fidelity_cost = row[7]
def cost_diff = row[8]
}
I replaced the hard-coded account number with a named parameter; you can use regular ? like in SQL if you prefer and run 'def results = Account.executeQuery(hql, [accountNumber])', and of course if you intented it to be hard-coded then restore that and don't pass in the 2nd parameter, just run 'def results = Account.executeQuery(hql)'
just sharing the solution that I came up (while waiting for an answer :P) but note that the previous answer is way much better and faster:
def acc = Account.findByFixedAccountNumber('636296651')
List advPos = AdventPosition.findAllByAccountNumber('636296651')
List fidPos = advPos.collect {
FidelityPosition.findAllByAccountNumberAndSymbol('636296651', it.symbol)
}
def item = [:]
def res = []
def limit = advPos.size() - 1
for(i in 0..limit){
item.security_type = advPos[i].securityType
item.symbol = advPos[i].symbol
item.security_description = advPos[i].securityDescription
item.axys_qty = advPos[i].tradeDateQty
item.fidelity_qty = fidPos[i].tradeDateQty
item.qty_diff = item.fidelity_qty - item.axys_qty
item.axys_cost = advPos[i].costBasis
item.fidelity_cost = fidPos[i].costBasis
item.cost_diff = item.fidelity_cost - item.axys_cost
res.add(item)
}

Resources