File: cloud_upload_notification_manager.h

package info (click to toggle)
chromium 138.0.7204.183-1~deb12u1
  • links: PTS, VCS
  • area: main
  • in suites: bookworm-proposed-updates
  • size: 6,080,960 kB
  • sloc: cpp: 34,937,079; ansic: 7,176,967; javascript: 4,110,704; python: 1,419,954; asm: 946,768; xml: 739,971; pascal: 187,324; sh: 89,623; perl: 88,663; objc: 79,944; sql: 50,304; cs: 41,786; fortran: 24,137; makefile: 21,811; php: 13,980; tcl: 13,166; yacc: 8,925; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (155 lines) | stat: -rw-r--r-- 6,356 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
// Copyright 2022 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef CHROME_BROWSER_UI_WEBUI_ASH_CLOUD_UPLOAD_CLOUD_UPLOAD_NOTIFICATION_MANAGER_H_
#define CHROME_BROWSER_UI_WEBUI_ASH_CLOUD_UPLOAD_CLOUD_UPLOAD_NOTIFICATION_MANAGER_H_

#include "base/files/file_path.h"
#include "base/functional/bind.h"
#include "base/functional/callback_forward.h"
#include "base/memory/raw_ptr.h"
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "base/timer/timer.h"
#include "chrome/browser/ash/file_manager/io_task.h"
#include "chrome/browser/notifications/notification_display_service.h"
#include "chrome/browser/ui/webui/ash/cloud_upload/cloud_upload_util.h"
#include "ui/message_center/public/cpp/notification.h"

class Profile;

namespace ash::cloud_upload {

// Creates, updates and deletes cloud upload system notifications. Ensures that
// notifications stay in the "in progress" state for a minimum of 5 seconds, and
// a minimum of 5 seconds for the 'complete' state unless the user chooses to
// click the "Show in folder" button which would close the notification early.
// For the error state, notifications stay open until the user closes them.
class CloudUploadNotificationManager
    : public base::RefCounted<CloudUploadNotificationManager> {
 public:
  using HandleCompleteNotificationClickCallback =
      base::OnceCallback<void(base::FilePath)>;

  CloudUploadNotificationManager(Profile* profile,
                                 const std::string& cloud_provider_name,
                                 const std::string& target_app_name,
                                 int num_files,
                                 UploadType upload_type);

  // Creates the notification with "in progress" state if it doesn't exist, or
  // updates the progress bar if it does. |progress| is within the 0-100 range.
  // The notification will stay in the "in progress" state for a minimum of 5
  // seconds, even at 100% progress.
  void ShowUploadProgress(int progress);

  // Shows the upload complete notification for 5 seconds, but only once the
  // minimum 5 seconds from the "in progress" state has finished.
  void MarkUploadComplete();

  // Shows the error state for the notification indefinitely, until closed by
  // the user. Does not wait for the progress notification to show for a minimum
  // time.
  void ShowUploadError(const std::string& message);

  // Closes any existing notification, interrupts ongoing timers, and calls the
  // completion callback, destroying this instance. This is called internally
  // after the notification has completed and timed out, or when the error
  // notification is clicked. It only needs to be called publicly in tests to
  // avoid leaking instances of this class, or when no notification was ever
  // started.
  void CloseNotification();

  void SetDestinationPath(base::FilePath destination_path) {
    destination_path_ = destination_path;
  }

  void SetCancelCallback(base::OnceClosure cancel_callback) {
    cancel_callback_ = std::move(cancel_callback);
  }

  // Used in tests to set a callback to check if
  // |HandleCompleteNotificationClick| is called with the expected
  // |destination_path_|.
  void SetHandleCompleteNotificationClickCallbackForTesting(
      HandleCompleteNotificationClickCallback callback) {
    callback_for_testing_ = std::move(callback);
  }

 private:
  friend base::RefCounted<CloudUploadNotificationManager>;
  ~CloudUploadNotificationManager();

  // Returns the message center display service that manages notifications.
  NotificationDisplayService* GetNotificationDisplayService();

  // Returns an instance of an 'ash' upload progress notification.
  std::unique_ptr<message_center::Notification>
  CreateUploadProgressNotification();

  // Returns an instance of an 'ash' upload complete notification.
  std::unique_ptr<message_center::Notification>
  CreateUploadCompleteNotification();

  // Returns an instance of an 'ash' upload error notification.
  std::unique_ptr<message_center::Notification> CreateUploadErrorNotification(
      std::string message);

  // Called when the minimum amount of time to display the "in progress"
  // notification is reached.
  void OnMinInProgressTimeReached();

  // Updates the notification immediately to show the complete state.
  void ShowCompleteNotification();

  // "Cancel" click handler for upload progress notification.
  void HandleProgressNotificationClick(std::optional<int> button_index);

  // "Sign in" click handler for authentication error notification.
  void HandleErrorNotificationClick(std::optional<int> button_index);

  // "Show in folder" click handler for upload complete notification.
  void HandleCompleteNotificationClick(std::optional<int> button_index);

  // A state machine and the possible transitions. The state of showing the
  // error notification is not explicit because it is never used to determine
  // later logic.
  enum class State {
    kUninitialized,  // --> kInProgress, kComplete
    kInProgress,     // --> kInProgressTimedOut, kWaitingForInProgressTimeout,
                     // (error)
    kInProgressTimedOut,           // --> kComplete, (error)
    kWaitingForInProgressTimeout,  // --> kComplete
    kComplete
  };

  // Returns true if upload is still in progress.
  bool CanCancel();

  // Counts the total number of notification manager instances. This counter is
  // never decremented.
  static inline int notification_manager_counter_ = 0;

  const raw_ptr<Profile, LeakedDanglingUntriaged> profile_;
  CloudProvider provider_;
  std::string cloud_provider_name_;
  std::string notification_id_;
  std::string target_app_name_;
  std::u16string display_source_;
  int num_files_;
  int progress_;
  UploadType upload_type_;
  base::FilePath destination_path_;
  base::OnceClosure callback_;
  base::OnceClosure cancel_callback_;
  HandleCompleteNotificationClickCallback callback_for_testing_;
  base::OneShotTimer in_progress_timer_;
  base::OneShotTimer complete_notification_timer_;
  State state_ = State::kUninitialized;
  base::WeakPtrFactory<CloudUploadNotificationManager> weak_ptr_factory_{this};
};

}  // namespace ash::cloud_upload

#endif  // CHROME_BROWSER_UI_WEBUI_ASH_CLOUD_UPLOAD_CLOUD_UPLOAD_NOTIFICATION_MANAGER_H_