【问题标题】:how to log runtime errors in grails如何在 grails 中记录运行时错误
【发布时间】:2014-01-16 23:52:47
【问题描述】:

我正在尝试调试一个保存域对象的简单问题。

class AppRideOfferController {
    def index() {}
    def create() {
        if(params.fromAddr && params.toAddr && params.preferences && params.startDate) {
            RideOffer rideOffer = new RideOffer(startLocation: params.fromAddr, endLocation: params.toAddr, startDateTime: new Date(Integer.parseInt((String) params.startDate)));
            rideOffer.save(flush: true);
            //assert(rideOffer.id);
            log.info("blah");
            render(contentType:"text/json") {
                result(blah: rideOffer)
            };
        }
    }
}

在上面的代码中,我只是创建了一个域对象,保存它,然后将它作为 json 返回,其中包含生成的 id。但是,如果我取消注释资产声明,它会失败,因为 id 未设置。

我在控制台上没有收到任何错误,所以我想知道如何将运行时错误堆栈跟踪记录到标准输出上?我的 Config.groovy 的 log4j 配置如下所示:

log4j = {
    // Example of changing the log pattern for the default console appender:
    //
    appenders {
        console name:'stdout', layout:pattern(conversionPattern: '%c{2} %m%n')
    }
    info 'grails.app.controllers',
         'grails.app.controller',
         'grails.app';
    error  'org.codehaus.groovy.grails.web.servlet',        // controllers
           'org.codehaus.groovy.grails.web.pages',          // GSP
           'org.codehaus.groovy.grails.web.sitemesh',       // layouts
           'org.codehaus.groovy.grails.web.mapping.filter', // URL mapping
           'org.codehaus.groovy.grails.web.mapping',        // URL mapping
           'org.codehaus.groovy.grails.commons',            // core / classloading
           'org.codehaus.groovy.grails.plugins',            // plugins
           'org.codehaus.groovy.grails.orm.hibernate',      // hibernate integration
           'org.springframework',
           'org.hibernate',
           'net.sf.ehcache.hibernate'
}

【问题讨论】:

  • 域类长什么样子?您是否在映射中特别提到生成器为assigned

标签: grails log4j


【解决方案1】:

如果您的代码生成运行时错误,您将看到error.gsp 视图。在文档中,您可以看到save() 不会产生异常,而是填充errors,这可能在您的域类验证中发生。如果您generate your controller,您将看到如何处理保存方法中的错误。

类似:

def save() {

  if(!instance.save(flush:true)) {
    //instance fails in validation, you need to respond those errors
    Locale locale = RequestContextUtils.getLocale(request) //Locale of the user
    render([success: false, errors: errorsToMap(instance.errors, locale)]) as JSON
  } else {
    render([success: true, record: instance]) as JSON
  }
}

//just a helper to format the errors output
private List<Map> errorsToMap(Errors errors, Locale locale) {

  def error = []

  for(def err : errors.allErrors) {
    if(err instanceof FieldError) {
      error << [id: err.field, msg: Holders.grailsApplication.mainContext.getMessage(err, locale)]
    }
  }

  return error
}

HoldersJSONRequestContextUtils 默认可用。

【讨论】:

    【解决方案2】:

    尝试替换rideOffer.save(flush: true);与rideOffer.save(刷新:真,failOnError:真);你应该会在控制台中看到错误

    【讨论】:

    • 在处理用户提供的参数时不要使用failOnError:true - 在这样的非异常情况下使用异常(您应该始终期望用户会犯错误或试图破解您的网站)是错误的,而且相当昂贵。
    猜你喜欢
    • 2020-02-11
    • 1970-01-01
    • 2020-11-25
    • 2023-03-25
    • 2018-07-27
    • 1970-01-01
    • 2023-04-08
    • 2017-10-03
    • 2012-09-12
    相关资源
    最近更新 更多