##// END OF EJS Templates
sidedata: add a function for _processflagsraw usage...
marmoute -
r43304:e8bc4c3d default
parent child Browse files
Show More
@@ -1,75 +1,79
1 1 # sidedata.py - Logic around store extra data alongside revlog revisions
2 2 #
3 3 # Copyright 2019 Pierre-Yves David <pierre-yves.david@octobus.net)
4 4 #
5 5 # This software may be used and distributed according to the terms of the
6 6 # GNU General Public License version 2 or any later version.
7 7 """core code for "sidedata" support
8 8
9 9 The "sidedata" are stored alongside the revision without actually being part of
10 10 its content and not affecting its hash. It's main use cases is to cache
11 11 important information related to a changesets.
12 12
13 13 The current implementation is experimental and subject to changes. Do not rely
14 14 on it in production.
15 15
16 16 Sidedata are stored in the revlog itself, withing the revision rawtext. They
17 17 are inserted, removed from it using the flagprocessors mechanism. The following
18 18 format is currently used::
19 19
20 20 initial header:
21 21 <number of sidedata; 2 bytes>
22 22 sidedata (repeated N times):
23 23 <sidedata-key; 2 bytes>
24 24 <sidedata-entry-length: 4 bytes>
25 25 <sidedata-content-sha1-digest: 20 bytes>
26 26 <sidedata-content; X bytes>
27 27 normal raw text:
28 28 <all bytes remaining in the rawtext>
29 29
30 30 This is a simple and effective format. It should be enought to experiment with
31 31 the concept.
32 32 """
33 33
34 34 from __future__ import absolute_import
35 35
36 36 import hashlib
37 37 import struct
38 38
39 39 from .. import error
40 40
41 41 SIDEDATA_HEADER = struct.Struct('>H')
42 42 SIDEDATA_ENTRY = struct.Struct('>HL20s')
43 43
44 44 def sidedatawriteprocessor(rl, text, sidedata):
45 45 sidedata = list(sidedata.items())
46 46 sidedata.sort()
47 47 rawtext = [SIDEDATA_HEADER.pack(len(sidedata))]
48 48 for key, value in sidedata:
49 49 digest = hashlib.sha1(value).digest()
50 50 rawtext.append(SIDEDATA_ENTRY.pack(key, len(value), digest))
51 51 for key, value in sidedata:
52 52 rawtext.append(value)
53 53 rawtext.append(bytes(text))
54 54 return ''.join(rawtext), False
55 55
56 56 def sidedatareadprocessor(rl, text):
57 57 sidedata = {}
58 58 offset = 0
59 59 nbentry, = SIDEDATA_HEADER.unpack(text[:SIDEDATA_HEADER.size])
60 60 offset += SIDEDATA_HEADER.size
61 61 dataoffset = SIDEDATA_HEADER.size + (SIDEDATA_ENTRY.size * nbentry)
62 62 for i in range(nbentry):
63 63 nextoffset = offset + SIDEDATA_ENTRY.size
64 64 key, size, storeddigest = SIDEDATA_ENTRY.unpack(text[offset:nextoffset])
65 65 offset = nextoffset
66 66 # read the data associated with that entry
67 67 nextdataoffset = dataoffset + size
68 68 entrytext = text[dataoffset:nextdataoffset]
69 69 readdigest = hashlib.sha1(entrytext).digest()
70 70 if storeddigest != readdigest:
71 71 raise error.SidedataHashError(key, storeddigest, readdigest)
72 72 sidedata[key] = entrytext
73 73 dataoffset = nextdataoffset
74 74 text = text[dataoffset:]
75 75 return text, True, sidedata
76
77 def sidedatarawprocessor(rl, text):
78 # side data modifies rawtext and prevent rawtext hash validation
79 return False
General Comments 0
You need to be logged in to leave comments. Login now