// Copyright 2018 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef SMBPROVIDER_METADATA_CACHE_H_
#define SMBPROVIDER_METADATA_CACHE_H_

#include <string>
#include <unordered_map>

#include <base/macros.h>
#include <base/time/time.h>

#include "smbprovider/proto.h"

namespace base {
class TickClock;
}

namespace smbprovider {

// Maintains a cache of file and directory metadata. This is the data
// that is returned by stat(); name, entry type, size, date modified.
//
// The libsmbclient API can return all metadata while enumerating a
// directory, but the Chrome FileSystemProvider API makes per entry
// requests for metadata. This cache will store the results found
// when reading a directory, then use the cache to attempt to satisfy
// requests for metadata.
class MetadataCache {
 public:
  enum class Mode {
    kStandard,  // Standard Cache behavior.
    kDisabled   // All lookups are cache misses.
  };

  // |entry_lifetime| determines how long an entry remains valid in the cache.
  MetadataCache(base::TickClock* tick_clock,
                base::TimeDelta entry_lifetime,
                Mode mode);
  MetadataCache(const MetadataCache&) = delete;
  MetadataCache& operator=(const MetadataCache&) = delete;

  ~MetadataCache();

  MetadataCache& operator=(MetadataCache&& other) = default;

  // Adds an entry to the cache.
  void AddEntry(const DirectoryEntry& entry);

  // Finds an entry at |full_path|. If found, returns true and out_entry
  // is set. |full_path| is a full smb url. If an entry is found but it
  // is expired, it is removed from the cache.
  bool FindEntry(const std::string& full_path, DirectoryEntry* out_entry);

  // Deletes all entries from the cache.
  void ClearAll();

  // Returns true if the cache is empty.
  bool IsEmpty() const;

  // Removes the entry at |entry_path| from the cache. |entry_cache| is a
  // full smb url.
  bool RemoveEntry(const std::string& entry_path);

  // Removes all entries in the cache that have expired.
  void PurgeExpiredEntries();

 private:
  struct CacheEntry {
    CacheEntry() = default;
    CacheEntry(const DirectoryEntry& entry, base::TimeTicks expiration_time)
        : entry(entry), expiration_time(expiration_time) {}
    CacheEntry(const CacheEntry&) = delete;
    CacheEntry& operator=(const CacheEntry&) = delete;

    CacheEntry& operator=(CacheEntry&& other) = default;

    DirectoryEntry entry;
    base::TimeTicks expiration_time;

  };

  // Returns true if the expiration time of this entry has passed.
  bool IsExpired(const CacheEntry& cache_entry) const;
  static bool IsExpired(const CacheEntry& cache_entry,
                        base::TimeTicks threshold);

  // Returns true if all the entries in the cache are expired.
  bool AreAllEntriesExpired() const;

  // Returns true if the cache should act as a cache.
  bool IsEnabled() const;

  std::unordered_map<std::string, CacheEntry> cache_;
  base::TickClock* tick_clock_;  // Not owned
  base::TimeDelta entry_lifetime_;
  base::TimeTicks max_expiration_time_;
  Mode mode_;
};

}  // namespace smbprovider

#endif  // SMBPROVIDER_METADATA_CACHE_H_
