CakePHP session data cleared on paginator sort - session

My session data is being saved in my form as expected.
However, when I run a sort on any column of my results, my form session values are cleared.
I am calling in my search form through en element as it's used on specific locations of the site.
Does anyone know why pagination is clearing out my session? Is this standard Cake?

The paginator sort elements are simply a link generated by the paginator and won't consider any of your form data. The first thing you need to make sure that you're doing is tell the paginator to include any URL paramters for the current page in the url it generates. Put this anywhere in the view before you call any of the $paginator functions.
$paginator->options(array('url' => $this->passedArgs));
Secondly, make sure that your search parameters are being included in the URL. It sounds like they probably aren't. I just answered another question on the best practices of search result URLs here: CakePHP Search Results Best Practices

I solved this:
CakePHP session ID path or other method to share the results of a url - recommendations welcome

Related

How to differentiate between two dynamic url in Laravel

I have two dynamic url with simillar structure. For example, lets say, Product page and category page.
I have set both pages in
Route::get('/{product}', [UsersController:: class, 'productDetail']);
Route::get('/{category}', [UsersController:: class, 'categoryProducts']);
But when I click on url which suppose to go in category page, it redirect to product page only because of same structure. How I can differentiate both URLs for Laravel without altering their url structure?
I don't think this can be done without modifying the URL pattern at least a little bit.
If you do something like /50?type=category then in the show method you can use the query parameter to determine which table to look at. But you'll have to use the same show method and I don't recommend doing it this way.
I hope someone else will be able to shine some more light on the matter.
this is the best practice for your case to make yourapi Resful
Route::get('/product/{product-id}', [UsersController:: class, 'productDetail']);
Route::get('/product/categories, [UsersController:: class, 'categoryProducts']);
learn more about Restful api here https://restfulapi.net/resource-naming/
This should be done by calling index, update diff() function. You can try by using the below:
Route::get('/category/{slug}', 'site\categorycontroller#show')->name('category.show');
Route::get('/product/{slug}', 'site\productcontroller#show')->name('product.show');

Link change SESSION var

I have a listing page for an e-commerce website with various items (item_list.php). This page is generated with a PHP loop and displays each item inside a <li> element. Every item is a link to the same page, called item_details.php .
When clicking on the link i want to run a script that changes a SESSION var to a certain $id (which will be excracted from the <li> itself with .innerHTML function) and then allowing the browser to move into the next page (item_details).
This is needed so i can display the proper information about each item.
I think this is possible with Ajax but I would prefer a solution that uses JS and PHP only.
(P.S.This is for a University project and im still a PHP newbie, i tried searching for an answer for a good while but couldn't find a solution)
No JS or other client-side code can set session values, so you need either an ajax call to php, or some workaround. This is not a complete answer, but something to get you thinking and hopefully going on the project again.
The obvious answer is just include it in the link and then get it in PHP from the $_GET -array, and filter it properly.
item title
If, however, there is some reason this is not a question with an obvious answer:
1.) Closest what you're after can be achieved with a callback and an ajax call. The idea is to have the actual link with a click function, returning false so the link doesn't fire at once, which also calls an ajax post request which finally will use document.location to redirect your browser.
I strongly advice against this, as this will prevent ctrl-clicks causing a flawed user experience.
Check out some code an examples here, which you could modify. You will also need an ajax.php file which will actually set the session value. https://developers.google.com/analytics/devguides/collection/analyticsjs/enhanced-ecommerce#product-click
2.) Now, a perhaps slightly better approach, if you truly need to do this client-side could be to use an click handler which instead of performing an ajax call or setting session directly, would be to use jQuery to set a cookie and then access this data on the item_list.php -page.
See more information and instructions here: https://www.electrictoolbox.com/jquery-cookies/
<script>
$('product_li a).click(function(){
$.cookie("li_click_data", $(this).parent().innerhtml());
return true;
});
</script>
......
<li class="product_li">your product title</li>
And in your target php file you check for the cookie. Remember, that this cookie can be set to anything, so never ever trust user data. Test and filter it in order to make sure your code is not compromised. I don't know what you want to do with this data.
$_COOKIE['li_click_data'];
3.) Finally, as the best approach, you should look at your current code, and see if there is something you can re-engineer. Here's a quick example.
You could do the following in php to save an array of the values in the session on each page load, and then get that value provided you have some kind of id or other usable identifier for your items:
// for list_items.php
foreach($item as $i) {
// Do what you normally do, but also set an array in the session.
// Presuming you have an id or some other means (here as item_id), to identify
// an item, then you can also access this array on the item_details -page.
$_SESSION['mystic_item_data_array'][$i['item_id]] = $i['thedata'];
}
// For item_details.php
$item_id = // whatever means you use to identify items, get that id.
$data_you_need = $_SESSION['mystic_item_data_array'][$item_id];
Finally.
All above ways are usable for small data like previous page, filters, keys and similar.
Basically, 1 and 2 (client-side) should only be used, if the data is actually generated client-side. If you have it in PHP already, then process it in php as well.
If your intention is to store actual html, then just regenerate that again on the other page and use one of the above ways to store the small data in case you need that.
I hope this gets you going and at least thinking of how to solve your project. Good luck!

Symfony2, doctrine2, session, best way to paginate search page

Let's imagine we have simple data and want to make pagination of it. It's not hard to do, simple _GET var with page number others doctrine with offset will allow us to do it in easy way, BUT How should it look like in search page? Let me explain.
For example we have simple route with /search url. Where we have form for our search. When use input string we user POST method on same page and will get result. Simple enough but if we add pagination here it become a problem with storing "inputed string".
If we store in session on search query it will be solution BUT... it's not. Why? User input search string - get result with pagination (here search string already in session) after that leave the page (or close browser, or left to another page). When he will return data from session will show him 'result of old query'...
So question is, what is the best practice for such situation? I want simple search query + pagination of it but if user left page - clear result.
Using POST instead of GET for search query is kinda unusual and not really safe. Since search query operations are read-only you should use GET to access/get the data. POST is used for updating or creating resources.
And how you will go back/forward in the pagination (using browser's buttons)? You always will be getting an alert box. AND you cannot share/bookmark the search query url.
BTW to answer your question, sessions and hidden input fields would be the way to go. You also can use a combination of get and post
When should I use GET or POST method? What's the difference between them?

xss protection and html purifier

I am currently using the CodeIgniter framework, and looking to strengthen the XSS protection by using HTMLPurifier (http://htmlpurifier.org/).
Is my understanding correct that you want to 'clean' data on post, so that its purified before its inserted into the Database? Or do I run it before displaying in the view?
If so, do I want to run HTMLPurifier on every single post that takes place? Since the app contains a lot of forms, I'd hate to have to selectively choose what gets cleaned and what doesnt - assuming that I can intercept all posts, is this the way to go? Of course, I validate some fields anyway (like email addresses, numeric numbers, etc)
Use $this->input->post() to get $_POST data. Codeigniter filters it automatically if global xss filter is set to true.
See the docs: http://codeigniter.com/user_guide/libraries/input.html
Edit: to clarify
Yes you should filter before inserting into the DB and yes you should filter all user input.
A quick google search, http://www.google.com/search?q=codeigniter+htmlpurifier, led to this page: http://codeigniter.com/wiki/htmlpurifier which is a helper for htmlpurifier. Regarding catching all $_POST data: you have to do something with the data, right? In your models, when you're doing that something, just make purify() part of that process:
$postdata = purify($_POST);

hide passed IDs in URL

noob question. when I pass an id in the route to query my DB, is there a way to prevent the actual id from showing in the URL in browser.
If not, is there a way to prevent the user from changing the id in the URL and access other information?
Some sort of validation you get from clicking the link on the previous page or something.
I hope this make sense.
You could retrieve your record with an hash instead of the id directly.
You can use package like https://github.com/mitchellvanw/hashids (there must be some others)
Also, if you just want to hide it, you can POST it to your page. Don't forget that users can still change the form informations.
U can use base64_encode() and base64_decode to hide url from users and preventing them to change.

Resources