[issue36300] eval of generator expressions cannot access local variables

2019-03-15 Thread Martin Hosken


New submission from Martin Hosken :

The following code fails:

>>> lcls = {'w': 100}
>>> eval('[w for x in ("hello", "world")]', None, lcls)
Traceback (most recent call last):
  File "", line 1, in 
  File "", line 1, in 
  File "", line 1, in 
NameError: name 'w' is not defined
>>> eval('[w, w, w]', None, lcls)
[100, 100, 100]

whereas in python2 it succeeds

>>> lcls = {'w': 100}
>>> eval('[w for x in ("hello", "world")]', None, lcls)
[100, 100]

--
messages: 337980
nosy: Martin Hosken
priority: normal
severity: normal
status: open
title: eval of generator expressions cannot access local variables

___
Python tracker 
<https://bugs.python.org/issue36300>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue36300] eval of generator expressions cannot access local variables

2019-03-15 Thread Martin Hosken


Change by Martin Hosken :


--
versions: +Python 3.6

___
Python tracker 
<https://bugs.python.org/issue36300>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue34600] python3 regression ElementTree.iterparse() unable to capture comments

2018-09-06 Thread Martin Hosken


New submission from Martin Hosken :

This is a regression from python2 by being forced to use cElementTree.

I have code that uses iterparse to process an XML file, but I also want to 
process comments and so I have a comment handling function called by the parser 
during iterparse. Under python3 I can find no way to achieve the same thing:

```
parser = et.XMLParser(target=et.TreeBuilder())
parser.parser.CommentHandler = myCommentHandler
for event, elem in et.iterparse(fh, parser=parser):
...
```

Somewhat ugly but works in python2, but I can find no way to set a comment 
handler on the parser in python3.


1. There is no way(?) to get to xml.etree.ElementTree.XMLParser since the C 
implementation completely masks the python versions.
2. It is possible to create a subclass of TreeBuilder to add a comment method. 
But the C version XMLParser requires that its TreeBuilder not be a subclass, 
when used in iterparse.

The only solution I found was to copy the XMLParser code out of ElementTree 
into a private module and use that pure python implementation.

Suggested solutions:
1. Allow access to all the python implementations in ElementTree and not just 
Element.
2. Allow a comments method to be passed to the XMLParser on creation.

Thank you.

--
components: XML
messages: 324719
nosy: Martin Hosken
priority: normal
severity: normal
status: open
title: python3 regression ElementTree.iterparse() unable to capture comments
type: behavior
versions: Python 3.6

___
Python tracker 
<https://bugs.python.org/issue34600>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue34600] python3 regression ElementTree.iterparse() unable to capture comments

2018-09-09 Thread Martin Hosken


Martin Hosken  added the comment:

Sorry. This test is rather long because it is 3 tests:

from __future__ import print_function
import sys
import xml.etree.ElementTree as et
import xml.etree.cElementTree as cet
from io import StringIO

teststr = u"""


Hello  World

"""
testf = StringIO(teststr)

if len(sys.argv) >= 2 and 'a' in sys.argv[1]:
testf.seek(0)
for event, elem in et.iterparse(testf, events=["end", "comment"]):
if event == 'end':
print(elem.tag + ": " + str(elem.text))
elif event == 'comment':
print("comment: " + elem.text)

if len(sys.argv) < 2 or 'b' in sys.argv[1]:
testf.seek(0)
def doComment(data):
parser.parser.StartElementHandler("!--", ('text', data))
parser.parser.EndElementHandler("!--")
parser = et.XMLParser()
parser.parser.CommentHandler = doComment
for event, elem in et.iterparse(testf, parser=parser):
if hasattr(elem, 'text'):
print(elem.tag + ": " + str(elem.text))
else:
print(elem.tag + ": " + elem.get('text', ""))

if len(sys.argv) < 2 or 'c' in sys.argv[1] or 'd' in sys.argv[1]:
testf.seek(0)
useet = et if len(sys.argv) < 2 or 'c' in sys.argv[1] else cet
class CommentingTb(useet.TreeBuilder):
def __init__(self):
self.parser = None
def comment(self, data):
self.parser.parser.StartElementHandler("!--", ('text', data))
self.parser.parser.EndElementHandler("!--")
tb = CommentingTb()
parser = useet.XMLParser(target=tb)
tb.parser = parser
kw = {'parser': parser} if len(sys.argv) < 2 or 'c' in sys.argv[1] else {}
for event, elem in useet.iterparse(testf, **kw):
if hasattr(elem, 'text'):
print(elem.tag + ": " + str(elem.text))
else:
print(elem.tag + ": " + elem.get('text', ""))

Test 'a' is how I would like to write the solution to my problem. Not sure why 
'comment' isn't supported by iterparse directly, but hey.

Test 'b' is how I solved in it python2

Test 'c' is how I would have to solve it in python3 if it worked

Test 'd' is the same as 'c' but uses cElementTree rather than ElementTree.

Results:

Success output for a test is:
```
!--: None
child: 
Hello 
root: 

```

Python2:
aFails (obviously)
bSucceeds
cSucceeds
dFails: can't inherit from cElementTree.TreeBuilder

Python3:
aFails (obviously)
bFails: XMLParser has no attribute 'parser'
cFails: event handling only supported for ElementTree.TreeBuilder targets
dFails: Gives output but no initial comment component (line 1)

The key failure here is Python3 'c'. This is what stops any hope of comment 
handling using the et.XMLParser. The only way I could get around it was to use 
my own copy from the source code.

--

___
Python tracker 
<https://bugs.python.org/issue34600>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue34600] python3 regression ElementTree.iterparse() unable to capture comments

2018-09-09 Thread Martin Hosken


Martin Hosken  added the comment:

Blast. Bugs. Sorry. Missing superclass init call in CommentingTb. I enclose the 
whole thing again to save editing. Also fixes comment output to give text.

from __future__ import print_function
import sys
import xml.etree.ElementTree as et
import xml.etree.cElementTree as cet
from io import StringIO

teststr = u"""


Hello  World

"""
testf = StringIO(teststr)

if len(sys.argv) >= 2 and 'a' in sys.argv[1]:
testf.seek(0)
for event, elem in et.iterparse(testf, events=["end", "comment"]):
if event == 'end':
print(elem.tag + ": " + str(elem.text))
elif event == 'comment':
print("comment: " + elem.text)

if len(sys.argv) < 2 or 'b' in sys.argv[1]:
testf.seek(0)
def doComment(data):
parser.parser.StartElementHandler("!--", ('text', data))
parser.parser.EndElementHandler("!--")
parser = et.XMLParser()
parser.parser.CommentHandler = doComment
for event, elem in et.iterparse(testf, parser=parser):
if elem.tag == "!--":
print(elem.tag + ": " + elem.get('text', ""))
else:
print(elem.tag + ": " + str(elem.text))

if len(sys.argv) < 2 or 'c' in sys.argv[1] or 'd' in sys.argv[1]:
testf.seek(0)
useet = et if len(sys.argv) < 2 or 'c' in sys.argv[1] else cet
class CommentingTb(useet.TreeBuilder):
def __init__(self):
useet.TreeBuilder.__init__(self)
self.parser = None
def comment(self, data):
self.parser.parser.StartElementHandler("!--", ('text', data))
self.parser.parser.EndElementHandler("!--")
tb = CommentingTb()
parser = useet.XMLParser(target=tb)
tb.parser = parser
kw = {'parser': parser} if len(sys.argv) < 2 or 'c' in sys.argv[1] else {}
for event, elem in useet.iterparse(testf, **kw):
if elem.tag == "!--":
print(elem.tag + ": " + elem.get('text', ""))
else:
print(elem.tag + ": " + str(elem.text))

--

___
Python tracker 
<https://bugs.python.org/issue34600>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com