安卓APP修改密碼的實現(數據庫的update)

APP端通過向服務器的servlet提交表單(郵箱+舊密碼+新密碼),然後服務器從數據庫中查相對應用戶名的舊密碼是否一致,如果一致則更新數據庫的新密碼,否則失敗。如果想要實現忘記並找回舊密碼的,請看這篇文章

前提:已建好數據庫,建好用戶表格,詳情請看這篇文章

效果展示:
在這裏插入圖片描述

1.需要用到的技術:

1.Android
2.servlet
3.MySQL(數據庫的查找、更新)
4.Tomcat
5.加密算法(數據加密傳輸)

2.Android APP的實現

(1)activity_alter_psw.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:gravity="center"
    android:orientation="vertical"
    android:padding="10dp">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="修改密碼"
        android:textColor="@color/colorPrimary"
        android:textSize="20sp"/>
    <EditText
        android:id="@+id/et_email"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="郵箱"/>
    <EditText
        android:id="@+id/et_now"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="舊密碼"/>

    <EditText
        android:id="@+id/et_new"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="新密碼"/>

    <EditText
        android:id="@+id/et_new_password"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="再次輸入密碼"/>

    <Button
        android:id="@+id/btn_update_password"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/lavender"
        android:text="重置密碼"
       />

   <Button
       android:id="@+id/update_forget_psw"
       android:layout_width="match_parent"
       android:layout_height="wrap_content"
       android:background="@color/lavender"
       android:layout_marginTop="7dp"
       android:text="忘記密碼"/>

</LinearLayout>


(2)AlterPSWActivity.java

import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.text.TextUtils;
import android.text.method.PasswordTransformationMethod;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import com.android.volley.AuthFailureError;
import com.android.volley.Request;
import com.android.volley.RequestQueue;
import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.android.volley.toolbox.StringRequest;
import com.android.volley.toolbox.Volley;
import com.example.administrator.loginclient.ActivityCollectors.ActivityCollector;
import com.example.administrator.loginclient.HttpsUtils.HTTPSTrustManager;
import com.example.administrator.loginclient.R;
import com.example.administrator.loginclient.RsaUtils.GenKeyFromString;
import com.example.administrator.loginclient.RsaUtils.MyConstant;
import com.example.administrator.loginclient.RsaUtils.RSAUtil;
import org.bouncycastle.util.encoders.Base64;
import org.json.JSONException;
import org.json.JSONObject;
import java.security.interfaces.RSAPublicKey;
import java.util.HashMap;
import java.util.Map;

/**
 * 修改密碼
 */
public class AlterPSWActivity extends BaseActivity implements View.OnClickListener {

    private EditText et_now,et_new,et_new2;
    private EditText et_email;
    private Button btn_update;
    private Button btn_forget;
    public static RequestQueue queue;
    private static Context mContext;


    @Override
    protected void onCreate( Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_alter_psw);
        queue = Volley.newRequestQueue(getApplicationContext());
        mContext = this;
        initView();//初始化UI
    }

    /**
     * 初始化UI
     */
    private void initView() {
        et_now=(EditText)findViewById(R.id.et_now);
        et_new=(EditText)findViewById(R.id.et_new);
        et_new2=(EditText)findViewById(R.id.et_new_password);
        et_now.setTransformationMethod(PasswordTransformationMethod.getInstance());//密碼不可見
        et_new.setTransformationMethod(PasswordTransformationMethod.getInstance());//密碼不可見
        et_new2.setTransformationMethod(PasswordTransformationMethod.getInstance());//密碼不可見
        et_email=(EditText)findViewById(R.id.et_email);

        btn_forget=(Button)findViewById(R.id.update_forget_psw);
        btn_update=(Button)findViewById(R.id.btn_update_password);
        btn_update.setOnClickListener(this);
        btn_forget.setOnClickListener(this);

    }

    @Override
    public void onClick(View v) {
        switch (v.getId()){
            case R.id.btn_update_password:
                //重置密碼
                String now=et_now.getText().toString().trim();
                String pass1=et_new.getText().toString().trim();
                String pass2=et_new2.getText().toString().trim();
                final String psw_old = et_now.getText().toString().trim();
                final String psw_new = et_new.getText().toString().trim();
                final String email=et_email.getText().toString().trim();

                // 獲取Rsa 工具類對象
                RSAUtil rsa = new RSAUtil();

                // 獲取公鑰
                RSAPublicKey pubKey = (RSAPublicKey) GenKeyFromString
                        .getPubKey(MyConstant.pubKey1);

                // 使用公鑰加密 數據
                byte[] enRsaByte_psw_old = new byte[0];
                byte[] enRsaBytes_psw_new = new byte[0];
                byte[] enRsaBytes_psw_email = new byte[0];

                try {
                    enRsaByte_psw_old = rsa.encrypt(pubKey, psw_old.getBytes());//舊密碼加密
                    enRsaBytes_psw_new = rsa.encrypt(pubKey, psw_new.getBytes());//新密碼加密
                    enRsaBytes_psw_email=rsa.encrypt(pubKey,email.getBytes());

                } catch (Exception e) {
                    e.printStackTrace();
                }

                /**
                 * base64對byte數組進行編碼,進過編碼後得到String傳輸到對服務端解碼得出byte數組。
                 */
                String enRsaStr_psw_old = new String(Base64.encode(enRsaByte_psw_old));//舊密碼byte數組轉成字符串
                String enRsaStr_psw_new = new String(Base64.encode(enRsaBytes_psw_new));//新密碼byte數組轉成字符串
                String enRsaStr_psw_email=new String(Base64.encode(enRsaBytes_psw_email));//郵箱byte數組轉成字符串


                if(!TextUtils.isEmpty(now)&&!TextUtils.isEmpty(pass1)&&!TextUtils.isEmpty(pass2)){

                    //和原始密碼一致
                   if(pass1.equals(now)||pass2.equals(now)){
                        Toast.makeText(AlterPSWActivity.this, "新舊密碼不能一樣,請再想個新密碼!", Toast.LENGTH_SHORT).show();

                    }else if(pass1.equals(pass2)){

                       Toast.makeText(AlterPSWActivity.this, "密碼校驗成功", Toast.LENGTH_SHORT).show();

                       //此處做修改密碼操作
                       UpdatePSWRequest(enRsaStr_psw_old,enRsaStr_psw_new,enRsaStr_psw_email);

                    }else{
                        Toast.makeText(AlterPSWActivity.this, "兩次密碼輸入不一致!", Toast.LENGTH_SHORT).show();

                    }
                }else{
                    Toast.makeText(AlterPSWActivity.this, "輸入框不能爲空!", Toast.LENGTH_SHORT).show();

                }

                break;
            case R.id.update_forget_psw:
                Intent intent = new Intent(AlterPSWActivity.this,ForgetPswActivity.class);
                intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);//關掉所要到的界面中間的activity
                AlterPSWActivity.this.startActivity(intent);
               // ActivityCollector.finishAll();//關掉之前的所有活動
                break;
    }
}
    public static void UpdatePSWRequest(final String password,final String updatePassword,final String email){
        //請求地址
        String url = "http://localhost:8083/MyFirstWebAPP/UpdatePasswordServlet";    //注①
        String tag = "Alter";    //注②

        //取得請求隊列
        RequestQueue requestQueue = queue;


        //防止重複請求,所以先取消tag標識的請求隊列
        requestQueue.cancelAll(tag);
        HTTPSTrustManager.allowAllSSL();//允許所有https請求

        //創建StringRequest,定義字符串請求的請求方式爲POST(省略第一個參數會默認爲GET方式)
        final StringRequest request = new StringRequest(Request.Method.POST, url,
                new Response.Listener<String>() {
                    @Override
                    public void onResponse(String response) {
                        try {
                            JSONObject jsonObject = (JSONObject) new JSONObject(response).get("params");  //注③
                            String result = jsonObject.getString("Result");  //注④
                            if (result.equals("UpdateSuccess")) {  //注⑤


                                Toast.makeText(mContext, "修改密碼成功,請重新登錄!", Toast.LENGTH_LONG).show();
                                Intent intent = new Intent(mContext,MainActivity.class);
                                //intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);//關掉所要到的界面中間的activity
                                mContext.startActivity(intent);
                                ActivityCollector.finishAll();//關掉之前的所有活動


                            }
                            else if (result.equals("TheOldPasswordIsError")){
                                //做自己的登錄失敗操作,如Toast提示

                                Toast.makeText(mContext, "原始密碼錯誤", Toast.LENGTH_LONG).show();
                            } else if (result.equals("TheEmailIsError")){
                                //做自己的登錄失敗操作,如Toast提示

                                Toast.makeText(mContext, "郵箱不存在", Toast.LENGTH_LONG).show();
                            }

                        } catch (JSONException e) {
                            //做自己的請求異常操作,如Toast提示(“無網絡連接”等)
                            Log.e("TAG", e.getMessage(), e);
                            Toast.makeText(mContext, "無網絡連接", Toast.LENGTH_LONG).show();

                        }
                    }
                }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                //做自己的響應錯誤操作,如Toast提示(“請稍後重試”等)
                Log.e("TAG", error.getMessage(), error);
                Toast.makeText(mContext, "請稍後重試", Toast.LENGTH_LONG).show();
            }
        }) {
            @Override
            protected Map<String, String> getParams() throws AuthFailureError {
                Map<String, String> params = new HashMap<>();
                params.put("Password", password);
                params.put("UpdatePassword", updatePassword);
                params.put("Email", email);
                return params;
            }
        };

        //設置Tag標籤
        request.setTag(tag);

        //將請求添加到隊列中
        requestQueue.add(request);

    }
}

(3)用到的依賴:

  implementation fileTree(include: ['*.jar'], dir: 'libs')
    implementation 'androidx.core:core:1.3.0'
    implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
    testImplementation 'junit:junit:4.12'
    implementation 'androidx.appcompat:appcompat:1.1.0'
    implementation 'com.android.volley:volley:1.1.1'
    implementation files('libs/sun.misc.BASE64Decoder.jar')
    implementation files('libs/bcprov-jdk15-1.45.jar')
    //noinspection GradleDeprecated
    implementation 'com.google.android.gms:play-services-appindexing:9.8.0'
    androidTestImplementation('androidx.test.espresso:espresso-core:3.1.0', {
        exclude group: 'com.android.support', module: 'support-annotations'
    })
    implementation 'com.google.android.material:material:1.3.0-alpha01'

外部包自行下載添加依賴,提取碼:jd3v

3.servlet的實現:

(1)web.xml增加

   <servlet>
        <servlet-name>UpdatePasswordServlet</servlet-name>
        <servlet-class>net.jw.MyFirstWebAPP.ServletPackage.UpdatePasswordServlet</servlet-class>
    </servlet>
   <servlet-mapping>
        <servlet-name>UpdatePasswordServlet</servlet-name>
        <url-pattern>/UpdatePasswordServlet</url-pattern>
    </servlet-mapping>

(2)UpdatePasswordServlet.java(servlet)

import java.io.IOException;
import java.io.PrintWriter;
import java.security.interfaces.RSAPrivateKey;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.jw.MyFirstWebAPP.RSAutil.GenKeyFromString;
import net.jw.MyFirstWebAPP.RSAutil.MyConstant;
import net.jw.MyFirstWebAPP.RSAutil.RSAUtil;
import net.jw.MyFirstWebAPP.User;
import net.jw.MyFirstWebAPP.UserDAO;
import net.sf.json.JSONObject;
import org.bouncycastle.util.encoders.Base64;

/**
 *更新密碼
 * @author Administrator
 */
public class UpdatePasswordServlet extends HttpServlet {

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {

        // 設置響應內容類型  
        response.setContentType("text/html;charset=utf-8");
        request.setCharacterEncoding("utf-8");
        response.setCharacterEncoding("utf-8");

        try (PrintWriter out = response.getWriter()) {

            //獲得請求中傳來的舊密碼、新密碼
            String Old_Password = request.getParameter("Password").trim();
            String password = request.getParameter("UpdatePassword").trim();
            String email = request.getParameter("Email").trim();
          
            //密碼驗證結果
            
            byte[] byterepsw_old = Base64.decode(Old_Password);//舊密碼解密BASE64
            byte[] byterepsw = Base64.decode(password);//密碼解密BASE64
            byte[] bytere_email = Base64.decode(email);//密碼解密BASE64
           
          //  System.out.println(byteres);
           // System.out.println("字符串轉成byte數組:"+new String(byteres));
             // 獲取私鑰	
            RSAUtil rsa = new RSAUtil();
            RSAPrivateKey priKey = (RSAPrivateKey) GenKeyFromString
				.getPrivateKey(MyConstant.priKey1);
             // 拿着私鑰解舊密碼
            byte[] encRsaByte_old = rsa.decrypt(priKey,
				byterepsw_old);
            // 拿着私鑰解 新密碼
            byte[] encRsaBytepsw = rsa.decrypt(priKey,
				byterepsw);
              // 拿着私鑰解新密碼
            byte[] encRsaByte_email = rsa.decrypt(priKey,
				bytere_email);
            String NewPassword=new String(encRsaBytepsw);//新密碼字符串
            
            int verifyResult = verifyUpdate(new String(encRsaByte_old),new String(encRsaByte_email),NewPassword);

            Map<String, String> params = new HashMap<>();
            JSONObject jsonObject = new JSONObject();

            if (verifyResult == 1) {
                params.put("Result", "UpdateSuccess");//郵箱存在,原始密碼正確,密碼修改成功
               
            } 
            else if (verifyResult == 0){
               
                params.put("Result", "TheEmailIsError");//郵箱不存在
            } else if (verifyResult == 2){
               
                params.put("Result", "TheOldPasswordIsError");//原始密碼錯誤
            }
                   
            jsonObject.put("params", params);
            out.write(jsonObject.toString());
        } catch (Exception ex) {
            Logger.getLogger(RegisterServlet.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        doPost(request, response);
    }

    /**
     * 驗證郵箱和密碼是否正確
     *
     * @param OldPassword
     * @param email
     * @param password
     */
    private int verifyUpdate(String OldPassword,String email,String password) {
      
       User user=UserDAO.queryPasswordByEmail(email);
       
       if(!UserDAO.checkEmail(email))
       {
           if(user.getPassword().equals(OldPassword))
           {    //更新密碼操作
               if(UserDAO.updatePassword(password, email)){
                   return 1;//密碼正確
               } 
            }
           else
             {
               return 2;//密碼錯誤
             }
       }
         return 0;       //郵箱不存在
    } 
}   

以上代碼有導入包報錯的以及數據庫的操作等等,請先閱讀這篇文章

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章