Would be nice to have a shields.io badge for VirusTotal through their public API.
Here is an example to have the number of postitives / total detections :
https://www.virustotal.com/vtapi/v2/file/reportPOSTURLencoded form data{
"scans": {},
"scan_id": "87b46227991cb84bc20f301aaf80e38e4e1ce41e42cd634d31e94929012391a7-1511111630",
"sha1": "70a2a163a25f24a3cf3ae7d1a524bd3a67373f71",
"resource": "87b46227991cb84bc20f301aaf80e38e4e1ce41e42cd634d31e94929012391a7",
"response_code": 1,
"scan_date": "2017-11-19 17:13:50",
"permalink": "https://www.virustotal.com/file/87b46227991cb84bc20f301aaf80e38e4e1ce41e42cd634d31e94929012391a7/analysis/1511111630/",
"verbose_msg": "Scan finished, information embedded",
"total": 67,
"positives": 1,
"sha256": "87b46227991cb84bc20f301aaf80e38e4e1ce41e42cd634d31e94929012391a7",
"md5": "8fa103433f571ee4bde82128aed418b8"
}
Then we can create a badge like :
Thanks!
But as you can see, the API required an API key :(
I will contact VirusTotal about it and i'll keep you in touch.
I like the idea of this badge,
Hopefully there is some way we can work around the API key.
@RedSparr0w, yes indeed, i have found the XHR payload.
The payload is : https://www.virustotal.com/ui/files/cd49e54905d4820f864c58ca8736114210abb98362d94e8c215b906a2a0a7002
Then process :
data.attributes.last_analysis_stats.maliciousdata.attributes.last_analysis_stats.undetected + data.attributes.last_analysis_stats.maliciousI have started with something like that for the PR :
// VirusTotal detections.
// API documentation : https://www.virustotal.com/en/documentation/public-api/
camp.route(/^\/virustotal\/detections\/(.*)\.(svg|png|gif|jpg|json)$/,
cache(function(data, match, sendBadge, request) {
var sha256 = match[1]; // eg, cd49e54905d4820f864c58ca8736114210abb98362d94e8c215b906a2a0a7002
var format = match[2];
var badgeData = getBadgeData('virustotal', data);
var options = {
method: 'GET',
json: true,
uri: 'https://www.virustotal.com/ui/files/' + sha256
};
request(options, function(err, res, json) {
if (err !== null || res.statusCode >= 500 || typeof json !== 'object') {
badgeData.text[1] = 'inaccessible';
sendBadge(format, badgeData);
return;
}
if (res.statusCode = 404) {
badgeData.text[1] = 'not found';
badgeData.colorscheme = 'lightgrey';
sendBadge(format, badgeData);
return;
}
try {
var detectedMalicious = json.data.attributes.last_analysis_stats.malicious
var detectedTotal = detectedMalicious + json.data.attributes.last_analysis_stats.undetected
badgeData.text[1] = detectedMalicious + ' / ' + detectedTotal;
badgeData.colorscheme = 'brightgreen';
if (detectedMalicious > 0) {
badgeData.colorscheme = 'red';
}
sendBadge(format, badgeData);
} catch(e) {
badgeData.text[1] = 'invalid';
sendBadge(format, badgeData);
}
});
}));
Seems good to you @RedSparr0w ?
Heres the new payload from the link you posted 馃槅
{
"error": {
"code": "BadRequestError",
"message": "Don't be evil"
}
}
It works in private browsing but it doesn't seem stable 馃槃
Seems to only show correctly when you type the link directly into the browser rather than clicking a link,
I assume any cross domain request would probably return the error also.
Closing this for now. Feel free to reopen if there is news with the upstream API!
Most helpful comment
Heres the new payload from the link you posted 馃槅