Remove Double Quotes from JSON Property
I am trying to create an interactive tour using hopscotch.js. The standard data structure that the JavaScript library requires in order for tour to work is as follows:
// Define the tour!
var tour = {
id: "hello-hopscotch",
steps: [
{
title: "My Header",
content: "This is the header of my page.",
target: "header",
placement: "right"
},
{
title: "My content",
content: "Here is where I put my content.",
target: document.querySelector("#content p"),
placement: "bottom"
}
]
};
Sequencing the tour steps directly in the JavaScript library works great, but ideally I want to be able to store all of this data in a database and use AJAX to pass the data through hopscotch.js. (This means that tours can be created dynamically or content
changed without releasing code).
Everything works fine when mine target
uses an element selector document.querySelector()
.
My basic C # model for each leg of the tour is as follows:
public class MockTourSteps
{
public string Title { get; set; }
public string Content { get; set; }
public string Target { get; set; }
public string Placement { get; set; }
}
Since target
is a string, I need to pass the value in double quotes.
The problem is that when it is serialized to JSON, the following error is thrown when the page is viewed with Chrome developer tools:
Syntax error, unrecognized expression: document.querySelector(".btn-primary")
By examining the JSON data that was returned to the page, I see that the double quotes around mine document.querySelector()
are causing the problem.
I need these double quotes to be removed from mine target
when I specify target
through document.querySelector()
, but the double quotes should remain when I specify target
based on an HTML tag such as header
.
Any ideas how I can achieve this?
source to share
The main problem is that in the above example you are using a javascript object, but you will receive the JSON from your server. You will need to use some client side JSON handling.
I think you can add more information to your model:
public class MockTourStep
{
public string Title { get; set; }
public string Content { get; set; }
public TargetC Target { get; set; }
public string Placement { get; set; }
public enum TargetType
{
ElementName,
QuerySelector
}
public class TargetC
{
[JsonConverter(typeof(StringEnumConverter))]
public TargetType Type { get; set; }
public string Value { get; set; }
}
}
And an example of an answer:
var tour = new
{
Id = "hello-hopscotch",
Steps = new List<MockTourStep>
{
new MockTourStep
{
Title = "My Header",
Content = "This is the header of my page.",
Target = new MockTourStep.TargetC
{
Type = MockTourStep.TargetType.ElementName,
Value = "header"
},
Placement = "bottom"
},
new MockTourStep
{
Title = "My content",
Content = "Here is where I put my content.",
Target = new MockTourStep.TargetC
{
Type = MockTourStep.TargetType.QuerySelector,
Value = "document.querySelector('#content p')"
},
Placement = "bottom"
}
}
};
Then on the client side, you can check the target type and set it to a valid value:
$.getJSON("url", function (tour) {
for (var i = 0; i < tour.steps.length; i++) {
var step = tour.steps[i];
switch (step.target.type) {
case "ElementName":
step.target = step.target.value;
break;
case "QuerySelector":
step.target = eval(step.target.value);
break;
default:
throw Error;
}
}
hopscotch.startTour(tour);
});
Please note what is eval
used for QuerySelector
. The use is eval
dangerous, so you need to check what you serve to the customer.
source to share