Пример #1
0
def get_wall_execute(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 10,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
    progress=None,
) -> pandas.DataFrame:
    """
    Возвращает список записей со стены пользователя или сообщества.

    @see: https://vk.com/dev/wall.get

    :param owner_id: Идентификатор пользователя или сообщества, со стены которого необходимо получить записи.
    :param domain: Короткий адрес пользователя или сообщества.
    :param offset: Смещение, необходимое для выборки определенного подмножества записей.
    :param count: Количество записей, которое необходимо получить (0 - все записи).
    :param max_count: Максимальное число записей, которое может быть получено за один запрос.
    :param filter: Определяет, какие типы записей на стене необходимо получить.
    :param extended: 1 — в ответе будут возвращены дополнительные поля profiles и groups, содержащие информацию о пользователях и сообществах.
    :param fields: Список дополнительных полей для профилей и сообществ, которые необходимо вернуть.
    :param progress: Callback для отображения прогресса.
    """
    outdated = pandas.DataFrame()
    code = f"""
            return API.wall.get ({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": "0",
            "count": "1",
            "filter": "{filter}",
            "extended": "0",
            "fields": ""
}});
"""
    data = {"code": code}
    response = session.post("execute", data=data).json()
    if "error" in response:
        raise APIError(response["error"]["error_msg"])
    if not progress:
        progress = lambda x: x
    for _ in progress(
            range(
                0,
                math.ceil(
                    (response["response"]["count"] if count == 0 else count) /
                    max_count))):
        outdated = outdated.append(
            pandas.json_normalize(
                get_posts_2500(owner_id, domain, offset, count, max_count,
                               filter, extended, fields)))
        time.sleep(1)
    return outdated
Пример #2
0
def get_posts_2500(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 10,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
) -> tp.Dict[str, tp.Any]:
    # fmt: off
    script = f"""
    var i = 0; 
    var result = [];
    while (i < {max_count}){{
        if ({offset}+i+100 > {count}){{
            result.push(API.wall.get({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": "{offset} +i",
            "count": "{count}-(i+{offset})",
            "filter": "{filter}",
            "extended": "{extended}",
            "fields": "{fields}"
        }}));
    }} 
    result.push(API.wall.get({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": "{offset} +i",
            "count": "{count}",
            "filter": "{filter}",
            "extended": "{extended}",
            "fields": "{fields}"
        }}));
        i = i + {max_count};
    }}
    return result;
    """
    # fmt: on
    data = {
        "code": script,
        "access_token": config.VK_CONFIG["access_token"],
        "v": config.VK_CONFIG["version"],
    }
    response = session.post("execute", data=data)
    doc = response.json()
    if "error" in doc or not response.ok:
        raise APIError(doc["error"]["error_msg"])
    return doc["response"]["items"]
Пример #3
0
def get_posts_2500(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 10,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
) -> tp.Dict[str, tp.Any]:
    code = f"""var i = 0;
    var offset = {offset};
    var response = [];
    while(i < 25) {{
        i = i + 1;
        offset = offset + 100;
        response.push(API.wall.get({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": offset,
            "count": "{count}",
            "filter": "{filter}",
            "extended": "{extended}",
            "fields": "{fields}"
        }}));
    }}
    return response"""
    response = session.post(
        "execute",
        data={
            "code": code,
            "access_token": config.VK_CONFIG["access_token"],
            "v": config.VK_CONFIG["version"],
        },
    )
    doc = response.json()
    if not response.ok or "error" in doc:
        raise APIError(doc["error"]["error_msg"])
    return doc["response"]["items"]
Пример #4
0
def get_wall_execute(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 100,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
    progress=tqdm,
) -> pd.DataFrame:
    """
    Возвращает список записей со стены пользователя или сообщества.

    @see: https://vk.com/dev/wall.get

    :param owner_id: Идентификатор пользователя или сообщества, со стены которого необходимо получить записи.
    :param domain: Короткий адрес пользователя или сообщества.
    :param offset: Смещение, необходимое для выборки определенного подмножества записей.
    :param count: Количество записей, которое необходимо получить (0 - все записи).
    :param max_count: Максимальное число записей, которое может быть получено за один запрос.
    :param filter: Определяет, какие типы записей на стене необходимо получить.
    :param extended: 1 — в ответе будут возвращены дополнительные поля profiles и groups, содержащие информацию о пользователях и сообществах.
    :param fields: Список дополнительных полей для профилей и сообществ, которые необходимо вернуть.
    :param progress: Callback для отображения прогресса.
    """

    params_: Params = {
        "owner_id": owner_id,
        "domain": domain,
        "offset": offset,
        "count": count,
        "filter": filter,
        "extended": extended,
        "fields": ",".join(fields) if fields else "",
        "max_count": max_count,
    }

    code = ("""
        var calls = 0,
            items = [],
            records = 0,
            params = """ + str(params_) + """,
        response = {"count":"1"};

    if (params.count == 0){
        params.count = 100;
        response = API.wall.get(params);
        records = response.count;
        items = items + response.items;
        calls = calls + 1;
    }else{
        records = params.count;
        if (params.count >= 100){
            params.count = 100;
        }        
    }
    var max_calls = """ + str(max_count) + """ / 100; 
    while(calls < max_calls && records > params.offset) {

        calls = calls + 1;  

        response = API.wall.get(params);
        items = items + response.items;
        params.offset = params.offset + params.count;
    };
    return {
        count: records,
        items: items
     };""")

    params = {
        "code": code,
        "access_token": config.VK_CONFIG["access_token"],
        "v": "5.126",
        "count": 0,
    }

    class Response(tp.TypedDict):
        items: list
        count: int

    res: Response = {"items": [], "count": 1}

    with progress(total=res["count"]) as pbar:
        while len(res["items"]) < res["count"]:
            j = session.post(url="execute", data=params).json()

            time.sleep(1)

            try:
                if j["response"]["items"]:
                    res["items"] += j["response"]["items"]
                else:
                    res["items"] += [
                        i for i in
                        range(2500 if res["count"] -
                              len(res["items"]) > 2500 else res["count"] -
                              len(res["items"]))
                    ]
                res["count"] = j["response"]["count"]
            except KeyError:
                raise APIError(j["error"])

            params["count"] = int(res["count"])
            pbar.total = res["count"]
            pbar.update(len(res["items"]) - params_["offset"])
            params_["offset"] = len(res["items"])

    return pd.DataFrame(res["items"])
Пример #5
0
def get_wall_execute(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 10,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
    progress=None,
) -> pd.DataFrame:
    """
    Возвращает список записей со стены пользователя или сообщества.

    @see: https://vk.com/dev/wall.get

    :param owner_id: Идентификатор пользователя или сообщества, со стены которого необходимо получить записи.
    :param domain: Короткий адрес пользователя или сообщества.
    :param offset: Смещение, необходимое для выборки определенного подмножества записей.
    :param count: Количество записей, которое необходимо получить (0 - все записи).
    :param max_count: Максимальное число записей, которое может быть получено за один запрос.
    :param filter: Определяет, какие типы записей на стене необходимо получить.
    :param extended: 1 — в ответе будут возвращены дополнительные поля profiles и groups, содержащие информацию о пользователях и сообществах.
    :param fields: Список дополнительных полей для профилей и сообществ, которые необходимо вернуть.
    :param progress: Callback для отображения прогресса.
    """
    response = session.post(
        url="execute",
        data={
            "code": f"""
            return API.wall.get({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": {offset},
            "count": "1",
            "filter": "{filter}",
            "extended": {extended},
            "v": {config.VK_CONFIG["version"]}
            }});
            """,
            "access_token": config.VK_CONFIG["access_token"],
            "v": config.VK_CONFIG["version"],
        },
    ).json()
    if "error" in response:
        raise APIError
    posts = response["response"]
    if response["response"]["count"] - offset > count and count != 0:
        max_count = count
    else:
        max_count = response["response"]["count"] - offset
    if max_count == 0:
        return json_normalize(posts["items"])
    window = range(0, max_count, 100)
    if progress:
        window = progress(window)
    num_records = max_count - len(posts)
    for i in window:
        try:
            posts2500 = get_posts_2500(
                owner_id=owner_id,
                domain=domain,
                offset=offset + len(posts),
                max_count=num_records,
                filter=filter,
                extended=extended,
                fields=fields,
            )
            posts.update(posts2500)
            if not (max_count - len(posts)) > num_records:
                num_records = max_count - len(posts)
        except:
            raise APIError
        time.sleep(0.34)

    return json_normalize(posts["items"])
Пример #6
0
def get_posts_2500(
    owner_id: str = "",
    domain: str = "",
    offset: int = 0,
    count: int = 10,
    max_count: int = 2500,
    filter: str = "owner",
    extended: int = 0,
    fields: tp.Optional[tp.List[str]] = None,
) -> tp.Dict[str, tp.Any]:

    if fields:
        code_fields = "?".join(fields)
    else:
        code_fields = ""
    if max_count <= 100:
        code = f"""
        return API.wall.get({{
            "owner_id": "{owner_id}",
            "domain": "{domain}",
            "offset": {offset},
            "count": {max_count},
            "filter": "{filter}",
            "extended": {extended},
            "fields": "{code_fields}",
            "v": {config.VK_CONFIG["version"]}
        }}).items;
        """
    else:
        if max_count > 2500:
            max_count = 2500
        code = f"""
        var wall_records = [];
        var offset = 100 + {offset};
        var count = {count};
        var max_offset = offset + {max_count};
        while (offset < max_offset && wall_records.length <= offset && offset-{offset} < {max_count}) {{
            if ({max_count} - wall_records.length < 100) {{
                count = {max_count} - wall_records.length;
            }};
            wall_records = wall_records + API.wall.get({{
                "owner_id": "{owner_id}",
                "domain": "{domain}",
                "offset": offset,
                "count": count,
                "filter": "{filter}",
                "extended": {extended},
                "fields": "{code_fields}",
                "v": {config.VK_CONFIG["version"]}
            }}).items;
            offset = offset + 100;
        }};
        return wall_records;
        """

    response = session.post(
        url="execute",
        data={
            "code": code,
            "access_token": config.VK_CONFIG["access_token"],
            "v": config.VK_CONFIG["version"],
        },
    ).json()
    if "response" in response:
        return response["response"]
    raise APIError