I have edited the Rainlab User plugin to allow for the user to upload a file on the frontend attached to their user profile. Works in the backend but not working on the frontend.
Inside User.php Model
public $attachOne = [
'avatar' => 'System\Models\File',
'id_document' => 'System\Models\File'
];
/**
* #var array The attributes that are mass assignable.
*/
protected $fillable = [
'name',
'surname',
'login',
'username',
'email',
'password',
'password_confirmation',
'created_ip_address',
'last_ip_address',
'id_document'
];
Inside Account.php Component
public function onSubmit()
{
if (!$user = $this->user()) {
return;
}
$data = post();
if ($this->updateRequiresPassword()) {
if (!$user->checkHashValue('password', $data['password_current'])) {
throw new ValidationException(['password_current' => Lang::get('rainlab.user::lang.account.invalid_current_pass')]);
}
}
if (Input::hasFile('avatar')) {
$user->avatar = Input::file('avatar');
}
if (Input::hasFile('id_document')) {
$user->id_document = Input::file('id_document');
}
$user->fill($data);
$user->save();
/*
* Password has changed, reauthenticate the user
*/
if (array_key_exists('password', $data) && strlen($data['password'])) {
Auth::login($user->reload(), true);
}
Flash::success(post('flash', Lang::get(/*Settings successfully saved!*/'rainlab.user::lang.account.success_saved')));
/*
* Redirect
*/
if ($redirect = $this->makeRedirection()) {
return $redirect;
}
$this->prepareVars();
}
Inside update.htm component
<form data-request="onSubmit" data-request-files data-request-flash>
<input type="hidden" name="_handler" value="onSubmit">
{{ form_token() }}
{{ form_sessionKey() }}
<div class="form-group">
<label for="accountName">Full Name</label>
<input name="name" type="text" class="form-control" id="accountName" value="{{ user.name }}">
</div>
<div class="form-group">
<label for="accountEmail">Email</label>
<input name="email" type="email" class="form-control" id="accountEmail" value="{{ user.email }}">
</div>
<div class="form-group">
<label for="accountEmail">ID Document</label>
<input type="file" name="id_document">
</div>
<div class="form-group">
<label for="accountEmail">Avatar</label>
<input type="file" name="avatar">
</div>
<button type="submit" class="btn btn-default">Save</button>
</form>
Result in system_files table when I submit the form
Database return
How do I make sure it adds all needed details in order to upload the file. Even the storage does not reflect the file on upload.
Related
How to upload a file and save it in Prestashop 1.7?
In ProductComments module I have a modal with a <form>:
post-comment-modal.tpl
<form id="post-product-comment-form" action="{$post_comment_url nofilter}" method="POST" enctype="multipart/form-data">
<div>
<div class="form-floating">
<input name="comment_title" type="text" class="form-control" placeholder="Title"/>
<label for="comment_title">Title</label>
</div>
<div class="form-floating">
<input name="customer_name" type="text" class="form-control" placeholder="Name"/>
<label for="customer_name">Name</label>
</div>
<div class="form-floating">
<textarea name="comment_content" class="form-control" placeholder="Review"></textarea>
<label for="comment_content">Review</label>
</div>
<input type="file" id="photo_input" name="photo_input" multiple> // I've added this field
<button type="submit">Send</button>
</div>
</form>
I've added there a <input type="file">.
This form is posted into ProductCommentsPostCommentModuleFrontController which extends ModuleFrontController
PostComment.php
class ProductCommentsPostCommentModuleFrontController extends ModuleFrontController
{
public function display()
{
$id_product = (int) Tools::getValue('id_product');
$comment_title = Tools::getValue('comment_title'); // Proper value
$comment_content = Tools::getValue('comment_content'); // Proper value
$customer_name = Tools::getValue('customer_name'); // Proper value
$criterions = (array) Tools::getValue('criterion');
$photo = Tools::getValue('photo_input'); // false
$file = $_FILES['photo_input']['name']; // null
// Validation
/** #var EntityManagerInterface $entityManager */
$entityManager = $this->container->get('doctrine.orm.entity_manager');
//Create product comment
$productComment = new ProductComment();
// Validation
$productComment
->setProductId($id_product)
->setTitle($comment_title)
->setContent($comment_content)
->setCustomerName($customer_name)
->setCustomerId($this->context->cookie->id_customer)
->setGuestId($this->context->cookie->id_guest)
->setDateAdd(new \DateTime('now', new \DateTimeZone('UTC')))
;
$entityManager->persist($productComment);
$this->addCommentGrades($productComment, $criterions);
$entityManager->flush();
$this->ajaxRender(
json_encode(
[
'success' => true,
'product_comment' => $productComment->toArray(),
]
)
);
}
Is there a way to extend this controller, and add a variable which holds a file upoaded by user by POST method?
I want to upload more than one image at a time through an in Laravel 8 to my SQL database, and I am not able to do it. I have managed to upload only one, but when I try with more I get failure.
My Database
Imagenes
id
nombre
id_coche
01
name.jpg
0004
...
...
...
My Code
Blade with the Form
#foreach ($Vehiculo as $obj) /*this is to take the Car ID*/
<form method="POST" action="{{ route('añadirImagen')}}" enctype="multipart/form-data" >
#csrf
<div class="form-row">
<div class="form-group col-md-3">
<div class="input-group">
<div class="input-group-prepend">
<span class="input-group-text">ID</span>
</div>
<input type="text" class="form-control" name="id_coche" value="{{$obj->id}}" style="background: white" required readonly>
</div>
</div>
<div class="col-md-6">
<input type="file" class="form-control" name="imagen" required multiple/>
</div>
<div class="form-group col-md-3">
<button type="submit" class="btn btn-success">AÑADIR IMAGENES</button>
</div>
</div>
</form>
#endforeach
Controller
"To upload only one image"
public function añadirImagen(Request $request){
$validated = $request->validate([
'id_coche' => 'required',
'nombre.*' => 'mimes:image'
]);
$data = $request->input();
$id_coche = $data['id_coche'];
$Imagenes= new Imagenes;
$Imagenes->id_coche = $id_coche;
if($request->file("imagen")!=null){
$nombre = $request->file('imagen');
$nombreFoto = $nombre->getClientOriginalName();
$nombre->move('img/Coches/', $nombreFoto);
$Imagenes->nombre = $nombreFoto;
}
$Imagenes->save();
return redirect()->back()->with('error','Se han añadido las imagenes correctamente.');
}
}
"My attempt to upload more than one"
public function añadirImagen(Request $request){
$validated = $request->validate([
'id_coche' => 'required',
'imagen.*' => 'mimes:image'
]);
$data = $request->input();
$id_coche = $data['id_coche'];
$Imagenes= new Imagenes;
$Imagenes->id_coche = $id_coche;
if($request->hasfile("imagen")){
$nombre_img = $request->file('imagen');
foreach($nombre_img as $nombre) {
$nombreFoto = $nombre->getClientOriginalName();
$nombre->move('img/Coches/', $nombreFoto);
$Imagenes->nombre = $nombreFoto;
}
}
$Imagenes->save();
When doing this, it adds in the database a single row, with the correct id_coche, the Auto_Increment does well the ID, but the name remains NULL.
Thank You.
You currently have:
<input type="file" class="form-control" name="imagen" required multiple/>
and it needs to be:
<input type="file" class="form-control" name="imagen[]" required/>
multiple attribute is not required.
Then you can do in your controller:
if($request->hasfile('imagen')) {
foreach($request->file('imagen') as $file)
{
...
}
}
I am using PHP Laravel framework. I am trying to save a form after submission. Strangely first time it is not saving, but subsequently, it is saving. On the first post request, the flow isn't even entering function save_application
Code below.
My controller:
class ApplicationController extends Controller
{
/**
* Create a new controller instance.
*
* #return void
*/
public function __construct()
{
$this->middleware('auth',['except' => ['store_application']]);
}
/**
* Show the application dashboard.
*
* #return \Illuminate\Http\Response
*/
public function save_application(Request $request){
$user = Auth::user();
if(isset($request->application)){
$application = Application::where("user_id",$user->id)->first();
if($application){
$application->update($request->application);
}else{
$application = new Application;
$application = Application::create($request->application);
$application->user_id = $user->id;
$application->save();
}
}
return $this->store_application($request);
}
public function store_application(Request $request){
if(isset($request->application)){
if($request->session()->has('application')){
$request->session()->forget('application');
}
$application_data = [];
$application = new Application;
$application->attributes = $request->application;
$application_data["application"] = $application;
$request->session()->put("application" , $application_data);
}
//
return Redirect::to("/application")->withErrors(array("success"=>"Thank you for submitting the application"));
}
}
My routers
Route::post('/application', 'ApplicationController#save_application')->name('application');
Route::post('/application_store', 'ApplicationController#store_application')->name('application');
My html
<form method="POST" action="/application" enctype="multipart/form-data" id='application_form'>
<input type="hidden" name="_token" value="xtQapusSjgf5XVUxjCOudedeH93a8hEqyfaNh8ChEaKt">
<input type='checkbox'>
<label>I've read and accept the terms and conditions</label>
<p class='font-size-16 font-bold text-uppercase text-black'>
Your information
</p>
<hr class='hr1'>
<div class='row form-group'>
<div class='col-lg-6'>
<label class='control-label'>First name*</label>
<input type='text' class='form-control' name='application[first_name]' value="">
</div>
<div class='col-lg-6'>
<label class='control-label' >Last name*</label>
<input type='text' class='form-control' name='application[last_name]' value="">
</div>
</div>
<div class='form-group'>
<label class='control-label' >Middle name</label>
<input type='text' class='form-control' name='application[middle_name]' value="">
</div>
<div class='form-group'>
<label class='control-label'>ID*</label>
<input type='text' class='form-control' name='application[]' value="">
</div>
<button class="btn btn-primary text-uppercase">Submit <i class='fa fa-check text-white'></i></button>
</form>
your routes have the same name, give them differents.
Route::post('/application', 'ApplicationController#save_application')->name('application');
Route::post('/application_store', 'ApplicationController#store_application')->name('other');
and in your form, you can:
<form method="POST" action="{{ route('application') }}" enctype="multipart/form-data" id='application_form'>
and as senty say:
<button type="submit">
</form>
I think you overcomplicate things, you can simply use updateOrCreate() to make it cleaner.
First of all, make sure $fillable or $guarded is utilized in your Application model. (Application.php)
protected $fillable = ['each', 'field', 'as', 'string'];
// or
protected $guarded = [];
Some improvements for your method:
public function save_application(Request $request){
// 1. Do a proper check
$request->validate([
'application.first_name' => 'required',
'application.middle_name' => 'required',
'application.last_name' => 'required'
]);
// 2. Update or Create
$application->updateOrCreate(
[ 'user_id' => $user->id ],
$request->application // I suppose this is an array that you want
);
// 3. Handle the redirect the right way so you can eliminate the other `store_applcation()` method entirely
return redirect()->back()->with([
'application' => $application
'success' => "Your Message"
]);
}
Also you don't need store_application() method in your controller or its route because your html form is POST'ing to /application route.
This is what you want, right?
Whenever a user goes to mywebsite.com/profile I want a form to pre populate the values they've entered during the signup/registration flow. I was able to do that with my form here
<h1><b>Your Profile</b></h1>
<form method="POST" action="/profile/update">
<div class="form-group hidden">
<input type="hidden" name="_token" value="{{ csrf_token() }}">
<input type="hidden" name="_method" value="PATCH">
</div>
<div class="form-group {{ $errors->has('name') ? ' has-error' : '' }}">
<label for="email" class="control-label"><b>Name:</b></label>
<input type="text" name="name" placeholder="Please enter your email here" class="form-control" value="{{ $user->name }}"/>
<?php if ($errors->has('name')) :?>
<span class="help-block">
<strong>{{$errors->first('name')}}</strong>
</span>
<?php endif;?>
</div>
<div class="form-group {{ $errors->has('email') ? ' has-error' : '' }}">
<label for="email" class="control-label"><b>Email:</b></label>
<input type="text" name="email" placeholder="Please enter your email here" class="form-control" value="{{ $user->email }}"/>
<?php if ($errors->has('email')) :?>
<span class="help-block">
<strong>{{$errors->first('email')}}</strong>
</span>
<?php endif;?>
</div>
<div class="form-group">
<button type="submit" class="btn btn-default"> Submit </button>
</div>
</form>
But now im running into the issue if the user just hits submit button without changing any fields, laravel's built in validations checks and gives me an error message of The name has already been taken. which is true. so im not sure how to handle this issue, but here is my controller below
<?php
namespace App\Http\Controllers;
use Auth;
use App\User;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
class ProfileController extends Controller
{
/**
* Update user profile & make backend push to DB
*
**/
public function index() {
/**
* fetching the user model
**/
$user = Auth::user();
//var_dump($user);
/**
* Passing the user data to profile view
*/
return view('profile', compact('user'));
}
public function update(Request $request) {
/**
* Validate request/input
**/
$this->validate($request, [
'name' => 'required|max:255|unique:users',
'email' => 'required|email|max:255|unique:users',
]);
/**
* storing the input fields name & email in variable $input
* type array
**/
$input = $request->only('name','email');
/**
* fetching the user model
*/
$user = Auth::user();
/**
* Accessing the update method and passing in $input array of data
**/
$user->update($input);
/**
* after everything is done return them pack to /profile/ uri
**/
return back();
}
}
and here is my routes file.
// only authenticated users
Route::group( ['middleware' => 'auth'], function() {
Route::get('/home', 'HomeController#index');
// practicing using forms for sending data to the DB & populating form fields with DB data
Route::get('profile', 'ProfileController#index');
Route::patch('profile/{id}', 'ProfileController#update');
});
Issue is due to unique validation rule. You can exclude the current user id by specifying unique validation rule. your code will be like this
public function update(Request $request) {
/**
* fetching the user model
*/
$user = Auth::user();
/**
* Validate request/input
**/
$this->validate($request, [
'name' => 'required|max:255|unique:users,name,'.$user->id,
'email' => 'required|email|max:255|unique:users,email,'.$user->id,
]);
/**
* storing the input fields name & email in variable $input
* type array
**/
$input = $request->only('name','email');
/**
* Accessing the update method and passing in $input array of data
**/
$user->update($input);
/**
* after everything is done return them pack to /profile/ uri
**/
return back();
}
here is laravel documentation link for this https://laravel.com/docs/5.1/validation#rule-unique
I'm doing PHP Laravel authentication. Registration and email activation seem works well. But when comes to login, it always return false. I have no idea about this. My email, password and active columns seems correct in my database.
User Modal
class User extends Eloquent implements UserInterface, RemindableInterface {
protected $fillable = array('email', 'username', 'password', 'password_temp', 'code', 'active');
use UserTrait, RemindableTrait;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password', 'remember_token');
}
Login.php
<form action="{{ URL::route('login-post')}}" method="post">
<!--/ sign in title-->
<!--text field-->
<div class="form-group">
<input type="email" name="email" placeholder="Email" class="form-control rounded input-lg text-center no-border" {{ (Input::old('email') ? ' value="'.Input::old('email') . '"' : '') }}>
#if($errors->has('email'))
{{ $errors->first('email') }}
#endif
</div>
<div class="form-group">
<input type="password" name="password" placeholder="Password" class="form-control rounded input-lg text-center no-border" {{ (Input::old('password') ? ' value="'.Input::old('password') . '"' : '') }}>
#if($errors->has('password'))
{{ $errors->first('password') }}
#endif
</div>
<!--/ text field-->
<div class="text-center m-t m-b">
<input type="checkbox" name="remember" id="remember">
<label for="remember">
Remember Me
</label>
</div>
<input type="submit" value="Sign in" class="btn btn-lg btn-warning lt b-white b-2x btn-block btn-rounded"></input>
{{ Form::token() }}
</form>
Controller
public function postSignIn() {
$validator = Validator::make(Input::all(),
array(
'email' => 'required|email',
'password' => 'required'
)
);
if ($validator->fails()) {
return Redirect::route('login')
->withErrors($validator)
->withInput();
}else {
$remember = (Input::has('remember')) ? true : false;
//Attempt user sign-in
$auth = Auth::attempt(array(
'email' => Input::get('email'),
'password' => Input::get('password'),
'active' => 1
), $remember);
if ($auth) {
//Redirect to the intended page
return Redirect::intended('home');
}else {
return Redirect::route('login')
->with('global','Email/Password is wrong or account is not activated.'.Hash::make(Input::get('password')));
}
}
return Redirect::route('login')
->with('global','There was a problem signing you in.');
}
Problem
It returns incorrect password always.
Solution
Password length must be at least 60 in database for Laravel.
I think there are two reasons (one or maybe two in the same time could couse this)
ONE : when you store your passwords you didn't hash them Hash::make()
TWO : you modified your config/app.php [key] value after setting your pass