首页 > 解决方案 > LARAVEL 7:ErrorException 未定义的索引

问题描述

尽管索引被定义为同一数组中的其他索引,但我在电子邮件 html 模板中使用数组索引时遇到错误。

使用电子邮件模板中的犯罪索引时会出现问题。至于我不使用它,事情如下所述。

事情从发送电子邮件的控制器功能开始

   public function sendToOne(Request $request){
        if ($request->ajax()) {
            $this->validate($request, [
            'user_id'=>'required',
            'infoletter_id'=>'required'
            ]);
            Log::debug('entering sendToOne with user_id '.$request->user_id);
            $infoletter=Infoletter::find($request->infoletter_id);
            $user=User::find( $request->user_id);
            $sender=User::find(1);
            $details=[
                'title'=>$infoletter->title,
                'body'=>$infoletter->body,
                'sender'=>$sender,
                'user'=>$user,
            ];
            $job=(new SendEmailJob($details))->delay($request->delay);
            dispatch($job);
            $duree=$request->delay;
            $minutes=intval(($duree % 3600) / 60);
            $secondes=intval((($duree % 3600) % 60));
            return response()->json(['success'=>'Envoi de l\'infolettre programmé pour '.$user->firstname.' '.$user->familyname .'. L\'envoi aura lieu dans '.$minutes.' minutes et '.$secondes.' secondes.']);
        }
        else{ return 'request is not ajax';}
    }

所涉及的数组是 $details 我在其中传递了一个发件人(用户类)以及一个用户(用户类也是)邮件的收件人。SendEmailJob 使用 $details 数组作为参数调用。

然后是 SendEmailJob

<?php

namespace App\Jobs;

use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use App\Mail\InfoletterMail;
use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Facades\Log;
use Carbon\carbon;

class SendEmailJob implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    protected $details;
    /**
     * Create a new job instance.
     *
     * @return void
     */
    public function __construct($details)
    {
        $this->details=$details;
    }
    /**
     * Execute the job.
     *
     * @return void
     */
    public function handle()
    {  
             Log::debug('entering function handle in SendEmailJob');
             Log::debug($this->details);
            $email = new InfoletterMail($this->details);           
            Mail::to($this->details['user']->email)->send($email);              
     }  
}

它的构造函数接收 details 数组作为参数,并在句柄函数中实例化一个 InfoletterMail 并传递相同的数组。请注意,在这个阶段,假设我不使用犯罪索引来防止错误,日志 (Log::debug($this->details);) 显示存在“发件人”索引。

然后是 InfoletterMail

<?php

namespace App\Mail;

use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Mail\Mailable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Facades\Log;

class InfoletterMail extends Mailable
{
    use Queueable, SerializesModels;
    protected $details;
    /**
     * Create a new message instance.
     *
     * @return void
     */
    public function __construct($details)
    {
        $this->details=$details;
    }

    /**
     * Build the message.
     *
     * @return $this
     */
    public function build()

    {
        Log::debug('entering build in InfoletterMail');
        Log::debug($this->details);
        return $this->view('emails.infoletter')->with('details',$this->details);
    }
}

在这个阶段,假设我不使用犯罪索引来防止错误,日志 (Log::debug($this->details);) 显示“发件人”索引存在且正确。

然后是电子邮件的视图(emails.infoletter),假设我使用了犯罪索引('sender')

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>
<body>
    @include('emails.inc.intro')
   <p style="text-align: center;"> Bonjour {{$details['user']->firstname}} {{$details['user']->familyname}} ,</p>
    <div>
        {{$details['body']}}
    </div>
   <p style="text-align: center;"> Bien à vous,</p>
   <p style="text-align: center;">{{$details['sender']->firstname}} {{$details['sender']->familyname}}</p>

</body>
</html>

然后是错误

未定义索引:发件人(查看:/ORIGINAL-P1/LARAVEL/denentzat/resources/views/emails/infoletter.blade.php)

我无法确定错误来自何处,我需要帮助。

标签: phplaravelemail

解决方案


我最终成功了。这有点难以解释,因此我会尽力说清楚。

事实上,电子邮件是从一个查看页面发送的,在发送之前它会呈现给发件人。

用户有不同的按钮,一个发送给所有用户,另一个发送给限制数量的用户等。

我是否打算延迟发送电子邮件?我使用 jquery 脚本来遍历用户。在每个循环中,我对控制器中的 sendToOne 操作执行 ajax 请求。控制器响应实例化作业 (SendMailJob) 的 ajax 请求,该作业本身实例化使用电子邮件模板的可邮寄 (InfoletterMail),参数 $details 是一个包含“发件人”索引的数组。

如果我之前没有在开头提到的视图中使用相同的电子邮件模板来显示邮件的预览,但忘记将“发件人”索引添加到传递给它的 $details 中,那么所有这些都是正确的。事实上,错误不是由邮件本身造成的,而是由预览造成的。对于那些感兴趣的人,这里是这个视图,其中包含创建预览的行以及我忘记添加“发件人”索引的位置。

$emailview=view('emails.infoletter')->with('details', ['title'=>$infoletter->title, 'body'=>$infoletter->body,'user'=>$fakeuser,'sender'=>auth()->user()]);
{!!html_entity_decode($emailview)!!}

视图代码

@extends('layouts.bare')


@section('content')

<div class="container mt-4 my-content">
    <div id='messages'>

    </div>  
 

    <div class="d-flex">
                    <a href="/infoletters" class="my-button">Retourner à la liste</a>
                    <a href="" class="my-button">Modifier</a>
                    
            
                <div>
                    {{--below a form with a submit button that will be intercepted by the java script at the bottom of page--}}   
                    {{--The script will trigger ajax requests / one per user--}}
                    {!! Form::open([]) !!}
                        <div class="row post-option-background">
                            <div class="col-md-12" >
                                {{ Form::hidden('infoletter_id', $infoletter->id) }}{{--permetra de retrouver title et body--}}
                                {{ Form::hidden('users', $users )}}{{--permetra de boucler dans jquery--}}
                            
                            </div>
                        </div>
                        {{Form::submit('Envoyer a tous',['class'=>'my-button btn  btn-submit btn-to-all','id'=>'btn-to-all'])}}

                    {!! Form::close() !!}
                </div>
                <div>
                    {{--below a form with a submit button that will be intercepted by the java script at the bottom of page--}}   
                    {{--The script will trigger ajax requests / one per user--}}
                    {!! Form::open([]) !!}
                        <div class="row post-option-background">
                            <div class="col-md-12" >
                                {{ Form::hidden('infoletter_id', $infoletter->id) }}{{--permetra de retrouver title et body--}}
                                {{ Form::hidden('users', $users )}}{{--permetra de boucler dans jquery--}}
                            
                            </div>
                        </div>
                        {{Form::submit('Envoyer au CA',['class'=>'my-button btn  btn-submit btn-to-CA','id'=>'btn-to-CA'])}}

                    {!! Form::close() !!}
                </div>
                <div>
                    {{--below a form with a submit button that will be intercepted by the java script at the bottom of page--}}   
                    {{--The script will trigger ajax requests / one per user--}}
                    {!! Form::open([]) !!}
                        <div class="row post-option-background">
                            <div class="col-md-12" >
                                {{ Form::hidden('infoletter_id', $infoletter->id) }}{{--permetra de retrouver title et body--}}
                                {{ Form::hidden('user_id',  Auth::user()->id )}}
                            
                            </div>
                        </div>
                        {{Form::submit('Envoyer à moi-même (test)',['class'=>'my-button btn  btn-submit btn-to-me','id'=>'btn-to-me'])}}

                    {!! Form::close() !!}
                </div>  

    </div>

</div>  
                
<div class="container mt-4 my-content"> 
    
    

    <div class="my-post-body">
        {!!html_entity_decode($emailview)!!}
        
    </div>      
</div>  

<script type="text/javascript">
    $( document ).ready(function() {
        //$('#messages').append('<h1> Le java scirpt fonctionne</h1>');
        $.ajaxSetup({
            headers: {
                'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content'),
                
            }
        });

        $('#btn-to-all').click(function(e){ 
            e.preventDefault();
            var infoletter_id = $("input[name=infoletter_id]").val();
            var users = $("input[name=users]").val();
            parsed_users=JSON.parse(users);
            var i=0;
            var url='{{ url('infoletters/sendToOne') }}';
            delay=0;
            for (i=0; i<parsed_users.length;i++){
                $.ajax({
                    type:'POST',
                    url:url,
                    data:{user_id:parsed_users[i].id,infoletter_id:infoletter_id,delay:delay},
                    dataType: 'json',
                    success:function(data){
                        $('#messages').prepend('<div class="comments-message" style="margin-bottom:15px;padding:5px;background-color: green; color: white; margin-top:5px;">'+data['success']+'!.</div>');
                    }
                });
                delay=delay+3;
            }   
        });
        $('#btn-to-CA').click(function(e){  
            e.preventDefault();
            var CAMembers=[23,1,4,12,55,19,7,17,18,10,25,5,24];
            var infoletter_id = $("input[name=infoletter_id]").val();
            var users = $("input[name=users]").val();
            parsed_users=JSON.parse(users);
            var i=0;
            var url='{{ url('infoletters/sendToOne') }}';
            delay=0;
            for (i=0; i<parsed_users.length;i++){
                if(CAMembers.includes(parsed_users[i].id)){
                    $.ajax({
                        type:'POST',
                        url:url,
                        data:{user_id:parsed_users[i].id,infoletter_id:infoletter_id,delay:delay},
                        dataType: 'json',
                        success:function(data){
                            $('#messages').prepend('<div class="comments-message" style="margin-bottom:15px;padding:5px;background-color: green; color: white; margin-top:5px;">'+data['success']+'!.</div>');
                        }
                    });
                delay=delay+3;

                }
            }   
        });

        $('#btn-to-me').click(function(e){  
            $('#messages').prepend('<div class="comments-message" style="margin-bottom:15px;padding:5px;background-color: green; color: white; margin-top:5px;">Le script fonctionne.</div>');
            e.preventDefault();
            var infoletter_id = $("input[name=infoletter_id]").val();
            var user_id = $("input[name=user_id]").val();
            var url='{{ url('infoletters/sendToOne') }}';
            $.ajax({
                    type:'POST',
                    url:url,
                    data:{user_id:user_id,infoletter_id:infoletter_id},
                    dataType: 'json',
                    success:function(data){
                        $('#messages').prepend('<div class="comments-message" style="margin-bottom:15px;padding:5px;background-color: green; color: white; margin-top:5px;">'+data['success']+'!.</div>');
                    }
                });
                
        });

        
    });
    </script>
@endsection

以及将另一个 $details 传递给视图的控制器操作,这就是问题的原因

  public function view($id)
    {
        //we empty the job tables
        Job::truncate();
        Failed_job::truncate();
        Log::emergency('Entering infoletter@view');
        Log::debug('Entering infoletter@view');
        $infoletter=Infoletter::find($id);
        $users=User::all();
     
        $fakeuser=new User();// to simulate the user in the presentation of the mail in the view
        $fakeuser->firstname='Prénom';
        $fakeuser->familyname='Fake name';
        $emailview=view('emails.infoletter')->with('details', ['title'=>$infoletter->title, 'body'=>$infoletter->body,'user'=>$fakeuser,'sender'=>auth()->user()]);
        return view('infoletters.view', compact('infoletter', 'users', 'emailview'));//here we pass a fake email view as example to bee shown
    }

推荐阅读