21

I'm building a website using WordPress as a backend, and AngularJS as the frontend. I'm using the WordPress JSON API to get my data to the front-end.

https://wordpress.org/plugins/json-api/

The problem

I'm using AngularJS to get my data from the WordPress JSON API. I have created the following service:

this.getPage = function ( slug ) {
    return $http.get('wordpress/api/get_page/?slug=' + slug)
}

I use this service in my controller to get the current page like this:

HTTPService.getPage('home')
    .success(function ( data ) {
        $scope.page = data.page;
        console.log(arguments);
    })
    .error( function () {
        console.log(arguments);
    })

This is working fine in all browsers, except for Safari on iOS. On Safari on iOS I get the following response when I log the error arguments:

Error response 0?

This is the safari debugger which showed when I connected my iPhone to my Mac. The error response which I get is error code 0..

What I have tried so far

I have set Access-Control-Allow-Origin "*" in the .htaccess file, but this doesn't seem to work. The request is done on the same domain with a relative URL, so I don't think that this is the problem.

So, does anyone know why this is not working on Safari (iOS)?

EDIT

Some extra information as requested:

llui85
  • 177
  • 2
  • 14
koningdavid
  • 7,903
  • 7
  • 35
  • 46
  • The error occurs both on safari iOS7 and safari iOS8 – koningdavid Oct 27 '14 at 12:26
  • Can you post your code to jsfiddle ? – Tyler.z.yang Oct 27 '14 at 12:41
  • Where is the error argument print from exactly? Could you post print of all of the arguments of the error handler (`function(data, status, headers, config)`) or more of your code? You should also check out [this old question](http://stackoverflow.com/questions/17035230/angular-js-breaks-in-safari-but-not-chrome). – Absor Oct 29 '14 at 19:09
  • Can you try it with the URL `/wordpress/api/get_page/?slug=` note the staring `/` and also when using the full url `http://your.server.somewhere.com/wordpress/api/get_page/?slug=` And you migth have a problem with your CORS setup so you can try to add also `Access-Control-Allow-Headers "*"`... – nemesv Oct 29 '14 at 19:38
  • @Absor Logging the arguments does exactly the same.. – koningdavid Oct 29 '14 at 20:02
  • @nemesv I've tried all your suggestions but none of them worked. Access-Control-Allow-Headers "*" is already there. – koningdavid Oct 29 '14 at 20:06
  • Ah yeah sorry, read the original wrong. Have you checked if the server gets the request when you're using safari? – Absor Oct 29 '14 at 20:19
  • I'd really go with [JSON REST API](https://wordpress.org/plugins/json-rest-api/) instead, this one will be merged with the Core at some point in the near future. I don't remember what it was, but had some issues with the plugin JSON API and ended dropping it once and for all... – brasofilo Oct 29 '14 at 21:06
  • 4
    Please show more details about the communication. From the `network` tab please show headers of both request and response + status code of the response. (Btw. I am experiencing a lot of strange misbehaviours of iOS, so would not be very surprised if yours is just another bug.) – artur grzesiak Oct 30 '14 at 08:54
  • @arturgrzesiak Ill post more details later today, thanks – koningdavid Oct 30 '14 at 09:06
  • @arturgrzesiak I have added the details as requested (sorry that its in dutch). – koningdavid Oct 30 '14 at 19:14
  • 1
    A 0 error code means that the request was aborted, timeout or was cancelled. Can't really figure anything else out without seeing the network tab or the error XHR – Cory Danielson Oct 30 '14 at 19:22
  • Yes, you've mentioned that you get `error code 0`, but is there not a message with the error as well? What happens when you make other requests from iOS Safari? e.g.: if you make a request to get the home page of your site, does it also come back with the same error, or does it come back with the homepage, or a different error? – Trolleymusic Nov 01 '14 at 15:19
  • See here for some code on how to make a regular request: http://jsfiddle.net/trolleymusic/uafoyuk4/ – Trolleymusic Nov 01 '14 at 15:32

1 Answers1

22

I'm pretty sure that this is due to the fact that Safari is the only browser that has the policy of blocking "3rd party cookies and other website data" by default. Actually, this issue shouldn't be exclusive of Safari iOS, it should also happen with Safari on your OSX. I'm pretty sure that if it's not happening in your MacBook is because one day you changed the default settings of the "Privacy".

You can try this, open Safari, go to "preferences" and under the tab "Pricacy" check if you have the option: "Block cookies and other website data" set to "From third parties and advertisers". This is the first, and the default option in the modern versions of Safari.

In your MacBook it will look like this:

enter image description here

And in iOS it will look like this:

enter image description here

Just to confirm that this is in fact what's causing your issue: change this setting to "Never", clear the cache and try to reproduce that problem again. I'm quite confident that you won't be able to reproduce it.

Now, if you set it back to "Block cookies and other website data: From third parties and advertisers" and you first clear the cache, you will have that problem again (with either iOS or OSX). After you've confirmed that this is the cause of your problem, set this setting back to "From third parties and advertisers", so that you can reproduce and address the problem with the default settings.

Bare in mind that every time that you want to re-test this issue you will be better off clearing the cache of Safary. Otherwise it could happen that Safari decides that the site serving the API can be trusted and you won't be able to reproduce the issue. So, just to be sure, clear the cache every time that you test this.

I believe that the root of this problem is that Safari wants to make sure that the user has had a direct interaction with the page that it's serving the "3rd party content" before the main page loads that content.

I would need to know more about your project in order to suggest an "optimal" solution. For instance: will the final app be integrated under the same domain as the API? Because if that's the case, you shouldn't have that issue when you go to production. I mean, if the app that you are developing will be hosted under: http://whatever.yourDomain.org and the API is going to be part of that same domain (yourDomain.org), then you shouldn't have that issue at all in production.

On the other hand, if you need to have have the API hosted under a different domain, then you will have to find a way to "trick" Safari. Have a look at this:

And this:

I hope that this helps.

Community
  • 1
  • 1
Josep
  • 12,926
  • 2
  • 42
  • 45
  • 3
    OP wrote: *The request is done on the same domain with a relative URL*, so 3rd party cookies should not be problematic here. – artur grzesiak Nov 04 '14 at 07:17
  • 2
    Changing the setting in iOS and clearing my browser cache actually fixed the problem. Now I can't seem to reproduce the error. And yeah the api is already on the same domain, but the problem occurred on the production site, that's what I still don't understand. – koningdavid Nov 04 '14 at 20:38
  • 2
    Thanks, I'll accept your answer since it fixed the problem! I however still don't really understand how it happened tho, since now I can't reproduce it :p.. I'm sure it's not only me because it happened on someone else her iPhone too. – koningdavid Nov 04 '14 at 20:40
  • @koningdavid at least now you are in the right track. – Josep Nov 04 '14 at 20:40
  • 3
    @koningdavid thanks for accepting the answer. However, I would like to get to the root of the issue. Could you please try to replicate this in "dummy" site so that we can reproduce it? – Josep Nov 04 '14 at 20:45
  • @koningdavid I once experienced a very similar issue, but the API was not inside the same domain, that's a bit odd. However, it's very tricky because once you have change the settings to "Never" and you get rid of the issue it's very difficult to replicate it again. In my case I had to change the settings back to "From third parties and advertisers", clear the cache completely (not only the cookies) and I think that I also had to re-start the browser. – Josep Nov 04 '14 at 20:50