CVE-2023-5511 (published 2023-10-11T01:15Z)

Cross-Site Request Forgery (CSRF) in GitHub repository snipe/snipe-it prior to v.6.2.3.

CVSS v3 base score: 8.8, HIGH (CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H)

Weakness information:
cwe_id: CWE-352
cwe_name: Cross-Site Request Forgery (CSRF)
description: The web application does not, or can not, sufficiently verify whether a well-formed, valid, consistent request was intentionally provided by the user who submitted the request.
extended_description: When a web server is designed to receive a request from a client without any mechanism for verifying that it was intentionally sent, then it might be possible for an attacker to trick a client into making an unintentional request to the web server which will be treated as an authentic request. This can be done via a URL, image load, XMLHttpRequest, etc. and can result in exposure of data or unintended code execution.
         

Fix information:
repo_url: https://github.com/snipe/snipe-it
commit_details: repo_url: https://github.com/snipe/snipe-it
author: snipe
author_date: 2023-10-09 16:13:41+01:00
msg: Set resend acceptance to POST

Signed-off-by: snipe <snipe@snipe.net>
repository: repo_url: https://github.com/snipe/snipe-it
repo_name: snipe/snipe-it
description: A free open source IT asset/license management system
repo_language: PHP
owner: snipe
file_changes: filename: ReportsController.php
change_type: ModificationType.MODIFY
diff: @@ -1043,27 +1043,37 @@ class ReportsController extends Controller
      * @throws \Illuminate\Auth\Access\AuthorizationException
      * @version v1.0
      */
-    public function sentAssetAcceptanceReminder($acceptanceId = null)
+    public function sentAssetAcceptanceReminder(Request $request)
     {
         $this->authorize('reports.view');
 
-        if (!$acceptance = CheckoutAcceptance::pending()->find($acceptanceId)) {
+        if (!$acceptance = CheckoutAcceptance::pending()->find($request->input('acceptance_id'))) {
+            \Log::debug('No pending acceptances');
             // Redirect to the unaccepted assets report page with error
             return redirect()->route('reports/unaccepted_assets')->with('error', trans('general.bad_data'));
         }
+
         $assetItem = $acceptance->checkoutable;
 
+        \Log::debug(print_r($assetItem, true));
+
         if (is_null($acceptance->created_at)){
+            \Log::debug('No acceptance created_at');
             return redirect()->route('reports/unaccepted_assets')->with('error', trans('general.bad_data'));
         } else {
             $logItem_res = $assetItem->checkouts()->where('created_at', '=', $acceptance->created_at)->get();
+
+            \Log::debug('Acceptance created at: '.$acceptance->created_at);
+            \Log::debug(print_r($logItem_res, true));
+
             if ($logItem_res->isEmpty()){
+                \Log::debug('Acceptance date mismatch');
                 return redirect()->route('reports/unaccepted_assets')->with('error', trans('general.bad_data'));
             }
             $logItem = $logItem_res[0];
         }
 
-        if(!$assetItem->assignedTo->locale){
+        if (!$assetItem->assignedTo->locale){
             Notification::locale(Setting::getSettings()->locale)->send(
                 $assetItem->assignedTo,
                 new CheckoutAssetNotification($assetItem, $assetItem->assignedTo, $logItem->user, $acceptance, $logItem->note)

programming_language: PHP
filename: unaccepted_assets.blade.php
change_type: ModificationType.MODIFY
diff: @@ -77,11 +77,23 @@
                     <td>{!! $item['assetItem']->present()->nameUrl() !!}</td>
                     <td>{{ $item['assetItem']->asset_tag }}</td>
                     <td @if($item['acceptance']->assignedTo === null || $item['acceptance']->assignedTo->trashed()) style="text-decoration: line-through" @endif>{!! ($item['acceptance']->assignedTo) ? $item['acceptance']->assignedTo->present()->nameUrl() : trans('admin/reports/general.deleted_user') !!}</td>
-                    <td>
+                    <td class="white-space: nowrap;">
+                        <nobr>
                         @if(!$item['acceptance']->trashed())
-                            @if ($item['acceptance']->assignedTo)<a href="{{ route('reports/unaccepted_assets_sent_reminder', ['acceptanceId' => $item['acceptance']->id]) }}" class="btn btn-sm bg-purple" data-tooltip="true">{{ trans('admin/reports/general.send_reminder') }}</a>@endif
+                           <form method="post" class="white-space: nowrap;" action="{{ route('reports/unaccepted_assets_sent_reminder') }}">
+                            @if ($item['acceptance']->assignedTo)
+                                @csrf
+                               <input type="hidden" name="acceptance_id" value="{{ $item['acceptance']->id }}">
+                                <button class="btn btn-sm btn-warning" data-tooltip="true" data-title="{{ trans('admin/reports/general.send_reminder') }}">
+                                    <i class="fa fa-repeat" aria-hidden="true"></i>
+                                </button>
+
+                            @endif
                             <a href="{{ route('reports/unaccepted_assets_delete', ['acceptanceId' => $item['acceptance']->id]) }}" class="btn btn-sm btn-danger delete-asset" data-tooltip="true" data-toggle="modal" data-content="{{ trans('general.delete_confirm', ['item' =>trans('admin/reports/general.acceptance_request')]) }}" data-title="{{  trans('general.delete') }}" onClick="return false;"><i class="fa fa-trash"></i></a>
+                           </form>
                         @endif
+
+                        </nobr>
                     </td>
                   </tr>
                   @endif

programming_language: PHP
filename: web.php
change_type: ModificationType.MODIFY
diff: @@ -368,8 +368,8 @@ Route::group(['middleware' => ['auth']], function () {
         'reports/unaccepted_assets/{deleted?}',
         [ReportsController::class, 'getAssetAcceptanceReport']
     )->name('reports/unaccepted_assets');
-    Route::get(
-        'reports/unaccepted_assets/{acceptanceId}/sent_reminder',
+    Route::post(
+        'reports/unaccepted_assets/sent_reminder',
         [ReportsController::class, 'sentAssetAcceptanceReminder']
     )->name('reports/unaccepted_assets_sent_reminder');
     Route::delete(

programming_language: PHP