@@ -1741,4 +1741,258 @@ def test_dict_args_str_list_3_10_union(client):
17411741 r = client .post (url , data = {"v" : json .dumps (d )})
17421742 assert "error" in r .json
17431743
1744+ def test_typeddict_normal (client ):
1745+ url = "/form/typeddict/"
1746+ # Test that correct input yields input value
1747+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1748+ r = client .post (url , data = {"v" : json .dumps (d )})
1749+ assert "v" in r .json
1750+ assert r .json ["v" ] == d
1751+ # Test that missing keys yields error
1752+ d = {"id" : 3 }
1753+ r = client .post (url , data = {"v" : json .dumps (d )})
1754+ assert "error" in r .json
1755+ # Test that incorrect values yields error
1756+ d = {"id" : 1.03 , "name" : "foo" , "timestamp" : datetime .datetime .now ().isoformat ()}
1757+ r = client .post (url , data = {"v" : json .dumps (d )})
1758+ assert "error" in r .json
1759+
1760+ def test_typeddict_functional (client ):
1761+ url = "/form/typeddict/functional"
1762+ # Test that correct input yields input value
1763+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1764+ r = client .post (url , data = {"v" : json .dumps (d )})
1765+ assert "v" in r .json
1766+ assert r .json ["v" ] == d
1767+ # Test that missing keys yields error
1768+ d = {"id" : 3 }
1769+ r = client .post (url , data = {"v" : json .dumps (d )})
1770+ assert "error" in r .json
1771+ # Test that incorrect values yields error
1772+ d = {"id" : 1.03 , "name" : "foo" , "timestamp" : datetime .datetime .now ().isoformat ()}
1773+ r = client .post (url , data = {"v" : json .dumps (d )})
1774+ assert "error" in r .json
1775+
1776+ def test_typeddict_optional (client ):
1777+ url = "/form/typeddict/optional"
1778+ # Test that correct input yields input value
1779+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1780+ r = client .post (url , data = {"v" : json .dumps (d )})
1781+ assert "v" in r .json
1782+ assert r .json ["v" ] == d
1783+ # Test that no input yields input value
1784+ d = None
1785+ r = client .post (url , data = {"v" : d })
1786+ assert "v" in r .json
1787+ assert r .json ["v" ] == d
1788+ # Test that missing keys yields error
1789+ d = {"id" : 3 }
1790+ r = client .post (url , data = {"v" : json .dumps (d )})
1791+ assert "error" in r .json
1792+ # Test that empty dict yields error
1793+ d = {}
1794+ r = client .post (url , data = {"v" : json .dumps (d )})
1795+ assert "error" in r .json
1796+
1797+ if sys .version_info >= (3 , 10 ):
1798+ def test_typeddict_union_optional (client ):
1799+ url = "/form/typeddict/union_optional"
1800+ # Test that correct input yields input value
1801+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1802+ r = client .post (url , data = {"v" : json .dumps (d )})
1803+ assert "v" in r .json
1804+ assert r .json ["v" ] == d
1805+ # Test that no input yields input value
1806+ d = None
1807+ r = client .post (url , data = {"v" : d })
1808+ assert "v" in r .json
1809+ assert r .json ["v" ] == d
1810+ # Test that missing keys yields error
1811+ d = {"id" : 3 }
1812+ r = client .post (url , data = {"v" : json .dumps (d )})
1813+ assert "error" in r .json
1814+ # Test that empty dict yields error
1815+ d = {}
1816+ r = client .post (url , data = {"v" : json .dumps (d )})
1817+ assert "error" in r .json
1818+
1819+ def test_typeddict_default (client ):
1820+ url = "/form/typeddict/default"
1821+ # Test that missing input for required and optional yields default values
1822+ r = client .post (url )
1823+ assert "n_opt" in r .json
1824+ assert r .json ["n_opt" ] == {"id" : 1 , "name" : "Bob" , "timestamp" : datetime .datetime (2025 , 11 , 18 , 0 , 0 ).isoformat ()}
1825+ assert "opt" in r .json
1826+ assert r .json ["opt" ] == {"id" : 2 , "name" : "Billy" , "timestamp" : datetime .datetime (2025 , 11 , 18 , 5 , 30 ).isoformat ()}
1827+ # Test that present TypedDict input for required and optional yields input values
1828+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1829+ r = client .post (url , data = {
1830+ "opt" : json .dumps (d ),
1831+ "n_opt" : json .dumps (d ),
1832+ })
1833+ assert "opt" in r .json
1834+ assert r .json ["opt" ] == d
1835+ assert "n_opt" in r .json
1836+ assert r .json ["n_opt" ] == d
1837+ # Test that present non-TypedDict input for required yields error
1838+ r = client .post (url , data = {"opt" : {"id" : 3 }, "n_opt" : "b" })
1839+ assert "error" in r .json
1840+
1841+ def test_typeddict_func (client ):
1842+ url = "/form/typeddict/func"
1843+ # Test that correct input yields input value
1844+ d = {"id" : 3 , "name" : "Bill" , "timestamp" : datetime .datetime .now ().isoformat ()}
1845+ r = client .post (url , data = {"v" : json .dumps (d )})
1846+ assert "v" in r .json
1847+ assert r .json ["v" ] == d
1848+ # Test that func failing input yields input value
1849+ d = {"id" : 3 , "name" : "Billy Bob Joe" , "timestamp" : datetime .datetime .now ().isoformat ()}
1850+ r = client .post (url , data = {"v" : json .dumps (d )})
1851+ assert "error" in r .json
1852+
1853+ def test_typeddict_json_schema (client ):
1854+ url = "/form/typeddict/json_schema"
1855+ # Test that correct input yields input value
1856+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1857+ r = client .post (url , data = {"v" : json .dumps (d )})
1858+ assert "v" in r .json
1859+ assert r .json ["v" ] == d
1860+ # Test that missing keys yields error
1861+ d = {"id" : 3 }
1862+ r = client .post (url , data = {"v" : json .dumps (d )})
1863+ assert "error" in r .json
1864+ # Test that incorrect values yields error
1865+ d = {"id" : 1.03 , "name" : "foo" , "timestamp" : datetime .datetime .now ().isoformat ()}
1866+ r = client .post (url , data = {"v" : json .dumps (d )})
1867+ assert "error" in r .json
1868+
1869+ def test_typeddict_not_required (client ):
1870+ url = "/form/typeddict/not_required"
1871+ # Test that all keys yields input value
1872+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1873+ r = client .post (url , data = {"v" : json .dumps (d )})
1874+ assert "v" in r .json
1875+ assert r .json ["v" ] == d
1876+ # Test that missing not requried key yields input value
1877+ d = {"name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1878+ r = client .post (url , data = {"v" : json .dumps (d )})
1879+ assert "v" in r .json
1880+ assert r .json ["v" ] == d
1881+ # Test that missing required keys yields error
1882+ d = {"name" : "Merriweather" }
1883+ r = client .post (url , data = {"v" : json .dumps (d )})
1884+ assert "error" in r .json
1885+
1886+ def test_typeddict_required (client ):
1887+ url = "/form/typeddict/required"
1888+ # Test that all keys yields input value
1889+ d = {"id" : 3 , "name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1890+ r = client .post (url , data = {"v" : json .dumps (d )})
1891+ assert "v" in r .json
1892+ assert r .json ["v" ] == d
1893+ # Test that missing not requried key yields input value
1894+ d = {"name" : "Merriweather" , "timestamp" : datetime .datetime .now ().isoformat ()}
1895+ r = client .post (url , data = {"v" : json .dumps (d )})
1896+ assert "v" in r .json
1897+ assert r .json ["v" ] == d
1898+ # Test that missing required keys yields error
1899+ d = {"name" : "Merriweather" }
1900+ r = client .post (url , data = {"v" : json .dumps (d )})
1901+ assert "error" in r .json
1902+
1903+ def test_typeddict_complex (client ):
1904+ url = "/form/typeddict/complex"
1905+ # Test that correct input yields input value
1906+ d = {
1907+ "name" : "change da world" ,
1908+ "children" : [
1909+ {
1910+ "id" : 4 ,
1911+ "name" : "my final message. Goodb ye" ,
1912+ "timestamp" : datetime .datetime .now ().isoformat (),
1913+ }
1914+ ],
1915+ "left" : {
1916+ "x" : 3.4 ,
1917+ "y" : 1.0 ,
1918+ "z" : 99999.34455663
1919+ },
1920+ "right" : {
1921+ "x" : 3.2 ,
1922+ "y" : 1.1 ,
1923+ "z" : 999.3663
1924+ },
1925+ }
1926+ r = client .post (url , data = {"v" : json .dumps (d )})
1927+ assert "v" in r .json
1928+ assert r .json ["v" ] == d
1929+ # Test that empty children list yields input value
1930+ d = {
1931+ "name" : "change da world" ,
1932+ "children" : [],
1933+ "left" : {
1934+ "x" : 3.4 ,
1935+ "y" : 1.0 ,
1936+ "z" : 99999.34455663
1937+ },
1938+ "right" : {
1939+ "x" : 3.2 ,
1940+ "y" : 1.1 ,
1941+ "z" : 999.3663
1942+ },
1943+ }
1944+ r = client .post (url , data = {"v" : json .dumps (d )})
1945+ assert "v" in r .json
1946+ assert r .json ["v" ] == d
1947+ # Test that incorrect child TypedDict yields error
1948+ d = {
1949+ "name" : "change da world" ,
1950+ "children" : [
1951+ {
1952+ "id" : 4 ,
1953+ "name" : 6 ,
1954+ "timestamp" : datetime .datetime .now ().isoformat (),
1955+ }
1956+ ],
1957+ "left" : {
1958+ "x" : 3.4 ,
1959+ "y" : 1.0 ,
1960+ "z" : 99999.34455663
1961+ },
1962+ "right" : {
1963+ "x" : 3.2 ,
1964+ "y" : 1.1 ,
1965+ "z" : 999.3663
1966+ },
1967+ }
1968+ r = client .post (url , data = {"v" : json .dumps (d )})
1969+ assert "error" in r .json
1970+ # Test that omitting NotRequired key in child yields input value
1971+ d = {
1972+ "name" : "tags" ,
1973+ "children" : [
1974+ {
1975+ "id" : 4 ,
1976+ "name" : "ice my wrist" ,
1977+ "timestamp" : datetime .datetime .now ().isoformat (),
1978+ }
1979+ ],
1980+ "left" : {
1981+ "x" : 3.4 ,
1982+ "y" : 1.0 ,
1983+ "z" : 99999.34455663
1984+ },
1985+ "right" : {
1986+ "x" : 3.2 ,
1987+ "y" : 1.1 ,
1988+ "z" : 999.3663
1989+ },
1990+ }
1991+ r = client .post (url , data = {"v" : json .dumps (d )})
1992+ assert "v" in r .json
1993+ assert r .json ["v" ] == d
1994+ # Test that incorrect values yields error
1995+ d = {"id" : 1.03 , "name" : "foo" , "timestamp" : datetime .datetime .now ().isoformat ()}
1996+ r = client .post (url , data = {"v" : json .dumps (d )})
1997+ assert "error" in r .json
17441998
0 commit comments