I have created a mailable php artisan make:mail SendInEmail
class SendInEmail extends Mailable
{
use Queueable, SerializesModels;
public $email;
public $sub;
public $emailcontent;
/**
* Create a new message instance.
*
* #return void
*/
public function __construct($email, $sub, $emailcontent)
{
$this->email = $email;
$this->sub = $sub;
$this->emailcontent = $emailcontent;
}
/**
* Build the message.
*
* #return $this
*/
public function build()
{
return $this->subject($sub)->view('emails.sendemail');
}
}
In the build function I am passing the $sub variable, which comes from the controller, but it gives me an error:
Undefined variable: sub
When I use this:
return $this->subject('Some subject')->view('emails.sendemail');
It works fine.
P.S I did some research and found that I need use function to pass the subject variable (some anonymous function magic) (Not sure how to do that with mailables)
You're using the wrong variable, so change it to $this->sub:
return $this->subject($this->sub)->view('emails.sendemail');
Related
Here is the piece of code. My idea is that each email comes out with one of the values/entry from one of my tables.
public function __construct($siniestro)
{
$this->siniestro = $siniestro;
$this->subject = {{ $siniestro->siniestro }};
}
[from this place I want to get my subject][1]
[1]: https://i.stack.imgur.com/D0PNO.png
this is all the code of my mailable
class ContactanosMailable extends Mailable
{
use Queueable, SerializesModels;
$this->subject = $siniestro->siniestro;
public $siniestro;
/**
* Create a new message instance.
*
* #return void
*/
public function __construct($siniestro)
{
$this->siniestro = $siniestro;
}
/**
* Build the message.
*
* #return $this
*/
public function build()
{
return $this->view('emails.contactanos');
}
}
If I can add something else just let me know, and I will.
I hope this can reach, it's getting complicated
I would do it like that :
class ContactanosMailable extends Mailable
{
use Queueable, SerializesModels;
public $siniestro;
/**
* Create a new message instance.
*
* #return void
*/
public function __construct($siniestro)
{
$this->siniestro = $siniestro;
// set the subject property
$this->subject = $siniestro->siniestro;
// or use the subject method
$this->subject($siniestro->siniestro);
}
/**
* Build the message.
*
* #return $this
*/
public function build()
{
return $this->view('emails.contactanos');
}
}
using the subject() method looks cleaner but both works
public function build(){
$from_email = "test#mail.com";
$subject = "Account Request";
return $this->from($from_email)->subject($subject)->view('emails.contactanos')
;
}
I have a mailable class which I use to send an email to users, which works fine. I want to write some phpunit test to check if the mail is actually sent. Unfortunately, I couldn't find a good explanation in the documentation.
My mailable class:
class UserInvite extends Mailable
{
use Queueable, SerializesModels;
public $user;
public $inviteMessage;
/**
* Create a new message instance.
*
* #param User $user
* #param string $inviteMessage
*/
public function __construct(User $user, string $inviteMessage)
{
$this->user = $user;
$this->inviteMessage = $inviteMessage;
}
/**
* Build the message.
*
* #return $this
*/
public function build()
{
return $this->view('emails.mail');
}
}
Test:
/** #test */
public function it_sends_invite()
{
Mail::fake();
$user = factory(User::class)->create();
$inviteMessage = 'test';
Mail::assertSent(new UserInvite($user, $inviteMessage));
}
Error:
ErrorException: Object of class App\Mail\UserInvite could not be converted to string
Solution:
/** #test */
public function it_sends_invite()
{
Mail::fake();
$user = factory(User::class)->create();
Mail::to($user)->send(new UserInvite($user, 'message'));
Mail::assertSent(UserInvite::class);
}
When testing for sent mails, you don't pass a whole mailable instance. PHPUnit wouldn't be able to compare a full object anyway. Instead, you just pass the fully qualified class name:
// use App\Mail\UserInvite;
Mail::assertSent(UserInvite::class);
$created array contain email value and name and some more. return $this->view('emails.created'); works fine , but I want to make email sender be that $created->email.or my controller Mail::to('email')->from($created->email)->send(new Created($created)); like this. but two ways are not working. How can I approach, handle this variable array on my app\Mail\Created.php file? I need some helps.
class Created extends Mailable
{
use Queueable, SerializesModels;
/**
* The created instance.
*
* #var created
*/
public $created;
/**
* Create a new message instance.
*
* #return void
*/
public function __construct($created)
{
$this->created = $created;
}
/**
* Build the message.
*
* #return $this
*/
public function build()
{
return $this->from($created->email)->view('emails.created');
}
}
Change your build function with this and check. Also make sure you pass email parameter in your array.
public function build()
{
return $this->from($this->created->email)->view('emails.created');
}
I have a PHP script that write into consol some logs,erros etc.
I want to save all this information into a variable for sending an email at the end of its execution.
I know i can use obstart and co for doing that but I also want that during its execution that the logs appear in real time. So I don't think the output buffering is the solution for my problem but I don't see another solution.
Is there a way for doing that please ?
Thanks by advance
You will have to come up with some kind of custom logger that apart from outputing messages to console will also send an email on script shutdown. Something like this:
interface MailerInterface {
function send($recipient, $title, $body);
}
interface LoggerInterface {
function log($message);
}
class ConsoleLoggerWithMailer implements LoggerInterface {
/**
* #var string[]
*/
private $messages = array();
/**
* #var MailerInterface
*/
private $mailer;
/**
* #var string
*/
private $recipient;
public function __construct() {
register_shutdown_function(array($this, 'sendMessages'));
}
/**
* #param MailerInterface $mailer
* #param string $recipient
*/
public function setMailer(MailerInterface $mailer, $recipient) {
$this->mailer = $mailer;
$this->recipient = $recipient;
}
/**
* #return string[]
*/
public function getMessages() {
return $this->messages;
}
public function log($message) {
$this->messages[] = $message;
printf("%s\n", $message);
}
public function sendMessages() {
if ($this->mailer === null || count($this->messages) === 0)
return;
$this->mailer->send($this->recipient, 'log', implode("\n", $this->messages));
}
}
Usage example assuming you also created some Mailer class implementing MailerInterface:
$mailer = new Mailer();
$logger = new ConsoleLoggerWithMailer();
$logger->setMailer($mailer, "webmaster#example.com");
$logger->log("Starting...");
$logger->log("Doing...");
$logger->log("End");
I want to have a class that i can use it this way:
Thing::doThis()->doThat()->doImportantThing();
OR
Thing::doThat()->doImportantThing();
OR
Thing::doImportantThing();
But currently i can only use it this way:
$thing = new Thing();
$thing->doThis()->doThat()->doImportantThing();
What do i have to change in the class so i can use it the way i want? I already return a Thing instance in every function call.
I want to use that for a simple reason, imagine a mail class, in the constructor you define a default from and to, but you might want to change it, so you do Mail::setFrom()->send(). If you want to change the to, you use Mail::setTo()->send(). It just makes it easier to use if it's going to be used in different projects by different people.
I want by calling Mail::{something} to have like a constructor call and then run the {something} function.
You can do this
class Thing {
public static function __callStatic($name, $arguments){
$thing = new self;
return $thing->$name($arguments);
}
public function __call($name, $arguments){
return $this->$name($arguments);
}
private function doThis(){
echo 'this'.PHP_EOL;
return $this;
}
private function doThat(){
echo 'that'.PHP_EOL;
return $this;
}
private function doImportantThing(){
echo 'Important'.PHP_EOL;
return $this;
}
}
Thing::doThis()->doThat();
Thing::doThat()->doImportantThing();
It is a really ugly work-around, though. And it disables you to have private methods.
DEMO
One great thing for static methods is that they can work in object context, and can be called like this: $instance->staticMethod()
Here it is (even you get code completion in ide, and works as axpected as you want):
class Mail
{
public static $from;
public static $to;
public static $subject;
public static $message;
protected static $onlyInstance;
protected function __construct ()
{
// disable creation of public instances
}
protected static function getself()
{
if (static::$onlyInstance === null)
{
static::$onlyInstance = new Mail;
}
return static::$onlyInstance;
}
/**
* set from
* #param string $var
* #return \Mail
*/
public static function from($var)
{
static::$from = $var;
return static::getself();
}
/**
* set to
* #param string $var
* #return \Mail
*/
public static function to($var)
{
static::$to = $var;
return static::getself();
}
/**
* set subject
* #param string $var
* #return \Mail
*/
public static function subject($var)
{
static::$subject = $var;
return static::getself();
}
/**
* set message
* #param string $var
* #return \Mail
*/
public static function message($var)
{
static::$message = $var;
return static::getself();
}
public static function send()
{
echo "<pre><b>Hurrah mail sent</b>"
. "\nFrom:\t ".static::$from.""
. "\nTo:\t ".static::$to." "
. "\nSubject: ".static::$subject.""
. "\nMessage: ".static::$message;
echo "</pre>";
}
}
Example usage:
Mail::from('george#garcha')
->to('michel#tome')
->subject('hehe works')
->message('your welcome')
->send();
Output
Hurrah mail sent
From: george#garcha
To: michel#tome
Subject: hehe works
Message: your welcome
Example 2 (this also works):
Mail::from('george#garcha')
->to('michel#tome');
Mail::subject('hehe works')
->message('your welcome')
->send();