python-fasthtml 0.1.5__tar.gz → 0.1.7__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {python_fasthtml-0.1.5/python_fasthtml.egg-info → python-fasthtml-0.1.7}/PKG-INFO +1 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/__init__.py +1 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/_modidx.py +3 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/components.py +18 -13
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/components.pyi +5 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/core.py +10 -8
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/fastapp.py +4 -3
- python-fasthtml-0.1.7/fasthtml/xt.py +4 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/xtend.py +3 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/xtend.pyi +3 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7/python_fasthtml.egg-info}/PKG-INFO +1 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/SOURCES.txt +1 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/settings.ini +1 -1
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/LICENSE +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/MANIFEST.in +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/README.md +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/authmw.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/cli.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/common.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/js.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/live_reload.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/oauth.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/starlette.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/svg.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/fasthtml/toaster.py +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/dependency_links.txt +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/entry_points.txt +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/not-zip-safe +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/requires.txt +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/top_level.txt +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/setup.cfg +0 -0
- {python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/setup.py +0 -0
|
@@ -10,7 +10,8 @@ d = { 'settings': { 'branch': 'main',
|
|
|
10
10
|
'fasthtml.cli.railway_deploy': ('cli.html#railway_deploy', 'fasthtml/cli.py'),
|
|
11
11
|
'fasthtml.cli.railway_link': ('cli.html#railway_link', 'fasthtml/cli.py')},
|
|
12
12
|
'fasthtml.common': {},
|
|
13
|
-
'fasthtml.components': { 'fasthtml.components.
|
|
13
|
+
'fasthtml.components': { 'fasthtml.components.File': ('components.html#file', 'fasthtml/components.py'),
|
|
14
|
+
'fasthtml.components.__getattr__': ('components.html#__getattr__', 'fasthtml/components.py'),
|
|
14
15
|
'fasthtml.components._fill_item': ('components.html#_fill_item', 'fasthtml/components.py'),
|
|
15
16
|
'fasthtml.components.fill_dataclass': ('components.html#fill_dataclass', 'fasthtml/components.py'),
|
|
16
17
|
'fasthtml.components.fill_form': ('components.html#fill_form', 'fasthtml/components.py'),
|
|
@@ -84,6 +85,7 @@ d = { 'settings': { 'branch': 'main',
|
|
|
84
85
|
'fasthtml.starlette': {},
|
|
85
86
|
'fasthtml.svg': {},
|
|
86
87
|
'fasthtml.toaster': {},
|
|
88
|
+
'fasthtml.xt': {},
|
|
87
89
|
'fasthtml.xtend': { 'fasthtml.xtend.A': ('xtend.html#a', 'fasthtml/xtend.py'),
|
|
88
90
|
'fasthtml.xtend.AX': ('xtend.html#ax', 'fasthtml/xtend.py'),
|
|
89
91
|
'fasthtml.xtend.Card': ('xtend.html#card', 'fasthtml/xtend.py'),
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
# AUTOGENERATED! DO NOT EDIT! File to edit: ../nbs/01_components.ipynb.
|
|
2
2
|
|
|
3
3
|
# %% auto 0
|
|
4
|
-
__all__ = ['voids', 'named', 'html_attrs', 'hx_attrs', 'show', 'xt_html', 'xt_hx', '
|
|
5
|
-
'html2xt', 'A', 'Abbr', 'Address', 'Area', 'Article', 'Aside', 'Audio', 'B', 'Base', 'Bdi',
|
|
6
|
-
'Blockquote', 'Body', 'Br', 'Button', 'Canvas', 'Caption', 'Cite', 'Code', 'Col', 'Colgroup', 'Data',
|
|
4
|
+
__all__ = ['voids', 'named', 'html_attrs', 'hx_attrs', 'show', 'xt_html', 'xt_hx', 'File', 'fill_form', 'fill_dataclass',
|
|
5
|
+
'find_inputs', 'html2xt', 'A', 'Abbr', 'Address', 'Area', 'Article', 'Aside', 'Audio', 'B', 'Base', 'Bdi',
|
|
6
|
+
'Bdo', 'Blockquote', 'Body', 'Br', 'Button', 'Canvas', 'Caption', 'Cite', 'Code', 'Col', 'Colgroup', 'Data',
|
|
7
7
|
'Datalist', 'Dd', 'Del', 'Details', 'Dfn', 'Dialog', 'Div', 'Dl', 'Dt', 'Em', 'Embed', 'Fencedframe',
|
|
8
8
|
'Fieldset', 'Figcaption', 'Figure', 'Footer', 'Form', 'H1', 'Head', 'Header', 'Hgroup', 'Hr', 'Html', 'I',
|
|
9
9
|
'Iframe', 'Img', 'Input', 'Ins', 'Kbd', 'Label', 'Legend', 'Li', 'Link', 'Main', 'Map', 'Mark', 'Menu',
|
|
@@ -65,7 +65,12 @@ _all_ = [
|
|
|
65
65
|
'Td', 'Template', 'Textarea', 'Tfoot', 'Th', 'Thead', 'Time', 'Title', 'Tr', 'Track', 'U', 'Ul', 'Var', 'Video', 'Wbr']
|
|
66
66
|
for o in _all_: _g[o] = partial(xt_hx, o.lower())
|
|
67
67
|
|
|
68
|
-
# %% ../nbs/01_components.ipynb
|
|
68
|
+
# %% ../nbs/01_components.ipynb 9
|
|
69
|
+
def File(fname):
|
|
70
|
+
"Use the unescaped text in file `fname` directly"
|
|
71
|
+
return NotStr(Path(fname).read_text())
|
|
72
|
+
|
|
73
|
+
# %% ../nbs/01_components.ipynb 14
|
|
69
74
|
def _fill_item(item, obj):
|
|
70
75
|
if not isinstance(item,list): return item
|
|
71
76
|
tag,cs,attr = item
|
|
@@ -81,19 +86,19 @@ def _fill_item(item, obj):
|
|
|
81
86
|
if tag=='textarea': cs=(val,)
|
|
82
87
|
return XT(tag,cs,attr)
|
|
83
88
|
|
|
84
|
-
# %% ../nbs/01_components.ipynb
|
|
89
|
+
# %% ../nbs/01_components.ipynb 15
|
|
85
90
|
def fill_form(form:XT, obj)->XT:
|
|
86
91
|
"Fills named items in `form` using attributes in `obj`"
|
|
87
92
|
if not isinstance(obj,dict): obj = asdict(obj)
|
|
88
93
|
return _fill_item(form, obj)
|
|
89
94
|
|
|
90
|
-
# %% ../nbs/01_components.ipynb
|
|
95
|
+
# %% ../nbs/01_components.ipynb 17
|
|
91
96
|
def fill_dataclass(src, dest):
|
|
92
97
|
"Modifies dataclass in-place and returns it"
|
|
93
98
|
for nm,val in asdict(src).items(): setattr(dest, nm, val)
|
|
94
99
|
return dest
|
|
95
100
|
|
|
96
|
-
# %% ../nbs/01_components.ipynb
|
|
101
|
+
# %% ../nbs/01_components.ipynb 19
|
|
97
102
|
def find_inputs(e, tags='input', **kw):
|
|
98
103
|
# Recursively find all elements in `e` with `tags` and attrs matching `kw`
|
|
99
104
|
if not isinstance(e, (list,tuple)): return []
|
|
@@ -107,18 +112,18 @@ def find_inputs(e, tags='input', **kw):
|
|
|
107
112
|
for o in cs: inputs += find_inputs(o, tags, **kw)
|
|
108
113
|
return inputs
|
|
109
114
|
|
|
110
|
-
# %% ../nbs/01_components.ipynb
|
|
115
|
+
# %% ../nbs/01_components.ipynb 23
|
|
111
116
|
def __getattr__(tag):
|
|
112
117
|
if tag.startswith('_') or tag[0].islower(): raise AttributeError
|
|
113
118
|
tag = tag.replace("_", "-")
|
|
114
119
|
def _f(*c, target_id=None, **kwargs): return xt_hx(tag, *c, target_id=target_id, **kwargs)
|
|
115
120
|
return _f
|
|
116
121
|
|
|
117
|
-
# %% ../nbs/01_components.ipynb
|
|
122
|
+
# %% ../nbs/01_components.ipynb 24
|
|
118
123
|
def html2xt(html):
|
|
119
124
|
rev_map = {'class': 'cls', 'for': 'fr'}
|
|
120
125
|
|
|
121
|
-
def _parse(elm, lvl=0):
|
|
126
|
+
def _parse(elm, lvl=0, indent=4):
|
|
122
127
|
if isinstance(elm, str): return repr(elm.strip()) if elm.strip() else ''
|
|
123
128
|
if isinstance(elm, list): return '\n'.join(_parse(o, lvl) for o in elm)
|
|
124
129
|
tag_name = elm.name.capitalize()
|
|
@@ -127,14 +132,14 @@ def html2xt(html):
|
|
|
127
132
|
cs = [repr(c.strip()) if isinstance(c, str) else _parse(c, lvl+1)
|
|
128
133
|
for c in cts if str(c).strip()]
|
|
129
134
|
attrs = []
|
|
130
|
-
for key, value in elm.attrs.items():
|
|
135
|
+
for key, value in sorted(elm.attrs.items(), key=lambda x: x[0]=='class'):
|
|
131
136
|
if isinstance(value,(tuple,list)): value = " ".join(value)
|
|
132
137
|
attrs.append(f'{rev_map.get(key, key).replace("-", "_")}={value!r}')
|
|
133
|
-
spc = " "*lvl*
|
|
138
|
+
spc = " "*lvl*indent
|
|
134
139
|
onlychild = not cts or (len(cts)==1 and isinstance(cts[0],str))
|
|
135
140
|
j = ', ' if onlychild else f',\n{spc}'
|
|
136
141
|
inner = j.join(filter(None, cs+attrs))
|
|
137
142
|
if onlychild: return f'{tag_name}({inner})'
|
|
138
|
-
return f'{tag_name}(\n{spc}{inner}\n{" "*(lvl-1)*
|
|
143
|
+
return f'{tag_name}(\n{spc}{inner}\n{" "*(lvl-1)*indent})'
|
|
139
144
|
|
|
140
145
|
return _parse(BeautifulSoup(html.strip(), 'html.parser'), 1)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
__all__ = ['voids', 'named', 'html_attrs', 'hx_attrs', 'show', 'xt_html', 'xt_hx', 'fill_form', 'fill_dataclass', 'find_inputs', 'html2xt', 'A', 'Abbr', 'Address', 'Area', 'Article', 'Aside', 'Audio', 'B', 'Base', 'Bdi', 'Bdo', 'Blockquote', 'Body', 'Br', 'Button', 'Canvas', 'Caption', 'Cite', 'Code', 'Col', 'Colgroup', 'Data', 'Datalist', 'Dd', 'Del', 'Details', 'Dfn', 'Dialog', 'Div', 'Dl', 'Dt', 'Em', 'Embed', 'Fencedframe', 'Fieldset', 'Figcaption', 'Figure', 'Footer', 'Form', 'H1', 'Head', 'Header', 'Hgroup', 'Hr', 'Html', 'I', 'Iframe', 'Img', 'Input', 'Ins', 'Kbd', 'Label', 'Legend', 'Li', 'Link', 'Main', 'Map', 'Mark', 'Menu', 'Meta', 'Meter', 'Nav', 'Noscript', 'Object', 'Ol', 'Optgroup', 'Option', 'Output', 'P', 'Picture', 'PortalExperimental', 'Pre', 'Progress', 'Q', 'Rp', 'Rt', 'Ruby', 'S', 'Samp', 'Script', 'Search', 'Section', 'Select', 'Slot', 'Small', 'Source', 'Span', 'Strong', 'Style', 'Sub', 'Summary', 'Sup', 'Table', 'Tbody', 'Td', 'Template', 'Textarea', 'Tfoot', 'Th', 'Thead', 'Time', 'Title', 'Tr', 'Track', 'U', 'Ul', 'Var', 'Video', 'Wbr']
|
|
1
|
+
__all__ = ['voids', 'named', 'html_attrs', 'hx_attrs', 'show', 'xt_html', 'xt_hx', 'File', 'fill_form', 'fill_dataclass', 'find_inputs', 'html2xt', 'A', 'Abbr', 'Address', 'Area', 'Article', 'Aside', 'Audio', 'B', 'Base', 'Bdi', 'Bdo', 'Blockquote', 'Body', 'Br', 'Button', 'Canvas', 'Caption', 'Cite', 'Code', 'Col', 'Colgroup', 'Data', 'Datalist', 'Dd', 'Del', 'Details', 'Dfn', 'Dialog', 'Div', 'Dl', 'Dt', 'Em', 'Embed', 'Fencedframe', 'Fieldset', 'Figcaption', 'Figure', 'Footer', 'Form', 'H1', 'Head', 'Header', 'Hgroup', 'Hr', 'Html', 'I', 'Iframe', 'Img', 'Input', 'Ins', 'Kbd', 'Label', 'Legend', 'Li', 'Link', 'Main', 'Map', 'Mark', 'Menu', 'Meta', 'Meter', 'Nav', 'Noscript', 'Object', 'Ol', 'Optgroup', 'Option', 'Output', 'P', 'Picture', 'PortalExperimental', 'Pre', 'Progress', 'Q', 'Rp', 'Rt', 'Ruby', 'S', 'Samp', 'Script', 'Search', 'Section', 'Select', 'Slot', 'Small', 'Source', 'Span', 'Strong', 'Style', 'Sub', 'Summary', 'Sup', 'Table', 'Tbody', 'Td', 'Template', 'Textarea', 'Tfoot', 'Th', 'Thead', 'Time', 'Title', 'Tr', 'Track', 'U', 'Ul', 'Var', 'Video', 'Wbr']
|
|
2
2
|
from dataclasses import dataclass, asdict, is_dataclass, make_dataclass, replace, astuple, MISSING
|
|
3
3
|
from bs4 import BeautifulSoup
|
|
4
4
|
from fastcore.utils import *
|
|
@@ -29,6 +29,10 @@ _all_ = ['A', 'Abbr', 'Address', 'Area', 'Article', 'Aside', 'Audio', 'B', 'Base
|
|
|
29
29
|
for o in _all_:
|
|
30
30
|
_g[o] = partial(xt_hx, o.lower())
|
|
31
31
|
|
|
32
|
+
def File(fname):
|
|
33
|
+
"""Use the unescaped text in file `fname` directly"""
|
|
34
|
+
...
|
|
35
|
+
|
|
32
36
|
def _fill_item(item, obj):
|
|
33
37
|
...
|
|
34
38
|
|
|
@@ -127,7 +127,7 @@ async def _from_body(req, p):
|
|
|
127
127
|
anno = p.annotation
|
|
128
128
|
# Get the fields and types of type `anno`, if available
|
|
129
129
|
d = _annotations(anno)
|
|
130
|
-
cargs = {k:_form_arg(k, v, d) for k,v in form2dict(form).items()}
|
|
130
|
+
cargs = {k:_form_arg(k, v, d) for k,v in form2dict(form).items() if not d or k in d}
|
|
131
131
|
return anno(**cargs)
|
|
132
132
|
|
|
133
133
|
# %% ../nbs/00_core.ipynb 37
|
|
@@ -150,15 +150,17 @@ async def _find_p(req, arg:str, p:Parameter):
|
|
|
150
150
|
return None
|
|
151
151
|
# Look through path, cookies, headers, session, query, and body in that order
|
|
152
152
|
res = req.path_params.get(arg, None)
|
|
153
|
-
if res
|
|
154
|
-
if res
|
|
155
|
-
if res
|
|
156
|
-
if res
|
|
157
|
-
if res
|
|
153
|
+
if res in (empty,None): res = req.cookies.get(arg, None)
|
|
154
|
+
if res in (empty,None): res = req.headers.get(snake2hyphens(arg), None)
|
|
155
|
+
if res in (empty,None): res = nested_idx(req.scope, 'session', arg) or None
|
|
156
|
+
if res in (empty,None): res = req.query_params.get(arg, None)
|
|
157
|
+
if res in (empty,None):
|
|
158
158
|
frm = await req.form()
|
|
159
159
|
res = _formitem(frm, arg)
|
|
160
|
-
#
|
|
161
|
-
if res
|
|
160
|
+
# Raise 400 error if the param does not include a default
|
|
161
|
+
if (res in (empty,None)) and p.default is empty: raise HTTPException(400, f"Missing required field: {arg}")
|
|
162
|
+
# If we have a default, return that if we have no value
|
|
163
|
+
if res in (empty,None): res = p.default
|
|
162
164
|
# We can cast str and list[str] to types; otherwise just return what we have
|
|
163
165
|
if not isinstance(res, (list,str)) or anno is empty: return res
|
|
164
166
|
anno = _fix_anno(anno)
|
|
@@ -14,14 +14,15 @@ def get_tbl(dt, nm, schema):
|
|
|
14
14
|
|
|
15
15
|
def fast_app(db=None, render=None, hdrs=None, tbls=None, before=None, middleware=None, live=False, debug=False, routes=None, exception_handlers=None,
|
|
16
16
|
on_startup=None, on_shutdown=None, lifespan=None, default_hdrs=True, secret_key=None, session_cookie='session_', max_age=365*24*3600,
|
|
17
|
-
sess_path='/', same_site='lax', sess_https_only=False, sess_domain=None, key_fname='.sesskey', **kwargs):
|
|
18
|
-
|
|
17
|
+
pico=None, sess_path='/', same_site='lax', sess_https_only=False, sess_domain=None, key_fname='.sesskey', bodykw=None, **kwargs):
|
|
18
|
+
|
|
19
|
+
h = (picolink,) if pico or (pico is None and default_hdrs) else ()
|
|
19
20
|
if hdrs: h += tuple(hdrs)
|
|
20
21
|
app_cls = FastHTMLWithLiveReload if live else FastHTML
|
|
21
22
|
app = app_cls(hdrs=h, before=before, middleware=middleware, debug=debug, routes=routes, exception_handlers=exception_handlers,
|
|
22
23
|
on_startup=on_startup, on_shutdown=on_shutdown, lifespan=lifespan, default_hdrs=default_hdrs, secret_key=secret_key,
|
|
23
24
|
session_cookie=session_cookie, max_age=max_age, sess_path=sess_path, same_site=same_site, sess_https_only=sess_https_only,
|
|
24
|
-
sess_domain=sess_domain, key_fname=key_fname)
|
|
25
|
+
sess_domain=sess_domain, key_fname=key_fname, **(bodykw or {}))
|
|
25
26
|
@app.route("/{fname:path}.{ext:static}")
|
|
26
27
|
async def get(fname:str, ext:str): return FileResponse(f'{fname}.{ext}')
|
|
27
28
|
if not db: return app,app.route
|
|
@@ -148,7 +148,7 @@ def loose_format(s, **kw):
|
|
|
148
148
|
|
|
149
149
|
# %% ../nbs/02_xtend.ipynb 34
|
|
150
150
|
def ScriptX(fname, type=None, _async=None, defer=None, charset=None, crossorigin=None, integrity=None, **kw):
|
|
151
|
-
"
|
|
151
|
+
"A `script` element with contents read from `fname`"
|
|
152
152
|
attrs = ['src', 'type', 'async', 'defer', 'charset', 'crossorigin', 'integrity', 'nomodule']
|
|
153
153
|
scr_kw = {k:kw.pop(k) for k in attrs if k in kw}
|
|
154
154
|
s = loose_format(Path(fname).read_text(), **kw)
|
|
@@ -156,6 +156,7 @@ def ScriptX(fname, type=None, _async=None, defer=None, charset=None, crossorigin
|
|
|
156
156
|
|
|
157
157
|
# %% ../nbs/02_xtend.ipynb 35
|
|
158
158
|
def replace_css_vars(css, pre='tpl', **kwargs):
|
|
159
|
+
"Replace `var(--)` CSS variables with `kwargs` if name prefix matches `pre`"
|
|
159
160
|
def replace_var(m):
|
|
160
161
|
var_name = m.group(1).replace('-', '_')
|
|
161
162
|
return kwargs.get(var_name, m.group(0))
|
|
@@ -163,6 +164,7 @@ def replace_css_vars(css, pre='tpl', **kwargs):
|
|
|
163
164
|
|
|
164
165
|
# %% ../nbs/02_xtend.ipynb 36
|
|
165
166
|
def StyleX(fname, **kw):
|
|
167
|
+
"A `style` element with contents read from `fname` and variables replaced from `kw`"
|
|
166
168
|
s = Path(fname).read_text()
|
|
167
169
|
attrs = ['type', 'media', 'scoped', 'title', 'nonce', 'integrity', 'crossorigin']
|
|
168
170
|
sty_kw = {k:kw.pop(k) for k in attrs if k in kw}
|
|
@@ -82,13 +82,15 @@ def loose_format(s, **kw):
|
|
|
82
82
|
...
|
|
83
83
|
|
|
84
84
|
def ScriptX(fname, type=None, _async=None, defer=None, charset=None, crossorigin=None, integrity=None, **kw):
|
|
85
|
-
"""
|
|
85
|
+
"""A `script` element with contents read from `fname`"""
|
|
86
86
|
...
|
|
87
87
|
|
|
88
88
|
def replace_css_vars(css, pre='tpl', **kwargs):
|
|
89
|
+
"""Replace `var(--)` CSS variables with `kwargs` if name prefix matches `pre`"""
|
|
89
90
|
...
|
|
90
91
|
|
|
91
92
|
def StyleX(fname, **kw):
|
|
93
|
+
"""A `style` element with contents read from `fname` and variables replaced from `kw`"""
|
|
92
94
|
...
|
|
93
95
|
|
|
94
96
|
def run_js(js, id=None, **kw):
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
[DEFAULT]
|
|
2
2
|
repo = fasthtml
|
|
3
3
|
lib_name = fasthtml
|
|
4
|
-
version = 0.1.
|
|
4
|
+
version = 0.1.7
|
|
5
5
|
min_python = 3.10
|
|
6
6
|
license = apache2
|
|
7
7
|
requirements = fastcore>=1.5.46 python-dateutil starlette>0.33 oauthlib itsdangerous uvicorn[standard]>=0.30 httpx fastlite>=0.0.6 python-multipart beautifulsoup4
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{python_fasthtml-0.1.5 → python-fasthtml-0.1.7}/python_fasthtml.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|