gettin request/query parameters with less code - laravel

Is this:
$paginate = $request->get('paginate');
Equivalent to this, for getting a query param if it is present or assign to the associated variable "null" it it is not present:
if ($request->has('paginate')) {
$paginate = $request->get('paginate');
} else {
$paginate=null;
}

According to get() method documentation:
This method belongs to Symfony HttpFoundation and is not usually needed when using Laravel.
Alternatively you can use filled and $request->paginate
So it checks if the request has the "item"and it has value.
$paginate = null;
if ($request->filled('paginate')){
$paginate = $request->paginate;
}

Related

How to update only one property of model?

I'm working on user consents. In my request I have these properties:
$newsLetters (bool|nullable),
$sms (bool|nullable),
$billEmail (bool|nullable),
I need update only one. So I need to find one which is not null and update it, if in my request is more than one properties with bool values i need to throw exception.
How can I achieve this?
My request extends spatie/laravel-data.
I don't understand why would you handle something like this on the backend (you can use radio button for this and always send only one value), you can use validation for requests or something like this:
$newsLetters = null;
$sms = true;
$billEmail = null;
$values = [$newsLetters, $sms, $billEmail];
$filter = sizeof(array_filter($values, function($el) { return $el === null;})) < 2;
if($filter) {
//return exception or whatever
} else {
//update values
}

Call to a member function update() on null with array/checkbox/edit

Need help here i m trying to take values from checkbox s and put them into a edit to change the value "Estado" to "Expedido" but when I run the code it gives me the error"Call to a member function update() on null".I also tried find and change the default of find() to the column i want and also tried with raw postgresql code.
$chassis= $request->chassis;
$escala = $request->escala;
if(Auth::check() == true)
{
foreach($chassis as $chassis)
{
$edit = expedicoes::whereIn('Chassis', explode(',',$chassis))->first()->update(['Estado' =>'Expedido']);
}
The method update(Array) doesnt exist on a model instance, it only exists on a query builder as a Builder instance.
either remove the first() call to call update on the query builder
$edit = expedicoes::whereIn('Chassis', explode(',',$chassis))->update(['Estado' =>'Expedido']);
Or update the on the model then call save()
$edit = expedicoes::whereIn('Chassis', explode(',',$chassis))->first();
if ($edit) {
$edit->Estado = 'Expedido';
$edit->save();
}
I suggest you remove the update call from the foreach loop, gather all "chassis" and run a single query
$extractedChassis = [];
foreach($chassis as $chassi)
{
$extractedChassis = array_merge($extractedChassis , explode(',',$chassi));
}
expedicoes::whereIn('Chassis', $extractedChassis)->update(['Estado' =>'Expedido']);
this code return null
expedicoes::whereIn('Chassis', explode(',',$chassis))->first()
so you have no items that Chassis in explode(',',$chassis)
to solve this you can check if its not return null then update it
$expedicoes = expedicoes::whereIn('Chassis', explode(',',$chassis))->first();
if(expedicoes ){
expedicoes ->update(['Estado' =>'Expedido']);
}
but i think your problem in column name so try to use chassis instead of Chassis
and estado instead of Estado

Web API parameter filtering

This must be simple and I'm being incredibly dense but I can't find an example to help me figure it out. I want to filter my list of tblAsset items by their assessmentId which is passed in through a parameter. I'm able to get the parameter value ok, but I'm not sure how to write the query.
My model is built from an existing Database using the Model creation wizard.
Thanks for any help!
public IEnumerable<tblAsset> GettblAssets()
{
NameValueCollection nvc = HttpUtility.ParseQueryString(Request.RequestUri.Query);
var assessmentId = nvc["aid"];
//limit the assets by assessmentId somehow and return
}
You could use the .Where extension method on the IQueryable<tblAsset> instance returned by your database:
public IEnumerable<tblAsset> GettblAssets()
{
NameValueCollection nvc = HttpUtility.ParseQueryString(Request.RequestUri.Query);
var assessmentId = nvc["aid"];
// TODO: you might need to adjust the property names of your model accordingly
// Also if the assessmentId property is an integer on your model type
// you will need to parse the value you read from the request to an integer
// using the int.Parse method
return db.tblAsset.Where(a => a.assessmentId == assessmentId);
}

Access to filter var attribute?

In Mage_Catalog_Block_Layer_View there is a variable called $_filters, that loops through and displays properties in the $_filter var. Whenever I try to var dump this variable, my server throws an error. This behavior is completely mysterious. Does anyone know if I can get back to the attribute code? I'd like to do something like this:
$_filter->getAttribute()->getAttributeCode();
Have you tried $_filter->getAttributeModel()->getAttributeCode()?
public function getFilters()
{
$filters = array();
if ($categoryFilter = $this->_getCategoryFilter()) {
$filters[] = $categoryFilter;
}
$filterableAttributes = $this->_getFilterableAttributes();
foreach ($filterableAttributes as $attribute) {
$filters[] = $this->getChild($attribute->getAttributeCode().'_filter');
}
return $filters;
}
you can see where the variable setting to this array takes place and how the attribute code is used in this class. Note that this is an array containing view objects not a object itself and dumping out all this just eats up your server memory. And of course you can't call methods on this array.
So there is no actual way to get this code out of this array and you probably have more success in template or subobject level or if you need this in the same class you can get the filters out of $this->_getFilterableAttributes() method or you can try and iterate over each filters array member and their sub-members
$filters['0']->getItems()

How to use Zend Framework Form Hash (token) with AJAX

I have included Zend_Form_Element_Hash into a form multiplecheckbox form. I have jQuery set to fire off an AJAX request when a checkbox is clicked, I pass the token with this AJAX request. The first AJAX request works great, but the subsequent ones fail.
I suspect it may be once the token has been validated it is then removed from the session (hop = 1).
What would be your plan of attack for securing a form with Zend Framework Hash yet using AJAX to complete some of these requests?
I finally abandoned using Zend_Form_Element_Hash and just created a token manually, registered it with Zend_Session and then checked it upon submission.
form.php
$myNamespace = new Zend_Session_Namespace('authtoken');
$myNamespace->setExpirationSeconds(900);
$myNamespace->authtoken = $hash = md5(uniqid(rand(),1));
$auth = new Zend_Form_Element_Hidden('authtoken');
$auth->setValue($hash)
->setRequired('true')
->removeDecorator('HtmlTag')
->removeDecorator('Label');
controller.php
$mysession = new Zend_Session_Namespace('authtoken');
$hash = $mysession->authtoken;
if($hash == $data['authtoken']){
print "success";
} else {
print "you fail";
}
This seems to work and still keeps things relatively sane and secure. I'd still rather use the Hash element, but I can't seem to make it work with AJAX.
Thanks all.
That's how to handled hash field in ajax form :
class AuthController extends Zend_Controller_Action
{
public function init()
{
$contextSwitch = $this->_helper->getHelper('contextSwitch');
$contextSwitch->addActionContext('index', 'json')
->initContext();
}
public function loginAction()
{
$form = new Application_Form_Login();
$request = $this->getRequest();
if ($request->isPost()) {
if ($form->isValid($request->getPost())) {
// some code ..
} else {
// some code ..
// Regenerate the hash and assign to the view
$reservationForm->hash->initCsrfToken();
$this->view->hash = $reservationForm->hash->getValue();
}
}
$this->view->form = $form;
}
}
And then in your view script ..
<? $this->dojo()->enable()
->requireModule('dojox.json.query')
->onLoadCaptureStart() ?>
function() {
var form = dojo.byId("login_form")
dojo.connect(form, "onsubmit", function(event) {
dojo.stopEvent(event);
var xhrArgs = {
form: this,
handleAs: "json",
load: function(data) {
// assign the new hash to the field
dojo.byId("hash").value = dojox.json.query("$.hash", data);
// some code ..
},
error: function(error) {
// some code ..
}
}
var deferred = dojo.xhrPost(xhrArgs);
});
}
<? $this->dojo()->onLoadCaptureEnd() ?>
Hope it's not too late :D
There is a solution:
Create, besides the form that will contain the data, a form without elements. From the controller you instantiate the two forms. Also in the controller, you add the element hash to the empty form. Both forms should be sent to the vision. Then, in the condition "if ($ request-> isXmlHttpRequest ())" in the controller you render the empty form. Then, you take the hash value with the method "getValue ()". This value must be sent in response by Ajax and then use JavaScript to replace the hash value that is already obsolete. The option to create an empty form for the hash is to avoid problems with other elements such as captcha that would have its id generated again if the form were rendered, and would also need to have the new information replaced. The validation will be done separately because there are two distinct forms. Later you can reuse the hash (empty) form whenever you want. The following are examples of the code.
//In the controller, after instantiating the empty form you add the Hash element to it:
$hash = new Zend_Form_Element_Hash('no_csrf_foo');
$hash_form->addElement('hash', 'no_csrf_foo', array('salt' => 'unique'));
//...
//Also in the controller, within the condition "if ($request->isXmlHttpRequest())" you render the form (this will renew the session for the next attempt to send the form) and get the new id value:
$hash_form->render($this->view);
$hash_value['hash'] = $hash_form->getElement('no_csrf_foo')->getValue();//The value must be added to the ajax response in JSON, for example. One can use the methods Zend_Json::decode($response) and Zend_Json::encode($array) for conversions between PHP array and JSON.
//---------------------------------------
//In JavaScript, the Ajax response function:
document.getElementById("no_csrf_foo").value = data.hash;//Retrieves the hash value from the Json response and set it to the hash input.
Leo
Form hashes are great in principle and a bit of a nightmare in practice. I think the best way to handle this is to return the new hash with the response when you make a request, and update the form markup or store in memory for your javascript as appropriate.
The new hash may be available from the form object, or you can read it from the session.
You hinted at the right answer in your question: increase the hop count.
There was specific mention of this in the ZF manual online, but they updated their manuals and now i can't find it (grin)- otherwise i would have posted the link for you.
If you want to use form validator in ajax side use following code :
Myform.php
class Application_Form_Myform extends Zend_Form
{
# init function & ...
public function generateform($nohash = false)
{
# Some elements
if(!$nohash)
{
$temp_csrf = new Zend_Session_Namespace('temp_csrf');
$my_hash = new Zend_Form_Element_Hash ( 'my_hash' );
$this->addElement ( $my_hash , 'my_hash');
$temp_csrf->hash = $my_hash->getHash();
}
# Some other elements
}
}
AjaxController.php
class AjaxController extends Zend_Controller_Action
{
// init ...
public function validateAction()
{
# ...
$temp_csrf = new Zend_Session_Namespace('temp_csrf');
if($temp_csrf->hash == $params['received_hash_from_client'])
{
$Myform = new Application_Form_Myform();
$Myform->generateform(true);
if($AF_Bill->isValid($params))
{
# Form data is valid
}else{
# Form invalid
}
}else{
# Received hash from client is not valid
}
# ...
}
}

Resources