Merge branch 'main' into next
This commit is contained in:
@@ -41,8 +41,8 @@ class Email extends Component
|
|||||||
#[Validate(['nullable', 'numeric', 'min:1', 'max:65535'])]
|
#[Validate(['nullable', 'numeric', 'min:1', 'max:65535'])]
|
||||||
public ?int $smtpPort = null;
|
public ?int $smtpPort = null;
|
||||||
|
|
||||||
#[Validate(['nullable', 'string', 'in:tls,ssl,none'])]
|
#[Validate(['nullable', 'string', 'in:starttls,tls,none'])]
|
||||||
public ?string $smtpEncryption = 'tls';
|
public ?string $smtpEncryption = null;
|
||||||
|
|
||||||
#[Validate(['nullable', 'string'])]
|
#[Validate(['nullable', 'string'])]
|
||||||
public ?string $smtpUsername = null;
|
public ?string $smtpUsername = null;
|
||||||
@@ -235,7 +235,7 @@ class Email extends Component
|
|||||||
'smtpFromName' => 'required|string',
|
'smtpFromName' => 'required|string',
|
||||||
'smtpHost' => 'required|string',
|
'smtpHost' => 'required|string',
|
||||||
'smtpPort' => 'required|numeric',
|
'smtpPort' => 'required|numeric',
|
||||||
'smtpEncryption' => 'required|string|in:tls,ssl,none',
|
'smtpEncryption' => 'required|string|in:starttls,tls,none',
|
||||||
'smtpUsername' => 'nullable|string',
|
'smtpUsername' => 'nullable|string',
|
||||||
'smtpPassword' => 'nullable|string',
|
'smtpPassword' => 'nullable|string',
|
||||||
'smtpTimeout' => 'nullable|numeric',
|
'smtpTimeout' => 'nullable|numeric',
|
||||||
|
|||||||
@@ -35,8 +35,8 @@ class SettingsEmail extends Component
|
|||||||
#[Validate(['nullable', 'numeric', 'min:1', 'max:65535'])]
|
#[Validate(['nullable', 'numeric', 'min:1', 'max:65535'])]
|
||||||
public ?int $smtpPort = null;
|
public ?int $smtpPort = null;
|
||||||
|
|
||||||
#[Validate(['nullable', 'string', 'in:tls,ssl,none'])]
|
#[Validate(['nullable', 'string', 'in:starttls,tls,none'])]
|
||||||
public ?string $smtpEncryption = 'tls';
|
public ?string $smtpEncryption = null;
|
||||||
|
|
||||||
#[Validate(['nullable', 'string'])]
|
#[Validate(['nullable', 'string'])]
|
||||||
public ?string $smtpUsername = null;
|
public ?string $smtpUsername = null;
|
||||||
@@ -142,7 +142,7 @@ class SettingsEmail extends Component
|
|||||||
'smtpFromName' => 'required|string',
|
'smtpFromName' => 'required|string',
|
||||||
'smtpHost' => 'required|string',
|
'smtpHost' => 'required|string',
|
||||||
'smtpPort' => 'required|numeric',
|
'smtpPort' => 'required|numeric',
|
||||||
'smtpEncryption' => 'required|string|in:tls,ssl,none',
|
'smtpEncryption' => 'required|string|in:starttls,tls,none',
|
||||||
'smtpUsername' => 'nullable|string',
|
'smtpUsername' => 'nullable|string',
|
||||||
'smtpPassword' => 'nullable|string',
|
'smtpPassword' => 'nullable|string',
|
||||||
'smtpTimeout' => 'nullable|numeric',
|
'smtpTimeout' => 'nullable|numeric',
|
||||||
|
|||||||
@@ -347,7 +347,7 @@ class Server extends BaseModel
|
|||||||
'loadBalancer' => [
|
'loadBalancer' => [
|
||||||
'servers' => [
|
'servers' => [
|
||||||
0 => [
|
0 => [
|
||||||
'url' => 'http://coolify:80',
|
'url' => 'http://coolify:8080',
|
||||||
],
|
],
|
||||||
],
|
],
|
||||||
],
|
],
|
||||||
@@ -445,7 +445,7 @@ $schema://$host {
|
|||||||
handle /terminal/ws {
|
handle /terminal/ws {
|
||||||
reverse_proxy coolify-realtime:6002
|
reverse_proxy coolify-realtime:6002
|
||||||
}
|
}
|
||||||
reverse_proxy coolify:80
|
reverse_proxy coolify:8080
|
||||||
}";
|
}";
|
||||||
$base64 = base64_encode($caddy_file);
|
$base64 = base64_encode($caddy_file);
|
||||||
instant_remote_process([
|
instant_remote_process([
|
||||||
|
|||||||
@@ -66,17 +66,24 @@ class EmailChannel
|
|||||||
}
|
}
|
||||||
|
|
||||||
if ($emailSettings->smtp_enabled) {
|
if ($emailSettings->smtp_enabled) {
|
||||||
|
$encryption = match (strtolower($emailSettings->smtp_encryption)) {
|
||||||
|
'starttls' => null,
|
||||||
|
'tls' => 'tls',
|
||||||
|
'none' => null,
|
||||||
|
default => null,
|
||||||
|
};
|
||||||
|
|
||||||
config()->set('mail.default', 'smtp');
|
config()->set('mail.default', 'smtp');
|
||||||
config()->set('mail.mailers.smtp', [
|
config()->set('mail.mailers.smtp', [
|
||||||
'transport' => 'smtp',
|
'transport' => 'smtp',
|
||||||
'host' => $emailSettings->smtp_host,
|
'host' => $emailSettings->smtp_host,
|
||||||
'port' => $emailSettings->smtp_port,
|
'port' => $emailSettings->smtp_port,
|
||||||
'encryption' => $emailSettings->smtp_encryption === 'none' ? null : $emailSettings->smtp_encryption,
|
'encryption' => $encryption,
|
||||||
'username' => $emailSettings->smtp_username,
|
'username' => $emailSettings->smtp_username,
|
||||||
'password' => $emailSettings->smtp_password,
|
'password' => $emailSettings->smtp_password,
|
||||||
'timeout' => $emailSettings->smtp_timeout,
|
'timeout' => $emailSettings->smtp_timeout,
|
||||||
'local_domain' => null,
|
'local_domain' => null,
|
||||||
'auto_tls' => $emailSettings->smtp_encryption === 'none' ? '0' : '',
|
'auto_tls' => $emailSettings->smtp_encryption === 'none' ? '0' : '', // If encryption is "none", it will not try to upgrade to TLS via StartTLS to make sure it is unencrypted.
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -67,17 +67,26 @@ function set_transanctional_email_settings(?InstanceSettings $settings = null):
|
|||||||
|
|
||||||
return 'resend';
|
return 'resend';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$encryption = match (strtolower(data_get($settings, 'smtp_encryption'))) {
|
||||||
|
'starttls' => null,
|
||||||
|
'tls' => 'tls',
|
||||||
|
'none' => null,
|
||||||
|
default => null,
|
||||||
|
};
|
||||||
|
|
||||||
if (data_get($settings, 'smtp_enabled')) {
|
if (data_get($settings, 'smtp_enabled')) {
|
||||||
config()->set('mail.default', 'smtp');
|
config()->set('mail.default', 'smtp');
|
||||||
config()->set('mail.mailers.smtp', [
|
config()->set('mail.mailers.smtp', [
|
||||||
'transport' => 'smtp',
|
'transport' => 'smtp',
|
||||||
'host' => data_get($settings, 'smtp_host'),
|
'host' => data_get($settings, 'smtp_host'),
|
||||||
'port' => data_get($settings, 'smtp_port'),
|
'port' => data_get($settings, 'smtp_port'),
|
||||||
'encryption' => data_get($settings, 'smtp_encryption'),
|
'encryption' => $encryption,
|
||||||
'username' => data_get($settings, 'smtp_username'),
|
'username' => data_get($settings, 'smtp_username'),
|
||||||
'password' => data_get($settings, 'smtp_password'),
|
'password' => data_get($settings, 'smtp_password'),
|
||||||
'timeout' => data_get($settings, 'smtp_timeout'),
|
'timeout' => data_get($settings, 'smtp_timeout'),
|
||||||
'local_domain' => null,
|
'local_domain' => null,
|
||||||
|
'auto_tls' => data_get($settings, 'smtp_encryption') === 'none' ? '0' : '', // If encryption is "none", it will not try to upgrade to TLS via StartTLS to make sure it is unencrypted.
|
||||||
]);
|
]);
|
||||||
|
|
||||||
return 'smtp';
|
return 'smtp';
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ return [
|
|||||||
],
|
],
|
||||||
|
|
||||||
'docker' => [
|
'docker' => [
|
||||||
'minimum_required_version' => '26.0',
|
'minimum_required_version' => '24.0',
|
||||||
],
|
],
|
||||||
|
|
||||||
'ssh' => [
|
'ssh' => [
|
||||||
|
|||||||
@@ -13,7 +13,6 @@ return new class extends Migration
|
|||||||
*/
|
*/
|
||||||
public function up(): void
|
public function up(): void
|
||||||
{
|
{
|
||||||
if (DB::table('instance_settings')->exists()) {
|
|
||||||
Schema::table('instance_settings', function (Blueprint $table) {
|
Schema::table('instance_settings', function (Blueprint $table) {
|
||||||
$table->text('smtp_from_address')->nullable()->change();
|
$table->text('smtp_from_address')->nullable()->change();
|
||||||
$table->text('smtp_from_name')->nullable()->change();
|
$table->text('smtp_from_name')->nullable()->change();
|
||||||
@@ -22,6 +21,7 @@ return new class extends Migration
|
|||||||
$table->text('smtp_username')->nullable()->change();
|
$table->text('smtp_username')->nullable()->change();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
if (DB::table('instance_settings')->exists()) {
|
||||||
$settings = DB::table('instance_settings')->get();
|
$settings = DB::table('instance_settings')->get();
|
||||||
foreach ($settings as $setting) {
|
foreach ($settings as $setting) {
|
||||||
try {
|
try {
|
||||||
@@ -45,11 +45,11 @@ return new class extends Migration
|
|||||||
public function down(): void
|
public function down(): void
|
||||||
{
|
{
|
||||||
Schema::table('instance_settings', function (Blueprint $table) {
|
Schema::table('instance_settings', function (Blueprint $table) {
|
||||||
$table->text('smtp_from_address')->nullable()->change();
|
$table->string('smtp_from_address')->nullable()->change();
|
||||||
$table->text('smtp_from_name')->nullable()->change();
|
$table->string('smtp_from_name')->nullable()->change();
|
||||||
$table->text('smtp_recipients')->nullable()->change();
|
$table->string('smtp_recipients')->nullable()->change();
|
||||||
$table->text('smtp_host')->nullable()->change();
|
$table->string('smtp_host')->nullable()->change();
|
||||||
$table->text('smtp_username')->nullable()->change();
|
$table->string('smtp_username')->nullable()->change();
|
||||||
});
|
});
|
||||||
|
|
||||||
if (DB::table('instance_settings')->exists()) {
|
if (DB::table('instance_settings')->exists()) {
|
||||||
|
|||||||
@@ -0,0 +1,114 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
use Illuminate\Database\Migrations\Migration;
|
||||||
|
use Illuminate\Support\Facades\DB;
|
||||||
|
|
||||||
|
class UpdateEmailEncryptionValues extends Migration
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Encryption mappings.
|
||||||
|
*/
|
||||||
|
private array $encryptionMappings = [
|
||||||
|
'tls' => 'starttls',
|
||||||
|
'ssl' => 'tls',
|
||||||
|
'' => 'none',
|
||||||
|
];
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Run the migrations.
|
||||||
|
*/
|
||||||
|
public function up(): void
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
DB::beginTransaction();
|
||||||
|
|
||||||
|
$instanceSettings = DB::table('instance_settings')->get();
|
||||||
|
foreach ($instanceSettings as $setting) {
|
||||||
|
try {
|
||||||
|
if (array_key_exists($setting->smtp_encryption, $this->encryptionMappings)) {
|
||||||
|
DB::table('instance_settings')
|
||||||
|
->where('id', $setting->id)
|
||||||
|
->update([
|
||||||
|
'smtp_encryption' => $this->encryptionMappings[$setting->smtp_encryption],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
\Log::error('Failed to update instance settings: '.$e->getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$emailSettings = DB::table('email_notification_settings')->get();
|
||||||
|
foreach ($emailSettings as $setting) {
|
||||||
|
try {
|
||||||
|
if (array_key_exists($setting->smtp_encryption, $this->encryptionMappings)) {
|
||||||
|
DB::table('email_notification_settings')
|
||||||
|
->where('id', $setting->id)
|
||||||
|
->update([
|
||||||
|
'smtp_encryption' => $this->encryptionMappings[$setting->smtp_encryption],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
\Log::error('Failed to update email settings: '.$e->getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DB::commit();
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
DB::rollBack();
|
||||||
|
\Log::error('Failed to update email encryption: '.$e->getMessage());
|
||||||
|
throw $e;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Reverse the migrations.
|
||||||
|
*/
|
||||||
|
public function down(): void
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
DB::beginTransaction();
|
||||||
|
|
||||||
|
$reverseMapping = [
|
||||||
|
'starttls' => 'tls',
|
||||||
|
'tls' => 'ssl',
|
||||||
|
'none' => '',
|
||||||
|
];
|
||||||
|
|
||||||
|
$instanceSettings = DB::table('instance_settings')->get();
|
||||||
|
foreach ($instanceSettings as $setting) {
|
||||||
|
try {
|
||||||
|
if (array_key_exists($setting->smtp_encryption, $reverseMapping)) {
|
||||||
|
DB::table('instance_settings')
|
||||||
|
->where('id', $setting->id)
|
||||||
|
->update([
|
||||||
|
'smtp_encryption' => $reverseMapping[$setting->smtp_encryption],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
\Log::error('Failed to reverse instance settings: '.$e->getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$emailSettings = DB::table('email_notification_settings')->get();
|
||||||
|
foreach ($emailSettings as $setting) {
|
||||||
|
try {
|
||||||
|
if (array_key_exists($setting->smtp_encryption, $reverseMapping)) {
|
||||||
|
DB::table('email_notification_settings')
|
||||||
|
->where('id', $setting->id)
|
||||||
|
->update([
|
||||||
|
'smtp_encryption' => $reverseMapping[$setting->smtp_encryption],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
\Log::error('Failed to reverse email settings: '.$e->getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DB::commit();
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
DB::rollBack();
|
||||||
|
\Log::error('Failed to reverse email encryption: '.$e->getMessage());
|
||||||
|
throw $e;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -58,7 +58,7 @@ services:
|
|||||||
expose:
|
expose:
|
||||||
- "${APP_PORT:-8000}"
|
- "${APP_PORT:-8000}"
|
||||||
healthcheck:
|
healthcheck:
|
||||||
test: curl --fail http://127.0.0.1:80/api/health || exit 1
|
test: curl --fail http://127.0.0.1:8080/api/health || exit 1
|
||||||
interval: 5s
|
interval: 5s
|
||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
@@ -93,7 +93,7 @@ services:
|
|||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
soketi:
|
soketi:
|
||||||
image: 'ghcr.io/coollabsio/coolify-realtime:1.0.4'
|
image: 'ghcr.io/coollabsio/coolify-realtime:1.0.5'
|
||||||
ports:
|
ports:
|
||||||
- "${SOKETI_PORT:-6001}:6001"
|
- "${SOKETI_PORT:-6001}:6001"
|
||||||
- "6002:6002"
|
- "6002:6002"
|
||||||
|
|||||||
@@ -48,11 +48,11 @@ services:
|
|||||||
- SSH_MUX_ENABLED=false
|
- SSH_MUX_ENABLED=false
|
||||||
- IS_WINDOWS_DOCKER_DESKTOP=true
|
- IS_WINDOWS_DOCKER_DESKTOP=true
|
||||||
ports:
|
ports:
|
||||||
- "${APP_PORT:-8000}:80"
|
- "${APP_PORT:-8000}:8080"
|
||||||
expose:
|
expose:
|
||||||
- "${APP_PORT:-8000}"
|
- "${APP_PORT:-8000}"
|
||||||
healthcheck:
|
healthcheck:
|
||||||
test: curl --fail http://localhost:80/api/health || exit 1
|
test: curl --fail http://localhost:8080/api/health || exit 1
|
||||||
interval: 5s
|
interval: 5s
|
||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
|
|||||||
@@ -58,7 +58,7 @@ services:
|
|||||||
expose:
|
expose:
|
||||||
- "${APP_PORT:-8000}"
|
- "${APP_PORT:-8000}"
|
||||||
healthcheck:
|
healthcheck:
|
||||||
test: curl --fail http://127.0.0.1:80/api/health || exit 1
|
test: curl --fail http://127.0.0.1:8080/api/health || exit 1
|
||||||
interval: 5s
|
interval: 5s
|
||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
@@ -93,7 +93,7 @@ services:
|
|||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
soketi:
|
soketi:
|
||||||
image: 'ghcr.io/coollabsio/coolify-realtime:next'
|
image: 'ghcr.io/coollabsio/coolify-realtime:1.0.5'
|
||||||
ports:
|
ports:
|
||||||
- "${SOKETI_PORT:-6001}:6001"
|
- "${SOKETI_PORT:-6001}:6001"
|
||||||
- "6002:6002"
|
- "6002:6002"
|
||||||
|
|||||||
@@ -48,11 +48,11 @@ services:
|
|||||||
- SSH_MUX_ENABLED=false
|
- SSH_MUX_ENABLED=false
|
||||||
- IS_WINDOWS_DOCKER_DESKTOP=true
|
- IS_WINDOWS_DOCKER_DESKTOP=true
|
||||||
ports:
|
ports:
|
||||||
- "${APP_PORT:-8000}:80"
|
- "${APP_PORT:-8000}:8080"
|
||||||
expose:
|
expose:
|
||||||
- "${APP_PORT:-8000}"
|
- "${APP_PORT:-8000}"
|
||||||
healthcheck:
|
healthcheck:
|
||||||
test: curl --fail http://localhost:80/api/health || exit 1
|
test: curl --fail http://localhost:8080/api/health || exit 1
|
||||||
interval: 5s
|
interval: 5s
|
||||||
retries: 10
|
retries: 10
|
||||||
timeout: 2s
|
timeout: 2s
|
||||||
|
|||||||
@@ -70,9 +70,9 @@
|
|||||||
<div class="flex flex-col w-full gap-2 xl:flex-row">
|
<div class="flex flex-col w-full gap-2 xl:flex-row">
|
||||||
<x-forms.input required id="smtpHost" placeholder="smtp.mailgun.org" label="Host" />
|
<x-forms.input required id="smtpHost" placeholder="smtp.mailgun.org" label="Host" />
|
||||||
<x-forms.input required id="smtpPort" placeholder="587" label="Port" />
|
<x-forms.input required id="smtpPort" placeholder="587" label="Port" />
|
||||||
<x-forms.select id="smtpEncryption" label="Encryption">
|
<x-forms.select required id="smtpEncryption" label="Encryption">
|
||||||
<option value="tls">TLS</option>
|
<option value="starttls">StartTLS</option>
|
||||||
<option value="ssl">SSL</option>
|
<option value="tls">TLS/SSL</option>
|
||||||
<option value="none">None</option>
|
<option value="none">None</option>
|
||||||
</x-forms.select>
|
</x-forms.select>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -43,9 +43,9 @@
|
|||||||
<div class="flex flex-col w-full gap-2 xl:flex-row">
|
<div class="flex flex-col w-full gap-2 xl:flex-row">
|
||||||
<x-forms.input required id="smtpHost" placeholder="smtp.mailgun.org" label="Host" />
|
<x-forms.input required id="smtpHost" placeholder="smtp.mailgun.org" label="Host" />
|
||||||
<x-forms.input required id="smtpPort" placeholder="587" label="Port" />
|
<x-forms.input required id="smtpPort" placeholder="587" label="Port" />
|
||||||
<x-forms.select id="smtpEncryption" label="Encryption">
|
<x-forms.select required id="smtpEncryption" label="Encryption">
|
||||||
<option value="tls">TLS</option>
|
<option value="starttls">StartTLS</option>
|
||||||
<option value="ssl">SSL</option>
|
<option value="tls">TLS/SSL</option>
|
||||||
<option value="none">None</option>
|
<option value="none">None</option>
|
||||||
</x-forms.select>
|
</x-forms.select>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user