根据Laravel 5.8和Eloquent的关系更新数据库表

问题描述 投票:0回答:2

我有一个问题,更新属于另一个表的表。我有一个用户表和一个食谱表。 Recipe模型属于User模型,User模型有很多Recipe。

每个食谱在我的索引视图中显示为一张小卡片,在该卡片上,以及每个单独的节目页面上,我正在打印recipe-> author。创建配方时,它会从users表中获取username属性,并将其设置为配方表上的author属性。但是,当我更新用户的用户名时,配方表中的author属性不会相应更新。

用户模型

 public function recipes(){
        return $this->hasMany('App\Recipe');
    }

食谱模型

 public function user(){
        return $this->belongsTo('App\User');
    }

在更新用户时,我可以在UserController中添加一些逻辑来解决这个问题吗?

UserController的@更新

$user = Auth::user();

        $this->validate(request(), [
            'name' => 'required',
            'username' => 'required',
        ]);

          // Handle File Upload 
          if(request()->hasfile('profile_pic')){
            // Get filename with extension
            $fileameWithExt = request()->file('profile_pic')->getClientOriginalName();
            // Get just filename
            $filename = pathinfo($fileameWithExt, PATHINFO_FILENAME);
            // Get just extension
            $extension = request()->file('profile_pic')->getClientOriginalExtension();
            // Filename to store
            $fileNameToStore = $filename . '_' . time() . '.' . $extension;
            // Upload Image
            $path = request()->file('profile_pic')->storeAs('public/profile_pictures', $fileNameToStore);
        } else {
            $fileNameToStore = 'noimage.jpg';
        }

        $user->name = request('name');
        $user->username = request('username');
        $user->description = request('description');
        $user->location = request('location');
        if(request()->hasFile('profile_pic')){
            $user->profile_pic = $fileNameToStore;
        }
        $user->push();

        $user_id = Auth::user()->id;
        return redirect()->route('user', ['id' => $user_id]);
    }

我已经阅读了Laravel文档,找不到任何可以完成我正在寻找的东西。非常感谢任何指导!

php laravel eloquent
2个回答
2
投票

你的意思是你在username存储users,你想在usernameauthor存储精确的recipes

为什么不使用关系$recipe->user->username引用名称。它将根据您在users中的user_id查询您的recipes表,并为您获取username

这样您就不会在数据库中存储重复数据。应该只有一个Single Source of Truth。您可以根据user_id获取用户数据,没有必要存储另一组数据,并在更改源时不断更新。

如果你发现查询整个User模型有点沉重,那么你可以使用Recipe::with('users:id,username')->get()只查询username

要么

如果您想维持当前的$recipe->author,您可以:

// Recipe class
public function getAuthorAttribute() {
  return $this->user->username;
}

1
投票

如果在迁移文件上设置外键,则可以将->onUpdate('CASCADE')子句添加到recipes表迁移的外部用户名。

注意:onCascade外部约束也可以在Laravel之外工作,因为它仅依赖于数据库引擎对外键的支持。

无论如何,请小心验证,因为您必须确保新选择的用户名尚未被其他人使用。

假设您的用户模型已连接到users表并且具有id主键,请确保在数据库中将用户名列设置为唯一,并相应地验证*用户输入。

前者是通过再次编辑您的迁移来完成的。

后者通过修改这些规则来解决:

// Do not forget the Rule import at the top of your controller
use Illuminate\Validation\Rule;

// Then in your method
$this->validate(request(), [
    'name' => 'required',
    'username' => [
        'required',
        Rule::unique('users', 'username')->ignore($user)
    ]
]);

注意:如果您修改迁移,则必须重新运行它们才能应用修改。

© www.soinside.com 2019 - 2024. All rights reserved.