本指南介绍了如何在 laravel 模型中实现敏感数据的加密和解密。通过执行以下步骤,您可以在将数据存储到数据库之前保护数据并在检索数据时对其进行解密。
先决条件
- Laravel:确保您使用的是 Laravel 项目。
- 加密密钥:Laravel 在 .env 文件中自动生成 APP_KEY。该密钥由 Laravel 的加密服务使用。
第 1 步:在模型中设置加密
在模型中,我们将使用 Laravel 的 encrypt() 和 decrypt() 函数自动处理指定字段的加密和解密。
Doctor模型
使用加密和解密方法创建或更新Doctor模型。我们将在将名字、姓氏、电子邮件和手机等字段保存到数据库之前对其进行加密。
<?phpnamespace AppModels;use IlluminateDatabaseEloquentModel;use IlluminateSupportFacadesCrypt;class Doctor extends Model{ protected $fillable = [ 'first_name', 'last_name', 'email', 'mobile', 'hashed_email', 'password' ]; // Automatically encrypt Attributes when setting them public function setFirstNameAttribute($value) { $this->attributes['first_name'] = encrypt($value); } public function setLastNameAttribute($value) { $this->attributes['last_name'] = encrypt($value); } public function setEmailAttribute($value) { $this->attributes['email'] = encrypt($value); } public function setMobileAttribute($value) { $this->attributes['mobile'] = encrypt($value); } // Automatically decrypt attributes when getting them public function getFirstNameAttribute($value) { return decrypt($value); } public function getLastNameAttribute($value) { return decrypt($value); } public function getEmailAttribute($value) { return decrypt($value); } public function getMobileAttribute($value) { return decrypt($value); }}
说明
- Setter 方法:使用 set{AttributeName }Attribute() 在数据存储到数据库之前对数据进行加密。
- Getter 方法:从数据库检索数据时,使用 get{AttributeName}Attribute() 解密。
第 2 步:数据存储和检索的控制器
在控制器中,您可以处理验证并调用模型的 直接加密属性,无需额外加密/解密 步骤。
DoctorController
DoctorController 通过验证来处理注册 输入数据,通过模型对其进行加密,并将其保存在数据库中。 获取医生数据时,会自动解密 敏感字段。
<?phpnamespace AppHttpControllers;use IlluminateHttpRequest;use AppModelsDoctor;use IlluminateSupportFacadesHash;class DoctorController extends Controller{ public function register(Request $request) { // Validate the incoming request $validatedData = $request->validate([ 'first_name' => 'required|string|max:255', 'last_name' => 'required|string|max:255', 'email' => 'required|string|email|max:255|unique:doctors,email', 'mobile' => 'required|string|size:10|unique:doctors,mobile', 'password' => 'required|string|min:8|confirmed', ]); // Hash the email to ensure uniqueness $hashedEmail = hash('sha256', $validatedData['email']); // Create a new doctor record (model will handle encryption) $doctor = Doctor::create([ 'first_name' => $validatedData['first_name'], 'last_name' => $validatedData['last_name'], 'email' => $validatedData['email'], 'hashed_email' => $hashedEmail, 'mobile' => $validatedData['mobile'], 'password' => Hash::make($validatedData['password']), ]); return response()->json([ 'message' => 'Doctor registered successfully', 'doctor' => $doctor ], 201); } public function show($id) { // Fetch the doctor record (model will decrypt the data automatically) $doctor = Doctor::findOrFail($id); return response()->json($doctor); }}
说明
- register 方法:验证传入的请求,创建新的医生记录,并根据模型的加密方法自动加密名字、姓氏、电子邮件和手机等字段。
- show 方法:通过 ID 检索医生记录。这 模型的 getter 方法之前会自动解密敏感字段 返回数据。
步骤 3:数据库配置
确保敏感数据的 doctor 表列的长度足以处理加密数据(通常为 TEXT 或 LONGTEXT)。
迁移设置示例:
Schema::create('doctors', function (Blueprint $table) { $table->id(); $table->text('first_name'); $table->text('last_name'); $table->text('email'); $table->string('hashed_email')->unique(); // SHA-256 hashed email $table->text('mobile'); $table->string('password'); $table->timestamps();});
注意:由于加密值可能比明文长得多值,加密字段首选文本。
步骤 4:处理解密异常
为了增强错误处理,请将解密逻辑包装在模型 getter 的 try-catch 块中:
public function getFirstNameAttribute($value){ try { return decrypt($value); } catch (DecryptException $e) { return null; // Or handle the error as needed }}
附加说明
- 环境安全:确保 APP_KEY 安全地存储在 .env 文件中。此密钥对于加密/解密至关重要。
- 数据备份:如果数据完整性至关重要,请确保您有备份机制,因为没有正确的 APP_KEY,加密数据将无法恢复。
摘要
- 模型加密:存储前使用setter方法加密数据,检索时使用getter方法解密。
- 控制器逻辑:控制器可以直接处理加密字段,无需额外的加密代码.
- 数据库配置:使用 TEXT 或 LONGTEXT 列作为加密字段。
- 安全注意事项:保护您的 APP_KEY 并在 getter 中使用异常处理来处理解密错误。
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END