# note about virtual events: sometimes running any_widget.update()
# before generating a virtual event is needed for the virtual event to
# actually do something, if you have weird problems with tests try
# adding any_widget.update() calls
# see also update(3tcl)

import atexit
import pathlib
import shutil
import tempfile
import tkinter

import pytest

import porcupine
from porcupine import (dirs, get_main_window, get_tab_manager, tabs,
                       pluginloader, plugins)
from porcupine import filetypes as filetypes_module


# this url is split on 2 lines because pep8, concatenate the lines when
# copy/pasting it to your browser:
#
#    https://docs.pytest.org/en/latest/example/simple.html#dynamically-adding-c
#    ommand-line-options
#
# use 'pytest --test-pastebins' to run tests that send stuff to pastebins, it's
# disabled by default because pastebins might block you for using them
# repeatedly too fast
def pytest_addoption(parser):
    parser.addoption(
        '--test-pastebins', action='store_true', default=False,
        help="run tests that invoke online pastebins")


def pytest_collection_modifyitems(config, items):
    if config.getoption("--test-pastebins"):
        # --test-pastebins given in cli: do not skip pastebin tests
        return
    skip_pastebins = pytest.mark.skip(reason="need --test-pastebins to run")
    for item in items:
        if "pastebin_test" in item.keywords:
            item.add_marker(skip_pastebins)


# works with this:  from porcupine import dirs
# does NOT work:    from porcupine.dirs import configdir
@pytest.fixture(scope='session')
def monkeypatch_dirs():
    # avoid errors from user's custom plugins
    user_plugindir = plugins.__path__.pop(0)
    assert user_plugindir == str(dirs.configdir / 'plugins')

    with tempfile.TemporaryDirectory() as d:
        dirs.cachedir = pathlib.Path(d) / 'cache'
        dirs.configdir = pathlib.Path(d) / 'config'
        yield


@pytest.fixture(scope='session')
def porcusession(monkeypatch_dirs):
    # these errors should not occur after the init
    with pytest.raises(RuntimeError):
        get_main_window()

    with pytest.raises(RuntimeError):
        get_tab_manager()

    porcupine.init()
    porcupine.get_main_window().withdraw()

    plugin_names = pluginloader.find_plugins()
    pluginloader.load(plugin_names, shuffle=True)

    yield

    # avoid "Do you want to save" dialogs
    for tab in list(porcupine.get_tab_manager().tabs()):
        porcupine.get_tab_manager().close_tab(tab)

    porcupine.quit()


# TODO: can this be deleted safely?
@pytest.fixture(scope='session')
def filetypes(porcusession):
    return filetypes_module


@pytest.fixture
def tabmanager(porcusession):
    assert not get_tab_manager().tabs(), "something hasn't cleaned up its tabs"
    yield get_tab_manager()
    assert not get_tab_manager().tabs(), "the test didn't clean up its tabs"


@pytest.fixture
def filetab(porcusession, tabmanager):
    tab = tabs.FileTab(tabmanager)
    tabmanager.add_tab(tab)
    yield tab
    tabmanager.close_tab(tab)

@@ -2221,35 +2221,42 @@
     
-porcupine.get_
+# can't hide the 
 main
-_
+ 
 window
-()
+ with 
 .wit
@@ -2262,16 +2262,73 @@
 thdraw()
+%0A    # doing that makes events not happen for some reason
 %0A%0A    pl
@@ -2886,34 +2886,34 @@
 nager()%0A    
-assert not
+for tab in
  get_tab_man
@@ -2929,45 +2929,50 @@
 bs()
-, %22the test didn't clean up its tabs%22
+:%0A        get_tab_manager().close_tab(tab)
 %0A%0A%0A@
@@ -3096,44 +3096,15 @@
     
-yield tab%0A    tabmanager.close_tab(tab)
+return tab
 %0A

test fixes