I'm beginner in PHP and phalcon, I want to use custom validation and creating default value.
My controller is:
use Phalcon\Mvc\Controller;
class OspoController extends Controller
{
public function indexAction()
{
}
public function createAction()
{
$ospo = new Ospos();
// Store and check for errors
$success = $ospo->save(
$this->request->getPost(),
array('isEmailConfirmed', 'email', 'password', 'salt' ,'phoneNum', 'verifiedPhoneStatus', 'languageId', 'firstName', 'lastName', 'address', 'cityId', 'provId', 'countryId', 'postCode')
);
$data = array();
if ($success) {
$data[] = array(
'status' => 'success'
);
echo json_encode($data);
} else {
foreach ($ospo->getMessages() as $message) {
$msg = $message->getMessage();
$data[] = array(
'message' => $msg
);
}
echo json_encode($data);
}
$this->view->disable();
}
I want if isEmailConfirmed is null - I want to create value that isEmailConfirmed = 0;
How to change array value of getPost()?
(can I do this) Should i change the code with
$isEmailConfirmed = $_POST['isEmailConfirmed'];
and
$ospo->save($isEmailConfirmed, $etc, $etc)?
Thank you.
First of all, you can just store POST data in a variable. Then just check for null and assign default value if needed before saving.
$data = $this->request->getPost();
if (!isset($data['isEmailConfirmed']) {
$data['isEmailConfirmed'] = 0;
}
Another way is to save null value, but in that case you should set up DEFAULT for that column in your database table.
Related
Using sessions we can achieve this, but need this without sessions or cookies.
<?php
class Employees extends CI_Controller
{
public function __construct()
{
parent::__construct();
}
public function auth() {
$adminEmail = $this->input->post('adminEmail');
$adminPassword = $this->input->post('adminPassword');
if ($adminEmail != "" && $adminPassword != "") {
$query = $this->db->query("select * from admin_tbl where email= '$adminEmail' and password = '$adminPassword'");
//if user exist
if ($query->num_rows() <= 0) {
$response = array();
$jwtoken = "";
$this->session->set_flashdata("invalid", "Wrong email or password");
$response = array(
'status' => 'invalid',
'message' => $_SESSION['invalid'],
'token' => $jwtoken,
);
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
} else {
// $this->session->set_userdata('adminEmail', $adminEmail);
$response = array();
$jwt = new JWT();
$data = array(
'adminEmail' => $adminEmail,
'iat' => time()
);
$jwtoken = $jwt->encode($data, jwtSecretKey, 'HS256');
// I want to pass $jwtoken's variable to all the functions in a controller
$this->session->set_flashdata("login", "Scucessfully login!");
// if (isset($_SESSION['adminEmail'])) {
if ($jwtoken != "") {
$response = array(
'status' => 'valid',
'message' => $_SESSION['login'],
'token' => $jwtoken
);
}
$abc = $jwtoken;
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
}
}
}
public function addNew()
{
$response = array();
$this->auth(); // this value is always null returned by auth() method
}
}
?>
This is more of a OOP programming basics question. If you want to re-use a variable in another function of the same controller object, you have to set the variable globally for the Employees class and then set/get its value in your functions by using $this->yourVariableName. But the set value of the object instance can only be reused in that instance only. Which means that after the auth() function, another function should be called subsequently to "access" the $this->yourVariableName.
Another way is to pass the $jwtoken as a parameter to a function.
But the following code answers your question "How to pass calculated/final value of one function to other functions in a controller of Codeigniter application", if it doesn't, then your question should be corrected I guess.
Edit:
Ow ok, first the auth() function is being called, then you would like to pass the $jwtoken value to another function, am I right? Well once a function is finished executing, the variable "disappears" if not passed to another function. If you would like to process the $jwtoken value immediately within the auth() function, then the answer is to pass the $jwtoken value to another function from within the auth() function:
<?php
class Employees extends CI_Controller
{
public function __construct() {
parent::__construct();
}
public function auth() {
$adminEmail = $this->input->post('adminEmail');
$adminPassword = $this->input->post('adminPassword');
if ($adminEmail != "" && $adminPassword != "") {
$query = $this->db->query("select * from admin_tbl where email= '$adminEmail' and password = '$adminPassword'");
//if user exist
if ($query->num_rows() <= 0) {
$response = array();
$jwtoken = "";
$this->session->set_flashdata("invalid", "Wrong email or password");
$response = array(
'status' => 'invalid',
'message' => $_SESSION['invalid'],
'token' => $jwtoken,
);
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
} else {
// $this->session->set_userdata('adminEmail', $adminEmail);
$response = array();
$jwt = new JWT();
$data = array(
'adminEmail' => $adminEmail,
'iat' => time()
);
$jwtoken = $jwt->encode($data, jwtSecretKey, 'HS256');
// I want to pass $jwtoken's variable to all the functions in a controller
// this is one way you can pass the value to another function, depending on what you want to do, you can also place a condition and continue only if the return value of the following function is respected:
$this->addNew($jwtoken);
// What is the addNew() supposed to do?
$this->session->set_flashdata("login", "Scucessfully login!");
// if (isset($_SESSION['adminEmail'])) {
if ($jwtoken != "") {
$response = array(
'status' => 'valid',
'message' => $_SESSION['login'],
'token' => $jwtoken
);
}
$abc = $jwtoken;
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
}
}
}
public function addNew($jwtoken = "default_value_if_not_set") {
echo $jwtoken;
}
}
Since you are creating an API, I assume the API is a REST api and stateless, so there is no interference of sessions and cookies.
I assume your process works like this:
User does a login request from the app to the api and the api returns a token when the credentials check is valid
The token is stored in the app (in a local database for example) and used for other requests
So the only thing you need to do is (I assume you have a route to addNew):
public function addNew() {
$token = $this->input->get('token');
$loginData = $this->validateToken($token);
//... add new process
}
And from your app you need to pass the token with the request to the api.
How do you validate the token?
To obtain the data you have set in the token, you have to decode the token:
/**
* throws SignatureInvalidException
*/
function validateToken($token)
{
$jwt = new JWT();
return $jwt->decode($token, jwtSecretKey, 'HS256');
}
Code improvement
Avoid using sessions and cookies
Since your api is stateless, you have to avoid settings cookies or sessions. So in your controller you can remove the flash data helper:
public function auth() {
$adminEmail = $this->input->post('adminEmail');
$adminPassword = $this->input->post('adminPassword');
if ($adminEmail != "" && $adminPassword != "") {
$query = $this->db->query("select * from admin_tbl where email= '$adminEmail' and password = '$adminPassword'");
//if user exist
if ($query->num_rows() <= 0) {
$response = array();
$jwtoken = "";
# REMOVE THIS LINE
# $this->session->set_flashdata("invalid", "Wrong email or password");
$response = array(
'status' => 'invalid',
'message' => "Wrong email or password", //CHANGE THIS LINE
'token' => $jwtoken,
);
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
} else {
// $this->session->set_userdata('adminEmail', $adminEmail);
$response = array();
$jwt = new JWT();
$data = array(
'adminEmail' => $adminEmail,
'iat' => time()
);
$jwtoken = $jwt->encode($data, jwtSecretKey, 'HS256');
// I want to pass $jwtoken's variable to all the functions in a controller
# REMOVE THIS LINE
# $this->session->set_flashdata("login", "Scucessfully login!");
// if (isset($_SESSION['adminEmail'])) {
if ($jwtoken != "") {
$response = array(
'status' => 'valid',
'message' => "Scucessfully login!", //CHANGE THIS LINE
'token' => $jwtoken
);
}
$abc = $jwtoken;
//used to send finalized values
$this->output
->set_content_type('application/json')
->set_output(json_encode($response));
return $jwtoken; //return value
}
}
}
Return the output response instead of $jwtoken
In your response you have already set the the token, so you can simply return the response:
return $this->output
->set_content_type('application/json')
->set_output(json_encode($response));
Your query is vulnerable to sql injections
Use escape method around you variables or bind the params:
$sql = "select * from admin_tbl where email=? and password = ?";
$query = $this->db->query($sql, array($adminEmail, $adminPassword));
I'm wondering how I can loop insert an array value to database through Laravel.
A sample of a Json is here:
[{"rid":"252","recipient_id":"1","email_type":"Body","to_cc_bcc":"to","start_dte":"2016-05-18","end_dte":""},{"rid":"252","recipient_id":"5","email_type":"Body","to_cc_bcc":"to","start_dte":"2016-05-18","end_dte":""}]
And my controller for storing such is this:
public function store()
{
// validate
// read more on validation at http://laravel.com/docs/validation
$rules = array(
'name' => 'required',
);
$validator = Validator::make(Input::all(), $rules);
// process the login
if ($validator->fails()) {
return Redirect::to('reports')
->withErrors($validator)
->withInput(Input::except('password'));
} else {
//Dump Recipient array
$cleanRecipients = json_decode(Input::get('test'), true);
foreach($cleanRecipients AS $value)
{
$report_recipient = new ReportRecipients;
$report_recipient->recipient_id = $value['recipient_id'];
$report_recipient->rid = $value['rid'];
$report_recipient->email_type = $value['email_type'];
$report_recipient->to_cc_bcc = $value['to_cc_bcc'];
$report_recipient->start_dte = !empty($value['start_dte']) ? $value['start_dte'] : null;
$report_recipient->end_dte = !empty($value['end_dte']) ? $value['end_dte'] : null;
}
$report_recipient->save();
// redirect
Session::flash('message', 'Report was Successfully Saved!');
return Redirect::to('reports');
What happens is that, it only stores the last set of values into the table and not all of them. I appreciate any help and thanks in advance.
Put your save() inside your loop. Also, you should do it in one transaction, to be atomic.
\DB::transaction(function() use($cleanRecipients) {
foreach($cleanRecipients AS $value) {
$report_recipient = new ReportRecipients;
$report_recipient->recipient_id = $value['recipient_id'];
$report_recipient->rid = $value['rid'];
$report_recipient->email_type = $value['email_type'];
$report_recipient->to_cc_bcc = $value['to_cc_bcc'];
$report_recipient->start_dte = !empty($value['start_dte']) ? $value['start_dte'] : null;
$report_recipient->end_dte = !empty($value['end_dte']) ? $value['end_dte'] : null;
$report_recipient->save();
});
You need to put $report_recipient->save(); inside your foreach loop.
Below code works adding single single entry i want to store multiple parent_id and user_id
public function test($p_id, $pl_id)
{
$CheckRelationship = UsersRelationship::where('parent_user_id', $p_id )->where('child_user_id', $pl_id )->first();
if( $CheckRelationship )
{
return Response::json( [
'ok'=> false,
'message'=> 'The profiles are currently linked '
] ,422);
}
$user = User::find( $pl_id );
$user->p_id = $p_id;
$user->updated_by = $p_id;
//$user->status = 1;
$user->save();
$UsersRelationship = new UsersRelationship;
$UsersRelationship->parent_user_id = $parent_id;
$UsersRelationship->child_user_id = $player_id;
$UsersRelationship->save();
return Response::json( [
'ok'=> true,
'message'=> 'Linked',
] ,200);
}
I want to pass multiple value
$UsersRelationship = new UsersRelationship;
$UsersRelationship->parent_user_id = $parent_id; //single value passing
$UsersRelationship->child_user_id = $player_id; //single value passing
$UsersRelationship->save();
foreach($UsersRelationship as $k=>$values){
$UsersRelationship['parent_user_id'] = $values;
$UsersRelationship['child_user_id'] = $values;
$UsersRelationship->save();
}
doesn't work for me please suggest where i am mistaking early reply highly appreciated thanks in advance
Parameters in URLs will work only for a singular user relationship. If you wish to pass multiple relationships, JSON is your friend.
JSON Sample:
[
{
'parent_user_id': 1,
'child_user_id': 2,
},
{
'parent_user_id': 2,
'child_user_id': 2,
}
]
PHP controller function:
public function test(\Illuminate\Http\Request $request) {
//Pass your information through a GET parameter or POST it through a form
// 'user_relationship' is the name of the field, expecting data in JSON format
$user_relationships = json_decode($request->get('user_relationship'));
//array to store all relationships that were not linked
$relationshipsNotLinked= [];
//Loop through each relationship, attach where possible
foreach($user_relationships as $user_relationship_row) {
$CheckRelationship = UsersRelationship::where('parent_user_id', $user_relationship_row['parent_user_id'] )->where('child_user_id', $user_relationship_row['child_user_id'] )->first();
//If exists, we don't save.
if( $CheckRelationship ) {
$relationshipsNotLinked[] = $user_relationship_row['child_user_id'];
} else {
//Else we link relationship
//Not sure what the links below does..
//users cannot have `p_id` attribute, given that they may have multiple parents. Same goes for 'updated_by' attribute
$user = User::find( $user_relationship_row['parent_user_id'] );
$user->updated_by = $user_relationship_row['parent_user_id'];
//$user->status = 1;
$user->save();
//Save relationship
$UsersRelationship = new UsersRelationship();
$UsersRelationship->parent_user_id = $user_relationship_row['parent_user_id'];
$UsersRelationship->child_user_id = $user_relationship_row['child_user_id'];
$UsersRelationship->save();
}
}
if(count($relationshipsNotlinked)) {
//Some relationships were not linked, we display an error message
return Response::json( [
'ok'=> false,
'message'=> 'The following profiles are already linked: '.implode(',',relationshipsNotLinked),
] ,422);
} else {
//Display success message
return Response::json( [
'ok'=> true,
'message'=> 'Linked',
] ,200);
}
}
Yii 2 Docs explains that I can set the fields that should be returned by default by toArray().
(http://www.yiiframework.com/doc-2.0/yii-base-model.html#fields()-detail)
Theres any possibility to ignore when contains null values?
function fields() {
return [
'email', // Ignore if email is null.
'fullName', // Ignore if fullName is null.
];
}
Try this:
function field() {
$return = [];
if(!empty($this->email)) {
$return[] = 'email';
}
if(!empty($this->fullName)) {
$return[] = 'fullName';
}
return $return;
}
I have file (ProfileController.php) which contains the following code:
public function editAction() {
if (Zend_Auth::getInstance()->hasIdentity()) {
try {
$form = new Application_Form_NewStory();
$request = $this->getRequest();
$story = new Application_Model_DbTable_Story();
$result = $story->find($request->getParam('id'));
// $values = array(
// 'names' => $result->names,
// 'password' => $result->password,
// );
if ($this->getRequest()->isPost()) {
if ($form->isValid($request->getPost())) {
$data = array(
'names' => $form->getValue("names"),
'password' => $form->getValue("password"),
);
$form->populate($data->toArray());
$where = array(
'id' => $request->getParam('id'),
);
$story->update($data, $where);
}
}
$this->view->form = $form;
$this->view->titleS= $result->title;
$this->view->storyS= $result->story;
} catch (Exception $e) {
echo $e;
}
} else {
$this->_helper->redirector->goToRoute(array(
'controller' => 'auth',
'action' => 'index'
));
}
}
and another file (edit.phtml) with following code:
<?php
try
{
$tmp = $this->form->setAction($this->url());
//$tmp->titleS=$this->title;
//$tmp->storyS=$this->story;
//echo $tmp->title = "aaaaa";
}
catch(Exception $e)
{
echo $e;
}
?>
I would like the users to be able to edit their Username and password. How do I go about it?
First: move the Zend_Auth stuff up to init() or preDispatch(), that way Auth will run against any or all actions in the controller.
The trick in getting more then one submit button to work is to give the buttons different names so that getParam('') has something to work with.
Normally I only do this sort of thing when doing deletes, for edit's or update's I just submit the whole array back to the database. I typically use the Zend_Db_Table_Row save() method instead of Zend_Db_Table's insert() or update() so the mechanism is a little different.
I just use a simple form to perform an update, here is the controller code (the view just echo's the form):
//update album information
public function updatealbumAction()
{ //get page number from session
$session = new Zend_Session_Namespace('page');
//get album id
$id = $this->getRequest()->getParam('id');
$model = new Music_Model_Mapper_Album();
//fetch the album database record
$album = $model->findById($id);
$form = new Admin_Form_Album();
//this form is used elsewhere so set the form action to this action
$form->setAction('/admin/music/updatealbum/');
if ($this->getRequest()->isPost()) {
if ($form->isValid($this->getRequest()->getPost())) {
$data = $form->getValues();//get valid and filtered form values
$newAlbum = new Music_Model_Album($data);//create new entity object
$update = $model->saveAlbum($newAlbum);//save/update album info
$this->message->addMessage("Update of Album '$update->name' complete!");//generate flash message
$this->getHelper('Redirector')->gotoSimple('update', null, null, array('page' => $session->page));//redirect back to the page the request came from
}
} else {
$form->populate($album->toArray());
$this->view->form = $form;
}
}
This is a pretty common update action.
Now here is how you might use different request parameters to perform an action on a record. I use this to delete database records but anything is possible.
public function deleteAction()
{
$session = new Zend_Session_Namespace('page');
$request = $this->getRequest()->getParams();
try {
switch ($request) {
//if
case isset($request['trackId']):
$id = $request['trackId'];
$model = new Music_Model_Mapper_Track();
$model->deleteTrack($id);
$this->message->addMessage("Track Deleted!");
break;
case isset($request['albumId']):
$id = $request['albumId'];
$model = new Music_Model_Mapper_Album();
$model->deletealbum($id);
$this->message->addMessage("Album Deleted!");
break;
case isset($request['artistId']):
$id = $request['artistId'];
$model = new Music_Model_Mapper_Artist();
$model->deleteArtist($id);
$this->message->addMessage("Artist Deleted!");
break;
default:
break;
}
$this->getHelper('Redirector')->gotoSimple('update', null, null, array('page' => $session->page));
} catch (Exception $e) {
$this->message->addMessage($e->getMessage());
$this->getHelper('Redirector')->gotoSimple('update', null, null, array('page' => $session->page));
}
}
you can pass the request parameters as submit button labels or as urls or whatever works for you.
Good Luck!