Skip to content

Weird caching issue with our new _request implementation #14

Closed

Description

@michael

@mattpass we've got a crazy crazy caching problem with our current XMLHttpRequest native implementation. I couldn't find out what's exactly happening here.

You need to use the updated github.js that I haven't commited yet because of this bug:

https://gist.github.com/3196019

The error can be reproduced like so:

var repo = github.getRepo("michael", "cmake_cdt7_stalled");

// Triggers GET: https://api.github.com/repos/michael/cmake_cdt7_stalled/git/refs/heads/prose-integration
repo.getRef('obu_cdt7_support', function(err, ref) {
  // Triggers DELETE: https://api.github.com/repos/michael/cmake_cdt7_stalled/git/refs/heads/prose-integration
  repo.deleteRef("heads/obu_cdt7_support", function(err) {
    // For some weired reason the delete request doesn't get started, request inspection in chrome reveals
    // it just returns the content from the previous GET request (from cache)
  });
});

That's what the request log looks like for the DELETE request. Expected is a 204 no-content (not from cache) that actually removes the ref but we get a 200 OK (from cache). Seems like the variation of the method (GET vs. DELETE) is not considered for the caching mechanism.

Request URL:https://api.github.com/repos/michael/cmake_cdt7_stalled/git/refs/heads/prose-integration
Request Method:DELETE
Status Code:200 OK (from cache)
Request Payload
{"user":"michael","name":"cmake_cdt7_stalled"}

Activity

  1. michael commented on Jul 29, 2012

    @michael
    CollaboratorAuthor

    @mattpass

    Can't be sure but maybe jquery is adding an anti-cache fragment to the url to solve this issue... ?

    https://github.com/jquery/jquery/blob/master/src/ajax.js#L632

    Did I mention how much I hate HTTP? Oh and caching. ;)

    Maybe I should just bring back jQuery... this thing is blocking a feature unfortunately.. and I've spent 3 hours of debugging last Friday. :(

  2. mattpass commented on Jul 29, 2012

    @mattpass
    Collaborator

    Mmm. Does this actually work with the jQuery AJAX version?

    I'd approach this scientifically by testing the sam operagion 5 times in a row using XHR method and then 5 times in a row using jQuery method.

    If you get odd results with XHR but the jQuery method works fine every time I'd look at why that is.

    First step is confirm that I reckon.

  3. mattpass commented on Jul 29, 2012

    @mattpass
    Collaborator

    Something else I noticed is you're initialising 2 functions on the same line, ie the del func nested inside the initialisation of the get func. I'm not 100% sure if I've got this right, but doing it this way may be starting them both at the same time and under the same ref ID?

    Side note: The xhr.open line has 2 params - for the method & URL. It does actually take a 3rd param for async behaviour or not via a true/false value. I've omitted this to go with the default of true, so it's not going to wait for a response and plough ahead with more code while a response is due to come back.

    So you have 2 xhr calls which may be triggered at the same time and because it's using async, the get call certainly isn't going to wait for a response from the del call and the responses may get lumped into the same ref ID.

    Sounds possible?

    What happens if you run them independently of each other and only do the get call when we have a response from the del call?

  4. michael commented on Jul 30, 2012

    @michael
    CollaboratorAuthor

    Mhh i think it shouldn't... The first call waits until the response is there.. then the second thing gets called. But let me double check. I'll also get in place a jquery $.ajax-based _request version so I can test the differences...

  5. michael commented on Jul 30, 2012

    @michael
    CollaboratorAuthor

    https://developer.mozilla.org/en/using_xmlhttprequest

    Read: Bypassing the cache

    Man, this explains why a thing like jQuery makes sense.

  6. mattpass commented on Jul 30, 2012

    @mattpass
    Collaborator

    Did not know Gecko uses the cache by default. Wonder if other browsers do too? I'd go with the timestamp idea to make it x-browser, which is what jQuery appears to do.

    Maybe something like this would work to add a timestamp with a random number appended and make URLs different therefore avoiding the cache:

    var rand = +new Date + Math.floor(Math.random()*1e20);
    url += url.indexOf('?') ? '&' : '?';
    url += 'rand='+rand;
    
  7. michael commented on Jul 30, 2012

    @michael
    CollaboratorAuthor

    Yeah, I'm going with that:

          function getURL() {
            var url = API_URL + path;
            return url + ((/\?/).test(url) ? "&" : "?") + (new Date()).getTime();
          }
    

    works.

  8. mattpass commented on Jul 30, 2012

    @mattpass
    Collaborator

    Ah good. So this solves the problem then?

  9. michael commented on Jul 30, 2012

    @michael
    CollaboratorAuthor

    Yeah. It does. Not quite happy about adding all those timestamps, but that's the only safe way it seems.

    Why can't browser's caching implementations not just consider the combination of method + url for uniqueness? Would save millions of people headaches. ;)

  10. mattpass commented on Jul 30, 2012

    @mattpass
    Collaborator

    Or better still not cache at all. ;D

  11. michael commented on Jul 30, 2012

    @michael
    CollaboratorAuthor

    Yeah. Always when I get cached data I feel kind of fooled. And with a reason! ;)

  12. added a commit that references this issue on Aug 23, 2014
  13. added 2 commits that reference this issue on Oct 23, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions