Repository: mondeja/mkdocs-include-markdown-plugin (python)

Issue:
Having several start-end tags in included page
Having several start-end tags in included page, results in including only the first appearance.

Is it possible to have more than one section included?

```markdown
<!--start-tag-->
## Important Content1
<!--end-tag-->

[unimportant content]

<!--start-tag-->
## Important Content2
<!--end-tag-->

```

Pull request description:
Allow to include from different parts of the same page
Using the same `start` and `end` arguments, allow to include multiple times from the same page. Closes #50 

Patch:
diff --git a/.bumpversion.cfg b/.bumpversion.cfg
index 33c175b..4a3b4f0 100644
--- a/.bumpversion.cfg
+++ b/.bumpversion.cfg
@@ -1,5 +1,5 @@
 [bumpversion]
-current_version = 3.0.1
+current_version = 3.1.0
 
 [bumpversion:file:mkdocs_include_markdown_plugin/__init__.py]
 
diff --git a/mkdocs_include_markdown_plugin/__init__.py b/mkdocs_include_markdown_plugin/__init__.py
index d559504..2245b6c 100644
--- a/mkdocs_include_markdown_plugin/__init__.py
+++ b/mkdocs_include_markdown_plugin/__init__.py
@@ -1,2 +1,2 @@
 __title__ = 'mkdocs_include_markdown_plugin'
-__version__ = '3.0.1'
+__version__ = '3.1.0'
diff --git a/mkdocs_include_markdown_plugin/event.py b/mkdocs_include_markdown_plugin/event.py
index f5b08d8..18ad096 100644
--- a/mkdocs_include_markdown_plugin/event.py
+++ b/mkdocs_include_markdown_plugin/event.py
@@ -100,14 +100,13 @@ def get_file_content(markdown, abs_src_path):
 
         #   string options
         start_match = re.search(ARGUMENT_REGEXES['start'], arguments_string)
-        if start_match is not None:
-            start = process.interpret_escapes(start_match.group(1))
-            _, _, text_to_include = text_to_include.partition(start)
-
         end_match = re.search(ARGUMENT_REGEXES['end'], arguments_string)
-        if end_match is not None:
-            end = process.interpret_escapes(end_match.group(1))
-            text_to_include, _, _ = text_to_include.partition(end)
+
+        text_to_include, _, _ = process.filter_inclusions(
+            start_match,
+            end_match,
+            text_to_include,
+        )
 
         # nested includes
         new_text_to_include = get_file_content(text_to_include, file_path_abs)
@@ -185,16 +184,13 @@ def get_file_content(markdown, abs_src_path):
 
         #   string options
         start_match = re.search(ARGUMENT_REGEXES['start'], arguments_string)
-        start = None
-        if start_match is not None:
-            start = process.interpret_escapes(start_match.group(1))
-            _, _, text_to_include = text_to_include.partition(start)
-
         end_match = re.search(ARGUMENT_REGEXES['end'], arguments_string)
-        end = None
-        if end_match is not None:
-            end = process.interpret_escapes(end_match.group(1))
-            text_to_include, _, _ = text_to_include.partition(end)
+
+        text_to_include, start, end = process.filter_inclusions(
+            start_match,
+            end_match,
+            text_to_include,
+        )
 
         # relative URLs rewriting
         if bool_options['rewrite-relative-urls']['value']:
diff --git a/mkdocs_include_markdown_plugin/process.py b/mkdocs_include_markdown_plugin/process.py
index 6dcccb2..4aa7be7 100644
--- a/mkdocs_include_markdown_plugin/process.py
+++ b/mkdocs_include_markdown_plugin/process.py
@@ -157,6 +157,33 @@ def interpret_escapes(value: str) -> str:
     return value.encode('latin-1', 'backslashreplace').decode('unicode_escape')
 
 
+def filter_inclusions(start_match, end_match, text_to_include):
+    """Manages inclusions from files using ``start`` and ``end`` diective
+    arguments.
+    """
+    start = None
+    end = None
+    if start_match is not None:
+        start = interpret_escapes(start_match.group(1))
+        if end_match is not None:
+            end = interpret_escapes(end_match.group(1))
+        new_text_to_include = ''
+        if end_match is not None:
+            for start_text in text_to_include.split(start)[1:]:
+                for i, end_text in enumerate(start_text.split(end)):
+                    if not i % 2:
+                        new_text_to_include += end_text
+        else:
+            new_text_to_include = text_to_include.split(start)[1]
+        if new_text_to_include:
+            text_to_include = new_text_to_include
+    elif end_match is not None:
+        end = interpret_escapes(end_match.group(1))
+        text_to_include, _, _ = text_to_include.partition(end)
+
+    return (text_to_include, start, end)
+
+
 def increase_headings_offset(markdown, offset=0):
     '''Increases the headings depth of a snippet of Makdown content.'''
     _inside_fenced_codeblock = False
diff --git a/setup.cfg b/setup.cfg
index 9ced3bb..203372c 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -1,6 +1,6 @@
 [metadata]
 name = mkdocs_include_markdown_plugin
-version = 3.0.1
+version = 3.1.0
 description = Mkdocs Markdown includer plugin.
 long_description = file: README.md
 long_description_content_type = text/markdown


Test patch:
diff --git a/tests/test_include.py b/tests/test_include.py
index 74c3507..df8bcfc 100644
--- a/tests/test_include.py
+++ b/tests/test_include.py
@@ -92,6 +92,46 @@ This must be included.
             id='start/end (unescaped special characters)',
         ),
 
+        # Multiples start and end matchs
+        pytest.param(
+            '''{%
+  include-markdown "{filepath}"
+  start="<!--start-tag-->"
+  end="<!--end-tag-->"
+  comments=false
+%}''',
+            '''Some text
+
+<!--start-tag-->
+This should be included.
+<!--end-tag-->
+
+This shouldn't be included.
+
+<!--start-tag-->
+This should be included also.
+<!--end-tag-->
+
+Here some text
+that should be ignored.
+
+<!--start-->
+<!--end-->
+
+Etc
+<!--start-tag-->
+This should be included even if hasn't defined after end tag.
+''',
+            '''
+This should be included.
+
+This should be included also.
+
+This should be included even if hasn't defined after end tag.
+''',
+            id='multiple-start-end-matchs',
+        ),
+
         # Preserve included indent
         pytest.param(
             '''1. Ordered list item
diff --git a/tests/test_include_markdown.py b/tests/test_include_markdown.py
index 67b8d9a..1968d8d 100644
--- a/tests/test_include_markdown.py
+++ b/tests/test_include_markdown.py
@@ -160,6 +160,46 @@ This must be included.
             id='comments=false',
         ),
 
+        # Multiples start and end matchs
+        pytest.param(
+            '''{%
+  include-markdown "{filepath}"
+  start="<!--start-tag-->"
+  end="<!--end-tag-->"
+  comments=false
+%}''',
+            '''Some text
+
+<!--start-tag-->
+This should be included.
+<!--end-tag-->
+
+This shouldn't be included.
+
+<!--start-tag-->
+This should be included also.
+<!--end-tag-->
+
+Here some text
+that should be ignored.
+
+<!--start-->
+<!--end-->
+
+Etc
+<!--start-tag-->
+This should be included even if hasn't defined after end tag.
+''',
+            '''
+This should be included.
+
+This should be included also.
+
+This should be included even if hasn't defined after end tag.
+''',
+            id='multiple-start-end-matchs',
+        ),
+
         # Don't preserve included indent
         pytest.param(
             '''1. Ordered list item