So I'm making a realtime chat with socket.io and node.js, and I have the chat and everything working, but if somebody links a website in the chat, I want it to be an hyperlink automatically.
I'm using autolinker.js to do this, and it's making the links as I want, but my problem is the way I output messages to avoid HTML injections.
for(var x = data.length - 1; x >= 0; x--) {
var autolinker = new Autolinker();
var linkedText = autolinker.link(data[x].message);
var message = document.createElement('div');
var linkOfMessage;
message.setAttribute('class', 'chat-message');
//message.textContent = data[x].name + ': ';
message.innerHTML = data[x].name + ': ' + linkedText;
// Append
messages.insertBefore(message, messages.firstChild);
messages.appendChild(message);
messages.scrollTop = messages.scrollHeight;
}
So the message is getting handled correctly, but with innerHTML, they can basically use scripts inside my chat, which is bad. But
message.textContent = data[x].name + ': ' + linkedText;
Will just display my hyperlink in plain text without it being clickable, is there anyway to do this without setting the site at risk?
I've spent a couple of hours looking around and couldn't fint anything related to this.
Thanks in advance!
You should always sanitize user input. You want links, so you have to allow some html tags in messages, but you want to filter out most of them (some are dangerous, like script, and some could "damage" your chat visuals). Try experimenting with packages such as
https://www.npmjs.com/package/sanitize-html
It's not a good idea to roll your own sanitizer. Packages like this allow to specify which tags to allow, which to remove and have various other, helpful options.
Related
so my web page is http://localhost:7777/newdev/art.html which points to my html art.html doc. I wanna acces that html using a different utl like: http://localhost:7777/newdev/data/. I would just like a verrry simple way to go to that url and pull up the art.html.
I have tried adding the html at the end and also changing the rest service to look for the http://localhost:7777/newdev/art.html.
$scope.done = function(){
$scope.major = "";
$scope.picked = document.getElementsByClassName("math").value + "," + document.getElementsByClassName("Science").value + "," + document.getElementsByClassName("Music").value + "," + document.getElementsByClassName("Art").value+ "," + document.getElementsByClassName("ss").value;
var url= 'done.html/';
url+= '?id='+$scope.picked;
window.open(url);
};
Expected results: I will go to http://localhost:7777/newdev/data/ and it will pull up my html document.
Actual result: The rest service doesn't get called or the html doesn't open
Things to think about: This is not for a large website, its for just a side project that is going to stay on my machine and only be ran locally for learning purposes. I am looking for the simple most basic why to do this so it'll give me a platform to grow a learn from.
I have been going through so many forums & wikipedia's since few days for trying to understand about XSS attacks alomost I have spent 2-3 days but still not get better idea as suggesting multiple solutions by experts & I want know how the hackers can inject malicious code on victims browser ? and my application have been use to run on some App Scanner standard testing tool so its caught so many XSS issues. I want put here one of XSS issue of my application so can please some one help me out to understand the what exactly I have to do for this issue. Still I have been trying a lot to get better understand about XSS issues. This is my code snippet
function getParameter(param) {
var val = "";
var qs = window.location.search;
var start = qs.indexOf(param);
if (start != -1) {
start += param.length + 1;
var end = qs.indexOf("&", start);
if (end == -1) {
end = qs.length
}
val = qs.substring(start,end);
}
return val;
}
var formName = getParameter("formName");
var myValue = ''+thisDay+'</td>';
document.getElementById('calendarA').innerHTML = myValue;
And these statements are
var qs = window.location.search;
val = qs.substring(start,end);
var formName = getParameter("formName");
var myValue = ''+thisDay+'</td>';
document.getElementById('calendarA').innerHTML = myValue;
cought by App scanner testing tool as possible code for XSS(Cross Site Scripting) issues but I am not sure how it is cause to XSS & how I can fix this issue now. Can anybody please provide insights on how this vulnerability can be fixed?
var myValue = ''+thisDay+'</td>';
This line doesn't have any escaping, it expects '(... \''+formName+'\' );...' to be a string. But it can become some other thing:
formName = "'); alert('I\'m free to do anything here'); (''+"
document.getElementById('calendarA').innerHTML = myValue;
Let's place such fragment into myValue:
... <img src=void onerror="alert('hacked')" /> ...
You can check it works:
document.querySelector('button').addEventListener('click', function () {
document.querySelector('output').innerHTML = document.querySelector('textarea').value;
})
<textarea>... <img src=void onerror="alert('hacked')" /> ...</textarea>
<button>Go</button>
<output></output>
You should never trust any data passed by url string. Any site can place any link to you site. Some user clicks it, goes to your site, parameters are executed in context of your site, and attacker can do anything he wants to.
Nothing in the code you've shown us is vulnerable.
You are reading user input, so there is the potential to introduce a vulnerability there. That is probably what the tool you are using is detecting.
If your code is vulnerable, then it will be because of whatever you do with the value of formName next (in the code you haven't shown us).
This is a possible DOM based XSS issue.
If you are using the value of formName like document.getElementById("demo").innerHTML=formName or somehow your DOM elements are being created/modified using the formName you are vulnerable,
as i can create a custom url like http://urwebsite.html?formName=<script>document.cookie_will_be_transfered_to_my_server_here</script> and ask a logged in person to click it(simple social engineering) .Now i have that person's session id, using which i can do what ever i want.
As a resolution, all the input data from the user has to be html encoded.
Hello Stack Overflow community,
I am a long time reader, first time poster. Have gotten tons of help from really smart people on this site through other's questions, but I've encountered a problem that has actually compelled me to sign up. Hopefully this post helps somebody else out who's looking for this same information.
I've been trying to figure out the easiest way to display blog information on one of my sites.
I decided to use tumblr and it's API to display this information. This is the code I've come across thats gotten me pretty far along the way:
html
<div id="Posts"><ul></ul></div>
javascript
function loadPosts () {
var key = "api_key=1waQ1OkbKW817GisHWCO0sIRZC4IP7sXeCK7EFulQskOYonz5E";
var api = "https://api.tumblr.com/v2/blog/cantbrooklyn.tumblr.com/";
var retrieve_more = function (offset) {
$.getJSON(api + "posts?callback=?&limit=20&offset=" + offset + "&" + key,function(data) {
$.each(data.response.posts, function(i, item) {
var content = item.body;
$("#Posts ul").append('<li>' + content + '</li>')
});
if (data.response.posts.length == 20) {
retrieve_more(offset + 20);
}
});
};
retrieve_more(0);
}
loadPosts();
jsfiddle
If you check the results of the code in jsfiddle, you will see a long list of my posts, but with many instances of the word "undefined." Each "undefined" is supposed to be one of my media post, showing a photo or a video. What's confusing is that images in my textual posts are showing up fine. So somewhere in the javascript, my code is omitting everything but text posts. If anybody has any idea what's wrong, I would appreciate the advice.
Thanks in advance!
zach
Just for fun, i'm trying to implement a "15 puzzle", but with 16 images (from 1 music photo) instead.
The thing is split into 2 scripts / sides. 1 Python CGI script that will perform the Last.FM query + splitting the image in Y x Z chunks. When the python script finishes it outputs a JSON string that contains the location (on server), extension etc.
{"succes": true, "content": {"nrofpieces": 16, "size": {"width": 1096, "height": 961}, "directoryname": "Mako", "extension": "jpeg"}}
On the other side is a HTML, JS, (CSS) combo that will query the CGI script for the images.
$(document).ready(function () {
var artiest = $("#artiest")
var rijen = $("#rijen")
var kolommen = $("#kolommen")
var speelveld = $("#speelveld")
var search = $("#search")
$("#buttonClick").click(function () {
var artiestZ = artiest.val()
var rijenZ = rijen.val()
var kolommenZ = kolommen.val()
$.getJSON("http://localhost:8000/cgi-bin/cgiScript.py", "artiest=" + artiestZ + "&rijen=" + rijenZ + "&kolommen=" + kolommenZ, function (JsonSring) {
console.log("HIIIIII")
if (JsonSring.succes === true){
console.log(JsonSring)
var baseUrl = "http://localhost:8000/"
var extension = JsonSring.content.extension
var url = baseUrl + JsonSring.content.directoryname + "/"
var amountX = rijenZ
var amountY = kolommenZ
for (var i = 0; i < amountX; i += 1){
for (var p = 0; p < amountY; p += 1){
console.log("HI")
var doc = new Image
doc.setAttribute("src", url + JsonSring.content.directoryname + i + "_" + p + "." +extension)
document.getElementById("speelveld").appendChild(doc)
}
}
}else {
// Search failed. Deal with it.
}
})
})
})
where the various id's link to various HTML elements. (Text Fields & Buttons & Div's).
Beneath is a screenshot of the full folder that contains the image files.
Now, coming to the point. All the HTML img tags with src seem correct, yet. Some images don't load, yet other do. I also noticed that all images failed to load in 2s intervals. Is there some kind of timeout, or so?
All this is being ran from a local machine, so disk speed and cpu shouldn't really affect the matter. Also, from what I understand: The call for making the img tags etc is done in a callback from the getJson, meaning it'll only run when getJson has finished / had a reply.
Does the great StackOverFlow community have an idea what's happening here?
To share my knowledge/experiences with the great StackOverflow community,
Small backstory
After progressing a bit further into the project I started to run into various issues going from JSON parsing to not having Allow-Control-Allow-Origin: * headers, making it very hard to get the Ajax Request (Client ==> Python CGI) done.
In the meantime I also started dev'ing on my main desktop (which for some reason either has massive issues with Python versioning or has none). But due to the terminal on my desktop having Python 3.4+ , there was no module CGIHTTPServer. After a small amount of digging, I found that CGIHTTPServer had been transfered into http.server, yet when running plain old python -m http.server, I noticed the CGI script wouldn't run. It would just display. Ofcourse, I forgot the option -cgi.
Main solution
The times I was succesfully using CGIHTTPServer, I had troubles. The images wouldn't load as described above. I suspect that the module just couldn't take the decent amount of requests. Meaning that when suddenly Y x Z requests came in, it would struggle to deliver all the data. ==> Connection Refused.
Since switching to python -m http.server -cgi, no problems what so ever. Currently working on a Bootstrap Grid for all those images!
Thx #Lashane and #Ruud.
I've read a few answers, and tried a bit of different code from them, but haven't been able to solve this. I am a newbie at this and it seems like quite a simple thing to do, apologies if the answer is really obvious, just need it to work really..
So far, I have an aspx page in Visual Studio 2010 / it was created by someone else, and has both JavaScript and cSharp code behind it.
What I would like to happen is that, an 'Edit' button appears on the page in a table in the correct place, and as a result of pressing it, another page is called allowing the editing (of contacts - it's an internal website).
I can get the link working OK as a 'normal' hyperlink, using this line of code:
var editcontact = '<td align = "right" colspan = "40" class =
"contactBorder"><a href="WebForm1.aspx?supplier_id=' +
dataRow.supplier_id + '">Open Contact(s) For Edit</a></td>';
edit contact then gets put in a table like structure (maybe it's "form" given the HTML tags):
finishedcontacts += openrow + contactid + contactname +
contactjobtitle + contactlocation + contacttelephone +
contactemail+ editcontact + '</form></tr>';
That's OK but it's not very 'nice', what I would like is an actual edit button, I can get the button to appear, but the last time I tried it pressing it does nothing:
var editcontact = '<asp:button id = "editImage4" runat="server"
Text="Click me"
OnClientClick="window.open(\'WebForm1.aspx\\?supplier_id=\' + dataRow.supplier_id + \', \'WebForm1\');" />';
Any ideas on how to get this working OK from a button?
Here is some other code I tried, which was to separate out the generation of the url from the calling code, but none of them seemed to work:
//var url = string.Format("{0}?supplier_id={1}", "../WebForm1.aspx", dataRow.supplier_id);
//var url = string.Format("{0}?supplier_id={1}", #"../WebForm1.aspx", dataRow.supplier_id);
//var url = 'string.Format("{0} supplier_id={1}", "WebForm1.aspx",'+ dataRow.supplier_id +')';
var url = 'WebForm1.aspx?supplier_id= '+ dataRow.supplier_id +'';
var supplierid1 = dataRow.supplier_id;
Any ideas what be greatly appreciated. This is my first ever post..
Use Response.Redirect(url) if you want to redirect using your button and this button must be a server side control.
In the end, a colleague helped me out with this.
As other posters identified there was some problems with the URL, and especially with the escapes.
Anyway below is the code in the unlikely event anyone needs something similar.
buttoncode = '';
var editcontact = '' + buttoncode + '';
And we added a function (which should probably be called a method or whatever):
function OpenContactForEdit(supplier_id)
{
window.location = "WebForm1.aspx?supplier_id=" + supplier_id;
}
Comments:
This bit is very important:
onClick="OpenContactForEdit(\'' + dataRow.supplier_id + '\')"
Note exactly how we needed to escape (and 'end escape') the single quotes.
I believe that was quite a big part of why, what I was doing was not working.