How to send parameter with try catch exception in yii2? - yii2

I have problem in sending email, looks like our server connection to mail server is unstable, sometimes it successfully sent, but sometimes it's not, it say ssl time out.
So my idea is catch timed out exception and insert in database then I can send later.
But I need to send few parameter with catch exception so I can insert database correctly.
So far what I want is something like this
try{
$message = Yii::$app->mail->compose();
if (Yii::$app->user->isGuest) {
$message->setFrom('from#domain.com');
} else {
$message->setFrom(Yii::$app->user->identity->email);
}
$message->setTo(Yii::$app->params['adminEmail'])
->setFrom(Yii::$app->params['adminEmail'])
->setTo("mymail#gmail.com")
->setSubject('Title 1')
->setHtmlBody("Hi, this is my content to check if registration email successfully sent")
->send();
$mail_from = "no-reply#myweb.com";
$mail_to = "customer#someweb.com";
$content = "here is content of email"
$other = "this other variable";
return 1;
}catch(\Swift_TransportException $e, $mail_from, $mail_to, $content, $other){
//if connection time out or something
$queue = new Queue;
$queue->mail_from = $mail_from;
$queue->mail_to = $mail_to;
$queue->content = $content;
$queue->other = $other;
$queue->fail_reason = $e->getMessage();
$queue->save()
}
but it give me undefined variable $mail_from, $mail_to, and etc
How I can fix my problem?
Thanks in advance.

To fix the undefined variable $mail_from, $mail_to, and etc error it's better to declare the variables outside the try block. Because you're declaring the variables at the end of the try, it fails before these variables are ever initialised.
$mail_from = "no-reply#myweb.com";
$mail_to = "customer#someweb.com";
$content = "here is content of email"
$other = "this other variable";
try {
$message = Yii::$app->mail->compose();
if (Yii::$app->user->isGuest) {
$message->setFrom('from#domain.com');
} else {
$message->setFrom(Yii::$app->user->identity->email);
}
$message->setTo(Yii::$app->params['adminEmail'])
->setFrom(Yii::$app->params['adminEmail'])
->setTo("mymail#gmail.com")
->setSubject('Title 1')
->setHtmlBody("Hi, this is my content to check if registration email successfully sent")
->send();
return 1;
} catch(\Swift_TransportException $e) {
//if connection time out or something
$queue = new Queue;
$queue->mail_from = $mail_from;
$queue->mail_to = $mail_to;
$queue->content = $content;
$queue->other = $other;
$queue->fail_reason = $e->getMessage();
$queue->save()
}
But there are more problems with this code. You're setting the from and to part multiple times. In the if/else you're calling setFrom and then again a few lines later. The same goes for setTo. The last call to the function will overrule the previous set value. So make sure you only call these functions once.

Related

backendError 500 (Bug in nextPageToken)

For some of the users iterating through the list of files started producing error 500 (backendError). Very few cases, but still.
Close investigation showed that sometimes after requesting a list of files strange nextPageToken was returned. Here is an example:
!!|~EAIaggELEgA6egpg96K5Moz_____f_8AAP__AAD_7qNsfh7Iy8rJyMnDy8bLytHI0bDOy6W4rZ6wvqmc_wAA__8A_v_-f_8A_wDuo2x-HsjLysnIyc7LxsvK0cjRsM7LpbitnrC-qZz_AP_-EJzHASFVhA7Kvoa7STkAAAAAc81GXUgBDEAAIgsJ4YZTXBEABAAgBg
This part right here "!!|~" (start of the string) was causing the errors. Removing it fixed the issue.
There were not so many cases. But still, can this be a bug?
UPDATE 1.
Here is a code sample using Google APIs Client Library for PHP. But the error reproduced only for few users. So there are not a lot of chances of reproducing it.
$client = new Google_Client( );
// ... setup client
$driveService = new Google_DriveService( $client );
$parameters = array();
try{
do{
$files = $driveService->files->listFiles( $parameters );
$parameters['pageToken'] = $files->nextPageToken;
// ...
} while( $parameters['pageToken'] );
}
catch( Google_ServiceException $exception ) {
// ... handle exception
}
}

Clean HTML output in ZF2

Is it possible to fomat(clean) output of html in Zend Framework 2? Right now it outputs without proper newline characters and tabs.
I know about this method:
$dom = new DOMDocument();
$dom->preserveWhiteSpace = FALSE;
$dom->loadHTML($html);
$dom->formatOutput = TRUE;
echo $dom->saveHTML();
But I do not understand where I could intercept output in ZF2. Any help would be appreciated.
Right now all the html code is created in layout.
You can attach a listener to the "finish" mvc-event ( http://framework.zend.com/manual/2.1/en/modules/zend.mvc.mvc-event.html ) and have it clean up the response before sending it out.
In your application's module.php add something like the following to the Module class.
public function onBootstrap(MvcEvent $e)
{
$eventManager = $e->getApplication()->getEventManager();
$eventManager->attach(MvcEvent::EVENT_FINISH, function(MvcEvent $e){
$content = $e->getResponse()->getContent();
$cleancontent = clean_up_html(content); // clean_up_html() not provided
$e->getResponse()->setContent($cleancontent);
});
}

PHP-EWS No Data Received Message

I just downloaded PHP-EWS, installed following the README instructions, and spun up a script to test out its functionalities. When I try running the script in my browser, I get the following message:
I get the same message when I supply a login I know is invalid. It seems I am connecting to my Exchange server, but it's not recognizing the credentials I provide.
Here is the script I am using
<?php
function __autoload($className)
{
$className = str_replace('_','/', $className);
$sFileName = $className . '.php';
if (file_exists($sFileName) && !class_exists($className))
{
require_once $sFileName;
}
// If the above if fails, you're program will terminate, there is no way to catch this.
}
include("ExchangeWebServices.php");
$host = "https://myexchange/EWS/Services.wsdl";
$username = "myusername#mydomain.com";
$password = "mypassword";
$ews = new ExchangeWebServices($host, $username, $password);
$request = new EWSType_FindItemType();
$request->ItemShape = new EWSType_ItemResponseShapeType();
$request->ItemShape->BaseShape = EWSType_DefaultShapeNamesType::DEFAULT_PROPERTIES;
$request->Traversal = EWSType_ItemQueryTraversalType::SHALLOW;
$request->ParentFolderIds = new EWSType_NonEmptyArrayOfBaseFolderIdsType();
$request->ParentFolderIds->DistinguishedFolderId = new EWSType_DistinguishedFolderIdType();
$request->ParentFolderIds->DistinguishedFolderId->Id = EWSType_DistinguishedFolderIdNameType::INBOX;
// sort order
$request->SortOrder = new EWSType_NonEmptyArrayOfFieldOrdersType();
$request->SortOrder->FieldOrder = array();
$order = new EWSType_FieldOrderType();
// sorts mails so that oldest appear first
// more field uri definitions can be found from types.xsd (look for UnindexedFieldURIType)
$order->FieldURI->FieldURI = 'item:DateTimeReceived';
$order->Order = 'Ascending';
$request->SortOrder->FieldOrder[] = $order;
$response = $ews->FindItem($request);
echo '<pre>'.print_r($response, true).'</pre>';
?>
Try testing your access by:
Hitting the server url directly: https://YOUREXCHANGESERVER/EWS/Services.wsdl
You should be prompted for credentials. After you enter your credentials you will be presented with the WSDL definition. If it does not present you a WSDL definition that looks like the example below then check with your administrator on credentials or if there are any firewall blocks put in place.
Example (Partial response):
<wsdl:definitions targetNamespace="http://schemas.microsoft.com/exchange/services /2006/messages"><wsdl:types><xs:schema><xs:import namespace="http://schemas.microsoft.com/exchange/services/2006/messages" schemaLocation="messages.xsd"/></xs:schema></wsdl:types>
A great tool I use in analyzing web services is: SOAP-UI by SmartBear

How to Pass a PHP Variable to a MySql Query to Create an Excel Document Download

I am trying to pass a variable from one PHP page to another PHP page, which will trigger an Excel download. However, I cannot figure out how to pass the variable and still have the download trigger. I understand that my PHP page which creates the Excel file cannot have any variables passed to it, or the download will not trigger.
For example, I would like to do the following (very simple example):
variable.php
<?php
$date = '2012-02-15';
echo '<input type="text" id="date" value="'.$date.'"/>';
echo '<span onclick="excelDownload()">Click</span>';
?>
passing.js
function excelDownload(str)
{
Ajax...
var date = document.getElementById('date').value;
var queryString = "?date=" + date;
xmlhttp.open("GET", "excel.php" + queryString, true);
Ajax....
}
excel.php
<?php
Connect to database...
$date = $_GET['date'];
$file = "Names: ";
$result = mysql_query("SELECT * FROM Something WHERE date_field = '$date'");
$data = mysql_fetch_array($result);
$file.= $data['names']." ";
header("Content-type: application/octet-stream");
header("Content-Disposition: attachment; filename=names.xls");
header("Pragma: no-cache");
header("Expires: 0");
print $file;
?>
Unfortunately, the $_GET[date'] variable causes the excel.php to not download. I have been able to get away with writing static MySql queries within the excel.php page, so I do not have to pass any variables. However, I now have the need to create dynamic excel downloads, but I am not strong enough in php to figure out my options. On a side note, I use Ajax and do not utilize "submit". Will this be a problem?
I figured out my problem and wanted to share my findings to close out this question. Basically, I should have been more detailed in my question. My Ajax function needed some tweaking so that the variable would pass and allow the headers to trigger a download.
I was using the following in my Ajax function:
Ajax...
{
if (xmlhttp.readyState == 4)
{
//nothing to allow download to trigger
}
}
var date = document.getElementById('date').value;
var queryString = "?date=" + date;
xmlhttp.open("GET", "excel.php" + queryString, true):
xmlhttp.send(null);
However, I should have used this:
Ajax...
{
if (xmlhttp.readyState == 4)
{
window.location = "excel.php" + queryString;
}
}
var date = document.getElementById('date').value;
var queryString = "?date=" + date;
xmlhttp.open("GET", "excel.php" + queryString, true):
xmlhttp.send(null);
While I was thinking my problem had to do with output before header(), the real issue was passing the variable.

When modifying linq-to-sql commandtext, should the connection be closed?

I'm modifying the commandtext of linq-to-sql to force it to use nolock, like this...
if (db.Connection.State == System.Data.ConnectionState.Closed)
db.Connection.Open();
var cmd = db.GetCommand(db.Customers.Where(p => p.ID == 1));
cmd.CommandText = cmd.CommandText.Replace("[Customers] AS [t0]", "[Customers] AS [t0] WITH (NOLOCK)");
var results = db.Translate(cmd.ExecuteReader());
It's an MVC application, so the datacontext is in the base controller, and may have been used before this code, and more importantly, after. Should I be closing the connection in this routine? Or not at all? Or only if I opened it here?
Update:
I'm now using the more general function (in the DataContext class) to modify the commandtext, and closing the connection if it was opened here. And the open has been moved down to the ExecuteReader. So far it has been working and reducing the sporadic deadlock issues. The results do not have to be right-up-to-the-second.
public List<T> GetWithNolock<T>(IQueryable<T> query)
{
// to skip nolock, just...
// return query.ToList();
List<T> results = null;
bool opened = false;
try
{
if (Connection.State == System.Data.ConnectionState.Closed)
{
Connection.Open();
opened = true;
}
using (var cmd = GetCommand(query))
{
cmd.CommandText = Regex.Replace(cmd.CommandText, #"((from|inner join) \[dbo.*as \[t\d+\])", "$1 with (nolock)", RegexOptions.IgnoreCase);
results = Translate<T>(cmd.ExecuteReader()).ToList();
}
}
finally
{
if (opened && Connection.State == System.Data.ConnectionState.Open)
{
Connection.Close();
}
}
return results;
}
I have found in the past that using a Transaction in the recommended way causes the site to run out of connections overnight. As far as I know, that's a bug in linq-to-sql. There may be ways around it, but I'm trying to keep my main code straightforward. I now "just" have to do this...
var users = GetWithNolock<User>(
Users
.Where(u => my query
);
If you Open it, you should Close it. Other LinqToSql operations match this pattern.
In my code, I unconditionally open the connection and close the connection in a finally. If someone passes me an open connection, that's their fault and I happen to close it for them.
You could delay opening the connection until just before ExecuteReader.