Skip to content

Commit a51cd1e

Browse files
author
gabino
committed
Add JwtToken resource for generating JWT tokens
1 parent a9c258c commit a51cd1e

File tree

5 files changed

+215
-0
lines changed

5 files changed

+215
-0
lines changed

cuenca/__init__.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@
4242
'WhatsappTransfer',
4343
'configure',
4444
'get_balance',
45+
'JwtToken',
4546
]
4647

4748
from . import http
@@ -65,6 +66,7 @@
6566
FileBatch,
6667
Identity,
6768
IdentityEvent,
69+
JwtToken,
6870
KYCValidation,
6971
KYCVerification,
7072
LimitedWallet,

cuenca/resources/__init__.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838
'WalletTransaction',
3939
'Webhook',
4040
'WhatsappTransfer',
41+
'JwtToken',
4142
]
4243

4344
from .accounts import Account
@@ -59,6 +60,7 @@
5960
from .files import File
6061
from .identities import Identity
6162
from .identity_events import IdentityEvent
63+
from .jwt_tokens import JwtToken
6264
from .kyc_validations import KYCValidation
6365
from .kyc_verifications import KYCVerification
6466
from .limited_wallets import LimitedWallet
@@ -123,6 +125,7 @@
123125
WhatsappTransfer,
124126
Webhook,
125127
Platform,
128+
JwtToken,
126129
]
127130
for resource_cls in resource_classes:
128131
RESOURCES[resource_cls._resource] = resource_cls # type: ignore

cuenca/resources/jwt_tokens.py

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
import datetime as dt
2+
from typing import Annotated, ClassVar
3+
4+
from cuenca_validations.types import Metadata
5+
from pydantic import ConfigDict
6+
7+
from ..http import Session, session as global_session
8+
from .base import Creatable
9+
10+
11+
class JwtToken(Creatable):
12+
_resource: ClassVar = 'token'
13+
14+
id: Annotated[str, Metadata(sensitive=True, log_chars=4)]
15+
token: Annotated[str, Metadata(sensitive=True, log_chars=4)]
16+
created_at: dt.datetime
17+
api_key_uri: str
18+
19+
model_config = ConfigDict(
20+
json_schema_extra={
21+
'example': {
22+
'id': (
23+
'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE3MzgzNjI'
24+
'4NzcsImlhdCI6MTczNzc1ODA3Nywic3ViIjoiQUtzY3p5N3RzaVJkMkl'
25+
'iakxfbllGb2xRIiwidWlkIjoiNjRiZmQ0OTItZGFhMy0xMWVmLWEyMWU'
26+
'tMGE1OGE5ZmVhYzAyIn0.Er8kDsw4rtGkwAXpEgUhwyXFiBjYlwDVTGF'
27+
'tYW7o0go'
28+
),
29+
'token': (
30+
'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE3MzgzNjI'
31+
'4NzcsImlhdCI6MTczNzc1ODA3Nywic3ViIjoiQUtzY3p5N3RzaVJkMkl'
32+
'iakxfbllGb2xRIiwidWlkIjoiNjRiZmQ0OTItZGFhMy0xMWVmLWEyMWU'
33+
'tMGE1OGE5ZmVhYzAyIn0.Er8kDsw4rtGkwAXpEgUhwyXFiBjYlwDVTGF'
34+
'tYW7o0go'
35+
),
36+
'created_at': '2025-01-24T22:34:37.659667',
37+
'api_key_uri': '/api_key/AKsczy7tsiRd2IbjL_nYFolQ',
38+
}
39+
}
40+
)
41+
42+
@classmethod
43+
def create(cls, session: Session = global_session) -> 'JwtToken':
44+
return cls._create(session=session)
Lines changed: 138 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,138 @@
1+
interactions:
2+
- request:
3+
body: '{"password": "111111"}'
4+
headers:
5+
Authorization:
6+
- DUMMY
7+
Content-Length:
8+
- '26'
9+
Content-Type:
10+
- application/json
11+
User-Agent:
12+
- cuenca-python/2.0.1
13+
X-Cuenca-Api-Version:
14+
- '2020-03-19'
15+
method: POST
16+
uri: https://sandbox.cuenca.com/user_logins
17+
response:
18+
body:
19+
string: '{"success":true,"id":"ULm7x8e0hfQYyUWwM3ysqgTw","last_login_at":"2025-01-27T22:50:04.745000Z"}'
20+
headers:
21+
Connection:
22+
- keep-alive
23+
Content-Length:
24+
- '94'
25+
Content-Type:
26+
- application/json
27+
Date:
28+
- Mon, 27 Jan 2025 23:08:55 GMT
29+
X-Request-Time:
30+
- 'value: 0.421'
31+
x-amz-apigw-id:
32+
- FEfBLEMtCYcEKuQ=
33+
x-amzn-Remapped-Connection:
34+
- keep-alive
35+
x-amzn-Remapped-Content-Length:
36+
- '94'
37+
x-amzn-Remapped-Date:
38+
- Mon, 27 Jan 2025 23:08:55 GMT
39+
x-amzn-Remapped-Server:
40+
- nginx/1.26.2
41+
x-amzn-RequestId:
42+
- 855b6c10-2e41-4b1f-b0fe-6030bd4e0032
43+
status:
44+
code: 201
45+
message: Created
46+
- request:
47+
body: '{}'
48+
headers:
49+
Authorization:
50+
- DUMMY
51+
Content-Length:
52+
- '2'
53+
Content-Type:
54+
- application/json
55+
User-Agent:
56+
- cuenca-python/2.0.1
57+
X-Cuenca-Api-Version:
58+
- '2020-03-19'
59+
X-Cuenca-LoginId:
60+
- ULm7x8e0hfQYyUWwM3ysqgTw
61+
method: POST
62+
uri: https://sandbox.cuenca.com/login_tokens
63+
response:
64+
body:
65+
string: '{"id":"LTqXrT9Z64S329W0D-uJKwmQ"}'
66+
headers:
67+
Connection:
68+
- keep-alive
69+
Content-Length:
70+
- '33'
71+
Content-Type:
72+
- application/json
73+
Date:
74+
- Mon, 27 Jan 2025 23:08:56 GMT
75+
X-Request-Time:
76+
- 'value: 0.202'
77+
x-amz-apigw-id:
78+
- FEfBSG6ZCYcEPMg=
79+
x-amzn-Remapped-Connection:
80+
- keep-alive
81+
x-amzn-Remapped-Content-Length:
82+
- '33'
83+
x-amzn-Remapped-Date:
84+
- Mon, 27 Jan 2025 23:08:56 GMT
85+
x-amzn-Remapped-Server:
86+
- nginx/1.26.2
87+
x-amzn-RequestId:
88+
- 7876a2df-cbdc-40f5-b2b8-c4dcfcdc2d23
89+
status:
90+
code: 201
91+
message: Created
92+
- request:
93+
body: '{}'
94+
headers:
95+
Authorization:
96+
- DUMMY
97+
Content-Length:
98+
- '2'
99+
Content-Type:
100+
- application/json
101+
User-Agent:
102+
- cuenca-python/2.0.1
103+
X-Cuenca-Api-Version:
104+
- '2020-03-19'
105+
X-Cuenca-LoginToken:
106+
- LTqXrT9Z64S329W0D-uJKwmQ
107+
method: POST
108+
uri: https://sandbox.cuenca.com/token
109+
response:
110+
body:
111+
string: '{"id":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3Mzg2MjQxMzYsImlhdCI6MTczODAxOTMzNiwic3ViIjoiQUsyTDh6Y0x2YlRJR1ZsQXdndm9LX1dnIiwidWlkIjoiYWYxM2JmZDgtZGQwMy0xMWVmLThkN2MtMGE1OGE5ZmVhYzAyIn0.tpCxBTcKGWvuRUsKmo7a7IcofgrhVmxIIEiaDBRbAhY","token":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3Mzg2MjQxMzYsImlhdCI6MTczODAxOTMzNiwic3ViIjoiQUsyTDh6Y0x2YlRJR1ZsQXdndm9LX1dnIiwidWlkIjoiYWYxM2JmZDgtZGQwMy0xMWVmLThkN2MtMGE1OGE5ZmVhYzAyIn0.tpCxBTcKGWvuRUsKmo7a7IcofgrhVmxIIEiaDBRbAhY","created_at":"2025-01-27T23:08:56.372428","api_key_uri":"/api_key/AK2L8zcLvbTIGVlAwgvoK_Wg"}'
112+
headers:
113+
Connection:
114+
- keep-alive
115+
Content-Length:
116+
- '576'
117+
Content-Type:
118+
- application/json
119+
Date:
120+
- Mon, 27 Jan 2025 23:08:56 GMT
121+
X-Request-Time:
122+
- 'value: 0.104'
123+
x-amz-apigw-id:
124+
- FEfBWHrtiYcEAJA=
125+
x-amzn-Remapped-Connection:
126+
- keep-alive
127+
x-amzn-Remapped-Content-Length:
128+
- '576'
129+
x-amzn-Remapped-Date:
130+
- Mon, 27 Jan 2025 23:08:56 GMT
131+
x-amzn-Remapped-Server:
132+
- nginx/1.26.2
133+
x-amzn-RequestId:
134+
- 79544974-46c4-4003-a548-48731d96f703
135+
status:
136+
code: 201
137+
message: Created
138+
version: 1

tests/resources/test_jwt_tokens.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import pytest
2+
3+
from cuenca import JwtToken, LoginToken, UserLogin
4+
from cuenca.http.client import Session
5+
6+
7+
@pytest.fixture(scope='function')
8+
def session():
9+
session = Session()
10+
session.configure(
11+
'api_key',
12+
'api_secret',
13+
sandbox=True,
14+
)
15+
return session
16+
17+
18+
@pytest.mark.vcr
19+
def test_jwt_tokens(session):
20+
UserLogin.create('111111', session=session)
21+
login_token = LoginToken.create(session=session)
22+
session.headers.pop(
23+
'X-Cuenca-LoginId',
24+
)
25+
session.configure(login_token=login_token.id)
26+
jwt_token = JwtToken.create(session=session)
27+
assert jwt_token
28+
assert isinstance(jwt_token.token, str)

0 commit comments

Comments
 (0)