From d619f4a0129d1fdd97b2e00d556b0b3db06f73cb Mon Sep 17 00:00:00 2001 From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com> Date: Thu, 13 Oct 2022 23:48:52 +0200 Subject: [PATCH] Add test coverage of splitter function in project tree --- tests/test_core/test_core_doctools.py | 4 +- tests/test_dialogs/test_dlg_docsplit.py | 45 ++++----- tests/test_gui/test_gui_projtree.py | 121 +++++++++++++++++++++++- 3 files changed, 139 insertions(+), 31 deletions(-) diff --git a/tests/test_core/test_core_doctools.py b/tests/test_core/test_core_doctools.py index bcff60ce..ab55aef4 100644 --- a/tests/test_core/test_core_doctools.py +++ b/tests/test_core/test_core_doctools.py @@ -27,9 +27,7 @@ from shutil import copyfile from mock import causeOSError from tools import C, buildTestProject, cmpFiles -from novelwriter.core.project import NWProject -from novelwriter.core.doctools import DocMerger, DocSplitter -from novelwriter.core.document import NWDoc +from novelwriter.core import NWProject, DocMerger, DocSplitter, NWDoc @pytest.mark.core diff --git a/tests/test_dialogs/test_dlg_docsplit.py b/tests/test_dialogs/test_dlg_docsplit.py index b95d497c..84b65a51 100644 --- a/tests/test_dialogs/test_dlg_docsplit.py +++ b/tests/test_dialogs/test_dlg_docsplit.py @@ -45,22 +45,17 @@ def testDlgSplit_Main(qtbot, monkeypatch, nwGUI, fncProj, mockRnd): docText = ( "Text\n\n" - "##! Prologue\n\n" - "Text\n\n" - "## Chapter One\n\n" - "### Scene One\n\n" - "Text\n\n" - "### Scene Two\n\n" - "Text\n\n" - "## Chapter Two\n\n" - "### Scene Three\n\n" - "Text\n\n" - "### Scene Four\n\n" - "Text\n\n" - "#! New Title\n\n" - "## New Chapter\n\n" - "### New Scene\n\n" - "#### New Section\n\n" + "##! Prologue\n\nText\n\n" + "## Chapter One\n\nText\n\n" + "### Scene One\n\nText\n\n" + "### Scene Two\n\nText\n\n" + "## Chapter Two\n\nText\n\n" + "### Scene Three\n\nText\n\n" + "### Scene Four\n\nText\n\n" + "#! New Title\n\nText\n\n" + "## New Chapter\n\nText\n\n" + "### New Scene\n\nText\n\n" + "#### New Section\n\nText\n\n" ) hSplitDoc = theProject.newFile("Split Doc", C.hNovelRoot) @@ -90,15 +85,15 @@ def testDlgSplit_Main(qtbot, monkeypatch, nwGUI, fncProj, mockRnd): assert data["headerList"][0] == (0, 1, "Split Doc") assert data["headerList"][1] == (4, 2, "Prologue") assert data["headerList"][2] == (8, 2, "Chapter One") - assert data["headerList"][3] == (10, 3, "Scene One") - assert data["headerList"][4] == (14, 3, "Scene Two") - assert data["headerList"][5] == (18, 2, "Chapter Two") - assert data["headerList"][6] == (20, 3, "Scene Three") - assert data["headerList"][7] == (24, 3, "Scene Four") - assert data["headerList"][8] == (28, 1, "New Title") - assert data["headerList"][9] == (30, 2, "New Chapter") - assert data["headerList"][10] == (32, 3, "New Scene") - assert data["headerList"][11] == (34, 4, "New Section") + assert data["headerList"][3] == (12, 3, "Scene One") + assert data["headerList"][4] == (16, 3, "Scene Two") + assert data["headerList"][5] == (20, 2, "Chapter Two") + assert data["headerList"][6] == (24, 3, "Scene Three") + assert data["headerList"][7] == (28, 3, "Scene Four") + assert data["headerList"][8] == (32, 1, "New Title") + assert data["headerList"][9] == (36, 2, "New Chapter") + assert data["headerList"][10] == (40, 3, "New Scene") + assert data["headerList"][11] == (44, 4, "New Section") # Loading the dialog on a non-file item produces an empty list nwSplit._loadContent(C.hNovelRoot) diff --git a/tests/test_gui/test_gui_projtree.py b/tests/test_gui/test_gui_projtree.py index 8e683742..82119f41 100644 --- a/tests/test_gui/test_gui_projtree.py +++ b/tests/test_gui/test_gui_projtree.py @@ -30,7 +30,7 @@ from PyQt5.QtWidgets import QMessageBox, QMenu, QTreeWidgetItem, QDialog from novelwriter.enum import nwItemLayout, nwItemType, nwItemClass from novelwriter.core import NWDoc -from novelwriter.dialogs import GuiEditLabel, GuiDocMerge +from novelwriter.dialogs import GuiEditLabel, GuiDocMerge, GuiDocSplit from novelwriter.gui.projtree import GuiProjectTree @@ -675,7 +675,7 @@ def testGuiProjTree_ContextMenu(qtbot, monkeypatch, nwGUI, fncDir, mockRnd): @pytest.mark.gui -def testGuiProjTree_MergeDocument(qtbot, monkeypatch, nwGUI, fncDir, mockRnd, ipsumText): +def testGuiProjTree_MergeDocuments(qtbot, monkeypatch, nwGUI, fncDir, mockRnd, ipsumText): """Test the merge document function. """ mergeData = {} @@ -780,7 +780,122 @@ def testGuiProjTree_MergeDocument(qtbot, monkeypatch, nwGUI, fncDir, mockRnd, ip # qtbot.stop() -# END Test testGuiProjTree_MergeDocument +# END Test testGuiProjTree_MergeDocuments + + +@pytest.mark.gui +def testGuiProjTree_SplitDocument(qtbot, monkeypatch, nwGUI, fncDir, mockRnd, ipsumText): + """Test the split document function. + """ + splitData = {} + splitText = [] + + # Block message box + monkeypatch.setattr(QMessageBox, "warning", lambda *a: QMessageBox.Yes) + monkeypatch.setattr(QMessageBox, "critical", lambda *a: QMessageBox.Yes) + monkeypatch.setattr(QMessageBox, "question", lambda *a: QMessageBox.Yes) + monkeypatch.setattr(QMessageBox, "information", lambda *a: QMessageBox.Yes) + + monkeypatch.setattr(GuiDocSplit, "__init__", lambda *a: None) + monkeypatch.setattr(GuiDocSplit, "exec_", lambda *a: None) + monkeypatch.setattr(GuiDocSplit, "result", lambda *a: QDialog.Accepted) + monkeypatch.setattr(GuiDocSplit, "getData", lambda *a: (splitData, splitText)) + + # Create a project + prjDir = os.path.join(fncDir, "project") + buildTestProject(nwGUI, prjDir) + + theProject = nwGUI.theProject + projTree = nwGUI.projView.projTree + + docText = ( + "Text\n\n" + "##! Prologue\n\nText\n\n" + "## Chapter One\n\nText\n\n" + "### Scene One\n\nText\n\n" + "### Scene Two\n\nText\n\n" + "## Chapter Two\n\nText\n\n" + "### Scene Three\n\nText\n\n" + "### Scene Four\n\nText\n\n" + "#! New Title\n\nText\n\n" + "## New Chapter\n\nText\n\n" + "### New Scene\n\nText\n\n" + "#### New Section\n\nText\n\n" + ) + + hSplitDoc = theProject.newFile("Split Doc", C.hNovelRoot) + theProject.writeNewFile(hSplitDoc, 1, True, docText) + projTree.revealNewTreeItem(hSplitDoc, nHandle=C.hNovelRoot, wordCount=True) + + docText = f"# Split Doc\n\n{docText}" + splitData["headerList"] = [ + (0, 1, "Split Doc"), + (4, 2, "Prologue"), + (8, 2, "Chapter One"), + (12, 3, "Scene One"), + (16, 3, "Scene Two"), + (20, 2, "Chapter Two"), + (24, 3, "Scene Three"), + (28, 3, "Scene Four"), + (32, 1, "New Title"), + (36, 2, "New Chapter"), + (40, 3, "New Scene"), + (44, 4, "New Section"), + ] + + fstSet = [ + "0000000000011", "0000000000012", "0000000000013", "0000000000014", + "0000000000015", "0000000000016", "0000000000017", "0000000000018", + "0000000000019", "000000000001a", "000000000001b", "000000000001c", + ] + sndSet = [ + "000000000001d", "000000000001e", "000000000001f", "0000000000020", + "0000000000021", "0000000000022", "0000000000023", "0000000000024", + "0000000000025", "0000000000026", "0000000000027", "0000000000028", + ] + trdSet = [ + "000000000002a", "000000000002b", "000000000002c", "000000000002d", + "000000000002e", "000000000002f", "0000000000030", "0000000000031", + "0000000000032", "0000000000033", "0000000000034", "0000000000035", + ] + + # Try to split an invalid document and a non-document + assert projTree._splitDocument(C.hInvalid) is False + assert projTree._splitDocument(C.hNovelRoot) is False + + # Split into same root folder + splitData["intoFolder"] = False + + # Writing fails + with monkeypatch.context() as mp: + mp.setattr("builtins.open", causeOSError) + assert projTree._splitDocument(hSplitDoc) is True + for tHandle in fstSet: + assert tHandle in theProject.tree + assert not os.path.isfile(os.path.join(prjDir, "content", f"{tHandle}.nwd")) + + # Writing succeeds + assert projTree._splitDocument(hSplitDoc) is True + for tHandle in sndSet: + assert tHandle in theProject.tree + assert os.path.isfile(os.path.join(prjDir, "content", f"{tHandle}.nwd")) + + # Add to a folder + splitData["intoFolder"] = True + assert projTree._splitDocument(hSplitDoc) is True + assert "0000000000029" in theProject.tree # The folder + for tHandle in trdSet: + assert tHandle in theProject.tree + assert os.path.isfile(os.path.join(prjDir, "content", f"{tHandle}.nwd")) + + # Cancelled by user + with monkeypatch.context() as mp: + mp.setattr(GuiDocSplit, "result", lambda *a: QDialog.Rejected) + assert projTree._splitDocument(hSplitDoc) is False + + # qtbot.stop() + +# END Test testGuiProjTree_SplitDocument @pytest.mark.gui