Caching Grails2.4.2EHCache插件1.0.5过早地退出密钥

Caching Grails2.4.2EHCache插件1.0.5过早地退出密钥,caching,grails,ehcache,Caching,Grails,Ehcache,使用grails2.4.2、cache:1.1.8和cache-ehcache:1.0.5,我发现缓存只包含一个条目。一旦添加了第二个条目,第一个条目就会消失 配置 BuildConfig.groovy: compile ":cache:1.1.8" compile ":cache-ehcache:1.0.5" grails.hibernate.cache.queries = true grails { cache { order = 2000 enabled = tru

使用grails2.4.2、cache:1.1.8和cache-ehcache:1.0.5,我发现缓存只包含一个条目。一旦添加了第二个条目,第一个条目就会消失

配置

BuildConfig.groovy:

compile ":cache:1.1.8"
compile ":cache-ehcache:1.0.5"
grails.hibernate.cache.queries = true

grails {
  cache {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}

grails.cache.clearAtStartup = true

grails.cache.config = {
  cache {
    name 'siteSettings'
  }
  provider {
    updateCheck false
    monitoring 'on'
    dynamicConfig false
  }
  defaultCache {
    maxElementsInMemory 10000
    timeToIdleSeconds 600
    timeToLiveSeconds 600
    overflowToDisk false
    diskPersistent false
    memoryStoreEvictionPolicy 'LRU'
  }
  defaults {
    maxElementsInMemory 10000
    timeToIdleSeconds 600
    timeToLiveSeconds 600
    overflowToDisk false
    diskPersistent false
    memoryStoreEvictionPolicy 'LRU'
  }
}
// wrong
grails {
  cache {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}

// right
grails {
  cache = {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}
Config.groovy:

compile ":cache:1.1.8"
compile ":cache-ehcache:1.0.5"
grails.hibernate.cache.queries = true

grails {
  cache {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}

grails.cache.clearAtStartup = true

grails.cache.config = {
  cache {
    name 'siteSettings'
  }
  provider {
    updateCheck false
    monitoring 'on'
    dynamicConfig false
  }
  defaultCache {
    maxElementsInMemory 10000
    timeToIdleSeconds 600
    timeToLiveSeconds 600
    overflowToDisk false
    diskPersistent false
    memoryStoreEvictionPolicy 'LRU'
  }
  defaults {
    maxElementsInMemory 10000
    timeToIdleSeconds 600
    timeToLiveSeconds 600
    overflowToDisk false
    diskPersistent false
    memoryStoreEvictionPolicy 'LRU'
  }
}
// wrong
grails {
  cache {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}

// right
grails {
  cache = {
    order = 2000
    enabled = true
    clearAtStartup = true
    shared = true
    ehcache {
      reloadable = false
    }
  }
}
SettingsService.groovy中的缓存方法:

@Cacheable(value='siteSettings')
public JSONElement getSiteSettings(Integer site){
  log.info "NOT CACHED for this request (${site})"
记录输出

1) 第一个请求,其中site=229(未缓存任何内容):

2) 第二个请求,其中site=229(缓存容纳229):

3) 第一个请求,其中site=282(缓存容纳229):

4) 第二个请求,其中site=282(缓存容纳282,而不是229):

5) 第三个请求,其中site=229(缓存容纳282,而不是229):

分析

  • 在site=229的第一个请求中,没有缓存任何内容。果然

  • 在site=229的第二个请求中,将缓存键入229的条目。果然

  • 在site=282的第一个请求中,键入229的条目被缓存,但键入282的条目不被缓存。果然

  • 在site=282的第二个请求中,键入282的条目被缓存,但键入229的条目不再被缓存。意外-应缓存两个密钥

  • 在site=229的第三个请求中,键入282的条目仍被缓存,但键入229的条目未被缓存。意外-期望缓存两个密钥(随后,282被逐出,而229被放入,这与观察到的行为相匹配)


  • 我做错了什么?谢谢您的帮助。

    正如我所怀疑的,配置有问题。为了让grails.plugin.cache.ConfigLoader识别Config.groovy中的grails.cache声明是一个闭包,必须有一个等号(=),如下所示:

    Config.groovy:

    compile ":cache:1.1.8"
    compile ":cache-ehcache:1.0.5"
    
    grails.hibernate.cache.queries = true
    
    grails {
      cache {
        order = 2000
        enabled = true
        clearAtStartup = true
        shared = true
        ehcache {
          reloadable = false
        }
      }
    }
    
    grails.cache.clearAtStartup = true
    
    grails.cache.config = {
      cache {
        name 'siteSettings'
      }
      provider {
        updateCheck false
        monitoring 'on'
        dynamicConfig false
      }
      defaultCache {
        maxElementsInMemory 10000
        timeToIdleSeconds 600
        timeToLiveSeconds 600
        overflowToDisk false
        diskPersistent false
        memoryStoreEvictionPolicy 'LRU'
      }
      defaults {
        maxElementsInMemory 10000
        timeToIdleSeconds 600
        timeToLiveSeconds 600
        overflowToDisk false
        diskPersistent false
        memoryStoreEvictionPolicy 'LRU'
      }
    }
    
    // wrong
    grails {
      cache {
        order = 2000
        enabled = true
        clearAtStartup = true
        shared = true
        ehcache {
          reloadable = false
        }
      }
    }
    
    // right
    grails {
      cache = {
        order = 2000
        enabled = true
        clearAtStartup = true
        shared = true
        ehcache {
          reloadable = false
        }
      }
    }
    
    不幸的是,在的文档中没有反映这一点,它显示了一个没有等号的config元素示例

    我在将grails.plugin.cache日志级别设置为“debug”后发现了这一点,当时出现了以下日志输出:

    DEBUG ehcache.EhcacheConfigLoader  - Not including configs from Config.groovy
    

    检查EhcacheConfigLoader的源代码表明,当cache.config设置不是闭包时,会出现此错误消息。将等号添加到配置中使其成为一个闭包,config.groovy中的缓存配置现在被加载,这似乎解决了问题。

    很抱歉,但整个线程都是基于一个错误。通过从grails external config.properties文件中删除一行来修复根本问题,该行似乎掩盖了config.groovy中grails.cache.config的正确定义。外部配置为:

    grails.cache.config.defaultCache.diskStore='java.io.tmpdir'
    

    建议在grails.cache声明中添加等号的修复方法不正确。

    站点设置、缓存密钥和密钥的来源是哪里。。。日志记录语句?你能在Ehcache上添加一个缓存事件监听器,看看你是否能有效地执行逐出操作吗?我实现了一个CacheEventListener,并将输出添加到我的原始帖子中。它似乎验证了我的猜测:每次向缓存中添加一个条目时,前一个条目都会被逐出。Louis,为了回答问题的第一部分,日志记录语句来源于调用可缓存grails服务方法的grails控制器操作。不幸的是,添加的等号导致grails单元测试因以下错误而中断:
    致命错误运行测试:没有方法签名:grails.plugin.cache.ehcache.EhcacheConfigLoader.processConfig()适用于参数类型:(Config$\u run\u closure2\u closure10,null)值:[Config$\u run\u closure2_closure10@283eea2a,null]
    。删除等号后,单元测试工作正常。通过在config.groovy中禁用“test”环境的所有缓存相关配置进行修复:
    if(!environment.current.equals(environment.test)){…