import pytest

from wcs.formdef import FormDef

from utilities import create_temporary_pub, clean_temporary_pub

def pytest_generate_tests(metafunc):
    if 'pub' in metafunc.fixturenames:
        metafunc.parametrize('pub', ['pickle', 'sql'], indirect=True)

@pytest.fixture
def pub(request):
    return create_temporary_pub(sql_mode=(request.param == 'sql'))

def teardown_module(module):
    clean_temporary_pub()

def test_tracking_code(pub):
    klass = pub.tracking_code_class
    klass.wipe()

    code = klass()
    code.store()
    code = klass()
    code.store()
    assert klass.count() == 2

    FormDef.wipe()
    formdef = FormDef()
    formdef.name = 'foobar'
    formdef.fields = []
    formdef.store()
    formdata = formdef.data_class()()
    formdata.store()

    code = klass.get(code.id)
    code.formdef = formdef
    code.formdata = formdata
    assert code.formdef_id == str(formdef.id)
    assert code.formdata_id == str(formdata.id)
    code.store()
    assert klass.count() == 2

    assert klass.get(code.id).formdef_id == code.formdef_id
    assert klass.get(code.id).formdata_id == code.formdata_id

    assert klass.get(code.id).formdata.tracking_code == code.id

def test_tracking_code_duplicate(pub):
    klass = pub.tracking_code_class
    klass.wipe()

    code = klass()
    code.store()
    code_id = code.id

    code = klass()
    real_get_new_id = klass.get_new_id

    marker = {}

    def fake_get_new_id(cls):
        if not hasattr(cls, 'cnt'):
            cls.cnt = 0
        cls.cnt += 1
        if cls.cnt < 5:
            return code_id
        else:
            marker['done'] = True
            return real_get_new_id(cls)
    klass.get_new_id = fake_get_new_id
    code.store()
    klass.get_new_id = real_get_new_id

    assert marker.get('done') # makes sure we got to the real new id code
    assert klass.count() == 2
