Updated Bulma CSS. Remastered whole GUI.

This commit is contained in:
Revertron
2021-03-24 19:06:22 +01:00
parent 1225bf6fbc
commit ffd03aa62e
7 changed files with 2118 additions and 1505 deletions
+2 -4
View File
@@ -28,13 +28,11 @@ num-bigint = "0.4.0"
num-traits = "0.2.14"
chrono = { version = "0.4.13", features = ["serde"] }
rand = "0.8.3"
# For ed25519-dalek
rand-old = { package = "rand", version = "0.7.0" }
rand-old = { package = "rand", version = "0.7.0" } # For ed25519-dalek
sqlite = "0.25.3"
uuid = { version = "0.8.2", features = ["serde", "v4"] }
mio = { version = "0.7.10", features = ["os-poll", "net"] }
# for DNS from hermes
derive_more = "0.99.9"
derive_more = "0.99.9" # for DNS from hermes
# Optional dependencies regulated by features
web-view = { version = "0.7.3", features = [], optional = true }
+1
View File
@@ -8,6 +8,7 @@ pub enum BlockQuality {
Fork,
}
#[derive(Debug)]
pub enum MineResult {
Fine,
WrongName,
+8 -7
View File
@@ -26,6 +26,7 @@ use alfis::blockchain::enums::MineResult;
pub fn run_interface(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>) {
let file_content = include_str!("webview/index.html");
let mut styles = inline_style(include_str!("webview/bulma.css"));
styles.push_str(&inline_style(include_str!("webview/styles.css")));
styles.push_str(&inline_style(include_str!("webview/busy_indicator.css")));
let scripts = inline_script(include_str!("webview/scripts.js"));
@@ -35,7 +36,7 @@ pub fn run_interface(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>) {
.title(&title)
.content(html)
.size(1023, 720)
.min_size(895, 350)
.min_size(773, 350)
.resizable(true)
.debug(false)
.user_data(())
@@ -48,7 +49,7 @@ pub fn run_interface(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>) {
SaveKey => { action_save_key(&context); }
CheckRecord { data } => { action_check_record(web_view, data); }
CheckDomain { name } => { action_check_domain(&context, web_view, name); }
MineDomain { name, records, .. } => {
MineDomain { name, records } => {
action_create_domain(Arc::clone(&context), Arc::clone(&miner), web_view, name, &records);
}
TransferDomain { .. } => {}
@@ -252,7 +253,7 @@ fn action_create_domain(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>,
}
let keystore = context.get_keystore().unwrap();
let pub_key = keystore.get_public();
match context.chain.can_mine_domain(&name, &records, &pub_key) {
match dbg!(context.chain.can_mine_domain(&name, &records, &pub_key)) {
MineResult::Fine => {
let zone = get_domain_zone(&name);
let difficulty = context.chain.get_zone_difficulty(&zone);
@@ -261,7 +262,7 @@ fn action_create_domain(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>,
let data = serde_json::to_string(&data).unwrap();
std::mem::drop(context);
create_domain(c, miner, &name, &data, difficulty, &keystore);
let _ = web_view.eval("domainMiningStarted()");
let _ = web_view.eval("domainMiningStarted();");
}
}
MineResult::WrongName => { show_warning(web_view, "You can't mine this domain!"); }
@@ -313,7 +314,8 @@ fn action_create_zone(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>, we
}
fn show_warning(web_view: &mut WebView<()>, text: &str) {
match web_view.eval(&format!("showWarning('{}');", text)) {
let str = text.replace('\'', "\\'");
match web_view.eval(&format!("showWarning('{}');", &str)) {
Ok(_) => {}
Err(_) => { warn!("Error showing warning!"); }
}
@@ -326,7 +328,6 @@ fn create_domain(context: Arc<Mutex<Context>>, miner: Arc<Mutex<Miner>>, name: &
error!("Unable to mine IANA/OpenNIC/etc zone {}!", &name);
return;
}
//let tags_vector: Vec<String> = tags.into().trim().split(",").map(|s| s.trim()).map(String::from).collect();
let transaction = Transaction::from_str(name, "dns".to_owned(), data.to_owned(), keystore.get_public().clone());
let block = Block::new(Some(transaction), keystore.get_public(), Bytes::default(), difficulty);
miner.lock().unwrap().add_block(block, keystore.clone());
@@ -343,7 +344,7 @@ pub enum Cmd {
MineZone { name: String, data: String },
CheckRecord { data: String },
CheckDomain { name: String },
MineDomain { name: String, records: String, tags: String },
MineDomain { name: String, records: String },
TransferDomain { name: String, owner: String },
StopMining,
}
+1980 -1214
View File
File diff suppressed because it is too large Load Diff
+88 -221
View File
@@ -1,5 +1,5 @@
<!DOCTYPE html>
<html>
<html class="is-clipped">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
@@ -10,6 +10,91 @@
</head>
<body onload="onLoad();">
<div class="container">
<!-- Credentials (Key management) -->
<div class="content">
<label class="label">Credentials</label>
<div class="field is-grouped">
<div class="control is-expanded has-icons-left">
<input class="input is-expanded" type="text" id="public_key_hash" placeholder="No key loaded" readonly>
<span class="icon is-small is-left">
<i class="fas fa-lock"></i>
</span>
</div>
<div class="buttons has-addons">
<button class="button is-info is-light" onclick="loadKey();">Load key</button>
<button class="button is-info is-light" id="save_key" onclick="saveKey();" disabled>Save key</button>
<button class="button is-info" onclick="createKey();">Mine new key</button>
</div>
</div>
<p class="help">To mine domains (or zones) you need to mine a strong pair of keys.</p>
</div>
<!-- Domain mining -->
<div class="content">
<label class="label">Mine domain name</label>
<div class="field is-grouped">
<div class="control is-expanded has-icons-left">
<input class="input is-expanded" type="text" placeholder="example.tld" id="new_domain" oninput="onDomainChange(this)">
<span class="icon is-small is-left">
<i class="fas fa-globe"></i>
</span>
</div>
<div class="buttons has-addons">
<button id="add_record_button" class="button is-info is-light" onclick="showNewRecordDialog();">Add record</button>
<button id="new_domain_button" class="button is-info" onclick="createDomain();">Mine domain</button>
</div>
</div>
<p class="help">Enter domain name, add some DNS-records, then hit the "Mine domain" button!</p>
<div id="domain_records">
<!-- Here will be our domain records, added by dialog -->
</div>
</div>
<!-- Zone mining -->
<div class="content">
<label class="label">Mine new zone</label>
<div class="field is-grouped">
<div class="control is-expanded has-icons-left">
<input class="input" type="text" placeholder="ygg" id="new_zone" oninput="onZoneChange()">
<span class="icon is-small is-left">
<i class="fas fa-map"></i>
</span>
</div>
<div class="control has-icons-left">
<input class="input" type="number" placeholder="Difficulty: 20-28" id="new_zone_difficulty" name="Just a name" oninput="onZoneChange()">
<span class="icon is-small is-left">
<i class="fas fa-fire"></i>
</span>
</div>
<div class="buttons has-addons">
<button class="button is-info" id="new_zone_button" onclick="createZone();">Mine zone</button>
</div>
</div>
<p class="help">If you feel that we need another zone you can mine that too. Just select a name, a difficulty for domains in that zone, and hit "Mine zone".</p>
</div>
<!-- Help -->
<div class="content center is-hidden" id="main">
<h1>Welcome to ALFIS!</h1>
<p>ALFIS stands for Alternative Free Identity System.</p>
<p>It gives you an opportunity to create your own domains and use them in decentralized networks, store security certificates for browsers to trust without any centralized CA.</p>
<h2>How this system works?</h2>
<h3>If you just want to be able to resolve our domains</h3>
<p>Carefully configure DNS section in <strong>alfis.toml</strong> and start ALFIS with <code>-n</code> command line switch.
It will start without GUI, but will work as local DNS-resolver.</p>
<h3>If you want to get your own domain</h3>
<ul>
<li>Generate a keypair in "Manage keys" part (you need just one for any number of domains)</li>
<li>Check available zones (for now we have a test zone <code>.yy</code>). In future version a list of available zones will be somewhere here</li>
<li>Go to "Mine domain" part and enter desired domain in first field, if it is not red - you can create it</li>
<li>Carefully add needed DNS-records (you can add them later, but you will need to mine it again)</li>
<li>Just click on "Mine domain" and wait for it, your domain (when properly cooked) will propagate to all blockchain nodes automatically</li>
</ul>
</div>
</div>
<div id="modal_dialog" class="modal">
<div class="modal-background"></div>
<div class="modal-content">
@@ -38,7 +123,7 @@
</div>
</div>
<div class="column is-narrow">
<div class="field">
<div class="control">
<label class="label">Type</label>
<div class="select">
<select id="record_type">
@@ -98,7 +183,7 @@
</div>
<br/>
<div class="buttons is-grouped is-centered">
<button class="button is-primary" id="new_record_positive_button">Ok</button>
<button class="button is-info" id="new_record_positive_button">Add</button>
<button class="button is-link is-light" id="new_record_negative_button">Cancel</button>
</div>
</div>
@@ -110,224 +195,6 @@
<p id="warning_text"></p>
</div>
<div class="container">
<div class="columns is-mobile">
<div class="column is-one-fifth">
<div class="menu">
<ul class="menu-list">
<li><a class="is-active" onclick="openTab(this, 'main')">Main</a></li>
</ul>
<p class="menu-label">Key management</p>
<ul class="menu-list">
<li><a onclick="openTab(this, 'key_load')">Manage keys</a></li>
</ul>
<p class="menu-label">Domain management</p>
<ul class="menu-list">
<li><a onclick="openTab(this, 'dom_new')">Mine domain</a></li>
<li><a onclick="openTab(this, 'zone_new')">Mine zone</a></li>
<!--<li><a onclick="openTab(this, 'dom_edit')">Manage domain</a></li>
<li><a onclick="openTab(this, 'dom_renew')">Renew domain</a></li>
<li><a onclick="openTab(this, 'dom_transfer')">Transfer domain</a></li>-->
</ul>
</div>
</div><!--column-->
<div class="column auto">
<div class="content center" id="main">
<h1>Welcome to ALFIS!</h1>
<p>ALFIS stands for Alternative Free Identity System.</p>
<p>It gives you an opportunity to create your own domains and use them in decentralized networks, store security certificates for browsers to trust without any centralized CA.</p>
<h2>How this system works?</h2>
<h3>If you just want to be able to resolve our domains</h3>
<p>Carefully configure DNS section in <strong>alfis.toml</strong> and start ALFIS with <code>-n</code> command line switch.
It will start without GUI, but will work as local DNS-resolver.</p>
<h3>If you want to get your own domain</h3>
<ul>
<li>Generate a keypair in "Manage keys" part (you need just one for any number of domains)</li>
<li>Check available zones (for now we have a test zone <code>.yy</code>). In future version a list of available zones will be somewhere here</li>
<li>Go to "Mine domain" part and enter desired domain in first field, if it is not red - you can create it</li>
<li>Carefully add needed DNS-records (you can add them later, but you will need to mine it again)</li>
<li>Just click on "Mine domain" and wait for it, your domain (when properly cooked) will propagate to all blockchain nodes automatically</li>
</ul>
</div>
<div class="content is-hidden" id="key_load">
<div class="field">
<label class="label">Key path</label>
<p id="key_file_name">Not loaded</p>
</div>
<div class="field">
<label class="label">Public key</label>
<p id="key_public_key">Not loaded</p>
</div>
<div class="field">
<label class="label">Public key hash</label>
<p id="key_public_hash">Not loaded</p>
</div>
<br>
<div class="field is-grouped">
<div class="control">
<button class="button is-warning" onclick="createKey();">Mine new key</button>
</div>
<div class="control">
<button class="button is-light" onclick="loadKey();">Load key</button>
</div>
<div class="control">
<button id="save_key" class="button is-light" onclick="saveKey();" disabled>Save key</button>
</div>
</div>
</div>
<div class="content is-hidden" id="dom_new">
<div class="columns">
<div class="column">
<div class="field">
<label class="label">Domain name</label>
<div class="control">
<input class="input" type="text" placeholder="example.ygg" id="new_domain" oninput="onDomainChange(this)" disabled>
</div>
</div>
</div>
<div class="column">
<div class="field">
<label class="label">Domain tags (will be used for search)</label>
<div class="control">
<input class="input" type="text" placeholder="blog, community, friendship" id="new_domain_tags" disabled>
</div>
</div>
</div>
</div>
<div class="block" id="domain_records">
<!-- Here will be our domain records, added by dialog -->
</div>
<div class="field is-grouped">
<div class="control">
<button id="new_domain_button" class="button is-warning" onclick="createDomain();" disabled>Mine domain</button>
</div>
<div class="control">
<button id="add_record_button" class="button is-light" onclick="showNewRecordDialog();" disabled>Add record</button>
</div>
</div>
</div>
<div class="content is-hidden" id="zone_new">
<div class="columns">
<div class="column">
<div class="field">
<label class="label">Zone name</label>
<div class="control">
<input class="input" type="text" placeholder="ygg" id="new_zone" oninput="onZoneChange()" disabled>
</div>
</div>
</div>
<div class="column">
<div class="field">
<label class="label">Difficulty (for all domains in zone)</label>
<div class="control">
<input class="input" type="number" placeholder="20" id="new_zone_difficulty" oninput="onZoneChange()" disabled>
</div>
</div>
</div>
</div>
<div class="field is-grouped">
<div class="control">
<button class="button is-warning" id="new_zone_button" onclick="createZone();" disabled>Mine zone</button>
</div>
</div>
</div>
<div class="content is-hidden" id="dom_edit">
<div class="field">
<label class="label">Your existing domain name</label>
<div class="control">
<input class="input" type="text" placeholder="example.ygg" id="change_domain">
</div>
</div>
<div class="field">
<label class="label">All new domain records</label>
<div class="control">
<textarea class="textarea" placeholder="@ IN AAAA 200:1111:2222:3333:4444:5555:6666:7777" id="change_domain_records"></textarea>
</div>
</div>
<div class="field">
<label class="label">Domain tags (will be used for search)</label>
<div class="control">
<input class="input" type="text" placeholder="blog, community, friendship" id="change_domain_tags">
</div>
</div>
<div class="field is-grouped">
<div class="control">
<button class="button is-link" onclick="changeDomain();">Replace records</button>
</div>
</div>
</div>
<div class="content is-hidden" id="dom_renew">
<div class="field">
<label class="label">Your existing domain name</label>
<div class="control">
<input class="input" type="text" placeholder="example.ygg" id="renew_domain">
</div>
</div>
<div class="field">
<label class="label">Days to add</label>
<div class="control">
<input class="input" type="text" placeholder="365" value="365" id="renew_domain_extend_days" disabled>
</div>
</div>
<div class="field is-grouped">
<div class="control">
<button class="button is-link" onclick="renewDomain();">Renew domain</button>
</div>
</div>
</div>
<div class="content is-hidden" id="dom_transfer">
<div class="field">
<label class="label">Your existing domain name</label>
<div class="control">
<input class="input" type="text" placeholder="example.ygg" id="transfer_domain">
</div>
</div>
<div class="field">
<label class="label">Public key of new owner</label>
<div class="control">
<input class="input" type="text" placeholder="3764ef954577a1815db3cc65aa3e2b18a52f12a3f6fcbd6a10d9ce8d06741ddd" id="transfer_domain_transfer_owner">
</div>
</div>
<div class="field is-grouped">
<div class="control">
<button class="button is-link" onclick="transferDomain();">Transfer domain</button>
</div>
</div>
</div>
</div>
</div> <!-- columns -->
</div>
<div class="footer is-family-code">
<div class="level">
<div class="level-left">
+19 -59
View File
@@ -34,14 +34,20 @@ function refresh_records_list() {
data = value.priority + " " + value.weight + " " + value.port + " " + value.host;
}
buf += "<div class=\"columns\">\n";
buf += "<div class=\"column\">" + getInput(value.domain) + "</div>\n";
buf += "<div class=\"column is-2\">" + getInput(value.type) + "</div>\n";
buf += "<div class=\"column is-2\">" + getInput(value.ttl) + "</div>\n";
buf += "<div class=\"column\">" + getInput(data) + "</div>\n";
buf += "<div class=\"column is-1 align-right\">\n<button class=\"button is-danger is-outlined\" id=\"record_delete\" onclick=\"delRecord(" + index + ");\">";
buf += "<span class=\"icon is-small\"><i class=\"fas fa-times\"></i></span></button></div>\n";
buf += "</div>";
var text = "<div class=\"field is-grouped\">" +
"<input class=\"input\" type=\"text\" value=\"{1}\" readonly>" +
"<input class=\"input ml-3 has-text-centered\" type=\"text\" size=\"6\" style=\"width: 15%;\" value=\"{2}\" readonly>" +
"<input class=\"input ml-3 has-text-centered\" type=\"text\" size=\"6\" style=\"width: 15%;\" value=\"{3}\" readonly>" +
"<input class=\"input ml-3\" type=\"text\" value=\"{4}\" readonly>" +
"<button class=\"button is-danger is-outlined ml-3\" id=\"record_delete\" onclick=\"delRecord({5});\">" +
" <span class=\"icon is-small\"><i class=\"fas fa-times\"></i></span>" +
"</button>" +
"</div>";
buf += text.replace("{1}", value.domain)
.replace("{2}", value.type)
.replace("{3}", value.ttl)
.replace("{4}", data)
.replace("{5}", index);
}
recordsBuffer.forEach(makeRecord);
@@ -90,28 +96,6 @@ function onLoad() {
external.invoke(JSON.stringify({cmd: 'loaded'}));
}
function openTab(element, tabName) {
// Declare all variables
var i, tabContent, tabLinks;
// Get all elements with class="content" and hide them
tabContent = document.getElementsByClassName("content");
for (i = 0; i < tabContent.length; i++) {
tabContent[i].className = "content is-hidden";
}
// Get all elements with class="tablinks" and remove the class "active"
tabLinks = document.getElementsByClassName("is-active");
for (i = 0; i < tabLinks.length; i++) {
tabLinks[i].className = "";
}
// Show the current tab, and add an "active" class to the button that opened the tab
document.getElementById(tabName).className = "content";
element.className = "is-active";
refresh_records_list();
}
function loadKey() {
external.invoke(JSON.stringify({cmd: 'loadKey'}));
}
@@ -141,8 +125,7 @@ function recordOkay(okay) {
function createDomain() {
new_domain = document.getElementById("new_domain").value.toLowerCase();
new_dom_records = JSON.stringify(recordsBuffer);
new_dom_tags = document.getElementById("new_domain_tags").value;
external.invoke(JSON.stringify({cmd: 'mineDomain', name: new_domain, records: new_dom_records, tags: new_dom_tags}));
external.invoke(JSON.stringify({cmd: 'mineDomain', name: new_domain, records: new_dom_records}));
}
function domainMiningStarted() {
@@ -159,25 +142,6 @@ function createZone() {
external.invoke(JSON.stringify({cmd: 'mineZone', name: new_zone, data: data}));
}
/*function changeDomain() {
domain = document.getElementById("change_domain").value;
dom_records = document.getElementById("change_domain_records").value;
dom_tags = document.getElementById("change_domain_records").value;
external.invoke(JSON.stringify({cmd: 'changeDomain', name: domain, records: dom_records, tags: dom_tags}));
}
function renewDomain() {
domain = document.getElementById("renew_domain").value;
days = document.getElementById("renew_domain_extend_days").value;
external.invoke(JSON.stringify({cmd: 'renewDomain', name: domain, days: days}));
}
function transferDomain() {
domain = document.getElementById("transfer_domain").value;
new_owner = document.getElementById("transfer_domain_transfer_owner").value;
external.invoke(JSON.stringify({cmd: 'transferDomain', name: domain, owner: new_owner}));
}*/
function sendAction(param) {
external.invoke(JSON.stringify(param));
}
@@ -306,19 +270,15 @@ function keystoreChanged(path, pub_key, hash) {
if (path == '') {
path = "In memory";
}
var key_file_name = document.getElementById("key_file_name");
key_file_name.innerHTML = path;
var key_public_key = document.getElementById("key_public_key");
key_public_key.innerHTML = pub_key;
var key_public_hash = document.getElementById("key_public_hash");
key_public_hash.innerHTML = hash;
var public_key_hash = document.getElementById("public_key_hash");
public_key_hash.value = hash;
var save_key = document.getElementById("save_key");
save_key.disabled = false;
var new_domain = document.getElementById("new_domain");
new_domain.disabled = false;
var new_domain_tags = document.getElementById("new_domain_tags");
new_domain_tags.disabled = false;
var new_zone = document.getElementById("new_zone");
new_zone.disabled = false;
var new_zone_difficulty = document.getElementById("new_zone_difficulty");
+20
View File
@@ -0,0 +1,20 @@
.container {
margin: 10pt;
}
.notification {
position: absolute;
z-index: 100;
width: 50%;
top: 10pt;
right: 10pt;
}
.footer {
background-color: #f4f4f4;
padding: 0.2rem 0.5rem 0.2rem 0.5rem;
width: 100%;
position: absolute;
bottom: 0px;
z-index: 9;
}