habulaj commited on
Commit
50a3d09
·
verified ·
1 Parent(s): 90f8b9c

Update routes/subscription.py

Browse files
Files changed (1) hide show
  1. routes/subscription.py +40 -54
routes/subscription.py CHANGED
@@ -3,10 +3,8 @@ import logging
3
  import json
4
  import os
5
  import requests
6
- import jwt
7
- from fastapi import APIRouter, HTTPException, Request
8
  from pydantic import BaseModel
9
- from fastapi import Header
10
 
11
  router = APIRouter()
12
 
@@ -30,16 +28,32 @@ SUPABASE_HEADERS = {
30
  "Content-Type": "application/json"
31
  }
32
 
33
- class CheckSubscriptionRequest(BaseModel):
34
- user_id: str
35
- stylist_id: str
36
-
37
  class SubscriptionRequest(BaseModel):
38
  id: str # ID do estilista
39
 
40
  class CreatePriceRequest(BaseModel):
41
  amount: int # Valor em centavos (ex: 2500 para R$25,00)
42
- user_id: str # ID do usuário que está criando o preço
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
43
 
44
  @router.post("/create_price")
45
  async def create_price(
@@ -50,33 +64,17 @@ async def create_price(
50
  if not user_token:
51
  raise HTTPException(status_code=401, detail="Missing User-key header")
52
 
53
- # 🔹 Verificação do token JWT no Supabase
54
- supabase_url = f"{SUPABASE_URL}/auth/v1/user"
55
- response = requests.get(supabase_url, headers={"Authorization": f"Bearer {user_token}"})
56
-
57
- if response.status_code != 200:
58
- raise HTTPException(status_code=401, detail="Invalid token")
59
-
60
- user_data = response.json()
61
- user_id = user_data.get("id")
62
- if not user_id:
63
- raise HTTPException(status_code=400, detail="Invalid token: User ID not found")
64
 
65
  amount = data.amount
66
- user_id_request = data.user_id
67
-
68
- if not amount or not user_id_request:
69
- raise HTTPException(status_code=400, detail="Amount and user_id are required")
70
 
71
- # 🔹 Buscar `price_id` do usuário no Supabase
72
- supabase_url = f"{SUPABASE_URL}/rest/v1/User?id=eq.{user_id_request}"
73
- supabase_headers = {
74
- "apikey": SUPABASE_KEY,
75
- "Authorization": f"Bearer {user_token}",
76
- "Content-Type": "application/json"
77
- }
78
 
79
- response = requests.get(supabase_url, headers=supabase_headers)
 
 
80
  user_data = response.json()
81
 
82
  if not user_data:
@@ -85,23 +83,21 @@ async def create_price(
85
  user = user_data[0]
86
  existing_price_id = user.get("price_id")
87
 
88
- # 🔹 Se existir um price_id, tentar atualizar
 
 
89
  if existing_price_id:
90
  try:
91
  stripe.Price.modify(
92
  existing_price_id,
93
  unit_amount=amount,
94
- metadata={"updated_at": "now"} # Apenas para gerar um evento de atualização
95
  )
96
  logger.info(f"✅ Price {existing_price_id} updated successfully.")
97
  updated_price_id = existing_price_id
98
  except stripe.error.InvalidRequestError:
99
  logger.warning(f"⚠️ Failed to update price {existing_price_id}, creating a new one instead.")
100
- updated_price_id = None
101
- else:
102
- updated_price_id = None
103
 
104
- # 🔹 Se não conseguiu atualizar, criar um novo preço
105
  if not updated_price_id:
106
  price = stripe.Price.create(
107
  unit_amount=amount,
@@ -112,7 +108,7 @@ async def create_price(
112
  updated_price_id = price.id
113
  logger.info(f"✅ New price created: {updated_price_id}")
114
 
115
- # 🔹 Pausar todas as assinaturas associadas ao preço antigo
116
  if existing_price_id:
117
  subscriptions = stripe.Subscription.list(status="active")
118
  for sub in subscriptions.auto_paging_iter():
@@ -120,14 +116,13 @@ async def create_price(
120
  stripe.Subscription.modify(sub.id, pause_collection={"behavior": "void"})
121
  logger.info(f"🔹 Subscription {sub.id} paused.")
122
 
123
- # 🔹 Desativar o preço antigo
124
  stripe.Price.modify(existing_price_id, active=False)
125
  logger.info(f"🚫 Price {existing_price_id} deactivated.")
126
 
127
- # 🔹 Atualizar Supabase com o novo `price_id`
128
  update_response = requests.patch(
129
  supabase_url,
130
- headers=supabase_headers,
131
  json={"price_id": updated_price_id}
132
  )
133
 
@@ -149,17 +144,8 @@ def create_checkout_session(
149
  if not user_token:
150
  raise HTTPException(status_code=401, detail="Missing User-key header")
151
 
152
- # 🔹 1. Verificação do token JWT no Supabase
153
- supabase_url = f"{SUPABASE_URL}/auth/v1/user"
154
- response = requests.get(supabase_url, headers={"Authorization": f"Bearer {user_token}"})
155
-
156
- if response.status_code != 200:
157
- raise HTTPException(status_code=401, detail="Invalid token")
158
-
159
- user_data = response.json()
160
- user_id = user_data.get("id")
161
- if not user_id:
162
- raise HTTPException(status_code=400, detail="Invalid token: User ID not found")
163
 
164
  # 🔹 2. Buscar estilista no Supabase
165
  response = requests.get(
@@ -178,7 +164,7 @@ def create_checkout_session(
178
  if not consultations or not stylist_stripe_id:
179
  raise HTTPException(status_code=400, detail="Stylist profile is incomplete")
180
 
181
- # 🔹 3. Buscar o stripe_id e price_id do usuário autenticado
182
  response_user = requests.get(
183
  f"{SUPABASE_URL}/rest/v1/User?id=eq.{user_id}",
184
  headers=SUPABASE_HEADERS
@@ -213,7 +199,7 @@ def create_checkout_session(
213
  ],
214
  metadata={
215
  "stylist_id": stylist_stripe_id,
216
- "user_id": user_id, # 🔹 Continua no metadata para rastreamento interno
217
  "consultations_per_month": consultations
218
  }
219
  )
 
3
  import json
4
  import os
5
  import requests
6
+ from fastapi import APIRouter, HTTPException, Header
 
7
  from pydantic import BaseModel
 
8
 
9
  router = APIRouter()
10
 
 
28
  "Content-Type": "application/json"
29
  }
30
 
 
 
 
 
31
  class SubscriptionRequest(BaseModel):
32
  id: str # ID do estilista
33
 
34
  class CreatePriceRequest(BaseModel):
35
  amount: int # Valor em centavos (ex: 2500 para R$25,00)
36
+
37
+ def verify_token(user_token: str) -> str:
38
+ """
39
+ Valida o token JWT no Supabase e retorna o `user_id` se for válido.
40
+ """
41
+ headers = {
42
+ "Authorization": f"Bearer {user_token}",
43
+ "apikey": SUPABASE_KEY,
44
+ "Content-Type": "application/json"
45
+ }
46
+
47
+ response = requests.get(f"{SUPABASE_URL}/auth/v1/user", headers=headers)
48
+
49
+ if response.status_code == 200:
50
+ user_data = response.json()
51
+ user_id = user_data.get("id")
52
+ if not user_id:
53
+ raise HTTPException(status_code=400, detail="Invalid token: User ID not found")
54
+ return user_id
55
+ else:
56
+ raise HTTPException(status_code=401, detail="Invalid or expired token")
57
 
58
  @router.post("/create_price")
59
  async def create_price(
 
64
  if not user_token:
65
  raise HTTPException(status_code=401, detail="Missing User-key header")
66
 
67
+ # 🔹 1. Validar o token e obter `user_id`
68
+ user_id = verify_token(user_token)
 
 
 
 
 
 
 
 
 
69
 
70
  amount = data.amount
 
 
 
 
71
 
72
+ if not amount:
73
+ raise HTTPException(status_code=400, detail="Amount is required")
 
 
 
 
 
74
 
75
+ # 🔹 2. Buscar `price_id` do usuário no Supabase
76
+ supabase_url = f"{SUPABASE_URL}/rest/v1/User?id=eq.{user_id}"
77
+ response = requests.get(supabase_url, headers=SUPABASE_HEADERS)
78
  user_data = response.json()
79
 
80
  if not user_data:
 
83
  user = user_data[0]
84
  existing_price_id = user.get("price_id")
85
 
86
+ # 🔹 3. Atualizar ou criar um novo `price_id`
87
+ updated_price_id = None
88
+
89
  if existing_price_id:
90
  try:
91
  stripe.Price.modify(
92
  existing_price_id,
93
  unit_amount=amount,
94
+ metadata={"updated_at": "now"}
95
  )
96
  logger.info(f"✅ Price {existing_price_id} updated successfully.")
97
  updated_price_id = existing_price_id
98
  except stripe.error.InvalidRequestError:
99
  logger.warning(f"⚠️ Failed to update price {existing_price_id}, creating a new one instead.")
 
 
 
100
 
 
101
  if not updated_price_id:
102
  price = stripe.Price.create(
103
  unit_amount=amount,
 
108
  updated_price_id = price.id
109
  logger.info(f"✅ New price created: {updated_price_id}")
110
 
111
+ # 🔹 4. Pausar assinaturas antigas e desativar o preço antigo
112
  if existing_price_id:
113
  subscriptions = stripe.Subscription.list(status="active")
114
  for sub in subscriptions.auto_paging_iter():
 
116
  stripe.Subscription.modify(sub.id, pause_collection={"behavior": "void"})
117
  logger.info(f"🔹 Subscription {sub.id} paused.")
118
 
 
119
  stripe.Price.modify(existing_price_id, active=False)
120
  logger.info(f"🚫 Price {existing_price_id} deactivated.")
121
 
122
+ # 🔹 5. Atualizar Supabase com o novo `price_id`
123
  update_response = requests.patch(
124
  supabase_url,
125
+ headers=SUPABASE_HEADERS,
126
  json={"price_id": updated_price_id}
127
  )
128
 
 
144
  if not user_token:
145
  raise HTTPException(status_code=401, detail="Missing User-key header")
146
 
147
+ # 🔹 1. Validar o token e obter `user_id`
148
+ user_id = verify_token(user_token)
 
 
 
 
 
 
 
 
 
149
 
150
  # 🔹 2. Buscar estilista no Supabase
151
  response = requests.get(
 
164
  if not consultations or not stylist_stripe_id:
165
  raise HTTPException(status_code=400, detail="Stylist profile is incomplete")
166
 
167
+ # 🔹 3. Buscar `stripe_id` e `price_id` do usuário autenticado
168
  response_user = requests.get(
169
  f"{SUPABASE_URL}/rest/v1/User?id=eq.{user_id}",
170
  headers=SUPABASE_HEADERS
 
199
  ],
200
  metadata={
201
  "stylist_id": stylist_stripe_id,
202
+ "user_id": user_id,
203
  "consultations_per_month": consultations
204
  }
205
  )