From a2f82b31a7e298ee4fa09a12a7b1014bf0194245 Mon Sep 17 00:00:00 2001 From: Jan-Pascal van Best <janpascal@vanbest.org> Date: Wed, 9 Nov 2016 02:32:56 +0100 Subject: [PATCH 1/6] Loiter new meaning (#5697) * Implement loiter option in FollowPath, loitering meaning not moving at all * More informative progress logging for FollowPath --- docs/configuration_files.md | 16 +++++++++++++- pokemongo_bot/cell_workers/follow_path.py | 27 ++++++++++++++--------- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/docs/configuration_files.md b/docs/configuration_files.md index 27b14d4728..c897fc3227 100644 --- a/docs/configuration_files.md +++ b/docs/configuration_files.md @@ -883,7 +883,15 @@ This task is an upgrade version of the MoveToMapPokemon task. It will fetch poke ### Description [[back to top](#table-of-contents)] -Walk to the specified locations loaded from .gpx or .json file. It is highly recommended to use website such as [GPSies](http://www.gpsies.com) which allow you to export your created track in JSON file. Note that you'll have to first convert its JSON file into the format that the bot can understand. See [Example of pier39.json] below for the content. I had created a simple python script to do the conversion. +Walk to the specified locations loaded from .gpx or .json file. It is highly +recommended to use website such as [GPSies](http://www.gpsies.com) which allow +you to export your created track in JSON file. Note that you'll have to first +convert its JSON file into the format that the bot can understand. See [Example +of pier39.json] below for the content. I had created a simple python script to +do the conversion. + +The `location` fields in the `.json` file can also contain a street address. In +this case the `location` is interpreted by the Google Maps API. The json file can contain for each point an optional `wander` field. This indicated the number of seconds the bot should wander after reaching the point. @@ -891,6 +899,12 @@ During this time, the next Task in the configuration file is executed, e.g. a MoveToFort task. This allows the bot to walk around the waypoint looking for forts for a limited time. +The `loiter` field, also optional for each point in the json file, works +similarly to the `wander` field. The difference is that with `loiter` the +next `Task` in the configuration file is /not/ executed, meaning the bot +will wait, without moving, at the point in the json file with the `loiter` +option. + ### Options [[back to top](#table-of-contents)] * `path_mode` - linear, loop, single diff --git a/pokemongo_bot/cell_workers/follow_path.py b/pokemongo_bot/cell_workers/follow_path.py index d0819531eb..6b3274c4b4 100644 --- a/pokemongo_bot/cell_workers/follow_path.py +++ b/pokemongo_bot/cell_workers/follow_path.py @@ -18,8 +18,9 @@ from datetime import datetime as dt, timedelta STATUS_MOVING = 0 -STATUS_WANDERING = 1 -STATUS_FINISHED = 2 +STATUS_LOITERING = 1 +STATUS_WANDERING = 2 +STATUS_FINISHED = 3 class FollowPath(BaseTask): SUPPORTED_TASK_API_VERSION = 1 @@ -28,7 +29,7 @@ def initialize(self): self._process_config() self.points = self.load_path() self.status = STATUS_MOVING - self.wander_end_time = 0 + self.waiting_end_time = 0 self.distance_unit = self.bot.config.distance_unit self.append_unit = False @@ -143,8 +144,11 @@ def work(self): if self.status == STATUS_FINISHED: return WorkerResult.SUCCESS - if self.status == STATUS_WANDERING and time.time() < self.wander_end_time: - return WorkerResult.SUCCESS + if time.time() < self.waiting_end_time: + if self.status == STATUS_WANDERING: + return WorkerResult.SUCCESS + elif self.status == STATUS_LOITERING: + return WorkerResult.RUNNING last_lat, last_lng, last_alt = self.bot.position @@ -184,19 +188,22 @@ def work(self): formatted="Walking from {last_position} to {current_position}, distance left: ({distance} {distance_unit}) ..", data={ 'last_position': (last_lat, last_lng, last_alt), - 'current_position': (lat, lng, alt), + 'current_position': point["location"], 'distance': format_dist(dist,self.distance_unit,self.append_unit), 'distance_unit': self.distance_unit } ) - if (self.bot.config.walk_min > 0 and is_at_destination) or (self.status == STATUS_WANDERING and time.time() >= self.wander_end_time): - if "loiter" in point: - self.logger.warning("'loiter' is obsolete, please change to 'wander' in {}".format(self.path_file)) + if (self.bot.config.walk_min > 0 and is_at_destination) or (self.status in [STATUS_WANDERING, STATUS_LOITERING] and time.time() >= self.waiting_end_time): + if "loiter" in point and self.status != STATUS_LOITERING: + self.logger.info("Loitering for {} seconds...".format(point["loiter"])) + self.status = STATUS_LOITERING + self.waiting_end_time = time.time() + point["loiter"] + return WorkerResult.RUNNING if "wander" in point and self.status != STATUS_WANDERING: self.logger.info("Wandering for {} seconds...".format(point["wander"])) self.status = STATUS_WANDERING - self.wander_end_time = time.time() + point["wander"] + self.waiting_end_time = time.time() + point["wander"] return WorkerResult.SUCCESS if (self.ptr + 1) == len(self.points): if self.path_mode == 'single': From e4b73f85c0d8b9c09f99d4333f1645650baca6ae Mon Sep 17 00:00:00 2001 From: mudmud2k <mudmud2k@mt2015.com> Date: Wed, 9 Nov 2016 02:36:32 +0100 Subject: [PATCH 2/6] pokecli.py: wait_time for every exception randomized (#5704) * pokecli.py: wait_time for every exception randomized randint(min,max) config.reconnecting -> min config.reconnection * 60 -> max * randint(timeout * 0.8 * 60, timeout * 1.2 * 60; docs update --- docs/configuration_files.md | 23 ++++++++++++----------- pokecli.py | 11 ++++++----- 2 files changed, 18 insertions(+), 16 deletions(-) diff --git a/docs/configuration_files.md b/docs/configuration_files.md index c897fc3227..2c1b663388 100644 --- a/docs/configuration_files.md +++ b/docs/configuration_files.md @@ -84,7 +84,7 @@ Document the configuration options of PokemonGo-Bot. | `action_wait_min` | 1 | Set the minimum time setting for anti-ban time randomizer | `action_wait_max` | 4 | Set the maximum time setting for anti-ban time randomizer | `debug` | false | Let the default value here except if you are developer | -| `test` | false | Let the default value here except if you are developer | +| `test` | false | Let the default value here except if you are developer | | `walker_limit_output` | false | Reduce output from walker functions | | | `location_cache` | true | Bot will start at last known location if you do not have location set in the config | | `distance_unit` | km | Set the unit to display distance in (km for kilometers, mi for miles, ft for feet) | @@ -97,6 +97,7 @@ Document the configuration options of PokemonGo-Bot. | `live_config_update.enabled` | false | Enable live config update | `live_config_update.tasks_only` | false | True: quick update for Tasks only (without re-login). False: slower update for entire config file. | `enable_social` | true | True: to chat with other pokemon go bot users [more information](https://github.com/PokemonGoF/PokemonGo-Bot/pull/4596) +| `reconnecting_timeout` | 5 | Set the wait time for the bot between tries, time will be randomized by 40% ## Logging configuration [[back to top](#table-of-contents)] @@ -163,7 +164,7 @@ The behaviors of the bot are configured via the `tasks` key in the `config.json` ### Task Options: [[back to top](#table-of-contents)] * CatchPokemon - * `enabled`: Default "true" | Enable/Disable the task. + * `enabled`: Default "true" | Enable/Disable the task. * `treat_unseen_as_vip`: Default `"true"` | If true, treat new to dex as VIP * `catch_visible_pokemon`: Default "true" | If enabled, attempts to catch "visible" pokemon that are reachable * `catch_lured_pokemon`: Default "true" | If enabled, attempts to catch "lured" pokemon that are reachable @@ -201,7 +202,7 @@ The behaviors of the bot are configured via the `tasks` key in the `config.json` * `log_interval`: `Default: 120`. Time (in seconds) to periodically print how far you are from having enough pokemon to evolve (more than `min_pokemon_to_be_evolved`) * `evolve_list`: Default `all` | Set to all, or specifiy different pokemon seperated by a comma * `donot_evolve_list`: Default `none` | Pokemon seperated by comma, will be ignored from evolve_list - * `min_evolve_speed`: Default `25` | Minimum seconds to wait between each evolution + * `min_evolve_speed`: Default `25` | Minimum seconds to wait between each evolution * `max_evolve_speed`: Default `30` | Maximum seconds to wait between each evolution * `min_pokemon_to_be_evolved`: Default: `1` | Minimum pokemon to be evolved * `use_lucky_egg`: Default: `False` | Only evolve if we can use a lucky egg @@ -220,8 +221,8 @@ The behaviors of the bot are configured via the `tasks` key in the `config.json` * IncubateEggs * `enable`: Disable or enable this task. * `longer_eggs_first`: Depreciated - * `infinite_longer_eggs_first`: Default `true` | Prioritize longer eggs in perminent incubators. - * `breakable_longer_eggs_first`: Default `false` | Prioritize longer eggs in breakable incubators. + * `infinite_longer_eggs_first`: Default `true` | Prioritize longer eggs in perminent incubators. + * `breakable_longer_eggs_first`: Default `false` | Prioritize longer eggs in breakable incubators. * `min_interval`: Default `120` | Minimum number of seconds between incubation updates. * `infinite`: Default `[2,5,10]` | Types of eggs to be incubated in permanent incubators. * `breakable`: Default `[2,5,10]` | Types of eggs to be incubated in breakable incubators. @@ -276,10 +277,10 @@ The behaviors of the bot are configured via the `tasks` key in the `config.json` * `level_limit`: Default `-1` | Bot will stop automatically after trainer reaches level limit. Set to `-1` to disable. * All tasks * `log_interval`: Default `0` | Minimum seconds interval before next log of the current task will be printed - - + + ### Specify a custom log_interval for specific task - + ``` { "type": "MoveToFort", @@ -292,9 +293,9 @@ The behaviors of the bot are configured via the `tasks` key in the `config.json` } } ``` - + Result: - + 2016-08-26 11:43:18,199 [MoveToFort] [INFO] [moving_to_fort] Moving towards pokestop ... - 0.07km 2016-08-26 11:43:23,641 [MoveToFort] [INFO] [moving_to_fort] Moving towards pokestop ... - 0.06km 2016-08-26 11:43:28,198 [MoveToFort] [INFO] [moving_to_fort] Moving towards pokestop ... - 0.05km @@ -917,7 +918,7 @@ option. * `path_file` - "/path/to/your/path.json" ### Notice -If you use the `single` `path_mode` without e.g. a `MoveToFort` task, your bot +If you use the `single` `path_mode` without e.g. a `MoveToFort` task, your bot with /not move at all/ when the path is finished. Similarly, if you use the `wander` option in your json path file without a following `MoveToFort` or similar task, your bot will not move during the wandering period. Please diff --git a/pokecli.py b/pokecli.py index d3c9353956..36df60566c 100644 --- a/pokecli.py +++ b/pokecli.py @@ -40,6 +40,7 @@ import subprocess from logging import Formatter +from random import randint codecs.register(lambda name: codecs.lookup("utf-8") if name == "cp65001" else None) @@ -185,7 +186,7 @@ def get_commit_hash(): finished = False while not finished: - wait_time = config.reconnecting_timeout * 60 + wait_time = randint((config.reconnecting_timeout * 0.8 * 60), (config.reconnecting_timeout * 1.2 * 60)) try: bot = initialize(config) bot = start_bot(bot, config) @@ -233,7 +234,7 @@ def get_commit_hash(): 'api_error', sender=bot, level='info', - formatted='Server busy or offline' + formatted='Server busy or offline, reconnecting in {:d} seconds'.format(wait_time) ) time.sleep(wait_time) except ServerSideRequestThrottlingException: @@ -241,9 +242,9 @@ def get_commit_hash(): 'api_error', sender=bot, level='info', - formatted='Server is throttling, reconnecting in 30 seconds' + formatted='Server is throttling, reconnecting in {:d} seconds'.format(wait_time) ) - time.sleep(30) + time.sleep(wait_time) except PermaBannedException: bot.event_manager.emit( 'api_error', @@ -257,7 +258,7 @@ def get_commit_hash(): 'api_error', sender=bot, level='info', - formatted='No player position set' + formatted='No player position set, reconnecting in {:d} seconds'.format(wait_time) ) time.sleep(wait_time) From 58c236120f16265b0f1d4c6e1397dfb87581bf35 Mon Sep 17 00:00:00 2001 From: Stuart Travers <gobberwart@gmail.com> Date: Thu, 10 Nov 2016 07:57:48 +1100 Subject: [PATCH 3/6] Fix ValueError crash ValueError, "non-integer arg 1 for randrange()" --- pokecli.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/pokecli.py b/pokecli.py index 36df60566c..f80dfc5edc 100644 --- a/pokecli.py +++ b/pokecli.py @@ -186,7 +186,9 @@ def get_commit_hash(): finished = False while not finished: - wait_time = randint((config.reconnecting_timeout * 0.8 * 60), (config.reconnecting_timeout * 1.2 * 60)) + min_wait_time = int(config.reconnecting_timeout * 0.8 * 60) + max_wait_time = int(config.reconnecting_timeout * 1.2 * 60) + wait_time = randint(min_wait_time, max_wait_time) try: bot = initialize(config) bot = start_bot(bot, config) From f6fec583f1ef53fa82586cb2653503555e329250 Mon Sep 17 00:00:00 2001 From: Stuart Travers <Gobberwart@users.noreply.github.com> Date: Fri, 11 Nov 2016 05:28:59 +1100 Subject: [PATCH 4/6] Fix hash/encrypt library searching (#5804) * Corrected maxos niantic lib filename Filename is libniantichash-macos-64.dylib not libniantichash-osx-64.so * Better search for encrypt/hash files Instead of just looking in root, or encrypt_location, or whatever the heck the last person did... will first search local or encrypt_location. If not found, will search pgoapi/lib. If still not found, abort. --- pokemongo_bot/__init__.py | 42 +++++++++++++++++++++++---------------- requirements.txt | 2 +- 2 files changed, 26 insertions(+), 18 deletions(-) diff --git a/pokemongo_bot/__init__.py b/pokemongo_bot/__init__.py index c0a27effe4..b3f497ec3b 100644 --- a/pokemongo_bot/__init__.py +++ b/pokemongo_bot/__init__.py @@ -979,25 +979,29 @@ def get_encryption_lib(self): if _platform == "Windows" or _platform == "win32": # Check if we are on 32 or 64 bit if sys.maxsize > 2**32: - file_name = 'src/pgoapi/pgoapi/lib/encrypt64.dll' + file_name = 'encrypt64.dll' else: - file_name = 'src/pgoapi/pgoapi/lib/encrypt32.dll' + file_name = 'encrypt32.dll' if _platform.lower() == "darwin": - file_name= 'src/pgoapi/pgoapi/lib/libencrypt-osx-64.so' + file_name= 'libencrypt-osx-64.so' if _platform.lower() == "linux" or _platform.lower() == "linux2": - file_name = 'src/pgoapi/pgoapi/lib/libencrypt-linux-x86-64.so' + file_name = 'libencrypt-linux-x86-64.so' if self.config.encrypt_location == '': path = os.path.abspath(os.path.join(os.path.dirname(__file__), os.pardir)) else: path = self.config.encrypt_location - full_path = path + '/'+ file_name - if not os.path.isfile(full_path): + full_path = '' + if os.path.isfile(path + '/' + file_name): # check encrypt_location or local dir first + full_path = path + '/' + file_name + elif os.path.isfile(path + '/src/pgoapi/pgoapi/lib/' + file_name): # if not found, check pgoapi lib folder + full_path = path + '/src/pgoapi/pgoapi/lib/' + file_name + + if full_path == '': self.logger.error(file_name + ' is not found! Please place it in the bots root directory or set encrypt_location in config.') - self.logger.info('Platform: '+ _platform + ' ' + file_name + ' directory: '+ path) sys.exit(1) else: - self.logger.info('Found '+ file_name +'! Platform: ' + _platform + ' ' + file_name + ' directory: ' + path) + self.logger.info('Found '+ file_name +'! Platform: ' + _platform + ' ' + file_name + ' directory: ' + full_path) return full_path @@ -1005,25 +1009,29 @@ def get_hash_lib(self): if _platform == "Windows" or _platform == "win32": # Check if we are on 32 or 64 bit if sys.maxsize > 2**32: - file_name = 'src/pgoapi/pgoapi/lib/niantichash64.dll' + file_name = 'niantichash64.dll' else: - file_name = 'src/pgoapi/pgoapi/lib/niantichash32.dll' + file_name = 'niantichash32.dll' if _platform.lower() == "darwin": - file_name= 'src/pgoapi/pgoapi/lib/libniantichash-osx-64.so' + file_name= 'libniantichash-macos-64.dylib' if _platform.lower() == "linux" or _platform.lower() == "linux2": - file_name = 'src/pgoapi/pgoapi/lib/libniantichash-linux-x86-64.so' + file_name = 'libniantichash-linux-x86-64.so' if self.config.encrypt_location == '': path = os.path.abspath(os.path.join(os.path.dirname(__file__), os.pardir)) else: path = self.config.encrypt_location - full_path = path + '/'+ file_name - if not os.path.isfile(full_path): - self.logger.error(file_name + ' is not found! Please place it in the bots root directory') - self.logger.info('Platform: '+ _platform + ' ' + file_name + ' directory: '+ path) + full_path = '' + if os.path.isfile(path + '/' + file_name): # check encrypt_location or local dir first + full_path = path + '/'+ file_name + elif os.path.isfile(path + '/src/pgoapi/pgoapi/lib/' + file_name): # if not found, check pgoapi lib folder + full_path = path + '/src/pgoapi/pgoapi/lib/' + file_name + + if full_path == '': + self.logger.error(file_name + ' is not found! Please place it in the bots root directory or set encrypt_location in config.') sys.exit(1) else: - self.logger.info('Found '+ file_name +'! Platform: ' + _platform + ' ' + file_name + ' directory: ' + path) + self.logger.info('Found '+ file_name +'! Platform: ' + _platform + ' ' + file_name + ' directory: ' + full_path) return full_path diff --git a/requirements.txt b/requirements.txt index 8f0a4ea255..74aee95ae5 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ numpy==1.11.0 networkx==1.11 --e git+https://github.com/pogodevorg/pgoapi.git/@v0.43.3-alpha#egg=pgoapi +-e git+https://github.com/sebastienvercammen/pgoapi.git#egg=pgoapi geopy==1.11.0 geographiclib==1.46.3 protobuf==3.0.0b4 From d6fbe9e67abda4c614f3d2edfbd63867a966b0bf Mon Sep 17 00:00:00 2001 From: Simba Zhang <solderzzc@users.noreply.github.com> Date: Sat, 12 Nov 2016 21:03:54 -0800 Subject: [PATCH 5/6] Update to the 0.45 of offical API. --- pokemongo_bot/__init__.py | 17 ++++++++--------- requirements.txt | 2 +- 2 files changed, 9 insertions(+), 10 deletions(-) diff --git a/pokemongo_bot/__init__.py b/pokemongo_bot/__init__.py index b3f497ec3b..08cac0b70b 100644 --- a/pokemongo_bot/__init__.py +++ b/pokemongo_bot/__init__.py @@ -122,7 +122,7 @@ def __init__(self, db, config): self.inventory_refresh_threshold = 10 self.inventory_refresh_counter = 0 self.last_inventory_refresh = time.time() - + # Catch on/off self.catch_disabled = False @@ -167,7 +167,7 @@ def _setup_event_system(self): if self.config.websocket_start_embedded_server: self.sio_runner = SocketIoRunner(self.config.websocket_server_url) self.sio_runner.start_listening_async() - + websocket_handler = SocketIoHandler( self, self.config.websocket_server_url @@ -738,11 +738,11 @@ def _register_events(self): self.event_manager.register_event('sniper_log', parameters=('message', 'message')) self.event_manager.register_event('sniper_error', parameters=('message', 'message')) self.event_manager.register_event('sniper_teleporting', parameters=('latitude', 'longitude', 'name')) - + # Catch-limiter self.event_manager.register_event('catch_limit_on') self.event_manager.register_event('catch_limit_off') - + def tick(self): self.health_record.heartbeat() @@ -996,7 +996,7 @@ def get_encryption_lib(self): full_path = path + '/' + file_name elif os.path.isfile(path + '/src/pgoapi/pgoapi/lib/' + file_name): # if not found, check pgoapi lib folder full_path = path + '/src/pgoapi/pgoapi/lib/' + file_name - + if full_path == '': self.logger.error(file_name + ' is not found! Please place it in the bots root directory or set encrypt_location in config.') sys.exit(1) @@ -1026,7 +1026,7 @@ def get_hash_lib(self): full_path = path + '/'+ file_name elif os.path.isfile(path + '/src/pgoapi/pgoapi/lib/' + file_name): # if not found, check pgoapi lib folder full_path = path + '/src/pgoapi/pgoapi/lib/' + file_name - + if full_path == '': self.logger.error(file_name + ' is not found! Please place it in the bots root directory or set encrypt_location in config.') sys.exit(1) @@ -1045,8 +1045,8 @@ def _setup_api(self): self.login() # chain subrequests (methods) into one RPC call - self.api.set_signature_lib(self.get_encryption_lib()) - self.api.set_hash_lib(self.get_hash_lib()) + #self.api.set_signature_lib(self.get_encryption_lib()) + #self.api.set_hash_lib(self.get_hash_lib()) self.logger.info('') # send empty map_cells and then our position @@ -1540,4 +1540,3 @@ def _refresh_inventory(self): inventory.refresh_inventory() self.last_inventory_refresh = now self.inventory_refresh_counter += 1 - diff --git a/requirements.txt b/requirements.txt index 74aee95ae5..fc7af4ddd9 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ numpy==1.11.0 networkx==1.11 --e git+https://github.com/sebastienvercammen/pgoapi.git#egg=pgoapi +-e git+https://github.com/pogodevorg/pgoapi#egg=pgoapi geopy==1.11.0 geographiclib==1.46.3 protobuf==3.0.0b4 From 71e1f268237af267183e9869b4e7bc5a199c6af0 Mon Sep 17 00:00:00 2001 From: Simba Zhang <solderzzc@users.noreply.github.com> Date: Sat, 12 Nov 2016 21:09:10 -0800 Subject: [PATCH 6/6] updated to .git of pgoapi. --- requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/requirements.txt b/requirements.txt index fc7af4ddd9..62c16aae25 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ numpy==1.11.0 networkx==1.11 --e git+https://github.com/pogodevorg/pgoapi#egg=pgoapi +-e git+https://github.com/pogodevorg/pgoapi.git#egg=pgoapi geopy==1.11.0 geographiclib==1.46.3 protobuf==3.0.0b4