def ego_network( user_id: tp.Optional[int] = None, friends: tp.Optional[tp.List[int]] = None ) -> tp.List[tp.Tuple[int, int]]: """ Построить эгоцентричный граф друзей. :param user_id: Идентификатор пользователя, для которого строится граф друзей. :param friends: Идентификаторы друзей, между которыми устанавливаются связи. """ if not friends: friends = tp.cast( tp.List[int], get_friends(user_id=tp.cast(int, user_id), fields=["nickname"]).items, ) mutual = get_mutual(source_uid=user_id, target_uids=friends) res = [] for m in mutual: m = tp.cast(MutualFriends, m) for f in m["common_friends"]: res.append((int(m["id"]), int(f))) return res
def ego_network( user_id: tp.Optional[int] = None, friends: tp.Optional[tp.List[int]] = None ) -> tp.List[tp.Tuple[int, int]]: """ Построить эгоцентричный граф друзей. :param user_id: Идентификатор пользователя, для которого строится граф друзей. :param friends: Идентификаторы друзей, между которыми устанавливаются связи. """ graph = [] if not friends: friends_fields: tp.List[tp.Dict[str, tp.Any]] = get_friends( user_id, fields=["nickname", "is_closed, deactivate"]).items # type: ignore friends = [ friend["id"] for friend in friends_fields if not (friend.get("deactivate") or friend.get("is_closed")) ] mutuals = get_mutual(user_id, target_uids=friends) for mutual in mutuals: mutual_m = tp.cast(MutualFriends, mutual) # type: ignore for common in mutual_m["common_friends"]: graph.append((mutual_m["id"], common)) return graph
def test_get_mutual_more_than100(self): responses.add( responses.GET, re.compile("https://api.vk.com/method/friends.getMutual\?.*offset=0.*"), match_querystring=True, json={"response": [{"id": 1, "common_friends": [2, 3], "common_count": 2}]}, status=200, ) responses.add( responses.GET, re.compile("https://api.vk.com/method/friends.getMutual\?.*offset=100.*"), match_querystring=True, json={"response": [{"id": 2, "common_friends": [1, 3], "common_count": 2}]}, status=200, ) responses.add( responses.GET, re.compile("https://api.vk.com/method/friends.getMutual\?.*offset=200.*"), match_querystring=True, json={"response": [{"id": 3, "common_friends": [1, 2], "common_count": 2}]}, status=200, ) mutual_friends = get_mutual(target_uids=list(range(300))) self.assertEqual( [ {"common_count": 2, "common_friends": [2, 3], "id": 1}, {"common_count": 2, "common_friends": [1, 3], "id": 2}, {"common_count": 2, "common_friends": [1, 2], "id": 3}, ], mutual_friends, )
def test_get_mutual(self): common_friends = [1, 2, 3, 4, 5] target_uid = 456 responses.add( responses.GET, re.compile(f"https://api.vk.com/method/friends.getMutual\?.*target_uid={target_uid}.*"), match_querystring=True, json={"response": common_friends}, status=200, ) responses.add( responses.GET, re.compile( f"https://api.vk.com/method/friends.getMutual\?.*target_uids={target_uid}.*" ), match_querystring=True, json={ "response": [ { "id": target_uid, "common_friends": common_friends, "common_count": len(common_friends), } ] }, status=200, ) mutual_friends = get_mutual(source_uid=123, target_uid=456) self.assertEqual(common_friends, mutual_friends)
def test_get_mutual_too_many_requests_handled_properly(self): common_friends = [{"id": 1, "common_friends": [2], "common_count": 1}] responses.add( responses.GET, "https://api.vk.com/method/friends.getMutual", json={"response": common_friends}, status=200, ) n_reqs = 4 start = time.time() mutual_friends = get_mutual(target_uids=list(range(n_reqs * 100))) end = time.time() self.assertGreaterEqual(end - start, 1.0, msg="Слишком много запросов в секунду") self.assertEqual(common_friends * n_reqs, mutual_friends)
def ego_network( user_id: tp.Optional[int] = None, friends: tp.Optional[tp.List[int]] = None ) -> tp.List[tp.Tuple[int, int]]: """ Построить эгоцентричный граф друзей. :param user_id: Идентификатор пользователя, для которого строится граф друзей. :param friends: Идентификаторы друзей, между которыми устанавливаются связи. """ network = [] if not friends: friends = get_friends(user_id).items # type: ignore mutual_friends = get_mutual(source_uid=user_id, target_uids=friends) for target in mutual_friends: for friend in target["common_friends"]: # type: ignore network.append((target["id"], friend)) # type: ignore return network
def ego_network( user_id: tp.Optional[int] = None, friends: tp.Optional[tp.List[int]] = None ) -> tp.List[tp.Tuple[int, int]]: if friends is False: fields: tp.List[tp.Dict[str, tp.Any]] = get_friends( user_id, fields=["nickname", "is_closed, deactivate"]).items friends = [ i["id"] for i in fields if not (i.get("deactivate") or i.get("is_closed")) ] mutuals = get_mutual(user_id, target_uids=friends) ego_net_graph = [] for mut in mutuals: mut = tp.cast(MutualFriends, mut) for common in mut["common_friends"]: ego_net_graph.append((mut["id"], common)) return ego_net_graph