Coverage for tests / test_tutorial / test_fastapi / test_simple_hero_api / test_tutorial001.py: 100%

43 statements  

« prev     ^ index     » next       coverage.py v7.13.0, created at 2026-06-10 09:40 +0000

1import importlib 1ijklmnop

2from types import ModuleType 1ijklmnop

3 

4import pytest 1ijklmnop

5from dirty_equals import IsOneOf 1ijklmnop

6from fastapi.testclient import TestClient 1ijklmnop

7from sqlmodel import create_engine 1ijklmnop

8from sqlmodel.pool import StaticPool 1ijklmnop

9 

10 

11@pytest.fixture( 1ijklmnop

12 name="module", 

13 params=[ 

14 pytest.param("tutorial001_py310"), 

15 ], 

16) 

17def get_module(request: pytest.FixtureRequest) -> ModuleType: 1ijklmnop

18 mod = importlib.import_module( 1ijklmnop

19 f"docs_src.tutorial.fastapi.simple_hero_api.{request.param}" 

20 ) 

21 mod.sqlite_url = "sqlite://" 1ijklmnop

22 mod.engine = create_engine( 1ijklmnop

23 mod.sqlite_url, connect_args=mod.connect_args, poolclass=StaticPool 

24 ) 

25 return mod 1ijklmnop

26 

27 

28def test_tutorial(module: ModuleType): 1ijklmnop

29 with TestClient(module.app) as client: 1abcdefgh

30 hero1_data = {"name": "Deadpond", "secret_name": "Dive Wilson"} 1abcdefgh

31 hero2_data = { 1abcdefgh

32 "name": "Spider-Boy", 

33 "secret_name": "Pedro Parqueador", 

34 "id": 9000, 

35 } 

36 response = client.post("/heroes/", json=hero1_data) 1abcdefgh

37 data = response.json() 1abcdefgh

38 

39 assert response.status_code == 200, response.text 1abcdefgh

40 assert data["name"] == hero1_data["name"] 1abcdefgh

41 assert data["secret_name"] == hero1_data["secret_name"] 1abcdefgh

42 assert data["id"] is not None 1abcdefgh

43 assert data["age"] is None 1abcdefgh

44 

45 response = client.post("/heroes/", json=hero2_data) 1abcdefgh

46 data = response.json() 1abcdefgh

47 

48 assert response.status_code == 200, response.text 1abcdefgh

49 assert data["name"] == hero2_data["name"] 1abcdefgh

50 assert data["secret_name"] == hero2_data["secret_name"] 1abcdefgh

51 assert data["id"] == hero2_data["id"], ( 1abcdefgh

52 "Up to this point it's still possible to " 

53 "set the ID of the hero in the request" 

54 ) 

55 assert data["age"] is None 1abcdefgh

56 

57 response = client.get("/heroes/") 1abcdefgh

58 data = response.json() 1abcdefgh

59 

60 assert response.status_code == 200, response.text 1abcdefgh

61 assert len(data) == 2 1abcdefgh

62 assert data[0]["name"] == hero1_data["name"] 1abcdefgh

63 assert data[0]["secret_name"] == hero1_data["secret_name"] 1abcdefgh

64 assert data[1]["name"] == hero2_data["name"] 1abcdefgh

65 assert data[1]["secret_name"] == hero2_data["secret_name"] 1abcdefgh

66 assert data[1]["id"] == hero2_data["id"] 1abcdefgh

67 

68 response = client.get("/openapi.json") 1abcdefgh

69 

70 assert response.status_code == 200, response.text 1abcdefgh

71 

72 assert response.json() == { 1abcdefgh

73 "openapi": "3.1.0", 

74 "info": {"title": "FastAPI", "version": "0.1.0"}, 

75 "paths": { 

76 "/heroes/": { 

77 "get": { 

78 "summary": "Read Heroes", 

79 "operationId": "read_heroes_heroes__get", 

80 "responses": { 

81 "200": { 

82 "description": "Successful Response", 

83 "content": {"application/json": {"schema": {}}}, 

84 } 

85 }, 

86 }, 

87 "post": { 

88 "summary": "Create Hero", 

89 "operationId": "create_hero_heroes__post", 

90 "requestBody": { 

91 "content": { 

92 "application/json": { 

93 "schema": {"$ref": "#/components/schemas/Hero"} 

94 } 

95 }, 

96 "required": True, 

97 }, 

98 "responses": { 

99 "200": { 

100 "description": "Successful Response", 

101 "content": {"application/json": {"schema": {}}}, 

102 }, 

103 "422": { 

104 "description": "Validation Error", 

105 "content": { 

106 "application/json": { 

107 "schema": { 

108 "$ref": "#/components/schemas/HTTPValidationError" 

109 } 

110 } 

111 }, 

112 }, 

113 }, 

114 }, 

115 } 

116 }, 

117 "components": { 

118 "schemas": { 

119 "HTTPValidationError": { 

120 "title": "HTTPValidationError", 

121 "type": "object", 

122 "properties": { 

123 "detail": { 

124 "title": "Detail", 

125 "type": "array", 

126 "items": { 

127 "$ref": "#/components/schemas/ValidationError" 

128 }, 

129 } 

130 }, 

131 }, 

132 "Hero": { 

133 "title": "Hero", 

134 "required": ["name", "secret_name"], 

135 "type": "object", 

136 "properties": { 

137 "id": { 

138 "title": "Id", 

139 "anyOf": [{"type": "integer"}, {"type": "null"}], 

140 }, 

141 "name": {"title": "Name", "type": "string"}, 

142 "secret_name": {"title": "Secret Name", "type": "string"}, 

143 "age": { 

144 "title": "Age", 

145 "anyOf": [{"type": "integer"}, {"type": "null"}], 

146 }, 

147 }, 

148 }, 

149 "ValidationError": { 

150 "title": "ValidationError", 

151 "required": ["loc", "msg", "type"], 

152 "type": "object", 

153 "properties": IsOneOf( 

154 { 

155 "loc": { 

156 "title": "Location", 

157 "type": "array", 

158 "items": { 

159 "anyOf": [ 

160 {"type": "string"}, 

161 {"type": "integer"}, 

162 ] 

163 }, 

164 }, 

165 "msg": {"title": "Message", "type": "string"}, 

166 "type": {"title": "Error Type", "type": "string"}, 

167 }, 

168 { 

169 "loc": { 

170 "title": "Location", 

171 "type": "array", 

172 "items": { 

173 "anyOf": [ 

174 {"type": "string"}, 

175 {"type": "integer"}, 

176 ] 

177 }, 

178 }, 

179 "msg": {"title": "Message", "type": "string"}, 

180 "type": {"title": "Error Type", "type": "string"}, 

181 "ctx": {"title": "Context", "type": "object"}, 

182 "input": {"title": "Input"}, 

183 }, 

184 ), 

185 }, 

186 } 

187 }, 

188 }