Created stripe webhook

pull/187/head^2
Matheus Lima 2019-06-25 16:25:15 -03:00
parent 557bda246d
commit 7e72507d6b
5 changed files with 52 additions and 1 deletions

View File

@ -2,6 +2,7 @@ import os
from flask import Flask
from public_api.endpoints.stripe_webhook import StripeWebHookEndpoint
from selene.api import SeleneResponse, selene_api
from selene.api.base_config import get_base_config
from selene.api.public_endpoint import check_oauth_token
@ -146,6 +147,12 @@ public.add_url_rule(
methods=['GET']
)
public.add_url_rule(
'/v1/user/stripe/webhook',
view_func=StripeWebHookEndpoint.as_view('stripe_webhook_api'),
methods=['POST']
)
"""
This is a workaround to allow the API return 401 when we call a non existent path. Use case:
GET /device/{uuid} with empty uuid. Core today uses the 401 to validate if it needs to perform a pairing process

View File

@ -0,0 +1,19 @@
import json
from http import HTTPStatus
from selene.api import PublicEndpoint
from selene.data.account import AccountRepository
class StripeWebHookEndpoint(PublicEndpoint):
def __init__(self):
super(StripeWebHookEndpoint, self).__init__()
def post(self):
event = json.loads(self.request.data)
type = event.get('type')
if type == 'customer.subscription.deleted':
customer = event['data']['object']['customer']
AccountRepository(self.db).end_active_membership(customer)
return '', HTTPStatus.OK

View File

@ -22,7 +22,8 @@ ONE_DAY = 86400
def check_oauth_token():
global_context.url = request.url
exclude_paths = ['/v1/device/code', '/v1/device/activate', '/api/account', '/v1/auth/token', '/v1/auth/callback']
exclude_paths = ['/v1/device/code', '/v1/device/activate', '/api/account', '/v1/auth/token', '/v1/auth/callback',
'/v1/user/stripe/webhook']
exclude = any(request.path.startswith(path) for path in exclude_paths)
if not exclude:
headers = request.headers

View File

@ -300,6 +300,17 @@ class AccountRepository(RepositoryBase):
)
self.cursor.update(db_request)
def end_active_membership(self, customer_id):
db_request = self._build_db_request(
sql_file_name='get_active_membership_by_payment_account_id.sql',
args=dict(payment_account_id=customer_id)
)
db_result = self.cursor.select_one(db_request)
if db_result is not None:
account_membership = AccountMembership(**db_result)
account_membership.end_date = datetime.utcnow()
self.end_membership(account_membership)
def get_active_account_membership(self, account_id) -> AccountMembership:
account_membership = None
db_request = self._build_db_request(

View File

@ -0,0 +1,13 @@
SELECT
acc_mem.id,
mem.type,
LOWER(acc_mem.membership_ts_range)::date start_date,
acc_mem.payment_method,
payment_account_id,
payment_id
FROM
account.account_membership acc_mem
INNER JOIN
account.membership mem ON acc_mem.membership_id = mem.id
WHERE
acc_mem.payment_account_id = %(payment_account_id)s AND UPPER(acc_mem.membership_ts_range) IS NULL