Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

BasePath and redirects #1440

Closed
akrabat opened this issue Aug 15, 2015 · 4 comments
Closed

BasePath and redirects #1440

akrabat opened this issue Aug 15, 2015 · 4 comments

Comments

@akrabat
Copy link
Member

akrabat commented Aug 15, 2015

I'm beginning to think that basePath is more of a hinderance than a help in Uri!

Consider a very usual use case of a view item page where you want to redirect if the item cannot be found. The basic route callback is:

$app->get('/books/{id}', function ($request, $response, $args) {
    $book = Book::find($args['id']);
    if (!$book) {
        // redirect to the route named 'book'
    }

    // return a response with the book information 
})->setName('view-book');

Now... how do we create the redirect?

I think that if you're using a URL like http://locahost/slim3/develop-testbed/public/books/2 where the base path is /slim3/develop-testbed/public, then you have to do this:

        $path = $this->router->pathFor('books-list');
        $basePath = $request->getUri()->getBasePath();
        $uri = $request->getUri()->withQuery('')->withPath($path);
        $uri = $uri->withBasePath($basePath); // has to be after withPath() call
        return $response->withRedirect((string)$uri, 307);

This is silly! i.e. Surely we can do better?

@JoeBengalen
Copy link
Contributor

Wont $request->getUri()->withPath('books') just work? You could remove the query and fragment part, but that has nothing to do with the basePath.

Also in your code sample, why do you declare the local $basePath? You are not using it.

@JoeBengalen
Copy link
Contributor

Ah I think I see the problem now;

pathFor() returns a preceding slash, which is why the base path is ignored when using it directory in $uri->withPath().

$app->get('/test', function ($request, $response, $args) {

    var_dump((string) $request->getUri()->withPath('books'));
    // -> http://localhost/dev/slim/index.php/books

    $path = $this->router->pathFor('books');
    var_dump((string) $request->getUri()->withPath($path));
    // -> http://localhost/books 

    $basePath = $request->getUri()->getBasePath();
    var_dump((string) $request->getUri()->withPath($basePath . $path));
    // -> http://localhost/dev/slim/index.php/books

    // ltrim would work here ...
    var_dump((string) $request->getUri()->withPath(ltrim($path, '/')));
    // -> http://localhost/dev/slim/index.php/books
});

$app->get('/books', function ($request, $response, $args) {})->setName('books');

Point being the pathFor and Uri not working very well in relation to the basePath.

@akrabat
Copy link
Member Author

akrabat commented Aug 15, 2015

Chatting with @JoeBengalen, one idea we've had is making the router basePath aware. This means that pathFor would always create a path that is absolute including the basePath.

Here's one possible implementation: https://github.com/slimphp/Slim/compare/3.x...akrabat:basepath-work?expand=1 is one solution

@silentworks
Copy link
Member

Just to add some previous feedback on having this in the past. #838 (comment)

I also looked at a similar issue on Silex repo: silexphp/Silex#678

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants