Guest User

Untitled

a guest
Jun 5th, 2024
500
1
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 10.75 KB | Source Code | 1 0
  1. import tkinter as tk
  2. from tkinter import ttk, messagebox
  3. from telethon import TelegramClient, events, sync
  4. from telethon.tl.functions.contacts import GetContactsRequest, ImportContactsRequest, DeleteContactsRequest, GetLocatedRequest, AddContactRequest
  5. from telethon.tl.types import InputPeerUser, InputPeerEmpty, UserStatusOffline, UserStatusRecently, UserStatusLastMonth, UserStatusLastWeek, InputGeoPoint
  6. from datetime import datetime, timedelta, timezone
  7. import asyncio
  8. import time
  9. import threading
  10. from tkintermapview import TkinterMapView
  11.  
  12. # Ваши данные из my.telegram.org
  13. api_id = APP_ID
  14. api_hash = 'APP_HASH'
  15. phone_number = '+70000000'
  16.  
  17. # Создаем клиент Telegram (вне функции main)
  18. client = TelegramClient("read_client", api_id=api_id, api_hash=api_hash, device_model="iPhone 55 Pro", system_version="IOS 100.1")
  19.  
  20. # Время задержки между запросами к API Telegram
  21. delay_seconds = 1
  22.  
  23. # Ваш часовой пояс (в секундах)
  24. timezone_offset = 3 * 60 * 60
  25.  
  26. class App(tk.Tk):
  27.     def __init__(self):
  28.         super().__init__()
  29.  
  30.         self.title("Поиск пользователей Telegram")
  31.         self.geometry("1024x800")
  32.  
  33.         # --- Разделение окна на фреймы ---
  34.         top_frame = tk.Frame(self)
  35.         top_frame.pack(side=tk.TOP, fill=tk.BOTH, expand=True)
  36.  
  37.         map_frame = tk.Frame(top_frame)
  38.         map_frame.pack(side=tk.LEFT, fill=tk.BOTH, expand=True)
  39.  
  40.         input_frame = ttk.LabelFrame(top_frame, text="Координаты")
  41.         input_frame.pack(side=tk.RIGHT, padx=10, pady=10, fill=tk.Y)
  42.  
  43.         results_frame = tk.Frame(self)
  44.         results_frame.pack(fill=tk.BOTH, expand=True)
  45.         # --- Конец разделения ---
  46.  
  47.         # Карта OpenStreetMap
  48.         self.map_widget = TkinterMapView(map_frame, width=600, height=400, corner_radius=0)
  49.         self.map_widget.pack(expand=True, fill=tk.BOTH)
  50.  
  51.  
  52.         # --- Фрейм для координат и кнопки ---
  53.         self.latitude = tk.StringVar(value="55.63729")
  54.         self.longitude = tk.StringVar(value="37.88502")
  55.         self.radius = tk.StringVar(value="500")
  56.        
  57.         latitude_fl = float(self.latitude.get())
  58.         longitude_fl = float(self.longitude.get())
  59.         self.map_widget.set_position(latitude_fl, longitude_fl)  # Москва
  60.         self.map_widget.set_zoom(18)
  61.        
  62.         # Маркер на карте
  63.         self.marker = None
  64.        
  65.         # Обработчик клика по карте
  66.         self.bind('<Button-1>', self.on_map_click)        
  67.  
  68.         ttk.Label(input_frame, text="Широта:").grid(row=0, column=0, padx=5, pady=5)
  69.         ttk.Entry(input_frame, textvariable=self.latitude).grid(row=0, column=1, padx=5, pady=5)
  70.  
  71.         ttk.Label(input_frame, text="Долгота:").grid(row=1, column=0, padx=5, pady=5)
  72.         ttk.Entry(input_frame, textvariable=self.longitude).grid(row=1, column=1, padx=5, pady=5)
  73.  
  74.         ttk.Label(input_frame, text="Радиус поиска:").grid(row=2, column=0, padx=5, pady=5)
  75.         ttk.Entry(input_frame, textvariable=self.radius).grid(row=2, column=1, padx=5, pady=5)
  76.  
  77.  
  78.         ttk.Button(input_frame, text="Начать поиск", command=self.start_search).grid(row=3, column=0, columnspan=2, padx=5, pady=10)
  79.         # --- Конец фрейма ---
  80.  
  81.         # --- Таблица для вывода результатов ---
  82.         self.results_table = ttk.Treeview(results_frame, columns=("ID", "Расстояние", "Username", "Имя", "Фамилия", "Дата онлайна"), show="headings")
  83.         self.results_table.heading("ID", text="ID")
  84.         self.results_table.heading("Расстояние", text="Расстояние (м)")
  85.         self.results_table.heading("Username", text="Username")
  86.         self.results_table.heading("Имя", text="Имя")
  87.         self.results_table.heading("Фамилия", text="Фамилия")
  88.         self.results_table.heading("Дата онлайна", text="Дата онлайна")
  89.  
  90.         self.results_table.column("ID", width=100)
  91.         self.results_table.column("Расстояние", width=100)
  92.         self.results_table.column("Username", width=150)
  93.         self.results_table.column("Имя", width=150)
  94.         self.results_table.column("Фамилия", width=150)
  95.         self.results_table.column("Дата онлайна", width=150)
  96.  
  97.         self.results_table.pack(fill=tk.BOTH, expand=True)
  98.         # --- Конец таблицы ---
  99.        
  100.  
  101.     def on_map_click(self, event):
  102.         # Получаем координаты клика
  103.         latitude = self.map_widget.get_position()[0]
  104.         longitude = self.map_widget.get_position()[1]
  105.        
  106.         # Удаляем старый маркер, если он есть
  107.         if self.marker:
  108.             self.map_widget.delete(self.marker)        
  109.        
  110.         # Создаем маркер на карте
  111.         self.marker = self.map_widget.set_marker(latitude, longitude, text="Выбранное место")
  112.  
  113.         # Обновляем поля ввода
  114.         self.latitude.set(str(latitude))
  115.         self.longitude.set(str(longitude))
  116.  
  117.     def start_search(self):
  118.         try:
  119.             latitude = float(self.latitude.get())
  120.             longitude = float(self.longitude.get())
  121.         except ValueError:
  122.             messagebox.showerror("Ошибка", "Неверный формат координат.")
  123.             return
  124.  
  125.         # Очищаем таблицу перед новым поиском
  126.         for item in self.results_table.get_children():
  127.             self.results_table.delete(item)
  128.  
  129.         # Запускаем асинхронную функцию поиска в отдельном потоке
  130.         threading.Thread(target=self.run_search, args=(latitude, longitude), daemon=True).start()
  131.  
  132.     def run_search(self, latitude, longitude):
  133.         try:
  134.             asyncio.run(self.search_users(latitude, longitude))
  135.         except Exception as e:
  136.             messagebox.showerror("Ошибка", f"Произошла ошибка: {e}")
  137.         finally:
  138.             messagebox.showinfo("Информация", "Поиск завершен.")
  139.  
  140.     async def search_users(self, latitude, longitude):
  141.         # Подключаемся к Telegram
  142.         await client.connect()
  143.  
  144.         client.session.save()
  145.  
  146.         # Авторизация
  147.         if not await client.is_user_authorized():
  148.             await client.send_code_request(phone_number)
  149.             # Введите код, полученный в Telegram
  150.             me = await client.sign_in(phone_number, input('Введите код авторизации: '))
  151.         else:
  152.             me = await client.get_me()
  153.  
  154.         try:
  155.             users = await client(GetLocatedRequest(
  156.                 geo_point=InputGeoPoint(
  157.                     lat=latitude,
  158.                     long=longitude,
  159.                     accuracy_radius=100
  160.                 ),
  161.                 self_expires=10
  162.             ))
  163.         except Exception as e:
  164.             messagebox.showerror("Ошибка", f"Ошибка при получении местоположений пользователей: {e}")
  165.             await client.disconnect()
  166.             return
  167.  
  168.         # print(users.stringify())
  169.        
  170.         # Сохранение сырого ответа
  171.         with open("raw_georequest.txt", "w", encoding="utf-8") as f2:
  172.             f2.write(users.stringify())
  173.        
  174.        
  175.         for user in users.updates[0].peers:
  176.             if hasattr(user, 'peer') and hasattr(user.peer, 'user_id'):
  177.                 await self.get_user_info(user)
  178.  
  179.         # Отключаемся от Telegram
  180.         await client.disconnect()
  181.  
  182.     async def get_user_info(self, user):
  183.         user_id = user.peer.user_id
  184.         distance = user.distance
  185.  
  186.         if distance <= int(self.radius.get()):  # Не дальше 600 метров  
  187.             await asyncio.sleep(delay_seconds)  
  188.  
  189.             try:
  190.                 full_user = await client.get_entity(user_id)
  191.             except Exception as e:
  192.                 messagebox.showerror("Ошибка", f"Ошибка при получении информации о пользователе {user_id}: {e}")
  193.                 return
  194.  
  195.             date_online_str = ''
  196.             date_online = None
  197.  
  198.             last_month = datetime.now() - timedelta(days=30)
  199.             last_week = datetime.now() - timedelta(days=7)
  200.  
  201.             if isinstance(full_user.status, UserStatusRecently):
  202.                 date_online_str = 'online'
  203.             else:
  204.                 if isinstance(full_user.status, UserStatusLastMonth):
  205.                     date_online = last_month
  206.                 if isinstance(full_user.status, UserStatusLastWeek):
  207.                     date_online = last_week
  208.                 if isinstance(full_user.status, UserStatusOffline):
  209.                     date_online = full_user.status.was_online                    
  210.  
  211.                 if date_online:
  212.                     date_online = date_online.replace(tzinfo=timezone.utc) + timedelta(seconds=timezone_offset)
  213.                     date_online_str = date_online.strftime("%d.%m.%Y %H:%M")
  214.  
  215.             # Добавление информации о пользователе в таблицу
  216.             self.results_table.insert("", tk.END, values=(
  217.                 user_id,
  218.                 distance,
  219.                 full_user.username,
  220.                 full_user.first_name,
  221.                 full_user.last_name,
  222.                 date_online_str
  223.             ))
  224.  
  225.             # Сохранение информации о пользователе в файл (по желанию)
  226.             with open("nearby_users.txt", "a", encoding="utf-8") as f:
  227.                 f.write(f"ID: {user_id}, Имя пользователя: {full_user.username}, Имя: {full_user.first_name}, Фамилия: {full_user.last_name}, Дата онлайна: {date_online_str}\n")
  228.  
  229.             # Добавление пользователя в контакты (с задержкой)
  230.             try:            
  231.                 result = await client(AddContactRequest(
  232.                     id=user_id,
  233.                     first_name=full_user.first_name if full_user.first_name else "",
  234.                     last_name=full_user.last_name if full_user.last_name else "",
  235.                     phone=full_user.phone if full_user.phone else "",
  236.                 ))
  237.             except Exception as e:
  238.                 messagebox.showerror("Ошибка", f"Ошибка при добавлении пользователя в контакты: {e}")  
  239.  
  240. if __name__ == "__main__":
  241.     app = App()
  242.     app.mainloop()
Advertisement
Add Comment
Please, Sign In to add comment