My template engine translates
"some data #{substitution_expression} some other data"
into
"some data" + (substitution_expression) + "some other data"
But if "some data" or "some other data" would have double quotes inside, the evalution fails.
I have to add slashes before these quotes, but I can not come up with the right regular expression for that.
Any help?
UPDATE:
This is how the template engine works:
It gets a template string, e.g.
template = 'template string "quoted text" #{expression}'
It changes the template string by a simple regexp to:
template = '"%s"' % re.compile(r'\#{(.*)}').match(r'" + (\1) + "', template)
# template == "template string "quoted text"" + (expression) + ""
# here is a problem with a "quoted text" - it needs \ before quotes`
This string is being inserted into lambda, and the result code string is being evaled:
return eval("lambda tpl_args: %s" % modified_template_string)
The lambda is being called later at the program with some tpl_args to generate a result string.
Have you tried the re.DOTALL flag?
re.compile(r'\#{(.*)}', re.DOTALL)
Related
I want to pass an array of strings to Mako's render method but this doesn't work:
from mako.template import Template
mytemplate = Template(filename="some.template")
str = mytemplate.render(first="John", last="Smith", nicknames=[
"JJ", "Johnny", "Jon"])
print(str)
some.template =
Hello ${first} ${last}
Your nicknames are:
% for n in ${nicknames}:
${n}
% endfor
Within a '%' line, you're writing regular Python code that doesn't need the escaping:
% for n in nicknames:
${n}
% endfor
I am trying to upload some data to Dydra from a Sesame triplestore I have on my computer. While the download from Sesame works fine, the triples get mixed up (the s-p-o relationships change as the object of one becomes object of another). Can someone please explain why this is happening and how it can be resolved? The code is below:
#Querying the triplestore to retrieve all results
sesameSparqlEndpoint = 'http://my.ip.ad.here:8080/openrdf-sesame/repositories/rep_name'
sparql = SPARQLWrapper(sesameSparqlEndpoint)
queryStringDownload = 'SELECT * WHERE {?s ?p ?o}'
dataGraph = Graph()
sparql.setQuery(queryStringDownload)
sparql.method = 'GET'
sparql.setReturnFormat(JSON)
output = sparql.query().convert()
print output
for i in range(len(output['results']['bindings'])):
#The encoding is necessary to parse non-English characters
output['results']['bindings'][i]['s']['value'].encode('utf-8')
try:
subject_extract = output['results']['bindings'][i]['s']['value']
if 'http' in subject_extract:
subject = "<" + subject_extract + ">"
subject_url = URIRef(subject)
print subject_url
predicate_extract = output['results']['bindings'][i]['p']['value']
if 'http' in predicate_extract:
predicate = "<" + predicate_extract + ">"
predicate_url = URIRef(predicate)
print predicate_url
objec_extract = output['results']['bindings'][i]['o']['value']
if 'http' in objec_extract:
objec = "<" + objec_extract + ">"
objec_url = URIRef(objec)
print objec_url
else:
objec = objec_extract
objec_wip = '"' + objec + '"'
objec_url = URIRef(objec_wip)
# Loading the data on a graph
dataGraph.add((subject_url,predicate_url,objec_url))
except UnicodeError as error:
print error
#Print all statements in dataGraph
for stmt in dataGraph:
pprint.pprint(stmt)
# Upload to Dydra
URL = 'http://dydra.com/login'
key = 'my_key'
with requests.Session() as s:
resp = s.get(URL)
soup = BeautifulSoup(resp.text,"html5lib")
csrfToken = soup.find('meta',{'name':'csrf-token'}).get('content')
# print csrf_token
payload = {
'account[login]':key,
'account[password]':'',
'csrfmiddlewaretoken':csrfToken,
'next':'/'
}
# print payload
p = s.post(URL,data=payload, headers=dict(Referer=URL))
# print p.text
r = s.get('http://dydra.com/username/rep_name/sparql')
# print r.text
dydraSparqlEndpoint = 'http://dydra.com/username/rep_name/sparql'
for stmt in dataGraph:
queryStringUpload = 'INSERT DATA {%s %s %s}' % stmt
sparql = SPARQLWrapper(dydraSparqlEndpoint)
sparql.setCredentials(key,key)
sparql.setQuery(queryStringUpload)
sparql.method = 'POST'
sparql.query()
A far simpler way to copy your data over (apart from using a CONSTRUCT query instead of a SELECT, like I mentioned in the comment) is simply to have Dydra itself directly access your Sesame endpoint, for example via a SERVICE-clause.
Execute the following on your Dydra database, and (after some time, depending on how large your Sesame database is), everything will be copied over:
INSERT { ?s ?p ?o }
WHERE {
SERVICE <http://my.ip.ad.here:8080/openrdf-sesame/repositories/rep_name>
{ ?s ?p ?o }
}
If the above doesn't work on Dydra, you can alternatively just directly access the RDF statements from your Sesame store by using the URI http://my.ip.ad.here:8080/openrdf-sesame/repositories/rep_name/statements. Assuming Dydra has an upload-feature where you can provide the URL of an RDF document, you can simply provide it the above URI and it should be able to load it.
The code above can work if the following changes are made:
Use CONSTRUCT query instead of SELECT. Details here -> How to iterate over CONSTRUCT output from rdflib?
Use key as input for both account[login] and account[password]
However, this is probably not the most efficient way. Primarily, doing individual INSERTs for every triple is not a good way. Dydra doesn't record all statements this way (I got only about 30% of the triples inserted). On the contrary, using the http://my.ip.ad.here:8080/openrdf-sesame/repositories/rep_name/statements method as suggested by Jeen enabled me to port all the data successfully.
Is there a way to display line breaks in a rendered Django string?
contact_message = "Name: %s | Email: %s" % (
form_name,
form_email,
)
For example, the code above currently prints as:
Name: <rendered name> | Email: <rendered email>
Is there a way to make it print like this:
Name: <rendered name>
Email: <rendered email>
I will be using the send_mail function, so I am hoping to make the readability more visually appealing.
Thank you!
When sending mail, a simple \n should be enough:
contact_message = "Name: %s\nEmail: %s" % (
form_name,
form_email,
)
This won't work in HTML, there you need HTML tags and then you have to mark the string as safe: https://docs.djangoproject.com/en/1.8/ref/utils/#module-django.utils.safestring
if you want just to have a new line you can just do it with:
contact_message = "Name: %s \n Email: %s" % (
form_name,
form_email,
)
\n is the way to go in django!
This is how I retrieve the post data from the webpage. The person models can be saved but it includes the "(u'')" string. For example if change the firstname to "Alex", it gets the raw value u('Alex') and saves it.
def submit_e(req, person_id=None):
if(req.POST):
try:
person_id = req.POST['driver']
person = Person.objects.get(pk=person_id)
person.firstname = req.POST['firstname'],
person.midname = req.POST['middleinitial'],
person.lastname = req.POST['lastname'],
person.full_clean()
person.save()
except Exception as e:
print e
return HttpResponseRedirect(reverse('users:user_main'))
NB: the following is my best guess at what you are seeing based on your question. If I have guessed wrongly, the please update your post with more details - putting print statements throughout your code and adding the output to your post would be a good start.
The u prefix on a string indicates a Unicode string. It is not actually part of the contents of the string. If we create a string in the interpreter:
>>> name = u'Me'
and then request details of the string,
>>> name
u'Me'
then the u is shown as it is part of the information about the string, which is what we have requested. If we print the contents of the string
>>> print name
Me
then the u is not shown (just like the quotes aren't shown).
Using the interpreter to try and reproduce your problem, I created a new user with a Unicode string for a username:
>>> from django.contrib.auth.models import User
>>> new_user = User()
>>> new_user.username = u'Me'
>>> new_user.save()
And as before, if we request the details about the string we see the u and the quotes, but if we print the contents of the string we don't:
>>> new_user.username
u'Me'
>>> print new_user.username
>>> Me
To further confirm the u was not stored, we can explore the database directly:
sqlite> select username from auth_user;
Me
you need to delete the "," at the end of each line
so, before:
person.firstname = req.POST['firstname'],
person.midname = req.POST['middleinitial'],
person.lastname = req.POST['lastname'],
after
person.firstname = req.POST['firstname']
person.midname = req.POST['middleinitial']
person.lastname = req.POST['lastname']
What I want to do is:
property = "name"
formatter = "my %s is %s" % property
print formatter % "wong2" // "my name is wong2"
but the first line gives "not enough arguments for format string" error.
>>> property = "name"
>>> formatter = "my %s is %%s" % property
>>> print formatter % "wong2"
my name is wong2
A double-percent will create a single-percent sign after formatting:
formatter = "my %s is %%s"
You can escape a formatter by doubling it
formatter = "my %s is %%s" % property
You can also do all substitutions at the same time using by-name instead of positional formatting:
formatter = "my %(property)s is %(name)s"
print formatter % { "property": "name",
"name": "wong2" }
This forms allows for a variable number of substitutions (i.e. not all keys in the dictionary needs to be used and they may be used more than once). This is important if for example the format string is read from a configuration file.
Here's a fun way to do it with a helper class
>>> property = "name"
>>> class D(dict):
... def __missing__(self, key):
... return "%("+key+")s"
...
>>> formatter = "my %(property)s is %(value)s"%D(property=property)
>>> formatter%D(value="wong2")
'my name is wong2'
I personally don't like the % formatting syntax, so I'll suggest quite the same as previous answers but using the format syntax:
property = 'name'
formatter = "my {} is {{}}".format(property) #=> "my name is {}"
print formatter.format('wong')