WTForms Set input field after post - python

For below example:
Product(form):
product = TextField('name')
If i set this field in GET action
form.product.data= "123",
render is "123".
However, if i try set this value after POST action,
i allways get value form POST
How can i set this value (rerender) after POST ?

I wanted change only particulars fields, but rest keep from POST.
I have noticed that data from POST has additional field "raw_data" and set form.product.data fiels hasn't done (re)render. Solution proved to be clear
form.product.raw_data = None
form.product.data = 123
render new value
Maybe little bit "elegant" , but works !!!

Are you asking how to clear form data from the form after a user has submitted it?
In that case you could re-initialize the form
when you do
product = Product(request.POST)
It will fill the data that the user submitted.
product = Product()
This will clear the data.
Note:
use 4 spaces for every line of the code, so it is displayed well.

Related

How to capture HTML5 data attribute when form is submitted to views.py of Django

As you can probably tell from the nature of my question, I'm a little new to this. I have read similar post on this subject matter but most of it went right past my head and I did not feel like it was 100% applicable to the circumstance that I was facing so I thought I'd ask the question in a simplified way.
The question:
let's say I'm running the below HTMl form and a user submits the form to my views.py as shown in the views section below, I would able to store the value of the user selection by using: car_selection = request.POST.get('car') .
My question is, how would I be able to capture the HTML5 data of " data-animal-type="spider" " ?
I know there are Gurus out there but please do not explode my head. I would really need simplified help.
Thanks for helping.
Example HTML Form:
<select name="carlist" >
option data-car-type="premium" name= "car" value="audi">Audi</option>
</select>
Example Django View Function
def getcar(request):
...
if request.method == 'POST'
...
selected_carn = request.POST.get('car')
Well, it actually is possible. Say your view looks like this:
def getcar(request):
...
if request.method == 'POST'
myform = MyForm(request.POST)
...
myform includes uncleaned form in html. The you can use BeautifulSoup to extract data. Something like this:
from bs4 import BeautifulSoup
test = BeautifulSoup(str(myform))
data-values = [item["data-car-type"] for item in test.find_all() if "data-car-type" in item.attrs]
This will extract values from data-car-type attributes.
That being said, this does seem like a bad design. I surely would never go to such length to get the "car type" data. It's probably written somewhere in your database. Get it from there.
I know this question is 4 year old but I came across this page when a similar question arose in my mind.
Short answer
It's not possible, unless your use Javascript on the front end side as a workaround. The accepted answer is false.
Explanation
Indeed, in the example above, try to print(request.POST) and you'll see that the QueryDict object request.POST received by the view does not contain any reference to the HTML5 data attribute you want to fetch. It's basically a kind of Python dictionary (with a few distinctive features, cf. documentation). Admittedly, if you print(myform) in the same example, you'll see some HTML code. But, this code is generated retroactively, when you associate data with the form. Thus, BeautifulSoup will never be able to find what you're looking for. From the Django documentation:
If the form is submitted using a POST request, the view will [...] create a form instance and populate it with data from the
request: form = NameForm(request.POST). This is called “binding data to
the form” (it is now a bound form).
Workaround
What I've done on my side and what I would suggest you to do is to use some Javascript on the client side to add the missing information to the form when it's submitted. For instance, it could look like this:
document.querySelector("#form_id").addEventListener("submit", function(e) {
const your_data_attribute = document.getElementById("XXX").dataset.yourInfo;
const another_hidden_field = document.getElementById("YYY");
another_hidden_field.value = your_data_attribute;
});

odoo 9 Automatically changing the selection field and radio button field depends on the changed other selection field

I need a help please.
So I wanted when I change the Internal Category (field name is categ_id) value to 500 final product,
and then the Routes field changes to :
Manufacture checked,
Make To Order checked,
Buy checked
and also the Value of Tracking field is changes as well to:
By Lots checked
How can I do that? Any suggestion ? Or my is it my question are not clear enough ?
Sorry for asking , I never done this before so yeah kind a confusing.
Here I got the picture the interface and the information about the field as well.
Routes field name
Tracking field name
Please anyone kindly to help me. I am so confused.
You could achieve this by using api onchange in Odoo 9.
#api.onchange('categ_id')
def onchange_categ_id(self):
for record in self:
# I prefer to check by id, but here I show how to check by string name in case you want it
if record.categ_id.name == '500 final product':
# because route_ids is many2many field,
# you need special commands to change the value
# here I use (6, _, ids) to set value.
# But before that, you have to get the ids of the routes you want from model stock.location.route
# (you could use search method to get the ids)
record.route_ids = [(6,0, list_of_id)]
record.tracking = 'lot'
...
You could refer to Odoo Doc to learn more about O2m and M2m commands

Add data to database on two seperate pages

I'm currently working on a webpage using the django framework for python.
I need to have a page where admin user's can register an event into the system.
Event being: Location on a map, Description, Images, links etc..
I feel it's a bit less confusing If I have the user add location details on the first page but when he has finished choosing a location he could click next, this would take him to another page where he would finish filling out the information about the event.
I'm not sure but I think this is rather a database question than a django question.
How would I continue adding to the same table in a database between two seperate pages?
I thought about using timestamp so I could select the last modified table on the next page but I think that might be risky + if the user goes back to modify the table the timestamp is useless.
I'm using Django 1.5 + postgresql database. Any reading references that might be good to check out for this kind of operation?
I've done something similar to this before. I asked users to enter a zip code on one page and then based upon that zip code it loaded in different options for the form on the next page. Here is how I did it using request.session
Note that this is is my soultion to MY problem. This may not be exactly what you are looking for but might help you get a start. If anyone has a better solution I'd love to see it since I'm not entirely happy with my answer.
views.py
def find_zip(request):
c={}
form = FindZip()
c['form'] = form
if request.method == 'POST':
form = FindZip(request.POST)
c['form'] = form
if form.is_valid():
zip = form.data['zip']
form = ExternalDonateForm(initial={'zip':zip})
request.session['_old_post'] = request.POST
c['form'] = form
response = HttpResponseRedirect('/external')
return response
return render_to_response(
'find_zip.html',
c,
context_instance=RequestContext(request)
I then try to retrive that session from the previous view
def donate_external(request):
zip = None
if request.session.get('_old_post'):
old_post = request.session.get('_old_post')
zip = old_post['zip']
)
# rest of code ....

WTForms FieldList with optional fields

I have the following form,
class AddForm(wtf.Form):
tags = TagListField("Tags (comma separated)", validators=[wtf.Required()])
question = wtf.TextField("Question", validators=[wtf.Required()])
answers = wtf.FieldList(wtf.TextField("Answer", validators=[wtf.Required()]), min_entries=2, max_entries=5)
And I have a form setup to display this form along with a button that adds more "answers" inputs dynamically (by the user clicking a button). However, when the form gets submitted, any fields that are added but not filled in are considered errors.
Specifically, if I have 3 inputs for "Answer", but I only fill in the first two, then the third one comes up as an error, even though I have specified that the minimum number of entries is 2. It seems like it should ignore this data.
Since I am using this with Flask I am going to just modify the request.form data to ignore blank fields. Is there something I'm missing?
May be your the
validators=[wtf.Required()])
is an issue ? Have you tried changing it to
validators=[wtf.Optional()])

Django: How to modify a text field before showing it in admin

I have a Django Model with a text field. I would like to modify the content of the text field before it's presented to the user in Django Admin.
I was expecting to see signal equivalent of post_load but it doesn't seem to exist.
To be more specific:
I have a text field that takes user input. In this text field there is a read more separator. Text before the separator is going to go into introtext field, everything after goes into fulltext field.
At the same time, I only want to show the user 1 text field when they're editing the article.
My plan was to on_load read the data from introtext and fulltext field and combine them into fulltext textarea. On pre_save, I would split the text using the read more separator and store intro in introtext and remainder in fulltext.
So, before the form is displayed, I need to populate the fulltext field with
introtext + '<!--readmore-->' + fulltext
and I need to be able to do this for existing items.
Have a look into Providing your own form for the admin pages.
Once you have your own form, you can use the default param in the form to provide the initial value you want. See the docs on the Initial param for the form field. As this link will show you, it is possible to use a callable or a constant as your initial value.
There is no post_load because there is no load function.
Loading of the instance is done in init function, therefore the right answer is to use post_init signal.

Categories

Resources