#!/usr/bin/env qore
# -*- mode: qore; indent-tabs-mode: nil -*-

%new-style
%enable-all-warnings
%require-types
%strict-args

%requires ../../../../../qlib/Util.qm
%requires ../../../../../qlib/QUnit.qm

%exec-class ModuleTest

class ModuleTest inherits QUnit::Test {
    constructor() : QUnit::Test("Modules test", "1.0") {
        addTestCase("dep load test", \depLoadTest());
        addTestCase("warning test", \warningTest());
        addTestCase("Test modules", \testModules());
        addTestCase("Side effect test", \sideEffectTest());

        our ModuleTest mt = self;

        set_return_value(main());
    }

    depLoadTest() {
        Program p(PO_NEW_STYLE);
        p.disableParseOptions(PO_NO_TOP_LEVEL_STATEMENTS);
        #p.setScriptPath(get_script_path());
        p.importGlobalVariable("mt");
        p.parse("%requires " + normalize_dir(get_script_dir()) + "/ModuleDepLoad_0.qm
Child c();
mt.assertEq(1, c.get());
", "p");
        p.run();
    }

    warningTest() {
        Program p();
        p.setScriptPath(get_script_path());
        assertThrows("DEPRECATED", \p.loadModule(), ("./Issue3212.qm", WARN_MODULES | WARN_DEPRECATED));
        p.loadModule("./Issue3212.qm");
        p.parse("int sub test0() { return test(); } int sub test1() { return deprecated_test(); }", "");
        assertEq(1, p.callFunction("test0"));
        assertEq(1, p.callFunction("test1"));
    }

    testModules() {
        Program p(PO_NEW_STYLE);
        p.disableParseOptions(PO_NO_TOP_LEVEL_STATEMENTS);
        p.setScriptPath(get_script_path());
        p.importGlobalVariable("mt");
        p.parse("
%requires ./C.qm
mt.assertEq(1, AC, \"AC\");
mt.assertEq(1, BC, \"BC\");
", "p");
        p.run();
    }

    sideEffectTest() {
        Program p(PO_NEW_STYLE);
        p.setScriptPath(get_script_path());
        assertThrows("PARSE-EXCEPTION", "parse options do not allow access", \p.parse(), ("%requires ./SideEffect.qm", ""));
    }
}
