2020-03-17 12:29:57 +03:00
|
|
|
/*
|
|
|
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
|
|
*
|
|
|
|
* This software may be used and distributed according to the terms of the
|
|
|
|
* GNU General Public License version 2.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#pragma once
|
|
|
|
|
|
|
|
#include <folly/futures/Promise.h>
|
|
|
|
#include <utility>
|
|
|
|
#include <variant>
|
|
|
|
|
|
|
|
#include "eden/fs/model/Blob.h"
|
|
|
|
#include "eden/fs/model/Hash.h"
|
|
|
|
#include "eden/fs/model/Tree.h"
|
|
|
|
#include "eden/fs/store/ImportPriority.h"
|
2020-04-09 22:11:40 +03:00
|
|
|
#include "eden/fs/telemetry/RequestMetricsScope.h"
|
2020-04-07 05:10:31 +03:00
|
|
|
#include "eden/fs/utils/Bug.h"
|
2020-03-17 12:29:57 +03:00
|
|
|
|
|
|
|
namespace facebook {
|
|
|
|
namespace eden {
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Represents an Hg import request. This class contains all the necessary
|
|
|
|
* information needed to fulfill the request as well as a promise that will be
|
|
|
|
* resolved after the requested data is imported.
|
|
|
|
*/
|
|
|
|
class HgImportRequest {
|
|
|
|
public:
|
2020-04-07 05:10:31 +03:00
|
|
|
struct BlobImport {
|
|
|
|
using Response = std::unique_ptr<Blob>;
|
|
|
|
|
|
|
|
Hash hash;
|
|
|
|
};
|
|
|
|
|
|
|
|
struct TreeImport {
|
|
|
|
using Response = std::unique_ptr<Tree>;
|
|
|
|
|
|
|
|
Hash hash;
|
2020-03-17 12:29:57 +03:00
|
|
|
};
|
|
|
|
|
2020-04-07 05:10:31 +03:00
|
|
|
struct Prefetch {
|
|
|
|
using Response = folly::Unit;
|
|
|
|
|
|
|
|
std::vector<Hash> hashes;
|
|
|
|
};
|
|
|
|
|
2020-04-09 22:11:40 +03:00
|
|
|
HgImportRequest(HgImportRequest&&) = default;
|
|
|
|
HgImportRequest& operator=(HgImportRequest&&) = default;
|
|
|
|
|
|
|
|
HgImportRequest(const HgImportRequest&) = delete;
|
|
|
|
HgImportRequest& operator=(const HgImportRequest&) = delete;
|
|
|
|
|
2020-03-17 12:29:57 +03:00
|
|
|
static std::pair<HgImportRequest, folly::SemiFuture<std::unique_ptr<Blob>>>
|
2020-04-09 22:11:40 +03:00
|
|
|
makeBlobImportRequest(
|
|
|
|
Hash hash,
|
|
|
|
ImportPriority priority,
|
|
|
|
std::unique_ptr<RequestMetricsScope> metricsScope);
|
2020-03-17 12:29:57 +03:00
|
|
|
|
|
|
|
static std::pair<HgImportRequest, folly::SemiFuture<std::unique_ptr<Tree>>>
|
2020-04-09 22:11:40 +03:00
|
|
|
makeTreeImportRequest(
|
|
|
|
Hash hash,
|
|
|
|
ImportPriority priority,
|
|
|
|
std::unique_ptr<RequestMetricsScope> metricsScope);
|
2020-03-17 12:29:57 +03:00
|
|
|
|
2020-04-07 05:10:31 +03:00
|
|
|
static std::pair<HgImportRequest, folly::SemiFuture<folly::Unit>>
|
2020-04-09 22:11:40 +03:00
|
|
|
makePrefetchRequest(
|
|
|
|
std::vector<Hash> hashes,
|
|
|
|
ImportPriority priority,
|
|
|
|
std::unique_ptr<RequestMetricsScope> metricsScope);
|
2020-04-07 05:10:31 +03:00
|
|
|
|
|
|
|
template <typename RequestType>
|
|
|
|
HgImportRequest(
|
|
|
|
RequestType request,
|
|
|
|
ImportPriority priority,
|
2020-05-06 06:55:16 +03:00
|
|
|
folly::Promise<typename RequestType::Response>&& promise)
|
2020-04-07 05:10:31 +03:00
|
|
|
: request_(std::move(request)),
|
|
|
|
priority_(priority),
|
2020-05-06 06:55:16 +03:00
|
|
|
promise_(std::move(promise)) {}
|
2020-04-07 05:10:31 +03:00
|
|
|
|
2020-04-07 05:10:31 +03:00
|
|
|
template <typename T>
|
|
|
|
const T* getRequest() noexcept {
|
|
|
|
return std::get_if<T>(&request_);
|
2020-03-17 12:29:57 +03:00
|
|
|
}
|
|
|
|
|
2020-05-06 06:55:16 +03:00
|
|
|
template <typename T>
|
|
|
|
bool isType() const noexcept {
|
|
|
|
return std::holds_alternative<T>(request_);
|
|
|
|
}
|
|
|
|
|
2020-05-06 06:55:16 +03:00
|
|
|
size_t getType() const noexcept {
|
|
|
|
return request_.index();
|
|
|
|
}
|
|
|
|
|
2020-03-17 12:29:57 +03:00
|
|
|
/**
|
2020-05-06 06:55:16 +03:00
|
|
|
* Set the inner Promise with the result of the function.
|
2020-03-17 12:29:57 +03:00
|
|
|
*/
|
2020-05-06 06:55:16 +03:00
|
|
|
template <typename T, typename Func>
|
|
|
|
void setWith(Func func) {
|
|
|
|
auto promise = std::get_if<folly::Promise<typename T::Response>>(&promise_);
|
2020-04-07 05:10:31 +03:00
|
|
|
|
|
|
|
if (!promise) {
|
|
|
|
EDEN_BUG() << "invalid promise type";
|
|
|
|
}
|
2020-03-17 12:29:57 +03:00
|
|
|
|
2020-05-06 06:55:16 +03:00
|
|
|
promise->setWith([func = std::move(func)]() { return func(); });
|
2020-03-17 12:29:57 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
private:
|
2020-04-07 05:10:31 +03:00
|
|
|
using Request = std::variant<BlobImport, TreeImport, Prefetch>;
|
2020-04-07 05:10:31 +03:00
|
|
|
using Response = std::variant<
|
|
|
|
folly::Promise<std::unique_ptr<Blob>>,
|
2020-04-07 05:10:31 +03:00
|
|
|
folly::Promise<std::unique_ptr<Tree>>,
|
|
|
|
folly::Promise<folly::Unit>>;
|
2020-03-17 12:29:57 +03:00
|
|
|
|
2020-04-07 05:10:31 +03:00
|
|
|
Request request_;
|
2020-03-17 12:29:57 +03:00
|
|
|
ImportPriority priority_;
|
2020-04-07 05:10:31 +03:00
|
|
|
Response promise_;
|
2020-03-17 12:29:57 +03:00
|
|
|
|
|
|
|
friend bool operator<(
|
|
|
|
const HgImportRequest& lhs,
|
|
|
|
const HgImportRequest& rhs) {
|
|
|
|
return lhs.priority_ < rhs.priority_;
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
} // namespace eden
|
|
|
|
} // namespace facebook
|