How can I show 404 error page when the ID is null? - database

I create a table in MYSQL. I insert some data into the table.
My question is about error when ID is NULL.
When the URL is ".com/blog/post/1" The content has ID 1 seen perfectly as well as the other ID's contents. But the problem is that I couldn't solve (because I am newbie in Codeigniter) when the url is ".com/blog/post" an error occurs.
I think the problem the "post/" needs and ID number after itself but how to change the error with a page like this shown below
Forbidden
You don't have permission to access /post/ on this server.

In your blog controller when somebody calls for a post then you can check if id is there, if not you can redirect them to blog index.
The blog controller will look like this.
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class Blog extends CI_Controller {
function __construct()
{
parent::__construct();
}
function index()
{
//List posts with title and excerpts and a read more link
}
function post($id=NULL)
{
if($id)
{
//Show detailed post
}
else
{
redirect('blog');
}
}
}

You can pass the ID to the function as a parameter; Like this;
public function post($id = false)
{
if (!$id)
{
// No ID supplied
}
else
{
// ID found.
// Carry on....
}
}
Hope this helps.

Related

Axios - receiving a 404 error when trying to delete user from database

so I'm currently trying to delete a user from a mySql database on clicking a delete button. The app is Laravel backend, React front end.
When I click the delete button, it returns a 404 error 'DELETE http://localhost:8000/delete/5 404 (Not Found)'
onDelete method:
onDelete(user_id) {
axios.delete('http://localhost:8000/users/delete/' + user_id)
.then((response) => {
})
}
UserController
public function destroy($id)
{
$user = User::find($id);
$user->delete();
}
Button in code:
<button onClick={this.onDelete.bind(this, Users.id)}>Delete</button>`
Web Route:
Route::delete('users/delete/{id}', 'Api\UserController#destroy');
The error contains the correct id (the last number in the error code url is the correct id of the user I'm trying to delete) but I've got no idea why it's giving me a 404 error.
Update Turns out the delete route isn't in my route list. (php artisan route:list)
Route::get('userList', 'Api\UserController#index');
Route::post('users/store', 'Api\UserController#store');
Route::delete('users/delete/{id}', 'Api\UserController#destroy');
Strange because the get and post routes are in the route list, but not my delete route. (The above code is in my web.php file) All three methods (index, store and destroy) are inside my UserController controller:
public function index()
{
$result = User::all();
return $result;
}
public function store(Request $request)
{
$user = new User();
$user->name = $request->user_name;
$user->email = $request->user_email;
$user->phone_number = $request->user_phoneNumber;
$user->account_type = $request->user_accType;
$user->qualifications = $request->user_qualifications;
$user->save();
}
public function destroy($id)
{
$user = User::find($id);
$user->delete();
}
The first is to understand whats the error code is saying, according to this 404 Not Found client error response code indicates that the server can't find the requested resource, first of try to clean this in a way
onDelete(user_id) {
url = `http://localhost:8000/users/delete/${user_id}`;
//here make sure url is fine with Id
axios.delete(url)
.then((response) => {
})
}
after this you have to check in the network call, either the request is going fine to the server with id or not. then lastly double check api is expecting the delete call or its expecting the get call with id for deletion, because many backend guys delete records by using get calls. ping me back if still is not fixed.

How to get this code work to store in Laravel. No errors and no storage

I can't store name and IP address to DB. I created a table 'info' with appropriate fields by running php artisan migrate.
A schema
Schema::create('info', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('ip');
$table->timestamp('created_at')->nullable();
});
A model for Info
class Info extends Model
{
protected $fillable = ['ip', 'name'];
}
Maybe the problem is in my HomeController where I get those variables?
<?php
namespace App\Http\Controllers;
use Illuminate\Foundation\Auth\User as Authenticatable;
use App\Info;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\Auth;
use Request;
class HomeController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}
public function store(Request $request) {
Info::create(['info' => $request->input('info')]);
}
public function index()
{
if (Auth::check())
{
$name = Auth::user()->name;
$ip = Request::ip();
\App\Events\eventIp::dispatch($ip,$name);
return view('home');
}
}
}
My routes in web.php
Route::post('/home','HomeController#store');
Route::get('/home', 'HomeController#index')->name('home');
});
But it doesn't work. Gives no errors and no records in DB.
Something make me think that it have to do with my index function. I got info in function index and maybe function store doesn't have a clue what I mean.
A controller action is basically a method that usually gets executed when you open an url (as you connect them to routes).
In your example you have connected two routes to their respective actions:
Route::post('/home','HomeController#store');
Route::get('/home', 'HomeController#index')->name('home');
Now, when you log in succesfully, imagine that you end up in the page with url http://localhost:8000/home in your web browser.
The key difference is the method which you use to call your route (you can get an overview of the differences here), in your case you are using GET method.
The resulting action executed it the one associated to /home route with the GET method, that is the HomeController#index action (or method).
The store method, although is in the same HomeController class, doesn't get triggered unless you execute the /home route, but with the POST method.
You can confirm that if you put a debug message in each of the methods like this:
class HomeController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}
public function store(Request $request)
{
echo 'I will not be executed';
}
public function index()
{
echo 'I have been executed';
}
}
If you want to simply save a info record when you visit the /home route with the GET method, you can put the save in the index method itself and get rid of the store method:
class HomeController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}
public function index()
{
// You can omit Auth::check() because you are using the auth middleware
// that exactly does this job.
Info::create([
'name' => Auth::user()->name,
'ip' => Request::ip(),
]);
return view('home');
}
}
Keep in mind that doing in this way you will get a new database record for each page view you make to that route (if you keep refreshing the page, you should see new records being added to database).
Update
When you use Eloquent Models, laravel will look for a table named after the pluralized model name (Info model will try to use infos table).
However you created a table named info. To solve that you can either rename the table and rerun the migration with php artisan migrate:refresh (it will delete all the existing data in the database you are using for your laravel app)
Or specify the table name to use for that laravel model:
class Info extends Model
{
protected $table = 'info';
protected $fillable = ['ip', 'name'];
}
How are you calling the functions? There is a couple of things wrong with your code, but you're saying there are no errors at all.
Firstly, your Info::create call does not need the ['info' => $request->input('info')] info. This is because your Info model has no database property called info, but normally you would get an obvious error with the approach, which is why I expect you are also calling the store method incorrectly.
Call the create method like so:
$infoModel = Info::create(['name' => $request->input('name'), 'ip' => $request->input['ip']]);
or, if you can guarantee your $request only contains the needed fields (properly validated), you can just do
$infoModel = Info::create($request->all());
Add a little more info to the question on how you are calling store and we can probably solve the rest of your problem.
Within your store function inside HomeController , use
Info::create([
'name' => Auth::user()->name,
'ip' => Request::ip(),
]);
and make sure Info model is imported.
Also make sure your route has the call to store function while POSTing data .

yii2 Getting array of data from one model and listing it in view of another

In photo controller while listing photo I can get user data using function
public function getUser()
{
return $this->hasOne(User::className(), ['id' => 'uID']);
}
So when I'm listing some photo in view I can access users db using
$model->user['username']
But what if I have db of comments of this photo. and want to get all coments while listing photo.
what should I write in photos model to get all comments of this photo and how can I list them in view ?
in model I think I must use this
public function getComments()
{
$modelComments = Comments::find()->where(['id'=>'commentID'])->all();
return [array('modelComments' => $modelComments)];
}
If this is correct how can I output all comments in view of photo ?
Does $model->user['username'] work at all? It should be $model->user->username.
Anyway set relation between photo and comments like with user but one-to-many.
public function getComments()
{
return $this->hasMany(Comments::className(), ['id' => 'commentID']);
}
Now when calling $model->comments you have got the array of all Comments models related to the photo.
Simpliest way of displaying them is to iterate over this array like:
foreach ($model->comments as $comment) {
echo $comment->content . '<br>';
// assuming column name with actual comment is "content"
}

CakePHP URL Parameter

How can I get the parameter in the URL and save it to a varialble so I can save it to my database?
example: www.mydomain.com/item/products/3 <-
This is for my upload image, so I can specify what product ID will I use for that image.
function add() {
if ($this->request->is('post')) {
$this->Upload->create();
if(empty($this->data['Upload']['image']['name'])) {
unset($this->request->data['Upload']['image']);
}
if(!empty($this->data['Upload']['image']['name'])) {
$filename = $this->request->data['Upload']['image']['name'];
$new_filename = STring::uuid().'-'.$filename;
$file_tmp_name = $this->request->data['Upload']['image']['tmp_name'];
$dir = WWW_ROOT.'img'.DS.'uploads';
move_uploaded_file($file_tmp_name,$dir.DS.$new_filename);
$this->request->data['Upload']['image'] = $new_filename;
if($this->Upload->save($this->request->data)) {
$this->Session->setFlash(__('Uploaded.'));
$this->redirect(array('action' => 'index'));
}
}
}
}
How will I add it here. Thank you in advance :)
Im using cakePHP
Just add the product id as a hidden input in the Form.
Then it will be included in the $this->data variable when you get the POST request.
For example in a controller method like the following
public function product($id) {
.....
}
You access it by the url (for example): www.mydomain.com/item/products/3 where Item is the controller, product is the method you are calling in that controller and 3 represent a parameter that is required to the function to work in this case $id. (assuming you don't have any routing configuration)
Is treated as a normal php variable, just do whatever you wanna do with it. Just make sure you pass the correct value

CakePHP unit test code coverage $this->request->data clause not executed

I am completely new to PHP unit testing (using PHPUnit) and CakePHP(2) as a framework, and I'm coming back to PHP after 5 years away.
I've got a website up and running and am writing unit tests as I go along as best practice. However, xdebug is showing that one of my clauses is not covered when I believe I am calling it and I just can't see why. I've googled the hell out of all search terms I can think of and re-read the relevant sections of the cookbook and (while I've learned a lot of other useful things) I didn't find an answer so am hoping that a simple answer is forthcoming from someone in the know :)
Here are the relevant sections of code:
Controller:
<?php
App::uses('AppController', 'Controller');
// app/Controller/ClientsController.php
class ClientsController extends AppController {
/* other functions */
public function edit($id = null) {
if (!$id) {
$this->Session->setFlash(__('Unable to find client to edit'));
return $this->redirect(array('action'=>'index'));
}
$client = $this->Client->findById($id);
if(!$client) {
$this->Session->setFlash(__('Unable to find client to edit'));
return $this->redirect(array('action'=>'index'));
}
if ($this->request->is('post')) {
$this->Client->id = $id;
if ($this->Client->saveAll($this->request->data)) {
$this->Session->setFlash(__('Client has been updated.'));
return $this->redirect(array('action'=>'index'));
} else {
$this->Session->setFlash(__('Unable to update client'));
}
}
if (!$this->request->data) {
$this->request->data = $client;
$this->Session->setFlash(__('Loading data'));
}
}
}
Test:
<?php
// Test cases for client controller module
class ClientsControllerTest extends ControllerTestCase {
public $fixtures = array('app.client');
/* other tests */
public function testEdit() {
// Expect success (render)
$result = $this->testAction('/Clients/edit/1');
debug($result);
}
}
?>
The code executes as expected. If I browse to "/Clients/edit/1", the flash message (Loading data) I expect is displayed indicating that there was no request data, so it's loaded from the $client. The correct data displays in the edit form.
When I call from within my test, I get a success message that the test has passed but xdebug code coverage is showing the if (!$this->request->data) { .. } clause is not covered, and no errors are apparent.
This seems counter-intuitive to me, so in a hope to avoid frustration with future (more complex) unit tests - can anyone explain why the test would pass but not execute this clause when it is called during normal access of the page?
(The fixture is correct both in terms of data structure and inserting the data before I'm attempting to edit it. Calling edit() from a test case with no id or an invalid id correctly executes the relevant clauses, as does passing data that does not pass validation.)
I've got a similar problem and I solved by adding the second parameter to testAction():
$this->testAction('/Clients/edit/1', array('method' => 'get'));
Also you may want to change your
if ($this->request->is('post') {
...
}
if (!$this->request->data) {
...
}
To:
if ($this->request->is('post') {
...
} else {
...
}
Hope it helps.

Resources