[英]simple encryption in android
我參考了這篇文章的簡單加密 ,
我正在使用edittext中的一些文本,然后使用自定義對話框從用戶獲取密鑰,然后按照文章中提到的那樣創建它,加密原始文本,解密它並將其顯示到屏幕上的Textview ..但是在運行異常后如logcat中所示在代碼中。它確實非常簡單,但我是android和java的新手所以面臨困難。可能我覺得我在變量傳遞中做錯了
Java代碼
package com.example.encryptiondecryption;
import java.security.SecureRandom;
import javax.crypto.Cipher;
import javax.crypto.KeyGenerator;
import javax.crypto.spec.SecretKeySpec;
import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.os.Bundle;
import android.util.Base64;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
public class MainActivity extends Activity implements OnClickListener {
static final String TAG = "SymmetricAlgorithmAES";
static final String TAG1 = "encccccccc";
EditText getData_edt, key_edt;
Button genkey_btn, encrypt_btn, decrypt_btn;
static String key_str = null;
static String getData_str = null;
static SecretKeySpec sks = null;
static byte[] encodedBytes = null;
static byte[] decodedBytes = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
getData_edt = (EditText) (findViewById(R.id.am_input_edt));
genkey_btn = (Button) (findViewById(R.id.am_key_btn));
encrypt_btn = (Button) (findViewById(R.id.am_encrypt_btn));
decrypt_btn = (Button) (findViewById(R.id.am_decrypt_btn));
getData_str = getData_edt.getText().toString();
genkey_btn.setOnClickListener(this);
encrypt_btn.setOnClickListener(this);
decrypt_btn.setOnClickListener(this);
}
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
switch (v.getId()) {
case R.id.am_key_btn:
genKey(sks);
break;
case R.id.am_encrypt_btn:
encrypt(sks);
break;
case R.id.am_decrypt_btn:
decrypt();
break;
default:
break;
}
}
private void genKey(SecretKeySpec sks) {
// TODO Auto-generated method stub
Context context = this;
final Dialog myDialog = new Dialog(context);
myDialog.setContentView(R.layout.dialog);
myDialog.setTitle("enter key");
key_edt = (EditText) myDialog.findViewById(R.id.dg_key_tv);
Button ok_btn = (Button) myDialog.findViewById(R.id.dg_ok_btn);
Button cancel_btn = (Button) myDialog.findViewById(R.id.dg_cancel_btn);
Log.d(TAG1, key_str);
ok_btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
key_str = key_edt.getText().toString();
}
});
try {
SecureRandom sr = SecureRandom.getInstance("SHA1PRNG");
sr.setSeed(key_str.getBytes());
KeyGenerator kg = KeyGenerator.getInstance("AES");
kg.init(128, sr);
sks = new SecretKeySpec((kg.generateKey()).getEncoded(), "AES");
Log.i("encrypt", sks.toString());
} catch (Exception e) {
Log.e(TAG, "AES secret key spec error");
}
cancel_btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
myDialog.dismiss();
}
});
myDialog.show();
}
private void encrypt(SecretKeySpec sks) {
// TODO Auto-generated method stub
try {
Cipher c = Cipher.getInstance("AES");
c.init(Cipher.ENCRYPT_MODE, sks);
encodedBytes = c.doFinal(getData_str.getBytes());
String encoded = Base64
.encodeToString(encodedBytes, Base64.DEFAULT);
System.out.println(" " + encoded);
} catch (Exception e) {
Log.e(TAG, "AES encryption error");
}
}
private void decrypt() {
// TODO Auto-generated method stub
try {
Cipher c = Cipher.getInstance("AES");
c.init(Cipher.DECRYPT_MODE, sks);
decodedBytes = c.doFinal(encodedBytes);
System.out.println(" " + new String(decodedBytes));
} catch (Exception e) {
Log.e(TAG, "AES decryption error");
TextView tvdecoded = (TextView) findViewById(R.id.am_show_tv);
tvdecoded.setText("DECOD\n" + new String(decodedBytes) + "\n");
}
}
}
XML
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.encryptiondecryption.MainActivity" >
<EditText
android:id="@+id/am_input_edt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:ems="10"
android:inputType="textMultiLine" />
<Button
android:id="@+id/am_key_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/am_input_edt"
android:layout_below="@+id/am_input_edt"
android:text="enter your key" />
<Button
android:id="@+id/am_encrypt_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@id/am_key_btn"
android:layout_below="@+id/am_key_btn"
android:text="Encrypt" />
<Button
android:id="@+id/am_decrypt_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@id/am_encrypt_btn"
android:layout_below="@+id/am_encrypt_btn"
android:text="Decrypt" />
<TextView
android:id="@+id/am_show_tv"
android:layout_width="match_parent"
android:layout_height="40dp"
android:layout_alignLeft="@+id/am_decrypt_btn"
android:layout_below="@+id/am_decrypt_btn"
android:layout_marginTop="15dp"
android:textAppearance="?android:attr/textAppearanceMedium" />
</RelativeLayout>
對話框的xml布局......
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<EditText
android:id="@+id/dg_key_tv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:ems="10" >
<requestFocus />
</EditText>
<Button
android:id="@+id/dg_ok_btn"
android:layout_width="61dp"
android:layout_height="wrap_content"
android:text="Ok" />
<Button
android:id="@+id/dg_cancel_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="cancel"
/>
Logcat錯誤
02-23 23:50:17.245: E/SymmetricAlgorithmAES(12735): AES secret key spec error
02-23 23:50:17.245: W/System.err(12735): java.lang.NullPointerException
02-23 23:50:17.265: W/System.err(12735): at com.example.encryptiondecryption.MainActivity.genKey(MainActivity.java:99)
02-23 23:50:17.265: W/System.err(12735): at com.example.encryptiondecryption.MainActivity.onClick(MainActivity.java:56)
02-23 23:50:17.265: W/System.err(12735): at android.view.View.performClick(View.java:4439)
02-23 23:50:17.265: W/System.err(12735): at android.widget.Button.performClick(Button.java:139)
02-23 23:50:17.265: W/System.err(12735): at android.view.View$PerformClick.run(View.java:18395)
02-23 23:50:17.265: W/System.err(12735): at android.os.Handler.handleCallback(Handler.java:725)
02-23 23:50:17.265: W/System.err(12735): at android.os.Handler.dispatchMessage(Handler.java:92)
02-23 23:50:17.265: W/System.err(12735): at android.os.Looper.loop(Looper.java:176)
02-23 23:50:17.265: W/System.err(12735): at android.app.ActivityThread.main(ActivityThread.java:5317)
02-23 23:50:17.265: W/System.err(12735): at java.lang.reflect.Method.invokeNative(Native Method)
02-23 23:50:17.265: W/System.err(12735): at java.lang.reflect.Method.invoke(Method.java:511)
02-23 23:50:17.265: W/System.err(12735): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1102)
02-23 23:50:17.265: W/System.err(12735): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:869)
02-23 23:50:17.265: W/System.err(12735): at dalvik.system.NativeStart.main(Native Method)
02-23 23:50:21.579: E/ViewRootImpl(12735): sendUserActionEvent() mView == null
02-23 23:50:23.491: E/SymmetricAlgorithmAES(12735): AES encryption error
02-23 23:50:24.932: E/SymmetricAlgorithmAES(12735): AES decryption error
02-23 23:50:24.932: W/System.err(12735): java.lang.NullPointerException
02-23 23:50:24.942: W/System.err(12735): at com.android.org.bouncycastle.jcajce.provider.symmetric.util.BaseBlockCipher.engineInit(BaseBlockCipher.java:385)
02-23 23:50:24.942: W/System.err(12735): at com.android.org.bouncycastle.jcajce.provider.symmetric.util.BaseBlockCipher.engineInit(BaseBlockCipher.java:625)
02-23 23:50:24.952: W/System.err(12735): at javax.crypto.Cipher.init(Cipher.java:519)
02-23 23:50:24.952: W/System.err(12735): at javax.crypto.Cipher.init(Cipher.java:479)
02-23 23:50:24.952: W/System.err(12735): at com.example.encryptiondecryption.MainActivity.decrypt(MainActivity.java:141)
02-23 23:50:24.952: W/System.err(12735): at com.example.encryptiondecryption.MainActivity.onClick(MainActivity.java:64)
02-23 23:50:24.952: W/System.err(12735): at android.view.View.performClick(View.java:4439)
02-23 23:50:24.952: W/System.err(12735): at android.widget.Button.performClick(Button.java:139)
02-23 23:50:24.952: W/System.err(12735): at android.view.View$PerformClick.run(View.java:18395)
02-23 23:50:24.952: W/System.err(12735): at android.os.Handler.handleCallback(Handler.java:725)
02-23 23:50:24.952: W/System.err(12735): at android.os.Handler.dispatchMessage(Handler.java:92)
02-23 23:50:24.952: W/System.err(12735): at android.os.Looper.loop(Looper.java:176)
02-23 23:50:24.952: W/System.err(12735): at android.app.ActivityThread.main(ActivityThread.java:5317)
02-23 23:50:24.952: W/System.err(12735): at java.lang.reflect.Method.invokeNative(Native Method)
02-23 23:50:24.952: W/System.err(12735): at java.lang.reflect.Method.invoke(Method.java:511)
02-23 23:50:24.952: W/System.err(12735): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1102)
02-23 23:50:24.952: W/System.err(12735): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:869)
02-23 23:50:24.952: W/System.err(12735): at dalvik.system.NativeStart.main(Native Method)
02-23 23:50:24.952: D/AndroidRuntime(12735): Shutting down VM
02-23 23:50:24.952: W/dalvikvm(12735): threadid=1: thread exiting with uncaught exception (group=0x412b3930)
02-23 23:50:24.962: E/AndroidRuntime(12735): FATAL EXCEPTION: main
02-23 23:50:24.962: E/AndroidRuntime(12735): java.lang.NullPointerException
02-23 23:50:24.962: E/AndroidRuntime(12735): at java.lang.String.<init>(String.java:141)
02-23 23:50:24.962: E/AndroidRuntime(12735): at com.example.encryptiondecryption.MainActivity.decrypt(MainActivity.java:148)
02-23 23:50:24.962: E/AndroidRuntime(12735): at com.example.encryptiondecryption.MainActivity.onClick(MainActivity.java:64)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.view.View.performClick(View.java:4439)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.widget.Button.performClick(Button.java:139)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.view.View$PerformClick.run(View.java:18395)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.os.Handler.handleCallback(Handler.java:725)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.os.Handler.dispatchMessage(Handler.java:92)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.os.Looper.loop(Looper.java:176)
02-23 23:50:24.962: E/AndroidRuntime(12735): at android.app.ActivityThread.main(ActivityThread.java:5317)
02-23 23:50:24.962: E/AndroidRuntime(12735): at java.lang.reflect.Method.invokeNative(Native Method)
02-23 23:50:24.962: E/AndroidRuntime(12735): at java.lang.reflect.Method.invoke(Method.java:511)
02-23 23:50:24.962: E/AndroidRuntime(12735): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1102)
02-23 23:50:24.962: E/AndroidRuntime(12735): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:869)
02-23 23:50:24.962: E/AndroidRuntime(12735): at dalvik.system.NativeStart.main(Native Method)
我認為您的一個問題是對將對象傳遞給方法時會發生什么的誤解。 在該方法中,您可以通過調用其方法來修改參數對象,但是您無法為其分配值並期望它以任何方式影響調用代碼。 有關這方面的更多詳細信息,請閱讀: Java是“傳遞引用”還是“按值傳遞”?
這會導致您的密鑰生成方法出現問題,您可以在其中傳入sks
字段並希望以下代碼更改字段值:
sks = new SecretKeySpec((kg.generateKey()).getEncoded(), "AES");
相反,這只會影響本地方法參數變量的值。 它對你的sks
字段沒有影響。 要解決此問題,請直接使用以下內容分配給該字段:
this.sks = new SecretKeySpec((kg.generateKey()).getEncoded(), "AES");
然后,您可以調整方法,使其不需要參數:
private void genKey() {
// ....
}
正如另一個答案所指出的,你的sks
變量的范圍需要是整個類,而不僅僅是genkey()
方法。 但是,該方法中還有另一個錯誤導致規范錯誤。 它創建一個對話框窗口並將監聽器添加到“確定”按鈕,但隨后嘗試創建密鑰(當TextView仍為空時)。 生成代碼應該是單擊偵聽器的一部分。
private void genKey() {
// TODO Auto-generated method stub
Context context = this;
final Dialog myDialog = new Dialog(context);
myDialog.setContentView(R.layout.dialog);
myDialog.setTitle("enter key");
key_edt = (EditText) myDialog.findViewById(R.id.dg_key_tv);
Button ok_btn = (Button) myDialog.findViewById(R.id.dg_ok_btn);
Button cancel_btn = (Button) myDialog.findViewById(R.id.dg_cancel_btn);
Log.d(TAG1, key_str);
ok_btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
key_str = key_edt.getText().toString();
// only try to create the Key Spec now we have our key string
// first check to make sure it's not blank
if(key_str != null && !key_str.isEmpty()){
try {
SecureRandom sr = SecureRandom.getInstance("SHA1PRNG");
sr.setSeed(key_str.getBytes());
KeyGenerator kg = KeyGenerator.getInstance("AES");
kg.init(128, sr);
this.sks = new SecretKeySpec((kg.generateKey()).getEncoded(), "AES");
Log.i("encrypt", sks.toString());
} catch (Exception e) {
Log.e(TAG, "AES secret key spec error");
}
}
else{ // string is empty
// make some toast to alert user
}
}
});
cancel_btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
myDialog.dismiss();
}
});
myDialog.show();
}
另請注意,這應該使用this.sks
將Keyspec存儲為類變量。 否則,一旦clickListener結束,它將被垃圾收集。 您的加密和解密函數應使用此類變量來完成其工作,並在尚未生成密鑰時顯示吐司或其他內容。
例如,使用您的encrypt()
方法:
private void encrypt() {
if (this.sks == null){
// make toast and tell user to generate the key
} else {
try {
Cipher c = Cipher.getInstance("AES");
// use the class key spec to encrypt
c.init(Cipher.ENCRYPT_MODE, this.sks);
encodedBytes = c.doFinal(getData_str.getBytes());
String encoded = Base64
.encodeToString(encodedBytes, Base64.DEFAULT);
System.out.println(" " + encoded);
} catch (Exception e) {
Log.e(TAG, "AES encryption error");
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.