def test_basic( builder: Callable[[EntityKey, Optional[int]], SubscriptionData], organization: Optional[int], entity_key: EntityKey, ) -> None: codec = SubscriptionDataCodec(entity_key) data = builder(entity_key, organization) assert codec.decode(codec.encode(data)) == data
def test_encode_snql() -> None: codec = SubscriptionDataCodec() subscription = build_snql_subscription_data() payload = codec.encode(subscription) data = json.loads(payload.decode("utf-8")) assert data["project_id"] == subscription.project_id assert data["time_window"] == int(subscription.time_window.total_seconds()) assert data["resolution"] == int(subscription.resolution.total_seconds()) assert data["query"] == subscription.query
def test_encode() -> None: codec = SubscriptionDataCodec() subscription = build_legacy_subscription_data() payload = codec.encode(subscription) data = json.loads(payload.decode("utf-8")) assert data["project_id"] == subscription.project_id assert data["conditions"] == subscription.conditions assert data["aggregations"] == subscription.aggregations assert data["time_window"] == int(subscription.time_window.total_seconds()) assert data["resolution"] == int(subscription.resolution.total_seconds())
def test_decode_snql() -> None: codec = SubscriptionDataCodec() subscription = build_snql_subscription_data() data = { "type": SubscriptionType.SNQL.value, "project_id": subscription.project_id, "time_window": int(subscription.time_window.total_seconds()), "resolution": int(subscription.resolution.total_seconds()), "query": subscription.query, } payload = json.dumps(data).encode("utf-8") assert codec.decode(payload) == subscription
def test_decode() -> None: codec = SubscriptionDataCodec() subscription = build_legacy_subscription_data() data = { "project_id": subscription.project_id, "conditions": subscription.conditions, "aggregations": subscription.aggregations, "time_window": int(subscription.time_window.total_seconds()), "resolution": int(subscription.resolution.total_seconds()), } payload = json.dumps(data).encode("utf-8") assert codec.decode(payload) == subscription
def test_decode_delegate() -> None: codec = SubscriptionDataCodec() subscription = build_delegate_subscription_data() data = { "type": SubscriptionType.DELEGATE.value, "project_id": subscription.project_id, "time_window": int(subscription.time_window.total_seconds()), "resolution": int(subscription.resolution.total_seconds()), "conditions": subscription.conditions, "aggregations": subscription.aggregations, "query": subscription.query, } payload = json.dumps(data).encode("utf-8") assert codec.decode(payload) == subscription
def test_encode_snql( builder: Callable[[EntityKey, Optional[int]], SubscriptionData], organization: Optional[int], entity_key: EntityKey, ) -> None: codec = SubscriptionDataCodec(entity_key) subscription = builder(entity_key, organization) payload = codec.encode(subscription) data = json.loads(payload.decode("utf-8")) assert data["project_id"] == subscription.project_id assert data["time_window"] == subscription.time_window_sec assert data["resolution"] == subscription.resolution_sec assert data["query"] == subscription.query assert_entity_subscription_on_subscription_class(organization, subscription, entity_key)
def test_decode_snql( builder: Callable[[EntityKey, Optional[int]], SubscriptionData], organization: Optional[int], entity_key: EntityKey, ) -> None: codec = SubscriptionDataCodec(entity_key) subscription = builder(entity_key, organization) data = { "project_id": subscription.project_id, "time_window": subscription.time_window_sec, "resolution": subscription.resolution_sec, "query": subscription.query, } if organization: data.update({"organization": organization}) payload = json.dumps(data).encode("utf-8") assert codec.decode(payload) == subscription
def create_subscription(*, dataset: Dataset, timer: Timer) -> RespTuple: subscription = SubscriptionDataCodec().decode(http_request.data) identifier = SubscriptionCreator(dataset).create(subscription, timer) return ( json.dumps({"subscription_id": str(identifier)}), 202, {"Content-Type": "application/json"}, )
def create_subscription(*, dataset: Dataset, timer: Timer): subscription = SubscriptionDataCodec().decode(http_request.data) # TODO: Check for valid queries with fields that are invalid for subscriptions. For # example date fields and aggregates. identifier = SubscriptionCreator(dataset).create(subscription, timer) return ( json.dumps({"subscription_id": str(identifier)}), 202, {"Content-Type": "application/json"}, )
class RedisSubscriptionDataStore(SubscriptionDataStore): """ A Redis backed store for subscription data. Stores subscriptions using `SubscriptionDataCodec`. Each instance of the store operates on a partition of data, defined by the `key` constructor param. """ KEY_TEMPLATE = "subscriptions:{}:{}" def __init__( self, client: RedisClientType, entity: EntityKey, partition_id: PartitionId ): self.client = client self.codec = SubscriptionDataCodec(entity) self.__key = f"subscriptions:{entity.value}:{partition_id}" def create(self, key: UUID, data: SubscriptionData) -> None: """ Stores subscription data in Redis. Will overwrite any existing subscriptions with the same id. """ self.client.hset(self.__key, key.hex.encode("utf-8"), self.codec.encode(data)) def delete(self, key: UUID) -> None: """ Removes a subscription from the Redis store. """ self.client.hdel(self.__key, key.hex.encode("utf-8")) def all(self) -> Iterable[Tuple[UUID, SubscriptionData]]: """ Fetches all subscriptions from the store. :return: An iterable of `Subscriptions`. """ return [ (UUID(key.decode("utf-8")), self.codec.decode(val)) for key, val in self.client.hgetall(self.__key).items() ]
def create_subscription(*, dataset: Dataset, timer: Timer, entity: Entity) -> RespTuple: if entity not in dataset.get_all_entities(): raise InvalidSubscriptionError( "Invalid subscription dataset and entity combination" ) entity_key = ENTITY_NAME_LOOKUP[entity] subscription = SubscriptionDataCodec(entity_key).decode(http_request.data) identifier = SubscriptionCreator(dataset, entity_key).create(subscription, timer) metrics.increment("subscription_created", tags={"entity": entity_key.value}) return ( json.dumps({"subscription_id": str(identifier)}), 202, {"Content-Type": "application/json"}, )
def test_basic(builder: Callable[[], SubscriptionData]) -> None: codec = SubscriptionDataCodec() data = builder() assert codec.decode(codec.encode(data)) == data
def __init__(self, client: RedisClientType, dataset: Dataset, partition_id: PartitionId): self.client = client self.codec = SubscriptionDataCodec() self.__key = f"subscriptions:{get_dataset_name(dataset)}:{partition_id}"
def __init__( self, client: RedisClientType, entity: EntityKey, partition_id: PartitionId ): self.client = client self.codec = SubscriptionDataCodec(entity) self.__key = f"subscriptions:{entity.value}:{partition_id}"
def test_basic(self): data = self.build_subscription_data() codec = SubscriptionDataCodec() assert codec.decode(codec.encode(data)) == data