0

I'm following the PayPal REST tutorial here: https://code.tutsplus.com/articles/paypal-integration-part-2-paypal-rest-api--cms-22917

I have this in my controller method (below),I believe it's the redirect line causing the issue, the previous line reaches out to paypal to get an id without issue. payment.GetApprovalUrl() retrieves the url listed in the error message:

public ActionResult CreatePayment()
{
var userId = _userRepository.LoggedInUserId(); 
var cart = _cartRepository.GetCart(userId);
var payment = PayPalRepository.CreatePayment(GetBaseUrl(), 
"sale",cart);
return Redirect(payment.GetApprovalUrl());
}

This action method is called from the paypal button javascript:

payment: function(resolve, reject) {
    // Set up the payment here, when the buyer clicks on the button
    var env = this.props.env;
    var client = this.props.client;

    var CREATE_PAYMENT_URL = 'http://localhost:3259/Payment/CreatePayment';
    return paypal.request.post(CREATE_PAYMENT_URL)
        .then(function (data) {
            console.log('data: ' + data);
            resolve(data.paymentID);
        })
        .catch(function (err) { reject(err); })

The console.log statement never executes, and the browser console shows this error: XMLHttpRequest cannot load https://www.sandbox.paypal.com/cgi-bin/webscr?cmd=_express-checkout&token=EC-7EL20553GB692634H. No 'Access-Control-Allow-Origin' header is present on the requested resource.

I have the controller tagged with an AllowCrossSiteJson attribute (found on stackoverflow, will update with reference to author) as follows:

public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            var ctx = filterContext.RequestContext.HttpContext;
            var origin = ctx.Request.Headers["Origin"];
            var allowOrigin = !string.IsNullOrWhiteSpace(origin) ? origin : "*";
            ctx.Response.AddHeader("Access-Control-Allow-Origin", allowOrigin);
            ctx.Response.AddHeader("Access-Control-Allow-Headers", "*");
            ctx.Response.AddHeader("Access-Control-Allow-Credentials", "true");
            base.OnActionExecuting(filterContext);

        }

What am I doing wrong, or not doing, in order to get by this error?

user1202839
  • 365
  • 1
  • 5
  • 18
  • 1
    The error says the failure is because the response from `https://www.sandbox.paypal.com/cgi-bin/webscr?cmd=_express-checkout&token=EC-7EL20553GB692634H` doesn’t have the `Access-Control-Allow-Origin` response header. No changes you make to your own server-side code will fix that. It doesn’t matter what headers you configure your own server to send—the problem is, Paypal isn’t sending the right headers, and you can’t make Paypal send any other response headers. – sideshowbarker May 01 '17 at 02:42
  • So your choices are to make the request to Paypal from your backend code or set up a CORS proxy https://stackoverflow.com/questions/20035101/no-access-control-allow-origin-header-is-present-on-the-requested-resource/42744707#42744707 – sideshowbarker May 01 '17 at 02:42
  • I must be doing something wrong... this tutorial : https://www.codeproject.com/Articles/870870/Using-Paypal-Rest-API-with-ASP-NET-MVC has the same basic paradigm, and the exact same line of code: return Redirect(paypalRedirectUrl); – user1202839 May 01 '17 at 11:01
  • That tutorial seems to be entirely about server-side ASP.NET MVC config and C# code calling the Paypal API. The error cited in the question is due to frontend JavaScript code calling some Paypal endpoint. So it seems you must have either written some separate frontend JavaScript code or your backend is generating some (and that code is different from the JavaScript snippet in the question, which is instead making a request to `http://localhost:3259/Payment/CreatePayment`). And in the end, your browser is refusing your to let your that frontend JavaScript code access the response from Paypal. – sideshowbarker May 01 '17 at 11:34
  • 1
    I guess the problem might be that the request from your frontend code to `http://localhost:3259/Payment/CreatePayment` is getting redirected to `https://www.sandbox.paypal.com/cgi-bin/webscr?cmd=_express-c‌​heckout&token=EC-7EL‌​20553GB692634H`. Maybe the `return Redirect(payment.GetApprovalUrl());` causes that. If that’s the case I think the server side code assumes the user gets navigated to the Paypal URL and sees the response. But your frontend code seems to be trying to consume to response instead of navigating the user to it. – sideshowbarker May 01 '17 at 11:39
  • Good point, looks like both tutorials are not using the approach of opening paypal in a lightbox in the context of the original site. My client side code was taken from the paypal docs here: https://developer.paypal.com/docs/integration/direct/express-checkout/integration-jsv4/advanced-integration/ – user1202839 May 01 '17 at 11:58

1 Answers1

0

Solution was that server side code should only return the payment.id as json, not the authorization url.

user1202839
  • 365
  • 1
  • 5
  • 18