Laravel: Save a hasOne relationship change - laravel-5

I currently have a relationship between checklistItem and actions as followed:
public function action()
{
return $this->belongsTo(Action::class, 'action_id', 'id');
}
public function checklistItem()
{
return $this->hasOne(ChecklistItem::class, 'action_id', 'id');
}
I currently made a method, when saving an action, the checklistItem status should also change depending on what was chosen:
public static function saveFromRequest(Request $request)
{
if (($action = parent::saveFromRequest($request)) !== null){
if (!is_null($action->checklistItem)) {
$action->checklistItem->value->status = $action->switchStatusChecklist($action);
//Need to update or save this specific checklistItem
$action->checklistItem->save();
}
}
return $action;
}
function switchStatusChecklist($action)
{
switch($action->status) {
case 'closed':
$status = 'checked';
break;
case 'canceled':
$status = 'notapplicable';
break;
default:
$status = 'open';
break;
}
return $status;
}
Problem:
My checklistitem does not get updated.

Related

Shows an error when using the Gate facade

When writing privileges and rights of a user shows error: 403
Forbidden
Controller code
class IndexController extends AdminController
{
public function __construct(){
parent::__construct();
if (Gate::denies('VIEW_ADMIN')) {
abort(403);
}
$this->template = env('THEME').'.admin.index';
}
AuthServiceProvider code
public function boot()
{
$this->registerPolicies();
Gate::define('VIEW_ADMIN', function($user){
return $user->canDo('VIEW_ADMIN');
});
//
}
Model User code
The User model is associated with the Roles model, and the Roles model is associated with the Permission model.
public function canDo($permission, $require = FALSE){
if (is_array($permission)) {
dump($permission);
}
else{
foreach ($this->roles as $role) {
foreach ($this->permissions as $permission) {
if (str_is($permission,$permission->name)) {
return true;
}
}
}
}
}
You rewrite input $permission on line foreach ($this->permissions as $permission) { so your if (str_is($permission,$permission->name)) is always FALSE because
str_is(array(), 'VIEW_ADMIN') === FALSE
You should do this
public function canDo($permission, $require = FALSE){
if (is_array($permission)) {
dump($permission);
}
else{
foreach ($this->roles as $role) {
foreach ($this->permissions as $permissionObject) {
if (str_is($permission,$permissionObject->name)) {
return true;
}
}
}
}
}
Also you should add return FALSE because return type is boolean in this case.

Laravel Eloquent Filtering Results

In my controller I retrieve a list of messages from the message model. I am trying to add a filter, but the filters are cancelling each other out.
// Controller
public function __construct(Message $messages)
{
$this->messages = $messages;
}
public function index($filter = null)
{
$messages = $this->messages
->actioned($filter == 'actioned' ? false : true)
->ignored($filter == 'ignored' ? true : false)
->get();
return view('...
}
// Model
public function scopeActioned($query, $actioned = true)
{
$constraint = ($actioned ? 'whereNotNull' : 'whereNull');
return $query->$constraint('ts_actioned');
}
public function scopeIgnored($query, $ignored = true)
{
return $query->where('is_ignored', ($ignored ? 'Yes' : 'No'));
}
How can I setup Eloquent so that scopeActioned is only called if $filter is set to 'actioned', and the same for ignored?
Simple Approach:
public function index($filter = null)
{
$query = $this->messages->query();
//applying filter
if($filter == 'actioned') {
$query->actioned();
}
if($filter == 'ignored') {
$query->ignored();
}
$messages = $query->get();
return view('...
}
Another Approach is work in Scope Function.
// Model
public function scopeActioned($query, $actioned = true)
{
if($actioned) {
$query->whereNotNull('ts_actioned');
}
return $query;
}
public function scopeIgnored($query, $ignored = true)
{
if($ignored) {
$query->where('is_ignored', 'Yes');
}
return $query;
}

How to differentiate the multiple panels with login and session?

It create the session but does not go to index2 and index3 always redirect with else and go to index method but i want to go index2 and index3 to handle other panels also.
Session is created successfully for all just comming else condition all the time.
My form data and array is also showing when i using the print_r for my code to view if the data is comming or not.
Problem is it is showing no any error just redirect with file of index method.
My Controller
class Main extends CI_Controller {
public function __construct()
{
parent::__construct();
$this->load->model('Main_Model');
$this->load->helper('url');
$this->load->library('session');
$method = $this->router->fetch_method();
$methods = array('index','index2','index3');
if(in_array($method,$methods))
{
if(!$this->session->has_userdata('signup_email'))
{
redirect(base_url('Main/login'));
}
}
}
public function index()
{
if($this->session->has_userdata('signup_email'))
{
$this->load->view('BKO/index');
}
}
public function index2()
{
if($this->session->has_userdata('signup_email'))
{
$this->load->view('Admin/index');
}
}
public function index3()
{
if($this->session->has_userdata('signup_email'))
{
$this->load->view('Owner/index');
}
}
public function login()
{
//$data['select'] = $this->Main_Model->get_select();
$this->load->view('login');
}
public function login_process()
{
//$roll = $this->input->post('select');
echo $email = $this->input->post('email');
echo $pass = $this->input->post('upass');
$query = $this->Main_Model->login_process($email,$pass);
if($query == TRUE)
{
$this->session->set_userdata('signup_email');
$session = array(
'signup_email' => $email
);
$this->session->set_userdata($session);
redirect(base_url('Main/check_login'));
}
else
{
$this->session->set_flashdata('error','Invalid Email or Password');
redirect(base_url('Main/login'));
}
}
public function check_login()
{
if($this->session->userdata() == 'admin#gmail.com')
{
echo "Welcome - <h2>".$this->session->userdata('username')."</h2>";
redirect(base_url('Main/index2'));
}
elseif($this->session->userdata() == 'owner#gmail.com')
{
echo "Welcome - <h2>".$this->session->userdata('username')."</h2>";
redirect(base_url('Main/index3'));
}
else
{
echo "Welcome - <h2>".$this->session->userdata('username')."</h2>";
redirect(base_url('Main/index'));
}
}
public function logout()
{
$this->session->sess_destroy();
redirect(base_url());
}
My Model
public function login_process($email,$pass)
{
//$this->db->select('*');
//$this->db->where('roll_id',$roll);
$this->db->where('signup_email',$email);
$this->db->where('signup_password',$pass);
$query = $this->db->get('signup');
if($query->num_rows() > 0)
{
$this->session->set_flashdata('signup_email');
return true;
}
else
{
return false;
}
}
You missed the parameter here
if($this->session->userdata() == 'admin#gmail.com')
instead it should be
if($this->session->userdata('signup_email') == 'admin#gmail.com')

Controller method's result is not accessible on view in CodeIgniter

I am trying to print a controller method's result on view but it is giving me an error:
Undefined variable: $states. Can someone help me to point out what is wrong in my code?
Model code:
public function state_names() {
$query = $this->db->select('name')
->get('place')
->where('parent','India');
$query->db->get();
return $query->result();
}
Controller Code:
public function state_names() {
$st['states'] = $this->place_model->state_names();
if ($this->form_validation->run('resource_signup') == TRUE) {
if (isset($st['states']) && $st['states']->num_rows() > 0) {
$this->load->view('/web/resource_signup',$st);
}
}
return array();
}
View code:
<?php foreach ($states as $state) {
echo $state->name;
}
try this one
public function state_names() {
$this->db->select('name')
$this->db->get('place')
$this->db->where('parent','India');
$query=$this->db->get();
return $query->result_array();
}
In your model you are running query twice - for each method get(). You should run it once:
public function state_names() {
$query = $this->db->select('name')
->where('parent','India')
->get('place');
return $query->result();
}
In your controller you can't check num_rows() because there are results - not full response from database.
public function state_names() {
$st['states'] = $this->place_model->state_names();
if ($this->form_validation->run('resource_signup') == TRUE) {
if (isset($st['states'])) {
$this->load->view('/web/resource_signup',$st);
}
}
return array();
}
Your Problem is 2 place First in Model and second in controller
if (isset($st['states']) && $st['states']->num_rows() > 0)
and Model
Model Solution
public function state_names() {
$query = $this->db->select('name')
->where('parent','India')
->get('place');
// $query->db->get();
if($query->num_rows() > 0){
return $query->result();
}
}
N.B [ Here Where will be first and get will be last its good practice ];
Controller Solution :
public function state_names() {
$st['states'] = $this->place_model->state_names();
if ($this->form_validation->run('resource_signup') == TRUE) {
if (isset($st['states']) ) {
$this->load->view('/web/resource_signup',$st);
}
}
return array();
}`

How to load models in the extended MY_Router class in codeigniter

I am not able to load models to the extended My_Router class in codeigniter. Below is my code:
class MY_Router extends CI_Router {
function MY_Router()
{
parent::CI_Router();
}
function _validate_request($segments)
{
// Does the requested controller exist in the root folder?
if (file_exists(APPPATH.'controllers/'.$segments[0].EXT))
{
return $segments;
}
// Is the controller in a sub-folder?
if (is_dir(APPPATH.'controllers/'.$segments[0]))
{
// Set the directory and remove it from the segment array
$this->set_directory($segments[0]);
$segments = array_slice($segments, 1);
if (count($segments) > 0)
{
// Does the requested controller exist in the sub-folder?
if ( ! file_exists(APPPATH.'controllers/'.$this->fetch_directory().$segments[0].EXT))
{
show_404($this->fetch_directory().$segments[0]);
}
}
else
{
$this->set_class($this->default_controller);
$this->set_method('index');
// Does the default controller exist in the sub-folder?
if ( ! file_exists(APPPATH.'controllers/'.$this->fetch_directory().$this->default_controller.EXT))
{
$this->directory = '';
return array();
}
}
return $segments;
}
// Let's check if there are category segments
$category_routes = $this->category_routing($segments);
if($category_routes !== FALSE)
{
return $category_routes;
}
$user_routes = $this->user_routing($segments);
if($user_routes != FALSE)
{
return $user_routes;
}
show_404($segments[0]);
}
function category_routing($segments)
{
$this->load->model('category_model');
if($this->category_model->category_exist($segments[0]))
{
//if only category
if(count($segments)==1)
{
return array('category', 'category_browse', $segments[0]);
}
//category pagination
if(count($segments)==2 and is_numeric($segments[1]))
{
return array('category','category_browse', $segments[0], $segments[1]);
}
//category upcoming
if(count($segments)==2 and $segments[1] == 'upcoming')
{
return array('category','upcoming', $segments[0]);
}
//category upcoming pagination
if(count($segments)==3 and $segments[1] == 'upcoming' and is_numeric($segments[3]))
{
return array('category','upcoming', $segments[0], $segments[3]);
}
//category top
if(count($segments)==3 and $segments[1] == 'top')
{
return array('category','top', $segments[0], $segments[2]);
}
//category top pagination
if(count($segments)==4 and $segments[1] == 'top' and is_numeric($segments[3]))
{
return array('category','top', $segments[0], $segments[3]);
}
}
return FALSE;
}
function user_routing($segments)
{
$this->load->model('dx_auth/users', 'user_model');
if($this->user_model->check_username($segments[0]))
{
//only profile
if(count($segments)==1)
{
return array('user','profile',$segments[0]);
}
//all friends
if(count($segments)==2 and $segment[1]=='allfriends')
{
return array('user','allfriends',$segments[0]);
}
//all subscribers
if(count($segments)==2 and $segment[1]=='allsubscribers')
{
return array('user','allsubscribers',$segments[0]);
}
//all subscription
if(count($segments)==2 and $segment[1]=='allsubscriptions')
{
return array('user','allsubscriptions',$segments[0]);
}
}
return FALSE;
}
}
I have tried loading the models by using get_instance function provided by codeigniter but seems like it doesnot work. All i need is load the models in extended system library.
There is no access to the CodeIgniter super-global until CI_Base has been called which is extended by Controller. The Controller class then loads the Loader library:
// In PHP 5 the Loader class is run as a discreet
// class. In PHP 4 it extends the Controller
if (floor(phpversion()) >= 5)
{
$this->load =& load_class('Loader');
$this->load->_ci_autoloader();
}
The Router is loaded very on (have a look in system/codeigniter/CodeIgniter.php to see exactly when, on line 99) so has barely anything available.
You can use load_class('Whatever'); to load classes in a different order, but this can really screw with things if you are not careful, and you still wont have access to the database drivers.
Basically, you can't do it this way. You would need to try and directly work with the database library or use native MySQL bindings to access your data.
Here is what i did and it worked..Thanks phil for suggestion.
class MY_Router extends CI_Router {
function MY_Router()
{
parent::CI_Router();
}
function _validate_request($segments)
{
// Does the requested controller exist in the root folder?
if (file_exists(APPPATH.'controllers/'.$segments[0].EXT))
{
return $segments;
}
// Is the controller in a sub-folder?
if (is_dir(APPPATH.'controllers/'.$segments[0]))
{
// Set the directory and remove it from the segment array
$this->set_directory($segments[0]);
$segments = array_slice($segments, 1);
if (count($segments) > 0)
{
// Does the requested controller exist in the sub-folder?
if ( ! file_exists(APPPATH.'controllers/'.$this->fetch_directory().$segments[0].EXT))
{
show_404($this->fetch_directory().$segments[0]);
}
}
else
{
$this->set_class($this->default_controller);
$this->set_method('index');
// Does the default controller exist in the sub-folder?
if ( ! file_exists(APPPATH.'controllers/'.$this->fetch_directory().$this->default_controller.EXT))
{
$this->directory = '';
return array();
}
}
return $segments;
}
// Let's check if there are category segments
$category_routes = $this->category_routing($segments);
if($category_routes !== FALSE)
{
return $category_routes;
}
$user_routes = $this->user_routing($segments);
if($user_routes !== FALSE)
{
return $user_routes;
}
show_404($segments[0]);
}
function category_routing($segments)
{
if($this->check_category_exist($segments[0]))
{
//if only category
if(count($segments)==1)
{
return array('category', 'category_browse', $segments[0]);
}
//category pagination
if(count($segments)==2 and is_numeric($segments[1]))
{
return array('category','category_browse', $segments[0], $segments[1]);
}
//category upcoming
if(count($segments)==2 and $segments[1] == 'upcoming')
{
return array('category','upcoming', $segments[0]);
}
//category upcoming pagination
if(count($segments)==3 and $segments[1] == 'upcoming' and is_numeric($segments[3]))
{
return array('category','upcoming', $segments[0], $segments[3]);
}
//category top
if(count($segments)==3 and $segments[1] == 'top')
{
return array('category','top', $segments[0], $segments[2]);
}
//category top pagination
if(count($segments)==4 and $segments[1] == 'top' and is_numeric($segments[3]))
{
return array('category','top', $segments[0], $segments[3]);
}
}
return FALSE;
}
function check_category_exist($cat_name)
{
//connect to database and find the category
include(APPPATH.'config/database'.EXT);
$conn = mysql_connect($db['default']['hostname'],$db['default']['username'],$db['default']['password']);
mysql_select_db($db['default']['database'],$conn);
$sql = sprintf("SELECT COUNT(id) as count FROM categories WHERE permalink = '%s'", mysql_real_escape_string($cat_name));
$query = mysql_query($sql);
$row = mysql_fetch_object($query);
mysql_close($conn);
if($row->count)
{
return TRUE;
}
return FALSE;
}
function user_routing($segments)
{
if($this->check_username_exist($segments[0]))
{
//only profile
if(count($segments)==1)
{
return array('user','profile',$segments[0]);
}
//all friends
if(count($segments)==2 and $segments[1]=='allfriends')
{
return array('user','allfriends',$segments[0]);
}
//all subscribers
if(count($segments)==2 and $segments[1]=='allsubscribers')
{
return array('user','allsubscribers',$segments[0]);
}
//all subscription
if(count($segments)==2 and $segments[1]=='allsubscriptions')
{
return array('user','allsubscriptions',$segments[0]);
}
}
return FALSE;
}
function check_username_exist($username)
{
//connect to database and find the category
include(APPPATH.'config/database'.EXT);
$conn = mysql_connect($db['default']['hostname'], $db['default']['username'], $db['default']['password']);
mysql_select_db($db['default']['database'],$conn);
$sql = sprintf("SELECT COUNT(id) as count FROM users WHERE username = '%s'", mysql_real_escape_string($username));
$query = mysql_query($sql);
$row = mysql_fetch_object($query);
mysql_close($conn);
if($row->count)
{
return TRUE;
}
return FALSE;
}
}
The following code will solve your problem too and will make your coding lot easier and flexible.
require_once( BASEPATH . 'database/DB' . EXT );
$db = & DB();
$query = $db->query("select ...");
$results = $query->result();
When using the base CodeIgniter class in external Libraries you have to invoke it again like this:
// load it
$CI =& get_instance();
$CI->load->model('model_name');
//use it
$CI->model_name->method()
Hope that helps

Resources