dfindexeddb 20241105__py3-none-any.whl → 20251109__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.
Files changed (33) hide show
  1. dfindexeddb/indexeddb/chromium/blink.py +116 -74
  2. dfindexeddb/indexeddb/chromium/definitions.py +148 -125
  3. dfindexeddb/indexeddb/chromium/record.py +426 -324
  4. dfindexeddb/indexeddb/chromium/v8.py +100 -78
  5. dfindexeddb/indexeddb/cli.py +122 -118
  6. dfindexeddb/indexeddb/firefox/definitions.py +7 -4
  7. dfindexeddb/indexeddb/firefox/gecko.py +98 -74
  8. dfindexeddb/indexeddb/firefox/record.py +66 -24
  9. dfindexeddb/indexeddb/safari/definitions.py +5 -3
  10. dfindexeddb/indexeddb/safari/record.py +68 -51
  11. dfindexeddb/indexeddb/safari/webkit.py +85 -71
  12. dfindexeddb/indexeddb/types.py +4 -1
  13. dfindexeddb/leveldb/cli.py +146 -138
  14. dfindexeddb/leveldb/definitions.py +6 -2
  15. dfindexeddb/leveldb/descriptor.py +70 -56
  16. dfindexeddb/leveldb/ldb.py +39 -33
  17. dfindexeddb/leveldb/log.py +41 -30
  18. dfindexeddb/leveldb/plugins/chrome_notifications.py +30 -18
  19. dfindexeddb/leveldb/plugins/interface.py +5 -6
  20. dfindexeddb/leveldb/plugins/manager.py +10 -9
  21. dfindexeddb/leveldb/record.py +71 -62
  22. dfindexeddb/leveldb/utils.py +21 -13
  23. dfindexeddb/utils.py +36 -31
  24. dfindexeddb/version.py +2 -2
  25. dfindexeddb-20251109.dist-info/METADATA +222 -0
  26. dfindexeddb-20251109.dist-info/RECORD +40 -0
  27. {dfindexeddb-20241105.dist-info → dfindexeddb-20251109.dist-info}/WHEEL +1 -1
  28. dfindexeddb-20241105.dist-info/AUTHORS +0 -12
  29. dfindexeddb-20241105.dist-info/METADATA +0 -424
  30. dfindexeddb-20241105.dist-info/RECORD +0 -41
  31. {dfindexeddb-20241105.dist-info → dfindexeddb-20251109.dist-info}/entry_points.txt +0 -0
  32. {dfindexeddb-20241105.dist-info → dfindexeddb-20251109.dist-info/licenses}/LICENSE +0 -0
  33. {dfindexeddb-20241105.dist-info → dfindexeddb-20251109.dist-info}/top_level.txt +0 -0
@@ -14,15 +14,15 @@
14
14
  # limitations under the License.
15
15
  """Parsers for blink javascript serialized objects."""
16
16
  from __future__ import annotations
17
- from dataclasses import dataclass
17
+
18
18
  import io
19
+ from dataclasses import dataclass
19
20
  from typing import Any, Optional, Union
20
21
 
21
- from dfindexeddb import errors
22
- from dfindexeddb import utils
23
- from dfindexeddb.indexeddb.chromium import definitions
24
- from dfindexeddb.indexeddb.chromium import v8
22
+ import snappy
25
23
 
24
+ from dfindexeddb import errors, utils
25
+ from dfindexeddb.indexeddb.chromium import definitions, v8
26
26
 
27
27
  _MS_PER_SECOND = 1000
28
28
 
@@ -34,12 +34,14 @@ class AudioData:
34
34
  Attributes:
35
35
  audio_frame_index: the Audio Frame index.
36
36
  """
37
+
37
38
  audio_frame_index: int
38
39
 
39
40
 
40
41
  @dataclass
41
42
  class BaseIndex:
42
43
  """A base index class."""
44
+
43
45
  index: int
44
46
 
45
47
 
@@ -57,6 +59,7 @@ class Blob:
57
59
  type: the type of the Blob.
58
60
  size: the size of the Blob.
59
61
  """
62
+
60
63
  uuid: str
61
64
  type: str
62
65
  size: int
@@ -78,9 +81,11 @@ class CryptoKey:
78
81
  usages: the CryptoKey usage.
79
82
  key_data: the raw key data.
80
83
  """
84
+
81
85
  algorithm_parameters: dict[str, Any]
82
86
  key_type: Union[
83
- definitions.WebCryptoKeyType, definitions.AsymmetricCryptoKeyType]
87
+ definitions.WebCryptoKeyType, definitions.AsymmetricCryptoKeyType
88
+ ]
84
89
  extractable: bool
85
90
  usages: definitions.CryptoKeyUsage
86
91
  key_data: bytes
@@ -95,6 +100,7 @@ class DOMException:
95
100
  message: the message.
96
101
  stack_unused: the stack unused.
97
102
  """
103
+
98
104
  name: str
99
105
  message: str
100
106
  stack_unused: str
@@ -109,6 +115,7 @@ class DOMFileSystem:
109
115
  name: the name.
110
116
  root_url: the root URL.
111
117
  """
118
+
112
119
  raw_type: int
113
120
  name: str
114
121
  root_url: str
@@ -121,6 +128,7 @@ class DOMMatrix2D:
121
128
  Attributes:
122
129
  values: the values.
123
130
  """
131
+
124
132
  values: list[float]
125
133
 
126
134
 
@@ -136,6 +144,7 @@ class DOMMatrix:
136
144
  Attributes:
137
145
  values: the values.
138
146
  """
147
+
139
148
  values: list[float]
140
149
 
141
150
 
@@ -154,6 +163,7 @@ class DOMPoint:
154
163
  z: the Z coordinate.
155
164
  w: the W coordinate.
156
165
  """
166
+
157
167
  x: float
158
168
  y: float
159
169
  z: float
@@ -175,6 +185,7 @@ class DOMQuad:
175
185
  p3: the third point.
176
186
  p4: the fourth point.
177
187
  """
188
+
178
189
  p1: DOMPoint
179
190
  p2: DOMPoint
180
191
  p3: DOMPoint
@@ -191,6 +202,7 @@ class DOMRect:
191
202
  width: the width.
192
203
  height: the height.
193
204
  """
205
+
194
206
  x: float
195
207
  y: float
196
208
  width: float
@@ -227,6 +239,7 @@ class File:
227
239
  last_modified_ms: the file last modified in milliseconds.
228
240
  is_user_visible: True if the file is user visible.
229
241
  """
242
+
230
243
  path: str
231
244
  name: Optional[str]
232
245
  relative_path: Optional[str]
@@ -250,6 +263,7 @@ class FileList:
250
263
  Attributes:
251
264
  files: the list of files.
252
265
  """
266
+
253
267
  files: list[File]
254
268
 
255
269
 
@@ -260,6 +274,7 @@ class FileListIndex:
260
274
  Attributes:
261
275
  file_indexes: the list of file indexes.
262
276
  """
277
+
263
278
  file_indexes: list[FileIndex]
264
279
 
265
280
 
@@ -271,6 +286,7 @@ class FileSystemHandle:
271
286
  name: the file system handle name.
272
287
  token_index: the file system token index.
273
288
  """
289
+
274
290
  name: str
275
291
  token_index: int
276
292
 
@@ -323,6 +339,7 @@ class TransformStreamTransfer(BaseIndex):
323
339
  @dataclass
324
340
  class OffscreenCanvasTransfer:
325
341
  """A Javascript Offscreen Canvas Transfer."""
342
+
326
343
  width: int
327
344
  height: int
328
345
  canvas_id: int
@@ -339,6 +356,7 @@ class UnguessableToken:
339
356
  high: the high part.
340
357
  low: the low part.
341
358
  """
359
+
342
360
  high: int
343
361
  low: int
344
362
 
@@ -357,17 +375,20 @@ class V8ScriptValueDecoder:
357
375
  value.
358
376
  version (int): the blink version.
359
377
  """
378
+
360
379
  _MIN_VERSION_FOR_SEPARATE_ENVELOPE = 16
361
380
 
362
381
  # As defined in trailer_reader.h
363
382
  _MIN_WIRE_FORMAT_VERSION = 21
364
383
 
365
384
  def __init__(self, raw_data: bytes):
366
- self.deserializer = None
367
385
  self.raw_data = raw_data
386
+ self.deserializer: v8.ValueDeserializer = v8.ValueDeserializer(
387
+ io.BytesIO(self.raw_data), delegate=self
388
+ )
368
389
  self.version = 0
369
- self.trailer_offset = None
370
- self.trailer_size = None
390
+ self.trailer_offset: int | None = None
391
+ self.trailer_size: int | None = None
371
392
 
372
393
  def _ReadVersionEnvelope(self) -> int:
373
394
  """Reads the Blink version envelope.
@@ -392,14 +413,17 @@ class V8ScriptValueDecoder:
392
413
 
393
414
  if self.version >= self._MIN_WIRE_FORMAT_VERSION:
394
415
  _, trailer_offset_tag = decoder.DecodeUint8()
395
- if (trailer_offset_tag !=
396
- definitions.BlinkSerializationTag.TRAILER_OFFSET):
397
- raise errors.ParserError('Trailer offset not found')
416
+ if trailer_offset_tag != definitions.BlinkSerializationTag.TRAILER_OFFSET:
417
+ raise errors.ParserError("Trailer offset not found")
398
418
  _, self.trailer_offset = decoder.DecodeInt(
399
- byte_count=8, byte_order='big', signed=False)
419
+ byte_count=8, byte_order="big", signed=False
420
+ )
400
421
  _, self.trailer_size = decoder.DecodeInt(
401
- byte_count=4, byte_order='big', signed=False)
402
- trailer_offset_data_size = 1 + 8 + 4 # 1 + sizeof(uint64) + sizeof(uint32)
422
+ byte_count=4, byte_order="big", signed=False
423
+ )
424
+ trailer_offset_data_size = (
425
+ 1 + 8 + 4
426
+ ) # 1 + sizeof(uint64) + sizeof(uint32)
403
427
  consumed_bytes += trailer_offset_data_size
404
428
  if consumed_bytes >= len(self.raw_data):
405
429
  return 0
@@ -417,8 +441,8 @@ class V8ScriptValueDecoder:
417
441
  _, length_bytes = self.deserializer.decoder.DecodeUint32Varint()
418
442
 
419
443
  algorithm_parameters = {
420
- 'id': crypto_key_algorithm_id,
421
- 'length_bits': length_bytes*8
444
+ "id": crypto_key_algorithm_id,
445
+ "length_bits": length_bytes * 8,
422
446
  }
423
447
 
424
448
  return definitions.WebCryptoKeyType.SECRET, algorithm_parameters
@@ -434,14 +458,14 @@ class V8ScriptValueDecoder:
434
458
  crypto_key_algorithm = definitions.CryptoKeyAlgorithm(raw_hash)
435
459
 
436
460
  algorithm_parameters = {
437
- 'id': crypto_key_algorithm,
438
- 'length_bits': length_bytes*8
461
+ "id": crypto_key_algorithm,
462
+ "length_bits": length_bytes * 8,
439
463
  }
440
464
 
441
465
  return definitions.WebCryptoKeyType.SECRET, algorithm_parameters
442
466
 
443
467
  def _ReadRSAHashedKey(
444
- self
468
+ self,
445
469
  ) -> tuple[definitions.AsymmetricCryptoKeyType, dict[str, Any]]:
446
470
  """Reads an RSA Hashed CryptoKey.
447
471
 
@@ -457,23 +481,24 @@ class V8ScriptValueDecoder:
457
481
  _, modulus_length_bits = self.deserializer.decoder.DecodeUint32Varint()
458
482
  _, public_exponent_size = self.deserializer.decoder.DecodeUint32Varint()
459
483
  _, public_exponent_bytes = self.deserializer.decoder.ReadBytes(
460
- count=public_exponent_size)
484
+ count=public_exponent_size
485
+ )
461
486
 
462
487
  _, raw_hash = self.deserializer.decoder.DecodeUint32Varint()
463
488
  hash_algorithm = definitions.CryptoKeyAlgorithm(raw_hash)
464
489
 
465
490
  algorithm_parameters = {
466
- 'id': crypto_key_algorithm,
467
- 'modulus_length_bits': modulus_length_bits,
468
- 'public_exponent_size': public_exponent_size,
469
- 'public_exponent_bytes': public_exponent_bytes,
470
- 'hash': hash_algorithm
491
+ "id": crypto_key_algorithm,
492
+ "modulus_length_bits": modulus_length_bits,
493
+ "public_exponent_size": public_exponent_size,
494
+ "public_exponent_bytes": public_exponent_bytes,
495
+ "hash": hash_algorithm,
471
496
  }
472
497
 
473
498
  return key_type, algorithm_parameters
474
499
 
475
500
  def _ReadECKey(
476
- self
501
+ self,
477
502
  ) -> tuple[definitions.AsymmetricCryptoKeyType, dict[str, Any]]:
478
503
  """Reads an EC Key parameters from the current decoder position.
479
504
 
@@ -490,14 +515,14 @@ class V8ScriptValueDecoder:
490
515
  named_curve_type = definitions.NamedCurve(raw_named_curve)
491
516
 
492
517
  algorithm_parameters = {
493
- 'crypto_key_algorithm': crypto_key_algorithm,
494
- 'named_curve_type': named_curve_type
518
+ "crypto_key_algorithm": crypto_key_algorithm,
519
+ "named_curve_type": named_curve_type,
495
520
  }
496
521
 
497
522
  return key_type, algorithm_parameters
498
523
 
499
524
  def _ReadED25519Key(
500
- self
525
+ self,
501
526
  ) -> tuple[definitions.AsymmetricCryptoKeyType, dict[str, Any]]:
502
527
  """Reads a ED25519 CryptoKey from the current decoder position.
503
528
 
@@ -508,17 +533,14 @@ class V8ScriptValueDecoder:
508
533
  crypto_key_algorithm = definitions.CryptoKeyAlgorithm(raw_id)
509
534
 
510
535
  _, raw_key_type = self.deserializer.decoder.DecodeUint32Varint()
511
- key_type = definitions.AsymmetricCryptoKeyType(
512
- raw_key_type)
536
+ key_type = definitions.AsymmetricCryptoKeyType(raw_key_type)
513
537
 
514
- algorithm_parameters = {
515
- 'crypto_key_algorithm': crypto_key_algorithm
516
- }
538
+ algorithm_parameters = {"crypto_key_algorithm": crypto_key_algorithm}
517
539
 
518
540
  return key_type, algorithm_parameters
519
541
 
520
542
  def ReadNoParamsKey(
521
- self
543
+ self,
522
544
  ) -> tuple[definitions.WebCryptoKeyType, dict[str, Any]]:
523
545
  """Reads a No Params CryptoKey from the current decoder position.
524
546
 
@@ -528,9 +550,7 @@ class V8ScriptValueDecoder:
528
550
  _, raw_id = self.deserializer.decoder.DecodeUint32Varint()
529
551
  crypto_key_algorithm = definitions.CryptoKeyAlgorithm(raw_id)
530
552
 
531
- algorithm_parameters = {
532
- 'crypto_key_algorithm': crypto_key_algorithm
533
- }
553
+ algorithm_parameters = {"crypto_key_algorithm": crypto_key_algorithm}
534
554
 
535
555
  return definitions.WebCryptoKeyType.SECRET, algorithm_parameters
536
556
 
@@ -571,12 +591,15 @@ class V8ScriptValueDecoder:
571
591
  path = self.deserializer.ReadUTF8String()
572
592
  name = self.deserializer.ReadUTF8String() if self.version >= 4 else None
573
593
  relative_path = (
574
- self.deserializer.ReadUTF8String() if self.version >= 4 else None)
594
+ self.deserializer.ReadUTF8String() if self.version >= 4 else None
595
+ )
575
596
  uuid = self.deserializer.ReadUTF8String()
576
597
  file_type = self.deserializer.ReadUTF8String()
577
598
  has_snapshot = (
578
599
  self.deserializer.decoder.DecodeUint32Varint()[1]
579
- if self.version >= 4 else 0)
600
+ if self.version >= 4
601
+ else 0
602
+ )
580
603
 
581
604
  if has_snapshot:
582
605
  _, size = self.deserializer.decoder.DecodeUint64Varint()
@@ -589,7 +612,9 @@ class V8ScriptValueDecoder:
589
612
 
590
613
  is_user_visible = (
591
614
  self.deserializer.decoder.DecodeUint32Varint()[1]
592
- if self.version >= 7 else 1)
615
+ if self.version >= 7
616
+ else 1
617
+ )
593
618
 
594
619
  return File(
595
620
  path=path,
@@ -600,7 +625,8 @@ class V8ScriptValueDecoder:
600
625
  has_snapshot=has_snapshot,
601
626
  size=size,
602
627
  last_modified_ms=last_modified_ms,
603
- is_user_visible=is_user_visible)
628
+ is_user_visible=is_user_visible,
629
+ )
604
630
 
605
631
  def _ReadFileIndex(self) -> Optional[FileIndex]:
606
632
  """Reads a FileIndex from the current position.
@@ -643,18 +669,18 @@ class V8ScriptValueDecoder:
643
669
  file_indexes.append(decoded_file_index)
644
670
  return FileListIndex(file_indexes=file_indexes)
645
671
 
646
- def _ReadImageBitmap(self):
672
+ def _ReadImageBitmap(self) -> None:
647
673
  """Reads an ImageBitmap."""
648
- raise NotImplementedError('V8ScriptValueDecoder._ReadImageBitmap')
674
+ raise NotImplementedError("V8ScriptValueDecoder._ReadImageBitmap")
649
675
 
650
676
  def _ReadImageBitmapTransfer(self) -> ImageBitmapTransfer:
651
677
  """Reads an ImageBitmapTransfer."""
652
678
  _, index = self.deserializer.decoder.DecodeUint32Varint()
653
679
  return ImageBitmapTransfer(index=index)
654
680
 
655
- def _ReadImageData(self):
681
+ def _ReadImageData(self) -> None:
656
682
  """Reads an ImageData from the current position."""
657
- raise NotImplementedError('V8ScriptValueDecoder._ReadImageData')
683
+ raise NotImplementedError("V8ScriptValueDecoder._ReadImageData")
658
684
 
659
685
  def _ReadDOMPoint(self) -> DOMPoint:
660
686
  """Reads a DOMPoint from the current position."""
@@ -726,7 +752,7 @@ class V8ScriptValueDecoder:
726
752
  _, index = self.deserializer.decoder.DecodeUint32Varint()
727
753
  return MojoHandle(index=index)
728
754
 
729
- def _ReadOffscreenCanvasTransfer(self):
755
+ def _ReadOffscreenCanvasTransfer(self) -> OffscreenCanvasTransfer:
730
756
  """Reads a Offscreen Canvas Transfer from the current position."""
731
757
  _, width = self.deserializer.decoder.DecodeUint32Varint()
732
758
  _, height = self.deserializer.decoder.DecodeUint32Varint()
@@ -741,7 +767,8 @@ class V8ScriptValueDecoder:
741
767
  canvas_id=canvas_id,
742
768
  client_id=client_id,
743
769
  sink_id=sink_id,
744
- filter_quality=filter_quality)
770
+ filter_quality=filter_quality,
771
+ )
745
772
 
746
773
  def _ReadReadableStreamTransfer(self) -> ReadableStreamTransfer:
747
774
  """Reads a Readable Stream Transfer from the current position."""
@@ -786,6 +813,10 @@ class V8ScriptValueDecoder:
786
813
  """
787
814
  _, raw_key_byte = self.deserializer.decoder.DecodeUint8()
788
815
  key_byte = definitions.CryptoKeySubTag(raw_key_byte)
816
+ algorithm_parameters: dict[str, Any] = {}
817
+ key_type: Union[
818
+ definitions.WebCryptoKeyType, definitions.AsymmetricCryptoKeyType, None
819
+ ] = None
789
820
  if key_byte == definitions.CryptoKeySubTag.AES_KEY:
790
821
  key_type, algorithm_parameters = self._ReadAESKey()
791
822
  elif key_byte == definitions.CryptoKeySubTag.HMAC_KEY:
@@ -799,7 +830,7 @@ class V8ScriptValueDecoder:
799
830
  elif key_byte == definitions.CryptoKeySubTag.NO_PARAMS_KEY:
800
831
  key_type, algorithm_parameters = self.ReadNoParamsKey()
801
832
  else:
802
- raise errors.ParserError('Unexpected CryptoKeySubTag')
833
+ raise errors.ParserError("Unexpected CryptoKeySubTag")
803
834
 
804
835
  _, raw_usages = self.deserializer.decoder.DecodeUint32Varint()
805
836
  usages = definitions.CryptoKeyUsage(raw_usages)
@@ -814,7 +845,7 @@ class V8ScriptValueDecoder:
814
845
  algorithm_parameters=algorithm_parameters,
815
846
  extractable=extractable,
816
847
  usages=usages,
817
- key_data=key_data
848
+ key_data=key_data,
818
849
  )
819
850
 
820
851
  def _ReadAudioData(self) -> AudioData:
@@ -850,26 +881,26 @@ class V8ScriptValueDecoder:
850
881
  _, index = self.deserializer.decoder.DecodeUint32Varint()
851
882
  return EncodedVideoChunk(index=index)
852
883
 
853
- def _ReadMediaStreamTrack(self):
884
+ def _ReadMediaStreamTrack(self) -> None:
854
885
  """Reads the media stream track from the current position."""
855
- raise NotImplementedError('V8ScriptValueDecoder._ReadMediaStreamTrack')
886
+ raise NotImplementedError("V8ScriptValueDecoder._ReadMediaStreamTrack")
856
887
 
857
- def _ReadCropTarget(self):
888
+ def _ReadCropTarget(self) -> None:
858
889
  """Reads the crop target from the current position."""
859
- raise NotImplementedError('V8ScriptValueDecoder._ReadCropTarget')
890
+ raise NotImplementedError("V8ScriptValueDecoder._ReadCropTarget")
860
891
 
861
- def _ReadRestrictionTarget(self):
892
+ def _ReadRestrictionTarget(self) -> None:
862
893
  """Reads the restriction target from the current position."""
863
- raise NotImplementedError('V8ScriptValueDecoder._ReadRestrictionTarget')
894
+ raise NotImplementedError("V8ScriptValueDecoder._ReadRestrictionTarget")
864
895
 
865
896
  def _ReadMediaSourceHandle(self) -> MediaSourceHandle:
866
897
  """Reads the media source handle from the current position."""
867
898
  _, index = self.deserializer.decoder.DecodeUint32Varint()
868
899
  return MediaSourceHandle(index=index)
869
900
 
870
- def _ReadFencedFrameConfig(self):
901
+ def _ReadFencedFrameConfig(self) -> None:
871
902
  """Reads the fenced frame target from the current position."""
872
- raise NotImplementedError('V8ScriptValueDecoder._ReadFencedFrameConfig')
903
+ raise NotImplementedError("V8ScriptValueDecoder._ReadFencedFrameConfig")
873
904
 
874
905
  def ReadTag(self) -> definitions.BlinkSerializationTag:
875
906
  """Reads a blink serialization tag from the current position.
@@ -886,7 +917,8 @@ class V8ScriptValueDecoder:
886
917
  except ValueError as err:
887
918
  offset = self.deserializer.decoder.stream.tell()
888
919
  raise errors.ParserError(
889
- f'Invalid blink tag encountered at offset {offset}') from err
920
+ f"Invalid blink tag encountered at offset {offset}"
921
+ ) from err
890
922
 
891
923
  def ReadHostObject(self) -> Any:
892
924
  """Reads a host object from the current position.
@@ -895,7 +927,7 @@ class V8ScriptValueDecoder:
895
927
  The Host Object.
896
928
  """
897
929
  tag = self.ReadTag()
898
- dom_object = None
930
+ dom_object: Any = None
899
931
 
900
932
  # V8ScriptValueDeserializer
901
933
  if tag == definitions.BlinkSerializationTag.BLOB:
@@ -911,14 +943,14 @@ class V8ScriptValueDecoder:
911
943
  elif tag == definitions.BlinkSerializationTag.FILE_LIST_INDEX:
912
944
  dom_object = self._ReadFileListIndex()
913
945
  elif tag == definitions.BlinkSerializationTag.IMAGE_BITMAP:
914
- dom_object = self._ReadImageBitmap()
946
+ self._ReadImageBitmap()
915
947
  elif tag == definitions.BlinkSerializationTag.IMAGE_BITMAP_TRANSFER:
916
948
  dom_object = self._ReadImageBitmapTransfer()
917
949
  elif tag == definitions.BlinkSerializationTag.IMAGE_DATA:
918
- dom_object = self._ReadImageData()
950
+ self._ReadImageData()
919
951
  elif tag == definitions.BlinkSerializationTag.DOM_POINT:
920
952
  dom_object = self._ReadDOMPoint()
921
- elif tag == definitions.BlinkSerializationTag.DOM_POINT_READ_ONLY:
953
+ elif tag == definitions.BlinkSerializationTag.DOM_POINT_READ_ONLY:
922
954
  dom_object = self._ReadDOMPointReadOnly()
923
955
  elif tag == definitions.BlinkSerializationTag.DOM_RECT:
924
956
  dom_object = self._ReadDOMRect()
@@ -969,15 +1001,15 @@ class V8ScriptValueDecoder:
969
1001
  elif tag == definitions.BlinkSerializationTag.ENCODED_VIDEO_CHUNK:
970
1002
  dom_object = self._ReadEncodedVideoChunk()
971
1003
  elif tag == definitions.BlinkSerializationTag.MEDIA_STREAM_TRACK:
972
- dom_object = self._ReadMediaStreamTrack()
1004
+ self._ReadMediaStreamTrack()
973
1005
  elif tag == definitions.BlinkSerializationTag.CROP_TARGET:
974
- dom_object = self._ReadCropTarget()
1006
+ self._ReadCropTarget()
975
1007
  elif tag == definitions.BlinkSerializationTag.RESTRICTION_TARGET:
976
- dom_object = self._ReadRestrictionTarget()
1008
+ self._ReadRestrictionTarget()
977
1009
  elif tag == definitions.BlinkSerializationTag.MEDIA_SOURCE_HANDLE:
978
1010
  dom_object = self._ReadMediaSourceHandle()
979
1011
  elif tag == definitions.BlinkSerializationTag.FENCED_FRAME_CONFIG:
980
- dom_object = self._ReadFencedFrameConfig()
1012
+ self._ReadFencedFrameConfig()
981
1013
  return dom_object
982
1014
 
983
1015
  def Deserialize(self) -> Any:
@@ -996,16 +1028,17 @@ class V8ScriptValueDecoder:
996
1028
  if self.trailer_size:
997
1029
  self.deserializer = v8.ValueDeserializer(
998
1030
  io.BytesIO(
999
- self.raw_data[version_envelope_size:self.trailer_offset]),
1000
- delegate=self)
1031
+ self.raw_data[version_envelope_size : self.trailer_offset]
1032
+ ),
1033
+ delegate=self,
1034
+ )
1001
1035
  else:
1002
1036
  self.deserializer = v8.ValueDeserializer(
1003
- io.BytesIO(
1004
- self.raw_data[version_envelope_size:]),
1005
- delegate=self)
1037
+ io.BytesIO(self.raw_data[version_envelope_size:]), delegate=self
1038
+ )
1006
1039
  is_supported = self.deserializer.ReadHeader()
1007
1040
  if not is_supported:
1008
- raise errors.ParserError('Unsupported header')
1041
+ raise errors.ParserError("Unsupported header")
1009
1042
  return self.deserializer.ReadValue()
1010
1043
 
1011
1044
  @classmethod
@@ -1015,4 +1048,13 @@ class V8ScriptValueDecoder:
1015
1048
  Returns:
1016
1049
  The deserialized script value.
1017
1050
  """
1051
+ if len(data) < 3:
1052
+ raise errors.ParserError("Data too short to contain a Blink SSV")
1053
+ if (
1054
+ data[0] == definitions.BlinkSerializationTag.VERSION
1055
+ and data[1] == definitions.REQUIRES_PROCESSING_SSV_PSEUDO_VERSION
1056
+ and data[2] == definitions.COMPRESSED_WITH_SNAPPY
1057
+ ):
1058
+ # ignore the wrapped header bytes when decompressing
1059
+ data = snappy.decompress(data[3:])
1018
1060
  return cls(data).Deserialize()