ShellRox
ShellRox

Reputation: 2602

HTTP 400 on payout

I've been trying to build Paypal cash out system for my website, I viewed countless Paypal API pages and interpreted all the examples to Python:

import requests
import string
import random
import json
from requests.auth import HTTPBasicAuth

class makePayment(object):
    def __init__(self, paypal_email, subject, amount, note, clientid, secret):
        self.access_token = self.obtain_access_token(clientid, secret) # Successfully obtained access token
        self.headers = {"Content-type": "application/json", "Authorization": "Bearer {0}".format(self.access_token)}
        self.sender_batch_id = self.generate_sender_batch_id() # Randomly generated sender_batch_id in base36 ([A-Z] and [1-9])
        self.payout_form = self.create_payout_form(self.sender_batch_id, paypal_email, subject, amount, note) # Not encoded in JSON, just normal HTML form
        self.response = requests.post("https://api.sandbox.paypal.com/v1/payments/payouts",
                                      data=self.payout_json,
                                      headers=self.headers)

    def httpResponse(self):
        return self.response

    @staticmethod
    def obtain_access_token(clientid, secret):
        headers = {"Accept": "application/json", "Accept-Language": "en_US"}
        response = requests.post("https://api.sandbox.paypal.com/v1/oauth2/token",
                                 auth=HTTPBasicAuth(clientid, secret),
                                 data={"grant_type": "client_credentials"},
                                 headers=headers)
        return dict(response.json()).get("access_token")

    @staticmethod
    def generate_sender_batch_id():
        base36 = str(string.digits + string.ascii_lowercase)
        return "".join([random.choice(base36) for char in range(1, 9)])

    @staticmethod
    def create_payout_form(sender_batch_id, paypal_email, subject, amount, note):
        payout_dict = {
            'sender_batch_header': {
                    'sender_batch_id': sender_batch_id,
                    'email_subject': subject,
            },
            'items': [{
                'recipient_type': 'EMAIL',
                'amount': {
                    'value': amount,
                    'currency': 'USD'
                },
                'receiver': paypal_email,
                'note': note,
                'sender_item_id': '${0} item'.format(amount),
            }]
        }
        return payout_dict

token generator, payout example

I get http error 400 (bad request), before that i've tried encoding data in json and got http error 422 (UNPROCESSABLE ENTITY), maybe json encoding was the proper method?

Take in note that sender_batch_id is randomly generated, since i don't know any other method to obtain it.

What am i doing incorrectly? Is there a possibility that i'm missing some parameters? I think there's some problem with the authentication header. Thanks!

Upvotes: 0

Views: 59

Answers (1)

ddor254
ddor254

Reputation: 1628

most of the times - POST requests that are from type "application/json" need to be sent in a json format :

 response = requests.post("https://api.sandbox.paypal.com/v1/oauth2/token",
                             auth=HTTPBasicAuth(clientid, secret),
                             json={"grant_type": "client_credentials"},
                             headers=headers)

i used

json

instead of

data 

in your POST request

Upvotes: 1

Related Questions