Coverage for tests / test_union_forms.py: 100%

34 statements  

« prev     ^ index     » next       coverage.py v7.13.3, created at 2026-02-12 18:15 +0000

1from typing import Annotated, Union 1abcd

2 

3from fastapi import FastAPI, Form 1abcd

4from fastapi.testclient import TestClient 1abcd

5from inline_snapshot import snapshot 1abcd

6from pydantic import BaseModel 1abcd

7 

8app = FastAPI() 1abcd

9 

10 

11class UserForm(BaseModel): 1abcd

12 name: str 1abcd

13 email: str 1abcd

14 

15 

16class CompanyForm(BaseModel): 1abcd

17 company_name: str 1abcd

18 industry: str 1abcd

19 

20 

21@app.post("/form-union/") 1abcd

22def post_union_form(data: Annotated[Union[UserForm, CompanyForm], Form()]): 1abcd

23 return {"received": data} 1efghij

24 

25 

26client = TestClient(app) 1abcd

27 

28 

29def test_post_user_form(): 1abcd

30 response = client.post( 1fhj

31 "/form-union/", data={"name": "John Doe", "email": "john@example.com"} 

32 ) 

33 assert response.status_code == 200, response.text 1fhj

34 assert response.json() == { 1fhj

35 "received": {"name": "John Doe", "email": "john@example.com"} 

36 } 

37 

38 

39def test_post_company_form(): 1abcd

40 response = client.post( 1egi

41 "/form-union/", data={"company_name": "Tech Corp", "industry": "Technology"} 

42 ) 

43 assert response.status_code == 200, response.text 1egi

44 assert response.json() == { 1egi

45 "received": {"company_name": "Tech Corp", "industry": "Technology"} 

46 } 

47 

48 

49def test_invalid_form_data(): 1abcd

50 response = client.post( 1nop

51 "/form-union/", 

52 data={"name": "John", "company_name": "Tech Corp"}, 

53 ) 

54 assert response.status_code == 422, response.text 1nop

55 

56 

57def test_empty_form(): 1abcd

58 response = client.post("/form-union/") 1qrs

59 assert response.status_code == 422, response.text 1qrs

60 

61 

62def test_openapi_schema(): 1abcd

63 response = client.get("/openapi.json") 1klm

64 assert response.status_code == 200, response.text 1klm

65 assert response.json() == snapshot( 1klm

66 { 

67 "openapi": "3.1.0", 

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

69 "paths": { 

70 "/form-union/": { 

71 "post": { 

72 "summary": "Post Union Form", 

73 "operationId": "post_union_form_form_union__post", 

74 "requestBody": { 

75 "content": { 

76 "application/x-www-form-urlencoded": { 

77 "schema": { 

78 "anyOf": [ 

79 {"$ref": "#/components/schemas/UserForm"}, 

80 { 

81 "$ref": "#/components/schemas/CompanyForm" 

82 }, 

83 ], 

84 "title": "Data", 

85 } 

86 } 

87 }, 

88 "required": True, 

89 }, 

90 "responses": { 

91 "200": { 

92 "description": "Successful Response", 

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

94 }, 

95 "422": { 

96 "description": "Validation Error", 

97 "content": { 

98 "application/json": { 

99 "schema": { 

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

101 } 

102 } 

103 }, 

104 }, 

105 }, 

106 } 

107 } 

108 }, 

109 "components": { 

110 "schemas": { 

111 "CompanyForm": { 

112 "properties": { 

113 "company_name": {"type": "string", "title": "Company Name"}, 

114 "industry": {"type": "string", "title": "Industry"}, 

115 }, 

116 "type": "object", 

117 "required": ["company_name", "industry"], 

118 "title": "CompanyForm", 

119 }, 

120 "HTTPValidationError": { 

121 "properties": { 

122 "detail": { 

123 "items": { 

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

125 }, 

126 "type": "array", 

127 "title": "Detail", 

128 } 

129 }, 

130 "type": "object", 

131 "title": "HTTPValidationError", 

132 }, 

133 "UserForm": { 

134 "properties": { 

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

136 "email": {"type": "string", "title": "Email"}, 

137 }, 

138 "type": "object", 

139 "required": ["name", "email"], 

140 "title": "UserForm", 

141 }, 

142 "ValidationError": { 

143 "properties": { 

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

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

146 "loc": { 

147 "items": { 

148 "anyOf": [{"type": "string"}, {"type": "integer"}] 

149 }, 

150 "type": "array", 

151 "title": "Location", 

152 }, 

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

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

155 }, 

156 "type": "object", 

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

158 "title": "ValidationError", 

159 }, 

160 } 

161 }, 

162 } 

163 )