PHP doesn't recognise an Object in my pattern MVC - php

I hope you could help me with this problem:
I tried to implement a pattern MVC in php + HTML5 + css. Now, apart the model, i have a problem when i try to instantiate an PHP object in one of my Controller.
In particular, i have to print the data about the authenticated user, stored in one object, $userObject, that i tried to instantiate with the DataBase data.
So I declared it, i initialized it at Null and, after, i tried to instantiate it with his constructor.
After, when i try to use it, PHP tells me: " Call to a member function getEmail() on a non-object in C:\Users\1USER\Documents\EasyPHP-DevServer-14.1VC11\data\localweb\projects\ammPHP\PHP\Controller\LoginController.php on line 99"
I show you the extract of codes about the problems:
/**the function handle_input rappresent the core of my controller, that popolates the variables of the master.PHP to make a virtual page and to visualize the user's profile.**/
private function handle_input(&$request, &$session)
{
$userObject = null;
$mysqli = new mysqli();
//login module: it verify the user data and modify the $_SESSION's array
//It makes also an object of class AuthenticatedUser that full with the database Data about the logged user.
if(isset($request["userid"]) && isset($request["password"]))
{
if($this->login($request["userid"], $request["password"]))
{
$session["loggedIn"] = true;
$mysqli->connect("localhost", "root", "password", "database");
$userid = $request["userid"];
$password = $request["password"];
$query = "SELECT * FROM loggeduser WHERE (userID = '$userid') AND (passwd = '$password');";
$result = $mysqli->query($query);
//errors checking salted
while($user = $result->fetch_object())
{
$userObject = new AuthenticatedUser($userid, $password, $user -> email, $user -> nome, $user -> cognome, $user -> dataNascita, $user -> città, $user -> CAP, $user -> indirizzo, $user -> cellulare);
}
}//user is logged-in
else if(isset($request["logout"]))
{
$this->logout();
}
//Master.php dedicated module: It verify that user is logged-in, then initialize
//the variables to popolate the master PHP and to make the virtual page of the profile's user.
if(isset($_SESSION["loggedIn"]) && $_SESSION[ "loggedIn"])
{
//CONTROLLO SULLE PAGINA RICHIESTE
if ($request["subpage"] == "profile")
{
$style = "PHP/view/LoggedUserStyle.php";
$header = "PHP/view/Header.php";
$loginFormContent = "PHP/view/loggedUserMenu.php"; //modificato col menù per utenti autenticati
$slideshow = null;
$userProfile = "PHP/view/userProfile.php";
**$user = $userObject -> getEmail(); //Here the problem, PHP tells me that $userObject is not an object! :/**
$payments = null;
$orders = null;
$notFoundContent ="PHP/view/content-not-found.php";
$footer="PHP/view/footer.php";
include("master.php");
}
[...]
}//closing function handle_input

Related

PHP set values from database

I am new and still lerning php and Im trying to set values that Im retrieving from postgresql database, but Im having problems with my code that i cant figure out and I hope someone here can help me. :)
This is the code:
public function __construct($username, $password)
{
$config = new Config();
$dbconn = pg_connect($config->getDbDsn()); // getDbDsn contains all the information that is needed to connect to the database.
$query = "SELECT username, password, id FROM user.member WHERE username = '$username'";
$result = pg_query($dbconn, $query);
$db = pg_fetch_all($result);
if($db)
{
foreach($db as $d)
{
if( $d['username'] == $username && $d['password'] == $password)
{
$this->verified = true;
$this->id = $d['id']; //save id does not work
$this->user = $d['username']; // save username does not work
}
else
{
$this->verified = false;
}
}
}
else
{
$this->verified = false;
}
}
Okay, this is what im trying to do. First im asking the database to give me the informationen from the table, that is a match to my users username and password. I am using a bool (verified) to verify the user. That works fine. But then, when Im trying to set the values of username and id for my user, that is impossible. If im creating a set_val-function (just to test my code, to try to find my error):
private $a = "";
private function set_val($data){ $this->a = $data; }
and I use that function to set value, in my construct-function:
$this->set_val('hello');
that works fine, until I put that function in my if($db)-statment, then it doesnt work anymore. (it works fine if I put it outside my if($db)-statement, like directly under $db = pg_fetch_all($result);).
$db = pg_fetch_all($result);
$this->set_val('hello'); // This works fine
if($db)
{
$this->set_val('hello'); // This does not work at all
foreach($db as $d)
$this->set_val('hello'); // And not this
}
For my get_val I have this code:
public function get_val(){
return $this->a;
}
(I also have the same get-functions for id and username)
And here Im trying to echo my value, which works fine, if I put the set_val-function outside my if-statement (and foreach-statement):
public function echo_val(){
echo $this->get_val();
}

Using password_hash and password_verify from different objects in OO PHP

I'm writing an MVC style application using OO PHP and have run into an issue when trying to use different classes when trying to register/login users. Essentially, I have an abstract User class holding some common properties and functions and 2 classes which extend this: a LoginUser class created when a user attempts to login and a RegisterUser class created when a user attempts to register.
My issue is this: When I successfully add a user to my database using a query that is called in the RegisterUser class (using the password_hash function on the password) and then try to login via a query called in the LoginUser class (using the password_verify function) the query result returns false, even when the password supplied is definitely the password that was entered at registration.
My question is this: Does the password_verify function have to be called by an object of the same class that used the password_hash function to create the hash? If so, why? I have tried looking at the PHP documentation and search results do not return an answer either!
The reason that I ask this is because the registration/login will succeed if all of the functions are held in a single User class, instead of inherited classes.
My User class:
abstract class User {
protected $checkedUserName = '';
protected $checkedPassword = '';
public function __construct($uncheckedUserName, $uncheckedPassword) {
$this->checkedUserName = $this->validateAndSanitizeUserName($uncheckedUserName);
$this->checkedPassword = $this->validateAndSanitizePassword($uncheckedPassword);
}
protected function validateAndSanitizeUserName($uncheckedUserName) {
$string = filter_var($uncheckedUserName, FILTER_VALIDATE_EMAIL); // Checks input is an email
$string = filter_var($string, FILTER_SANITIZE_EMAIL); // Removes illegal chars
$string = filter_var($string, FILTER_SANITIZE_SPECIAL_CHARS); // Removes HTML tags, etc replacing them with char codes
return $string;
}
protected function validateAndSanitizePassword($uncheckedPassword) {
$string = filter_var($uncheckedPassword, FILTER_VALIDATE_REGEXP, ["options"=>["regexp"=>"/(?=.*\d)(?=.*[a-z])(?=.*[A-Z]).{8,}/"]]); // Checks the password against the regex on the form
$string = filter_var($string, FILTER_SANITIZE_SPECIAL_CHARS); // Removes HTML tags, etc replacing them with char codes
return $string;
}
protected function checkIfUserExists() {
// Set the initial status of user exists
$userExists = false;
// Open a connection to the database
$con = Db::getInstance();
// Prepare the query
$checkIfUserExists = $con->prepare("SELECT * FROM users2 WHERE username=?");
//Execute the query with the checked username
$checkIfUserExists->execute([$this->checkedUserName]);
// Set $userExists dependent on result
if($checkIfUserExists->rowCount() !== 0) {
$userExists = true;
}
return $userExists;
}
}
My LoginUser class:
class LoginUser extends User{
public function __construct($uncheckedUserName, $uncheckedPassword) {
parent::__construct($uncheckedUserName, $uncheckedPassword);
}
private function getPasswordHashes() {
// Only connect to the database when connection is needed
$con = Db::getInstance();
// Check if username and password match
// Prepare the query
$checkUser = $con->prepare("SELECT * from users2 WHERE username = ?");
// Execute the query using an array to bind the parameter to ?
$checkUser->execute([$this->checkedUserName]);
return $checkUser;
}
public function getLogInResult() {
// Initialise the results variable
$resultsFound = 0;
// Only proceed if the username actually exists
if($this->checkIfUserExists()) {
// Call the function to get the records that match the username
$checkUser = $this->getPasswordHashes();
// Check to see if exactly one match was found and verify the password
if($checkUser->rowCount() === 1) { // Note this may not work in other databases - it does in MySQL
foreach($checkUser as $user) {
if(password_verify($this->checkedPassword, $user['passwordHash'])) {
$resultsFound++;
}
}
}
return $resultsFound;
}
}
}
My RegisterUser class:
lass RegisterUser extends User{
private $checkedFirstName = '';
private $checkedLastName = '';
public function __construct($uncheckedUserName, $uncheckedPassword, $uncheckedFirstName, $uncheckedLastName) {
parent::__construct($uncheckedUserName, $uncheckedLastName);
$this->checkedFirstName = $this->sanitizeString($uncheckedFirstName);
$this->checkedLastName = $this->sanitizeString($uncheckedLastName);
}
private function sanitizeString($uncheckedString) {
$string = filter_var($uncheckedString, FILTER_SANITIZE_STRING);
return $string;
}
private function insertUserDetails() {
// Hash the supplied password in preparation for insertion
//$hashedPassword = password_hash($this->checkedPassword, PASSWORD_DEFAULT);
// Connect to the database
$con = Db::getInstance();
// Prepare the query
$addUser = $con->prepare("INSERT INTO users2 VALUES (?, ?, ?, ?)");
// Execute the query using an array to bind the parameters
$addUser->execute([$this->checkedUserName, password_hash($this->checkedPassword, PASSWORD_DEFAULT), $this->checkedFirstName, $this->checkedLastName]);
// Return the result
return $addUser;
}
public function getRegisterResult() {
// Initialise the variable to store the result state
$result = false;
// Only proceed if the username does not exist
if(!($this->checkIfUserExists())) {
$addUser = $this->insertUserDetails();
// If the details were successfully added
if($addUser->rowCount() === 1) {
$result = true;
}
}
return $result;
}
}
So, when completing the registration form, the getRegisterResult() function is called on a new RegisterUser object. When logging in, the getLoginResult() function is called on a new LoginUser object but the result returns false...
In answer to my question, it doesn't matter which classes use password_hash and password_verify, if there's a match with the password to verify and the hash from the database it should return a positive result!
The issue was with __construct() for the RegisterUser class - the call to the parent passed in $uncheckedLastName rather than the $uncheckedPassword and therefore the password being set at registration was not what was supplied in the password field but that what was supplied in the LastName field!

Undefined index error when trying to echo values, I am using functions outside of the class

Hey guys I have a question and I still consider myself pretty new at coding, so forgive me if I come off foolish.
I am studying in school as of now and we have a project to build a full stack recreation of craigslist. Any who the problem I am having deals with PHP. I have created an account page with text areas. I would like to echo out the user's information on their so the user can see what he put on and update as he likes. Since my navbar is included on every page, I added the code:
if(isset($_SESSION['logged_in_user'])){
var_dump($_SESSION['logged_in_user']);
$user = $_SESSION['logged_in_user'];
var_dump($user);
}
on my account page I figured I can echo it out as
<?= $attributes['first_name']?> within the placeholders. But I keep getting:
Undefined index: first_name
Also when I var_dump($user) I get an protected $attributes array.
In My Auth class is where I first defined $user as such:
public static function attempt($attemptedUsername, $attemptedPassword) {
$user = User::findByUserName($attemptedUsername);
if ($user == null) {
return false;
}
$validPassword = password_verify($attemptedPassword,$user->password);
if ($validPassword == true) {
$_SESSION['logged_in_user'] = $user;
}
return false;
}
and my findByUserName function is in the user class. the code is:
public static function findByUserName($user_name){
// Get connection to the database
self::dbConnect();
$stmt = self::$dbc->prepare('SELECT * FROM users WHERE user_name = :user_name');
$stmt->bindValue(':user_name', $user_name , PDO::PARAM_STR);
//execute gets its own line, t or false
$stmt->execute();
$result=$stmt->fetch(PDO::FETCH_ASSOC);
// #TODO: Create select statement using prepared statements
// #TODO: Store the result in a variable named $result
// The following code will set the attributes on the calling object based on the result variable's contents
$instance = null;
if ($result) {
$instance = new static($result);
}
return $instance;
}
Your problem seems to be with not being able to access the variable $user outside of the static method attempt() this can be fixed by declaring the variable globally at the beginning of the method attempt() like this:
public static function attempt($attemptedUsername, $attemptedPassword) {
global $user;
$user = User::findByUserName($attemptedUsername);
if ($user == null) {
return false;
}
$validPassword = password_verify($attemptedPassword,$user->password);
if ($validPassword == true) {
$_SESSION['logged_in_user'] = $user;
}
return false;
}
More information can be found on this in the PHP documentation here.

Can't pass mysqli object to class in PHP

So I'm working on a simple user class in php, which has a class variable which contains the mysqli object, however I keep getting the error:
Fatal error: Call to a member function real_escape_string() on a non-object in */classes/user.php on line X
I've checked everything, it should work, but it doesn't. Somehow. This is my code:
namespace bibliotheek;
class user
{
private $mysql;
private $logged_in = false;
private $user_data = null; //ARRAY: user_id, e-mail, password, bevoegdheid, naam, achternaam, adres, postcode, stad
function __construct(\mysqli $mysql, $salt)
{
$this->mysql = $mysql;
}
public function login($email, $pass, $hash = false)
{
$email = $this->mysql->real_escape_string($email);
if($hash == false)
$pass = sha1($this->salt.$pass);
$query = "SELECT *
FROM gebruikers
WHERE gebruikers.email = '$email' AND gebruikers.password = '$pass'";
$result = $this->mysql->query($query);
$user_data = $result->fetch_assoc();
if($user_data == null)
return;
$this->logged_in = true;
$this->user_data = $user_data;
$this->create_cookies($email, $pass);
}
}
And this is how the mysqli object gets passed to the class:
$mysql = new mysqli($cfg['mysql_server'], $cfg['username'], $cfg['password'], $cfg['database']);
$user = new bibliotheek\user($mysql, $cfg['salt']);
the mysql login data is correct, I've made sure of that.
I must be missing something really obvious here, but I just can't see it. Any help is greatly appreciated. Thanks!
And this is how it should be
error_reporting(E_ALL);
$mysql = new mysqli($cfg['mysql_server'], $cfg['username'], $cfg['password'], $cfg['database']);
if ( !$mysql )
{
throw new Exception(mysqli_connect_error()));
}
$user = new bibliotheek\user($mysql, $cfg['salt']);
I'm really f-ing stupid, I compacted my code a bit when I posted it on here and I left out this part:
$this->mysql = $mysql;
$this->mysql = $salt;
Kill me now.

I am a new programmer and I can not get my fields to be stored in the database from a registration form

If I declare a global variable such as a database connection of $mysqli how do I use that in a class. i am trying to use it in my user class. Do i store it as a public variable in the class or as a global in the function itself. I also think there is something wrong with my following code but I may be wrong.
class USER
{
function __constructor()
{
}
/*
* adds a new user
* returns FALSE on error
* returns user id on success
*/
function add_member($name, $email, $password)
{
global $mysqli;
$query = "INSERT INTO members
SET
user_name = {'$name'},
user_email = {'$email'},
password = ['$password'}";
$success = $mysqli -> query ($query);
if (!$success || $mysqli -> affected_rows == 0)
{
echo "<p> An error occurred: you just are not tough enough!!!</p>";
return FALSE;
}
$uid = $mysqli -> insert_id;
return $uid;
}
} // end class
$uc = new USER();
?>
<?php
require_once ('includes/classes/database.php');
require_once('includes/classes/user.php');
require_once('includes/header.php');
// if user submits a new registration
if (isset($_POST['name'],$_POST['email'],$_POST['pwd'],$_POST['pwd2']))
{
// validate input fields
$name = $_POST['name'];
$email = $_POST['email'];
$password = $_POST['pwd'];
$password2 = $_POST['pwd2'];
// if error fall through and redisplay page with errors
// if no errors update database and redirect to homepage
if ($uc->add_member($name, $email, $password) === FALSE)
{
echo "System Error. damn if I know what to do";
}
else
{
header("location: homepage.php");
}
}
You um... don't. Instead use a variable inside of the class:
class USER
{
private $mysql;
function __constructor($mysqli)
{
$this->mysqli = $mysqli;
}
function add_member($name, $email, $password)
{
$mysqli = $this->mysqli;
/* yada yada */
Couple of issues by the way:
// You want the ' outside of the {}
$query = "INSERT INTO members
SET
user_name = '{$name}',
user_email = '{$email}',
password = '{$password}'";// there was a [ not a {
You also want to call mysqli_real_escape_string on all of those variables. Or better yet use mysqli_bind_param and a prepared statement.

Categories