blob: fa577808f10db64a53911f6995c426e699a64dc3 [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 <map>
#include <string>
#include <vector>
#include "cast/common/public/service_info.h"
#include "cast/sender/cast_app_availability_tracker.h"
#include "cast/sender/cast_platform_client.h"
#include "cast/sender/public/cast_app_discovery_service.h"
#include "platform/api/time.h"
#include "util/weak_ptr.h"
namespace openscreen {
namespace cast {
// Keeps track of availability queries, receives receiver updates, and issues
// app availability requests based on these signals.
class CastAppDiscoveryServiceImpl : public CastAppDiscoveryService {
// |platform_client| must outlive |this|.
CastAppDiscoveryServiceImpl(CastPlatformClient* platform_client,
ClockNowFunctionPtr clock);
~CastAppDiscoveryServiceImpl() override;
// CastAppDiscoveryService implementation.
Subscription StartObservingAvailability(
const CastMediaSource& source,
AvailabilityCallback callback) override;
// Reissues app availability requests for currently registered (device_id,
// app_id) pairs whose status is kUnavailable or kUnknown.
void Refresh() override;
void AddOrUpdateReceiver(const ServiceInfo& receiver);
void RemoveReceiver(const ServiceInfo& receiver);
struct AvailabilityCallbackEntry {
uint32_t id;
AvailabilityCallback callback;
// Issues an app availability request for |app_id| to the receiver given by
// |device_id|.
void RequestAppAvailability(const std::string& device_id,
const std::string& app_id);
// Updates the availability result for |device_id| and |app_id| with |result|,
// and notifies callbacks with updated availability query results.
void UpdateAppAvailability(const std::string& device_id,
const std::string& app_id,
AppAvailabilityResult result);
// Updates the availability query results for |sources|.
void UpdateAvailabilityQueries(const std::vector<CastMediaSource>& sources);
std::vector<ServiceInfo> GetReceiversByIds(
const std::vector<std::string>& device_ids) const;
// Returns true if an app availability request should be issued for
// |device_id| and |app_id|. |now| is used for checking whether previously
// cached results should be refreshed.
bool ShouldRefreshAppAvailability(const std::string& device_id,
const std::string& app_id,
Clock::time_point now) const;
void RemoveAvailabilityCallback(uint32_t id) override;
std::map<std::string, ServiceInfo> receivers_by_id_;
// Registered availability queries and their associated callbacks keyed by
// media source IDs.
std::map<std::string, std::vector<AvailabilityCallbackEntry>> avail_queries_;
// Callback ID tracking.
uint32_t next_avail_query_id_ = 1U;
CastPlatformClient* const platform_client_;
CastAppAvailabilityTracker availability_tracker_;
const ClockNowFunctionPtr clock_;
WeakPtrFactory<CastAppDiscoveryServiceImpl> weak_factory_;
} // namespace cast
} // namespace openscreen