Laravel - Итерация сводных данных (свойство не существует в этом экземпляре коллекции)

У меня связь "многие ко многим" между Order и Product

Product.php

public function orders()
{
    return $this->belongsToMany(Order::class)
                ->withTimestamps()
                ->withPivot('qty');
}

Order.php

public function products()
{
    return $this->belongsToMany(Product::class)
                ->withTimestamps()
                ->withPivot('qty');
}

Теперь, когда я пытаюсь использовать итерацию в представлении (в этом случае я просто пытаюсь показать форму, которая выполняет итерацию по всем доступным Product, я всегда получаю сообщение об ошибке ...

Property [products] does not exist on this collection instance.

create.blade.php

@foreach ($products->orders as $product)

# Order inputs are here

{{ Form::text('qty', $product->pivot->qty, [
                          'type' => 'tel',
                            'min' => 0,
                            'max' => 20,
                            'step' => 1,
                            'placeholder' => '0',
                            'class' => 'meal'
                            ]) }}
@endforeach

Я также пробовал @foreach ($products->orders as $product), и оба подхода дают мне ту же ошибку.

Я попытался исправить эту ошибку в своем контроллере разными способами, вот моя последняя попытка:

OrderControlller.php

public function create()
{
    $user = Auth::user();
    $products = Product::get();
    $orders = $user->orders;

    return view('orders.create', compact('products', 'orders', 'user'));
}

ОБНОВИТЬ

@alan ответ правильный, но я уверен ...

Я все еще получаю сообщение «Свойство [pivot] не существует в этом экземпляре коллекции» всякий раз, когда я пытаюсь запустить итерацию.

Концепция итерации внутри итерации в этом случае меня сбивает с толку.

Я не могу представить себе, как Laravel обрабатывает pivot-соединение. В tinker, когда я загружаю только таблицу Product, столбца qty нет. (Это имеет смысл, потому что это находится в сводной таблице). Это также объясняет эту новую ошибку.

Должен ли я делать что-то в этом роде? :

поменял create.blade.php

@foreach ($products as $product)
 {{ Form::text('qty', $product->orders->pivot->qty }}

OrderController.php

$user = Auth::user();
$orders = $user->orders;
$products= []; #pass products to view as an array
$p = $orders->products; #this relationship brings in pivot data? 
foreach ($p as $orders) {
   #would I then somehow pass just this qty here?
}

Проблема в том, что я всегда получаю сообщение об ошибке «Свойство не существует», будь то «продукты», «заказы» или «сводка».

Похоже, что $ products - это коллекция, а заказы определяются как отношения для отдельного продукта. Вам нужно сначала пройтись по продуктам. Тогда вы сможете получить из него доступ к заказам отдельного продукта.

Alan Perez 07.12.2018 22:41

@ Алан, я думаю, что теперь понимаю ошибку. В этой коллекции нет «заказов», потому что я определяю «$ products» только как данные из таблицы продуктов. (В настоящее время я не создаю никаких ассоциаций, которые вводят сводные данные). Таким образом, «-> заказы» создают своего рода взаимно-однозначные отношения, которые можно повторять, только если я работаю в более крупной итерации, которая приносит это сводные данные? Здесь есть некая концепция, ускользающая от меня.

sgt_disco 07.12.2018 23:18
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Оживление вашего приложения Laravel: Понимание режима обслуживания
Оживление вашего приложения Laravel: Понимание режима обслуживания
Здравствуйте, разработчики! В сегодняшней статье мы рассмотрим важный аспект управления приложениями, который часто упускается из виду в суете...
Коллекции в Laravel более простым способом
Коллекции в Laravel более простым способом
Привет, читатели, сегодня мы узнаем о коллекциях. В Laravel коллекции - это способ манипулировать массивами и играть с массивами данных. Благодаря...
Поиск нового уровня в Laravel с помощью MeiliSearch и Scout
Поиск нового уровня в Laravel с помощью MeiliSearch и Scout
Laravel Scout - это популярный пакет, который предоставляет простой и удобный способ добавить полнотекстовый поиск в ваше приложение Laravel. Он...
Освоение архитектуры микросервисов с Laravel: Лучшие практики, преимущества и советы для разработчиков
Освоение архитектуры микросервисов с Laravel: Лучшие практики, преимущества и советы для разработчиков
В последние годы архитектура микросервисов приобрела популярность как способ построения масштабируемых и гибких приложений. Laravel , популярный PHP...
Как построить CRUD-приложение в Laravel
Как построить CRUD-приложение в Laravel
Laravel - это популярный PHP-фреймворк, который позволяет быстро и легко создавать веб-приложения. Одной из наиболее распространенных задач в...
1
2
1 509
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Это должно сработать. Вы пытались получить доступ к свойству orders в переменной $ products, которая является коллекцией Laravel (метод get в модели возвращает коллекцию). Поэтому вместо этого вы просто перебираете продукты и получаете доступ к сводной таблице из отдельной модели продукта.

@foreach ($products as $product)

# Order inputs are here

{{ Form::text('qty', $product->orders->pivot->qty, [
                          'type' => 'tel',
                            'min' => 0,
                            'max' => 20,
                            'step' => 1,
                            'placeholder' => '0',
                            'class' => 'meal'
                            ]) }}
@endforeach

Обновлять: На самом деле в этом есть смысл. Запись в сводной таблице определяет связь между заказом и продуктом. Итак, чтобы получить доступ к записи в сводной таблице, вы должны получить доступ к продукту или заказу из его взаимосвязи. Я бы так и поступил.

OrderController.php

$user = Auth::user();
$user->load("orders.products"); // eager load relationship to avoid N+1 problem
$orders = $user->orders;
return view('orders.create', compact('orders', 'user'));

create.blade.php

@foreach ($orders as $order)
    @foreach ($order->products as $product)


    {{ Form::text('qty', $product->pivot->qty, [
                          'type' => 'tel',
                            'min' => 0,
                            'max' => 20,
                            'step' => 1,
                            'placeholder' => '0',
                            'class' => 'meal'
                            ]) }}
     @endforeach
@endforeach

Некоторые ресурсы:

Нетерпеливая загрузка

Отношения многие ко многим

Кажется, я все еще что-то упускаю в своих попытках сделать эту новую итерацию. Я обновил вопрос по этому поводу.

sgt_disco 08.12.2018 01:34

Хорошо, теперь это имеет смысл. Спасибо.

sgt_disco 08.12.2018 02:56

Другие вопросы по теме