.htaccess, how can I remove pattern from url? - ajax

I would like to clean my urls from this:
https://example.com/track&id=180
to:
https://example.com/track/180
My code is as follow:
My .htaccess
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} -f [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^ - [L]
RewriteRule ^welcome/([^/]+)/?$ index.php?a=welcome&filter=$1 [NC,QSA,L]
RewriteRule ^track/([^/]+)/?$ index.php?a=track&filter=$1 [NC,QSA,L]
RewriteRule ^(([^/]+)+)(/([^/]{0,32})(/.+)?)?$ index.php?a=$1&q=$3 [L,QSA]
But if I use the 2nd example (the url without &id=) via Ajax it returns "undefined".
I tried the Ajax call with this link button
Click Here
I supposed it's undefined because in my requests I get the id parameter in PHP as $_GET['id'];.
So my question is: why it doesn't work on Ajax?
Here is my functions.js
$(function() {
$("body").on("click", "a[rel='loadpage']", function(e) {
// Get the link location that was clicked
startLoadingBar();
pageurl = $(this).attr('href');
// Replace the path of the url from index to the path with raw content
var custom = pageurl;
var custom = custom.replace(baseUrl+'/track', 'page.php?a=track');
var custom = custom.replace(baseUrl+'/', 'page.php?a=welcome');
// Request the page
$.ajax({url:custom,success: function(data) {
// Show the content
$('#content').html(data);
// Stop the loading bar
stopLoadingBar();
// Scroll the document at the top of the page
$(document).scrollTop(0);
// Reload functions
selectExplore();
reload();
}});
// Store the url to the last page accessed
if(pageurl != window.location){
window.history.pushState({path:pageurl}, '', pageurl);
}
return false;
});
});
.htaccess isn't my forte, so any help would be much appreciated.
Thanks in advance.

You can use this JS code to send your AJAX call:
var custom = pageurl.replace(baseUrl+'/track/', '/page.php?a=track&id=');
// Request the page
$.ajax({url:custom,success: function(data) {
// ...
}

Related

Laravel Redirect for Weird Encoded Space

It seems we have some weird broken incoming links for our website that we would like to redirect. We are using Laravel on Apache.
Here is the incoming url: /flannel-sheets%C2%A0
Here is where we want to send it: /flannel-sheets
%C2%A0 seems to decode to a strange space.
I have tried these lines in the web.php file
$this->get( 'flannel-sheets%C2%A0', function() { return redirect( '/flannel-sheets' ); });
$this->get('flannel-sheets ', function() { return redirect( '/flannel-sheets' ); });
$this->get('flannel-sheets$nbsp;', function() { return redirect( '/flannel-sheets' ); });
I have also tried using Apache redirects in my 000-default.config and .htaccess files
Redirect 301 /flannel-sheets%C2%A0 https://example.com/flannel-sheets
Neither of these methods are working for me. What should I do?
So it is a non-breaking space (0xC2 0xA0). Annoying to deal with these once they are in the wild, bad inbound links that is.
Using mod_rewrite is probably the best option here. Something like this would work...
RewriteRule ^(.+)\xc2\xa0$ $1 [L,NE]
You'll want to check for those characters, not their URL encodings. I'm wondering if mod_speling offers anything useful for this scenario... not seeing anything so far.
you can fix it using :
# remove spaces from start or after /
RewriteRule ^(.*/|)[\s%20]+(.+)$ $1$2 [L]
# remove spaces from end or before /
RewriteRule ^(.+?)[\s%20]+(/.*|)$ $1$2 [L]
# replace spaces by - in between
RewriteRule ^([^\s%20]*)(?:\s|%20)+(.*)$ $1-$2 [L,R]
or you can receive the broken routes dynamically
$this->get( '/{route}', function($route) {
//filter $route the way you need
); });

Laravel index route issue when using for a subsection in another fw (external public dir)

I'm using a Laravel app with an external public directory, e.g. root/Laravel, and root/html/public.
I need this app to load from a require on a php file (root/html/this-section.php) that already has another framework loading it, hence that other fw has its own head, and body tag. This app will load between the header and footer of that file.
When I set up the routes, i notice that both of the following routes work, but i get different results.
Route::get('/', 'HomeController#index');
Route::get('/this-section', 'HomeController#index');
# this also works as a substitute for above, still same issue though
Route::get('//', 'HomeController#index');
These are the same pages, the controller has the same code, I would expect that the pages load the same. Whats happening is the main index site.com/ is loading correctly, but the latter is loading without the html <head> and <body> tags which exist on this-section.php. So essentially, the latter is not loading the parent page, its only loading what it sees on the blade templates.
I suspect maybe either need to add a rewrite to the .htaccess to cover this, or set up a custom redirect or return of a view or response in the controller (I need help here with suggestions) where I can then make a second method, e.g. thisSectionIndex() and return that suggestion.
At first I had things working with overriding the public_path() to the correct path this-section however that backfired when i made the sub routes
e.g. when using the following route setup
Route::get('/', 'HomeController#index');
Route::get('/feature', 'SectionController#feature');
It caused the feature route to be 500 or 404, I think it couldn't find the files, so I realized I needed to unfortunately add in the /this-section portion to the route ,which opened a can of worms pretty much.
Route::get('/', 'HomeController#index');
Route::get('/this-section', 'HomeController#index');
Route::get('/this-section/feature', 'SectionController#feature');
ON a side note, some fallout for this which I found a temporary work-around for already, was {{assets()}} broke. I had assets() overridden to not have to use the this-section/ portion, e.g. like this {{assets(/this-section/css/styles.css)}}. The temp worksround was to unfortunately have to manually add the paths and forego using {{assets()}} altogether in the blade templates until i figure that part out, because no path is working for them now.
Some background info:
Im overriding the public path like this
#Laravel\app\SectionApplication
class SectionApplication extends \Illuminate\Foundation\Application
{
public function publicPath()
{
$newBasePath = $this->basePath . DIRECTORY_SEPARATOR . '..' .
DIRECTORY_SEPARATOR . 'html/this-section';
return $newBasePath;
}
}
#Laravel/bootstrap/app.php
// $app = new Illuminate\Foundation\Application(
// realpath(__DIR__.'/../')
// );
$app = new App\SectionApplication(
realpath(__DIR__.'/../')
);
Here is the pertinent(adjusted) parts of the laravel bootstrapper index (html/this-section/index.php)
function public_path($path = '')
{
return realpath(__DIR__);
}
//adjust your relative laravel framework path here
$laravelRelPath = '../../Laravel';
//override the blade {{asset()}} helper
function asset($path, $secure = null)
{
$newPubPath = 'this-section/'; //relative from html where the index.php will be
return app('url')->asset($newPubPath . $path, $secure);
}
.htaccess is located outside of Laravel, and in html/
<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
Options -MultiViews
</IfModule>
RewriteEngine On
#Rewritebase /this-section/
#RewriteRule ^(.*)$ this-section/$1 [L]
# Redirect Trailing Slashes If Not A Folder...
RewriteCond %{REQUEST_FILENAME} !-d
# Handle Front Controller...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
# Handle Authorization Header
RewriteCond %{HTTP:Authorization} .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
</IfModule>
With the help of this topic
and this topic I found a working solution. Adjustments are needed When your loading in the application. You want to bootstrap it from the same path as the file loads the bootstrap, then override the .htaccess for that particular path only.
move laravels bootstrap file html/this-section/index.php file up one directory, next to the file html/this-section.php, and rename it to html/this-section-laravel-boostrap.php
adjust the path for laravel on html/this-section-laravel-boostrap.php by removing one directory ../
e.g. from $laravelRelPath = '../../Laravel'; to $laravelRelPath = '../Laravel';
add the following code to htlm/this-section.php (the file loads the bootstrap)
if (strpos($_SERVER['REQUEST_URI'],'this-section') !== false) {
require_once('this-section-laravel-bootstrap.php');
}
add the following to the .htaccess to snag the uri
#Rewritebase /
RewriteRule ^this-section/?$ / [L,NC]
The only route needed for this-section
Route::get('/this-section', 'HomeController#index')
In your blade templates, call your assets like this so they load on every sub sections url, e.g. for css
<link rel="stylesheet" href="/this-section/css/styles.css">
The application will now bootstrap, and always use the outer contents from the parent file that loads it. See below for an example parent test file(html/this-section.php) for this.
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8">
<title>Parent Application</title>
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
</head>
<body>
<header>
<nav>
<ul>
<li>menu</li>
</ul>
</nav>
</header>
<?php
<--! laravel sandwich -->
if (strpos($_SERVER['REQUEST_URI'],'this-section') !== false) {
require_once('this-section-laravel-bootstrap.php');
}
?>
<footer>
<p>Copyright <?php echo date('Y'); ?> - All rights reserved.</p>
</footer> -->
</body>
</html>
Bonus
assets are now loading correctly, you probably dont need step 5.
{{asset('css/vendors.css')}}

RewriteRule Form Get Request

When i submit my form this is my url:
index.php?pagina=search&terms=soccer
I want to change it to:
/pagina/search/terms/soccer
what I have so far doesn't work
#searchRewriteRules
RewriteCond %{QUERY_STRING} ^terms=([a-zA-Z0-9]+)$
RewriteRule ^index.php$ /pagina/search/terms/%1? [R=301]
Could somebody help me
Your query string is pagina=search&terms=soccer. You need to match that completely. Please note that if you are doing a POST request you loose the POST body on the redirect. Besides that you need to translate the pretty url back to the normal url, and prevent an infinite redirect from happening.
RewriteCond %{THE_REQUEST} ^(GET|POST)\ /index\.php?pagina=search&terms=([a-zA-Z0-9]+)\ HTTP
RewriteRule ^ /pagina/search/terms/%2? [R=301,L]
RewriteRule ^pagina/search/terms/(.*)$ /index.php?pagina=search&terms=$1 [L]
it's working with jquery.
I have created a new page called rewritesearch.php and inserted into my main page where the form is.
rewritesearch.php
// Base Url
$url = BASE_URL;
echo <<<EOT
<script>
$(document).ready(function() {
$('#submit').click(function() {
// get the terms value
var terms = $('.search').val();
goUrl = '{$url}pagina/search/terms/'+terms+'/';
window.location = goUrl;
return false; // Prevent the default button behaviour
});
$('#search_form').submit( function() {
return false; // May be necessary to prevent the default form behaviour
});
});
</script>
EOT;

Unique Inconsistent CI Blank Page Issue

With reference to the CodeIgniter Blank Page question I asked previously.
Some new information has come to light that might shed some light on the problem.
My newly built server (CI 2.1.3 - latest release) where this was working correctly and not giving the WSOD is on a sub-domain of my development server. The WSOD issue is STILL occurring on the "live" site which is not in a sub-domain.
Obviously the "live" site is in public_html and the development version is in the "codeigniter" subdomain. Everything else is identical on both servers. Same PHP 5.3 setup. Same .htaccess file. Same CI 2.1.3 setup, obviously with config changed to point to the sub-domain in "development" and the domain in "live".
The issues are the same. On ENTER PRESS or external link ACTIVATION (such as from an email) I get WSOD in "live" but this works correctly in "development". Every controller that is activated without a button click in "live" gives me WSOD, while ALL the pages work correctly in "development".
As a check, I built a completely fresh CI root install (no sub-domain) and the problem mirrors exactly what is going on in "live".
The processes that are exhibiting the WSOD behaviour do not have views attached but simply print out a message on success.
Here is the code:
.htaccess - in the sub-domain folder of "development" and public_html of "live":
Options -Indexes
Options +FollowSymLinks
RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_URI} ^system.*
RewriteRule ^(.*)$ /index.php?/$1 [L]
RewriteCond %{REQUEST_URI} ^application.*
RewriteRule ^(.*)$ /index.php?/$1 [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ /index.php?/$1 [L]
ErrorDocument 404 /index.php
One of the controllers giving the WSOD in "live" when pasting into browser after logging in, but is working in "development" is inviteusers.php simply takes a Company ID and User ID and sends the user a link with login details for the new account. Some extraneous code in the "message" body has been removed to shorten it:
<?php if ( ! defined('BASEPATH')) exit('No Direct Script Access Allowed');
/**
* Invite Users Controller
*
* ----------------------------------------------------------------------------
*/
class InviteUsers extends MY_Controller
{
function __construct()
{
parent::__construct();
$this->load->model('UserDetails_model');
$this->load->helper('date');
}
public function index()
{
if (!$this->session->userdata('clientid') && !$this->session->userdata('userid')) {
redirect('login');
}
// Add Client ID for All Uninvited Users for a Client
$lookupid['clientid'] = "CID";
// Add User ID to Add ONE Uninvited user for a Client
// Change UserDetails_model to take UID if this option is used
$lookupid['userid'] = "UID";
$invites = $this->UserDetails_model->getInvites($lookupid);
foreach ($invites as $invite) {
if ($invite['new'] == "Y") {
$message = "Hi ".$invite['username']." ".$invite['usersurname'].", \n \n";
$this->load->helper('email');
$this->email->set_newline("\r\n");
$this->email->from('email#address.com', 'System Messenger');
$this->email->to($invite['useremail']);
$this->email->bcc('admin#address.com');
$this->email->subject('Temporary Login Details');
$this->email->message($message);
$sent = $this->email->send();
if ($sent) {
echo "SUCCESS!!! ";
echo "NAME: ".$invite['username']." ".$invite['usersurname']." ";
echo "E-MAIL: ".$invite['useremail']." ";
echo "PASSWORD: ".$invite['temppass']." ";
echo "NEW: ".$invite['new']."";
}
} else {
$message = "Hi ".$invite['username']." ".$invite['usersurname'].", \n \n";
$this->load->helper('email');
$this->email->set_newline("\r\n");
$this->email->from('email#address.com', 'System Messenger');
$this->email->to($invite['useremail']);
$this->email->bcc('admin#address.com');
$this->email->subject('Temporary Login Details');
$this->email->message($message);
$sent = $this->email->send();
if ($sent) {
echo "SUCCESS!!! ";
echo "NAME: ".$invite['username']." ".$invite['usersurname']." ";
echo "E-MAIL: ".$invite['useremail']." ";
echo "PASSWORD: ".$invite['temppass']." ";
echo "NEW: ".$invite['new']." ";
}
}
}
}
}
/*
* End of file inviteusers.php
* Location: ./application/controllers/inviteusers.php
*/
As I said before - THIS PROCESS IS WORKING IN DEVELOPMENT but gives WSOD in LIVE.
MY_Controller simply performs the session lookups and checks some variables. It is simple and solid and has been working without mods since forever.
I think there may be a BIG CLUE in the fact that it works correctly in a recently set up sub-domain with the SAME .htaccess file and config changed to reflect the URL. All other environment variables are EXACTLY IDENTICAL. Same server, same hosting company, same Apache version running the same modules, same PHP version with the same modules, timeouts, memory etc. set.
The controllers giving the WSOD provide me with quick and easy access to certain admin functions so they must work... And they do... In a "development" sub-domain on an identical server to "live" which runs in public_html.
If a certain conditional scenario is met, you aren't outputting anything!
You are only echoing information if the $sent variable equates to true, AKA your email has sent successfully. If it doesn't, you aren't showing anything! Since there is no actual PHP errors, enabling those won't solve anything (although 99% of the time, that is the problem behind blank pages).
Throw an else statement on there with the email's debugger, and you should get some sort of indication about what's going on.
if ($sent) {
echo "SUCCESS!!! ";
echo "NAME: ".$invite['username']." ".$invite['usersurname']." ";
echo "E-MAIL: ".$invite['useremail']." ";
echo "PASSWORD: ".$invite['temppass']." ";
echo "NEW: ".$invite['new']."";
}
else
{
echo $this->email->print_debugger();
}
Also, for what it's worth, your .htaccess doesn't need rules for the system and application folders. You also don't need slashes on the front of your RewriteRule URLs (RewriteBase handles that for you).
Options -Indexes
Options +FollowSymLinks
RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php?/$1 [L]
ErrorDocument 404 index.php

Codeigniter url routing selecting menu item adds segments to url

In a fresh installation of codeigniter 2.1.3 I have a controller 'home.php' with two functions:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class Home extends CI_Controller {
public function index()
{
$this->load->view('home');
}
public function homefunction()
{
$this->load->view('homefunction');
}
}
I have a view 'home.php'. The anchors represent the menu:
<p>Home</p>
<br/>
Home
Home Function
and a view 'homefunction.php'
<p>Function in the Home controller</p>
<br/>
Home
Home Function
my routes:
$route['default_controller'] = "home";
I have 'eliminated' index.php from the URL with .htaccess and config.php
my .htaccess is:
RewriteEngine On
RewriteBase /test/
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/$1 [PT,L]
in the config.php file I have set:
$config['base_url'] = 'http://localhost/test';
$config['index_page'] = '';
Now I run http://localhost/test and my home page loads with the menu. The url in the browser is localhost/test/. Then I click the 'Home' anchor menu item the url in the browser becomes localhost/test/home. I click the other menu item 'Home Function' the home function page loads and the url becomes localhost/test/home/homefunction. In the menu of the home function view I click the 'home' item and the url becomes localhost/test/home/home. I was expecting to become localhost/test/home. Then I click the menu item 'Home Function' the home function view is not loading and the url becomes localhost/test/home/home/homefunction, the homefunction page is not loading I click again home and I get in the url localhost/test/home/home/home and this goes on each time I click home function menu item and then home menu item a home section is added in the url.
I know it is something simple that maybe has to do with routing but I' stuck and I can't find a similar problem with google. Can anyone help?
Load url helper class. That would make you easy and dynamic.
$this->load->helper('url');
or load it as default, on config/autoload.php
$autoload['helper'] = array('url');
and every time you assign you url as :
Home
Home Function
You are encouraged to use this function any time you need to generate a local URL so that your pages become more portable in the event your URL changes.
URL helper: codeigniter
Go for
Home
Home Function
or
Home
Home Function

Resources