Skip to content

Commit

Permalink
replace single contribution API with bulk contribution API
Browse files Browse the repository at this point in the history
  • Loading branch information
thelostone-mc committed Oct 5, 2020
1 parent 1468fcc commit a016e43
Show file tree
Hide file tree
Showing 3 changed files with 104 additions and 87 deletions.
3 changes: 2 additions & 1 deletion app/grants/admin.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,8 @@ class GrantAdmin(GeneralAdmin):
'subscriptions_links', 'contributions_links', 'logo', 'logo_svg', 'image_css',
'link', 'clr_prediction_curve', 'hidden', 'next_clr_calc_date', 'last_clr_calc_date',
'metadata', 'twitter_handle_1', 'twitter_handle_2', 'view_count', 'is_clr_eligible', 'in_active_clrs',
'last_update', 'funding_info', 'twitter_verified', 'twitter_verified_by', 'twitter_verified_at', 'stats_history'
'last_update', 'funding_info', 'twitter_verified', 'twitter_verified_by', 'twitter_verified_at', 'stats_history',
'zcash_payout_address'
]
readonly_fields = [
'logo_svg_asset', 'logo_asset',
Expand Down
14 changes: 7 additions & 7 deletions app/grants/urls.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,12 +20,12 @@
from django.urls import path, re_path

from grants.views import (
add_grant_from_collection, bulk_fund, bulk_grants_for_cart, clr_grants, contribute_to_grant_v1, flag, get_collection, get_collections_list,
get_grant_payload, get_grants, get_replaced_tx, grant_activity, grant_categories, grant_details, grant_fund,
grant_new, grant_new_whitelabel, grants, grants_addr_as_json, grants_bulk_add, grants_by_grant_type,
grants_cart_view, grants_clr, grants_stats_view, invoice, leaderboard, new_matching_partner, profile, quickstart,
remove_grant_from_collection, save_collection, subscription_cancel, toggle_grant_favorite, verify_grant,
zksync_get_interrupt_status, zksync_set_interrupt_status,
add_grant_from_collection, bulk_fund, bulk_grants_for_cart, clr_grants, contribute_to_grants_v1, flag,
get_collection, get_collections_list, get_grant_payload, get_grants, get_replaced_tx, grant_activity,
grant_categories, grant_details, grant_fund, grant_new, grant_new_whitelabel, grants, grants_addr_as_json,
grants_bulk_add, grants_by_grant_type, grants_cart_view, grants_clr, grants_stats_view, invoice, leaderboard,
new_matching_partner, profile, quickstart, remove_grant_from_collection, save_collection, subscription_cancel,
toggle_grant_favorite, verify_grant, zksync_get_interrupt_status, zksync_set_interrupt_status,
)

app_name = 'grants'
Expand Down Expand Up @@ -77,5 +77,5 @@
path('v1/api/collections/<int:collection_id>/grants/add', add_grant_from_collection, name='add_grant'),
path('v1/api/collections/<int:collection_id>/grants/remove', remove_grant_from_collection, name='remove_grant'),
path('v1/api/collections/', get_collections_list, name='get_collection'),
path('v1/api/<int:grant_id>/contribute', contribute_to_grant_v1, name='contribute_to_grant_v1')
path('v1/api/contribute', contribute_to_grants_v1, name='contribute_to_grants_v1')
]
174 changes: 95 additions & 79 deletions app/grants/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -1256,7 +1256,7 @@ def grant_new(request):
if request.method == 'POST':

from grants.utils import add_grant_to_active_clrs

response = {
'status': 400,
'message': 'error: Bad Request. Unable to create grant'
Expand Down Expand Up @@ -2340,7 +2340,7 @@ def add_grant_from_collection(request, collection_id):
@csrf_exempt
@require_POST
# @login_required
def contribute_to_grant_v1(request, grant_id):
def contribute_to_grants_v1(request):

response = {
'status': 400,
Expand All @@ -2366,102 +2366,118 @@ def contribute_to_grant_v1(request, grant_id):
response['message'] = 'error: contribution to a grant is a POST operation'
return JsonResponse(response)

if not grant_id:
response['message'] = 'error: grant_id is mandatory param'
return JsonResponse(response)
request_body = json.loads(request.body.decode("utf-8"))

try:
grant = Grant.objects.get(pk=grant_id)
except Grant.DoesNotExist:
response['message'] = 'error: invalid grant'
contributions = request_body.get('contributions', None)
if not contributions:
response['message'] = 'error: contributions in a mandatory parameter'
return JsonResponse(response)

if grant.link_to_new_grant or not grant.active:
response['message'] = 'error: grant is no longer active'
return JsonResponse(response)

if is_grant_team_member(grant, profile):
response['message'] = 'error: team members cannot contribute to own grant'
return JsonResponse(response)

contributor_address = request.POST.get('contributor_address', None)
if not contributor_address:
response['message'] = 'error: contributor_address is mandatory param'
return JsonResponse(response)
failed_contributions = []

token_symbol = request.POST.get('token_symbol', None)
if not token_symbol:
response['message'] = 'error: token_symbol is mandatory param'
return JsonResponse(response)

amount_per_period = request.POST.get('amount_per_period', None)
if not amount_per_period:
response['message'] = 'error: amount_per_period is mandatory param'
return JsonResponse(response)
for contribution in contributions:

tenant = request.POST.get('tenant', None)
if not tenant:
response['message'] = 'error: tenant is mandatory param'
return JsonResponse(response)
grant_id = contribution.get('grant_id', None)
if not grant_id:
response['message'] = 'error: grant_id is mandatory param'
return JsonResponse(response)

if not tenant in ['ETH', 'ZCASH']:
response['message'] = 'error: tenant chain is not supported.'
return JsonResponse(response)
try:
grant = Grant.objects.get(pk=grant_id)
except Grant.DoesNotExist:
response['message'] = f'error: invalid grant {grant_id}'
return JsonResponse(response)

if grant.link_to_new_grant or not grant.active:
response['message'] = f'error: grant {grant_id} is no longer active'
return JsonResponse(response)

tx_id = request.POST.get('tx_id', None)
comment = request.POST.get('comment', None)
network = grant.network
hide_wallet_address = request.POST.get('hide_wallet_address', None)
if is_grant_team_member(grant, profile):
response['message'] = f'error: team members cannot contribute to own grant {grant_id}'
return JsonResponse(response)

try:
contributor_address = contribution.get('contributor_address', None)
if not contributor_address:
response['message'] = f'error: contributor_address is mandatory param for grant {grant_id}'
return JsonResponse(response)

# step 2 : create 1 time subscription
subscription = Subscription()
subscription.contributor_address = contributor_address
subscription.amount_per_period = amount_per_period
subscription.token_symbol = token_symbol
subscription.contributor_profile = profile
subscription.grant = grant
subscription.comments = comment
subscription.network = network
subscription.tenant = tenant
# recurring payments set to none
subscription.active = False
subscription.real_period_seconds = 0
subscription.frequency = 1
subscription.frequency_unit ='days'
subscription.token_address = ''
subscription.gas_price = 0
subscription.new_approve_tx_id = ''
subscription.split_tx_id = ''
token_symbol = contribution.get('token_symbol', None)
if not token_symbol:
response['message'] = f'error: token_symbol is mandatory param for grant {grant_id}'
return JsonResponse(response)

subscription.error = True # cancel subs so it doesnt try to bill again
subscription.subminer_comments = "skipping subminer bc this is subscriptions aren't supported for this flow"
amount_per_period = contribution.get('amount_per_period', None)
if not amount_per_period:
response['message'] = f'error: amount_per_period is mandatory param for grant {grant_id}'
return JsonResponse(response)

subscription.save()
tenant = contribution.get('tenant', None)
if not tenant:
response['message'] = f'error: tenant is mandatory param for grant {grant_id}'
return JsonResponse(response)

if not tenant in ['ETH', 'ZCASH']:
response['message'] = f'error: tenant chain is not supported for grant {grant_id}'
return JsonResponse(response)

# step 3: create contribution + fire celery
contribution = subscription.create_contribution(tx_id)
sync_payout(contribution)
tx_id = contribution.get('tx_id', None)
comment = contribution.get('comment', None)
network = grant.network
hide_wallet_address = contribution.get('hide_wallet_address', None)

try:

# step 4 : other tasks
if hide_wallet_address and not profile.hide_wallet_address:
profile.hide_wallet_address = hide_wallet_address
profile.save()
# step 2 : create 1 time subscription
subscription = Subscription()
subscription.contributor_address = contributor_address
subscription.amount_per_period = amount_per_period
subscription.token_symbol = token_symbol
subscription.contributor_profile = profile
subscription.grant = grant
subscription.comments = comment
subscription.network = network
subscription.tenant = tenant
# recurring payments set to none
subscription.active = False
subscription.real_period_seconds = 0
subscription.frequency = 1
subscription.frequency_unit ='days'
subscription.token_address = ''
subscription.gas_price = 0
subscription.new_approve_tx_id = ''
subscription.split_tx_id = ''

subscription.error = True # cancel subs so it doesnt try to bill again
subscription.subminer_comments = "skipping subminer as subscriptions aren't supported for this flow"

subscription.save()

# step 3: create contribution + fire celery
contribution = subscription.create_contribution(tx_id)
sync_payout(contribution)


# step 4 : other tasks
if hide_wallet_address and not profile.hide_wallet_address:
profile.hide_wallet_address = hide_wallet_address
profile.save()

except Exception as error:
failed_contributions.append({
'grant_id': grant_id,
'message': f'grant contribution not recorded',
'error': error
})

except Exception as error:
if len(failed_contributions):
response = {
'status': 500,
'message': 'grant contribution not recorded',
'error': error
'failed_contributions': failed_contributions
}
else:
response = {
'status': 204,
'message': 'grant contributions recorded'
}

response = {
'status': 204,
'message': 'grant contribution recorded'
}

return JsonResponse(response)

0 comments on commit a016e43

Please sign in to comment.