title: How to refresh Volley caching
body: <p>I have enabled Volley caching to view data in offline mode also. JSON data is updated with certain time period. But I can't update new json data with <code>SwipeRefreshLayout</code>. If I removed Volley caching code, data is refreshed. I want to expire old cache and load new cache while clicking refresh button.</p>
  
  <p>I have the following code to refresh.</p>
  
  <pre><code>mSwipeRefreshLayout = (SwipeRefreshLayout) findViewById(R.id.swipeRefreshLayout);
  mSwipeRefreshLayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
      @Override
      public void onRefresh() {
          mExampleList.clear();
          parseJSON();
          mSwipeRefreshLayout.setRefreshing(true);
  
          if (mSwipeRefreshLayout != null &amp;&amp; mSwipeRefreshLayout.isRefreshing()) {
              mSwipeRefreshLayout.setRefreshing(false);  // This hides the spinner
          }
      }
  });
  mExampleList = new ArrayList&lt;&gt;();
  
  mRequestQueue = Volley.newRequestQueue(this);
  parseJSON();
  </code></pre>
  
  <p>Here's how I implemented JSON parsing and enabling volley cache.</p>
  
  <pre><code>private void parseJSON() {
  
      String url = "http://fitandfineindustries.com/newsapi.php";
  
      JsonObjectRequest request = new JsonObjectRequest(Request.Method.GET, url, null,
              new Response.Listener&lt;JSONObject&gt;() {
                  @Override
                  public void onResponse(JSONObject response) {
                      try {
                          JSONArray jsonArray = response.getJSONArray("info");
  
                          for (int i = 0; i &lt; jsonArray.length(); i++) {
                              JSONObject hit = jsonArray.getJSONObject(i);
  
                              String creatorName = hit.getString("heading");
                              String img = hit.getString("img");
                              String imageUrl = img.length() == 0 ? "file:///android_asset/fitandfineindustries.jpg" : "http://fitandfineindustries.com/images/plan/"+img;
  
                              mExampleList.add(new NewsItem(imageUrl, creatorName));
                          }
  
                          mNewsAdapter = new NewsAdapter(AgroActivity.this, mExampleList);
                          mRecyclerView.setAdapter(mNewsAdapter);
                          mNewsAdapter.setOnItemClickListener(AgroActivity.this);
  
                      } catch (JSONException e) {
                          e.printStackTrace();
                      }
                  }
              }, new Response.ErrorListener() {
          @Override
          public void onErrorResponse(VolleyError error) {
              error.printStackTrace();
          }
      }){
          @Override
          protected Response&lt;JSONObject&gt; parseNetworkResponse(NetworkResponse response) {
              try {
                  Cache.Entry cacheEntry = HttpHeaderParser.parseCacheHeaders(response);
                  if (cacheEntry == null) {
                      cacheEntry = new Cache.Entry();
                  }
                  final long cacheHitButRefreshed = 1 * 60 * 1000; // in 1 minutes cache will be hit, but also refreshed on background
                  final long cacheExpired = 24 * 60 * 60 * 1000; // in 24 hours this cache entry expires completely
                  long now = System.currentTimeMillis();
                  final long softExpire = now + cacheHitButRefreshed;
                  final long ttl = now + cacheExpired;
                  cacheEntry.data = response.data;
                  cacheEntry.softTtl = softExpire;
                  cacheEntry.ttl = ttl;
                  String headerValue;
                  headerValue = response.headers.get("Date");
  
                  if (headerValue != null) {
                      cacheEntry.serverDate = HttpHeaderParser.parseDateAsEpoch(headerValue);
                  }
  
                  headerValue = response.headers.get("Last-Modified");
  
                  if (headerValue != null) {
                      cacheEntry.lastModified = HttpHeaderParser.parseDateAsEpoch(headerValue);
                  }
  
                  cacheEntry.responseHeaders = response.headers;
                  final String jsonString = new String(response.data,
                          HttpHeaderParser.parseCharset(response.headers));
                  return Response.success(new JSONObject(jsonString), cacheEntry);
              } catch (UnsupportedEncodingException e) {
                  return Response.error(new ParseError(e));
              } catch (JSONException e) {
                  return Response.error(new ParseError(e));
              }
          }
  
          @Override
          protected void deliverResponse(JSONObject response) {
              super.deliverResponse(response);
          }
  
          @Override
          public void deliverError(VolleyError error) {
              super.deliverError(error);
          }
  
          @Override
          protected VolleyError parseNetworkError(VolleyError volleyError) {
              return super.parseNetworkError(volleyError);
          }
      };
      mRequestQueue.add(request);
  }
  </code></pre>