jsencrypt icon indicating copy to clipboard operation
jsencrypt copied to clipboard

There seems to be a problem with public key decryption

Open sceneNoLonger opened this issue 6 years ago • 16 comments

I want to use the private key to encrypt the server and the public key to decrypt the browser. However, using the public key to decrypt is problematic.

The chasing code finds that an exception occurs when the public key is decrypted, resulting in the return of false.

PKCS8 format used by my server, key length 2048

sceneNoLonger avatar Apr 23 '19 10:04 sceneNoLonger

Public key is used only for encryption. Private key can decrypt and encrypt both. The idea of RSA is not to be able to decrypt with the public key. The reason is that the public key contains only N and E and the private key have additional D which is a must for decryption.

more info: https://en.wikipedia.org/wiki/RSA_(cryptosystem)

So in conclusion i would say that this effect is by RSA design.

savs90 avatar Apr 26 '19 09:04 savs90

Public key is used only for encryption. Private key can decrypt and encrypt both. The idea of RSA is not to be able to decrypt with the public key. The reason is that the public key contains only N and E and the private key have additional D which is a must for decryption.

more info: https://en.wikipedia.org/wiki/RSA_(cryptosystem)

So in conclusion i would say that this effect is by RSA design.

Thank you. If so, I will use the public key to encrypt on the server and the private key to decrypt in the browser.

Finally, thank you very much.

sceneNoLonger avatar Apr 26 '19 10:04 sceneNoLonger

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

savs90 avatar Apr 26 '19 10:04 savs90

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

Is there a good way to solve this problem, such as providing a public key decryption method?

Because, as you said, then I will not be able to use RSA, if so, my interactive data will become public, obviously not what I want.

Therefore, if we can provide a JS public key decryption, I think it is better, JAVA language can be public key decryption, I think, JS language can also do it.

I've seen a framework provided by Google, named JSRSASIGN, which can decrypt through public key. However, it seems to conflict with JAVA. I can't parse the encrypted text with JAVA. Maybe its API is too powerful. I haven't found the right way. I prefer JSEncrypt because it's lightweight and interacts with JAVA.

The only disadvantage is that public key decryption is not possible. If it can be provided, it would be very good.

sceneNoLonger avatar Apr 28 '19 05:04 sceneNoLonger

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

Is there a good way to solve this problem, such as providing a public key decryption method?

Because, as you said, then I will not be able to use RSA, if so, my interactive data will become public, obviously not what I want.

Therefore, if we can provide a JS public key decryption, I think it is better, JAVA language can be public key decryption, I think, JS language can also do it.

I've seen a framework provided by Google, named JSRSASIGN, which can decrypt through public key. However, it seems to conflict with JAVA. I can't parse the encrypted text with JAVA. Maybe its API is too powerful. I haven't found the right way. I prefer JSEncrypt because it's lightweight and interacts with JAVA.

The only disadvantage is that public key decryption is not possible. If it can be provided, it would be very good.

First i want to say that sign/verify is the opposite process of crypt/decrypt. In signing you first use the math formula for decrypting with the private key and after that you use the public key to encrypt the result and get the plain text. So mathematically is possible but i don`t know if some does this.

The whole idea in RSA is to have two pairs of Keys. One pair for the client and one pair for the server(or other client). They exchange their public keys and encrypt the messages with them. This means:

  1. Client encrypt text with Server public key and send it to server
  2. Server receive encrypted text and decrypt it with his private key
  3. Server generate an answer and encrypt it with Client public key and send it to client
  4. Client receive the answer decrypt it with his private key.

savs90 avatar Apr 28 '19 06:04 savs90

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

Is there a good way to solve this problem, such as providing a public key decryption method? Because, as you said, then I will not be able to use RSA, if so, my interactive data will become public, obviously not what I want. Therefore, if we can provide a JS public key decryption, I think it is better, JAVA language can be public key decryption, I think, JS language can also do it. I've seen a framework provided by Google, named JSRSASIGN, which can decrypt through public key. However, it seems to conflict with JAVA. I can't parse the encrypted text with JAVA. Maybe its API is too powerful. I haven't found the right way. I prefer JSEncrypt because it's lightweight and interacts with JAVA. The only disadvantage is that public key decryption is not possible. If it can be provided, it would be very good.

First i want to say that sign/verify is the opposite process of crypt/decrypt. In signing you first use the math formula for decrypting with the private key and after that you use the public key to encrypt the result and get the plain text. So mathematically is possible but i don`t know if some does this.

The whole idea in RSA is to have two pairs of Keys. One pair for the client and one pair for the server(or other client). They exchange their public keys and encrypt the messages with them. This means:

  1. Client encrypt text with Server public key and send it to server
  2. Server receive encrypted text and decrypt it with his private key
  3. Server generate an answer and encrypt it with Client public key and send it to client
  4. Client receive the answer decrypt it with his private key.

Thank you very much.

sceneNoLonger avatar Apr 28 '19 07:04 sceneNoLonger

return false ,maybe check your code: var Base64 = xxxx; Don't use 'var Base64'

bxcrs avatar May 28 '19 10:05 bxcrs

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

Is there a good way to solve this problem, such as providing a public key decryption method? Because, as you said, then I will not be able to use RSA, if so, my interactive data will become public, obviously not what I want. Therefore, if we can provide a JS public key decryption, I think it is better, JAVA language can be public key decryption, I think, JS language can also do it. I've seen a framework provided by Google, named JSRSASIGN, which can decrypt through public key. However, it seems to conflict with JAVA. I can't parse the encrypted text with JAVA. Maybe its API is too powerful. I haven't found the right way. I prefer JSEncrypt because it's lightweight and interacts with JAVA. The only disadvantage is that public key decryption is not possible. If it can be provided, it would be very good.

First i want to say that sign/verify is the opposite process of crypt/decrypt. In signing you first use the math formula for decrypting with the private key and after that you use the public key to encrypt the result and get the plain text. So mathematically is possible but i don`t know if some does this.

The whole idea in RSA is to have two pairs of Keys. One pair for the client and one pair for the server(or other client). They exchange their public keys and encrypt the messages with them. This means:

  1. Client encrypt text with Server public key and send it to server
  2. Server receive encrypted text and decrypt it with his private key
  3. Server generate an answer and encrypt it with Client public key and send it to client
  4. Client receive the answer decrypt it with his private key.

But in this way, the client has the private key, all the people can use the private key to get the public key, so does it make sense to use two pairs of Keys?

OutUniverse avatar Jun 06 '19 02:06 OutUniverse

It is not very good idea to use the private key in the browser. From the private key it is very easy to generate the public key and therefore there will be no point from the encryption . Also keep in mind that you dont even need the public key , because when you have the private key you can encrypt and decrypt with it .

Is there a good way to solve this problem, such as providing a public key decryption method? Because, as you said, then I will not be able to use RSA, if so, my interactive data will become public, obviously not what I want. Therefore, if we can provide a JS public key decryption, I think it is better, JAVA language can be public key decryption, I think, JS language can also do it. I've seen a framework provided by Google, named JSRSASIGN, which can decrypt through public key. However, it seems to conflict with JAVA. I can't parse the encrypted text with JAVA. Maybe its API is too powerful. I haven't found the right way. I prefer JSEncrypt because it's lightweight and interacts with JAVA. The only disadvantage is that public key decryption is not possible. If it can be provided, it would be very good.

First i want to say that sign/verify is the opposite process of crypt/decrypt. In signing you first use the math formula for decrypting with the private key and after that you use the public key to encrypt the result and get the plain text. So mathematically is possible but i don`t know if some does this. The whole idea in RSA is to have two pairs of Keys. One pair for the client and one pair for the server(or other client). They exchange their public keys and encrypt the messages with them. This means:

  1. Client encrypt text with Server public key and send it to server
  2. Server receive encrypted text and decrypt it with his private key
  3. Server generate an answer and encrypt it with Client public key and send it to client
  4. Client receive the answer decrypt it with his private key.

But in this way, the client has the private key, all the people can use the private key to get the public key, so does it make sense to use two pairs of Keys?

The client has his own private key that no one else has. The server also has his own private key that no one else has.

  • So the client send its public key to the server. The server uses client's public key to encrypt the data and send it back to it. The client is the only one who can decrypt the data because it owns the private key and nobody else know it.
  • Now the other way around. The server sends its public key to the client/s. The client uses server`s public key and encrypt the data and send it back. The server is the only one who can decrypt it because is the only one who knows the private key.

So you never share private key, but only your public key.

savs90 avatar Jun 06 '19 07:06 savs90

Thank you reply at first. But i want to know where to save the private and public key in the client? In theory, data that exists on the client side is available, so everyone can get it. For example, in browser, if i save the public and private key in the cookie, csrf can get it, and they can use the public key to encrypt and use the private key to decrypt. The problem still bothers me.

OutUniverse avatar Jun 06 '19 07:06 OutUniverse

If you dont want to sign and verify who the client is, you can just generate a different key pair for every session. Also if the client is password protected you can just encrypt the private key with the user password and save it in the cookies. In this way the cookie information is useless if you dont have the password.

savs90 avatar Jun 06 '19 18:06 savs90

Thank you very much for your reply. Have a nice day!

OutUniverse avatar Jun 10 '19 00:06 OutUniverse

If you dont want to sign and verify who the client is, you can just generate a different key pair for every session. Also if the client is password protected you can just encrypt the private key with the user password and save it in the cookies. In this way the cookie information is useless if you dont have the password.

How can I encrypt the private key with a password within the browser?

abhijithvijayan avatar Jun 27 '19 07:06 abhijithvijayan

openSSL does have this function: RSA_public_decrypt, so I get it is perfectly Ok to decrypt using the public key. It is a pity not be able to do it here with JSEncrypt.

clauderobi avatar Jul 08 '20 14:07 clauderobi

Encrypting using the public key and decrypting with the private key is one of the most common things people do with asymmetric algorithms, it allows anybody to send you something securely.

If you do it the other way: encrypt using the private key, and decrypt with the public key then it proves the message was sent by the holder of the private key. But because anyone presumably can get hold of the public key, people don't tend to encrypt the whole message, they instead just sign a hash of the data using the private key. Hence RSACryptoServiceProvider has Sign__ and Verify__ methods to do just that.

Still, there are Encrypt/Decrypt methods.

savs90 avatar Jul 08 '20 14:07 savs90

我们的场景是这样的:Web服务,客户端是浏览器,用于低级别的加密,只是避免个别字段的明文传输。使用固定的RSA密码对,公钥保存在浏览器的js中,服务端使用密钥加密,浏览器端使用公钥解密。

目前的解决方案:重写RSAKey.prototype.decrypt方法,修改doPrivate 为 doPublic,并修改pkcs1unpad2方法,去掉第二个参数和相关的处理逻辑,可以解决公钥无法解密的问题。

使用密钥加密和使用私钥解密是人们使用非廉价算法最常见的操作之一,它允许任何人安全地向您发送内容。

如果您以另一种方式执行此操作:使用私钥加密,加入公钥解密,则证明该消息是由私钥持有者发送的。没有人可以获取公钥,因此人们不会倾向于加密整个消息,而是只是使用私钥对数据的哈希值进行签名。因此,RSACryptoServiceProvider 有 Sign__ 和 verify__ 机构名称。

听起来,还是有加密/解密方法。

puregardenia avatar May 23 '24 08:05 puregardenia