Ignore unknown functions in Jinja2 - jinja2

When rendering a Jinja2 template, either something like:
"hello {{world}}"
"hello {{get_world()}}"
I am interested in simply "passing along" any templated variables or functions that are not provided to Jinja. For example, if the variable {{world}} does not exist in the context, I want the output to keep {{world}}. If the the function {{get_world()}} does not exist in the context, I want to keep {{get_world()}}.
The closest I've gotten is with the following:
from jinja2 import Environment, BaseLoader, DebugUndefined
template = Environment(loader=BaseLoader, undefined=DebugUndefined).from_text("my template")
However, this above only works with the example "hello {{world}}", but not the example "hello {{get_world()}}". How can I achieve this functionality for both of these cases?

Related

In Jupyter Notebook, how to show output within function without using print

I want the code to show "123" without using built-in print function, but it does not. What should I do?
from IPython.core.interactiveshell import InteractiveShell
InteractiveShell.ast_node_interactivity = "all"
def myf():
"123"
myf()
If I got right, you just want to print the "123", right?
def myf():
print("123")
myf()
If you want to receive the "123" as a result of your def, would be something like this :
def myf():
x = "123"
return x
Z = myf()
print (Z)
"123"
You can use the display function:
Although, I don't think that's what you want. The settings you're enabling:
from IPython.core.interactiveshell import InteractiveShell
InteractiveShell.ast_node_interactivity = "all"
Only apply to returned values; that's why you don't see it printed. If you return the value and call the function a few times, you'll see them:
I don't have a direct answer to this, but I have some pointers to the problem.
Normal output is written either in stdout or stderr by some Python provided method. However, when utilizing the IPython feature of checking a value by using either direct value ("123") or variable (first line a = "123", second line a). This output stream can not be captured with simple %%capture magic in Jupyter; the output vanishes in the scope of the function definition.
I do agree that this would be useful; in machine learning we sometimes use dependency inversion like structures, where we modify functions instead of line-by-line code, where debugging gets hard since we can not capture some of the outputs without injecting a print or display. However, not using display might have unwanted and hard to predict consequences as some of the models can be rather verbose in what they write. However, capturing some outputs without extra prints and displays from user defined cells might be nice feature.
Notice that sometimes print doesn't work, but display does. Print might not always understand how our utilities in pandas or matplotlib works.

How to pass parameters or variables of arm template in log query

While working on log Queries in an arm template, I stuck with how to pass parameter values or variable values in the log Query.
parameters:
{
"resProviderName":
{
"value": "Microsoft.Storage"
}
}
For Eg:
AzureMetrics | where ResourceProvider == **parameters('resProviderName')** | where Resource == 'testacc'
Here I am facing an error like, it was taking parameters('resProviderName') as a value and it was not reading value from that particular parameter "resProviderName" and my requirement is to take the values from parameters or variables and should not hardcode like what I did in the above query as Resource=='testacc'.
Do we have any option to read the values from either parameters or variables in the log query?
If so, please help on this issue.
The answer to this would depend on what this query segment is a part of, and how your template is structured.
It appears that you're trying to reference a resource in the query. It is best to use one of the many available template resource functions if you want the details of the resource like its resourceID (within the resources section). When referencing a resource that is deployed in the same template, provide the name of the resource through a parameter. When referencing a resource that isn't deployed in the same template, fetch the resource ID.
Also, I'd recommend referring to the ARM snippet given this example to understand how queries can be constructed as custom variables as opposed to the other way round. According to ARM template best practices, variables should be used for values that you need to use more than once in a template. If a value is used only once, a hard-coded value makes your template easier to read. For more info, please take a look at this doc.
Hope this helps.
This is an old question but I bumped into this while searching for the same issue.
I'm much more familiar with Bicep templates so what I did to figure out was to create a Bicep template, construct the query by using the variables and compile it. This will generate a ARM template and you can analyze it.
I figured out you can use both concat or format functions in order to construct your query using variables.
I preferred the format one since it looks more elegant and readable (also, Bicep build generates the string using the format function).
So based on this example, the query would be something like this:
query: "[format('AzureMetrics | where ResourceProvider == {0} | where Resource == ''testacc'' ', parameters('resProviderName') )]"
Don't forget to escape the ' in the ARM template which you do by doubling the single quote.
I hope this helps some people.
André

Web2Py - generic view for csv?

For web2py there are generic views e.g. for JSON.
I could not find a sample.
When looking at the web2py manual 10.1.2 and 10.1.6, its written:
'.. define a "generic.csv" file, but one would have to specify the name of the object to be serialized ("animals" in the example)'
Looking at the generic pdf view
{{
import os
from gluon.contrib.generics import pdf_from_html
filename = '%s/%s.html' % (request.controller,request.function)
if os.path.exists(os.path.join(request.folder,'views',filename)):
html=response.render(filename)
else:
html=BODY(BEAUTIFY(response._vars))
pass
=pdf_from_html(html)
}}
and also the specified csv (Manual charpter 10.1.6):
{{
import cStringIO
stream=cStringIO.StringIO() animals.export_to_csv_file(stream)
response.headers['Content-Type']='application/vnd.ms-excel'
response.write(stream.getvalue(), escape=False)
}}
Massimo is writing: 'web2py does not provide a "generic.csv";'
He is not fully against it but..
So lets try to get it and deactivate when necessary.
The generic view should look similar to (the non working)
(well, this we better call pseudocode as it is not working):
{{
import os
from gluon.contrib.generics export export_to_csv_file(stream)
filename = '%s/%s' % (request.controller,request.function)
if os.path.exists(os.path.join(request.folder,'views',filename)):
csv=response.render(filename)
else:
csv=BODY(BEAUTIFY(response._vars))
pass
= export_to_csv_file(stream)
}}
Whats wrong?
Or is there a sample?
Is there a reson not to have a generic csv?
{{
import os
from gluon.contrib.generics export export_to_csv_file(stream)
filename = '%s/%s' % (request.controller,request.function)
if os.path.exists(os.path.join(request.folder,'views',filename)):
csv=response.render(filename)
else:
csv=BODY(BEAUTIFY(response._vars))
pass
= export_to_csv_file(stream)
}}
Adapting the generic.pdf code so literally as above would not work for CSV output, as the generic.pdf code is first executing the standard HTML template and then simply converting the generated HTML to a PDF. This approach does not make sense for CSV, as CSV requires data of a particular structure.
As stated in the documentation:
Notice that one could also define a "generic.csv" file, but one would
have to specify the name of the object to be serialized ("animals" in
the example). This is why we do not provide a "generic.csv" file.
The execution of a view is triggered by a controller action returning a dictionary. The keys of the dictionary become available as variables in the view execution environment (the entire dictionary is also available as response._vars). If you want to create a generic.csv view, you therefore need to establish some conventions about what variables are in the returned dictionary as well as the possible structure(s) of the returned data.
For example, the controller could return something like dict(data=mydata). The code in generic.csv would then access the data variable and could convert it to CSV. In that case, there would have to be some convention about the structure of data -- perhaps it could be required to be a list of dictionaries or a DAL Rows object (or optionally either one).
Another possible convention is for the controller to return something like dict(columns=mycolumns, rows=myrows), where columns is a list of column names and rows is a list of lists containing the data for each row.
The point is, there is no universal convention for what the controller might return and how that can be converted into CSV, so you first need to decide on some conventions and then write generic.csv accordingly.
For example, here is a very simple generic.csv that would work only if the controller returns dict(rows=myrows), where myrows is a DAL Rows object:
{{
import cStringIO
stream=cStringIO.StringIO() rows.export_to_csv_file(stream)
response.headers['Content-Type']='application/vnd.ms-excel'
response.write(stream.getvalue(), escape=False)
}}
I tried:
# Sample from Web2Py manual 10.1.1 Page 464
def count():
session.counter = (session.counter or 0) + 1
return dict(counter=session.counter, now = request.now)
#and my own creation from a SQL table (if possible used for json and csv):
def csv_rt_bat_c_x():
battdat = db().select(db.csv_rt_bat_c.rec_time, db.csv_rt_bat_c.cellnr,
db.csv_rt_bat_c.volt_act, db.csv_rt_bat_c.id).as_list()
return dict(battdat=battdat)
Bot times I get an error when trying csv. It works for /default/count.json but not for /default/count.csv
I suppose the requirement:
dict(rows=myrows)
"where myrows is a DAL Rows object" is not met.

How to insert the current date with jinja2

I am new to use Jinja2 and try to insert the current date in a document as a bottom line to tell users when the document was produced.
My current solution is
Produced on {{ utils.today|date('%x') }}
There are no error messages, but nothing is produced.
The solution need to be Jinja2 only, as I have no python process running - using Ginger (a Haskell program) to process the template.
Context Processors can be used to inject values into templates before rendering it.
In app.py:
import datetime
#app.context_processor
def inject_today_date():
return {'today_date': datetime.date.today()}
And add this in the html file:
<p>{{today_date}}</p>
Output: 2019-01-07
Jinja2 doesn't have native support for inserting the date. However, you can easily prepare the date in whatever library you use to render the template and pass the value to the rendering function.
Using jinja2 in Python:
import datetime
date = datetime.date.today()
template = Template('Produced on {{ date }}')
template.render(date=date)
If you are using Ginger, you would have the same template, just make sure to create the date in Haskell and render the template with that value.
You can also write or install a jinja2 extension that will make utilities for working with dates available in the template.
For example, after installing jinja2-time [1], your template would look like this:
Produced on {% now 'local' %}
[1]: untested code

How do XQuery function namespaces work?

EDIT
I want to group together related functions to show that they are related.
If I have local:f1() and local:f2() then I could just change their names to local:menu-f1() and local:menu-f2() but is there a mechanism in the XQuery language to group related functions?
OP
I am very excited to discover that XQuery functions can be declared in a namespace other than local:. Where can I find info about how this works?
Having always declared functions in this way;
declare function local:foo() {
3+4
};
.. and used them in this way;
local:foo()
.. I discover that they can be declared like this;
declare namespace baz = "fred:bloggs";
declare function baz:foo() {
3+4
};
.. and used like this;
baz:foo()
But I can only find reference-like information about declare namespace and declare function separately, not tutorial-like information about how XQuery function namespaces work in general.
Is there a newbie guide to XQuery function namespaces?
I'm using a Saxon processor - XQuery 1.0.
What you are probably using are normal XQuery namespaces - what you probably are looking for are modules. You can put a bunch of functions in its own module namespace like this:
module namespace foo = "http://www.myurl.com/foo";
declare function foo:bar($args as item()*) as item()* {
() (: do something cool :)
};
Afterwards you can import the module in you main query and call the function:
import module namespace foo = "http://www.myurl.com/foo";
foo:bar(<my-element/>)
The problem is, that it is not standardized, how the processor has to find the query. And I don't know how Saxon implements the module resolving mechanism (you should look into the documentation and/or write to the Saxon mailing list).
But most XQuery processors look at the path given by an "at" clause relative from the location of the query. So to have something that should work on most implementations: For example you could store the module in a file named foo.xq and place it into the same directory than your main query and then for the module import you would write:
import module namespace foo = "http://www.myurl.com/foo" at "foo.xq";
which gives a hint to the XQuery engine where it should look for the module.
You can find some (not a lot at the moment) documentation about this stuff at http://www.xquery.me/ - hope this helps.
EDIT
Ok I see, you only want to group your functions. To do that you already figured out everything you need to know. But I still want to emphasize that splitting your query up into modules would probably be the better solution for your use-case (it's just somehow nicer, since your have more modularity and in the upcoming XQuery 3.0 recommendation you will even have the possibility to put stuff like private functions and variables in there). But if your query does not get big, your solution is of course also ok.
You can think about XML namespaces the same way you would think about namespaces in C++. In XQuery, functions, elements, collections, variables, attributes etc can be in an own namespace (again - like in C++). There are some implicitely defined namespaces like xs (the XML Schema namespace where you can find the data types like boolean, integer etc), local (a namespace where you can put in functions so that you are not forced to define your own namespace in a main query), fn (where all functions from the "XQuery 1.0 and XPath 2.0 functions and operators" recommendation are defined). But the prefix of this function is only an alias - you can use whatever you want.
So let's say you have the following code in the prolog of your query:
declare namespace blubb = "http://www.w3.org/2001/XMLSchema";
blubb:integer would be exactly the same type than xs:integer - the same holds for functions:
declare namespace l = "http://www.w3.org/2005/xquery-local-functions";
With declaring that you can access every function in the local namespace with the "l" prefix (so l:bar() if local:bar() exists).
If you do not type a prefix, XQuery assumes that this function is in the "fn" namespace. This is why bot
fn:concat("Hello ", "World!")
and
concat("Hello ", "World!")
are equivalent. You can change this behavior. You could include this line into the prolog:
declare default function namespace "http://www.w3.org/2005/xquery-local-functions";
which would tell the XQuery processor that you do not want to prefix local functions (so bar() would be equivalent to local:bar()).
I am not sure if I answered your questions or at least was able to bring in some clarity. I do not know about a tutorial for that (since in the beginning it is somehow confusing but in the end you realize that there is not a lot to say about since the mechanisms are much simpler than they look in the first place). The document where I always look up stuff is the recommendation at http://www.w3.org/TR/xquery/
If this does not help you please try to qualify and I can try again with an explanation..