Skip to content

Commit

Permalink
Better MimicDict and New Mixin
Browse files Browse the repository at this point in the history
- Added more tests for dict
- MimicDict Class now using MutableMapping
- New HTTPTransaction SubClass used by Request and Response
  • Loading branch information
Cyb3r-Jak3 committed Sep 6, 2020
1 parent 0418234 commit bc56274
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 35 deletions.
10 changes: 3 additions & 7 deletions haralyzer/http.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
"""Creates the Request and Response sub class that are used by each entry"""
from cached_property import cached_property
from .mixins import GetHeaders, MimicDict
from .mixins import HttpTransaction


class Request(GetHeaders, MimicDict, object):
class Request(HttpTransaction):
"""Request object for an HarEntry"""
def __init__(self, entry):
self.raw_entry = entry

def __str__(self):
return "HarEntry.Request for %s" % self.raw_entry["url"]
Expand Down Expand Up @@ -75,10 +73,8 @@ def userAgent(self):
return self.get_header_value("User-Agent")


class Response(GetHeaders, MimicDict, object):
class Response(HttpTransaction):
"""Response object for a HarEntry"""
def __init__(self, entry):
self.raw_entry = entry

# Root Level values

Expand Down
36 changes: 20 additions & 16 deletions haralyzer/mixins.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
"""Mixin Objects that allow for shared methods"""
from abc import ABC
from collections.abc import MutableMapping
from cached_property import cached_property


class GetHeaders(object):
Expand All @@ -14,7 +17,7 @@ def get_header_value(self, name):
return x["value"]


class MimicDict(object):
class MimicDict(MutableMapping, ABC):
"""Mixin for functions to mimic a dictionary for backward compatibility"""

def __getitem__(self, item):
Expand All @@ -23,20 +26,21 @@ def __getitem__(self, item):
def __len__(self):
return len(self.raw_entry)

def get(self, item, default=None):
"""
Mimics dict.get()
"""
return self.raw_entry.get(item, default)
def __delitem__(self, key):
del self.raw_entry[key]

def keys(self):
"""
Mimics dict.keys()
"""
return self.raw_entry.keys()
def __iter__(self):
return iter(self.raw_entry)

def items(self):
"""
Mimics dict.items()
"""
return self.raw_entry.items()
def __setitem__(self, key, value):
self.raw_entry[key] = value


class HttpTransaction(GetHeaders, MimicDict):
def __init__(self, entry):
self.raw_entry = entry

# Base class gets properties that belong to both request/response
@cached_property
def headers(self):
return self.raw_entry["headers"]
14 changes: 9 additions & 5 deletions tests/test_entry.py
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ def test_backwards(har_data):
assert single_entry["pageref"] == "page_3"
assert single_entry["connection"] == "80"
with pytest.raises(KeyError):
single_entry["_securityState"]
assert single_entry["_securityState"]
assert single_entry["serverIPAddress"] == "216.70.110.121"
assert single_entry["time"] == 153
assert single_entry["timings"] == {'receive': 0, 'send': 0, 'connect': 0, 'dns': 0, 'wait': 76, 'blocked': 77}
Expand All @@ -103,8 +103,12 @@ def test_backwards(har_data):
assert single_entry.get("time") == 153
assert single_entry.get("NothingHere", "Default") == "Default"

assert single_entry.request["method"] == "GET"
assert single_entry.request.get("method") == "GET"
assert single_entry.request["method"] == single_entry.request.get("method") == "GET"

assert single_entry.response["status"] == 200
assert single_entry.response.get("status") == 200
assert single_entry.response["status"] == single_entry.response.get("status") == 200

# MISC TESTS FOR DICT COMPATIBILITY/COVERAGE
single_entry["Testing"] = "HelloWorld"
assert "Testing" in single_entry
del single_entry["Testing"]
assert iter(single_entry)
17 changes: 10 additions & 7 deletions tests/test_page.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ def test_init(har_data):
Test the object loading
"""
with pytest.raises(ValueError):
page = HarPage(PAGE_ID)
assert HarPage(PAGE_ID)

init_data = har_data('humanssuck.net.har')

Expand Down Expand Up @@ -59,13 +59,13 @@ def test_filter_entries(har_data):
entries = page.filter_entries(request_type='.*ET')
assert len(entries) == 4
for entry in entries:
assert entry.request.method == 'GET'
assert entry.request.method == entry["request"]["method"] == 'GET'

# Filter by request type and content_type
entries = page.filter_entries(request_type='.*ET', content_type='image.*')
assert len(entries) == 1
for entry in entries:
assert entry.request.method == 'GET'
assert entry.request.method == entry["request"]["method"] == 'GET'
for header in entry.request.headers:
if header['name'] == 'Content-Type':
assert re.search('image.*', header['value'])
Expand All @@ -75,11 +75,14 @@ def test_filter_entries(har_data):
status_code='2.*')
assert len(entries) == 1
for entry in entries:
assert entry.request.method == 'GET'
assert entry.request.method == entry["request"]["method"] == 'GET'
assert re.search('2.*', str(entry.response.status))
for header in entry.response.headers:
if header['name'] == 'Content-Type':
assert re.search('image.*', header['value'])
for header in entry["response"]["headers"]:
if header['name'] == 'Content-Type':
assert re.search('image.*', header['value'])

entries = page.filter_entries(request_type='.*ST')
assert len(entries) == 0
Expand Down Expand Up @@ -123,7 +126,7 @@ def test_entries(har_data):
page = HarPage(PAGE_ID, har_data=init_data)

for entry in page.entries:
assert entry.pageref == page.page_id
assert entry.pageref == entry["pageref"] == page.page_id


def test_file_types(har_data):
Expand Down Expand Up @@ -152,10 +155,10 @@ def test_request_types(har_data):

# Check request type lists
for req in page.get_requests:
assert req.request.method == 'GET'
assert req.request.method == req["request"]["method"] == 'GET'

for req in page.post_requests:
assert req.request.method == 'POST'
assert req.request.method == req["request"]["method"] == 'POST'


def test_sizes_trans(har_data):
Expand Down

0 comments on commit bc56274

Please sign in to comment.