tesla-fleet-api 0.9.10__py3-none-any.whl → 0.9.13__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- tesla_fleet_api/const.py +1 -1
- tesla_fleet_api/vehiclesigned.py +20 -19
- {tesla_fleet_api-0.9.10.dist-info → tesla_fleet_api-0.9.13.dist-info}/METADATA +1 -1
- {tesla_fleet_api-0.9.10.dist-info → tesla_fleet_api-0.9.13.dist-info}/RECORD +7 -7
- {tesla_fleet_api-0.9.10.dist-info → tesla_fleet_api-0.9.13.dist-info}/WHEEL +1 -1
- {tesla_fleet_api-0.9.10.dist-info → tesla_fleet_api-0.9.13.dist-info}/LICENSE +0 -0
- {tesla_fleet_api-0.9.10.dist-info → tesla_fleet_api-0.9.13.dist-info}/top_level.txt +0 -0
tesla_fleet_api/const.py
CHANGED
tesla_fleet_api/vehiclesigned.py
CHANGED
@@ -117,17 +117,13 @@ if TYPE_CHECKING:
|
|
117
117
|
class Session:
|
118
118
|
"""A connect to a domain"""
|
119
119
|
|
120
|
-
key: bytes
|
121
|
-
counter: int
|
122
|
-
epoch: bytes
|
123
|
-
delta: int
|
124
|
-
hmac: bytes
|
125
|
-
publicKey: bytes
|
126
|
-
lock: Lock
|
127
|
-
|
128
120
|
def __init__(self):
|
121
|
+
self.counter: int = 0
|
122
|
+
self.epoch: bytes | None = None
|
123
|
+
self.delta: int = 0
|
124
|
+
self.hmac: bytes | None = None
|
125
|
+
self.publicKey: bytes | None = None
|
129
126
|
self.lock = Lock()
|
130
|
-
self.counter = 0
|
131
127
|
|
132
128
|
def update(self, sessionInfo: SessionInfo, privateKey: ec.EllipticCurvePrivateKey):
|
133
129
|
"""Update the session with new information"""
|
@@ -136,7 +132,7 @@ class Session:
|
|
136
132
|
self.delta = int(time.time()) - sessionInfo.clock_time
|
137
133
|
if (self.publicKey != sessionInfo.publicKey):
|
138
134
|
self.publicKey = sessionInfo.publicKey
|
139
|
-
|
135
|
+
key = hashlib.sha1(
|
140
136
|
privateKey.exchange(
|
141
137
|
ec.ECDH(),
|
142
138
|
ec.EllipticCurvePublicKey.from_encoded_point(
|
@@ -145,11 +141,12 @@ class Session:
|
|
145
141
|
),
|
146
142
|
).digest()[:16]
|
147
143
|
self.hmac = hmac.new(
|
148
|
-
|
144
|
+
key, "authenticated command".encode(), hashlib.sha256
|
149
145
|
).digest()
|
150
146
|
|
151
147
|
def get(self) -> HMAC_Personalized_Signature_Data:
|
152
148
|
"""Sign a command and return session metadata"""
|
149
|
+
assert self.ready, "Session is not ready"
|
153
150
|
self.counter = self.counter+1
|
154
151
|
return HMAC_Personalized_Signature_Data(
|
155
152
|
epoch=self.epoch,
|
@@ -157,6 +154,9 @@ class Session:
|
|
157
154
|
expires_at=int(time.time()) - self.delta + 10,
|
158
155
|
)
|
159
156
|
|
157
|
+
@property
|
158
|
+
def ready(self) -> bool:
|
159
|
+
return self.epoch is not None and self.hmac is not None and self.delta > 0
|
160
160
|
|
161
161
|
class VehicleSigned(VehicleSpecific):
|
162
162
|
"""Class describing the Tesla Fleet API vehicle endpoints and commands for a specific vehicle with command signing."""
|
@@ -181,7 +181,10 @@ class VehicleSigned(VehicleSpecific):
|
|
181
181
|
encoding=Encoding.X962, format=PublicFormat.UncompressedPoint
|
182
182
|
)
|
183
183
|
self._from_destination = randbytes(16)
|
184
|
-
self._sessions = {
|
184
|
+
self._sessions = {
|
185
|
+
Domain.DOMAIN_VEHICLE_SECURITY: Session(),
|
186
|
+
Domain.DOMAIN_INFOTAINMENT: Session(),
|
187
|
+
}
|
185
188
|
|
186
189
|
async def _send(self, msg: RoutableMessage) -> RoutableMessage:
|
187
190
|
"""Serialize a message and send to the signed command endpoint."""
|
@@ -206,11 +209,8 @@ class VehicleSigned(VehicleSpecific):
|
|
206
209
|
|
207
210
|
return resp_msg
|
208
211
|
|
209
|
-
async def _handshake(self, domain: Domain) ->
|
212
|
+
async def _handshake(self, domain: Domain) -> None:
|
210
213
|
"""Perform a handshake with the vehicle."""
|
211
|
-
if session := self._sessions.get(domain):
|
212
|
-
return session
|
213
|
-
self._sessions[domain] = Session()
|
214
214
|
|
215
215
|
LOGGER.debug(f"Handshake with domain {Domain.Name(domain)}")
|
216
216
|
msg = RoutableMessage()
|
@@ -222,8 +222,6 @@ class VehicleSigned(VehicleSpecific):
|
|
222
222
|
# Send handshake message
|
223
223
|
await self._send(msg)
|
224
224
|
|
225
|
-
return self._sessions[domain]
|
226
|
-
|
227
225
|
async def _sendVehicleSecurity(self, command: UnsignedMessage) -> dict[str, Any]:
|
228
226
|
"""Sign and send a message to Infotainment computer."""
|
229
227
|
return await self._sign(DOMAIN_VEHICLE_SECURITY, command.SerializeToString())
|
@@ -238,7 +236,10 @@ class VehicleSigned(VehicleSpecific):
|
|
238
236
|
"""Send a signed message to the vehicle."""
|
239
237
|
LOGGER.debug(f"Sending to domain {Domain.Name(domain)}")
|
240
238
|
|
241
|
-
session =
|
239
|
+
session = self._sessions[domain]
|
240
|
+
if not session.ready:
|
241
|
+
await self._handshake(domain)
|
242
|
+
|
242
243
|
hmac_personalized = session.get()
|
243
244
|
|
244
245
|
msg = RoutableMessage()
|
@@ -1,6 +1,6 @@
|
|
1
1
|
tesla_fleet_api/__init__.py,sha256=BVZUDsfaxT05tAfcMHHWiyFyXwmDOx_wP_IHZBscgho,729
|
2
2
|
tesla_fleet_api/charging.py,sha256=N_mc8axrXj3iduqLj_jCt4Vx86tHqe3xqQT4R1R7HvU,1689
|
3
|
-
tesla_fleet_api/const.py,sha256
|
3
|
+
tesla_fleet_api/const.py,sha256=9OlHiC61VNFMB0ZemPHaqZ4hiC8i7vZlPy5CU2Q59rs,12889
|
4
4
|
tesla_fleet_api/energy.py,sha256=S7D75MPuMVsHgkyUcFfMqjGCLZBM5YVFlWLEHbaX-zw,5957
|
5
5
|
tesla_fleet_api/energyspecific.py,sha256=UfeaGE59aoAa8UhpQCXUi0sOrNCA40xZlqwF73BXTVY,4254
|
6
6
|
tesla_fleet_api/exceptions.py,sha256=qnRWqPJ_5gia4-j3o4mP5OwUuBRtC3SAbZKo-_XSRiI,29729
|
@@ -13,7 +13,7 @@ tesla_fleet_api/teslemetry.py,sha256=_n59RQvJKl82ylLe09bLY_8iyfjz_DHqCdRVsWeif4s
|
|
13
13
|
tesla_fleet_api/tessie.py,sha256=4dBYxe1G2v9JvJGRbb01wXrAmvWT4jOfV4f_VQE_vkE,2302
|
14
14
|
tesla_fleet_api/user.py,sha256=TZE2oh-n5zrhKXmGRuiNL9voKVODD7rBhGE_IObYVGA,1179
|
15
15
|
tesla_fleet_api/vehicle.py,sha256=U1FNWfVut_mqdkkKlcfUlFSiaQ_l1bDABd1NTJJd_aw,35039
|
16
|
-
tesla_fleet_api/vehiclesigned.py,sha256=
|
16
|
+
tesla_fleet_api/vehiclesigned.py,sha256=nYtTKBvNhldh_BzfQBcc64ATS7f8K6Y7OBRJJsI6Qjg,42215
|
17
17
|
tesla_fleet_api/vehiclespecific.py,sha256=IwLoQMmWQrLJPcVBsrvCWvc6Iz4DEjhrKZxtV6QZnTk,22361
|
18
18
|
tesla_fleet_api/pb2/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
19
19
|
tesla_fleet_api/pb2/__init__.pyi,sha256=qFXWNIgl71wB260u-XPzaAwWAHL6krw21q-aXnBtop0,252
|
@@ -35,8 +35,8 @@ tesla_fleet_api/pb2/vcsec_pb2.py,sha256=PDv9TfiXnNs6sQ0D5vBrsSSPinSqu3eBUwvTcG8x
|
|
35
35
|
tesla_fleet_api/pb2/vcsec_pb2.pyi,sha256=cyK1uyRtDjRVqVlyl5uRQYY1RhFlWSJheLg3PGfs-_s,28524
|
36
36
|
tesla_fleet_api/pb2/vehicle_pb2.py,sha256=bqyFJM-1qZ7W9XKREINhYZx8yXAudmq6W8_Pdfkhbkk,44711
|
37
37
|
tesla_fleet_api/pb2/vehicle_pb2.pyi,sha256=sAUW_9aVB8NqJCnhZjXMLfqfePLVZv_7PfSKZKEBaQA,74251
|
38
|
-
tesla_fleet_api-0.9.
|
39
|
-
tesla_fleet_api-0.9.
|
40
|
-
tesla_fleet_api-0.9.
|
41
|
-
tesla_fleet_api-0.9.
|
42
|
-
tesla_fleet_api-0.9.
|
38
|
+
tesla_fleet_api-0.9.13.dist-info/LICENSE,sha256=xx0jnfkXJvxRnG63LTGOxlggYnIysveWIZ6H3PNdCrQ,11357
|
39
|
+
tesla_fleet_api-0.9.13.dist-info/METADATA,sha256=9RtGoU2ztEb3tDQif0eSE9vH3U4ZJ7xZPeQqJpcYi9w,4023
|
40
|
+
tesla_fleet_api-0.9.13.dist-info/WHEEL,sha256=52BFRY2Up02UkjOa29eZOS2VxUrpPORXg1pkohGGUS8,91
|
41
|
+
tesla_fleet_api-0.9.13.dist-info/top_level.txt,sha256=jeNbog_1saXBFrGpom9WyPWmilxsyP3szL_G7JLWQfM,16
|
42
|
+
tesla_fleet_api-0.9.13.dist-info/RECORD,,
|
File without changes
|
File without changes
|