Compare commits
63 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 79a4acae1a | |||
| 91e0b26bbb | |||
| 5f82214703 | |||
| d517e2fd61 | |||
| 28612d8b61 | |||
| 6ee3d0eb97 | |||
| 7987a4eca4 | |||
| 2aa8e1e76b | |||
| be0e327221 | |||
| 9a1acced58 | |||
| d74df93c48 | |||
| b9a9949570 | |||
| 4ccba5337a | |||
| 8aae2b46cd | |||
| d03d4deef9 | |||
| 21ceea0aed | |||
| 2219c9ccb5 | |||
| bf9e53fbe7 | |||
| f68580b482 | |||
| aec2f2a249 | |||
| 831da2d6d1 | |||
| f2aebe5f9a | |||
| 40c0ba9a95 | |||
| f5a0726f98 | |||
| 2263dae8f4 | |||
| f182ce1c89 | |||
| c6dde67e86 | |||
| 88f03e6b55 | |||
| 8827d33a43 | |||
| c3e8f64064 | |||
| 68cfbaab2e | |||
| 66ac5d05ad | |||
| 18012279f9 | |||
| 2abfd8da74 | |||
| ec7d70cea0 | |||
| 6c285b0273 | |||
| e65269e9c7 | |||
| 5d112be49a | |||
| d3f5fde84a | |||
| 496b176d4e | |||
| fd66f7aeb4 | |||
| c71086d2f3 | |||
| 153f849ef7 | |||
| fcdb945f5f | |||
| 377c92a290 | |||
| 5824ac3b28 | |||
| fad0ed6d5b | |||
| ec9c69323a | |||
| 338106734a | |||
| 81fcb4c7b3 | |||
| 5ae65d5329 | |||
| d04b0e4d4b | |||
| a6d0209e93 | |||
| 810f6a3970 | |||
| 1379821876 | |||
| 33236f16ac | |||
| 90dddee923 | |||
| 7869ffcc79 | |||
| 1687e4b850 | |||
| 4a3d8f2cc0 | |||
| c19f1b77b0 | |||
| 132f296f03 | |||
| 870b097f03 |
@@ -117,7 +117,7 @@ class LdapSync extends Command
|
||||
$this->dryrun = true;
|
||||
}
|
||||
$this->checkIfLdapIsEnabled();
|
||||
$this->checkLdapConnetion();
|
||||
$this->checkLdapConnection();
|
||||
$this->setBaseDn();
|
||||
$this->getUserDefaultLocation();
|
||||
/*
|
||||
@@ -191,21 +191,27 @@ class LdapSync extends Command
|
||||
];
|
||||
// Only update the database if is not a dry run
|
||||
if (!$this->dryrun) {
|
||||
if ($user->save()) {
|
||||
$summary['note'] = ($user->wasRecentlyCreated ? 'CREATED' : 'UPDATED');
|
||||
$summary['status'] = 'SUCCESS';
|
||||
} else {
|
||||
$errors = '';
|
||||
foreach ($user->getErrors()->getMessages() as $error) {
|
||||
$errors .= implode(", ",$error);
|
||||
if ($user->isDirty()) { //if nothing on the user changed, don't bother trying to save anything nor put anything in the summary
|
||||
if ($user->save()) {
|
||||
$summary['note'] = ($user->wasRecentlyCreated ? 'CREATED' : 'UPDATED');
|
||||
$summary['status'] = 'SUCCESS';
|
||||
} else {
|
||||
$errors = '';
|
||||
foreach ($user->getErrors()->getMessages() as $error) {
|
||||
$errors .= implode(", ",$error);
|
||||
}
|
||||
$summary['note'] = $snipeUser->getDN().' was not imported. REASON: '.$errors;
|
||||
$summary['status'] = 'ERROR';
|
||||
}
|
||||
$summary['note'] = $snipeUser->getDN().' was not imported. REASON: '.$errors;
|
||||
$summary['status'] = 'ERROR';
|
||||
} else {
|
||||
$summary = null;
|
||||
}
|
||||
}
|
||||
|
||||
// $summary['note'] = ($user->getOriginal('username') ? 'UPDATED' : 'CREATED'); // this seems, kinda, like, superfluous, relative to the $summary['note'] thing above, yeah?
|
||||
$this->summary->push($summary);
|
||||
if($summary) { //if the $user wasn't dirty, $summary was set to null so that we will skip the following push()
|
||||
$this->summary->push($summary);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -241,7 +247,9 @@ class LdapSync extends Command
|
||||
}
|
||||
|
||||
if ($ldapUsers->getCurrentPage() < $ldapUsers->getPages()-1) {
|
||||
$this->processLdapUsers($ldapUsers->getCurrentPage() + 1);
|
||||
$current_page = $ldapUsers->getCurrentPage();
|
||||
unset($ldapUsers); //deliberately unset the variable so we don't OOM
|
||||
$this->processLdapUsers($current_page + 1); //this recursive call means that the $ldapUsers variable is not going to get GC'ed until everything returns. Blech.
|
||||
}
|
||||
}
|
||||
|
||||
@@ -349,7 +357,7 @@ class LdapSync extends Command
|
||||
*
|
||||
* @since 5.0.0
|
||||
*/
|
||||
private function checkLdapConnetion(): void
|
||||
private function checkLdapConnection(): void
|
||||
{
|
||||
try {
|
||||
$this->ldap->testLdapAdUserConnection();
|
||||
|
||||
@@ -58,7 +58,7 @@ class SendExpectedCheckinAlerts extends Command
|
||||
$recipients = collect(explode(',', $settings->alert_email))->map(function ($item, $key) {
|
||||
return new AlertRecipient($item);
|
||||
});
|
||||
Notification::send($recipients, new ExpectedCheckinAdminNotification($assets));
|
||||
\Notification::send($recipients, new ExpectedCheckinAdminNotification($assets));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -55,14 +55,14 @@ class SendExpirationAlerts extends Command
|
||||
$assets = Asset::getExpiringWarrantee($threshold);
|
||||
if ($assets->count() > 0) {
|
||||
$this->info(trans_choice('mail.assets_warrantee_alert', $assets->count(), ['count' => $assets->count(), 'threshold' => $threshold]));
|
||||
Notification::send($recipients, new ExpiringAssetsNotification($assets, $threshold));
|
||||
\Notification::send($recipients, new ExpiringAssetsNotification($assets, $threshold));
|
||||
}
|
||||
|
||||
// Expiring licenses
|
||||
$licenses = License::getExpiringLicenses($threshold);
|
||||
if ($licenses->count() > 0) {
|
||||
$this->info(trans_choice('mail.license_expiring_alert', $licenses->count(), ['count' => $licenses->count(), 'threshold' => $threshold]));
|
||||
Notification::send($recipients, new ExpiringLicenseNotification($licenses, $threshold));
|
||||
\Notification::send($recipients, new ExpiringLicenseNotification($licenses, $threshold));
|
||||
}
|
||||
} else {
|
||||
if ($settings->alert_email == '') {
|
||||
|
||||
@@ -52,7 +52,7 @@ class SendInventoryAlerts extends Command
|
||||
return new AlertRecipient($item);
|
||||
});
|
||||
|
||||
Notification::send($recipients, new InventoryAlert($items, $settings->alert_threshold));
|
||||
\Notification::send($recipients, new InventoryAlert($items, $settings->alert_threshold));
|
||||
}
|
||||
} else {
|
||||
if ($settings->alert_email == '') {
|
||||
|
||||
@@ -75,7 +75,8 @@ class AccessoryCheckoutController extends Controller
|
||||
'accessory_id' => $accessory->id,
|
||||
'created_at' => Carbon::now(),
|
||||
'user_id' => Auth::id(),
|
||||
'assigned_to' => $request->get('assigned_to')
|
||||
'assigned_to' => $request->get('assigned_to'),
|
||||
'note' => $request->input('note')
|
||||
]);
|
||||
|
||||
DB::table('accessories_users')->where('assigned_to', '=', $accessory->assigned_to)->where('accessory_id', '=', $accessory->id)->first();
|
||||
|
||||
@@ -94,7 +94,7 @@ class AcceptanceController extends Controller {
|
||||
if (!Storage::exists('private_uploads/signatures')) Storage::makeDirectory('private_uploads/signatures', 775);
|
||||
|
||||
|
||||
|
||||
$sig_filename = '';
|
||||
if ($request->filled('signature_output')) {
|
||||
$sig_filename = "siglog-" .Str::uuid() . '-'.date('Y-m-d-his').".png";
|
||||
$data_uri = e($request->input('signature_output'));
|
||||
|
||||
@@ -154,7 +154,6 @@ class AccessoriesController extends Controller
|
||||
$offset = request('offset', 0);
|
||||
$limit = request('limit', 50);
|
||||
|
||||
$accessory->lastCheckoutArray = $accessory->lastCheckout->toArray();
|
||||
$accessory_users = $accessory->users;
|
||||
$total = $accessory_users->count();
|
||||
|
||||
|
||||
@@ -49,6 +49,7 @@ class ReportsController extends Controller
|
||||
'created_at',
|
||||
'target_id',
|
||||
'user_id',
|
||||
'accept_signature',
|
||||
'action_type',
|
||||
'note'
|
||||
];
|
||||
|
||||
@@ -76,9 +76,32 @@ class AssetCheckinController extends Controller
|
||||
$asset->status_id = e($request->get('status_id'));
|
||||
}
|
||||
|
||||
// This is just meant to correct legacy issues where some user data would have 0
|
||||
// as a location ID, which isn't valid. Later versions of Snipe-IT have stricter validation
|
||||
// rules, so it's necessary to fix this for long-time users. It's kinda gross, but will help
|
||||
// people (and their data) in the long run
|
||||
|
||||
if ($asset->rtd_location_id=='0') {
|
||||
\Log::debug('Manually override the RTD location IDs');
|
||||
\Log::debug('Original RTD Location ID: '.$asset->rtd_location_id);
|
||||
$asset->rtd_location_id = '';
|
||||
\Log::debug('New RTD Location ID: '.$asset->rtd_location_id);
|
||||
}
|
||||
|
||||
if ($asset->location_id=='0') {
|
||||
\Log::debug('Manually override the location IDs');
|
||||
\Log::debug('Original Location ID: '.$asset->location_id);
|
||||
$asset->location_id = '';
|
||||
\Log::debug('New RTD Location ID: '.$asset->location_id);
|
||||
}
|
||||
|
||||
$asset->location_id = $asset->rtd_location_id;
|
||||
\Log::debug('After Location ID: '.$asset->location_id);
|
||||
\Log::debug('After RTD Location ID: '.$asset->rtd_location_id);
|
||||
|
||||
|
||||
if ($request->filled('location_id')) {
|
||||
\Log::debug('NEW Location ID: '.$request->get('location_id'));
|
||||
$asset->location_id = e($request->get('location_id'));
|
||||
}
|
||||
|
||||
@@ -97,6 +120,6 @@ class AssetCheckinController extends Controller
|
||||
return redirect()->route("hardware.index")->with('success', trans('admin/hardware/message.checkin.success'));
|
||||
}
|
||||
// Redirect to the asset management page with error
|
||||
return redirect()->route("hardware.index")->with('error', trans('admin/hardware/message.checkin.error'));
|
||||
return redirect()->route("hardware.index")->with('error', trans('admin/hardware/message.checkin.error').$asset->getErrors());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -80,7 +80,7 @@ class AssetCheckoutController extends Controller
|
||||
}
|
||||
|
||||
// Redirect to the asset management page with error
|
||||
return redirect()->to("hardware/$assetId/checkout")->with('error', trans('admin/hardware/message.checkout.error'))->withErrors($asset->getErrors());
|
||||
return redirect()->to("hardware/$assetId/checkout")->with('error', trans('admin/hardware/message.checkout.error').$asset->getErrors());
|
||||
} catch (ModelNotFoundException $e) {
|
||||
return redirect()->back()->with('error', trans('admin/hardware/message.checkout.error'))->withErrors($asset->getErrors());
|
||||
} catch (CheckoutNotAllowed $e) {
|
||||
|
||||
@@ -143,11 +143,10 @@ class LicenseFilesController extends Controller
|
||||
// We have to override the URL stuff here, since local defaults in Laravel's Flysystem
|
||||
// won't work, as they're not accessible via the web
|
||||
if (config('filesystems.default') == 'local') {
|
||||
\Log::debug('The private filesystem is local');
|
||||
return Response::make(Storage::get($file));
|
||||
|
||||
return Storage::download($file);
|
||||
} else {
|
||||
if ($download != 'true') {
|
||||
\Log::debug('display the file');
|
||||
if ($contents = file_get_contents(Storage::url($file))) {
|
||||
return Response::make(Storage::url($file)->header('Content-Type', mime_content_type($file)));
|
||||
}
|
||||
|
||||
@@ -70,7 +70,7 @@ class ManufacturersController extends Controller
|
||||
$manufacturer->support_url = $request->input('support_url');
|
||||
$manufacturer->support_phone = $request->input('support_phone');
|
||||
$manufacturer->support_email = $request->input('support_email');
|
||||
$manufacturer = $request->handleImages($manufacturer,600, public_path().'/uploads/manufacturers');
|
||||
$manufacturer = $request->handleImages($manufacturer);
|
||||
|
||||
|
||||
|
||||
@@ -137,7 +137,7 @@ class ManufacturersController extends Controller
|
||||
$manufacturer->image = null;
|
||||
}
|
||||
|
||||
$manufacturer = $request->handleImages($manufacturer,600, public_path().'/uploads/manufacturers');
|
||||
$manufacturer = $request->handleImages($manufacturer);
|
||||
|
||||
|
||||
if ($manufacturer->save()) {
|
||||
|
||||
@@ -682,7 +682,7 @@ class ReportsController extends Controller
|
||||
$diff = ($asset->purchase_cost - $depreciation);
|
||||
$row[] = Helper::formatCurrencyOutput($depreciation);
|
||||
$row[] = Helper::formatCurrencyOutput($diff);
|
||||
$row[] = ($asset->depreciated_date()!='') ? $asset->depreciated_date()->format('Y-m-d') : '';
|
||||
$row[] = ($asset->depreciation) ? $asset->depreciated_date()->format('Y-m-d') : '';
|
||||
}
|
||||
|
||||
if ($request->filled('checkout_date')) {
|
||||
|
||||
@@ -106,7 +106,7 @@ class SecurityHeaders
|
||||
$csp_policy[] = "connect-src 'self'";
|
||||
$csp_policy[] = "object-src 'none'";
|
||||
$csp_policy[] = "font-src 'self' data:";
|
||||
$csp_policy[] = "img-src 'self' data: gravatar.com maps.google.com maps.gstatic.com *.googleapis.com";
|
||||
$csp_policy[] = "img-src 'self' data: ".config('app.url')." https://secure.gravatar.com http://gravatar.com maps.google.com maps.gstatic.com *.googleapis.com";
|
||||
$csp_policy = join(';', $csp_policy);
|
||||
$response->headers->set('Content-Security-Policy', $csp_policy);
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@ class SaveUserRequest extends FormRequest
|
||||
{
|
||||
|
||||
$rules = [
|
||||
'manager_id' => "nullable|exists:users,id|different:users.id"
|
||||
'manager_id' => "nullable|exists:users,id"
|
||||
];
|
||||
|
||||
switch($this->method())
|
||||
|
||||
@@ -68,8 +68,13 @@ class AccessoriesTransformer
|
||||
|
||||
|
||||
$array = array();
|
||||
|
||||
|
||||
foreach ($accessory_users as $user) {
|
||||
\Log::debug(print_r($user->pivot, true));
|
||||
\Log::debug(print_r($user->pivot, true));
|
||||
$array[] = [
|
||||
|
||||
'assigned_pivot_id' => $user->pivot->id,
|
||||
'id' => (int) $user->id,
|
||||
'username' => e($user->username),
|
||||
@@ -77,7 +82,8 @@ class AccessoriesTransformer
|
||||
'first_name'=> e($user->first_name),
|
||||
'last_name'=> e($user->last_name),
|
||||
'employee_number' => e($user->employee_num),
|
||||
'checkout_notes' => $accessory->lastCheckoutArray[0]['note'],
|
||||
'checkout_notes' => $user->pivot->note,
|
||||
'last_checkout' => Helper::getFormattedDateObject($user->pivot->created_at, 'datetime'),
|
||||
'type' => 'user',
|
||||
'available_actions' => ['checkin' => true]
|
||||
];
|
||||
|
||||
@@ -113,7 +113,7 @@ class ActionlogsTransformer
|
||||
] : null,
|
||||
|
||||
'note' => ($actionlog->note) ? e($actionlog->note): null,
|
||||
'signature_file' => ($actionlog->signature_filename) ? route('log.signature.view', ['filename' => $actionlog->signature_filename ]) : null,
|
||||
'signature_file' => ($actionlog->accept_signature) ? route('log.signature.view', ['filename' => $actionlog->accept_signature ]) : null,
|
||||
'log_meta' => ((isset($clean_meta)) && (is_array($clean_meta))) ? $clean_meta: null,
|
||||
'action_date' => ($actionlog->action_date) ? Helper::getFormattedDateObject($actionlog->action_date, 'datetime'): null,
|
||||
|
||||
|
||||
@@ -234,7 +234,7 @@ class Accessory extends SnipeModel
|
||||
|
||||
public function users()
|
||||
{
|
||||
return $this->belongsToMany('\App\Models\User', 'accessories_users', 'accessory_id', 'assigned_to')->withPivot('id')->withTrashed();
|
||||
return $this->belongsToMany('\App\Models\User', 'accessories_users', 'accessory_id', 'assigned_to')->withPivot('id', 'created_at', 'note')->withTrashed();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -120,9 +120,6 @@ class Setting extends Model
|
||||
try {
|
||||
$usercount = User::withTrashed()->count();
|
||||
$settingsCount = self::count();
|
||||
\Log::debug('User table and settings table exist and have records.');
|
||||
\Log::debug('Settings: '.$settingsCount );
|
||||
\Log::debug('Users: '.$usercount );
|
||||
return $usercount > 0 && $settingsCount > 0;
|
||||
} catch (\Throwable $th) {
|
||||
\Log::debug('User table and settings table DO NOT exist or DO NOT have records');
|
||||
|
||||
+3
-2
@@ -74,7 +74,7 @@ class User extends SnipeModel implements AuthenticatableContract, AuthorizableCo
|
||||
'password' => 'required|min:8',
|
||||
'locale' => 'max:10|nullable',
|
||||
'website' => 'url|nullable',
|
||||
'manager_id' => 'nullable|exists:users,id|different:users.id',
|
||||
'manager_id' => 'nullable|exists:users,id',
|
||||
'location_id' => 'exists:locations,id|nullable',
|
||||
];
|
||||
|
||||
@@ -295,7 +295,8 @@ class User extends SnipeModel implements AuthenticatableContract, AuthorizableCo
|
||||
*/
|
||||
public function accessories()
|
||||
{
|
||||
return $this->belongsToMany('\App\Models\Accessory', 'accessories_users', 'assigned_to', 'accessory_id')->withPivot('id')->withTrashed();
|
||||
return $this->belongsToMany('\App\Models\Accessory', 'accessories_users', 'assigned_to', 'accessory_id')
|
||||
->withPivot('id', 'created_at', 'note')->withTrashed();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -33,7 +33,8 @@ return [
|
||||
* how many proxies that client's request has
|
||||
* subsequently passed through.
|
||||
*/
|
||||
'proxies' => null, // [<ip addresses>,], '*'
|
||||
'proxies' => env('APP_TRUSTED_PROXIES') !== null ?
|
||||
explode(',', env('APP_TRUSTED_PROXIES')) : '*',
|
||||
|
||||
/*
|
||||
* To trust one or more specific proxies that connect
|
||||
|
||||
+6
-6
@@ -1,10 +1,10 @@
|
||||
<?php
|
||||
return array (
|
||||
'app_version' => 'v5.0.0',
|
||||
'full_app_version' => 'v5.0.0 - build 4484-g33cf4896d',
|
||||
'build_version' => '4484',
|
||||
'app_version' => 'v5.0.3',
|
||||
'full_app_version' => 'v5.0.3 - build 5443-g5f8221470',
|
||||
'build_version' => '5443',
|
||||
'prerelease_version' => '',
|
||||
'hash_version' => 'g33cf4896d',
|
||||
'full_hash' => 'v5.0.0-1-g33cf4896d',
|
||||
'branch' => 'develop',
|
||||
'hash_version' => 'g5f8221470',
|
||||
'full_hash' => 'v5.0.2-27-g5f8221470',
|
||||
'branch' => 'master',
|
||||
);
|
||||
@@ -0,0 +1,89 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use App\Models\Accessory;
|
||||
use App\Models\Actionlog;
|
||||
|
||||
class MoveAccessoryCheckoutNoteToJoinTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::table('accessories_users', function (Blueprint $table) {
|
||||
$table->string('note')->nullable(true)->default(null);
|
||||
});
|
||||
|
||||
// Loop through the checked out accessories, find their related action_log entry, and copy over the note
|
||||
// to the newly created note field
|
||||
|
||||
$accessories = Accessory::get();
|
||||
$count = 0;
|
||||
\Log::debug('Accessory Count: '. $accessories->count());
|
||||
|
||||
|
||||
// Loop through all of the accessories
|
||||
foreach ($accessories as $accessory) {
|
||||
$count++;
|
||||
|
||||
\Log::debug('Querying join logs');
|
||||
$join_logs = DB::table('accessories_users')->get();
|
||||
|
||||
// Loop through the accessories_users records
|
||||
foreach ($join_logs as $join_log) {
|
||||
\Log::debug($join_logs->count().' join log records');
|
||||
\Log::debug('Looking for accessories_users that match '. $join_log->created_at);
|
||||
|
||||
// Get the records from action_logs so we can copy the notes over to the new notes field
|
||||
// on the accessories_users table
|
||||
$action_log_entries = Actionlog::where('created_at', '=',$join_log->created_at)
|
||||
->where('target_id', '=',$join_log->assigned_to)
|
||||
->where('item_id', '=',$accessory->id)
|
||||
->where('target_type', '=','App\\Models\\User')
|
||||
->where('action_type', '=', 'checkout')
|
||||
->orderBy('created_at', 'DESC')->get();
|
||||
|
||||
\Log::debug($action_log_entries->count().' matching entries in the action_logs table');
|
||||
\Log::debug('Looking for action_logs that match '. $join_log->created_at);
|
||||
|
||||
foreach ($action_log_entries as $action_log_entry) {
|
||||
|
||||
\Log::debug('Checkout date in asset log: '.$action_log_entry->created_at.' against accessories_users: '.$join_log->created_at);
|
||||
\Log::debug('Action log: '.$action_log_entry->created_at);
|
||||
\Log::debug('Join log: '.$join_log->created_at);
|
||||
|
||||
if ($action_log_entry->created_at == $join_log->created_at) {
|
||||
DB::table('accessories_users')
|
||||
->where('id', $join_log->id)
|
||||
->update(['note' => $action_log_entry->note]);
|
||||
} else {
|
||||
\Log::debug('No match');
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::table('accessories_users', function (Blueprint $table) {
|
||||
$table->dropColumn('note');
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use App\Models\User;
|
||||
use App\Models\Asset;
|
||||
|
||||
class FixZeroValuesForLocations extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
App\Models\Asset::where('location_id', '=', '0')
|
||||
->update(['location_id' => null]);
|
||||
|
||||
App\Models\Asset::where('rtd_location_id', '=', '0')
|
||||
->update(['rtd_location_id' => null]);
|
||||
|
||||
App\Models\User::where('location_id', '=', '0')
|
||||
->update(['location_id' => null]);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
||||
@@ -144,6 +144,10 @@ a, a:link, a:visited, .btn-primary.hover {
|
||||
#assetsListingTable>tbody>tr.selected>td {
|
||||
background-color: var(--back-main);
|
||||
}
|
||||
#assetsListingTable>tbody>tr>td {
|
||||
color: var(--link);
|
||||
}
|
||||
|
||||
body {
|
||||
color: var(--text-main);
|
||||
}
|
||||
@@ -201,6 +205,13 @@ body {
|
||||
background-color: var(--back-main);
|
||||
color: var(--text-main);
|
||||
}
|
||||
.dynamic-form-row{
|
||||
color: @green;
|
||||
}
|
||||
|
||||
.select2-container--default .select2-selection--single .select2-selection__rendered {
|
||||
color: var(--header);
|
||||
}
|
||||
.form-control {
|
||||
background-color: var(--back-main);
|
||||
color: var(--text-main);
|
||||
@@ -219,6 +230,9 @@ input[type=text], input[type=search] {
|
||||
background-color: var(--back-sub)!important;
|
||||
color: var(--text-main);
|
||||
}
|
||||
li.select2-results__option{
|
||||
color:@green;
|
||||
}
|
||||
#licensesTable>tbody>tr>td>nobr>a>i.fa {
|
||||
color: var(--text-main);
|
||||
}
|
||||
@@ -293,7 +307,9 @@ input[type=text], input[type=search] {
|
||||
#webui>div>div>div>div>div>table>tbody>tr>td>a>i.fa {
|
||||
color: var(--text-main);
|
||||
}
|
||||
|
||||
#webui>#app>.row>.col-md-12>.box>.box-body>.row>.col-md-12 {
|
||||
color:@green;
|
||||
}
|
||||
a {
|
||||
color: var(--link);
|
||||
&:link {
|
||||
@@ -333,4 +349,3 @@ a {
|
||||
border-top: 1px solid #dddddd;
|
||||
display: table-cell;
|
||||
}
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ return array(
|
||||
'ad_domain_help' => 'This is sometimes the same as your email domain, but not always.',
|
||||
'ad_append_domain_label' => 'Append domain name',
|
||||
'ad_append_domain' => 'Append domain name to username field',
|
||||
'ad_append_domain_help' => 'User doesn\'t require to write "username@domain.local", they can just type "username".' ,
|
||||
'ad_append_domain_help' => 'User isn\'t required to write "username@domain.local", they can just type "username".' ,
|
||||
'admin_cc_email' => 'CC Email',
|
||||
'admin_cc_email_help' => 'If you would like to send a copy of checkin/checkout emails that are sent to users to an additional email account, enter it here. Otherwise leave this field blank.',
|
||||
'is_ad' => 'This is an Active Directory server',
|
||||
|
||||
@@ -76,6 +76,7 @@
|
||||
<tr>
|
||||
<th data-searchable="false" data-formatter="usersLinkFormatter" data-sortable="false" data-field="name">{{ trans('general.user') }}</th>
|
||||
<th data-searchable="false" data-sortable="false" data-field="checkout_notes">{{ trans('general.notes') }}</th>
|
||||
<th data-searchable="false" data-formatter="dateDisplayFormatter" data-sortable="false" data-field="last_checkout">{{ trans('admin/hardware/table.checkout_date') }}</th>
|
||||
<th data-searchable="false" data-sortable="false" data-field="actions" data-formatter="accessoriesInOutFormatter">{{ trans('table.actions') }}</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
@section('content')
|
||||
|
||||
|
||||
<link rel="stylesheet" href="{{ mix('css/signature-pad.min.css') }}">
|
||||
<link rel="stylesheet" href="{{ url('css/signature-pad.min.css') }}">
|
||||
|
||||
<style>
|
||||
.form-horizontal .control-label, .form-horizontal .radio, .form-horizontal .checkbox, .form-horizontal .radio-inline, .form-horizontal .checkbox-inline {
|
||||
@@ -25,6 +25,12 @@
|
||||
overflow: scroll;
|
||||
}
|
||||
|
||||
.m-signature-pad--body {
|
||||
border-style: solid;
|
||||
border-color: grey;
|
||||
border-width: thin;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
|
||||
|
||||
@@ -94,28 +94,25 @@
|
||||
</div>
|
||||
|
||||
<!-- Avatar -->
|
||||
|
||||
@if ($user->avatar)
|
||||
<div class="form-group {{ $errors->has('avatar_delete') ? 'has-error' : '' }}">
|
||||
<label class="col-md-3 control-label" for="avatar_delete">{{ trans('general.avatar_delete') }}</label>
|
||||
<div class="col-md-8">
|
||||
{{ Form::checkbox('avatar_delete') }}
|
||||
<img src="{{ url('/') }}/uploads/avatars/{{ $user->avatar }}" class="avatar img-circle" alt="{{ $user->present()->fullName() }} avatar image">
|
||||
{!! $errors->first('avatar_delete', '<span class="alert-msg" aria-hidden="true">:message</span>') !!}
|
||||
<div class="form-group {{ $errors->has('image_delete') ? 'has-error' : '' }}">
|
||||
<label class="col-md-3 control-label" for="avatar_delete">{{ trans('general.image_delete') }}</label>
|
||||
<div class="col-md-9">
|
||||
<label for="avatar_delete">
|
||||
{{ Form::checkbox('avatar_delete', '1', old('avatar_delete'), array('class' => 'minimal')) }}
|
||||
</label>
|
||||
<br>
|
||||
<img src="{{ url('/') }}/uploads/avatars/{{ $user->avatar }}" alt="{{ $user->present()->fullName() }} avatar image">
|
||||
{!! $errors->first('avatar_delete', '<span class="alert-msg" aria-hidden="true"><br>:message</span>') !!}
|
||||
</div>
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<div class="form-group {{ $errors->has('avatar') ? 'has-error' : '' }}">
|
||||
<label class="col-md-3 control-label" for="avatar">{{ trans('general.image_upload') }}</label>
|
||||
<div class="col-md-5">
|
||||
<label class="btn btn-default">
|
||||
{{ trans('button.select_file') }}
|
||||
<input type="file" name="avatar" accept="image/gif,image/jpeg,image/png,image/svg" hidden>
|
||||
</label>
|
||||
<p class="help-block">{{ trans('general.image_filetypes_help') }}</p>
|
||||
{!! $errors->first('avatar', '<span class="alert-msg" aria-hidden="true">:message</span>') !!}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@include ('partials.forms.edit.image-upload', ['fieldname' => 'avatar'])
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -47,7 +47,7 @@
|
||||
</div>
|
||||
|
||||
|
||||
@include ('partials.forms.edit.model-select', ['translated_name' => trans('admin/hardware/form.model'), 'fieldname' => 'model_id', 'required' => 'true'])
|
||||
@include ('partials.forms.edit.model-select', ['translated_name' => trans('admin/hardware/form.model'), 'fieldname' => 'model_id', 'field_req' => true])
|
||||
|
||||
|
||||
<div id='custom_fields_content'>
|
||||
|
||||
@@ -39,7 +39,6 @@
|
||||
data-pagination="true"
|
||||
data-id-table="requestedAssets"
|
||||
data-cookie-id-table="requestedAssets"
|
||||
data-url="{{ route('api.consumables.index') }}"
|
||||
data-export-options='{
|
||||
"fileName": "export-assetrequests-{{ date('Y-m-d') }}",
|
||||
"ignoreColumn": ["actions","image","change","checkbox","checkincheckout","icon"]
|
||||
|
||||
@@ -71,7 +71,7 @@
|
||||
@if (!$asset->model)
|
||||
<div class="col-md-12">
|
||||
<div class="callout callout-danger">
|
||||
<h2>NO MODEL ASSOCIATED</h4>
|
||||
<h2>NO MODEL ASSOCIATED</h2>
|
||||
<p>This will break things in weird and horrible ways. Edit this asset now to assign it a model. </p>
|
||||
</div>
|
||||
</div>
|
||||
@@ -735,7 +735,7 @@
|
||||
@endif
|
||||
|
||||
@if (($asset->assignedTo) && ($asset->deleted_at==''))
|
||||
<h2>{{ trans('admin/hardware/form.checkedout_to') }}</h4>
|
||||
<h2>{{ trans('admin/hardware/form.checkedout_to') }}</h2>
|
||||
<p>
|
||||
@if($asset->checkedOutToUser()) <!-- Only users have avatars currently-->
|
||||
<img src="{{ $asset->assignedTo->present()->gravatar() }}" class="user-image-inline" alt="{{ $asset->assignedTo->present()->fullName() }}">
|
||||
|
||||
@@ -1,20 +1,17 @@
|
||||
@component('mail::message')
|
||||
|
||||
{{ trans_choice('mail.assets_warrantee_alert', $assets->count(), ['count'=>$assets->count(), 'threshold' => $threshold]) }}
|
||||
|
||||
@component('mail::table')
|
||||
| |{{ trans('mail.name') }} |{{ trans('mail.expires') }} |{{ trans('mail.Days') }}|{{ trans('mail.supplier') }} | {{ trans('mail.assigned_to') }}
|
||||
| |:------------- |:-------------|:---------|:---------|:---------|:---------|
|
||||
|
||||
<table width="100%">
|
||||
<tr><td> </td><td>{{ trans('mail.name') }}</td><td>{{ trans('mail.Days') }}</td><td>{{ trans('mail.expires') }}</td><td>{{ trans('mail.supplier') }}</td><td>{{ trans('mail.assigned_to') }}</td></tr>
|
||||
@foreach ($assets as $asset)
|
||||
@php
|
||||
$expires = \App\Helpers\Helper::getFormattedDateObject($asset->present()->warrantee_expires, 'date');
|
||||
$diff = round(abs(strtotime($asset->present()->warrantee_expires) - strtotime(date('Y-m-d')))/86400);
|
||||
$icon = ($diff <= ($threshold / 2)) ? '🚨' : (($diff <= $threshold) ? '⚠️' : ' ');
|
||||
|
||||
@endphp
|
||||
|{{ $icon }}| [{{ $asset->present()->name }}]({{ route('hardware.show', $asset->id) }}) | {{ $expires['formatted'] }} | {{ $diff }} {{ trans('mail.Days') }} | {{ ($asset->supplier ? e($asset->supplier->name) : '') }}|{{ ($asset->assignedTo ? e($asset->assignedTo->present()->name()) : '') }}
|
||||
<tr><td>{{ $icon }} </td><td> <a href="{{ route('hardware.show', $asset->id) }}">{{ $asset->present()->name }}</a> </td><td> {{ $diff }} {{ trans('mail.Days') }} </td><td> {{ $expires['formatted'] }} </td><td> {{ ($asset->supplier ? e($asset->supplier->name) : '') }} </td><td> {{ ($asset->assignedTo ? e($asset->assignedTo->present()->name()) : '') }} </td></tr>
|
||||
@endforeach
|
||||
</table>
|
||||
@endcomponent
|
||||
|
||||
|
||||
@endcomponent
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
{{ Form::label($fieldname, $translated_name, array('class' => 'col-md-3 control-label')) }}
|
||||
|
||||
<div class="col-md-7{{ ((isset($required) && ($required =='true'))) ? ' required' : '' }}">
|
||||
<select class="js-data-ajax" data-endpoint="models" data-placeholder="{{ trans('general.select_model') }}" name="{{ $fieldname }}" style="width: 100%" id="model_select_id" aria-label="{{ $fieldname }}" data-validation="required" required>
|
||||
<select class="js-data-ajax" data-endpoint="models" data-placeholder="{{ trans('general.select_model') }}" name="{{ $fieldname }}" style="width: 100%" id="model_select_id" aria-label="{{ $fieldname }}" {{ (isset($field_req) ? 'data-validation="required" required' : '') }}>
|
||||
@if ($model_id = old($fieldname, (isset($item)) ? $item->{$fieldname} : ''))
|
||||
<option value="{{ $model_id }}" selected="selected">
|
||||
{{ (\App\Models\AssetModel::find($model_id)) ? \App\Models\AssetModel::find($model_id)->name : '' }}
|
||||
|
||||
@@ -128,7 +128,7 @@
|
||||
<div id="purgebarcodesstatus-error" class="text-danger"></div>
|
||||
</div>
|
||||
<div class="col-md-9 col-md-offset-3">
|
||||
<p class="help-block">This will attempt to delete cached barcodes. This would typically only be used if your barcode dettings have changed, or if your Snipe-IT URL has changed. Barcodes will be re-generated when accessed next.</p>
|
||||
<p class="help-block">This will attempt to delete cached barcodes. This would typically only be used if your barcode settings have changed, or if your Snipe-IT URL has changed. Barcodes will be re-generated when accessed next.</p>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
@@ -353,6 +353,8 @@
|
||||
<form action="{{ route('users/bulkedit') }}" method="POST">
|
||||
<!-- CSRF Token -->
|
||||
<input type="hidden" name="_token" value="{{ csrf_token() }}" />
|
||||
<input type="hidden" name="bulk_actions" value="delete" />
|
||||
|
||||
<input type="hidden" name="ids[{{ $user->id }}]" value="{{ $user->id }}" />
|
||||
<button style="width: 100%;" class="btn btn-sm btn-danger hidden-print">{{ trans('button.checkin_and_delete') }}</button>
|
||||
</form>
|
||||
|
||||
+18
-18
@@ -1,19 +1,19 @@
|
||||
<table class="action" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table width="100%" border="0" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table border="0" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td>
|
||||
<a href="{{ $url }}" class="button button-{{ $color ?? 'blue' }}" target="_blank">{{ $slot }}</a>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
<table class="action" align="center" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table width="100%" border="0" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table border="0" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td>
|
||||
<a href="{{ $url }}" class="button button-{{ $color ?? 'primary' }}" target="_blank">{{ $slot }}</a>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
+9
-9
@@ -1,11 +1,11 @@
|
||||
<tr>
|
||||
<td>
|
||||
<table class="footer" align="center" width="570" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td class="content-cell" align="center">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
<td>
|
||||
<table class="footer" align="center" width="570" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td class="content-cell" align="center">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
+5
-33
@@ -1,35 +1,7 @@
|
||||
<tr>
|
||||
<td class="header"{!! ($snipeSettings->header_color!='') ? ' style="background-color: '.e($snipeSettings->header_color).'"' : '' !!}>
|
||||
|
||||
@if (($snipeSettings->show_images_in_email=='1' ) && ($snipeSettings::setupCompleted()))
|
||||
|
||||
<!-- show text and logo -->
|
||||
@if ($snipeSettings->brand == '3')
|
||||
@if ($snipeSettings->email_logo!='')
|
||||
<img class="logo-text" src="{{ Storage::disk('public')->url('').e($snipeSettings->email_logo) }}"alt="{{ $snipeSettings->site_name }}">
|
||||
@elseif ($snipeSettings->logo!='')
|
||||
<img class="logo-text" src="{{ Storage::disk('public')->url('').e($snipeSettings->logo) }}"alt="{{ $snipeSettings->site_name }}">
|
||||
@endif
|
||||
|
||||
{{ $snipeSettings->site_name }}
|
||||
|
||||
|
||||
<!-- show only logo -->
|
||||
@elseif ($snipeSettings->brand == '2')
|
||||
@if ($snipeSettings->email_logo!='')
|
||||
<img class="logo-only" style="float:left" src="{{ Storage::disk('public')->url('').e($snipeSettings->email_logo) }}" alt="{{ $snipeSettings->site_name }}">
|
||||
@elseif ($snipeSettings->logo!='')
|
||||
<img class="logo-only" src="{{ Storage::disk('public')->url('').e($snipeSettings->logo) }}" alt="{{ $snipeSettings->site_name }}">
|
||||
@endif
|
||||
|
||||
<!-- show only text -->
|
||||
@else
|
||||
{{ $snipeSettings->site_name }}
|
||||
@endif
|
||||
|
||||
|
||||
@else
|
||||
{{ $snipeSettings->site_name }}
|
||||
@endif
|
||||
</td>
|
||||
<td class="header">
|
||||
<a href="{{ $url }}">
|
||||
{{ $slot }}
|
||||
</a>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
+41
-47
@@ -1,60 +1,54 @@
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
||||
<head>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
|
||||
</head>
|
||||
<body>
|
||||
<style>
|
||||
@media only screen and (max-width: 600px) {
|
||||
.inner-body {
|
||||
width: 100% !important;
|
||||
}
|
||||
<style>
|
||||
@media only screen and (max-width: 600px) {
|
||||
.inner-body {
|
||||
width: 100% !important;
|
||||
}
|
||||
|
||||
.footer {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
.footer {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 500px) {
|
||||
.button {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
.logo {
|
||||
width:50px;
|
||||
height:50px;
|
||||
}
|
||||
</style>
|
||||
@media only screen and (max-width: 500px) {
|
||||
.button {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
<table class="wrapper" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table class="content" width="100%" cellpadding="0" cellspacing="0">
|
||||
{{ $header ?? '' }}
|
||||
<table class="wrapper" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table class="content" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
{{ $header ?? '' }}
|
||||
|
||||
<!-- Email Body -->
|
||||
<tr>
|
||||
<td class="body" width="100%" cellpadding="0" cellspacing="0">
|
||||
<table class="inner-body" align="center" width="90%" cellpadding="0" cellspacing="0">
|
||||
<!-- Body content -->
|
||||
<tr>
|
||||
<td class="content-cell">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
<!-- Email Body -->
|
||||
<tr>
|
||||
<td class="body" width="100%" cellpadding="0" cellspacing="0">
|
||||
<table class="inner-body" align="center" width="570" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<!-- Body content -->
|
||||
<tr>
|
||||
<td class="content-cell">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
|
||||
{{ $subcopy ?? '' }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
{{ $subcopy ?? '' }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
{{ $footer ?? '' }}
|
||||
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{{ $footer ?? '' }}
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
+3
-2
@@ -1,7 +1,7 @@
|
||||
<table class="panel" width="100%" cellpadding="0" cellspacing="0">
|
||||
<table class="panel" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td class="panel-content">
|
||||
<table width="100%" cellpadding="0" cellspacing="0">
|
||||
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td class="panel-item">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
@@ -11,3 +11,4 @@
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
||||
+6
-6
@@ -1,7 +1,7 @@
|
||||
<table class="promotion" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
<table class="promotion" align="center" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td align="center">
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<table width="100%" border="0" cellpadding="0" cellspacing="0">
|
||||
<table width="100%" border="0" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table border="0" cellpadding="0" cellspacing="0">
|
||||
<table border="0" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td>
|
||||
<a href="{{ $url }}" class="button button-green" target="_blank">{{ $slot }}</a>
|
||||
|
||||
+6
-6
@@ -1,7 +1,7 @@
|
||||
<table class="subcopy" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td>
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
<table class="subcopy" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
||||
<tr>
|
||||
<td>
|
||||
{{ Illuminate\Mail\Markdown::parse($slot) }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
+54
-54
@@ -1,13 +1,15 @@
|
||||
/* Base */
|
||||
|
||||
body, body *:not(html):not(style):not(br):not(tr):not(code) {
|
||||
font-family: Avenir, Helvetica, sans-serif;
|
||||
body,
|
||||
body *:not(html):not(style):not(br):not(tr):not(code) {
|
||||
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif,
|
||||
'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol';
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
background-color: #f5f8fa;
|
||||
color: #74787E;
|
||||
background-color: #f8fafc;
|
||||
color: #74787e;
|
||||
height: 100%;
|
||||
hyphens: auto;
|
||||
line-height: 1.4;
|
||||
@@ -30,7 +32,7 @@ blockquote {
|
||||
}
|
||||
|
||||
a {
|
||||
color: #3869D4;
|
||||
color: #3869d4;
|
||||
}
|
||||
|
||||
a img {
|
||||
@@ -40,7 +42,7 @@ a img {
|
||||
/* Typography */
|
||||
|
||||
h1 {
|
||||
color: #2F3133;
|
||||
color: #3d4852;
|
||||
font-size: 19px;
|
||||
font-weight: bold;
|
||||
margin-top: 0;
|
||||
@@ -48,7 +50,7 @@ h1 {
|
||||
}
|
||||
|
||||
h2 {
|
||||
color: #2F3133;
|
||||
color: #3d4852;
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
margin-top: 0;
|
||||
@@ -56,7 +58,7 @@ h2 {
|
||||
}
|
||||
|
||||
h3 {
|
||||
color: #2F3133;
|
||||
color: #3d4852;
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
margin-top: 0;
|
||||
@@ -64,7 +66,7 @@ h3 {
|
||||
}
|
||||
|
||||
p {
|
||||
color: #74787E;
|
||||
color: #3d4852;
|
||||
font-size: 16px;
|
||||
line-height: 1.5em;
|
||||
margin-top: 0;
|
||||
@@ -82,7 +84,7 @@ img {
|
||||
/* Layout */
|
||||
|
||||
.wrapper {
|
||||
background-color: #f5f8fa;
|
||||
background-color: #f8fafc;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
@@ -105,7 +107,6 @@ img {
|
||||
.header {
|
||||
padding: 25px 0;
|
||||
text-align: center;
|
||||
font-size: 20px;
|
||||
}
|
||||
|
||||
.header a {
|
||||
@@ -119,9 +120,9 @@ img {
|
||||
/* Body */
|
||||
|
||||
.body {
|
||||
background-color: #FFFFFF;
|
||||
border-bottom: 1px solid #EDEFF2;
|
||||
border-top: 1px solid #EDEFF2;
|
||||
background-color: #ffffff;
|
||||
border-bottom: 1px solid #edeff2;
|
||||
border-top: 1px solid #edeff2;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
@@ -131,9 +132,10 @@ img {
|
||||
}
|
||||
|
||||
.inner-body {
|
||||
background-color: #FFFFFF;
|
||||
background-color: #ffffff;
|
||||
margin: 0 auto;
|
||||
padding: 0;
|
||||
width: 90%;
|
||||
-premailer-cellpadding: 0;
|
||||
-premailer-cellspacing: 0;
|
||||
-premailer-width: 570px;
|
||||
@@ -142,7 +144,7 @@ img {
|
||||
/* Subcopy */
|
||||
|
||||
.subcopy {
|
||||
border-top: 1px solid #EDEFF2;
|
||||
border-top: 1px solid #edeff2;
|
||||
margin-top: 25px;
|
||||
padding-top: 25px;
|
||||
}
|
||||
@@ -164,7 +166,7 @@ img {
|
||||
}
|
||||
|
||||
.footer p {
|
||||
color: #AEAEAE;
|
||||
color: #aeaeae;
|
||||
font-size: 12px;
|
||||
text-align: center;
|
||||
}
|
||||
@@ -180,19 +182,21 @@ img {
|
||||
}
|
||||
|
||||
.table th {
|
||||
border-bottom: 1px solid #EDEFF2;
|
||||
border-bottom: 1px solid #edeff2;
|
||||
padding-bottom: 8px;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.table td {
|
||||
color: #74787E;
|
||||
color: #74787e;
|
||||
font-size: 15px;
|
||||
line-height: 15px;
|
||||
padding: 8px 0;
|
||||
line-height: 18px;
|
||||
padding: 10px 0;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.content-cell {
|
||||
padding: 20px;
|
||||
padding: 35px;
|
||||
}
|
||||
|
||||
/* Buttons */
|
||||
@@ -210,34 +214,37 @@ img {
|
||||
.button {
|
||||
border-radius: 3px;
|
||||
box-shadow: 0 2px 3px rgba(0, 0, 0, 0.16);
|
||||
color: #FFF;
|
||||
color: #fff;
|
||||
display: inline-block;
|
||||
text-decoration: none;
|
||||
-webkit-text-size-adjust: none;
|
||||
}
|
||||
|
||||
.button-blue {
|
||||
background-color: #3097D1;
|
||||
border-top: 10px solid #3097D1;
|
||||
border-right: 18px solid #3097D1;
|
||||
border-bottom: 10px solid #3097D1;
|
||||
border-left: 18px solid #3097D1;
|
||||
.button-blue,
|
||||
.button-primary {
|
||||
background-color: #3490dc;
|
||||
border-top: 10px solid #3490dc;
|
||||
border-right: 18px solid #3490dc;
|
||||
border-bottom: 10px solid #3490dc;
|
||||
border-left: 18px solid #3490dc;
|
||||
}
|
||||
|
||||
.button-green {
|
||||
background-color: #2ab27b;
|
||||
border-top: 10px solid #2ab27b;
|
||||
border-right: 18px solid #2ab27b;
|
||||
border-bottom: 10px solid #2ab27b;
|
||||
border-left: 18px solid #2ab27b;
|
||||
.button-green,
|
||||
.button-success {
|
||||
background-color: #38c172;
|
||||
border-top: 10px solid #38c172;
|
||||
border-right: 18px solid #38c172;
|
||||
border-bottom: 10px solid #38c172;
|
||||
border-left: 18px solid #38c172;
|
||||
}
|
||||
|
||||
.button-red {
|
||||
background-color: #bf5329;
|
||||
border-top: 10px solid #bf5329;
|
||||
border-right: 18px solid #bf5329;
|
||||
border-bottom: 10px solid #bf5329;
|
||||
border-left: 18px solid #bf5329;
|
||||
.button-red,
|
||||
.button-error {
|
||||
background-color: #e3342f;
|
||||
border-top: 10px solid #e3342f;
|
||||
border-right: 18px solid #e3342f;
|
||||
border-bottom: 10px solid #e3342f;
|
||||
border-left: 18px solid #e3342f;
|
||||
}
|
||||
|
||||
/* Panels */
|
||||
@@ -247,7 +254,7 @@ img {
|
||||
}
|
||||
|
||||
.panel-content {
|
||||
background-color: #EDEFF2;
|
||||
background-color: #f1f5f8;
|
||||
padding: 16px;
|
||||
}
|
||||
|
||||
@@ -263,8 +270,8 @@ img {
|
||||
/* Promotions */
|
||||
|
||||
.promotion {
|
||||
background-color: #FFFFFF;
|
||||
border: 2px dashed #9BA2AB;
|
||||
background-color: #ffffff;
|
||||
border: 2px dashed #9ba2ab;
|
||||
margin: 0;
|
||||
margin-bottom: 25px;
|
||||
margin-top: 25px;
|
||||
@@ -284,15 +291,8 @@ img {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.logo-text {
|
||||
max-width: 150px;
|
||||
max-height: 150px;
|
||||
vertical-align:middle;
|
||||
}
|
||||
/* Utilities */
|
||||
|
||||
.logo-only {
|
||||
max-width: 640px;
|
||||
max-height: 150px;
|
||||
vertical-align:middle;
|
||||
.break-all {
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
|
||||
+31
-31
@@ -1,39 +1,39 @@
|
||||
@component('mail::layout')
|
||||
{{-- Header --}}
|
||||
@slot('header')
|
||||
@component('mail::header', ['url' => config('app.url')])
|
||||
@if (($snipeSettings->show_images_in_email=='1' ) && ($snipeSettings::setupCompleted()))
|
||||
{{-- Header --}}
|
||||
@slot('header')
|
||||
@component('mail::header', ['url' => config('app.url')])
|
||||
@if (($snipeSettings->show_images_in_email=='1' ) && ($snipeSettings::setupCompleted()))
|
||||
|
||||
@if ($snipeSettings->brand == '3')
|
||||
@if ($snipeSettings->logo!='')
|
||||
<img class="navbar-brand-img logo" src="{{ url('/') }}/uploads/{{ $snipeSettings->logo }}">
|
||||
@endif
|
||||
{{ $snipeSettings->site_name }}
|
||||
@if ($snipeSettings->brand == '3')
|
||||
@if ($snipeSettings->logo!='')
|
||||
<img class="navbar-brand-img logo" src="{{ url('/') }}/uploads/{{ $snipeSettings->logo }}">
|
||||
@endif
|
||||
{{ $snipeSettings->site_name }}
|
||||
|
||||
@elseif ($snipeSettings->brand == '2')
|
||||
@if ($snipeSettings->logo!='')
|
||||
<img class="navbar-brand-img logo" src="{{ url('/') }}/uploads/{{ $snipeSettings->logo }}">
|
||||
@endif
|
||||
@else
|
||||
{{ $snipeSettings->site_name }}
|
||||
@endif
|
||||
@else
|
||||
Snipe-IT
|
||||
@endif
|
||||
@endcomponent
|
||||
@endslot
|
||||
@elseif ($snipeSettings->brand == '2')
|
||||
@if ($snipeSettings->logo!='')
|
||||
<img class="navbar-brand-img logo" src="{{ url('/') }}/uploads/{{ $snipeSettings->logo }}">
|
||||
@endif
|
||||
@else
|
||||
{{ $snipeSettings->site_name }}
|
||||
@endif
|
||||
@else
|
||||
Snipe-IT
|
||||
@endif
|
||||
@endcomponent
|
||||
@endslot
|
||||
|
||||
{{-- Body --}}
|
||||
{{ $slot }}
|
||||
{{-- Body --}}
|
||||
{{ $slot }}
|
||||
|
||||
{{-- Subcopy --}}
|
||||
@isset($subcopy)
|
||||
@slot('subcopy')
|
||||
@component('mail::subcopy')
|
||||
{{ $subcopy }}
|
||||
@endcomponent
|
||||
@endslot
|
||||
@endisset
|
||||
{{-- Subcopy --}}
|
||||
@isset($subcopy)
|
||||
@slot('subcopy')
|
||||
@component('mail::subcopy')
|
||||
{{ $subcopy }}
|
||||
@endcomponent
|
||||
@endslot
|
||||
@endisset
|
||||
|
||||
{{-- Footer --}}
|
||||
@slot('footer')
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}: {{ $url }}
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}
|
||||
@@ -0,0 +1 @@
|
||||
[{{ $slot }}]({{ $url }})
|
||||
@@ -0,0 +1,9 @@
|
||||
{!! strip_tags($header) !!}
|
||||
|
||||
{!! strip_tags($slot) !!}
|
||||
@isset($subcopy)
|
||||
|
||||
{!! strip_tags($subcopy) !!}
|
||||
@endisset
|
||||
|
||||
{!! strip_tags($footer) !!}
|
||||
@@ -0,0 +1,27 @@
|
||||
@component('mail::layout')
|
||||
{{-- Header --}}
|
||||
@slot('header')
|
||||
@component('mail::header', ['url' => config('app.url')])
|
||||
{{ config('app.name') }}
|
||||
@endcomponent
|
||||
@endslot
|
||||
|
||||
{{-- Body --}}
|
||||
{{ $slot }}
|
||||
|
||||
{{-- Subcopy --}}
|
||||
@isset($subcopy)
|
||||
@slot('subcopy')
|
||||
@component('mail::subcopy')
|
||||
{{ $subcopy }}
|
||||
@endcomponent
|
||||
@endslot
|
||||
@endisset
|
||||
|
||||
{{-- Footer --}}
|
||||
@slot('footer')
|
||||
@component('mail::footer')
|
||||
© {{ date('Y') }} {{ config('app.name') }}. @lang('All rights reserved.')
|
||||
@endcomponent
|
||||
@endslot
|
||||
@endcomponent
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}
|
||||
@@ -0,0 +1 @@
|
||||
[{{ $slot }}]({{ $url }})
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}
|
||||
@@ -0,0 +1 @@
|
||||
{{ $slot }}
|
||||
-54
@@ -187,29 +187,6 @@ $up = shell_exec('php artisan up');
|
||||
echo '-- '.$up."\n\n";
|
||||
|
||||
|
||||
echo "--------------------------------------------------------\n";
|
||||
echo "Step 11: Checking for v5 public storage directories: \n";
|
||||
echo "--------------------------------------------------------\n\n";
|
||||
|
||||
|
||||
if ((!file_exists('storage/app/public')) && (!is_dir('storage/app/public'))) {
|
||||
echo "- No public directory found in storage/app - creating one.\n\n";
|
||||
if (!mkdir('storage/app/public', 0777, true)) {
|
||||
echo "ERROR: Failed to create directory at storage/app/public. You should do this manually.\n\n";
|
||||
}
|
||||
$storage_simlink = shell_exec('php artisan storage:link');
|
||||
echo $storage_simlink;
|
||||
|
||||
} else {
|
||||
echo "- Public storage directory already exists. Skipping...\n\n";
|
||||
}
|
||||
|
||||
echo "- Copying files into storage/app/public.\n\n";
|
||||
if (rmove('public/uploads','storage/app/public')) {
|
||||
echo "- Copy successful.\n\n";
|
||||
} else {
|
||||
echo "- Copy failed - you should do this manually by copying the files from public/uploads into the storage/app/public directory.\n\n";
|
||||
}
|
||||
|
||||
echo "--------------------------------------------------------\n";
|
||||
echo "FINISHED! Clear your browser cookies and re-login to use :\n";
|
||||
@@ -217,34 +194,3 @@ echo "your upgraded Snipe-IT.\n";
|
||||
echo "--------------------------------------------------------\n\n";
|
||||
|
||||
|
||||
/**
|
||||
* Recursively move files from one directory to another
|
||||
*
|
||||
* @param String $src - Source of files being moved
|
||||
* @param String $dest - Destination of files being moved
|
||||
*/
|
||||
function rmove($src, $dest){
|
||||
|
||||
// If source is not a directory stop processing
|
||||
if(!is_dir($src)) return false;
|
||||
|
||||
// If the destination directory does not exist create it
|
||||
if(!is_dir($dest)) {
|
||||
if(!mkdir($dest)) {
|
||||
// If the destination directory could not be created stop processing
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Open the source directory to read in files
|
||||
$i = new DirectoryIterator($src);
|
||||
foreach($i as $f) {
|
||||
if($f->isFile()) {
|
||||
rename($f->getRealPath(), "$dest/" . $f->getFilename());
|
||||
} else if(!$f->isDot() && $f->isDir()) {
|
||||
rmove($f->getRealPath(), "$dest/$f");
|
||||
unlink($f->getRealPath());
|
||||
}
|
||||
}
|
||||
unlink($src);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user