Django not adding a string to models - javascript

I am having a problem after I restarted my project from scratch
I can add a value manually to my django model, but when it comes from a variable the user entered, it only pass a blank string..
Some pictures of the logs to be more explicit:
Process:
So, I am having a simple model Tech and I have a page where you can add a new name to Tech model.
I enter the name (here i entered the name ede dede), click add, then i send it to the backend using AJAX.
In the shell in VSCODE I see I received the element, but when I add it to my django model Tech, and then print the new object in Tech, it has an ID, everything, but the name is a blank string ""
Moreover, When i print it in my python code, it doesnt even give me the queryset, i have nothing.
How come?
Here is a piece of my code
VIEWS.PY:
#ajax_required
#require_http_methods(["POST"])
def AddNewEmployee(request):
newtechname = request.POST.get('new_employee').title()
response_data = {}
print('new employee: '+newtechname)
print(type(newtechname))
if Tech.objects.filter(name=newtechname).exists():
response_data['success'] = False
response_data['result'] = 'This name already exists'
return HttpResponse(
json.dumps(response_data),
content_type="application/json"
)
else:
techname = Tech(name=newtechname)
techname = Tech(selected=True) #add new tech to model
techname.save() #save new name to model
response_data['success'] = True
response_data['result'] = 'Added a new teammate successfully!'
response_data['tech_id'] = techname.id #get new name id from model
response_data['tech_name'] = techname.name
response_data['tech_selected'] = techname.selected
print(techname)
return HttpResponse(
json.dumps(response_data),
content_type="application/json"
)
MODELS.PY
class Tech(models.Model):
name = models.CharField(max_length=200)
selected = models.BooleanField(default=False)
def __str__(self):
return self.name
JS:
$('#add-employee').on('submit',function(e){
e.preventDefault();
if(e.target.getAttribute('id')==('add-employee')){
console.log('form submitted!'); //sanity check
AddNewEmployee();
}
});
function AddNewEmployee(){
console.log('AddNewEmployee is working!');
console.log($('#addtech_id').val()); //get the input value from input id
const addemployee_form_url = $('#add-employee').attr('action'); //get the form url
new_employee = $('#addtech_id').val(); // data sent with the post request
console.log(typeof new_employee);
let request_data = {
'new_employee': new_employee,
'csrf_token':csrftoken
}
$self = $(this)
$.ajax({
url : addemployee_form_url, //endpoint
type : "POST", //httpmethod
data : request_data,
//handle a successful response
success : function(response){
$('#addtech_id').val(''); //remove the value from the input
console.log(response); // log the returned json to the console
console.log("A connexion to the backend has been established with success!"); // sanity check
//Add to selected list
if (response['success']){
AddToSelectedList(response['tech_id'], response['tech_name']);
$('#results').html("<h5><div class='alert-box alert radius' data-alert style='color:green;'>"+response['result']+"</div><h5>");
}
else{
$('#results').html("<h5><div class='alert-box alert radius' data-alert style='color:red;'>This name is already in the list!</div><h5>");
}
},
// handle a non-successful response
error : function(xhr,errmsg,err) {
$('#results').html("<div class='alert-box alert radius' data-alert>Oops! We have encountered an error: "+errmsg+
" <a href='#' class='close'>×</a></div>"); // add the error to the dom
console.log(xhr.status + ": " + xhr.responseText); // provide a bit more info about the error to the console
}
});
}
What I dont understand is, why is it printing (in views.py) newtechname correctly, which i can even see its type is a string so no problem, then, it passes an empty string to Tech model when techname = Tech(name=newtechname)
Thanks for your help!

The problem is here
else:
techname = Tech(name=newtechname)
techname = Tech(selected=True) #add new tech to model
techname.save() #save new name to model
You are trying to create an object that does not exist as Tech(name=newtechname) doesn't create the object, you can use that after using Tech.objects.create()
So in your case changing that with the traditional objects.create() has resolved the issue.

Related

Can't show data in javascript console

I have a registration form in my Laravel project. I submit that registration form data to laravel controller using ajax from javascript. After successfully stored those registration data in database I return the insertedID from controller to javascript and use console.log() function to show that id. In my javascript, console.log() shows that id and auto disappear after half mili second. But I don't want it to disappear.
Here is my js code
var name = $('#reg_name').val(); //reg_name is the id of the input field
var email = $('#reg_email').val(); //reg_email is the id of the input field
$.get( 'signup', {'name': name, 'email': email,'_token':$('input[name=_token]').val()}, function( data )
{
//Here 'signup' is my route name
console.log(data);
});
Here is my controller function
public function signup(RegistrationFormValidation $request)
{
$data = new User();
$data->name = $request->name;
$data->email = $request->email;
$data->save();
$lastInsertedId = $data->id;
if($lastInsertedId > 0)
{
return $lastInsertedId;
}
else
{
return 0;
}
}
Here I concise my code.
What's the problem in my javascript ?
If you are loading a new page, the default behaviour of the Chrome Dev Tools is to clear the logs. You can enable the Preserve log checkbox at the top of the console to prevent this behaviour.
In other situations, the data emitted to the console is modified after the logging to reflect subsequent updates. To prevent this, one can log a JSON serialized version of the data:
console.log(JSON.stringify(data))
(but probably this is not your case).

NodeJS Update API - Internal Server Error

It's about time I call in the big guns for this as I can't seem to figure it out.
I have a simple CRUD API in Node. I'm using EJS on the front-end. Essentially, I've got a selectAllRecords view where I display a table of all the records. I have a button next to each record to edit the record. When the button is clicked, it redirects to an editrecord.ejs page, hits the API for a single record where each line is displayed as a value in an input box. From there, I have an onclick method with an XMLHttpRequest making a put request to update the database. However, I'm getting an error - 500 (Internal Server Error) - I'm sure it's something fairly simple I'm missing, but I can't seem to figure it out.
Any help is greatly appreciated! Code below:
First on my view:
<script type="text/javascript">
function someFunc() {
var id = <%= id %>;
var url = '/api/edit/' + candID;
console.log('url ' + url);
var name = document.getElementById("name").value;
var email = document.getElementById("email").value;
var data = {
name: name,
email: email,
}
var json = JSON.stringify(data);
console.log('json ' + json);
var xhr = new XMLHttpRequest();
xhr.open("PUT", url, true);
xhr.setRequestHeader('Content-type', 'application/json; charset=utf-8');
xhr.send(json);
};
and in my queries.js file:
function updateCandidate(req, res, next) {
var candID = parseInt(req.params.id);
console.log('hit update');
console.log('name ' + req.body.name);
db.none('update cands set name=$1, email=$2 where id=$3',
[req.body.name, req.body.email, candID])
.then(function () {
var candID = candID
var name = data.name;
var email = data.email;
res.render("edited", {"candID":candID, "name":name, "email":email});
})
.catch(function (err) {
return next(err);
});
}
A potentially important note, when I hit the update button and execute the someFunc() function, the dev tool logs show a PUT request to 'api/edit/50' (or whatever ID) and '500 (Internal Server Error)' -- If i hard reload the 'getAllRecords' view, the updates are reflected so it's an issue with the render or redirect (I've tried both)
EDIT
As suggested, I removed the render from the updateCandidate method, but I still get a 500 Internal Server Error. the devtools show me the PUT request is hitting the right URL so i'm really not sure why this isn't functioning correctly. Updated code below...
function updateCandidate(req, res, next) {
var candID = parseInt(req.params.id);
db.none('update cands set name=$1, email=$2, client=$3, jobtitle=$4, question1=$5, question2=$6, question3=$7 where id=$8',
[req.body.name, req.body.email, req.body.client,
req.body.jobtitle, req.body.question1, req.body.question2, req.body.question3, candID])
.then(function (data, err) {
res.status(200)
.json({
status: 'success',
message: `Edited Candidate`
});
})
.catch(function (err) {
return next(err);
});
}
You are sending an ajax request to update the record. So, you should not try to render a view or redirect user as the response of this request. Instead, you can send back a JSON object with some properties e.g. "status".
Then on client side, you check the returned JSON response and based on "status" parameter ( or any other you chose ), you can either update your data or reload the page using window.reload on client side.
Your db query says
db.none('update cands set name=$1, email=$2 where id=$8', [req.body.name, req.body.email]) ...
Shouldn't it be
db.none('update cands set name=$1, email=$2 where id=$8', [req.body.name, req.body.email, candID])

Get error or an empty value while trying for passing id from django template to reactjs

I am getting an error saying unexpected token while trying for passing id from django template to reatjs for uploading multiple images to its associated foreign key object. The error is shown as unexpected token }. In depth it is shown as
in console
var uploadUrl = {
url:
};
What i am trying to do is , I have created a listing page with multiple form and it is entirely developed using reactjs. I want user to fill the data about room and upload multiple images related to their room. There are two models one with room info and another gallery(multiple image is associated with one rent). I wanted the uploaded images be associated with its rent so i coded it as below
urls.py
urlpatterns = [
url(r'^add/$', AddView.as_view(), name="add"),
url(r'^add/space/$', AddSpaceView.as_view(), name="addSpace"),
url(r'^upload/image/(?P<pk>\d+)/$', ImageUpload, name="ImageUpload"),
]
views.py
def ImageUpload(request,pk=None): // for saving images only to its asscoiated rent
if request.POST or request.FILES:
rental = Rental.objects.get(id=pk)
for file in request.FILES.getlist('image'):
image = GalleryImage.objects.create(image=file,rental=rental)
image.save()
return render(request,'rentals/add.html')
class AddView(TemplateView): // for listing page
template_name = 'rentals/add.html'
class AddSpaceView(View): // for saving data to database except image
def post(self,request,*args,**kwargs):
if request.POST:
rental = Rental()
rental.ownerName = request.POST.get('ownerName')
rental.email = request.POST.get('email')
rental.phoneNumber = request.POST.get('phoneNumber')
rental.room = request.POST.get('room')
rental.price = request.POST.get('price')
rental.city = request.POST.get('city')
rental.place = request.POST.get('place')
rental.water = request.POST.get('water')
rental.amenities = request.POST.get('amenities')
rental.save()
return HttpResponseRedirect('/')
listing.js(ajax code for uploading multiple image)
var image = [];
image = new FormData(files);
$.each(files,function(i,file){
image.append('image',file);
});
$.ajax({
url:"/upload/image/", // want to used id over here that is passed from add.html script tag so that image will be uploaded to its associated foriegn key object
data:image,
contentType:false,
processData:false,
type:'POST',
mimeType: "multipart/form-data",
success: function(data) {
console.log('success');
}
});
}
add.html page
<div id="listing">
</div>
{% include 'includes/script.html'%}
<script type="text/javascript">
var uploadUrl = {
url: {% for rental in object_list %} { "id": {{ rental.id }} } {% endfor %} // here is an error
};
console.log('url is', url);
$(function() {
app.showListingSpaceForm("listing");
});
</script>
The code might explained what i was trying to achieve. If models.py is also required for more scrutiny then i will update it.
You're missing a fundamental piece: TemplateView has no concept of object_list, you have to populate it yourself. If your view is simple enough use ListView and set your model property. If not, you have to manually populate the object list, something like this:
def get_context_data(self, **kwargs):
context['object_list'] = MyModel.objects.all()
That was just an example to set you on the right path.

Google Script send form values by email, error: cannot read property "namedValues"

Project key: MyvPlY2KvwGODjsi4szfo389owhmw9jII
I am trying to run a script that sends the contents of my form by email each time the form is submitted. I was following the instructions from this link below exactly until I started getting errors and I received advice to change my script to open spreadsheets by id:
http://www.snipe.net/2013/04/email-contents-google-form/
When I complete the form, it is supposed to email the contents to my email.
The problem I am now having is that the function which goes through the form values doesn't work. It's returning the error
TypeError: Cannot read property "namedValues" from undefined. (line 15, file "Code")"
in regards to the piece of code below:
for(var i in headers)
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
I am not too familiar with Google Apps Scripts so I'm not sure how to work around this issue either. Is there anything you recommend? I have included the entire script below.
function sendFormByEmail(e)
{
// Remember to replace this email address with your own email address
var email = "sample#email.com";
var s = SpreadsheetApp.openById("1hOqnK0IVa2WT6-c-MY0jyGGSpIJIV2yzTXdQYX4UQQA").getSheets()[0];
var headers = s.getRange(1,1,1,s.getLastColumn()).getValues()[0];
var message = "";
var subject = "New User Form";
// The variable e holds all the form values in an array.
// Loop through the array and append values to the body.
for(var i in headers)
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
// Insert variables from the spreadsheet into the subject.
// In this case, I wanted the new hire's name and start date as part of the
// email subject. These are the 3rd and 16th columns in my form.
// This creates an email subject like "New Hire: Jane Doe - starts 4/23/2013"
subject += e.namedValues[headers[2]].toString() + " - starts " + e.namedValues[headers[15]].toString();
// Send the email
MailApp.sendEmail(email, subject, message);
}
The function appears to be undefined as 'e' is not received as part of the function context. You'll need to set a trigger for the submission of the form, and send the information to the function. You can use the following code:
/* Send Confirmation Email with Google Forms */
function Initialize() {
var triggers = ScriptApp.getProjectTriggers();
for (var i in triggers) {
ScriptApp.deleteTrigger(triggers[i]);
}
ScriptApp.newTrigger("SendConfirmationMail")
.forSpreadsheet(SpreadsheetApp.getActiveSpreadsheet())
.onFormSubmit()
.create();
}
function SendConfirmationMail(e) {
try {
var ss, cc, sendername, subject, columns;
var header, message, value, textbody, sender, itemID, url;
// This is your email address and you will be in the CC
cc = "name#email.com";
// This will show up as the sender's name
sendername = "name to be displayed as sender";
// Optional but change the following variable
// to have a custom subject for Google Docs emails
subject = "Choose an approppiate subject";
// This is the body of the auto-reply
message = "";
ss = SpreadsheetApp.getActiveSheet();
columns = ss.getRange(1, 1, 1, ss.getLastColumn()).getValues()[0];
// This is the submitter's email address
sender = e.namedValues["Username"].toString();
// Only include form values that are not blank
for ( var keys in columns ) {
var key = columns[keys];
//Use this to look for a particular named key
if ( e.namedValues[key] ) {
if ( key == "Username" ) {
header = "The user " + e.namedValues[key] + " has submitted the form, please review the following information.<br />";
} else {
message += key + ' ::<br /> '+ e.namedValues[key] + "<br />";
}
}
}
}
textbody = header + message;
textbody = textbody.replace("<br>", "\n");
Logger.log("Sending email");
GmailApp.sendEmail(cc, subject, textbody,
{cc: cc, name: sendername, htmlBody: textbody});
} catch (e) {
Logger.log(e.toString());
}
}
I have the same error and it took me some time to figure out how to solve it.
The problem is that you are writing your code in the form, and you should do it in your spreadsheet.
When I created the function inside the form and registered the event, it was called but the parameter didn't have the same structure (and didn't have the field namedValues, so the error "Cannot read property "namedValues" from undefined"). A better way to check this is to log the object as a JSON string:
Logger.log("e: " + JSON.stringify(e));
So, the steps I have made to correct this issue:
Create a spreadsheet
Create the form through the spreadsheet (inside the spreadsheet select Tools->Create a form), and create your form
Go back to your spreadsheet, and create the script (Tools->Script Editor)
Write your function
Register the function (Edit->Current Project's Triggers): function sendFormByEmail, Event: From Spreadsheet -> On form submit
Hope this helps
There is an error in this line of code:
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
it's this part:
e.namedValues[headers[i]].toString()
I'm just guessing that you want:
e.namedValues + [headers[i]].toString()
You're missing a plus sign if you want to concatenate the values.

Form Information to Appear On Another Page

I am trying to create a form that, once submitted, will be sent to my index.html page for other users to view. I want it so multiple users anywhere in the world can submit information and so the website displays all their information at once.
Here is my submit page's PHP code:
<form action="submit_a_message.php" method="post">
<textarea name="message" cols="60" rows="10" maxlength="500"></textarea><br>
<input type="submit">
</form>
I am trying to figure out how to make the information submited via that form appear on my index.html page. This is the code I found online, but it doesn't work. Why?
<?php>
string file_get_contents ( string $submit_a_message.php [, bool $use_include_path = false [, resource $context [, int $offset = -1 [, int $maxlen ]]]] )
<?>
Any help would be greatly appreciated.
To make submitted text avaliable on your index page, you need a place where you would store it. You can use MySQL base to do that, or (if you can't or you really don't want) you can use text file with your texts/posts (that is not really good way, i warned you).
To do that with MySQL you can use a code like this on your submit_a_message.php:
<?php
//connection to database and stuff
...
if $_POST['message'] {
$message = $_POST['message'];
$sql = "insert into `mytable` values $message"; //that is SQL request that inserts message into database
mysql_query($sql) or die(mysql_error()); // run that SQL or show an error
}
?>
In order to show desired vaues from table use above-like idea, your SQL request would be like select * from mytable where id = 123
if your not married to the idea of using php and learning how to manage and access a database you could use jquery and a trird party backend like parse.com
If your new to storing and retrieving data, I would definately reccomend the services that https://parse.com/ offeres. It makes storing and retrieving data trivial. Best of all, the service is free unless your app makes more than 30 API requests per second. I have an app that 61 users use daily and we have never come close to the 30 req per second limit.
To save your info, you could write:
$('document').ready(function(){
$('#submit_btn').on('click',function(){ // detect button click, need to add "submit_btn" as the id for your button
var Message = Parse.Object.extend("Message"); //create a reference to your class
var newObject = new EventInfo(); //create a new instance of your class
newObject.set("messageText", $("#myMessage").val()); //set some properties on the object, your input will need the id "myMessage"
newObject.save(null, { //save the new object
success: function(returnedObject) {
console.log('New object created with objectId: ' + returnedObject.id);
},
error: function(returnedObject, error) {
console.log('Failed to create new object, with error code: ' + error.message);
}
});
});
});
Retrieving that info later would be as easy as:
var Message = Parse.Object.extend("Message"); //create a reference to your class
var query = new Parse.Query(Message); //create a query to get stored objects with this class
query.find({
success: function(results) { //"results" is an array, you can fine tune your queries to retrieve specific saved objects too
for (var i = 0; i < results.length; i++) {
var object = results[i];
$(body).append("Message #" + (i+1) + object.get("messageText");
}
},
error: function(error) {
console.log("Failed to complete Query - Error: " + error.code + " " + error.message);
}
});

Categories

Resources