blob: 76c71b471557bb9eee787bc60894060424ad92f6 [file] [log] [blame]
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/enterprise/connectors/service_providers.h"
#include <memory>
#include <string>
#include <vector>
#include "base/bind.h"
#include "base/callback.h"
#include "base/files/file_path.h"
#include "base/files/file_util.h"
#include "base/json/json_reader.h"
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "base/optional.h"
#include "base/task/task_traits.h"
#include "base/task/thread_pool.h"
#include "base/values.h"
#include "components/component_updater/component_installer.h"
#include "components/component_updater/component_updater_service.h"
#include "components/update_client/update_client.h"
namespace {
const base::FilePath::CharType kConfigFileName[] =
FILE_PATH_LITERAL("service_providers.json");
// The SHA256 of the SubjectPublicKeyInfo used to sign the extension.
// The extension id is: dfcoifdifjfolmglbbogapfcihdgckga
// SHA256: 352e8538595ebc6b11e60f5287362a60a4c4f0c2fb3595c43621942ffbd973b5
const uint8_t kPublicKeySHA256[32] = {
0x35, 0x2e, 0x85, 0x38, 0x59, 0x5e, 0xbc, 0x6b, 0x11, 0xe6, 0x0f,
0x52, 0x87, 0x36, 0x2a, 0x60, 0xa4, 0xc4, 0xf0, 0xc2, 0xfb, 0x35,
0x95, 0xc4, 0x36, 0x21, 0x94, 0x2f, 0xfb, 0xd9, 0x73, 0xb5};
base::Optional<base::Value> LoadConfigFromDisk(const base::FilePath& path) {
// TODO(crbug/1081375): replace this with a safe read function.
std::string json;
if (!base::ReadFileToString(path, &json)) {
return base::nullopt;
}
return base::JSONReader::Read(json);
}
} // namespace
namespace enterprise_connectors {
class ServiceProvidersConfigPolicy
: public component_updater::ComponentInstallerPolicy {
public:
ServiceProvidersConfigPolicy();
~ServiceProvidersConfigPolicy() override;
const base::Value& GetServiceProvidersConfig() const { return config_; }
private:
void SetConfig(base::Optional<base::Value> config);
// component_updater::ComponentInstallerPolicy overrides:
bool VerifyInstallation(const base::DictionaryValue& manifest,
const base::FilePath& install_dir) const override;
bool SupportsGroupPolicyEnabledComponentUpdates() const override;
bool RequiresNetworkEncryption() const override;
update_client::CrxInstaller::Result OnCustomInstall(
const base::DictionaryValue& manifest,
const base::FilePath& install_dir) override;
void OnCustomUninstall() override;
void ComponentReady(const base::Version& version,
const base::FilePath& install_dir,
std::unique_ptr<base::DictionaryValue> manifest) override;
base::FilePath GetRelativeInstallDir() const override;
void GetHash(std::vector<uint8_t>* hash) const override;
std::string GetName() const override;
std::vector<std::string> GetMimeTypes() const override;
update_client::InstallerAttributes GetInstallerAttributes() const override;
base::Value config_;
base::WeakPtrFactory<ServiceProvidersConfigPolicy> factory_{this};
};
ServiceProvidersConfigPolicy::ServiceProvidersConfigPolicy() = default;
ServiceProvidersConfigPolicy::~ServiceProvidersConfigPolicy() = default;
void ServiceProvidersConfigPolicy::SetConfig(
base::Optional<base::Value> config) {
if (!config.has_value())
return;
config_ = std::move(config.value());
}
bool ServiceProvidersConfigPolicy::VerifyInstallation(
const base::DictionaryValue& manifest,
const base::FilePath& install_dir) const {
const base::FilePath config_file = install_dir.Append(kConfigFileName);
return base::PathExists(config_file);
}
bool ServiceProvidersConfigPolicy::SupportsGroupPolicyEnabledComponentUpdates()
const {
return false;
}
bool ServiceProvidersConfigPolicy::RequiresNetworkEncryption() const {
return false;
}
update_client::CrxInstaller::Result
ServiceProvidersConfigPolicy::OnCustomInstall(
const base::DictionaryValue& manifest,
const base::FilePath& install_dir) {
return update_client::CrxInstaller::Result(0); // Nothing custom here.
}
void ServiceProvidersConfigPolicy::OnCustomUninstall() {}
void ServiceProvidersConfigPolicy::ComponentReady(
const base::Version& version,
const base::FilePath& install_dir,
std::unique_ptr<base::DictionaryValue> manifest) {
const base::FilePath config_file = install_dir.Append(kConfigFileName);
base::ThreadPool::PostTaskAndReplyWithResult(
FROM_HERE, {base::MayBlock(), base::TaskPriority::BEST_EFFORT},
base::BindOnce(&LoadConfigFromDisk, config_file),
base::BindOnce(&ServiceProvidersConfigPolicy::SetConfig,
factory_.GetWeakPtr()));
}
base::FilePath ServiceProvidersConfigPolicy::GetRelativeInstallDir() const {
return base::FilePath(FILE_PATH_LITERAL("ECSerivceProvidersConfig"));
}
void ServiceProvidersConfigPolicy::GetHash(std::vector<uint8_t>* hash) const {
hash->assign(kPublicKeySHA256,
kPublicKeySHA256 + base::size(kPublicKeySHA256));
}
std::string ServiceProvidersConfigPolicy::GetName() const {
return "Enterprise Connectors Service Providers Configuration";
}
std::vector<std::string> ServiceProvidersConfigPolicy::GetMimeTypes() const {
return std::vector<std::string>();
}
update_client::InstallerAttributes
ServiceProvidersConfigPolicy::GetInstallerAttributes() const {
return update_client::InstallerAttributes();
}
void RegisterServiceProvidersComponent(
component_updater::ComponentUpdateService* cus) {
auto installer = base::MakeRefCounted<component_updater::ComponentInstaller>(
std::make_unique<ServiceProvidersConfigPolicy>());
installer->Register(cus, base::OnceClosure());
}
} // namespace enterprise_connectors