Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit9fb8d5c

Browse files
add tests forscrapy#7036
this is mostly ai generatedidk those comments and docstring are helpful imo
1 parent1c6ba00 commit9fb8d5c

File tree

1 file changed

+83
-0
lines changed

1 file changed

+83
-0
lines changed

‎tests/test_request_attrs.py‎

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
fromtypingimportAny
2+
3+
importpytest
4+
5+
fromscrapy.http.requestimportNO_CALLBACK,Request
6+
fromscrapy.http.request.formimportFormRequest
7+
fromscrapy.http.request.json_requestimportJsonRequest
8+
9+
_attr_value_map:dict[str,Any]= {
10+
"url":"http://example.com/test",
11+
"callback":NO_CALLBACK,
12+
"method":"POST",
13+
"headers": {
14+
b"X-Test-Header": [b"1"],
15+
# `JsonRequest` will eventually add those even if they are not present
16+
b"Accept": [b"application/json, text/javascript, */*; q=0.01"],
17+
b"Content-Type": [b"application/json"],
18+
},
19+
"body":b"hello",
20+
"cookies": {"a":"1"},
21+
"meta": {"k":"v"},
22+
"encoding":"koi8-r",
23+
"priority":5,
24+
"dont_filter":True,
25+
"errback":NO_CALLBACK,
26+
"flags": ["f1","f2"],
27+
"cb_kwargs": {"x":1},
28+
}
29+
30+
31+
def_assert_equal_attribute(obj:Request,attr:str,expected:Any):
32+
val=getattr(obj,attr)
33+
ifattr=="headers":
34+
# Headers object -> dict
35+
assertdict(val)==dict(expected)
36+
elifattr=="body":
37+
# body should be bytes
38+
assertval==expected
39+
else:
40+
assertval==expected
41+
42+
43+
@pytest.mark.parametrize("request_class", [Request,JsonRequest,FormRequest])
44+
@pytest.mark.parametrize("attr",Request.attributes)
45+
deftest_attribute_setattr_and_replace_behavior(
46+
request_class:type[Request],attr:str
47+
):
48+
"""Ensure current assignment and replace semantics for Request.attributes.
49+
50+
- If setattr(obj, attr, val) works today, it must keep working and
51+
replace() should carry the value over.
52+
- If setattr(obj, attr, val) raises AttributeError today (read-only),
53+
replace(**{attr: val}) should still allow creating a Request with that attr.
54+
"""
55+
r=request_class("http://example.com/")
56+
57+
ifattrnotin_attr_value_map:
58+
return
59+
60+
val=_attr_value_map[attr]
61+
62+
# first try direct setattr
63+
try:
64+
setattr(r,attr,val)
65+
exceptAttributeError:
66+
# attribute is read-only
67+
# ensure replace(**{attr: val}) creates a new request with that value
68+
r2=r.replace(**{attr:val})
69+
_assert_equal_attribute(r2,attr,val)
70+
# original request must remain unchanged (unless replace mutated it)
71+
# (for read-only attributes we expect original not to equal val)
72+
ifgetattr(r,attr)==val:
73+
pytest.fail(
74+
f"Attribute{attr} unexpectedly mutated original Request when "
75+
f"it should have been read-only (direct setattr raised)."
76+
)
77+
else:
78+
# direct setattr succeeded; attribute must reflect assigned value
79+
_assert_equal_attribute(r,attr,val)
80+
81+
# and replace() must preserve it (replace uses getattr(self, x))
82+
r2=r.replace()
83+
_assert_equal_attribute(r2,attr,getattr(r,attr))

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp