仅当新值不为nil时,带有expires_in的Rails.cache.fetch才会过期 [英] Rails.cache.fetch with expires_in only expire if new value is not nil

查看:83
本文介绍了仅当新值不为nil时,带有expires_in的Rails.cache.fetch才会过期的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想做一个简单的Rails.cache.fetch,约10分钟后使其失效.缓存中填充了来自外部API的json数据.但是,有时无法访问外部API.因此,当缓存过期并尝试获取新的json数据时,缓存内容将变得无效.

I want to do a simple Rails.cache.fetch and expire it after about 10 minutes. The cache gets filled with json data from an external API. However the external API is not reachable sometimes. So when the cache expires and tries to fetch new json data, the cache content gets invalid.

如果fetch_json返回有效数据,如何使Rails.cache.fetch仅使缓存过期?但是,如果缓存收到新的有效数据,则它应在10分钟后过期.

How can I make Rails.cache.fetch ONLY EXPIRE the cache if the fetch_json returns valid data? However the cache should expire after 10 minutes if it receives new valid data.

这是我尝试执行的操作,但是不起作用.此要点中更好的代码突出显示: https://gist.github.com/i42n/6094528

This is how I tried to do it, but it does not work. Better Code highlighting in this Gist: https://gist.github.com/i42n/6094528

有什么技巧可以使我获得这份工作吗?

Any tips how I can get this work?

module ExternalApiHelper

    require 'timeout'
    require 'net/http'

    def self.fetch_json(url)
        begin
            result = Timeout::timeout(2) do # 2 seconds
                # operation that may cause a timeout
                uri = URI.parse(url)
                http = Net::HTTP.new(uri.host, uri.port)
                request = Net::HTTP::Get.new(uri.request_uri)
                response = http.request(request)
                return JSON.parse(response.body)
            end
            return result
        rescue
            # if any error happens in the block above, return empty string
            # this will result in fetch_json_with_cache using the last value in cache
            # as long as no new data arrives
            return ""
        end
    end

    def self.fetch_json_with_cache(url, expire_time)
        cache_backup = Rails.cache.read(url)
        api_data = Rails.cache.fetch(url, :expires_in => expire_time) do
            new_data = fetch_json(url)
            if new_data.blank?
                # if API fetch did not return valid data, return the old cache state
                cache_backup
            else
                new_data
            end
        end
        return api_data
    end

end

推荐答案

解决了这个问题.也许不是最优雅的方法,但是可以工作: https://github.com/ReliveRadio/reliveradio-website /blob/4874cf4158361c73a693e65643d9e7f11333d9d6/app/helpers/external_api_helper.rb

Solved it like this. Maybe not the most elegant way to do it, but works: https://github.com/ReliveRadio/reliveradio-website/blob/4874cf4158361c73a693e65643d9e7f11333d9d6/app/helpers/external_api_helper.rb

这篇关于仅当新值不为nil时,带有expires_in的Rails.cache.fetch才会过期的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆