mirror of https://github.com/CIRCL/lookyloo
chg: Improve hostname popup
parent
e1f9238bac
commit
ccad142dd0
|
@ -17,7 +17,7 @@ from lookyloo.lookyloo import Lookyloo
|
||||||
from lookyloo.exceptions import NoValidHarFile
|
from lookyloo.exceptions import NoValidHarFile
|
||||||
from .proxied import ReverseProxied
|
from .proxied import ReverseProxied
|
||||||
|
|
||||||
from typing import Optional, Dict, Any, List
|
from typing import Optional, Dict, Any, List, Tuple
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
|
@ -164,11 +164,12 @@ def hostnode_popup(tree_uuid: str, node_uuid: str):
|
||||||
'request_cookie': "/static/cookie_read.png",
|
'request_cookie': "/static/cookie_read.png",
|
||||||
}
|
}
|
||||||
|
|
||||||
urls = []
|
|
||||||
sanejs_lookups: Dict[str, List[str]] = {}
|
sanejs_lookups: Dict[str, List[str]] = {}
|
||||||
if hasattr(lookyloo, 'sanejs') and lookyloo.sanejs.available:
|
if hasattr(lookyloo, 'sanejs') and lookyloo.sanejs.available:
|
||||||
to_lookup = [url.body_hash for url in hostnode.urls if hasattr(url, 'body_hash')]
|
to_lookup = [url.body_hash for url in hostnode.urls if hasattr(url, 'body_hash')]
|
||||||
sanejs_lookups = lookyloo.sanejs.hashes_lookup(to_lookup)
|
sanejs_lookups = lookyloo.sanejs.hashes_lookup(to_lookup)
|
||||||
|
|
||||||
|
urls: List[Tuple[bool, str, str]] = []
|
||||||
for url in hostnode.urls:
|
for url in hostnode.urls:
|
||||||
if hasattr(url, 'body_hash') and url.body_hash in sanejs_lookups:
|
if hasattr(url, 'body_hash') and url.body_hash in sanejs_lookups:
|
||||||
url.add_feature('sane_js_details', sanejs_lookups[url.body_hash])
|
url.add_feature('sane_js_details', sanejs_lookups[url.body_hash])
|
||||||
|
@ -180,7 +181,12 @@ def hostnode_popup(tree_uuid: str, node_uuid: str):
|
||||||
else:
|
else:
|
||||||
# Predefined generic file
|
# Predefined generic file
|
||||||
url.add_feature('sane_js_details_to_print', sanejs_lookups[url.body_hash])
|
url.add_feature('sane_js_details_to_print', sanejs_lookups[url.body_hash])
|
||||||
urls.append(url)
|
|
||||||
|
# For the popup, we need:
|
||||||
|
# * https vs http
|
||||||
|
# * everything after the domain
|
||||||
|
# * the full URL
|
||||||
|
urls.append((url.name.startswith('https'), url.name.split('/', 3)[-1], url))
|
||||||
return render_template('hostname_popup.html',
|
return render_template('hostname_popup.html',
|
||||||
tree_uuid=tree_uuid,
|
tree_uuid=tree_uuid,
|
||||||
hostname_uuid=node_uuid,
|
hostname_uuid=node_uuid,
|
||||||
|
|
|
@ -3,11 +3,42 @@
|
||||||
{% block title %}Details for {{ hostname }} {% endblock %}
|
{% block title %}Details for {{ hostname }} {% endblock %}
|
||||||
|
|
||||||
{% block scripts %}
|
{% block scripts %}
|
||||||
|
{{ super() }}
|
||||||
<script>
|
<script>
|
||||||
function whereAmI() {
|
function whereAmI() {
|
||||||
window.opener.ProcessChildMessage("{{ hostname_uuid }}");
|
window.opener.ProcessChildMessage("{{ hostname_uuid }}");
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
|
<script>
|
||||||
|
// Source: https://codepen.io/nathanlong/pen/ZpAmjv
|
||||||
|
function copyToClipboard(text, el) {
|
||||||
|
var elOriginalText = el.attr('data-original-title');
|
||||||
|
|
||||||
|
var copyTextArea = document.createElement("textarea");
|
||||||
|
copyTextArea.value = text;
|
||||||
|
document.body.appendChild(copyTextArea);
|
||||||
|
copyTextArea.select();
|
||||||
|
|
||||||
|
var successful = document.execCommand('copy');
|
||||||
|
var msg = successful ? 'Copied!' : 'Whoops, not copied!';
|
||||||
|
el.attr('data-original-title', msg).tooltip('show');
|
||||||
|
|
||||||
|
document.body.removeChild(copyTextArea);
|
||||||
|
el.attr('data-original-title', elOriginalText);
|
||||||
|
}
|
||||||
|
|
||||||
|
$(document).ready(function() {
|
||||||
|
// Copy to clipboard
|
||||||
|
// Grab any text in the attribute 'data-copy' and pass it to the copy function
|
||||||
|
$('.js-copy').tooltip();
|
||||||
|
$('.js-copy').click(function() {
|
||||||
|
var text = $(this).attr('data-copy');
|
||||||
|
var el = $(this);
|
||||||
|
copyToClipboard(text, el);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
{% block content %}
|
{% block content %}
|
||||||
|
@ -18,9 +49,27 @@
|
||||||
</center>
|
</center>
|
||||||
<p>Click on the URL to get the content of the response</p>
|
<p>Click on the URL to get the content of the response</p>
|
||||||
<ul class="list-group-flush">
|
<ul class="list-group-flush">
|
||||||
{% for url in urls %}
|
{% for secure, path, url in urls %}
|
||||||
<li class="list-group-item">
|
<li class="list-group-item">
|
||||||
<p class="h3">{{ url.name }}</p>
|
<div class="h3">
|
||||||
|
<button type="button" class="btn btn-default btn-copy js-copy"
|
||||||
|
data-toggle="tooltip" data-placement="bottom" data-copy="{{url.name}}" title="Copy to clipboard">
|
||||||
|
<svg class="bi bi-clipboard" width="1em" height="1em" viewBox="0 0 16 16" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path fill-rule="evenodd" d="M4 1.5H3a2 2 0 0 0-2 2V14a2 2 0 0 0 2 2h10a2 2 0 0 0 2-2V3.5a2 2 0 0 0-2-2h-1v1h1a1 1 0 0 1 1 1V14a1 1 0 0 1-1 1H3a1 1 0 0 1-1-1V3.5a1 1 0 0 1 1-1h1v-1z"/>
|
||||||
|
<path fill-rule="evenodd" d="M9.5 1h-3a.5.5 0 0 0-.5.5v1a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-1a.5.5 0 0 0-.5-.5zm-3-1A1.5 1.5 0 0 0 5 1.5v1A1.5 1.5 0 0 0 6.5 4h3A1.5 1.5 0 0 0 11 2.5v-1A1.5 1.5 0 0 0 9.5 0h-3z"/>
|
||||||
|
</svg>
|
||||||
|
</button>
|
||||||
|
{% if secure %}
|
||||||
|
<svg class="bi bi-lock" width="1em" height="1em" viewBox="0 0 16 16" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path fill-rule="evenodd" d="M11.5 8h-7a1 1 0 0 0-1 1v5a1 1 0 0 0 1 1h7a1 1 0 0 0 1-1V9a1 1 0 0 0-1-1zm-7-1a2 2 0 0 0-2 2v5a2 2 0 0 0 2 2h7a2 2 0 0 0 2-2V9a2 2 0 0 0-2-2h-7zm0-3a3.5 3.5 0 1 1 7 0v3h-1V4a2.5 2.5 0 0 0-5 0v3h-1V4z"/>
|
||||||
|
</svg>
|
||||||
|
{% else %}
|
||||||
|
<svg class="bi bi-unlock" width="1em" height="1em" viewBox="0 0 16 16" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path fill-rule="evenodd" d="M9.655 8H2.333c-.264 0-.398.068-.471.121a.73.73 0 0 0-.224.296 1.626 1.626 0 0 0-.138.59V14c0 .342.076.531.14.635.064.106.151.18.256.237a1.122 1.122 0 0 0 .436.127l.013.001h7.322c.264 0 .398-.068.471-.121a.73.73 0 0 0 .224-.296 1.627 1.627 0 0 0 .138-.59V9c0-.342-.076-.531-.14-.635a.658.658 0 0 0-.255-.237A1.122 1.122 0 0 0 9.655 8zm.012-1H2.333C.5 7 .5 9 .5 9v5c0 2 1.833 2 1.833 2h7.334c1.833 0 1.833-2 1.833-2V9c0-2-1.833-2-1.833-2zM8.5 4a3.5 3.5 0 1 1 7 0v3h-1V4a2.5 2.5 0 0 0-5 0v3h-1V4z"/>
|
||||||
|
</svg>
|
||||||
|
{%endif%}
|
||||||
|
... /{{ path }}
|
||||||
|
</div>
|
||||||
<ul class="list-group">
|
<ul class="list-group">
|
||||||
<li class="list-group-item">
|
<li class="list-group-item">
|
||||||
<p class="h4">Response</p>
|
<p class="h4">Response</p>
|
||||||
|
@ -37,16 +86,20 @@
|
||||||
{%endif%}
|
{%endif%}
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% if not url.empty_response %}
|
|
||||||
<div>
|
<div>
|
||||||
|
{% if not url.empty_response %}
|
||||||
<a href="{{ url_for('urlnode_details', tree_uuid=tree_uuid, node_uuid=url.uuid) }}">
|
<a href="{{ url_for('urlnode_details', tree_uuid=tree_uuid, node_uuid=url.uuid) }}">
|
||||||
Download response body.
|
Download response body.
|
||||||
</a></br>
|
</a></br>
|
||||||
Body size: {{ sizeof_fmt(url.body.getbuffer().nbytes) }}
|
Body size: {{ sizeof_fmt(url.body.getbuffer().nbytes) }}
|
||||||
</div>
|
|
||||||
{% else %}
|
{% else %}
|
||||||
Empty body.
|
Empty body.
|
||||||
{%endif%}
|
{%endif%}
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
Status Code: {{ url.response['status'] }}
|
||||||
|
</div>
|
||||||
|
|
||||||
{% if url.sane_js_details_to_print %}
|
{% if url.sane_js_details_to_print %}
|
||||||
<div>
|
<div>
|
||||||
{% if url.sane_js_details_to_print is string %}
|
{% if url.sane_js_details_to_print is string %}
|
||||||
|
|
Loading…
Reference in New Issue