I'm doing a project in php mvc but without framework. I organized the files in this way:
Directory public: there are files accessible from the outside
Directory View: there are files .php but essentially only html
Direcory Model: contains the files related to the database connection, and classes that define the objects, for example, the class User.php
Directory Controller: contains a 'generic' class Controller and Controller classes more 'specific'
I creat a login page (View/login.php) with a form whose action value is public/index.php. In index.php there is this code:
$controller = new LoginController();
$view = $controller->invoke();
$view->render();
invoke() is a function in Controller/LoginController.php that reads the data entered by the user and controls them, if they are correct (there is user in the database with the username and password) then creates two global variables and make a redirect:
$_SESSION['logged_in'] = 1;
$_SESSION['username'] = $username;
$url = "../public/home.php";
header("Location: $url", true, 302);
exit();
public/home.php does this:
$controller = new HomeController();
$view = $controller->invoke();
$view->render();
HomeController is a class that extends Controller. The constructor of Controller see if there are the variables $_SESSION['logged_in'] and $_SESSION['username'].
If they not exists it makes a redirect to public/index.php.
My problem is that the row with header("refresh:0; url=../public/home.php "); does not redirect.
Explain: when I insert the correct data (registered user) redirects for a short time but then returns to home.php.
Instead it should redirect to home.php and stay there, do not go to index.php .
I also tried with header("refresh: 0; url = ../public/home.php"); but it's the same problem.
How can I solve this problem?
Thank you and sorry for my poor English!
Add php ob_start() function on top of the page. If you call ob_start() while another ob_start() is active. Just make sure that you call ob_end_flush() the appropriate number of times. If multiple output callback functions are active, output is being filtered sequentially through each of them in nesting order.
Ref: http://in2.php.net/ob_start
Related
My applications is now in phalcon php framework. I want to redirect a url which contain .html at the end. To redirect, I wrote the controller name as WindshieldReplacementHtmlController.php but because of the dot in between I could not redirect. How can I solve this?
Redirect from:
localhost/windshield-replacement.html
to
localhost/greenvalleyaz
When I type localhost/windshield-replacement-html its redirecting to the target but when i use localhost/windshield-replacement.html its not detecting the controller.
is it the correct way to do that ?
In MVC you should not show the View Directly
you have to access a controller action --> in action you have to render view
In the Example I want to show user/order.phtml
I will access this page from Browser localhost/appname/user/orders
UserController.php
use Phalcon\Mvc\View;
class UserController {
function ProfileAction(){ //access localhost/appname/controller/profile
}
function loginAction(){ //access localhost/appname/controller/profile
}
function ordersAction(){ //access localhost/appname/controller/orders
$view = new View();
// Setting views directory
$view->setViewsDir('app/views/');
$view->start();
// Shows recent posts view (app/views/user/orders.phtml)
$view->render('user', 'orders');
$view->finish();
// Printing views output
echo $view->getContent();
}
}
Refer : Phalcon_Mvc_View
I built an user login to my site by this guide:
http://www.iluv2code.com/login-with-codeigniter-php.html
I have few question about session's
I need to put the session_start(); in every controller or there is a way in codeigniter that it will automaticlly be in all controllers? (should I do that?)
and there is a other way rether to put in every function that:
if($this->session->userdata('logged_in'))
{
//function code
}else{
//If no session, redirect to login page
redirect('../login', 'refresh');
}
or should I do that for every controller function (for example if I have controller named page and he have the functions :index,edit,view I need to put it for every one of them?
and last question, I have logout button on the top of every page called by view/header
should I also put this function:
function logout()
{
$this->session->unset_userdata('logged_in');
session_destroy();
redirect('home', 'refresh');
}
in every controller or I can do it a "golbel" function in some way?
EDIT:
I use this in hooks.php:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
/*
| -------------------------------------------------------------------------
| Hooks
| -------------------------------------------------------------------------
| This file lets you define "hooks" to extend CI without hacking the core
| files. Please see the user guide for info:
|
| http://codeigniter.com/user_guide/general/hooks.html
|
*/
$hook['post_controller_constructor'] = array(
'class' => 'SessionData',
'function' => 'initializeData',
'filename' => 'loginHelper.php',
'filepath' => 'hooks',
'params' => array()
);
and this in loginHelper.php:
<?
class SessionData {
var $CI;
function __construct(){
$this->CI =& get_instance();
if(!isset($this->CI->session)) //Check if session lib is loaded or not
$this->CI->load->library('session'); //If not loaded, then load it here
}
function initializeData() {
// This function will run after the constructor for the controller is ran
// Set any initial values here
if(!$this->CI->session->userdata('logged_in')){ //call session methods with super object
redirect('../login', 'refresh');
}else{
$data['user'] = $this->CI->session->userdata('logged_in');
}
}
}
?>
/* End of file hooks.php */
/* Location: ./application/config/hooks.php */
the user['data'] not created in all the pages. where am I wrong?
For your second question about logout, I usually put the logout function in a User controller and call it as Log Out.
For your first question, I saw a tutorial how you do user login in a controller and extend that controller in your regular controller, thats how you avoid login check in every function. I am trying to find that tutorial, once I get it, I'll share it, but the concept is like that way.
you do not need to put the session_start(); in every controller!
You could simply start the session class in the autoload.php file in your config directory!
$autoload['libraries'] = array('database', 'session', 'encrypt');
Also, it is better to check if the user is logged in, inside the constructor function of the classes!
if(!$this->session->userdata('logged_in'))
redirect('loginController/loginFunction', 'refresh');
and to destroy all the sessions when logging out, you could use sess_destroy();
Initializing a Session
To autoload Session, open the application/config/autoload.php file and add the item you want loaded to the autoload array so: $autoload['libraries'] = array('session'); Yo don't use session_start(); and session_destroy(); at all.
Session Documentation:
https://ellislab.com/codeigniter/user-guide/libraries/sessions.html
Auto-loading Resources:
https://ellislab.com/codeigniter/user-guide/general/autoloader.html
To Check Login
Use Hooks to avoid chunky code dupplications and it is better practise. Navigate bottom of the page and read Hook Points so you get an idea. It is easy! Definitely learn hooks.
Logout
You answer explained here.
After alot of working I solved the problem with the login check.
I didn't use the hooks. I build a MY_Controller in core folder and exteds it in all my controllers expect from the login controller.
In the MY_Controller I use thie login check.
CodeIgniter core controllers:
https://philsturgeon.uk/blog/2010/02/CodeIgniter-Base-Classes-Keeping-it-DRY/
Forgive me if this is a "duh" question or if you need more information to answer, I am new to CodeIgniter and still haven't figured out a few things with best practices and such...
In routes.php I have $route['default_controller'] = "home"; so my default_controller is obviously "home".
Inside my home.php controller I have:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class Home extends CI_Controller {
function __construct() {
// blah
}
function index(){
// blah
}
function login(){
// blah
}
}
Which works fine and everything, there is no problems with that. The only thing I can't figure out is if I want to access the login function, I currently have to go to www.blah.com/home/login. How can I change it so it just goes to www.blah.com/login, without creating a new controller (I would like to keep some of these one time base urls all in my default controller)? Is that even possible or do I just have to create a new controller?
If I just have to create a new one, is there a best practices for how many controllers you have, etc.
Documentation says: This route will tell the Router what URI segments to use if those provided in the URL cannot be matched to a valid route.
So use $route['login'] = 'home/login';
The way I have it set up is to have the index function act as the gatekeeper: if not logged in, show a login form view, if logged in, redirect to your (protected) home page. The login function is only accessed via post, when the user submits his login/pwd, and performs the login logic.
You need add a line to your application/config/routes.php file
$route['login'] = "home/login";
I am using native PHP sessions ($_SESSION) with CodeIgniter framework.
I have a "Login" controller loads view where user enters login and password.
After the user submits the login form, the "Login" controllers authenticate() method is called.
If everything is alright i add some data to $_SESSION array, then i redirect user to "Organisation" controllers myOrganisation() method.
I'm calling session_start() in Login/login() , Login/authenticate() and Organisation/myOrganisation() methods, but still the session is not passed, because in myOrganisation() method the session is new.
I tested my cookies functionality with creating 2 test php pages, where i just echo session id. It works perfectly.
Maybe i am not putting session_start() in all places it needs to be? (i put them in all controllers methods).
Login Controller:
class Login extends CI_Controller {
public function index() {
session_start();
$this->load->view("Login/index", $data);
public function authenticate() {
session_start();
$_SESSION['login'] = $login; // everything is alright, redirect
header("location: ".base_url()."Organisations/MyOrganisation");
Organisation controller:
public function MyOrganisation() {
session_start(); // here session is a new one, not passed
if(isset($_SESSION['login'])) {
I don't know what was wrong with the session_start() placements that i did, but the one thing that solved the problem was to place it in index.php in main folder
session_start() can also be specified in a constructor, not every method in a class. That means both your controllers can have this:
function __construct () {
ini_set("session.gc_maxlifetime", 14400);
ini_set("session.cookie_domain", .yourdomain.com);
session_set_cookie_params(14400, '/', .yourdomain.com);
session_start();
}
The first 3 lines in a constructor are to make sure the session cookie is valid for a long time and under you domain.
Besides that (and not closed index() and authenticate() methods), where's $login coming from?
I have some problems using Code Igniter and I feel there is something I don't understand because I can't get my redirects and my headers to work. Here is the situation :
When site is entered, the default "home" controller is called.
public function initialize()
{
printf("CONSTRUCTION OF HOME CONTROLLER - \n");
// print_r($_SESSION);
//TODO : CONSIDER CREATING A LIBRARY TO AVOID WRITING THIS OFTEN. NOT
// SESSION TROLLING DETECTION
if( isset($_SESSION['banana']))
{
echo "SPLITTING THE TRUTH";
}
// GETTING AS SERIOUS AS GREG
if( !isset($_SESSION['username']))
{
printf("USERNAME IS NOT SET. SETTING UP THE LOGIN PAGE. \n");
redirect('home_invite');
}
else
{
$this->load->view('welcome_message');
}
}
public function index()
{
//INITIALIZING THE PATH USED FOR THIS NAVIGATION
printf("TROLLING THE BEGINNING OF THIS CONTROLLER HOME - ");
$this->initialize();
printf("TROLLING THE END OF THIS CONTROLLER HOME - ");
//TODO : CONSIDER CREATING A LIBRARY TO AVOID WRITING THIS OFTEN
}
Index calls initialize who verify if the user has already a session variable with username in it. If that's the case, we would proceed to check his level of privileges, etc, and load corresponding view. Thats not the problem.
If the session is not started, I want to load the "login" view, called here "home_invite". And I want to redirect him to that page. But if I use this code, the page will show a 404 error.
If I use $this->load->view('home_invite'), it works, but I don't understand and I feel it isn't what I want it to do.
Why is redirect not working in this context?
Using the redirect() method redirects to a URL. You therefore need to pass it a full URL (as it uses the header() function which according to the RFC for HTTP1.1 requires a full URL.
This means that you can use
redirect(site_url('home_invite'));
Which will redirect your user to http://www.yoursite.com/home_invite
This means that you must have a controller called home_invite available as you can't load a view from the URL. Equally you could create a method in your existing controller and use the routes.php file to masquerade /your_controller/home_invite as /home_invite
The site_url() function is also part of the URL helper you've already included to use redirect().
If you don't want to use site_url(), you could just as well hard code the URL in like
redirect('http://www.yoursite.com/home_invite');