django-fast-treenode 1.1.3__py3-none-any.whl → 2.0.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. {django_fast_treenode-1.1.3.dist-info → django_fast_treenode-2.0.0.dist-info}/METADATA +156 -46
  2. django_fast_treenode-2.0.0.dist-info/RECORD +41 -0
  3. {django_fast_treenode-1.1.3.dist-info → django_fast_treenode-2.0.0.dist-info}/WHEEL +1 -1
  4. treenode/__init__.py +0 -7
  5. treenode/admin.py +327 -82
  6. treenode/apps.py +20 -3
  7. treenode/cache.py +231 -0
  8. treenode/docs/Documentation +130 -54
  9. treenode/forms.py +75 -19
  10. treenode/managers.py +260 -48
  11. treenode/models/__init__.py +7 -0
  12. treenode/models/classproperty.py +24 -0
  13. treenode/models/closure.py +168 -0
  14. treenode/models/factory.py +71 -0
  15. treenode/models/proxy.py +650 -0
  16. treenode/static/treenode/css/tree_widget.css +62 -0
  17. treenode/static/treenode/css/treenode_admin.css +106 -0
  18. treenode/static/treenode/js/tree_widget.js +161 -0
  19. treenode/static/treenode/js/treenode_admin.js +171 -0
  20. treenode/templates/admin/export_success.html +26 -0
  21. treenode/templates/admin/tree_node_changelist.html +11 -0
  22. treenode/templates/admin/tree_node_export.html +27 -0
  23. treenode/templates/admin/tree_node_import.html +27 -0
  24. treenode/templates/widgets/tree_widget.css +23 -0
  25. treenode/templates/widgets/tree_widget.html +21 -0
  26. treenode/urls.py +34 -0
  27. treenode/utils/__init__.py +4 -0
  28. treenode/utils/base36.py +35 -0
  29. treenode/utils/exporter.py +141 -0
  30. treenode/utils/importer.py +296 -0
  31. treenode/version.py +11 -1
  32. treenode/views.py +102 -2
  33. treenode/widgets.py +49 -27
  34. django_fast_treenode-1.1.3.dist-info/RECORD +0 -33
  35. treenode/compat.py +0 -8
  36. treenode/factory.py +0 -68
  37. treenode/models.py +0 -668
  38. treenode/static/select2tree/.gitkeep +0 -1
  39. treenode/static/select2tree/select2tree.css +0 -176
  40. treenode/static/select2tree/select2tree.js +0 -181
  41. treenode/static/treenode/css/treenode.css +0 -85
  42. treenode/static/treenode/js/treenode.js +0 -201
  43. treenode/templates/widgets/.gitkeep +0 -1
  44. treenode/templates/widgets/attrs.html +0 -7
  45. treenode/templates/widgets/options.html +0 -1
  46. treenode/templates/widgets/select2tree.html +0 -22
  47. treenode/tests.py +0 -3
  48. {django_fast_treenode-1.1.3.dist-info → django_fast_treenode-2.0.0.dist-info}/LICENSE +0 -0
  49. {django_fast_treenode-1.1.3.dist-info → django_fast_treenode-2.0.0.dist-info}/top_level.txt +0 -0
  50. /treenode/{docs → templates/admin}/.gitkeep +0 -0
@@ -1,28 +1,44 @@
1
- Metadata-Version: 2.1
1
+ Metadata-Version: 2.2
2
2
  Name: django-fast-treenode
3
- Version: 1.1.3
3
+ Version: 2.0.0
4
4
  Summary: Application for supporting tree (hierarchical) data structure in Django projects
5
5
  Home-page: https://github.com/TimurKady/fast-treenode
6
6
  Author: Timur Kady
7
- Author-email: timurkady@yandex.com
8
- License: MIT
9
- Classifier: Environment :: Web Environment
10
- Classifier: Framework :: Django
11
- Classifier: Framework :: Django :: 3.0
12
- Classifier: Intended Audience :: Developers
13
- Classifier: License :: OSI Approved :: MIT License
14
- Classifier: Operating System :: OS Independent
15
- Classifier: Programming Language :: Python :: 3
16
- Classifier: Programming Language :: Python :: 3.9
17
- Classifier: Programming Language :: Python :: 3.10
18
- Classifier: Programming Language :: Python :: 3.11
19
- Classifier: Framework :: Django
20
- Classifier: Framework :: Django :: 3.0
21
- Classifier: Framework :: Django :: 4.0
22
- Requires-Python: >=3.8
7
+ Author-email: Timur Kady <kaduevtr@gmail.com>
8
+ License: MIT License
9
+
10
+ Copyright (c) 2020-2023 Timur Kady
11
+
12
+ Permission is hereby granted, free of charge, to any person obtaining a copy
13
+ of this software and associated documentation files (the "Software"), to deal
14
+ in the Software without restriction, including without limitation the rights
15
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
16
+ copies of the Software, and to permit persons to whom the Software is
17
+ furnished to do so, subject to the following conditions:
18
+
19
+ The above copyright notice and this permission notice shall be included in all
20
+ copies or substantial portions of the Software.
21
+
22
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
23
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
24
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
25
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
26
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
27
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
28
+ SOFTWARE.
29
+ Project-URL: Homepage, https://github.com/TimurKady/django-fast-treenode
30
+ Project-URL: Documentation, https://github.com/TimurKady/django-fast-treenode#readme
31
+ Project-URL: Source, https://github.com/TimurKady/django-fast-treenode
32
+ Project-URL: Issues, https://github.com/TimurKady/django-fast-treenode/issues
33
+ Requires-Python: >=3.9
23
34
  Description-Content-Type: text/markdown
24
35
  License-File: LICENSE
25
- Requires-Dist: Django >=3.0
36
+ Requires-Dist: Django<5.0,>=3.2
37
+ Requires-Dist: pympler>=1.0
38
+ Provides-Extra: import-export
39
+ Requires-Dist: openpyxl; extra == "import-export"
40
+ Requires-Dist: pyyaml; extra == "import-export"
41
+ Requires-Dist: pandas; extra == "import-export"
26
42
 
27
43
  # Django-fast-treenode
28
44
  __Combination of Adjacency List and Closure Table__
@@ -76,8 +92,7 @@ You can easily find additional information on your own on the Internet.
76
92
  4. Make your model-admin inherit from ```treenode.admin.TreeNodeModelAdmin``` (described below)
77
93
  5. Run python manage.py makemigrations and ```python manage.py migrate```
78
94
 
79
- When updating an existing project, simply call ```cls.update_tree()``` function once.
80
- It will automatically build a new and complete Closure Table for your tree.
95
+ For more information on migrating from the **django-treenode** package and upgrading to version 2.0, see [below](#migration-guide).
81
96
 
82
97
  ## Configuration
83
98
  ### `models.py`
@@ -143,6 +158,8 @@ CACHES = {
143
158
  },
144
159
  "treenode": {
145
160
  "BACKEND": "django.core.cache.backends.locmem.LocMemCache",
161
+ "KEY_PREFIX": "", # This is important!
162
+ "VERSION": None, # This is important!
146
163
  },
147
164
  }
148
165
  ```
@@ -150,15 +167,42 @@ CACHES = {
150
167
 
151
168
  ```
152
169
  class YoursForm(TreeNodeForm):
153
-
154
- class Meta:
155
- widgets = {
156
- 'tn_parent': TreeWidget(attrs={'style': 'min-width:400px'}),
157
- }
170
+ # Your code is here
158
171
  ```
159
172
 
160
- ## Usage
173
+ ## Updating to django-fast-treenode 2.X
174
+ ### Overview
175
+ If you are upgrading from a previous version, you need to follow these steps to ensure compatibility and proper functionality.
176
+
177
+ ### Update Process
178
+ 1. **Upgrade the package**
179
+ Run the following command to install the latest version:
180
+
181
+ ```bash
182
+ pip install --upgrade django-fast-treenode
183
+ ```
184
+
185
+ 2. **Apply database migrations**
186
+ After upgrading, you need to apply the necessary database migrations:
187
+
188
+ ```bash
189
+ python manage.py makemigrations
190
+ python manage.py migrate
191
+ ```
192
+
193
+ 3. **Restart the application**
194
+ Finally, restart your Django application to apply all changes:
195
+
196
+ ```bash
197
+ python manage.py runserver
198
+ ```
161
199
 
200
+ **Important Notes**: Failing to apply migrations (`migrate`) after upgrading may lead to errors when interacting with tree nodes.
201
+
202
+ By following these steps, you will ensure a smooth transition to the latest version of django-fast-treenode without data inconsistencies.
203
+
204
+
205
+ ## Usage
162
206
  ### Methods/Properties
163
207
 
164
208
  - [`delete`](#delete)
@@ -213,11 +257,17 @@ class YoursForm(TreeNodeForm):
213
257
  - [`update_tree`](#update_tree)
214
258
 
215
259
  #### `delete`
216
- **Delete a node** if `cascade=True` (default behaviour), children and descendants will be deleted too,
217
- otherwise children's parent will be set to `None` (then children become roots):
260
+ **Delete a node** provides two deletion strategies:
261
+ - **Cascade Delete (`cascade=True`)**: Removes the node along with all its descendants.
262
+ - **Reparenting (`cascade=False`)**: Moves the children of the deleted node up one level in the hierarchy before removing the node itself.
263
+
218
264
  ```python
219
- obj.delete(cascade=True)
265
+ node.delete(cascade=True) # Deletes node and all its descendants
266
+ node.delete(cascade=False) # Moves children up and then deletes the node
220
267
  ```
268
+ This ensures greater flexibility in managing tree structures while preventing orphaned nodes.
269
+
270
+ ---
221
271
 
222
272
  #### `delete_tree`
223
273
  **Delete the whole tree** for the current node class:
@@ -339,6 +389,8 @@ obj.get_descendants_tree()
339
389
  obj.descendants_tree
340
390
  ```
341
391
 
392
+ **Important**: In future projects, avoid using `get_descendants_tree()`. It will be removed in the next version.
393
+
342
394
  #### `get_descendants_tree_display`
343
395
  Get a **multiline** `string` representing the **model tree**:
344
396
  ```python
@@ -347,6 +399,8 @@ obj.get_descendants_tree_display(include_self=False, depth=None)
347
399
  obj.descendants_tree_display
348
400
  ```
349
401
 
402
+ **Important**: In future projects, avoid using `get_descendants_tree_display()`. It will be removed in the next version.
403
+
350
404
  #### `get_first_child`
351
405
  Get the **first child node**:
352
406
  ```python
@@ -570,27 +624,83 @@ obj.is_sibling_of(target_obj)
570
624
  ```python
571
625
  cls.update_tree()
572
626
  ```
627
+ ## **Cache Management**
628
+ ### **Overview**
629
+ In v2.0, the caching mechanism has been improved to prevent excessive memory usage when multiple models inherit from `TreeNode`. The new system introduces **FIFO (First-In-First-Out) cache eviction**, with plans to test and integrate more advanced algorithms in future releases.
630
+
631
+ ### **Key Features**
632
+ **Global Cache Limit**: The setting `TREENODE_CACHE_LIMIT` defines the maximum cache size (in MB) for all models inheriting from `TreeNode`. Default is **100MB** if not explicitly set in `settings.py`.
633
+ **settings.py**
634
+ ``` python
635
+ TREENODE_CACHE_LIMIT = 100
636
+ ```
637
+ **Automatic Management**: In most cases, users don’t need to manually manage cache operations.
638
+ **Manual Cache Clearing**:
639
+ - **Clear cache for a single model**: Use `clear_cache()` at the model level:
640
+ ```python
641
+ MyTreeNodeModel.clear_cache()
642
+ ```
643
+ - **Clear cache for all models**: Use the global `treenode_cache.clear()` method:
644
+ ```python
645
+ from treenode.cache import treenode_cache
646
+ treenode_cache.clear()
647
+ ```
648
+
649
+ ## **Export and Import Functionality**
650
+ ### **Overview**
651
+ TreeNode v2.0 includes **built-in export and import features** for easier data migration. Supported Formats: `csv`, `json`, `xlsx`, `yaml`, `tsv`
652
+ ### Installation for Import/Export Features
653
+ By default, import/export functionality is **not included** to keep the package lightweight. If you need these features, install the package with:
654
+ ```bash
655
+ pip install django-fast-treenode[import_export]
656
+ ```
657
+ Once installed, **import/export buttons will appear** in the Django admin interface.
658
+ ### **Important Considerations**
659
+ Exporting objects with M2M fields may lead to serialization issues. Some formats (e.g., CSV) do not natively support many-to-many relationships. If you encounter errors, consider exporting data in `json` or `yaml` format, which better handle nested structures.
660
+
661
+ ## Migration Guide
662
+ #### Switching from `django-treenode`
663
+ The migration process from `django-treenode` is fully automated. No manual steps are required. Upon upgrading, the necessary data structures will be checked and updated automatically. In exceptional cases, you can call the update code `cls.update_tree()` manually.
664
+
665
+
666
+ #### Upgrading to `django-fast-treenode` 2.0
667
+ To upgrade to version 2.0, simply run:
668
+ ```bash
669
+ pip install --upgrade django-fast-treenode
670
+ ```
671
+ or
672
+ ```bash
673
+ pip install django-fast-treenode[import_export]
674
+ ```
675
+ After upgrading, ensure that your database schema is up to date by running:
676
+ ```bash
677
+ python manage.py makemigrations
678
+ python manage.py migrate
679
+ ```
680
+ This will apply any necessary database changes automatically.
573
681
 
574
- ## License
575
- Released under [MIT License](https://github.com/TimurKady/django-fast-treenode/blob/main/LICENSE).
682
+ ## To do
683
+ These improvements aim to enhance usability, performance, and maintainability for all users of `django-fast-treenode`:
684
+ * **Cache Algorithm Optimization**: Testing and integrating more advanced cache eviction strategies.
685
+ * **Drag-and-Drop UI Enhancements**: Adding intuitive drag-and-drop functionality for tree node management.
686
+ * to be happy, to don't worry, until die.
576
687
 
577
- ## Cautions
578
- The provided code is already being used in production projects, even though I have only done general testing. That is why the risk of using the code lies entirely with you.
688
+ Your wishes, objections, comments are welcome.
579
689
 
580
- **Warning**: don't access the tree node fields directly! Most of them have been removed as unnecessary. In the future, only `tn_parent` and `tn_priority` will be kept. Use the functions described in the documentation above or the documentation for the [original application](https://github.com/fabiocaccamo/django-treenode).
581
690
 
582
- ## Credits
583
- This software contains, uses, including in a modified form:
584
- * [django-treenode](https://github.com/fabiocaccamo/django-treenode) by [Fabio Caccamo](https://github.com/fabiocaccamo);
585
- * [Select2-to-Tree](https://github.com/clivezhg/select2-to-tree) Select2 extension by [clivezhg](https://github.com/clivezhg)
691
+ # Django-fast-treenode
692
+ ## License
693
+ Released under [MIT License](https://github.com/TimurKady/django-fast-treenode/blob/main/LICENSE).
586
694
 
587
- Special thanks to [Mathieu Leplatre](https://blog.mathieu-leplatre.info/pages/about.html) for the advice used in writing this application
695
+ ## Cautions
696
+ **Warning**: Do not access the tree node fields directly! Most of *django-treenode* model fields have been removed as unnecessary. Now only `tn_parent` and `tn_priority` are supported and will be kept in the future.
588
697
 
589
- ## To do
590
- Future plans:
591
- * may be will add the ability to determine the priority of the parent by any field, for example, by creation date or alphabetical order;
592
- * drug-and-drop support;
593
- * to be happy, to don't worry, until die.
698
+ **Risks of Direct Field Access:**
699
+ - **Database Integrity Issues**: Directly modifying fields may break tree integrity, causing inconsistent parent-child relationships.
700
+ - **Loss of Cached Data**: The caching system relies on controlled updates. Bypassing methods like `set_parent()` or `update_tree()` may lead to outdated or incorrect data.
701
+ - **Unsupported Behavior**: Future versions may change field structures or remove unnecessary fields. Relying on them directly risks breaking compatibility.
594
702
 
703
+ Instead, always use the **documented methods** described above or refer to the [original application documentation](https://github.com/fabiocaccamo/django-treenode).
595
704
 
596
- Your wishes, objections, comments are welcome.
705
+ ## Credits
706
+ This software contains, uses, and includes, in a modified form, [django-treenode](https://github.com/fabiocaccamo/django-treenode) by [Fabio Caccamo](https://github.com/fabiocaccamo). Special thanks to [Mathieu Leplatre](https://blog.mathieu-leplatre.info/pages/about.html) for the advice used in writing this application.
@@ -0,0 +1,41 @@
1
+ treenode/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
+ treenode/admin.py,sha256=x5vJDiZjqcsUAVlK1qkZPK66lQeJq8zYgWwwejentYM,14077
3
+ treenode/apps.py,sha256=M0O9IKEnJZFfhfz12v4wksYJ-0ECyj1Cy3qXrfywos8,472
4
+ treenode/cache.py,sha256=Z_FpaS0vTKXqAI4n1QkZ7A_ILsLU3Q8rLgerA6pYyAA,7210
5
+ treenode/forms.py,sha256=imoLzr7qFlOBdeMQK12rAFp6hINpe0PS_U4-V8RRcDU,2802
6
+ treenode/managers.py,sha256=7z8GU64A2_jEonJyQDTyIpdOocaBbM352DkwZTHjdQk,10828
7
+ treenode/urls.py,sha256=7N0d4XiI6880sc8P89eWGr-ZjmOqPorA-fWfcnviqAM,876
8
+ treenode/version.py,sha256=-zaHoXRvTvJ0QzwA9ocYp7O38iBtIarACZbCNzwyc4s,222
9
+ treenode/views.py,sha256=vBDIxmYXBwmJxRnInvUVGy75FQmt-XN_HnEaKIu-fVs,3365
10
+ treenode/widgets.py,sha256=4Q6WlPPT5fggEuTXiZ_Z40pjb46CylSp28pa0xBT_Ps,2079
11
+ treenode/docs/Documentation,sha256=6USAESU8MuY1vlj95yY8S6T0o_0RsktGv6S_0SdSkwk,21030
12
+ treenode/models/__init__.py,sha256=gjDwVai0jf-l0hMaeeEBTYLR-DXkxUZMLUMGGs_tnuo,83
13
+ treenode/models/classproperty.py,sha256=IrwBWpmyjsAXpkpfDSOIMsnX6EMcbXql3mZjurHgRcw,556
14
+ treenode/models/closure.py,sha256=chTa9T9yC3H_2LaZXR7KLdNh1pc50iUolut5GB4Bm-Q,5297
15
+ treenode/models/factory.py,sha256=Wt1szWhbeICPwm0-RUy9p4VovcxltHECVxTSRyCQHc8,2100
16
+ treenode/models/proxy.py,sha256=6BFElk_NL1ARTEAikOOfMneUK5wEjofNnfXQWFSZUsA,21766
17
+ treenode/static/.gitkeep,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
18
+ treenode/static/treenode/.gitkeep,sha256=frcCV1k9oG9oKj3dpUqdJg1PxRT2RSN_XKdLCPjaYaY,2
19
+ treenode/static/treenode/css/.gitkeep,sha256=frcCV1k9oG9oKj3dpUqdJg1PxRT2RSN_XKdLCPjaYaY,2
20
+ treenode/static/treenode/css/tree_widget.css,sha256=Qsnr9cExetL7BFKErRSns4APzM8-9DM4g6nqMelPzUI,1972
21
+ treenode/static/treenode/css/treenode_admin.css,sha256=GiCJ_zNZs7JmJgjCHsn1tJinNEU_lTOYYPZ7S0fnvis,2195
22
+ treenode/static/treenode/js/.gitkeep,sha256=frcCV1k9oG9oKj3dpUqdJg1PxRT2RSN_XKdLCPjaYaY,2
23
+ treenode/static/treenode/js/tree_widget.js,sha256=Du3a76tojdIqWndji88Omt5MvajXK7GpypC9DYIFBMk,6571
24
+ treenode/static/treenode/js/treenode_admin.js,sha256=3fdvy1VoHb3rmzI19YXw4JPt6ZGKn_AhTEky8YQEilU,6821
25
+ treenode/templates/.gitkeep,sha256=frcCV1k9oG9oKj3dpUqdJg1PxRT2RSN_XKdLCPjaYaY,2
26
+ treenode/templates/admin/.gitkeep,sha256=frcCV1k9oG9oKj3dpUqdJg1PxRT2RSN_XKdLCPjaYaY,2
27
+ treenode/templates/admin/export_success.html,sha256=xN2D-BCH249CJB10fo_vHYUyFenQ9mFKqq7UTWcrXS4,747
28
+ treenode/templates/admin/tree_node_changelist.html,sha256=ykksipIBMy2LvH6UqPuM-y00UlXAjsypMHqiMm_KlTg,261
29
+ treenode/templates/admin/tree_node_export.html,sha256=vJxEoGI-US6VdFddxAFgL5r3MgGt6mgA43vltCsbA2k,1043
30
+ treenode/templates/admin/tree_node_import.html,sha256=ZFoveJ08X99EGiwFCfQowXI9oS9VgcFtRLYVDIWq-Fg,969
31
+ treenode/templates/widgets/tree_widget.css,sha256=2bEaxu1x7QJZ7erbs2SLMaxeaiMkjQXadfcDEW8wfok,551
32
+ treenode/templates/widgets/tree_widget.html,sha256=GKcCU-B2FkkJ2BSOuXOw9e_PdYTtADcvyITEXqOlZ9Y,723
33
+ treenode/utils/__init__.py,sha256=jAVT-uNGQDKPVq5ET4JE2GhRpzbxFdHU25w9sLC3_To,134
34
+ treenode/utils/base36.py,sha256=ydgu9hqDaK-WyS8zG-mtSWo7hJqbB4iHqkGz4-IVrb4,834
35
+ treenode/utils/exporter.py,sha256=l-IEsk2fK8xe-E-Hi7SMOV7ZIwxM6mZih5-0rhvsx9E,5396
36
+ treenode/utils/importer.py,sha256=n23PBFPXN-6S_Dl8Qmx56sp0eLy_lWfpxrzJqwygQf0,14190
37
+ django_fast_treenode-2.0.0.dist-info/LICENSE,sha256=GiiEe4Y9oOCbn9eGuNew1mMYHU_bJWaCK9zOusnKvvU,1091
38
+ django_fast_treenode-2.0.0.dist-info/METADATA,sha256=4KtUbAU7CMjjTFPk_5cv5jfkPZTID5Onf-U8p-gycr8,23215
39
+ django_fast_treenode-2.0.0.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
40
+ django_fast_treenode-2.0.0.dist-info/top_level.txt,sha256=fmgxHbXyx1O2MPi_9kjx8aL9L-8TmV0gre4Go8XgqFk,9
41
+ django_fast_treenode-2.0.0.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: bdist_wheel (0.43.0)
2
+ Generator: setuptools (75.8.0)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5
 
treenode/__init__.py CHANGED
@@ -1,7 +0,0 @@
1
- class classproperty(object):
2
-
3
- def __init__(self, getter):
4
- self.getter = getter
5
-
6
- def __get__(self, instance, owner):
7
- return self.getter(owner)