File size: 8,571 Bytes
a028061
28dbcf4
0472e0d
 
 
 
28dbcf4
 
a028061
0472e0d
9b29345
 
 
 
a028061
0472e0d
9b29345
0472e0d
 
764a151
0472e0d
 
098508e
0472e0d
 
 
764a151
098508e
764a151
0472e0d
 
 
 
 
 
972cdd8
0472e0d
 
a028061
28dbcf4
 
 
 
 
 
 
 
 
 
036dfdc
 
508f6a9
9e7bfa3
0472e0d
28dbcf4
9e7bfa3
 
28dbcf4
508f6a9
 
9e7bfa3
 
0472e0d
 
28dbcf4
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
9b29345
0472e0d
9b29345
cb5e151
0472e0d
cb5e151
0472e0d
9b29345
0472e0d
 
9b29345
0472e0d
28dbcf4
508f6a9
9e7bfa3
 
508f6a9
 
cb5e151
 
 
28dbcf4
cb5e151
 
 
9b29345
 
 
 
 
 
cb5e151
9e7bfa3
 
508f6a9
9e7bfa3
 
508f6a9
 
9e7bfa3
 
508f6a9
 
 
 
9e7bfa3
 
 
 
 
 
 
 
036dfdc
508f6a9
 
 
 
 
 
05ccaed
 
508f6a9
0472e0d
 
 
28dbcf4
 
 
 
 
0472e0d
 
 
28dbcf4
 
 
 
 
 
 
 
 
 
0472e0d
 
 
02e4f0b
9aebc33
28dbcf4
a028061
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
from datetime import datetime

import gradio as gr
from langchain.prompts import ChatPromptTemplate
from langchain_community.llms import Ollama

from func_facebook import get_page_id, get_unanswered_comments, reply_comment, \
    process_negative_comments, process_negative_comments_in_post, get_comments, has_page_replied


def log_message(message):
    timestamp = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
    print(f"[{timestamp}] {message}")


llm = Ollama(model="llama3.1")
log_message("Модель Ollama 'llama3.1' инициализирована.")

template = """
You are an assistant answering users' questions using only the links provided in the context. Your tasks:

1. **Brevity**: Respond concisely, using only relevant information from the context.
2. **Politeness**: Start your response with a greeting if appropriate, but prioritize maintaining a respectful and professional tone.
3. **Clarity**: Avoid unnecessary explanations and use simple language.
4. **Language of the response**: Detect the language of the user's comment and reply in the same language.
5. **Safety**: Do not use phrases like "according to the context" and remove any warnings.
6. **Accuracy**: Only use the links provided in the context and **always include them at the end of your response**.
7. **Stay on Topic**: If the user's input is a greeting or not directly related to the context, politely guide them back to the relevant topic without engaging in small talk.
8. **Links**: Always provide the relevant links from the context at the end of the response and **do not add any other links**.

<context>
{context}
</context>

Question: {input}

"""


def generate_response(user_query, context):
    log_message(f"Генерация ответа на запрос: {user_query}")
    prompt = ChatPromptTemplate.from_template(template)

    log_message(f"Контекст из базы данных: {context[:100]}...")
    full_prompt = prompt.format(context=context, input=user_query)

    response = llm.invoke(full_prompt)
    log_message(f"Сгенерированный ответ: {response}")
    return response


def generate_responses(user_queries, context):
    log_message(f"Генерация ответов на {len(user_queries)} запросов")
    prompt = ChatPromptTemplate.from_template(template)

    # Формируем список полных промптов для каждого запроса
    full_prompts = [prompt.format(context=context, input=query) for query in user_queries]

    # Используем llm.batch для получения ответов на все промпты
    responses = llm.batch(full_prompts)
    log_message("Ответы сгенерированы.")
    return responses


def process_single_post(post_id, token, action, user_context):
    log_message(f"Начинаем обработку поста {post_id}")
    page_id = get_page_id(token)
    full_post_id = page_id + "_" + post_id
    # Шаг 1: Скрытие негативных комментариев
    processed_comments = process_negative_comments_in_post(full_post_id, token, action)

    # Шаг 2: Получение неотвеченных комментариев
    comments = get_comments(full_post_id, token)
    unanswered_comments = []
    for comment in comments:
        comment_id = comment['id']
        if not comment.get('is_hidden', False) and not has_page_replied(comment_id, get_page_id(token), token):
            unanswered_comments.append(comment)

    log_message(f"Найдено {len(unanswered_comments)} неотвеченных комментариев.")

    # Шаг 3: Ответ на неотвеченные комментарии
    replies = []
    for comment in unanswered_comments:
        message = comment['message']
        response_message = generate_response(message, context=user_context)
        if reply_comment(comment_id=comment['id'], message=response_message, token=token):
            replies.append({
                'comment_id': comment['id'],
                'comment_message': comment['message'],
                'reply_message': response_message
            })

    return [{
        "status": "completed",
        "post_id": full_post_id,
        "hidden_or_deleted_comments": processed_comments,
        "replies": replies
    }]


def process_comments(ACCESS_TOKEN, action, user_context):
    log_message(f"Selected action: {action}")

    hidden_comments_data = process_negative_comments(ACCESS_TOKEN, action)
    log_message(f"Количество постов с скрытыми комментариями: {len(hidden_comments_data)}")

    log_message("Получение неотвеченных комментариев.")
    posts_with_unanswered_comments = get_unanswered_comments(ACCESS_TOKEN)

    page_id = get_page_id(ACCESS_TOKEN)
    if not page_id:
        log_message("Не удалось получить ID страницы.")
        return {"status": "failed", "reason": "Не удалось получить ID страницы."}

    log_message(f"ID страницы: {page_id}")

    processed_comment_ids = set()  # Отслеживание обработанных комментариев

    all_comments = []
    all_comment_ids = []
    comment_id_to_post_id = {}
    comment_id_to_message = {}

    for post_data in posts_with_unanswered_comments:
        post_id = post_data['post_id']
        # post_message = post_data['post_message']
        unanswered_comments = post_data['unanswered_comments']

        for comment in unanswered_comments:
            comment_id = comment['id']
            if comment_id in processed_comment_ids:
                log_message(f"Комментарий {comment_id} уже обработан. Пропуск.")
                continue
            processed_comment_ids.add(comment_id)

            message = comment['message']
            log_message(f"Добавление комментария для обработки: {message}")

            # Сохраняем данные комментария
            all_comments.append(message)
            all_comment_ids.append(comment_id)
            comment_id_to_post_id[comment_id] = post_id
            comment_id_to_message[comment_id] = message

    # Генерируем ответы на все комментарии батчем
    responses = generate_responses(all_comments, context=user_context)

    # Собираем результаты в список для отображения
    result_data = []

    for comment_id, response_message in zip(all_comment_ids, responses):
        log_message(f"Ответ на комментарий {comment_id}: {response_message}")
        success = reply_comment(comment_id=comment_id, message=response_message, token=ACCESS_TOKEN)
        if success:
            log_message(f"Успешно отправлен ответ на комментарий {comment_id}")
        else:
            log_message(f"Ошибка при отправке ответа на комментарий {comment_id}")

        # Добавляем информацию в результат
        result_data.append({
            'Post ID': comment_id_to_post_id[comment_id],
            'Comment ID': comment_id,
            'Comment': comment_id_to_message[comment_id],
            'Response': response_message
        })

    return result_data


with gr.Blocks() as demo:
    gr.Markdown("# Facebook Comment Filter")
    token_input = gr.Textbox(label="Access Token")
    context_input = gr.Textbox(label="Контекст")
    radio = gr.Radio(["Hide", "Delete"], info="Choose hide or delete comments", show_label=False)

    with gr.Tab("Главная страница"):
        output_main = gr.JSON()
        process_btn = gr.Button("Процессировать комментарии")
        process_btn.click(process_comments, inputs=[token_input, radio, context_input],
                          # Обновлено: добавлен context_input
                          outputs=output_main)

    with gr.Tab("Обработать пост"):
        post_id = gr.Textbox(label="Post ID")
        output = gr.JSON()
        process_post_btn = gr.Button("Обработать пост")
        process_post_btn.click(process_single_post, inputs=[post_id, token_input, radio, context_input],
                               outputs=output)

if __name__ == "__main__":
    demo.launch(
        debug=True,
        server_port=7860,
        server_name="0.0.0.0"
    )