Use blade in blade - php

In my database I save texts that contains blade markup like:
Hello {!! $name !!} how are you today.
I pass this text to my email template in a variable $text. In the email I use {!! $text !!} to get the text in the mail. However when the email is send it shows the {!! signs instead of the variable (which is also passed).
How can I save blade markup in my database and pass it to my code where it needs to replace {!! something !!} with the right variable?
My mail function.
$email = $order->email;
$name = $order->billingname;
//The text From the database.
$emailText = Email::findOrFail(5);
$mailtext = $emailText->text;
Mail::send('emails.tracktrace', ['text'=>$mailtext'email' => $email, 'name' => $name],
function ($m) use ($code, $email, $name) {
$m->from('info#domain.com', 'domain');
$m->to($email, $name)->subject('Track your package!');
});
Update
I've got a workaround where i do:
$mailtext = str_replace('[name]', $name, $mailtext);
this way the user can use [name], I would still like to know how to use it with blade only.

You can't have a blade-string to compiled PHP code without rendering it at the first place. You should try your custom rendering class or invoke Blade.
public function send()
{
$emailText = Email::findOrFail(5);
$name = $order->billingname;
$mailtext = \Blade::compileString($emailText->text);
ob_start();
eval("?> $mailtext <?php");
$mailtext = ob_get_clean();
Mail::send('emails.tracktrace', [
'text' => $mailtext,
'email' => $email,
'name' => $name
],
function ($m) use ($code, $email, $name) {
$m->from('info#domain.com', 'domain');
$m->to($email, $name)->subject('Track your package!');
});
}
However it's not safe as there is an eval. [Tested in Laravel 5.1]
Also there are some well written packages out there for this specific purpose, like StringBladeCompiler v3

I have used the email like below, all the dynamic variables to be replaced are like '{{ $name }}' in the email template.
I created a data array and used it directly with the mail library. This way you can replace multiple dynamic variables in mail template on the go.
You need to keep your text in the email template and use dynamic vales from database.
If your text for the email is dynamic and comes from database, you can use the text in place of the email template in the function and pass $data variables array to replace them all in one go.
$data = array('name' => $customer->Name, 'InvoiceID' => $dueinvoice["InvoiceNumber"],'AmountDue' => $dueinvoice["AmountDue"],'DueDate' => $duedate ,'CurrencyCode' => $dueinvoice["CurrencyCode"]);
\Mail::queue('emails.DueDateNotification',$data, function($message) use($customer)
{
$message->subject('DueDate Notification');
$message->to($customer->EmailAddress);
});
Another thing is try to use the 'queue' function for mail as its reduces load and add the email to laravel email queue and sent one by one
Hope this helps you :)

Related

Symfony | Form | Mail

I've got problem with Symfony and I hope you would help me :)
I created a Form, which takes data from user (email, name, message) and then it saves data in database. Everything works fine but i also want to send e-mail with this data.
I want to use mail function mail(to,subject,message,headers,parameters);.
My Controller class looks like:
public function ContactFormAction(Request $request){
$post = new ContactForm();
$form = $this->createFormBuilder($post)
->setMethod('POST')
->add('email','text',['label' => 'Adres e-mail'])
->add('name','text', ['label' => 'Imię'])
->add('message','text', ['label' => 'Wiadomość'])
->add('save','submit', ['label' => 'Wyślij'])
->getForm();
$form->handleRequest($request);
if ($form->isSubmitted()) {
$post = $form->getData();
$em = $this->getDoctrine()->getManager();
$em->persist($post);
$em->flush();
$message=''; //thats my problem
mail('example#example.pl', 'Subject', $message);
return $this->redirectToRoute('onas');
}
return $this->render('default/aboutus.html.twig', ['form' => $form->createView()]);
}
My Problem is: how should the $message variable looks like if I want to get this data from user (from a form on my webpage).
Thanks a lot for all your answers :)
Not sure that I follow, but, you want to send plain text using user's input just do $message = $post->getMessage(); and pass it on to mail. Is that the issue?
E-mail are, by default, sent in text/plain encoding, so you won't be able to use HTML. Personally, I prefer to format it a little better than old-plain-text. To achieve this, I usually create a Twig template, pass the input data to it and render what I need. That template could contain some HTML which could enhance the email's visual look.

how to replace text with another similar to mail merge?

I am working in Magento, and i have developed a module to send text messages to customers. In the settings of the module, the admin can set the message that will be sent to the customer. I'm trying to add a features that will allow the replacement of texts with data from my database.
for example, i currently have the following code that fetches the saved settings for the body of the text message:
$body = $settings['sms_notification_message'];
The message that is fetched looks like this:
Dear {{firstname}},
your order ({{ordernumber}}) has been shipped.
tracking#: {(trackingnumber}}
Thanks for your business!
{{storename}}
The goal is to have the module replace the variables in "{{ }}" with the customer and store information.
Unfortunately, i'm unable to figure out how to make it replace the information before sending the message. It is currently being send as is.
The easiest way to do it would be to use str_replace, like so:
// Set up the message
$message = <<< MESSAGE
Dear {{firstname}},
your order ({{ordernumber}}) has been shipped.
tracking#: {{trackingnumber}}
Thanks for your business!
{{storename}}
MESSAGE;
// Assign the values in an associative array
$values = [
'firstname' => 'firstnamevalue',
'ordernumber' => 'ordernumbervalue',
'trackingnumber' => 'trackingnumbervalue',
'storename' => 'storenamevalue'
];
// Create arrays $target indicating the value to change
$targets = [];
foreach ($values as $k => $v) {
$targets[] = '{{'.$k.'}}';
}
// Use str_replace to perform the substitution
echo str_replace($targets,$values,$message);

Passing form input data to the mail view - Laravel

I am making a form which will send an email.
Currently its a generic blade form which points to /admin/newemail
I have my route and for testing the mail is sent from that route:
Route::get('admin/newemail', function()
{
$email = 'email#hotmail.com';
$data = Input::all();
Mail::send('emails.newemail', $data, function($message) use ($email){
// $message details
});
});
And then to trial this I tried in my view: (there is a field name of 'subject' in my form)
echo Input::get("subject");
I actually have two issues. (I am using the log driver)
1) The email is not showing in the log, its just showing [] []
2) The data is not showing neither and its blank.
If I simply have:
echo "hello!";
Then the log will output hello, likewise If i change my mail data variable to an array:
$data = array('test' => 'test');
Then in the view:
echo $test;
That also works. But I want it to take my inputs from my form.
Here, Try this:
Mail::send('emails.welcome', array('key' => 'value'), function($message)
{
$message->to('foo#example.com', 'John Smith')->subject('Welcome!');
});
Here, key will be any name which you want to give and value will be the data you want to assign, it could be form data or could be from database.
Now, after doing that create a file in your views/emails as welcome.blade.php and to fetch the value passed through mail function use:
{{ $key }}
Above is the blade format to represent data.
For more info on mail, visit this, and for blade templates go here.
See, if that helps you.
Mail::send('emails.welcome', Input::all(), function($message)
{
$message->to('foo#example.com', 'John Smith')->subject('Welcome!');
});
and in your view you have
{{Input::get("subject")}}
This is what i use myself and it works perfectly.

Passed data to custom email view is not avaliable

As you know, send a email via laravel is so simple as:
// setting data
$data = array(
'band' => 'Kings of leon'
);
// send email
\Mail::send('emails.activation', $data , function($message)
{
$message->to('foo#example.com', 'John Smith')->subject('Welcome!');
});
Then in /app/views/emails/activation.blade.php view could contains a not complicated structure:
My fav band is {{ $band }}. Here a logo:
<img src="{{ $message->embed('/img/logo_small.png') }}" alt="">
Views path:
/app/config/views.php
'paths' => array(DIR.'/../views', ),
Everything above works like a champ. However, if you change the email view from emails.activation to another one belonging in different path from default cause two problem:
The $message var is not longer available in the view
The $data arg is not passed to the view.
So, lets see:
// setting data
$data = array(
'band' => 'Kings of leon'
);
// send email using different view outside of default path
\Mail::send('theme::views.emails.activation', $data , function($message)
{
$message->to('foo#example.com', 'John Smith')->subject('Welcome!');
});
The view is successfully found, but when it is compiled throws two exception stating undefined var: $message and undefined var: $band.
am I missing an extra-configuration? or is it a bug? Thank you.
update
After an exhaustive revision, the problem resided in a calling of the email view twice in the same controller, for example:
$stringLocation = \Theme::getViewLocation('emails.activation');
... more stuff here
\Mail::send($stringLocation, $data , function($message)
{
$message->to('foo#example.com', 'John Smith')->subject('Welcome!');
});
So, calling getViewLocation() compiled the view, and of course, the data were not present at this exact point. My bad was believe that the error was in \Mail::send line than getViewLocation.

Phalcon form sanitize

Is there a way in which one can filter data that is auto-completed in a form generated by VOLT.
Consider the login form: Email/password.
When I edit the HTML (in the broser) and send the email as an array ('name="email[]") I can sanitize it in PHP and 'cast' as en email:
$loginEmail = $this->request->getPost("email",'string');
$loginEmail = $this->filter->sanitize($loginEmail, "email");
in order to prevent other attacks.
But when making the email field an array VOLT generates an error:
"Notice: Array to string conversion in ..."
VOLT form values are populated automatically...
I know I should disable NOTICES in production but still...
How can I treat this by using VOLT?
EDIT
Template sample:
{{ text_field('id':"email","class":"form-control", "size": 32,"placeholder":'Email address') }}
After a var_dump and setting the email string through validation I get at a certain point:
protected '_viewParams' =>
array (size=5)
'title' => string 'Test' (length=5)
'showSlider' => boolean true
'hideUnlogged' => boolean true
'user' => null
'email' => boolean false
BUT the variables are sent to VOLT in an upper layer because it is still set as an ARRAY.
The only viable solution is to make an object or something and get from a config what validation rules to apply to forms (by name) and rewrite the post variable in public/index.php something like this:
if(isset($_POST['email']))
{
$_POST['email'] = filter_var($_POST['email'], FILTER_VALIDATE_EMAIL);
}
If anyone has a better solution in which this can be done in a controller rather that this or in a service with event handlers...
You can do anything you wish by implementing a custom filter and doing a proper conversion from array to string.
$filter = new \Phalcon\Filter();
//Using an anonymous function
$filter->add('superSanitisedString', function($value) {
if (is_array($value)) {
$value = empty($value) ? '' : reset($value);
}
return (string) $value;
});
//Sanitize with the "superSanitisedString" filter
$filtered = $filter->sanitize($possibleArray, "superSanitisedString");
But… don't bend the stick too much – this is a clear validation job and then sanitisation. Check that the value is a string, if not – ask to provide one. It's easier and smarter to protect your app from invalid inputs than from idiots who provide that input :)
Edit:
You can use a custom volt filter which can be added as a service, implement a class with a static method to return the sanitized value and use it in the template.

Categories