Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/svg/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
RSA的JavaScript加密和php-openssl解密_Javascript_Php - Fatal编程技术网

RSA的JavaScript加密和php-openssl解密

RSA的JavaScript加密和php-openssl解密,javascript,php,Javascript,Php,我正在做一个登录系统。 我希望客户机(使用他的私钥)对来自服务器的随机消息进行加密,并将结果发送到服务器。然后,服务器将用公钥破译消息并进行比较 我试过jsencrypt。我有一个密码结果,但我不能使用openssl_public_decrypt进行解密,但它不起作用 请提供建议或帮助 下面是javascript加密完成的文件 <?php //Génération d'un message aleatoires $i = 4; global $bytes; $bytes = opens

我正在做一个登录系统。 我希望客户机(使用他的私钥)对来自服务器的随机消息进行加密,并将结果发送到服务器。然后,服务器将用公钥破译消息并进行比较


我试过jsencrypt。我有一个密码结果,但我不能使用openssl_public_decrypt进行解密,但它不起作用

请提供建议或帮助

下面是javascript加密完成的文件

<?php


//Génération d'un message aleatoires
$i = 4;
global $bytes;
$bytes = openssl_random_pseudo_bytes($i, $cstrong);
$hex = pack('H*', bin2hex($bytes));;
$username = $_POST["username"];
$password = $_POST["password"];


echo '<!DOCTYPE html>
<html>
<head>
    <title>Accueil</title>
    <script language="javascript">
    function controle(form1, n) {
        if(n == 0){
            var pub = document.form1.clepub.value;
            var fso = new ActiveXObject("Scripting.FileSystemObject");
            // 2=overwrite, true=create if not exist, 0 = ASCII
            var varFileObject = fso.OpenTextFile(pub, 1, false, 0);
            //varFileObject.write("File handling in Javascript");
            var s = varFileObject.ReadAll();
            varFileObject.close();
            return s;
        }
        else{
            var priv = document.form1.clepriv.value;
            var fso = new ActiveXObject("Scripting.FileSystemObject");
            // 2=overwrite, true=create if not exist, 0 = ASCII
            var varFileObject = fso.OpenTextFile(priv, 1, false, 0);
            //varFileObject.write("File handling in Javascript");
            var s = varFileObject.ReadAll();
            varFileObject.close();
            return s;
        }
        //alert("La clé privée est : " + s);
    }
</script>
<script src="jquery-1.12.1.min.js"></script>
<script src="jsencrypt-master/bin/jsencrypt.js"></script>
<script language="javascript">
  function chiffrer()  {
        document.getElementById("testme").style.visibility="hidden";
      // Encrypt with the public key...
      var encrypt = new JSEncrypt();
      encrypt.setPublicKey(controle(form1, 1));
      //alert(controle(form1, 1));
      var encrypted = encrypt.encrypt("'.$hex.'");

      document.getElementById("submit").style.visibility="visible";

      document.getElementById("input").value = encrypted;
      //alert(encrypted);
      //document.getElementById("input").value = encryptedb64tohex(encrypted);
  }
</script>';
echo '</head>
<body>
<h1>Bienvenue sur TelGov</h1>
<h2>Engager votre clef privee</h2>
<form  action="compare.php" method="POST" name = "form1">
    <!--<label for="clepub">Engager votre clef publique</label>
    <input name="clepub" id="clepub" type="file"></input>
    <label for="clepriv">Engager votre clef privee</label>-->
    <input name="clepriv" id="clepriv" type="file"></input>
    <br/><br/>
    <input name="hash" id="hash" type="hidden" value="'.$hex.'"></input>
    <br/><br/>
    <input id="input" name="input" type="hidden" ></input><br/>
    <input id="testme" type="button" value="Engager" onclick="chiffrer()" /><br/>
    <input type="hidden" name="username" value="'.$username.'">
    <input type="hidden" name="password" value="'.$password.'">
    <!--<br/><br/>
    <input type="button" name="bouton" value="Controler" onClick="controle(form1)">
    <br/><br/>-->
    <input type="submit" id = "submit" value="Se connecter" style="visibility: hidden;"</input>
</form>
</body>

</html>';

我正在使用Jsencrypt库。
我发现用Jsencrypt用私钥加密,用php openssl用公钥解密是不可能的。

所以我改变了我的方法,我使用了带有公钥的JSAN加密和php openssl解密。这项工作做得很好

我找到了这个jsencrypt库(),经过两天的尝试,我得到了我的解决方案

我遇到的唯一问题是当我发送一条长文本时。这是因为根据定义,RSA支持长度有限的字符串

PKCS#1定义的RSA加密有限大小的“消息”。具有 常用的“v1.5填充”和2048位RSA密钥,最大 可以使用RSA加密的数据大小为245字节。没有了

i、 e。 如果我使用1024的私钥位,我可以发送

"José compró en Perú una vieja zampoña. Excusándose, Sofía tiró su whisky al desagüe de la banqueta."
没有了。 如果我使用512的私钥位,我可以发送

"José compró en Perú una vieja zampoña. Excusánd"
没有了

关于长字符串JavaScript控制台报告:“消息对RSA来说太长”

然后,如果你想加密长字符串,你必须在javascript加密之前和解密之后压缩和拆分它们,在php上连接和解压缩,我认为zlib是一个很好的拆分/连接解决方案,因为它在javascript和php上受支持

我的工作代码如下:

<?php
    //------------------------------------------------------------
    // Global Settings.
    //------------------------------------------------------------
    ini_set('display_errors', 1);
    error_reporting(E_ALL);
    $directorio = "/path/to/key/directory/apache/writable/";
    $nombre_base = "llaves_php";

    //------------------------------------------------------------
    // Initialization.
    //------------------------------------------------------------
    $encabezado_html = "";
    $cuerpo_html = "";

    //------------------------------------------------------------
    // Loading keys
    //------------------------------------------------------------
    list($privateKey, $pubKey) =
        cargar_llaves_RSA($directorio, $nombre_base);

    //------------------------------------------------------------
    // Form that uses javascript to encrypt data.
    // (it uses only the public key)
    //------------------------------------------------------------
    $librerias_html = "
        <script type='text/javascript'
                src='https://ajax.googleapis.com/ajax/libs/".
                    "jquery/3.2.1/jquery.min.js'></script>
        <script type='text/javascript'
                src='lib/jsencrypt.js'></script>
        ";

    $pubKey_html = htmlentities($pubKey);
    $datos_html = "
        <h2>Cifrando con Javascript</h2>
        <input type='text' id='mensaje' />
        <br />
        <button id='ENVIAR'>Enviar</button>
        <br />
        <textarea id='pubkey' style='display: none;'>".
        $pubKey_html.
        "</textarea>
        <script type='text/javascript'>
            $('#ENVIAR').click(function () {
                var codificador = new JSEncrypt();
                codificador.setKey($('#pubkey').val());
                var cifrado = codificador.encrypt($('#mensaje').val());
                window.open('?mensaje=' + encodeURIComponent(cifrado)
                           , '_top');
            });
        </script>
        ";

    //------------------------------------------------------------
    // Decrypting using php (it uses only the privateKey)
    //------------------------------------------------------------
    if (isset($_REQUEST['mensaje'])) {
        openssl_private_decrypt( base64_decode($_REQUEST['mensaje'])
                               , $descifrado
                               , $privateKey);
        $datos_html.= "
            <h2>Descifrando con PHP</h2>
            ".$descifrado."
            ";
    }

    //------------------------------------------------------------
    // HTML DISPLAY
    //------------------------------------------------------------
    $encabezado_html.= "<title>Receptor de mensaje cifrado</title>"
                     . $librerias_html;

    $cuerpo_html.= $datos_html;

    $contenido = "<head>$encabezado_html</head><body>$cuerpo_html</body>";
    $contenido = "<html>$contenido</html>";
    print $contenido;

//============================================================
//============================================================
// Functions
//============================================================
//============================================================

    //------------------------------------------------------------
    function cargar_llaves_RSA($directorio, $nombre_base) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO: Genera o carga desde archivos las llaves RSA
    // ENTRADAS:
    // $directorio: Directorio donde se encuentran los archivos.
    // $nombre_base: Nombre, sin extensión, de los archivos con
    //               las llaves.
    // SALIDAS:
    //------------------------------------------------------------
        if (  !file_exists($directorio.$nombre_base.".crt")
           || !file_exists($directorio.$nombre_base.".pub")) {
            list($privateKey, $pubKey) = crear_llaves_RSA($directorio.$nombre_base);
        } else {
            //------------------------------------------------------------
            // CARGA DE LLAVES RSA ARCHIVADAS
            //------------------------------------------------------------
            $privateKey = file_get_contents($directorio.$nombre_base.".crt");
        if (!$privKey = openssl_pkey_get_private($privateKey))
            die('Loading Private Key failed');
            $pubKey  = file_get_contents($directorio.$nombre_base.".pub");
        }

    return array($privateKey, $pubKey);
    }

    //------------------------------------------------------------
    function crear_llaves_RSA($ruta_base) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO:
    // generacion de llaves RSA en php
    // ENTRADAS:
    // $ruta_base: Ruta de los archivos a generar sin extensión.
    // SALIDAS:
    // Se generarán dos archivos, uno con la llave privada con
    // extensión .crt, el otro con llave pública con extensión
    // .pub; la función retorna tanto la llave pública como la
    // privada en un arreglo.
    //------------------------------------------------------------
        $config = array(
            "private_key_bits" => 1024,
            "private_key_type" => OPENSSL_KEYTYPE_RSA,
        );

        $llavePrivadaCruda = openssl_pkey_new($config);
        openssl_pkey_export_to_file($llavePrivadaCruda, $ruta_base.".crt");
        $privateKey = file_get_contents($ruta_base.".crt");
        openssl_pkey_export($llavePrivadaCruda, $privKey);

        $pubKeyData = openssl_pkey_get_details($llavePrivadaCruda);
        $pubKey = $pubKeyData["key"];
        file_put_contents($ruta_base.".pub", $pubKey);
        openssl_free_key($llavePrivadaCruda);

    return array($privateKey, $pubKey);
    }

    //------------------------------------------------------------
    function Mostrar($valor) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO: Genera el código HTML para presentar una
    // variable embebida en la página.
    // ENTRADAS:
    // $valor: el valor a presentar.
    // SALIDAS: código html que permite visualizar la variable.
    //------------------------------------------------------------
        $retorno = htmlentities(stripslashes(var_export($valor, true)));
        $retorno = "<pre>$retorno</pre>";
        return $retorno;
    }

?>
以及一个可由php在公共区域外写入的目录,名为



你的问题是?你能给我一些建议吗?我已经试过了。我有一个密码结果,但我不能使用openssl_public_decrypt来解密,但它不工作什么不工作?向我们展示一个示例。提供您两侧的代码,以及任何错误日志、要加密/解密的数据示例、您使用的密钥、生成的加密数据、生成的解密数据以及任何其他相关详细信息。“它不起作用”就像你告诉你的医生“它疼”而不提供任何进一步的细节一样有用。这不是问题的答案。2.这不是使用RSA发送长消息的方式,RSA不是为此而设计的,或者使用AES等对称加密,或者如果需要密钥对,则使用混合加密,即使用随机密钥对称加密数据,使用RSA加密密钥并将其打包在一起。看见3.请不要试图发明你们自己的密码术,使用经过严格审查的方法。按照设计,加密是用公钥进行的,解密是用私钥进行的。考虑,如果公钥被用于解密,每个人都可以解密该消息,因为公钥不是秘密的。但是,您可能不需要密钥对(通常情况下),只需要一个用于加密和解密的密钥,如果需要,请使用对称加密,如AES,它具有速度、简单性和无限数据长度的优势。
<?php
    //------------------------------------------------------------
    // Global Settings.
    //------------------------------------------------------------
    ini_set('display_errors', 1);
    error_reporting(E_ALL);
    $directorio = "/path/to/key/directory/apache/writable/";
    $nombre_base = "llaves_php";

    //------------------------------------------------------------
    // Initialization.
    //------------------------------------------------------------
    $encabezado_html = "";
    $cuerpo_html = "";

    //------------------------------------------------------------
    // Loading keys
    //------------------------------------------------------------
    list($privateKey, $pubKey) =
        cargar_llaves_RSA($directorio, $nombre_base);

    //------------------------------------------------------------
    // Form that uses javascript to encrypt data.
    // (it uses only the public key)
    //------------------------------------------------------------
    $librerias_html = "
        <script type='text/javascript'
                src='https://ajax.googleapis.com/ajax/libs/".
                    "jquery/3.2.1/jquery.min.js'></script>
        <script type='text/javascript'
                src='lib/jsencrypt.js'></script>
        ";

    $pubKey_html = htmlentities($pubKey);
    $datos_html = "
        <h2>Cifrando con Javascript</h2>
        <input type='text' id='mensaje' />
        <br />
        <button id='ENVIAR'>Enviar</button>
        <br />
        <textarea id='pubkey' style='display: none;'>".
        $pubKey_html.
        "</textarea>
        <script type='text/javascript'>
            $('#ENVIAR').click(function () {
                var codificador = new JSEncrypt();
                codificador.setKey($('#pubkey').val());
                var cifrado = codificador.encrypt($('#mensaje').val());
                window.open('?mensaje=' + encodeURIComponent(cifrado)
                           , '_top');
            });
        </script>
        ";

    //------------------------------------------------------------
    // Decrypting using php (it uses only the privateKey)
    //------------------------------------------------------------
    if (isset($_REQUEST['mensaje'])) {
        openssl_private_decrypt( base64_decode($_REQUEST['mensaje'])
                               , $descifrado
                               , $privateKey);
        $datos_html.= "
            <h2>Descifrando con PHP</h2>
            ".$descifrado."
            ";
    }

    //------------------------------------------------------------
    // HTML DISPLAY
    //------------------------------------------------------------
    $encabezado_html.= "<title>Receptor de mensaje cifrado</title>"
                     . $librerias_html;

    $cuerpo_html.= $datos_html;

    $contenido = "<head>$encabezado_html</head><body>$cuerpo_html</body>";
    $contenido = "<html>$contenido</html>";
    print $contenido;

//============================================================
//============================================================
// Functions
//============================================================
//============================================================

    //------------------------------------------------------------
    function cargar_llaves_RSA($directorio, $nombre_base) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO: Genera o carga desde archivos las llaves RSA
    // ENTRADAS:
    // $directorio: Directorio donde se encuentran los archivos.
    // $nombre_base: Nombre, sin extensión, de los archivos con
    //               las llaves.
    // SALIDAS:
    //------------------------------------------------------------
        if (  !file_exists($directorio.$nombre_base.".crt")
           || !file_exists($directorio.$nombre_base.".pub")) {
            list($privateKey, $pubKey) = crear_llaves_RSA($directorio.$nombre_base);
        } else {
            //------------------------------------------------------------
            // CARGA DE LLAVES RSA ARCHIVADAS
            //------------------------------------------------------------
            $privateKey = file_get_contents($directorio.$nombre_base.".crt");
        if (!$privKey = openssl_pkey_get_private($privateKey))
            die('Loading Private Key failed');
            $pubKey  = file_get_contents($directorio.$nombre_base.".pub");
        }

    return array($privateKey, $pubKey);
    }

    //------------------------------------------------------------
    function crear_llaves_RSA($ruta_base) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO:
    // generacion de llaves RSA en php
    // ENTRADAS:
    // $ruta_base: Ruta de los archivos a generar sin extensión.
    // SALIDAS:
    // Se generarán dos archivos, uno con la llave privada con
    // extensión .crt, el otro con llave pública con extensión
    // .pub; la función retorna tanto la llave pública como la
    // privada en un arreglo.
    //------------------------------------------------------------
        $config = array(
            "private_key_bits" => 1024,
            "private_key_type" => OPENSSL_KEYTYPE_RSA,
        );

        $llavePrivadaCruda = openssl_pkey_new($config);
        openssl_pkey_export_to_file($llavePrivadaCruda, $ruta_base.".crt");
        $privateKey = file_get_contents($ruta_base.".crt");
        openssl_pkey_export($llavePrivadaCruda, $privKey);

        $pubKeyData = openssl_pkey_get_details($llavePrivadaCruda);
        $pubKey = $pubKeyData["key"];
        file_put_contents($ruta_base.".pub", $pubKey);
        openssl_free_key($llavePrivadaCruda);

    return array($privateKey, $pubKey);
    }

    //------------------------------------------------------------
    function Mostrar($valor) {
    //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // PROPÓSITO: Genera el código HTML para presentar una
    // variable embebida en la página.
    // ENTRADAS:
    // $valor: el valor a presentar.
    // SALIDAS: código html que permite visualizar la variable.
    //------------------------------------------------------------
        $retorno = htmlentities(stripslashes(var_export($valor, true)));
        $retorno = "<pre>$retorno</pre>";
        return $retorno;
    }

?>
├── script.php
└── lib
    └── jsencrypt.js
/path/to/key/directory/apache/writable/