Authentication with wallet

Balych

Active Member
Sep 12, 2015
365
211
113
Dash Address
Xba1ychX7CjgbRrCKE1LjHjT3jLUhcexs5
English translate, original here.

I got an idea, why should server keep passwords and users remember it, when we have such a wonderful thing - blockchain.
User provide public key (address) and confirms ownership of it by sign random string obtained from server, and server can validate session by verifying signed string.

Here some example, demo available at https://auth.dashnetwork.info/

Enter your DASH-address (actually it can be any other coin, which support signing/verifying messages):



Server generate random string (need some work of it randomness...) and ask user to sign it:



It would be nice to see something like BIP-0021, but for messaging.

So, sign message with dash-cli or Dash Core:



Paste signature and enjoy success login:



Source:

PHP:
<?php
session_start();
require_once('easydash.php');

if ($_POST['login']) {
    $_SESSION['login'] = filter_input(INPUT_POST, 'login', FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => '/^[X][a-km-zA-HJ-NP-Z1-9]{25,34}$/')));
    if ($_SESSION['login'] == true) {
        $_SESSION['message'] = sha1(crypt(time().inet_pton($_SERVER['REMOTE_ADDR']).$_SESSION['login']));
        echo '
            Sign this message:<br /><br />
            <input type="text" id="message" value="'.$_SESSION['message'].'" readonly /><br /><br />
            <input type="text" name="signature" id="signature" placeholder="Input signature"  ><br /><br />
            <input type="submit" value="Login" />';
    }
}

if ($_POST['signature']) {
    $_SESSION['signature'] = filter_input(INPUT_POST, 'signature', FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => '/[a-zA-Z0-9=\/+]{88}/')));
    $dash = new \elbereth\EasyDash('rpc_username','rpc_password');
    $_SESSION['auth'] = $dash->verifymessage($_SESSION['login'],$_SESSION['signature'],$_SESSION['message']);
}

if ($_POST['logout']) {
    $_SESSION = array();
    session_destroy();
}

function is_auth() {
    if ($_SESSION['auth'] == true) {
        echo '
            Hello, '.$_SESSION['login'].'!<br /><br /><input type="hidden" name="logout" value="1"><input type="submit" value="Logout" />';
    } else if (!$_POST['login'] || ($_SESSION['login']==false && $_POST['login'])){
        echo '
            Hello, guest!<br /><br />
                <input type="text" name="login" id="login" placeholder="Input your DASH address" /><br /><br />
                <input type="submit" value="Login" />';
        $_SESSION = array();
        session_destroy();
    }
}

is_auth();
?>

HTML:
<!DOCTYPE html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Dash Network Info</title>
<style type="text/css">
body {
    margin: 0;
    padding: 0;
}
html, body, #wrapper { height: 100%; }
#wrapper {
    width: 100%;
    display:table;
}
#main_cell, #link_cell {
    display: table-cell;
    vertical-align: middle;
    text-align: center;
}
#main_cell { height: 95%; }
#link_cell { height: 5%; }
body * {
    font-family: Verdana;
    font-size: 3vmin;
    font-size: 3vm;
}
input {
    min-width: 70vmin;
    min-width: 70vm;
    text-align: center;
}
#login, #signature, #message {
    outline: none;
    border: 0;
    border-bottom: #ccc 1px solid;
}
.row { display: table-row; }
a { text-decoration:none; }
a:link, a:visited { color: #1c75bc; }
a:hover, a:active { color: #ec2227; }
</style>
<script src="jquery.min.js"></script>
<script>
$(function() {
    auth();
    $("#auth_form").submit(function() {
        auth();
        return false;
    })
})
function auth() {
    $.ajax({
        url: "auth.php",
        type: "post",
        dataType: "html",
        data: $("#auth_form").serialize(),
        success: function(data) {
            $('#auth_div').html(data);
        },
        error: function() {
            $('#auth_div').html('Authentication not available');
        }
    })
}
</script>
</head>
<body>
<div id="wrapper">
    <div class="row">
        <div id="main_cell">
            <form action="" method="POST" id="auth_form">
                <div id="auth_div">
               
                </div>
            </form>
        </div>
    </div>
    <div class="row">
        <div id="link_cell">
            <a id="link" href="https://www.dash.org">www.dash.org</a>
        </div>
    </div>
</div>
</body>
</html>

3rd-party script easydash.php is used to verify the signature, but can be achieved with dash-cli. Also it requires JQuery.

Not sure about regex accuracy..

Of course it's not complete solution, but may be useful to someone for further idea development. As 2FA element, for example.
 

Balych

Active Member
Sep 12, 2015
365
211
113
Dash Address
Xba1ychX7CjgbRrCKE1LjHjT3jLUhcexs5
Added possibility to authenticate with BTC-address. Server-side verifying with Electrum wallet instead of Bitcoin Core for HDD space economy.

PHP:
<?php
session_start();
require_once('easydash.php');

if ($_POST['login']) {
    $_SESSION['login'] = filter_input(INPUT_POST, 'login', FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => '/^[X][a-km-zA-HJ-NP-Z1-9]{25,34}$/')));
    $_SESSION['coin'] = 'dash';
    if ($_SESSION['login'] == false) {
        $_SESSION['login'] = filter_input(INPUT_POST, 'login', FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => '/^[13][a-km-zA-HJ-NP-Z1-9]{25,34}$/')));
        $_SESSION['coin'] = 'btc';
    }
    if ($_SESSION['login'] == true) {
        $_SESSION['message'] = sha1(crypt(time().inet_pton($_SERVER['REMOTE_ADDR']).$_SESSION['login']));
        echo '
            Sign this message:<br /><br />
            <input type="text" id="message" value="'.$_SESSION['message'].'" readonly /><br /><br />
            <input type="text" name="signature" id="signature" placeholder="Input signature"  ><br /><br />
            <input type="submit" value="Login" />';
    }
}

if ($_POST['signature']) {
    $_SESSION['signature'] = filter_input(INPUT_POST, 'signature', FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => '/[a-zA-Z0-9=\/+]{88}/')));
    switch ($_SESSION['coin']) {
        case 'btc':
            $curl = curl_init();
            curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
            curl_setopt($curl, CURLOPT_POST, 1);
            curl_setopt($curl, CURLOPT_URL, 'http://127.0.0.1:7777');
            $data = '{"id":"curltext","method":"verifymessage","params":["'.$_SESSION['login'].'","'.$_SESSION['signature'].'","'.$_SESSION['message'].'"]}';
            curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
            $result = json_decode(curl_exec($curl), true);
            $_SESSION['auth'] = $result['result'];
            break;
        case 'dash':
            $dash = new \elbereth\EasyDash('rpc_user','rpc_password');
            $_SESSION['auth'] = $dash->verifymessage($_SESSION['login'],$_SESSION['signature'],$_SESSION['message']);
            break;
    }
}

if ($_POST['logout']) {
    $_SESSION = array();
    session_destroy();
}

function is_auth() {
    if ($_SESSION['auth'] == true) {
        echo '
            Hello, '.$_SESSION['login'].'!<br /><br /><input type="hidden" name="logout" value="1"><input type="submit" value="Logout" />';
    } else if (!$_POST['login'] || ($_SESSION['login']==false && $_POST['login'])){
        echo '
            Hello, guest!<br /><br />
                <input type="text" name="login" id="login" placeholder="Input your BTC or DASH address" /><br /><br />
                <input type="submit" value="Login" />';
        $_SESSION = array();
        session_destroy();
    }
}

is_auth();
?>
 
Last edited: