Uncaught SyntaxError: Unexpected end of JSON input. Can't properly parse the info to JSON from the html












0















Getting the error when trying to open the modal with product details after products were queried with help of ajax



Error itself:



Uncaught SyntaxError: Unexpected end of JSON input
at JSON.parse (<anonymous>)
at HTMLButtonElement.<anonymous> (scripts.js:54)
at HTMLDocument.dispatch (jquery-3.3.1.js:5183)
at HTMLDocument.elemData.handle (jquery-3.3.1.js:4991)


To be clear: I have some filters, result of which is filtered in the python filter_items function then it uses JSONResponse to send it to the front-end
in form of a dictionary(as_dict() function in Item model) were they are added to hidden input value. JS function takes that hidden input value and renders the results of filtering using the data from that input.



Item Model which is queried with help of filter function:



class Item(models.Model):

ITEM_TYPES = (
('UM', 'Umbrella'),
('SK', 'Skirt'),
('TR', 'Trousers'),
('OT', 'Other')
)

BRANDS = (
('VS', 'Versace'),
('SP', 'Supreme'),
('SI', 'Stone Island'),
('FP', 'Fred Perry'),
)

title = models.CharField(max_length=256)
image = models.ImageField(upload_to='img/')
brand = models.CharField(max_length=256)
type = models.CharField(choices=ITEM_TYPES, max_length=2)
description = models.TextField(blank=True, null=True)
season = models.TextField(blank=True, null=True)
discount = models.FloatField(blank=True, null=True)
price = models.FloatField()

def __str__(self):
return self.title + ' ' + self.type

def as_dict(self):
data = {"title": self.title, "image": self.image.url, "brand": self.brand, "type": self.type,
"discount": self.discount, "price": self.price, "rus_representation": self.rus_representation,
"description": self.description, "season": self.season, "images": [self.image.url]}

if self.images:
for image in self.images.all():
data['images'].append(image.image.url)

# data['dumped'] = json.dumps(data)
# print(data['dumped'])
return data

def dumped_as_dict(self):
return json.dumps(self.as_dict())

@property
def rus_representation(self):

if self.type == 'UM':
return 'Зонтик'
elif self.type == 'SK':
return 'Юбка'
elif self.type == 'TR':
return 'Штаны'
elif self.type == 'OT':
return 'Другое'


Class based view with filter function inside of it:



class ProductsListView(ListView):
model = Item
types = Item.ITEM_TYPES
brands = Item.BRANDS

def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
context['types'] = self.types
context['brands'] = self.brands
return context

@classmethod
def filter_items(cls, request, *args, **kwargs):
if request.is_ajax():
data = request.GET

queryset = Item.objects.all()

if not data['type'] == 'ALL':
queryset = queryset.filter(type=data['type'])

if not data['brand'] == 'ALL':
queryset = queryset.filter(brand__contains=data['brand'])
return JsonResponse({'result': [item.as_dict() for item in queryset]})


JavaScript filter function:



    $('.choice-link').click(function () {
var choice = $(this).text();

$(this).siblings().attr('id', '');

$(this).attr('id', 'active');

$(this).parent().parent().children('button').text(choice);

var data = {
'brand': $('.brand-dropdown').children('#active').attr('data-choice'),
'type': $('.type-dropdown').children('#active').attr('data-choice')
};

$.ajax({
url: '../ajax/filter/',
data: data,
success: function (data) {
$('.item-block').remove();
$.each(data.result, function (index, item) {
if (!item.discount) {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
} else {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span><span class="discount badge badge-danger">' + item.discount + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
}
$('.items-list').children('hr').after(el)
});

}
})
});


Java Script function which fills the modal with related data:



$(document).on('click', '.item-btn', function () {
var data = JSON.parse($(this).siblings('input').val()); (line 54 where error message points)

$('.product-title').html(data.rus_representation + ' "<i>' + data.brand + '</i>"' + '<hr>');

if(data.description) {
$('.product-description').text(data.description);
}else{
$('.product-description').html('<h4>Описнаие пока не добавлено</h4>')
}

$('.carousel-inner').empty();
$.each(data.images, function (index, img) {
if(index === 0){
var el = '<div class="carousel-item active"><img class="d-block w-100" src="'+ img +'"></div>'
} else {
var el = '<div class="carousel-item"><img class="d-block w-100" src="'+ img +'"></div>'
}

$('.carousel-inner').append(el)
});

$('.product-brand').html('<i>' + data.brand + '</i>');
$('.product-type').text(data.rus_representation);
$('.product-season').text(data.season);

if (data.discount){
$('.discount-in-modal').html('<span class="discount badge badge-danger" style="position: relative; top: -5px">'+ data.discount +' $</span>');
}

$('.product-price').text(data.price);


});



HTML:



            {% for item in object_list %}
<div class="item-block flex" style="flex-direction: column">
<input type="hidden" value="{{ item.dumped_as_dict }}">
<img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5); max-height: 300px" src="{{ item.image.url }}">
<h6 class="item-title">
{{item.rus_representation}} "{{item.brand}}"
<hr>
</h6>
<p class="flex" style="align-items: flex-start">
<span class="price-tag">{{ item.price }} $</span>
{% if item.discount %}
<span class="discount badge badge-danger">{{ item.discount }} $</span>
{% endif %}
</p>
<button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" src="{% static 'img/arrow.png' %}"></button>
</div>
{% endfor %}


IF do console.log(JSON.stringify(item));:



{"title":"tst","image":"/media/img/_58A1259_sm.jpg","brand":"GUCCI","type":"SK","discount":9000000,"price":9,"rus_representation":"Юбка","description":"LoL Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.","season":"","images":["/media/img/_58A1259_sm.jpg","/media/img/_58A7975_sm.jpg"]}


How it should look like:



opening the modal on initial load



What I have:



if use filtering and them trying to open details modal



Adding view from Inspector:
For some reasons string is not fully added to value attr










share|improve this question




















  • 1





    What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

    – snakecharmerb
    Dec 29 '18 at 15:55











  • JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

    – Vlad Ivanyk
    Dec 29 '18 at 15:58













  • This might be a better approach - json in the value attribute may not be parsed correctly.

    – snakecharmerb
    Dec 29 '18 at 16:09











  • @VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

    – Pointy
    Dec 29 '18 at 16:17











  • @Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

    – Vlad Ivanyk
    Dec 29 '18 at 16:27


















0















Getting the error when trying to open the modal with product details after products were queried with help of ajax



Error itself:



Uncaught SyntaxError: Unexpected end of JSON input
at JSON.parse (<anonymous>)
at HTMLButtonElement.<anonymous> (scripts.js:54)
at HTMLDocument.dispatch (jquery-3.3.1.js:5183)
at HTMLDocument.elemData.handle (jquery-3.3.1.js:4991)


To be clear: I have some filters, result of which is filtered in the python filter_items function then it uses JSONResponse to send it to the front-end
in form of a dictionary(as_dict() function in Item model) were they are added to hidden input value. JS function takes that hidden input value and renders the results of filtering using the data from that input.



Item Model which is queried with help of filter function:



class Item(models.Model):

ITEM_TYPES = (
('UM', 'Umbrella'),
('SK', 'Skirt'),
('TR', 'Trousers'),
('OT', 'Other')
)

BRANDS = (
('VS', 'Versace'),
('SP', 'Supreme'),
('SI', 'Stone Island'),
('FP', 'Fred Perry'),
)

title = models.CharField(max_length=256)
image = models.ImageField(upload_to='img/')
brand = models.CharField(max_length=256)
type = models.CharField(choices=ITEM_TYPES, max_length=2)
description = models.TextField(blank=True, null=True)
season = models.TextField(blank=True, null=True)
discount = models.FloatField(blank=True, null=True)
price = models.FloatField()

def __str__(self):
return self.title + ' ' + self.type

def as_dict(self):
data = {"title": self.title, "image": self.image.url, "brand": self.brand, "type": self.type,
"discount": self.discount, "price": self.price, "rus_representation": self.rus_representation,
"description": self.description, "season": self.season, "images": [self.image.url]}

if self.images:
for image in self.images.all():
data['images'].append(image.image.url)

# data['dumped'] = json.dumps(data)
# print(data['dumped'])
return data

def dumped_as_dict(self):
return json.dumps(self.as_dict())

@property
def rus_representation(self):

if self.type == 'UM':
return 'Зонтик'
elif self.type == 'SK':
return 'Юбка'
elif self.type == 'TR':
return 'Штаны'
elif self.type == 'OT':
return 'Другое'


Class based view with filter function inside of it:



class ProductsListView(ListView):
model = Item
types = Item.ITEM_TYPES
brands = Item.BRANDS

def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
context['types'] = self.types
context['brands'] = self.brands
return context

@classmethod
def filter_items(cls, request, *args, **kwargs):
if request.is_ajax():
data = request.GET

queryset = Item.objects.all()

if not data['type'] == 'ALL':
queryset = queryset.filter(type=data['type'])

if not data['brand'] == 'ALL':
queryset = queryset.filter(brand__contains=data['brand'])
return JsonResponse({'result': [item.as_dict() for item in queryset]})


JavaScript filter function:



    $('.choice-link').click(function () {
var choice = $(this).text();

$(this).siblings().attr('id', '');

$(this).attr('id', 'active');

$(this).parent().parent().children('button').text(choice);

var data = {
'brand': $('.brand-dropdown').children('#active').attr('data-choice'),
'type': $('.type-dropdown').children('#active').attr('data-choice')
};

$.ajax({
url: '../ajax/filter/',
data: data,
success: function (data) {
$('.item-block').remove();
$.each(data.result, function (index, item) {
if (!item.discount) {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
} else {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span><span class="discount badge badge-danger">' + item.discount + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
}
$('.items-list').children('hr').after(el)
});

}
})
});


Java Script function which fills the modal with related data:



$(document).on('click', '.item-btn', function () {
var data = JSON.parse($(this).siblings('input').val()); (line 54 where error message points)

$('.product-title').html(data.rus_representation + ' "<i>' + data.brand + '</i>"' + '<hr>');

if(data.description) {
$('.product-description').text(data.description);
}else{
$('.product-description').html('<h4>Описнаие пока не добавлено</h4>')
}

$('.carousel-inner').empty();
$.each(data.images, function (index, img) {
if(index === 0){
var el = '<div class="carousel-item active"><img class="d-block w-100" src="'+ img +'"></div>'
} else {
var el = '<div class="carousel-item"><img class="d-block w-100" src="'+ img +'"></div>'
}

$('.carousel-inner').append(el)
});

$('.product-brand').html('<i>' + data.brand + '</i>');
$('.product-type').text(data.rus_representation);
$('.product-season').text(data.season);

if (data.discount){
$('.discount-in-modal').html('<span class="discount badge badge-danger" style="position: relative; top: -5px">'+ data.discount +' $</span>');
}

$('.product-price').text(data.price);


});



HTML:



            {% for item in object_list %}
<div class="item-block flex" style="flex-direction: column">
<input type="hidden" value="{{ item.dumped_as_dict }}">
<img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5); max-height: 300px" src="{{ item.image.url }}">
<h6 class="item-title">
{{item.rus_representation}} "{{item.brand}}"
<hr>
</h6>
<p class="flex" style="align-items: flex-start">
<span class="price-tag">{{ item.price }} $</span>
{% if item.discount %}
<span class="discount badge badge-danger">{{ item.discount }} $</span>
{% endif %}
</p>
<button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" src="{% static 'img/arrow.png' %}"></button>
</div>
{% endfor %}


IF do console.log(JSON.stringify(item));:



{"title":"tst","image":"/media/img/_58A1259_sm.jpg","brand":"GUCCI","type":"SK","discount":9000000,"price":9,"rus_representation":"Юбка","description":"LoL Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.","season":"","images":["/media/img/_58A1259_sm.jpg","/media/img/_58A7975_sm.jpg"]}


How it should look like:



opening the modal on initial load



What I have:



if use filtering and them trying to open details modal



Adding view from Inspector:
For some reasons string is not fully added to value attr










share|improve this question




















  • 1





    What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

    – snakecharmerb
    Dec 29 '18 at 15:55











  • JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

    – Vlad Ivanyk
    Dec 29 '18 at 15:58













  • This might be a better approach - json in the value attribute may not be parsed correctly.

    – snakecharmerb
    Dec 29 '18 at 16:09











  • @VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

    – Pointy
    Dec 29 '18 at 16:17











  • @Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

    – Vlad Ivanyk
    Dec 29 '18 at 16:27
















0












0








0








Getting the error when trying to open the modal with product details after products were queried with help of ajax



Error itself:



Uncaught SyntaxError: Unexpected end of JSON input
at JSON.parse (<anonymous>)
at HTMLButtonElement.<anonymous> (scripts.js:54)
at HTMLDocument.dispatch (jquery-3.3.1.js:5183)
at HTMLDocument.elemData.handle (jquery-3.3.1.js:4991)


To be clear: I have some filters, result of which is filtered in the python filter_items function then it uses JSONResponse to send it to the front-end
in form of a dictionary(as_dict() function in Item model) were they are added to hidden input value. JS function takes that hidden input value and renders the results of filtering using the data from that input.



Item Model which is queried with help of filter function:



class Item(models.Model):

ITEM_TYPES = (
('UM', 'Umbrella'),
('SK', 'Skirt'),
('TR', 'Trousers'),
('OT', 'Other')
)

BRANDS = (
('VS', 'Versace'),
('SP', 'Supreme'),
('SI', 'Stone Island'),
('FP', 'Fred Perry'),
)

title = models.CharField(max_length=256)
image = models.ImageField(upload_to='img/')
brand = models.CharField(max_length=256)
type = models.CharField(choices=ITEM_TYPES, max_length=2)
description = models.TextField(blank=True, null=True)
season = models.TextField(blank=True, null=True)
discount = models.FloatField(blank=True, null=True)
price = models.FloatField()

def __str__(self):
return self.title + ' ' + self.type

def as_dict(self):
data = {"title": self.title, "image": self.image.url, "brand": self.brand, "type": self.type,
"discount": self.discount, "price": self.price, "rus_representation": self.rus_representation,
"description": self.description, "season": self.season, "images": [self.image.url]}

if self.images:
for image in self.images.all():
data['images'].append(image.image.url)

# data['dumped'] = json.dumps(data)
# print(data['dumped'])
return data

def dumped_as_dict(self):
return json.dumps(self.as_dict())

@property
def rus_representation(self):

if self.type == 'UM':
return 'Зонтик'
elif self.type == 'SK':
return 'Юбка'
elif self.type == 'TR':
return 'Штаны'
elif self.type == 'OT':
return 'Другое'


Class based view with filter function inside of it:



class ProductsListView(ListView):
model = Item
types = Item.ITEM_TYPES
brands = Item.BRANDS

def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
context['types'] = self.types
context['brands'] = self.brands
return context

@classmethod
def filter_items(cls, request, *args, **kwargs):
if request.is_ajax():
data = request.GET

queryset = Item.objects.all()

if not data['type'] == 'ALL':
queryset = queryset.filter(type=data['type'])

if not data['brand'] == 'ALL':
queryset = queryset.filter(brand__contains=data['brand'])
return JsonResponse({'result': [item.as_dict() for item in queryset]})


JavaScript filter function:



    $('.choice-link').click(function () {
var choice = $(this).text();

$(this).siblings().attr('id', '');

$(this).attr('id', 'active');

$(this).parent().parent().children('button').text(choice);

var data = {
'brand': $('.brand-dropdown').children('#active').attr('data-choice'),
'type': $('.type-dropdown').children('#active').attr('data-choice')
};

$.ajax({
url: '../ajax/filter/',
data: data,
success: function (data) {
$('.item-block').remove();
$.each(data.result, function (index, item) {
if (!item.discount) {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
} else {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span><span class="discount badge badge-danger">' + item.discount + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
}
$('.items-list').children('hr').after(el)
});

}
})
});


Java Script function which fills the modal with related data:



$(document).on('click', '.item-btn', function () {
var data = JSON.parse($(this).siblings('input').val()); (line 54 where error message points)

$('.product-title').html(data.rus_representation + ' "<i>' + data.brand + '</i>"' + '<hr>');

if(data.description) {
$('.product-description').text(data.description);
}else{
$('.product-description').html('<h4>Описнаие пока не добавлено</h4>')
}

$('.carousel-inner').empty();
$.each(data.images, function (index, img) {
if(index === 0){
var el = '<div class="carousel-item active"><img class="d-block w-100" src="'+ img +'"></div>'
} else {
var el = '<div class="carousel-item"><img class="d-block w-100" src="'+ img +'"></div>'
}

$('.carousel-inner').append(el)
});

$('.product-brand').html('<i>' + data.brand + '</i>');
$('.product-type').text(data.rus_representation);
$('.product-season').text(data.season);

if (data.discount){
$('.discount-in-modal').html('<span class="discount badge badge-danger" style="position: relative; top: -5px">'+ data.discount +' $</span>');
}

$('.product-price').text(data.price);


});



HTML:



            {% for item in object_list %}
<div class="item-block flex" style="flex-direction: column">
<input type="hidden" value="{{ item.dumped_as_dict }}">
<img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5); max-height: 300px" src="{{ item.image.url }}">
<h6 class="item-title">
{{item.rus_representation}} "{{item.brand}}"
<hr>
</h6>
<p class="flex" style="align-items: flex-start">
<span class="price-tag">{{ item.price }} $</span>
{% if item.discount %}
<span class="discount badge badge-danger">{{ item.discount }} $</span>
{% endif %}
</p>
<button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" src="{% static 'img/arrow.png' %}"></button>
</div>
{% endfor %}


IF do console.log(JSON.stringify(item));:



{"title":"tst","image":"/media/img/_58A1259_sm.jpg","brand":"GUCCI","type":"SK","discount":9000000,"price":9,"rus_representation":"Юбка","description":"LoL Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.","season":"","images":["/media/img/_58A1259_sm.jpg","/media/img/_58A7975_sm.jpg"]}


How it should look like:



opening the modal on initial load



What I have:



if use filtering and them trying to open details modal



Adding view from Inspector:
For some reasons string is not fully added to value attr










share|improve this question
















Getting the error when trying to open the modal with product details after products were queried with help of ajax



Error itself:



Uncaught SyntaxError: Unexpected end of JSON input
at JSON.parse (<anonymous>)
at HTMLButtonElement.<anonymous> (scripts.js:54)
at HTMLDocument.dispatch (jquery-3.3.1.js:5183)
at HTMLDocument.elemData.handle (jquery-3.3.1.js:4991)


To be clear: I have some filters, result of which is filtered in the python filter_items function then it uses JSONResponse to send it to the front-end
in form of a dictionary(as_dict() function in Item model) were they are added to hidden input value. JS function takes that hidden input value and renders the results of filtering using the data from that input.



Item Model which is queried with help of filter function:



class Item(models.Model):

ITEM_TYPES = (
('UM', 'Umbrella'),
('SK', 'Skirt'),
('TR', 'Trousers'),
('OT', 'Other')
)

BRANDS = (
('VS', 'Versace'),
('SP', 'Supreme'),
('SI', 'Stone Island'),
('FP', 'Fred Perry'),
)

title = models.CharField(max_length=256)
image = models.ImageField(upload_to='img/')
brand = models.CharField(max_length=256)
type = models.CharField(choices=ITEM_TYPES, max_length=2)
description = models.TextField(blank=True, null=True)
season = models.TextField(blank=True, null=True)
discount = models.FloatField(blank=True, null=True)
price = models.FloatField()

def __str__(self):
return self.title + ' ' + self.type

def as_dict(self):
data = {"title": self.title, "image": self.image.url, "brand": self.brand, "type": self.type,
"discount": self.discount, "price": self.price, "rus_representation": self.rus_representation,
"description": self.description, "season": self.season, "images": [self.image.url]}

if self.images:
for image in self.images.all():
data['images'].append(image.image.url)

# data['dumped'] = json.dumps(data)
# print(data['dumped'])
return data

def dumped_as_dict(self):
return json.dumps(self.as_dict())

@property
def rus_representation(self):

if self.type == 'UM':
return 'Зонтик'
elif self.type == 'SK':
return 'Юбка'
elif self.type == 'TR':
return 'Штаны'
elif self.type == 'OT':
return 'Другое'


Class based view with filter function inside of it:



class ProductsListView(ListView):
model = Item
types = Item.ITEM_TYPES
brands = Item.BRANDS

def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
context['types'] = self.types
context['brands'] = self.brands
return context

@classmethod
def filter_items(cls, request, *args, **kwargs):
if request.is_ajax():
data = request.GET

queryset = Item.objects.all()

if not data['type'] == 'ALL':
queryset = queryset.filter(type=data['type'])

if not data['brand'] == 'ALL':
queryset = queryset.filter(brand__contains=data['brand'])
return JsonResponse({'result': [item.as_dict() for item in queryset]})


JavaScript filter function:



    $('.choice-link').click(function () {
var choice = $(this).text();

$(this).siblings().attr('id', '');

$(this).attr('id', 'active');

$(this).parent().parent().children('button').text(choice);

var data = {
'brand': $('.brand-dropdown').children('#active').attr('data-choice'),
'type': $('.type-dropdown').children('#active').attr('data-choice')
};

$.ajax({
url: '../ajax/filter/',
data: data,
success: function (data) {
$('.item-block').remove();
$.each(data.result, function (index, item) {
if (!item.discount) {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
} else {
var el = '<div class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'><img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5);" src="' + item.image + '"><h6 class="item-title">' + item.rus_representation + ' "' + item.brand + '"<hr></h6><p class="flex" style="align-items: flex-start"><span class="price-tag">' + item.price + ' $</span><span class="discount badge badge-danger">' + item.discount + ' $</span></p><button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" "></button></div>';
}
$('.items-list').children('hr').after(el)
});

}
})
});


Java Script function which fills the modal with related data:



$(document).on('click', '.item-btn', function () {
var data = JSON.parse($(this).siblings('input').val()); (line 54 where error message points)

$('.product-title').html(data.rus_representation + ' "<i>' + data.brand + '</i>"' + '<hr>');

if(data.description) {
$('.product-description').text(data.description);
}else{
$('.product-description').html('<h4>Описнаие пока не добавлено</h4>')
}

$('.carousel-inner').empty();
$.each(data.images, function (index, img) {
if(index === 0){
var el = '<div class="carousel-item active"><img class="d-block w-100" src="'+ img +'"></div>'
} else {
var el = '<div class="carousel-item"><img class="d-block w-100" src="'+ img +'"></div>'
}

$('.carousel-inner').append(el)
});

$('.product-brand').html('<i>' + data.brand + '</i>');
$('.product-type').text(data.rus_representation);
$('.product-season').text(data.season);

if (data.discount){
$('.discount-in-modal').html('<span class="discount badge badge-danger" style="position: relative; top: -5px">'+ data.discount +' $</span>');
}

$('.product-price').text(data.price);


});



HTML:



            {% for item in object_list %}
<div class="item-block flex" style="flex-direction: column">
<input type="hidden" value="{{ item.dumped_as_dict }}">
<img class="img-fluid" style="box-shadow: 0 0 10px rgba(0,0,0,0.5); max-height: 300px" src="{{ item.image.url }}">
<h6 class="item-title">
{{item.rus_representation}} "{{item.brand}}"
<hr>
</h6>
<p class="flex" style="align-items: flex-start">
<span class="price-tag">{{ item.price }} $</span>
{% if item.discount %}
<span class="discount badge badge-danger">{{ item.discount }} $</span>
{% endif %}
</p>
<button type="button" class="item-btn btn-sm btn btn-outline-info" data-toggle="modal" data-target=".details-modal">Подробней <img style="height: 10px" src="{% static 'img/arrow.png' %}"></button>
</div>
{% endfor %}


IF do console.log(JSON.stringify(item));:



{"title":"tst","image":"/media/img/_58A1259_sm.jpg","brand":"GUCCI","type":"SK","discount":9000000,"price":9,"rus_representation":"Юбка","description":"LoL Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.","season":"","images":["/media/img/_58A1259_sm.jpg","/media/img/_58A7975_sm.jpg"]}


How it should look like:



opening the modal on initial load



What I have:



if use filtering and them trying to open details modal



Adding view from Inspector:
For some reasons string is not fully added to value attr







javascript python json django






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Dec 29 '18 at 16:38







Vlad Ivanyk

















asked Dec 29 '18 at 15:47









Vlad IvanykVlad Ivanyk

33




33








  • 1





    What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

    – snakecharmerb
    Dec 29 '18 at 15:55











  • JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

    – Vlad Ivanyk
    Dec 29 '18 at 15:58













  • This might be a better approach - json in the value attribute may not be parsed correctly.

    – snakecharmerb
    Dec 29 '18 at 16:09











  • @VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

    – Pointy
    Dec 29 '18 at 16:17











  • @Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

    – Vlad Ivanyk
    Dec 29 '18 at 16:27
















  • 1





    What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

    – snakecharmerb
    Dec 29 '18 at 15:55











  • JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

    – Vlad Ivanyk
    Dec 29 '18 at 15:58













  • This might be a better approach - json in the value attribute may not be parsed correctly.

    – snakecharmerb
    Dec 29 '18 at 16:09











  • @VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

    – Pointy
    Dec 29 '18 at 16:17











  • @Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

    – Vlad Ivanyk
    Dec 29 '18 at 16:27










1




1





What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

– snakecharmerb
Dec 29 '18 at 15:55





What we need to see here is the html that the JSON.parse line is operating on - it looks like it doesn't contain valid json.

– snakecharmerb
Dec 29 '18 at 15:55













JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

– Vlad Ivanyk
Dec 29 '18 at 15:58







JavaScript filter function part, you can see the variable el there, which holds the html for just filtered results Will aslo add html on how it looks like on initial load

– Vlad Ivanyk
Dec 29 '18 at 15:58















This might be a better approach - json in the value attribute may not be parsed correctly.

– snakecharmerb
Dec 29 '18 at 16:09





This might be a better approach - json in the value attribute may not be parsed correctly.

– snakecharmerb
Dec 29 '18 at 16:09













@VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

– Pointy
Dec 29 '18 at 16:17





@VladIvanyk the problem is that whatever is in the .value of the <input> is not valid JSON, but you did not post what the .value actually looks like.

– Pointy
Dec 29 '18 at 16:17













@Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

– Vlad Ivanyk
Dec 29 '18 at 16:27







@Pointy As I said above it is visible in the js function responsible for filtering $('.choice-link').click(function () { where I have variable el inside the $.each loop. var el = '<div id="item'+ index +'" class="item-block flex" style="flex-direction: column"><input type="hidden" value='+ JSON.stringify(item) +'> If I got you right of coursse

– Vlad Ivanyk
Dec 29 '18 at 16:27














1 Answer
1






active

oldest

votes


















0














When you build that HTML string, your code does something like this:



var el = '<div ... value=' + JSON.stringify(x) + ' ... >';


The HTML result will therefore be



var el = '<div ... value={ ... } ... >';


Because the attribute value for "value" is not quoted in the resulting HTML source, the first space character in the JSON is the end of the attribute value, as far as the HTML parser is concerned.



You need to include quotes at least:



var el = '<div ... value='' + JSON.stringify(x) + '' ... >';


I would also strongly suggest that you use an HTML entity encoder to encode any HTML metacharacters in the string, something like



function scrubHtml(s) {
return s.replace(/[<>'"&]/g, function(meta) {
return "&#" + meta.charCodeAt(0) + ";";
});
}





share|improve this answer


























  • Yeah!!! You are right! Thank you man!

    – Vlad Ivanyk
    Dec 29 '18 at 16:50











  • That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

    – Vlad Ivanyk
    Dec 29 '18 at 16:56













  • HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

    – Pointy
    Dec 29 '18 at 18:45











  • @VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

    – Pointy
    Dec 29 '18 at 18:56













Your Answer






StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");

StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});

function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});


}
});














draft saved

draft discarded


















StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53970986%2funcaught-syntaxerror-unexpected-end-of-json-input-cant-properly-parse-the-inf%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown

























1 Answer
1






active

oldest

votes








1 Answer
1






active

oldest

votes









active

oldest

votes






active

oldest

votes









0














When you build that HTML string, your code does something like this:



var el = '<div ... value=' + JSON.stringify(x) + ' ... >';


The HTML result will therefore be



var el = '<div ... value={ ... } ... >';


Because the attribute value for "value" is not quoted in the resulting HTML source, the first space character in the JSON is the end of the attribute value, as far as the HTML parser is concerned.



You need to include quotes at least:



var el = '<div ... value='' + JSON.stringify(x) + '' ... >';


I would also strongly suggest that you use an HTML entity encoder to encode any HTML metacharacters in the string, something like



function scrubHtml(s) {
return s.replace(/[<>'"&]/g, function(meta) {
return "&#" + meta.charCodeAt(0) + ";";
});
}





share|improve this answer


























  • Yeah!!! You are right! Thank you man!

    – Vlad Ivanyk
    Dec 29 '18 at 16:50











  • That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

    – Vlad Ivanyk
    Dec 29 '18 at 16:56













  • HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

    – Pointy
    Dec 29 '18 at 18:45











  • @VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

    – Pointy
    Dec 29 '18 at 18:56


















0














When you build that HTML string, your code does something like this:



var el = '<div ... value=' + JSON.stringify(x) + ' ... >';


The HTML result will therefore be



var el = '<div ... value={ ... } ... >';


Because the attribute value for "value" is not quoted in the resulting HTML source, the first space character in the JSON is the end of the attribute value, as far as the HTML parser is concerned.



You need to include quotes at least:



var el = '<div ... value='' + JSON.stringify(x) + '' ... >';


I would also strongly suggest that you use an HTML entity encoder to encode any HTML metacharacters in the string, something like



function scrubHtml(s) {
return s.replace(/[<>'"&]/g, function(meta) {
return "&#" + meta.charCodeAt(0) + ";";
});
}





share|improve this answer


























  • Yeah!!! You are right! Thank you man!

    – Vlad Ivanyk
    Dec 29 '18 at 16:50











  • That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

    – Vlad Ivanyk
    Dec 29 '18 at 16:56













  • HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

    – Pointy
    Dec 29 '18 at 18:45











  • @VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

    – Pointy
    Dec 29 '18 at 18:56
















0












0








0







When you build that HTML string, your code does something like this:



var el = '<div ... value=' + JSON.stringify(x) + ' ... >';


The HTML result will therefore be



var el = '<div ... value={ ... } ... >';


Because the attribute value for "value" is not quoted in the resulting HTML source, the first space character in the JSON is the end of the attribute value, as far as the HTML parser is concerned.



You need to include quotes at least:



var el = '<div ... value='' + JSON.stringify(x) + '' ... >';


I would also strongly suggest that you use an HTML entity encoder to encode any HTML metacharacters in the string, something like



function scrubHtml(s) {
return s.replace(/[<>'"&]/g, function(meta) {
return "&#" + meta.charCodeAt(0) + ";";
});
}





share|improve this answer















When you build that HTML string, your code does something like this:



var el = '<div ... value=' + JSON.stringify(x) + ' ... >';


The HTML result will therefore be



var el = '<div ... value={ ... } ... >';


Because the attribute value for "value" is not quoted in the resulting HTML source, the first space character in the JSON is the end of the attribute value, as far as the HTML parser is concerned.



You need to include quotes at least:



var el = '<div ... value='' + JSON.stringify(x) + '' ... >';


I would also strongly suggest that you use an HTML entity encoder to encode any HTML metacharacters in the string, something like



function scrubHtml(s) {
return s.replace(/[<>'"&]/g, function(meta) {
return "&#" + meta.charCodeAt(0) + ";";
});
}






share|improve this answer














share|improve this answer



share|improve this answer








edited Dec 29 '18 at 18:57

























answered Dec 29 '18 at 16:46









PointyPointy

315k44455515




315k44455515













  • Yeah!!! You are right! Thank you man!

    – Vlad Ivanyk
    Dec 29 '18 at 16:50











  • That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

    – Vlad Ivanyk
    Dec 29 '18 at 16:56













  • HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

    – Pointy
    Dec 29 '18 at 18:45











  • @VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

    – Pointy
    Dec 29 '18 at 18:56





















  • Yeah!!! You are right! Thank you man!

    – Vlad Ivanyk
    Dec 29 '18 at 16:50











  • That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

    – Vlad Ivanyk
    Dec 29 '18 at 16:56













  • HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

    – Pointy
    Dec 29 '18 at 18:45











  • @VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

    – Pointy
    Dec 29 '18 at 18:56



















Yeah!!! You are right! Thank you man!

– Vlad Ivanyk
Dec 29 '18 at 16:50





Yeah!!! You are right! Thank you man!

– Vlad Ivanyk
Dec 29 '18 at 16:50













That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

– Vlad Ivanyk
Dec 29 '18 at 16:56







That part you added after editing it replaces /[<>'"&]/g symbols with "&" + meta.charCodeAt(0) + ";"; but what is that symbol ?

– Vlad Ivanyk
Dec 29 '18 at 16:56















HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

– Pointy
Dec 29 '18 at 18:45





HTML entity notation: &nnn; where the nnn part is a character code. That protects embedded HTML special characters from confusing the HTML parser. The resulting attribute values will be plain strings; those symbols are "digested" by HTML into simple characters.

– Pointy
Dec 29 '18 at 18:45













@VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

– Pointy
Dec 29 '18 at 18:56







@VladIvanyk oops except I forgot something important!! It should be &# not just & - fixing the answer now. My apologies.

– Pointy
Dec 29 '18 at 18:56




















draft saved

draft discarded




















































Thanks for contributing an answer to Stack Overflow!


  • Please be sure to answer the question. Provide details and share your research!

But avoid



  • Asking for help, clarification, or responding to other answers.

  • Making statements based on opinion; back them up with references or personal experience.


To learn more, see our tips on writing great answers.




draft saved


draft discarded














StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53970986%2funcaught-syntaxerror-unexpected-end-of-json-input-cant-properly-parse-the-inf%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown





















































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown

































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown







Popular posts from this blog

Mossoró

Error while reading .h5 file using the rhdf5 package in R

Pushsharp Apns notification error: 'InvalidToken'