Skip to content

Commit

Permalink
Update to v3.7.15
Browse files Browse the repository at this point in the history
  • Loading branch information
Alexander Mishchenko committed Jun 24, 2021
1 parent 809ba88 commit 2b3d114
Show file tree
Hide file tree
Showing 5 changed files with 70 additions and 36 deletions.
2 changes: 1 addition & 1 deletion insomniac/__version__.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
__title__ = 'insomniac'
__description__ = 'Simple Instagram bot for automated Instagram interaction using Android.'
__url__ = 'https://github.com/alexal1/Insomniac/'
__version__ = '3.7.14'
__version__ = '3.7.15'
__debug_mode__ = False
__author__ = 'Insomniac Team'
__author_email__ = 'info@insomniac-bot.com'
Expand Down
1 change: 0 additions & 1 deletion insomniac/safely_runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ def wrapper(*args, **kwargs):
close_instagram(device_wrapper.device_id, device_wrapper.app_id)
sleeper.random_sleep()
open_instagram(device_wrapper.device_id, device_wrapper.app_id)
sleeper.random_sleep()
navigate(device_wrapper.get(), TabBarTabs.PROFILE)
except LanguageChangedException:
print_timeless("")
Expand Down
1 change: 0 additions & 1 deletion insomniac/session.py
Original file line number Diff line number Diff line change
Expand Up @@ -184,7 +184,6 @@ def start_session(self, args, device_wrapper, app_version, save_profile_info=Tru
if __version__.__debug_mode__:
device_wrapper.get().start_screen_record()
open_instagram(args.device, args.app_id)
sleeper.random_sleep()
if save_profile_info:
self.session_state.my_username, \
self.session_state.my_followers_count, \
Expand Down
35 changes: 30 additions & 5 deletions insomniac/utils.py
Original file line number Diff line number Diff line change
@@ -1,18 +1,18 @@
import base64
import os
import string
import random
import re
import shutil
import string
import subprocess
import sys
import traceback
import random
import colorama
import base64
from datetime import datetime
from datetime import datetime, timedelta
from random import randint
from subprocess import PIPE
from time import sleep

import colorama
from colorama import Fore, Style, AnsiToWin32

import insomniac.__version__ as __version__
Expand Down Expand Up @@ -343,6 +343,31 @@ def _get_log_file_name(logs_directory_name):
return log_path


class Timer:

duration = None
start_time = None
end_time = None

def __init__(self, seconds):
self.duration = timedelta(seconds=seconds)
self.start()

def start(self):
self.start_time = datetime.now()
self.end_time = self.start_time + self.duration

def is_expired(self):
return datetime.now() > self.end_time

def get_seconds_left(self):
time_since_start = datetime.now() - self.start_time
if time_since_start >= self.duration:
return 0
else:
return int((self.duration - time_since_start).total_seconds())


class Logger(object):
is_log_initiated = False

Expand Down
67 changes: 39 additions & 28 deletions insomniac/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,9 @@
from insomniac.utils import *


TEXTVIEW_OR_BUTTON_REGEX = 'android.widget.TextView|android.widget.Button'


def case_insensitive_re(str_list):
if isinstance(str_list, str):
strings = str_list
Expand Down Expand Up @@ -173,11 +176,18 @@ def navigate_to(self, tab: TabBarTabs):
descriptionMatches=case_insensitive_re(TabBarView.PROFILE_CONTENT_DESC)
)

if button.exists():
# Two clicks to reset tab content
button.click()
button.click()
return
timer = Timer(seconds=20)
while not timer.is_expired():
if button.exists():
# Two clicks to reset tab content
button.click()
button.click()
return
else:
seconds_left = timer.get_seconds_left()
if seconds_left > 0:
print(COLOR_OKGREEN + f"Opening {tab_name}, {seconds_left} seconds left..." + COLOR_ENDC)
sleep(2)

print(COLOR_FAIL + f"Didn't find tab {tab_name} in the tab bar... "
f"Maybe English language is not set!?" + COLOR_ENDC)
Expand Down Expand Up @@ -318,15 +328,15 @@ class SearchView(InstagramView):

def refresh(self):
posts_grid = self.device.find(resourceId=PostsGridView.POSTS_GRID_RESOURCE_ID.format(self.device.app_id),
className=PostsGridView.POSTS_GRID_CLASS_NAME)
classNameMatches=PostsGridView.POSTS_GRID_CLASS_NAME)
if posts_grid.exists():
posts_grid.scroll(DeviceFacade.Direction.TOP)

def _get_search_edit_text(self):
search_edit_text = self.device.find(resourceId=f"{self.device.app_id}:id/action_bar_search_edit_text",
className="android.widget.EditText")
if not search_edit_text.exists(quick=True):
print(COLOR_FAIL + "Cannot find search bar. Will try to refresh the page." + COLOR_ENDC)
print(COLOR_OKGREEN + "Cannot find search bar. Will try to refresh the page." + COLOR_ENDC)
self.refresh()
return search_edit_text

Expand Down Expand Up @@ -386,6 +396,10 @@ def _get_tab_view(self, tab: SearchTabs):
def navigate_to_username(self, username, on_action):
print_debug(f"Navigate to profile @{username}")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()

# Check if username already exists in the recent search list -> act as human
username_view_recent = self._get_username_row(username)
if username_view_recent.exists(quick=True):
Expand All @@ -394,11 +408,7 @@ def navigate_to_username(self, username, on_action):
return ProfileView(self.device, is_own_profile=False)
print(f"@{username} is not in recent searching history...")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()
search_edit_text.set_text(username)

search_text = self.device.find(resourceId=self.SEARCH_TEXT_ID.format(self.device.app_id),
className=self.SEARCH_TEXT_CLASSNAME)
search_text.click(ignore_if_missing=True)
Expand All @@ -423,6 +433,10 @@ def navigate_to_username(self, username, on_action):
def navigate_to_hashtag(self, hashtag):
print_debug(f"Navigate to hashtag #{hashtag}")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()

# Check if hashtag already exists in the recent search list -> act as human
hashtag_view_recent = self._get_hashtag_row(hashtag)
if hashtag_view_recent.exists(quick=True):
Expand All @@ -431,11 +445,7 @@ def navigate_to_hashtag(self, hashtag):
return HashTagView(self.device)
print(f"#{hashtag} is not in recent searching history...")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()
search_edit_text.set_text(hashtag)

search_text = self.device.find(resourceId=self.SEARCH_TEXT_ID.format(self.device.app_id),
className=self.SEARCH_TEXT_CLASSNAME)
search_text.click(ignore_if_missing=True)
Expand All @@ -458,6 +468,10 @@ def navigate_to_hashtag(self, hashtag):
def navigate_to_place(self, place):
print_debug(f"Navigate to place {place}")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()

# Check if place already exists in the recent search list -> act as human
place_view_recent = self._get_place_row(place)
if place_view_recent.exists(quick=True):
Expand All @@ -466,11 +480,7 @@ def navigate_to_place(self, place):
return PlacesView(self.device)
print(f"{place} is not in recent searching history...")

search_edit_text = self._get_search_edit_text()
search_edit_text.click()
self._handle_permission_request()
search_edit_text.set_text(place)

search_text = self.device.find(resourceId=self.SEARCH_TEXT_ID.format(self.device.app_id),
className=self.SEARCH_TEXT_CLASSNAME)
search_text.click(ignore_if_missing=True)
Expand Down Expand Up @@ -793,13 +803,13 @@ def like(self):
class PostsGridView(InstagramView):

POSTS_GRID_RESOURCE_ID = '{0}:id/recycler_view'
POSTS_GRID_CLASS_NAME = 'androidx.recyclerview.widget.RecyclerView'
POSTS_GRID_CLASS_NAME = 'androidx.recyclerview.widget.RecyclerView|android.view.View'

def open_random_post(self) -> Optional['PostsViewList']:
# Scroll down several times to pick random post
scroll_times = randint(0, 5)
posts_grid = self.device.find(resourceId=self.POSTS_GRID_RESOURCE_ID.format(self.device.app_id),
className=self.POSTS_GRID_CLASS_NAME)
classNameMatches=self.POSTS_GRID_CLASS_NAME)
print(f"Scroll down {scroll_times} times.")
for _ in range(0, scroll_times):
posts_grid.scroll(DeviceFacade.Direction.BOTTOM)
Expand Down Expand Up @@ -845,8 +855,10 @@ def open_random_post(self) -> Optional['PostsViewList']:


class ProfileView(ActionBarView):

FOLLOWERS_BUTTON_ID_REGEX = '{0}:id/row_profile_header_followers_container|{1}:id/row_profile_header_container_followers'
FOLLOWING_BUTTON_ID_REGEX = '{0}:id/row_profile_header_following_container|{1}:id/row_profile_header_container_following'
MESSAGE_BUTTON_CLASS_NAME_REGEX = TEXTVIEW_OR_BUTTON_REGEX

def __init__(self, device: DeviceFacade, is_own_profile=False):
super().__init__(device)
Expand Down Expand Up @@ -1130,8 +1142,7 @@ def navigate_to_following(self):

def open_messages(self):
message_button = self.device.find(
className='android.widget.Button',
clickable=True,
classNameMatches=self.MESSAGE_BUTTON_CLASS_NAME_REGEX,
textMatches=case_insensitive_re('Message')
)
if message_button.exists(quick=True):
Expand Down Expand Up @@ -1166,10 +1177,10 @@ def switch_to_tab(self, tab):
sleeper.random_sleep()
following_tab = self.device.find(className="android.widget.TextView",
clickable=True,
textContains="Following")
textMatches="(?i).*?following")
followers_tab = self.device.find(className="android.widget.TextView",
clickable=True,
textContains="Followers")
textMatches="(?i).*?followers")
if tab == self.Tab.FOLLOWERS:
followers_tab.click()
else:
Expand Down Expand Up @@ -1356,17 +1367,17 @@ def getTimestamp(self):
class DialogView(InstagramView):

UNFOLLOW_BUTTON_ID_REGEX = '{0}:id/follow_sheet_unfollow_row|{1}:id/button_positive|{2}:id/primary_button'
UNFOLLOW_BUTTON_CLASS_NAME_REGEX = 'android.widget.TextView|android.widget.Button'
UNFOLLOW_BUTTON_CLASS_NAME_REGEX = TEXTVIEW_OR_BUTTON_REGEX
UNFOLLOW_BUTTON_TEXT_REGEX = case_insensitive_re("Unfollow")
LOCATION_DENY_BUTTON_ID_REGEX = '.*?:id/permission_deny.*?'
LOCATION_DENY_BUTTON_CLASS_NAME_REGEX = 'android.widget.TextView|android.widget.Button'
LOCATION_DENY_BUTTON_CLASS_NAME_REGEX = TEXTVIEW_OR_BUTTON_REGEX
LOCATION_CHECKBOX_ID_REGEX = '.*?:id/do_not_ask_checkbox'

def is_visible(self) -> bool:
dialog_v1 = self.device.find(resourceId=f'{self.device.app_id}:id/dialog_root_view',
className='android.widget.FrameLayout')
dialog_v2 = self.device.find(resourceId=f'{self.device.app_id}:id/dialog_container',
className='android.view.ViewGroup')
classNameMatches='android.view.ViewGroup|android.view.View')
dialog_v3 = self.device.find(resourceId=f'{self.device.app_id}:id/content',
className='android.widget.FrameLayout')
dialog_v4 = self.device.find(resourceIdMatches='com.android.(permissioncontroller|packageinstaller):id/.*?',
Expand Down

0 comments on commit 2b3d114

Please sign in to comment.