From 2a1311b2baa1b45fde7a4056cb96ad9e626f56d6 Mon Sep 17 00:00:00 2001 From: Andy Heathershaw Date: Tue, 6 Sep 2016 13:26:02 +0100 Subject: [PATCH] Finished the test e-mail settings functionality and introduced TLS encryption. Tested with Office 365. --- .../Controllers/Admin/DefaultController.php | 73 +++++++++++++++++++ app/Http/Requests/SaveSettingsRequest.php | 2 + app/Mail/TestMailConfig.php | 20 +++-- app/Providers/AppServiceProvider.php | 7 +- public/ripple.svg | 1 + public/themes/bootstrap3/theme.css | 4 + resources/lang/en/admin.php | 1 + .../themes/base/admin/settings.blade.php | 62 +++++++++++++++- .../themes/base/email/test_email.blade.php | 9 +++ .../views/themes/base/email_layout.blade.php | 8 ++ routes/web.php | 1 + 11 files changed, 178 insertions(+), 10 deletions(-) create mode 100644 public/ripple.svg create mode 100644 resources/views/themes/base/email/test_email.blade.php create mode 100644 resources/views/themes/base/email_layout.blade.php diff --git a/app/Http/Controllers/Admin/DefaultController.php b/app/Http/Controllers/Admin/DefaultController.php index ff14f73..b0de72e 100644 --- a/app/Http/Controllers/Admin/DefaultController.php +++ b/app/Http/Controllers/Admin/DefaultController.php @@ -9,9 +9,13 @@ use App\Facade\UserConfig; use App\Helpers\ConfigHelper; use App\Http\Controllers\Controller; use App\Http\Requests\SaveSettingsRequest; +use App\Mail\TestMailConfig; use App\Photo; use Illuminate\Http\Request; +use Illuminate\Support\Facades\App; +use Illuminate\Support\Facades\Auth; use Illuminate\Support\Facades\DB; +use Illuminate\Support\Facades\Mail; class DefaultController extends Controller { @@ -30,15 +34,23 @@ class DefaultController extends Controller public function saveSettings(SaveSettingsRequest $request) { + $passwordKeys = [ + 'smtp_password' + ]; $checkboxKeys = [ 'allow_self_registration', 'require_email_verification', + 'smtp_encryption' ]; $updateKeys = [ 'app_name', 'date_format', 'sender_address', 'sender_name', + 'smtp_server', + 'smtp_port', + 'smtp_username', + 'smtp_password', 'theme' ]; @@ -47,7 +59,24 @@ class DefaultController extends Controller foreach ($updateKeys as $key) { $config = UserConfig::getOrCreateModel($key); + + // Bit of a hack when the browser returns an empty password field - meaning the user didn't change it + // - don't touch it! + if ( + $key == 'smtp_password' && + strlen($config->value) > 0 && + strlen($request->request->get($key)) == 0 && + strlen($request->request->get('smtp_username')) > 0 + ) + { + continue; + } + $config->value = $request->request->get($key); + if (in_array($key, $passwordKeys)) + { + $config->value = encrypt($config->value); + } if (isset($defaults[$key]) && $defaults[$key] == $config->value) { @@ -102,4 +131,48 @@ class DefaultController extends Controller 'theme_names' => $themeNamesLookup ]); } + + public function testMailSettings(SaveSettingsRequest $request) + { + try + { + $validKeys = [ + 'sender_address', + 'sender_name', + 'smtp_server', + 'smtp_port', + 'smtp_username', + 'smtp_password', + 'smtp_encryption' + ]; + $config = $request->only($validKeys); + + /** @var \Swift_Mailer $swiftMailer */ + $swiftMailer = resolve('mailer')->getSwiftMailer(); + + /** @var \Swift_SmtpTransport $transport */ + $transport = $swiftMailer->getTransport(); + $transport->setHost($config['smtp_server']); + $transport->setPort(intval($config['smtp_port'])); + $transport->setUsername($config['smtp_username']); + $transport->setPassword($config['smtp_password']); + + if (isset($config['smtp_encryption']) && strtolower($config['smtp_encryption']) == 'on') + { + $transport->setEncryption('tls'); + } + else + { + $transport->setEncryption(''); + } + + Mail::to(Auth::user())->send(new TestMailConfig($config['sender_name'], $config['sender_address'])); + + return response()->json(array('is_successful' => true, 'message' => 'sent_successfully')); + } + catch (\Exception $ex) + { + return response()->json(array('is_successful' => false, 'message' => $ex->getMessage())); + } + } } \ No newline at end of file diff --git a/app/Http/Requests/SaveSettingsRequest.php b/app/Http/Requests/SaveSettingsRequest.php index dd0035a..fb59558 100644 --- a/app/Http/Requests/SaveSettingsRequest.php +++ b/app/Http/Requests/SaveSettingsRequest.php @@ -26,6 +26,8 @@ class SaveSettingsRequest extends FormRequest return [ 'app_name' => 'required|max:255', 'date_format' => 'required', + 'smtp_server' => 'required', + 'smtp_port' => 'required:integer' ]; } } diff --git a/app/Mail/TestMailConfig.php b/app/Mail/TestMailConfig.php index 938e1f2..dc0695d 100644 --- a/app/Mail/TestMailConfig.php +++ b/app/Mail/TestMailConfig.php @@ -2,23 +2,28 @@ namespace App\Mail; +use App\Facade\Theme; +use App\Facade\UserConfig; use Illuminate\Bus\Queueable; use Illuminate\Mail\Mailable; use Illuminate\Queue\SerializesModels; -use Illuminate\Contracts\Queue\ShouldQueue; class TestMailConfig extends Mailable { use Queueable, SerializesModels; + private $senderAddress; + private $senderName; + /** * Create a new message instance. * * @return void */ - public function __construct() + public function __construct($senderName, $senderAddress) { - // + $this->senderName = $senderName; + $this->senderAddress = $senderAddress; } /** @@ -28,8 +33,11 @@ class TestMailConfig extends Mailable */ public function build() { - return $this->from(UserConfig::get('sender_address'), UserConfig::get('sender_name')) - ->subject(trans('email.test_email_subject', ['app_name' => UserConfig::get('app_name')])) - ->view(Theme::viewName('email.test_email')); + $subject = trans('email.test_email_subject', ['app_name' => UserConfig::get('app_name')]); + + return $this->from($this->senderAddress, $this->senderName) + ->subject($subject) + ->view(Theme::viewName('email.test_email')) + ->with(['subject' => $subject]); } } diff --git a/app/Providers/AppServiceProvider.php b/app/Providers/AppServiceProvider.php index fd78b8a..1f30ae8 100644 --- a/app/Providers/AppServiceProvider.php +++ b/app/Providers/AppServiceProvider.php @@ -86,6 +86,11 @@ class AppServiceProvider extends ServiceProvider $transport->setHost(UserConfig::get('smtp_server')); $transport->setPort(intval(UserConfig::get('smtp_port'))); $transport->setUsername(UserConfig::get('smtp_username')); - $transport->setPassword(UserConfig::get('smtp_password')); + $transport->setPassword(decrypt(UserConfig::get('smtp_password'))); + + if (UserConfig::get('smtp_encryption')) + { + $transport->setEncryption('tls'); + } } } diff --git a/public/ripple.svg b/public/ripple.svg new file mode 100644 index 0000000..5eb9a62 --- /dev/null +++ b/public/ripple.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/public/themes/bootstrap3/theme.css b/public/themes/bootstrap3/theme.css index 1b4d024..6c7675f 100644 --- a/public/themes/bootstrap3/theme.css +++ b/public/themes/bootstrap3/theme.css @@ -4,6 +4,10 @@ font-family: Raleway, sans-serif; } +body { + padding-bottom: 40px; +} + .album-index img { max-width: 100%; } diff --git a/resources/lang/en/admin.php b/resources/lang/en/admin.php index 0f05aac..82ad363 100644 --- a/resources/lang/en/admin.php +++ b/resources/lang/en/admin.php @@ -14,6 +14,7 @@ return [ 'settings_link' => 'Settings', 'settings_save_action' => 'Update Settings', 'settings_saved_message' => 'The settings were updated successfully.', + 'settings_test_email_action' => 'Send a test e-mail', 'settings_title' => 'Settings', 'stats_albums' => 'album|albums', 'stats_panel' => 'Statistics', diff --git a/resources/views/themes/base/admin/settings.blade.php b/resources/views/themes/base/admin/settings.blade.php index fe910c9..2cae600 100644 --- a/resources/views/themes/base/admin/settings.blade.php +++ b/resources/views/themes/base/admin/settings.blade.php @@ -20,6 +20,7 @@ {{-- Tab panes --}}
+ {{-- General --}}
{!! Form::label('app_name', 'Gallery name:', ['class' => 'control-label']) !!} @@ -45,6 +46,7 @@
+ {{-- E-mail --}}
{!! Form::label('sender_name', 'Sender name:', ['class' => 'control-label']) !!} @@ -58,7 +60,7 @@
-

Configure your SMTP server using the settings below.

+

Configure your SMTP server using the settings below. If your server does not require authentication, leave the Username and Password fields empty.

{!! Form::label('smtp_server', 'Hostname:', ['class' => 'control-label']) !!} @@ -77,10 +79,32 @@
{!! Form::label('smtp_password', 'Password:', ['class' => 'control-label']) !!} - {!! Form::text('smtp_password', old('smtp_password'), ['class' => 'form-control']) !!} + {!! Form::password('smtp_password', ['class' => 'form-control']) !!} +
+ +
+ +
+ +
+ + +
+ + + +
+ {{-- Security --}}
-@endsection \ No newline at end of file +@endsection + +@push('scripts') + +@endpush \ No newline at end of file diff --git a/resources/views/themes/base/email/test_email.blade.php b/resources/views/themes/base/email/test_email.blade.php new file mode 100644 index 0000000..d380c32 --- /dev/null +++ b/resources/views/themes/base/email/test_email.blade.php @@ -0,0 +1,9 @@ +@extends('themes.base.email_layout') + +@section('title', $subject) +@section('content') +

Hi {{ Auth::user()->name }},

+

This e-mail confirms your e-mail settings are correct.

+

You can now press "Save Settings" on the Settings screen to save these settings.

+

Regards,
{{ UserConfig::get('app_name') }}

+@endsection \ No newline at end of file diff --git a/resources/views/themes/base/email_layout.blade.php b/resources/views/themes/base/email_layout.blade.php new file mode 100644 index 0000000..bc50c14 --- /dev/null +++ b/resources/views/themes/base/email_layout.blade.php @@ -0,0 +1,8 @@ + + + @yield('title') + + + @yield('content') + + \ No newline at end of file diff --git a/routes/web.php b/routes/web.php index 56cb0bc..87899ef 100644 --- a/routes/web.php +++ b/routes/web.php @@ -17,6 +17,7 @@ Auth::routes(); Route::group(['prefix' => 'admin'], function () { Route::get('/', 'Admin\DefaultController@index')->name('admin'); Route::post('settings/save', 'Admin\DefaultController@saveSettings')->name('admin.saveSettings'); + Route::post('settings/test-email', 'Admin\DefaultController@testMailSettings')->name('admin.testMailSettings'); Route::get('settings', 'Admin\DefaultController@settings')->name('admin.settings'); // Album management