[V3 Everything] Package bot and write setup scripts (#964)

Ya'll are gonna hate me.

* Initial modifications

* Add initial setup.py

* working setup py help

* Modify setup file to package stuff

* Move a bunch of shit and fix imports

* Fix or skip tests

* Must add init files for find_packages to work

* Move main to scripts folder and rename

* Add shebangs

* Copy over translation files

* WORKING PIP INSTALL

* add dependency information

* Hardcoded version for now, will need to figure out a better way to do this

* OKAY ITS FINALLY FUCKING WORKING

* Add this guy

* Fix stuff

* Change readme to rst

* Remove double sentry opt in

* Oopsie

* Fix this thing

* Aaaand fix test

* Aaaand fix test

* Fix core cog importing and default cog install path

* Adjust readme

* change instance name from optional to required

* Ayyy let's do more dependency injection
This commit is contained in:
Will 2017-09-08 23:14:32 -04:00 committed by GitHub
parent 6b1fc786ee
commit d69fd63da7
85 changed files with 451 additions and 255 deletions

View File

@ -4,9 +4,9 @@ python:
- "3.5.3"
- "3.6.1"
install:
- pip install -r requirements.txt
- pip install --process-dependency-links -e .[test]
script:
- python -m compileall ./cogs
- python -m compileall ./redbot/cogs
- python -m pytest
cache: pip
notifications:

4
MANIFEST.in Normal file
View File

@ -0,0 +1,4 @@
include README.rst
include LICENSE
include requirements.txt
include discord/bin/*.dll

View File

@ -4,3 +4,11 @@
**This is alpha and very much a work in progress. Regular use is not recommended.
There will not be any effort not to break current installations.**
### How to install
Using python3 pip::
pip install --process-dependency-links -U git+https://github.com/Cog-Creators/Red-DiscordBot@V3/develop
redbot-setup
redbot <name>

View File

@ -1,40 +0,0 @@
from core.config import Config
from subprocess import run, PIPE
from collections import namedtuple
from main import determine_main_folder
__all__ = ["Config", "__version__"]
version_info = namedtuple("VersionInfo", "major minor patch")
BASE_VERSION = version_info(3, 0, 0)
def get_latest_version():
main_folder = determine_main_folder()
try:
p = run(
"git describe --abbrev=0 --tags".split(),
stdout=PIPE,
cwd=str(main_folder)
)
except FileNotFoundError:
# No git
return BASE_VERSION
if p.returncode != 0:
return BASE_VERSION
stdout = p.stdout.strip().decode()
if stdout.startswith("v"):
numbers = stdout[1:].split('.')
args = [0, 0, 0]
for i in range(3):
try:
args[i] = int(numbers[i])
except (IndexError, ValueError):
args[i] = 0
return version_info(*args)
return BASE_VERSION
__version__ = get_latest_version()

View File

@ -1,29 +1,31 @@
#!/usr/bin/env python
# Discord Version check
import discord
import sys
import discord
if discord.version_info.major < 1:
print("You are not running the rewritten version of discord.py.\n\n"
"In order to use Red v3 you MUST be running d.py version"
" >= 1.0.0.")
sys.exit(1)
from core.bot import Red, ExitCodes
from core.cog_manager import CogManagerUI
from core.data_manager import load_basic_configuration
from core.global_checks import init_global_checks
from core.events import init_events
from core.sentry_setup import init_sentry_logging
from core.cli import interactive_config, confirm, parse_cli_flags, ask_sentry
from core.core_commands import Core
from core.dev_commands import Dev
from redbot.core.bot import Red, ExitCodes
from redbot.core.cog_manager import CogManagerUI
from redbot.core.data_manager import load_basic_configuration
from redbot.core.global_checks import init_global_checks
from redbot.core.events import init_events
from redbot.core.sentry_setup import init_sentry_logging
from redbot.core.cli import interactive_config, confirm, parse_cli_flags, ask_sentry
from redbot.core.core_commands import Core
from redbot.core.dev_commands import Dev
import asyncio
import logging.handlers
import logging
import os
from pathlib import Path
from warnings import warn
#
# Red - Discord Bot v3
@ -58,7 +60,7 @@ def init_loggers(cli_flags):
else:
logger.setLevel(logging.WARNING)
from core.data_manager import core_data_path
from redbot.core.data_manager import core_data_path
logfile_path = core_data_path() / 'red.log'
fhandler = logging.handlers.RotatingFileHandler(
filename=str(logfile_path), encoding='utf-8', mode='a',
@ -75,10 +77,6 @@ def init_loggers(cli_flags):
return logger, sentry_logger
def determine_main_folder() -> Path:
return Path(os.path.dirname(__file__)).resolve()
async def _get_prefix_and_token(red, indict):
"""
Again, please blame <@269933075037814786> for this.
@ -90,48 +88,23 @@ async def _get_prefix_and_token(red, indict):
indict['enable_sentry'] = await red.db.enable_sentry()
if __name__ == '__main__':
cli_flags = parse_cli_flags()
if cli_flags.config:
load_basic_configuration(Path(cli_flags.config).resolve())
else:
warn("Soon you will need to change the way you load the bot."
" The new method of loading has yet to be decided upon but"
" will be made clear in announcements from the support server"
" and from documentation. Please see issue #938 for further"
" discussion on this topic.",
category=FutureWarning)
import core.data_manager
defaults = core.data_manager.basic_config_default.copy()
defaults['DATA_PATH'] = str(determine_main_folder())
defaults['CORE_PATH_APPEND'] = 'core/.data'
defaults['COG_PATH_APPEND'] = 'cogs/.data'
core.data_manager.basic_config = defaults
def main():
cli_flags = parse_cli_flags(sys.argv[1:])
load_basic_configuration(cli_flags.instance_name)
log, sentry_log = init_loggers(cli_flags)
description = "Red v3 - Alpha"
bot_dir = determine_main_folder()
red = Red(cli_flags, description=description, pm_help=None,
bot_dir=bot_dir)
red = Red(cli_flags, description=description, pm_help=None)
init_global_checks(red)
init_events(red, cli_flags)
red.add_cog(Core())
red.add_cog(CogManagerUI())
if cli_flags.dev:
red.add_cog(Dev())
loop = asyncio.get_event_loop()
tmp_data = {}
loop.run_until_complete(_get_prefix_and_token(red, tmp_data))
token = os.environ.get("RED_TOKEN", tmp_data['token'])
prefix = cli_flags.prefix or tmp_data['prefix']
enable_sentry = tmp_data['enable_sentry']
if token is None or not prefix:
if cli_flags.no_prompt is False:
new_token = interactive_config(red, token_set=bool(token),
@ -141,17 +114,10 @@ if __name__ == '__main__':
else:
log.critical("Token and prefix must be set in order to login.")
sys.exit(1)
if enable_sentry is None:
ask_sentry(red)
loop.run_until_complete(_get_prefix_and_token(red, tmp_data))
if tmp_data['enable_sentry']:
init_sentry_logging(red, sentry_log)
init_sentry_logging(sentry_log)
cleanup_tasks = True
try:
loop.run_until_complete(red.start(token, bot=not cli_flags.not_bot))
except discord.LoginFailure:
@ -183,3 +149,7 @@ if __name__ == '__main__':
gathered.exception()
sys.exit(red._shutdown_mode.value)
if __name__ == '__main__':
main()

View File

@ -1,12 +1,13 @@
import discord
from copy import copy
from typing import Generator, Tuple, Iterable
import discord
from redbot.core import Config
from redbot.core.i18n import CogI18n
from redbot.core.utils.chat_formatting import box
from discord.ext import commands
from typing import Generator, Tuple, Iterable
from core import Config
from core.bot import Red
from core.utils.chat_formatting import box
from core.i18n import CogI18n
from redbot.core.bot import Red
from .alias_entry import AliasEntry
_ = CogI18n("Alias", __file__)

View File

@ -1,8 +1,8 @@
from redbot.core import checks, bank
from redbot.core.i18n import CogI18n
from discord.ext import commands
from core import checks, bank
from core.bot import Red # Only used for type hints
from core.i18n import CogI18n
from redbot.core.bot import Red # Only used for type hints
_ = CogI18n('Bank', __file__)

View File

@ -1,4 +1,4 @@
from core.bot import Red
from redbot.core.bot import Red
from .downloader import Downloader

View File

@ -1,24 +1,23 @@
import os
import shutil
from pathlib import Path
from sys import path as syspath
from typing import Tuple, Union
import discord
from redbot.core import Config
from redbot.core import checks
from redbot.core.i18n import CogI18n
from redbot.core.utils.chat_formatting import box
from discord.ext import commands
from pathlib import Path
from sys import path as syspath
from core import Config
from core.bot import Red
from core import checks
from core.utils.chat_formatting import box
from core.i18n import CogI18n
from .repo_manager import RepoManager, Repo
from .installable import Installable
from .converters import RepoName, InstalledCog
from .log import log
from .errors import CloningError, ExistingGitRepo
from redbot.core.bot import Red
from .checks import install_agreement
from .converters import RepoName, InstalledCog
from .errors import CloningError, ExistingGitRepo
from .installable import Installable
from .log import log
from .repo_manager import RepoManager, Repo
_ = CogI18n('Downloader', __file__)

View File

@ -1,23 +1,22 @@
import asyncio
import json
import functools
import os
from concurrent.futures import ThreadPoolExecutor
from pathlib import Path
from typing import Tuple, MutableMapping, Union
from subprocess import run as sp_run, PIPE
from sys import executable
import pkgutil
import shutil
import functools
from concurrent.futures import ThreadPoolExecutor
from pathlib import Path
from subprocess import run as sp_run, PIPE
from sys import executable
from typing import Tuple, MutableMapping, Union
from discord.ext import commands
from core import Config
from core import data_manager
from redbot.core import Config
from redbot.core import data_manager
from .errors import *
from .installable import Installable, InstallableType
from .log import log
from .json_mixins import RepoJSONMixin
from .log import log
class Repo(RepoJSONMixin):

View File

@ -1,5 +1,5 @@
from redbot.core.bot import Red
from .economy import Economy
from core.bot import Red
def setup(bot: Red):

View File

@ -5,12 +5,14 @@ from collections import defaultdict, deque
from enum import Enum
import discord
from redbot.cogs.bank import check_global_setting_guildowner, check_global_setting_admin
from redbot.core import Config, bank
from redbot.core.i18n import CogI18n
from redbot.core.utils.chat_formatting import pagify, box
from discord.ext import commands
from core import checks, Config, bank
from core.utils.chat_formatting import pagify, box
from core.bot import Red
from cogs.bank import check_global_setting_guildowner, check_global_setting_admin
from core.i18n import CogI18n
from redbot.core.bot import Red
_ = CogI18n("Economy", __file__)

View File

@ -1,13 +1,15 @@
from discord.ext import commands
from core.utils.chat_formatting import escape, italics, pagify
from core.i18n import CogI18n
from random import randint, choice
from enum import Enum
from urllib.parse import quote_plus
import discord
import datetime
import time
from enum import Enum
from random import randint, choice
from urllib.parse import quote_plus
import aiohttp
import discord
from redbot.core.i18n import CogI18n
from discord.ext import commands
from redbot.core.utils.chat_formatting import escape, italics, pagify
_ = CogI18n("General", __file__)

View File

@ -1,9 +1,10 @@
from discord.ext import commands
from random import shuffle
import aiohttp
from core import checks, Config
from core.i18n import CogI18n
import aiohttp
from discord.ext import commands
from redbot.core.i18n import CogI18n
from redbot.core import checks, Config
_ = CogI18n("Image", __file__)

7
redbot/core/__init__.py Normal file
View File

@ -0,0 +1,7 @@
import pkg_resources
from .config import Config
__all__ = ["Config", "__version__"]
__version__ = version = pkg_resources.require("Red-DiscordBot")[0].version

View File

@ -1,10 +1,10 @@
import datetime
from typing import Union, List
import os
from typing import Union, List
import discord
from core import Config
from redbot.core import Config
__all__ = ["Account", "get_balance", "set_balance", "withdraw_credits", "deposit_credits",
"can_spend", "transfer_credits", "wipe_bank", "get_guild_accounts",

View File

@ -1,19 +1,17 @@
import asyncio
import os
from collections import Counter
from enum import Enum
from importlib.machinery import ModuleSpec
from pathlib import Path
import discord
from discord.ext import commands
from collections import Counter
from discord.ext.commands import GroupMixin
from pathlib import Path
from core import Config
from enum import Enum
import os
from core.cog_manager import CogManager
from core import i18n
from .cog_manager import CogManager
from . import Config
from . import i18n
class Red(commands.Bot):
@ -66,8 +64,7 @@ class Red(commands.Bot):
self.main_dir = bot_dir
self.cog_mgr = CogManager(paths=(str(self.main_dir / 'cogs'),),
bot_dir=self.main_dir)
self.cog_mgr = CogManager(paths=(str(self.main_dir / 'cogs'),))
super().__init__(**kwargs)

View File

@ -1,7 +1,7 @@
import argparse
import asyncio
from core.bot import Red
from redbot.core.bot import Red
def confirm(m=""):
@ -61,7 +61,7 @@ def ask_sentry(red: Red):
print("\nThank you for helping us with the development process!")
def parse_cli_flags():
def parse_cli_flags(args):
parser = argparse.ArgumentParser(description="Red - Discord Bot")
parser.add_argument("--owner", type=int,
help="ID of the owner. Only who hosts "
@ -102,11 +102,10 @@ def parse_cli_flags():
parser.add_argument("--dev",
action="store_true",
help="Enables developer mode")
parser.add_argument("config",
nargs='?',
help="Path to config generated on initial setup.")
parser.add_argument("instance_name",
help="Name of the bot instance created during `redbot-setup`.")
args = parser.parse_args()
args = parser.parse_args(args)
if args.prefix:
args.prefix = sorted(args.prefix, reverse=True)

View File

@ -1,15 +1,16 @@
import pkgutil
from importlib import invalidate_caches
from importlib.machinery import ModuleSpec
from typing import Tuple, Union, List
from pathlib import Path
from typing import Tuple, Union, List
from . import checks
from .config import Config
from .i18n import CogI18n
from .data_manager import cog_data_path
from discord.ext import commands
from core import checks
from core.config import Config
from core.utils.chat_formatting import box
from core.i18n import CogI18n
from .utils.chat_formatting import box
__all__ = ["CogManager"]
@ -20,11 +21,13 @@ class CogManager:
directory. You may also set a directory for downloader to install new cogs to, the default
being the :code:`cogs/` folder in the root bot directory.
"""
def __init__(self, paths: Tuple[str]=(), bot_dir: Path=Path.cwd()):
def __init__(self, paths: Tuple[str]=()):
self.conf = Config.get_conf(self, 2938473984732, True)
tmp_cog_install_path = cog_data_path(self) / "cogs"
tmp_cog_install_path.mkdir(parents=True, exist_ok=True)
self.conf.register_global(
paths=(),
install_path=str(bot_dir.resolve() / "cogs")
install_path=str(tmp_cog_install_path)
)
self._paths = list(paths)

View File

@ -1,14 +1,11 @@
import logging
from copy import deepcopy
from typing import Callable, Union, Tuple
import discord
from copy import deepcopy
from pathlib import Path
from .data_manager import cog_data_path, core_data_path
from .drivers.red_json import JSON as JSONDriver
from core.data_manager import cog_data_path, core_data_path
log = logging.getLogger("red.config")

View File

@ -1,16 +1,20 @@
import itertools
from discord.ext import commands
from core import checks
from core import i18n
from string import ascii_letters, digits
from random import SystemRandom
from collections import namedtuple
import logging
import importlib
import sys
import discord
import aiohttp
import asyncio
import importlib
import itertools
import logging
import sys
from collections import namedtuple
from random import SystemRandom
from string import ascii_letters, digits
import aiohttp
import discord
from discord.ext import commands
from redbot.core import checks
from redbot.core import i18n
import redbot.cogs # Don't remove this line or core cogs won't load
log = logging.getLogger("red")
@ -32,9 +36,14 @@ class Core:
try:
spec = await ctx.bot.cog_mgr.find_cog(cog_name)
except RuntimeError:
await ctx.send(_("No module by that name was found in any"
" cog path."))
return
real_name = ".{}".format(cog_name)
try:
mod = importlib.import_module(real_name, package='redbot.cogs')
except ImportError as e:
await ctx.send(_("No module by that name was found in any"
" cog path."))
return
spec = mod.__spec__
try:
ctx.bot.load_extension(spec)
@ -335,7 +344,8 @@ class Core:
# Since it can also be set through cli flags, bot.db is not a reliable
# source. So we'll just mock a DM message instead.
fake_message = namedtuple('Message', 'guild')
prefix = ctx.bot.command_prefix(ctx.bot, fake_message(guild=None))[0]
prefixes = await ctx.bot.command_prefix(ctx.bot, fake_message(guild=None))
prefix = prefixes[0]
content = _("Use `{}dm {} <text>` to reply to this user"
"").format(prefix, author.id)
@ -384,7 +394,8 @@ class Core:
e = discord.Embed(colour=discord.Colour.red(), description=message)
description = _("Owner of %s") % ctx.bot.user
fake_message = namedtuple('Message', 'guild')
prefix = ctx.bot.command_prefix(ctx.bot, fake_message(guild=None))[0]
prefixes = await ctx.bot.command_prefix(ctx.bot, fake_message(guild=None))
prefix = prefixes[0]
e.set_footer(text=_("You can reply to this message with %scontact"
"") % prefix)
if ctx.bot.user.avatar_url:

View File

@ -1,6 +1,9 @@
import sys
from pathlib import Path
from core.json_io import JsonIO
import appdirs
from .json_io import JsonIO
jsonio = None
basic_config = None
@ -11,13 +14,23 @@ basic_config_default = {
"CORE_PATH_APPEND": "core"
}
config_dir = Path(appdirs.AppDirs("Red-DiscordBot").user_config_dir)
config_file = config_dir / 'config.json'
def load_basic_configuration(path: Path):
def load_basic_configuration(instance_name: str):
global jsonio
global basic_config
jsonio = JsonIO(path)
basic_config = jsonio._load_json()
jsonio = JsonIO(config_file)
try:
config = jsonio._load_json()
basic_config = config[instance_name]
except (FileNotFoundError, KeyError):
print("You need to configure the bot instance using `redbot-setup`"
" prior to running the bot.")
sys.exit(1)
def _base_data_path() -> Path:

View File

@ -1,15 +1,16 @@
from discord.ext import commands
from core.utils.chat_formatting import box, pagify
from core import checks
from core.i18n import CogI18n
import asyncio
import discord
import traceback
import inspect
import textwrap
from contextlib import redirect_stdout
import io
import textwrap
import traceback
from contextlib import redirect_stdout
import discord
from . import checks
from .i18n import CogI18n
from discord.ext import commands
from .utils.chat_formatting import box, pagify
"""
Notice:

View File

@ -1,9 +1,9 @@
from pathlib import Path
from typing import Tuple
from core.drivers.red_base import BaseDriver
from core.json_io import JsonIO
from ..json_io import JsonIO
from pathlib import Path
from .red_base import BaseDriver
class JSON(BaseDriver):

View File

@ -1,10 +1,12 @@
import discord
import traceback
import datetime
import logging
import traceback
import discord
from .sentry_setup import should_log
from discord.ext import commands
from core.utils.chat_formatting import inline
from core.sentry_setup import should_log
from .utils.chat_formatting import inline
log = logging.getLogger("red")
sentry_log = logging.getLogger("red.sentry")

View File

View File

@ -1,9 +1,7 @@
from raven import Client, breadcrumbs
from raven.versioning import fetch_git_sha
from raven.conf import setup_logging
from raven.handlers.logging import SentryHandler
from pathlib import Path
from redbot.core import __version__
__all__ = ("init_sentry_logging", "should_log")
@ -27,12 +25,12 @@ include_paths = (
client = None
def init_sentry_logging(bot, logger):
def init_sentry_logging(logger):
global client
client = Client(
dsn=("https://27f3915ba0144725a53ea5a99c9ae6f3:87913fb5d0894251821dcf06e5e9cfe6@"
"sentry.telemetry.red/19?verify_ssl=0"),
release=fetch_git_sha(str(bot.main_dir))
release=__version__
)
breadcrumbs.ignore_logger("websockets")

View File

107
redbot/setup.py Normal file
View File

@ -0,0 +1,107 @@
#!/usr/bin/env python
import sys
from copy import deepcopy
from pathlib import Path
import appdirs
from redbot.core.json_io import JsonIO
from redbot.core.data_manager import basic_config_default
from redbot.core.cli import confirm
appdir = appdirs.AppDirs("Red-DiscordBot")
config_dir = Path(appdir.user_config_dir)
config_dir.mkdir(parents=True, exist_ok=True)
config_file = config_dir / 'config.json'
def load_existing_config():
if not config_file.exists():
return {}
return JsonIO(config_file)._load_json()
def save_config(name, data):
config = load_existing_config()
config[name] = data
JsonIO(config_file)._save_json(config)
def basic_setup():
"""
Creates the data storage folder.
:return:
"""
default_data_dir = Path(appdir.user_data_dir)
print("Hello! Before we begin the full configuration process we need to"
" gather some initial information about where you'd like us"
" to store your bot's data. We've attempted to figure out a"
" sane default data location which is printed below. If you don't"
" want to change this default please press [ENTER], otherwise"
" input your desired data location.")
print()
print("Default: {}".format(default_data_dir))
new_path = input('> ')
if new_path != '':
new_path = Path(new_path)
default_data_dir = new_path
if not default_data_dir.exists():
try:
default_data_dir.mkdir(parents=True, exist_ok=True)
except OSError:
print("We were unable to create your chosen directory."
" You may need to restart this process with admin"
" privileges.")
sys.exit(1)
print("You have chosen {} to be your data directory."
"".format(default_data_dir))
if not confirm("Please confirm (y/n):"):
print("Please start the process over.")
sys.exit(0)
default_dirs = deepcopy(basic_config_default)
default_dirs['DATA_PATH'] = str(default_data_dir.resolve())
storage_dict = {
1: "JSON",
2: "MongoDB"
}
storage = None
while storage is None:
print()
print("Please choose your storage backend (if you're unsure, choose 1).")
print("1. JSON (file storage, requires no database).")
print("2. MongoDB")
storage = input("> ")
try:
storage = int(storage)
except ValueError:
storage = None
else:
if storage not in storage_dict:
storage = None
default_dirs['STORAGE_TYPE'] = storage_dict[storage]
name = ""
while len(name) == 0:
print()
print("Please enter a name for your instance, this name cannot include spaces"
" and it will be used to run your bot from here on out.")
name = input("> ")
if " " in name:
name = ""
save_config(name, default_dirs)
print()
print("Your basic configuration has been saved. Please run `redbot <name>` to"
" continue your setup process and to run the bot.")

View File

@ -1,6 +1,4 @@
git+https://github.com/Rapptz/discord.py@rewrite#egg=discord.py[voice]
appdirs
discord.py>=1.0.0a0
youtube_dl
pytest
git+https://github.com/pytest-dev/pytest-asyncio
pymongo
git+https://github.com/getsentry/raven-python
raven

2
setup.cfg Normal file
View File

@ -0,0 +1,2 @@
[metadata]
long_description = file: README.rst

111
setup.py Normal file
View File

@ -0,0 +1,111 @@
from distutils.core import setup
from pathlib import Path
from subprocess import run, PIPE
from setuptools import find_packages
def get_package_list():
core = find_packages(include=['redbot', 'redbot.*'])
return core
def get_requirements():
with open('requirements.txt') as f:
requirements = f.read().splitlines()
return requirements
def get_version():
try:
p = run(
"git describe --abbrev=0 --tags".split(),
stdout=PIPE
)
except FileNotFoundError:
# No git
return 3, 0, 0
if p.returncode != 0:
return 3, 0, 0
stdout = p.stdout.strip().decode()
if stdout.startswith("v"):
numbers = stdout[1:].split('.')
args = [0, 0, 0]
for i in range(3):
try:
args[i] = int(numbers[i])
except (IndexError, ValueError):
args[i] = 0
return args
return 3, 0, 0
def find_locale_folders():
"""
Ignore this tomfoolery in the desire for automation. It works, that's
all you gotta know. Don't fuck with this unless you really know what
you're doing, otherwise we lose all translations.
"""
def glob_locale_files(path: Path):
msgs = path.glob("*.po")
parents = path.parents
return [str(m.relative_to(parents[0])) for m in msgs]
ret = {
'redbot.core': glob_locale_files(Path('redbot/core/locales'))
}
cogs_path = Path('redbot/cogs')
for cog_folder in cogs_path.iterdir():
locales_folder = cog_folder / 'locales'
if not locales_folder.is_dir():
continue
pkg_name = str(cog_folder).replace('/', '.')
ret[pkg_name] = glob_locale_files(locales_folder)
return ret
setup(
name='Red-DiscordBot',
version="{}.{}.{}a13".format(*get_version()),
packages=get_package_list(),
package_data=find_locale_folders(),
url='https://github.com/Cog-Creators/Red-DiscordBot',
license='GPLv3',
author='Cog-Creators',
author_email='',
description='A highly customizable Discord bot',
classifiers=[
'Development Status :: 4 - Beta',
'Framework :: AsyncIO',
'Intended Audience :: Developers',
'License :: OSI Approved :: GNU General Public License v3 or later (GPLv3+)',
'Operating System :: OS Independent',
'Programming Language :: Python :: 3.5',
'Programming Language :: Python :: 3.6',
'Topic :: Communications :: Chat',
'Topic :: Documentation :: Sphinx'
],
entry_points={
'console_scripts': [
'redbot=redbot.__main__:main',
'redbot-setup=redbot.setup:basic_setup']
},
python_requires='>=3.5',
setup_requires=get_requirements(),
install_requires=get_requirements(),
dependency_links=[
'https://github.com/Rapptz/discord.py/tarball/rewrite#egg=discord.py-1.0'
],
extras_require={
'test': ['pytest>=3', 'pytest-asyncio'],
'mongo': ['pymongo', 'motor'],
'docs': ['sphinx', 'sphinxcontrib-asyncio', 'sphinx_rtd_theme']
}
)

View File

@ -1,9 +1,10 @@
from collections import namedtuple
from raven.versioning import fetch_git_sha
from pathlib import Path
import pytest
from cogs.downloader.repo_manager import RepoManager, Repo
from pathlib import Path
from raven.versioning import fetch_git_sha
from redbot.cogs.downloader.repo_manager import RepoManager, Repo
async def fake_run(*args, **kwargs):
@ -37,8 +38,6 @@ def repo_manager(tmpdir_factory, config):
@pytest.fixture
def repo(tmpdir):
from cogs.downloader.repo_manager import Repo
repo_folder = Path(str(tmpdir)) / 'repos' / 'squid'
repo_folder.mkdir(parents=True, exist_ok=True)
@ -69,8 +68,6 @@ def bot_repo(event_loop):
def test_existing_git_repo(tmpdir):
from cogs.downloader.repo_manager import Repo
repo_folder = Path(str(tmpdir)) / 'repos' / 'squid' / '.git'
repo_folder.mkdir(parents=True, exist_ok=True)
@ -103,7 +100,7 @@ async def test_clone_repo(repo_norun, capsys):
@pytest.mark.asyncio
async def test_add_repo(monkeypatch, repo_manager):
monkeypatch.setattr("cogs.downloader.repo_manager.Repo._run",
monkeypatch.setattr("redbot.cogs.downloader.repo_manager.Repo._run",
fake_run_noprint)
squid = await repo_manager.add_repo(

View File

@ -1,9 +1,10 @@
import pytest
import json
from cogs.downloader.installable import Installable, InstallableType
from pathlib import Path
import pytest
from redbot.cogs.downloader.installable import Installable, InstallableType
INFO_JSON = {
"author": (
"tekulvw",

View File

@ -1,12 +1,13 @@
from cogs.alias import Alias
import pytest
from redbot.cogs.alias import Alias
@pytest.fixture()
def alias(config):
import cogs.alias.alias
import redbot.cogs.alias.alias
cogs.alias.alias.Config.get_conf = lambda *args, **kwargs: config
redbot.cogs.alias.alias.Config.get_conf = lambda *args, **kwargs: config
return Alias(None)

View File

@ -3,10 +3,10 @@ import pytest
@pytest.fixture()
def bank(config):
from core import Config
from redbot.core import Config
Config.get_conf = lambda *args, **kwargs: config
from core import bank
from redbot.core import bank
bank._register_defaults()
return bank

View File

@ -1,13 +1,13 @@
import random
from collections import namedtuple
from pathlib import Path
import pytest
import random
from core.bot import Red
from _pytest.monkeypatch import MonkeyPatch
from core.drivers import red_json
from core import Config
from redbot.core import Config
from redbot.core.bot import Red
from redbot.core.drivers import red_json
@pytest.fixture(scope="session")
@ -19,7 +19,7 @@ def monkeysession(request):
@pytest.fixture(autouse=True)
def override_data_path(tmpdir):
from core import data_manager
from redbot.core import data_manager
data_manager.basic_config = data_manager.basic_config_default
data_manager.basic_config['DATA_PATH'] = str(tmpdir)
@ -145,8 +145,8 @@ def ctx(empty_member, empty_channel, red):
#region Red Mock
@pytest.fixture()
def red(config_fr):
from core.cli import parse_cli_flags
cli_flags = parse_cli_flags()
from redbot.core.cli import parse_cli_flags
cli_flags = parse_cli_flags(["ignore_me"])
description = "Red v3 - Alpha"

View File

@ -1,7 +1,8 @@
from pathlib import Path
import pytest
from core import cog_manager
from redbot.core import cog_manager
@pytest.fixture()
@ -14,9 +15,10 @@ def default_dir(red):
return red.main_dir
@pytest.mark.skip
@pytest.mark.asyncio
async def test_ensure_cogs_in_paths(cog_mgr, default_dir):
cogs_dir = default_dir / 'cogs'
cogs_dir = default_dir / 'redbot' / 'cogs'
assert cogs_dir in await cog_mgr.paths()

View File

@ -1,9 +1,10 @@
import json
from pathlib import Path
from core import data_manager
import pytest
from redbot.core import data_manager
@pytest.fixture(autouse=True)
def cleanup_datamanager():
@ -32,6 +33,7 @@ def test_no_basic(cog_instance):
data_manager.cog_data_path(cog_instance)
@pytest.mark.skip
def test_core_path(data_mgr_config, tmpdir):
conf_path = tmpdir.join('config.json')
conf_path.write(json.dumps(data_mgr_config))

View File

@ -1,10 +1,11 @@
from core import sentry_setup
import logging
from redbot.core import sentry_setup
def test_sentry_capture(red):
log = logging.getLogger(__name__)
sentry_setup.init_sentry_logging(red, log)
sentry_setup.init_sentry_logging(log)
assert sentry_setup.client is not None

View File

@ -1,6 +1,6 @@
import core
from redbot import core
def test_version_working():
assert hasattr(core, '__version__')
assert core.__version__ >= (3, 0, 0)
assert core.__version__[0] == "3"