Skip to content

Commit b67cf9c

Browse files
committed
fixes #572
1 parent 1226761 commit b67cf9c

File tree

3 files changed

+70
-13
lines changed

3 files changed

+70
-13
lines changed

fastcore/_modidx.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -558,7 +558,9 @@
558558
'fastcore.xdg.xdg_runtime_dir': ('xdg.html#xdg_runtime_dir', 'fastcore/xdg.py'),
559559
'fastcore.xdg.xdg_state_home': ('xdg.html#xdg_state_home', 'fastcore/xdg.py')},
560560
'fastcore.xml': { 'fastcore.xml.XT': ('xml.html#xt', 'fastcore/xml.py'),
561+
'fastcore.xml.XT.__getattr__': ('xml.html#xt.__getattr__', 'fastcore/xml.py'),
561562
'fastcore.xml.XT.__init__': ('xml.html#xt.__init__', 'fastcore/xml.py'),
563+
'fastcore.xml.XT.__setattr__': ('xml.html#xt.__setattr__', 'fastcore/xml.py'),
562564
'fastcore.xml.XT.attrs': ('xml.html#xt.attrs', 'fastcore/xml.py'),
563565
'fastcore.xml.XT.children': ('xml.html#xt.children', 'fastcore/xml.py'),
564566
'fastcore.xml.XT.tag': ('xml.html#xt.tag', 'fastcore/xml.py'),

fastcore/xml.py

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -27,14 +27,22 @@ def _attrmap(o):
2727

2828
# %% ../nbs/11_xml.ipynb 5
2929
class XT(list):
30-
def __init__(self, tag, cs, attrs): super().__init__([tag, cs, attrs])
30+
def __init__(self, tag, cs, attrs=None, **kwargs): super().__init__([tag, cs, {**(attrs or {}), **kwargs}])
3131
@property
3232
def tag(self): return self[0]
3333
@property
3434
def children(self): return self[1]
3535
@property
3636
def attrs(self): return self[2]
3737

38+
def __setattr__(self, k, v):
39+
if k.startswith('__') or k in ('tag','cs','attrs'): return super().__setattr__(k,v)
40+
self.attrs[k.lstrip('_').replace('_', '-')] = v
41+
42+
def __getattr__(self, k):
43+
if k.startswith('__') or k not in self.attrs: raise AttributeError(k)
44+
return self.attrs[k.lstrip('_').replace('_', '-')]
45+
3846
# %% ../nbs/11_xml.ipynb 6
3947
def xt(tag:str, *c, **kw):
4048
"Create an XML tag structure `[tag,children,attrs]` for `toxml()`"
@@ -56,13 +64,13 @@ def xt(tag:str, *c, **kw):
5664

5765
for o in _all_: _g[o] = partial(xt, o.lower())
5866

59-
# %% ../nbs/11_xml.ipynb 12
67+
# %% ../nbs/11_xml.ipynb 14
6068
voids = set('area base br col command embed hr img input keygen link meta param source track wbr !doctype'.split())
6169

62-
# %% ../nbs/11_xml.ipynb 13
70+
# %% ../nbs/11_xml.ipynb 15
6371
def _escape(s): return '' if s is None else escape(s) if isinstance(s, str) else s
6472

65-
# %% ../nbs/11_xml.ipynb 14
73+
# %% ../nbs/11_xml.ipynb 16
6674
def _to_attr(k,v):
6775
if isinstance(v,bool):
6876
if v==True : return str(k)
@@ -74,7 +82,7 @@ def _to_attr(k,v):
7482
if qt in v: qt = "'"
7583
return f'{k}={qt}{v}{qt}'
7684

77-
# %% ../nbs/11_xml.ipynb 15
85+
# %% ../nbs/11_xml.ipynb 17
7886
def to_xml(elm, lvl=0):
7987
"Convert `xt` element tree into an XML string"
8088
if elm is None: return ''
@@ -98,12 +106,12 @@ def to_xml(elm, lvl=0):
98106
if tag not in voids: res += f'{sp}{cltag}\n'
99107
return res
100108

101-
# %% ../nbs/11_xml.ipynb 17
109+
# %% ../nbs/11_xml.ipynb 19
102110
def highlight(s, lang='xml'):
103111
"Markdown to syntax-highlight `s` in language `lang`"
104112
return f'```{lang}\n{to_xml(s)}\n```'
105113

106-
# %% ../nbs/11_xml.ipynb 18
114+
# %% ../nbs/11_xml.ipynb 20
107115
def showtags(s):
108116
return f"""<code><pre>
109117
{escape(to_xml(s))}

nbs/11_xml.ipynb

Lines changed: 53 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -72,13 +72,21 @@
7272
"source": [
7373
"#|export\n",
7474
"class XT(list):\n",
75-
" def __init__(self, tag, cs, attrs): super().__init__([tag, cs, attrs])\n",
75+
" def __init__(self, tag, cs, attrs=None, **kwargs): super().__init__([tag, cs, {**(attrs or {}), **kwargs}])\n",
7676
" @property\n",
7777
" def tag(self): return self[0]\n",
7878
" @property\n",
7979
" def children(self): return self[1]\n",
8080
" @property\n",
81-
" def attrs(self): return self[2]"
81+
" def attrs(self): return self[2]\n",
82+
"\n",
83+
" def __setattr__(self, k, v):\n",
84+
" if k.startswith('__') or k in ('tag','cs','attrs'): return super().__setattr__(k,v)\n",
85+
" self.attrs[k.lstrip('_').replace('_', '-')] = v\n",
86+
"\n",
87+
" def __getattr__(self, k):\n",
88+
" if k.startswith('__') or k not in self.attrs: raise AttributeError(k)\n",
89+
" return self.attrs[k.lstrip('_').replace('_', '-')]"
8290
]
8391
},
8492
{
@@ -144,7 +152,7 @@
144152
" (['div',\n",
145153
" ('Some text',\n",
146154
" ['input', (), {'name': 'me'}],\n",
147-
" ['img', (), {'data': {'a': 1}, 'src': 'filename'}]),\n",
155+
" ['img', (), {'data': 1, 'src': 'filename'}]),\n",
148156
" {'class': 'myclass'}],),\n",
149157
" {}]),\n",
150158
" {}]\n"
@@ -154,7 +162,7 @@
154162
"source": [
155163
"samp = Html(\n",
156164
" Head(Title('Some page')),\n",
157-
" Body(Div('Some text', Input(name='me'), Img(src=\"filename\", data={'a':1}), klass='myclass'))\n",
165+
" Body(Div('Some text', Input(name='me'), Img(src=\"filename\", data=1), klass='myclass'))\n",
158166
")\n",
159167
"pprint(samp)"
160168
]
@@ -190,6 +198,44 @@
190198
"print(elem.attrs)"
191199
]
192200
},
201+
{
202+
"cell_type": "markdown",
203+
"id": "bb61f88e",
204+
"metadata": {},
205+
"source": [
206+
"You can also get and set attrs directly:"
207+
]
208+
},
209+
{
210+
"cell_type": "code",
211+
"execution_count": null,
212+
"id": "5c7f175d",
213+
"metadata": {},
214+
"outputs": [
215+
{
216+
"name": "stdout",
217+
"output_type": "stream",
218+
"text": [
219+
"newid\n"
220+
]
221+
},
222+
{
223+
"data": {
224+
"text/plain": [
225+
"['p', ('Some text',), {'id': 'newid'}]"
226+
]
227+
},
228+
"execution_count": null,
229+
"metadata": {},
230+
"output_type": "execute_result"
231+
}
232+
],
233+
"source": [
234+
"elem.id = 'newid'\n",
235+
"print(elem.id)\n",
236+
"elem"
237+
]
238+
},
193239
{
194240
"cell_type": "code",
195241
"execution_count": null,
@@ -282,7 +328,7 @@
282328
" <div class=\"myclass\">\n",
283329
"Some text\n",
284330
" <input name=\"me\">\n",
285-
" <img src=\"filename\" data='{\"a\": 1}'>\n",
331+
" <img src=\"filename\" data=\"1\">\n",
286332
" </div>\n",
287333
" </body>\n",
288334
"</html>\n",
@@ -291,7 +337,8 @@
291337
}
292338
],
293339
"source": [
294-
"print(to_xml(samp))"
340+
"h = to_xml(samp)\n",
341+
"print(h)"
295342
]
296343
},
297344
{

0 commit comments

Comments
 (0)