dissect.target 3.16.dev12__py3-none-any.whl → 3.16.dev13__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.
@@ -43,6 +43,7 @@ GENERIC_COOKIE_FIELDS = [
43
43
  ("boolean", "is_secure"),
44
44
  ("boolean", "is_http_only"),
45
45
  ("boolean", "same_site"),
46
+ ("path", "source"),
46
47
  ]
47
48
 
48
49
  GENERIC_HISTORY_RECORD_FIELDS = [
@@ -38,8 +38,7 @@ class ChromePlugin(ChromiumMixin, BrowserPlugin):
38
38
  )
39
39
 
40
40
  BrowserCookieRecord = create_extended_descriptor([UserRecordDescriptorExtension])(
41
- "browser/chrome/cookie",
42
- GENERIC_COOKIE_FIELDS,
41
+ "browser/chrome/cookie", GENERIC_COOKIE_FIELDS
43
42
  )
44
43
 
45
44
  BrowserDownloadRecord = create_extended_descriptor([UserRecordDescriptorExtension])(
@@ -117,59 +117,60 @@ class ChromiumMixin:
117
117
  if not len(self._build_userdirs(self.DIRS)):
118
118
  raise UnsupportedPluginError("No Chromium-based browser directories found")
119
119
 
120
- def downloads(self, browser_name: Optional[str] = None) -> Iterator[BrowserDownloadRecord]:
121
- """Return browser download records from supported Chromium-based browsers.
120
+ def history(self, browser_name: Optional[str] = None) -> Iterator[BrowserHistoryRecord]:
121
+ """Return browser history records from supported Chromium-based browsers.
122
122
 
123
123
  Args:
124
124
  browser_name: The name of the browser as a string.
125
125
 
126
126
  Yields:
127
127
  Records with the following fields:
128
- ts_start (datetime): Download start timestamp.
129
- ts_end (datetime): Download end timestamp.
128
+ ts (datetime): Visit timestamp.
130
129
  browser (string): The browser from which the records are generated from.
131
130
  id (string): Record ID.
132
- path (string): Download path.
133
- url (uri): Download URL.
134
- tab_url (string): Tab URL.
135
- tab_referrer_url (string): Referrer URL.
136
- size (varint): Download file size.
137
- mime_type (string): MIME type.
138
- state (varint): Download state number.
139
- source: (path): The source file of the download record.
131
+ url (uri): History URL.
132
+ title (string): Page title.
133
+ description (string): Page description.
134
+ rev_host (string): Reverse hostname.
135
+ visit_type (varint): Visit type.
136
+ visit_count (varint): Amount of visits.
137
+ hidden (string): Hidden value.
138
+ typed (string): Typed value.
139
+ session (varint): Session value.
140
+ from_visit (varint): Record ID of the "from" visit.
141
+ from_url (uri): URL of the "from" visit.
142
+ source: (path): The source file of the history record.
140
143
  """
141
144
  for user, db_file, db in self._iter_db("History"):
142
145
  try:
143
- download_chains = defaultdict(list)
144
- for row in db.table("downloads_url_chains"):
145
- download_chains[row.id].append(row)
146
-
147
- for chain in download_chains.values():
148
- chain.sort(key=lambda row: row.chain_index)
149
-
150
- for row in db.table("downloads").rows():
151
- if download_path := row.target_path:
152
- download_path = self.target.fs.path(download_path)
146
+ urls = {row.id: row for row in db.table("urls").rows()}
147
+ visits = {}
153
148
 
154
- url = None
155
- download_chain = download_chains.get(row.id)
149
+ for row in db.table("visits").rows():
150
+ visits[row.id] = row
151
+ url = urls[row.url]
156
152
 
157
- if download_chain:
158
- url = download_chain[-1].url
159
- url = try_idna(url)
153
+ if row.from_visit and row.from_visit in visits:
154
+ from_visit = visits[row.from_visit]
155
+ from_url = urls[from_visit.url]
156
+ else:
157
+ from_visit, from_url = None, None
160
158
 
161
- yield self.BrowserDownloadRecord(
162
- ts_start=webkittimestamp(row.start_time),
163
- ts_end=webkittimestamp(row.end_time) if row.end_time else None,
159
+ yield self.BrowserHistoryRecord(
160
+ ts=webkittimestamp(row.visit_time),
164
161
  browser=browser_name,
165
- id=row.get("id"),
166
- tab_url=try_idna(row.get("tab_url")),
167
- tab_referrer_url=try_idna(row.get("tab_referrer_url")),
168
- path=download_path,
169
- url=url,
170
- size=row.get("total_bytes"),
171
- mime_type=row.get("mime_type"),
172
- state=row.get("state"),
162
+ id=row.id,
163
+ url=try_idna(url.url),
164
+ title=url.title,
165
+ description=None,
166
+ rev_host=None,
167
+ visit_type=None,
168
+ visit_count=url.visit_count,
169
+ hidden=url.hidden,
170
+ typed=None,
171
+ session=None,
172
+ from_visit=row.from_visit or None,
173
+ from_url=try_idna(from_url.url) if from_url else None,
173
174
  source=db_file,
174
175
  _target=self.target,
175
176
  _user=user,
@@ -212,11 +213,72 @@ class ChromiumMixin:
212
213
  is_secure=bool(cookie.is_secure),
213
214
  is_http_only=bool(cookie.is_httponly),
214
215
  same_site=bool(cookie.samesite),
216
+ source=db_file,
215
217
  _user=user,
216
218
  )
217
219
  except SQLError as e:
218
220
  self.target.log.warning("Error processing cookie file: %s", db_file, exc_info=e)
219
221
 
222
+ def downloads(self, browser_name: Optional[str] = None) -> Iterator[BrowserDownloadRecord]:
223
+ """Return browser download records from supported Chromium-based browsers.
224
+
225
+ Args:
226
+ browser_name: The name of the browser as a string.
227
+
228
+ Yields:
229
+ Records with the following fields:
230
+ ts_start (datetime): Download start timestamp.
231
+ ts_end (datetime): Download end timestamp.
232
+ browser (string): The browser from which the records are generated from.
233
+ id (string): Record ID.
234
+ path (string): Download path.
235
+ url (uri): Download URL.
236
+ tab_url (string): Tab URL.
237
+ tab_referrer_url (string): Referrer URL.
238
+ size (varint): Download file size.
239
+ mime_type (string): MIME type.
240
+ state (varint): Download state number.
241
+ source: (path): The source file of the download record.
242
+ """
243
+ for user, db_file, db in self._iter_db("History"):
244
+ try:
245
+ download_chains = defaultdict(list)
246
+ for row in db.table("downloads_url_chains"):
247
+ download_chains[row.id].append(row)
248
+
249
+ for chain in download_chains.values():
250
+ chain.sort(key=lambda row: row.chain_index)
251
+
252
+ for row in db.table("downloads").rows():
253
+ if download_path := row.target_path:
254
+ download_path = self.target.fs.path(download_path)
255
+
256
+ url = None
257
+ download_chain = download_chains.get(row.id)
258
+
259
+ if download_chain:
260
+ url = download_chain[-1].url
261
+ url = try_idna(url)
262
+
263
+ yield self.BrowserDownloadRecord(
264
+ ts_start=webkittimestamp(row.start_time),
265
+ ts_end=webkittimestamp(row.end_time) if row.end_time else None,
266
+ browser=browser_name,
267
+ id=row.get("id"),
268
+ tab_url=try_idna(row.get("tab_url")),
269
+ tab_referrer_url=try_idna(row.get("tab_referrer_url")),
270
+ path=download_path,
271
+ url=url,
272
+ size=row.get("total_bytes"),
273
+ mime_type=row.get("mime_type"),
274
+ state=row.get("state"),
275
+ source=db_file,
276
+ _target=self.target,
277
+ _user=user,
278
+ )
279
+ except SQLError as e:
280
+ self.target.log.warning("Error processing history file: %s", db_file, exc_info=e)
281
+
220
282
  def extensions(self, browser_name: Optional[str] = None) -> Iterator[BrowserExtensionRecord]:
221
283
  """Iterates over all installed extensions for a given browser.
222
284
 
@@ -303,67 +365,6 @@ class ChromiumMixin:
303
365
  except (AttributeError, KeyError) as e:
304
366
  self.target.log.info("No browser extensions found in: %s", json_file, exc_info=e)
305
367
 
306
- def history(self, browser_name: Optional[str] = None) -> Iterator[BrowserHistoryRecord]:
307
- """Return browser history records from supported Chromium-based browsers.
308
-
309
- Args:
310
- browser_name: The name of the browser as a string.
311
-
312
- Yields:
313
- Records with the following fields:
314
- ts (datetime): Visit timestamp.
315
- browser (string): The browser from which the records are generated from.
316
- id (string): Record ID.
317
- url (uri): History URL.
318
- title (string): Page title.
319
- description (string): Page description.
320
- rev_host (string): Reverse hostname.
321
- visit_type (varint): Visit type.
322
- visit_count (varint): Amount of visits.
323
- hidden (string): Hidden value.
324
- typed (string): Typed value.
325
- session (varint): Session value.
326
- from_visit (varint): Record ID of the "from" visit.
327
- from_url (uri): URL of the "from" visit.
328
- source: (path): The source file of the history record.
329
- """
330
- for user, db_file, db in self._iter_db("History"):
331
- try:
332
- urls = {row.id: row for row in db.table("urls").rows()}
333
- visits = {}
334
-
335
- for row in db.table("visits").rows():
336
- visits[row.id] = row
337
- url = urls[row.url]
338
-
339
- if row.from_visit and row.from_visit in visits:
340
- from_visit = visits[row.from_visit]
341
- from_url = urls[from_visit.url]
342
- else:
343
- from_visit, from_url = None, None
344
-
345
- yield self.BrowserHistoryRecord(
346
- ts=webkittimestamp(row.visit_time),
347
- browser=browser_name,
348
- id=row.id,
349
- url=try_idna(url.url),
350
- title=url.title,
351
- description=None,
352
- rev_host=None,
353
- visit_type=None,
354
- visit_count=url.visit_count,
355
- hidden=url.hidden,
356
- typed=None,
357
- session=None,
358
- from_visit=row.from_visit or None,
359
- from_url=try_idna(from_url.url) if from_url else None,
360
- source=db_file,
361
- _target=self.target,
362
- _user=user,
363
- )
364
- except SQLError as e:
365
- self.target.log.warning("Error processing history file: %s", db_file, exc_info=e)
366
-
367
368
 
368
369
  class ChromiumPlugin(ChromiumMixin, BrowserPlugin):
369
370
  """Chromium browser plugin."""
@@ -36,8 +36,7 @@ class EdgePlugin(ChromiumMixin, BrowserPlugin):
36
36
  )
37
37
 
38
38
  BrowserCookieRecord = create_extended_descriptor([UserRecordDescriptorExtension])(
39
- "browser/edge/cookie",
40
- GENERIC_COOKIE_FIELDS,
39
+ "browser/edge/cookie", GENERIC_COOKIE_FIELDS
41
40
  )
42
41
 
43
42
  BrowserDownloadRecord = create_extended_descriptor([UserRecordDescriptorExtension])(
@@ -176,6 +176,7 @@ class FirefoxPlugin(BrowserPlugin):
176
176
  is_secure=bool(cookie.isSecure),
177
177
  is_http_only=bool(cookie.isHttpOnly),
178
178
  same_site=bool(cookie.sameSite),
179
+ source=db_file,
179
180
  _user=user,
180
181
  )
181
182
  except SQLError as e:
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: dissect.target
3
- Version: 3.16.dev12
3
+ Version: 3.16.dev13
4
4
  Summary: This module ties all other Dissect modules together, it provides a programming API and command line tools which allow easy access to various data sources inside disk images or file collections (a.k.a. targets)
5
5
  Author-email: Dissect Team <dissect@fox-it.com>
6
6
  License: Affero General Public License v3
@@ -112,11 +112,11 @@ dissect/target/plugins/apps/av/sophos.py,sha256=gSfTvjBZMuT0hsL-p4oYxuYmakbqApoO
112
112
  dissect/target/plugins/apps/av/symantec.py,sha256=RFLyNW6FyuoGcirJ4xHbQM8oGjua9W4zXmC7YDF-H20,14109
113
113
  dissect/target/plugins/apps/av/trendmicro.py,sha256=jloy_N4hHAqF1sVIEeD5Q7LRYal3_os14Umk-hGaAR4,4613
114
114
  dissect/target/plugins/apps/browser/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
115
- dissect/target/plugins/apps/browser/browser.py,sha256=h32A0gyV2ehcWcozQJC8yXQ4L94FKjh1Rb31ZnUcX0Y,2658
116
- dissect/target/plugins/apps/browser/chrome.py,sha256=0DzhvUUA6xKZ9iTrCQmgAWWAsA8czMfIeXAT1fuZ1dE,2644
117
- dissect/target/plugins/apps/browser/chromium.py,sha256=yhgHdAifVUs20uqYEDAnn1nLJfV1p62cyXq2Ilum7zU,17734
118
- dissect/target/plugins/apps/browser/edge.py,sha256=QuJpPcdU5RGWzeweJjJJZyJgmPVaYBCsjhLt-xYKsX0,2482
119
- dissect/target/plugins/apps/browser/firefox.py,sha256=G42FU1KqqnFpAERcB_WU8QT6AcaXiimLhNgFII9gFEM,11333
115
+ dissect/target/plugins/apps/browser/browser.py,sha256=_QP1u57-wOSiLvpTUotWDpqBdRn-WEWpBDzCMqZTYO0,2682
116
+ dissect/target/plugins/apps/browser/chrome.py,sha256=XMDq3v-fA0W16gm5jXryP73PEtF7bRw5Pfqy5JQd-U8,2635
117
+ dissect/target/plugins/apps/browser/chromium.py,sha256=Y1sS0EqF5F5abpLXNog2HwI5QV5d3qnBvZMnE0MPdyU,17774
118
+ dissect/target/plugins/apps/browser/edge.py,sha256=cjMbAGtlTVyJLuha3D0uNbai0mJnkXmp6d0gBfceWB4,2473
119
+ dissect/target/plugins/apps/browser/firefox.py,sha256=6dUTNfclNTsqB_GA-4q38tyHPuiw8lgNEmmtfIWbMUY,11373
120
120
  dissect/target/plugins/apps/browser/iexplore.py,sha256=LUXXCjMBBFcFN2ceBpks8qM1PyOvrBPn1guA4WM4oSU,8706
121
121
  dissect/target/plugins/apps/container/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
122
122
  dissect/target/plugins/apps/container/docker.py,sha256=guFPqRLbeP4p8R6lDIZVKWnva5_S7rQUVKG21QDz-B4,6416
@@ -323,10 +323,10 @@ dissect/target/volumes/luks.py,sha256=OmCMsw6rCUXG1_plnLVLTpsvE1n_6WtoRUGQbpmu1z
323
323
  dissect/target/volumes/lvm.py,sha256=wwQVR9I3G9YzmY6UxFsH2Y4MXGBcKL9aayWGCDTiWMU,2269
324
324
  dissect/target/volumes/md.py,sha256=j1K1iKmspl0C_OJFc7-Q1BMWN2OCC5EVANIgVlJ_fIE,1673
325
325
  dissect/target/volumes/vmfs.py,sha256=-LoUbn9WNwTtLi_4K34uV_-wDw2W5hgaqxZNj4UmqAQ,1730
326
- dissect.target-3.16.dev12.dist-info/COPYRIGHT,sha256=m-9ih2RVhMiXHI2bf_oNSSgHgkeIvaYRVfKTwFbnJPA,301
327
- dissect.target-3.16.dev12.dist-info/LICENSE,sha256=DZak_2itbUtvHzD3E7GNUYSRK6jdOJ-GqncQ2weavLA,34523
328
- dissect.target-3.16.dev12.dist-info/METADATA,sha256=2f1MjScJ_LT0j-Kji3WLYlt_olRxKtE3s7y1T-eUGhw,11113
329
- dissect.target-3.16.dev12.dist-info/WHEEL,sha256=oiQVh_5PnQM0E3gPdiz09WCNmwiHDMaGer_elqB3coM,92
330
- dissect.target-3.16.dev12.dist-info/entry_points.txt,sha256=tvFPa-Ap-gakjaPwRc6Fl6mxHzxEZ_arAVU-IUYeo_s,447
331
- dissect.target-3.16.dev12.dist-info/top_level.txt,sha256=Mn-CQzEYsAbkxrUI0TnplHuXnGVKzxpDw_po_sXpvv4,8
332
- dissect.target-3.16.dev12.dist-info/RECORD,,
326
+ dissect.target-3.16.dev13.dist-info/COPYRIGHT,sha256=m-9ih2RVhMiXHI2bf_oNSSgHgkeIvaYRVfKTwFbnJPA,301
327
+ dissect.target-3.16.dev13.dist-info/LICENSE,sha256=DZak_2itbUtvHzD3E7GNUYSRK6jdOJ-GqncQ2weavLA,34523
328
+ dissect.target-3.16.dev13.dist-info/METADATA,sha256=3C3Z4nrLFNTsMdbf_ij7Tjztn8Yra3gKF232itkAgmM,11113
329
+ dissect.target-3.16.dev13.dist-info/WHEEL,sha256=oiQVh_5PnQM0E3gPdiz09WCNmwiHDMaGer_elqB3coM,92
330
+ dissect.target-3.16.dev13.dist-info/entry_points.txt,sha256=tvFPa-Ap-gakjaPwRc6Fl6mxHzxEZ_arAVU-IUYeo_s,447
331
+ dissect.target-3.16.dev13.dist-info/top_level.txt,sha256=Mn-CQzEYsAbkxrUI0TnplHuXnGVKzxpDw_po_sXpvv4,8
332
+ dissect.target-3.16.dev13.dist-info/RECORD,,