django-spire 0.21.1__py3-none-any.whl → 0.22.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 (40) hide show
  1. django_spire/consts.py +1 -1
  2. django_spire/core/{tags → tag}/intelligence/tag_set_bot.py +5 -4
  3. django_spire/core/tag/mixins.py +23 -0
  4. django_spire/core/{tags → tag}/models.py +1 -1
  5. django_spire/core/tag/service/tag_service.py +72 -0
  6. django_spire/core/{tags → tag}/tests/test_intelligence.py +1 -1
  7. django_spire/core/tag/tests/test_tags.py +102 -0
  8. django_spire/core/tag/tools.py +66 -0
  9. django_spire/core/templates/django_spire/tag/element/tag.html +1 -0
  10. django_spire/core/templatetags/spire_core_tags.py +12 -0
  11. django_spire/knowledge/collection/models.py +2 -2
  12. django_spire/knowledge/collection/services/tag_service.py +16 -14
  13. django_spire/knowledge/entry/models.py +2 -2
  14. django_spire/knowledge/entry/querysets.py +5 -0
  15. django_spire/knowledge/entry/services/tag_service.py +5 -5
  16. django_spire/knowledge/intelligence/bots/entries_search_llm_bot.py +44 -0
  17. django_spire/knowledge/intelligence/intel/entry_intel.py +24 -4
  18. django_spire/knowledge/intelligence/workflows/knowledge_workflow.py +46 -25
  19. django_spire/knowledge/templates/django_spire/knowledge/collection/page/display_page.html +6 -4
  20. django_spire/knowledge/templates/django_spire/knowledge/entry/version/page/editor_page.html +3 -2
  21. django_spire/knowledge/templates/django_spire/knowledge/message/knowledge_message_intel.html +14 -6
  22. django_spire/settings.py +1 -1
  23. {django_spire-0.21.1.dist-info → django_spire-0.22.0.dist-info}/METADATA +2 -2
  24. {django_spire-0.21.1.dist-info → django_spire-0.22.0.dist-info}/RECORD +32 -34
  25. django_spire/core/tags/mixins.py +0 -61
  26. django_spire/core/tags/tests/test_tags.py +0 -102
  27. django_spire/core/tags/tools.py +0 -20
  28. django_spire/knowledge/intelligence/bots/entry_search_llm_bot.py +0 -45
  29. django_spire/knowledge/intelligence/decoders/collection_decoder.py +0 -19
  30. django_spire/knowledge/intelligence/decoders/entry_decoder.py +0 -22
  31. django_spire/knowledge/intelligence/intel/collection_intel.py +0 -8
  32. django_spire/knowledge/templates/django_spire/knowledge/entry/version/page/form_page.html +0 -26
  33. /django_spire/core/{tags → tag}/__init__.py +0 -0
  34. /django_spire/core/{tags → tag}/intelligence/__init__.py +0 -0
  35. /django_spire/core/{tags → tag}/querysets.py +0 -0
  36. /django_spire/core/{tags/tests → tag/service}/__init__.py +0 -0
  37. /django_spire/{knowledge/intelligence/decoders → core/tag/tests}/__init__.py +0 -0
  38. {django_spire-0.21.1.dist-info → django_spire-0.22.0.dist-info}/WHEEL +0 -0
  39. {django_spire-0.21.1.dist-info → django_spire-0.22.0.dist-info}/licenses/LICENSE.md +0 -0
  40. {django_spire-0.21.1.dist-info → django_spire-0.22.0.dist-info}/top_level.txt +0 -0
@@ -1,5 +1,7 @@
1
1
  {% extends 'django_spire/knowledge/page/full_page.html' %}
2
2
 
3
+ {% load spire_core_tags %}
4
+
3
5
  {% block full_page_sub_navigation_title %}
4
6
  {{ collection.name_short }}
5
7
  {% endblock %}
@@ -49,16 +51,16 @@
49
51
  <div class="row">
50
52
  <div class="col-12 col-lg-8 mx-auto pb-4">
51
53
  Tags:
52
- {% for tag in collection.tags.all %}
53
- <span class="badge bg-secondary">{{ tag.name }}</span>
54
+ {% for tag, weight in collection.simplified_and_weighted_tag_dict|safe_dict_items %}
55
+ {% include 'django_spire/tag/element/tag.html' %}
54
56
  {% endfor %}
55
57
  </div>
56
58
  </div>
57
59
  <div class="row">
58
60
  <div class="col-12 col-lg-8 mx-auto pb-4">
59
61
  Aggregated Tags:
60
- {% for tag in collection.services.tag.get_aggregated_tag_set %}
61
- <span class="badge bg-secondary">{{ tag }}</span>
62
+ {% for tag, weight in collection.services.tag.get_simplified_and_weighted_aggregated_tag_set|safe_dict_items %}
63
+ {% include 'django_spire/tag/element/tag.html' %}
62
64
  {% endfor %}
63
65
  </div>
64
66
  </div>
@@ -1,6 +1,7 @@
1
1
  {% extends 'django_spire/knowledge/page/full_page.html' %}
2
2
 
3
3
  {% load static %}
4
+ {% load spire_core_tags %}
4
5
 
5
6
  {% block base_body_additional_top_js %}
6
7
  {{ block.super }}
@@ -46,8 +47,8 @@
46
47
  <div class="row">
47
48
  <div class="col-12 mb-3">
48
49
  {% include 'django_spire/element/attribute_element.html' with attribute_title='Tags' %}
49
- {% for tag in entry.tags.all %}
50
- <span class="badge bg-secondary">{{ tag.name }}</span>
50
+ {% for tag, weight in entry.simplified_and_weighted_tag_dict|safe_dict_items %}
51
+ {% include 'django_spire/tag/element/tag.html' %}
51
52
  {% endfor %}
52
53
  </div>
53
54
  </div>
@@ -4,19 +4,27 @@
4
4
  {% for entry_intel in message_intel.entries_intel %}
5
5
 
6
6
  <div class="row">
7
- <div class="col pt-2">
8
- <a href="{% url 'django_spire:knowledge:entry:version:page:editor' pk=entry_intel.entry_id %}?show_sub_nav=false&block_id={{ entry_intel.relevant_block_id }}" target="_blank">
9
- {{ entry_intel.relevant_heading_text }}
10
- </a>
7
+ <div class="col">
8
+ {{ entry_intel.relevant_text }}
11
9
  </div>
12
10
  </div>
13
11
 
14
12
  <div class="row">
15
- <div class="col pb-2">
16
- {{ entry_intel.relevant_subject_text }}
13
+ <div class="col pt-1 pb-3 fs-7">
14
+ <a href="{% url 'django_spire:knowledge:entry:version:page:editor' pk=entry_intel.entry.id %}?show_sub_nav=false&block_id={{ entry_intel.relevant_block_id }}"
15
+ target="_blank">
16
+ {{ entry_intel.relevant_heading_text }}
17
+ </a>
17
18
  </div>
18
19
  </div>
19
20
 
20
21
  {% endfor %}
21
22
 
23
+ <div class="row">
24
+ <div class="col">
25
+ Is there anything else I can help with?
26
+ </div>
27
+ </div>
28
+
29
+
22
30
  {% endblock %}
django_spire/settings.py CHANGED
@@ -14,7 +14,7 @@ DJANGO_SPIRE_AI_CHAT_ROUTERS = {
14
14
 
15
15
  DJANGO_SPIRE_AI_INTENT_CHAT_ROUTERS = {
16
16
  'KNOWLEDGE_SEARCH': {
17
- 'INTENT_DESCRIPTION': 'The user is asking about information in the knowledge base.',
17
+ 'INTENT_DESCRIPTION': 'The user is asking about information, help or support that could be found in knowledge base.',
18
18
  'REQUIRED_PERMISSION': 'django_spire_knowledge.view_collection',
19
19
  'CHAT_ROUTER': 'django_spire.knowledge.intelligence.router.KnowledgeSearchRouter',
20
20
  },
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: django-spire
3
- Version: 0.21.1
3
+ Version: 0.22.0
4
4
  Summary: A project for Django Spire
5
5
  Author-email: Brayden Carlson <braydenc@stratusadv.com>, Nathan Johnson <nathanj@stratusadv.com>
6
6
  License: Copyright (c) 2024 Stratus Advanced Technologies and Contributors.
@@ -49,7 +49,7 @@ Requires-Dist: beautifulsoup4>=4.14.2
49
49
  Requires-Dist: boto3>=1.34.0
50
50
  Requires-Dist: botocore>=1.34.0
51
51
  Requires-Dist: crispy-bootstrap5==2024.10
52
- Requires-Dist: dandy>=1.3.3
52
+ Requires-Dist: dandy>=1.3.5
53
53
  Requires-Dist: django>=5.1.8
54
54
  Requires-Dist: django-crispy-forms==2.3
55
55
  Requires-Dist: django-glue>=0.8.1
@@ -1,8 +1,8 @@
1
1
  django_spire/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
2
  django_spire/conf.py,sha256=c5Hs-7lk9T15254tOasiQ2ZTFLQIVJof9_QJDfm1PAI,933
3
- django_spire/consts.py,sha256=8Fe05Utjk0aOGITBGS1hnpxPylEe0jr6D-RLI-y7jPw,171
3
+ django_spire/consts.py,sha256=TSGO2fhA5NvrhZi9txx5DGQlgsO1tZDXIoDfg7qdtqY,171
4
4
  django_spire/exceptions.py,sha256=L5ndRO5ftMmh0pHkO2z_NG3LSGZviJ-dDHNT73SzTNw,48
5
- django_spire/settings.py,sha256=g6GVznY_k9vuBnOdJfcI0yDEMBzg9FKiSllSwXrgGM4,972
5
+ django_spire/settings.py,sha256=B4GPqBGt_dmkt0Ay0j-IP-SZ6mY44m2Ap5kVSON5YLA,1005
6
6
  django_spire/urls.py,sha256=mKeZszb5U4iIGqddMb5Tt5fRC72U2wABEOi6mvOfEBU,656
7
7
  django_spire/utils.py,sha256=kW0HP1xWj8Oz0h1GWs4NflnD8Jq8_F4hABwKTiT-Iyk,1006
8
8
  django_spire/ai/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -581,16 +581,18 @@ django_spire/core/static/django_spire/js/modal.js,sha256=ay0Sovi0HhedEz3dRhB_INh
581
581
  django_spire/core/static/django_spire/js/session_controller.js,sha256=aMom087y00MUhdxrZlrg89f88mBC7cWEhGWopeb5hlQ,232
582
582
  django_spire/core/static/django_spire/js/theme.js,sha256=Aq3KOJarjCr_Qjn0HyJlEFG0FWW1C948ppVvWxW554o,9606
583
583
  django_spire/core/static/django_spire/js/ui.js,sha256=Xrnw6cMmddCiUKC7iAJn1U7lk3nMJYxFJJO-J5zCqSw,673
584
- django_spire/core/tags/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
585
- django_spire/core/tags/mixins.py,sha256=ibnPcLmdB0js8ha4M93CqRv5kOQ7fijKBCLoxM9F7C0,1979
586
- django_spire/core/tags/models.py,sha256=zKXITkpyYNe80-CmJh46qw0YqxbJM79ud2wpgznmZH4,819
587
- django_spire/core/tags/querysets.py,sha256=vLdAV9KRTn-B9G9vhB4tQ3j-iNyz6OVZR5E9nVvAZY8,263
588
- django_spire/core/tags/tools.py,sha256=CB8vOlFSmk8Q79x-5OGYXCGx-VteTgDAPUCVOYaTmhU,787
589
- django_spire/core/tags/intelligence/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
590
- django_spire/core/tags/intelligence/tag_set_bot.py,sha256=-U-dkyodua48F6xatV1XHzeTTO-Zukl6rYOLMLxdIig,1289
591
- django_spire/core/tags/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
592
- django_spire/core/tags/tests/test_intelligence.py,sha256=UJj9OL_RaZQZ0tVih1VjntB9K5UkTg__VwE7iOr3Kog,1074
593
- django_spire/core/tags/tests/test_tags.py,sha256=dTf0hkbgmnGK4HjdKO21dOdZLuZ2qqgeatsQvqqNeEg,3516
584
+ django_spire/core/tag/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
585
+ django_spire/core/tag/mixins.py,sha256=jbBlg-ycTUE7SX1j08iRE2cu8_9j6dp5eI2uzeoYC7Y,707
586
+ django_spire/core/tag/models.py,sha256=50z8sVEollHQoedHxDyjcfy6PiJ3C5A6CKZEum7Qhfw,818
587
+ django_spire/core/tag/querysets.py,sha256=vLdAV9KRTn-B9G9vhB4tQ3j-iNyz6OVZR5E9nVvAZY8,263
588
+ django_spire/core/tag/tools.py,sha256=SyYRrYhjwu-TFnUeHRq82J21n5aVe8Wwy-iO5GGvvd8,2142
589
+ django_spire/core/tag/intelligence/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
590
+ django_spire/core/tag/intelligence/tag_set_bot.py,sha256=1kIZjt3NB52z1HMOocuGZn0LCng0zuqwmw1tzycxua8,1345
591
+ django_spire/core/tag/service/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
592
+ django_spire/core/tag/service/tag_service.py,sha256=R_YUQsSYn4kDhKjfeOvoGUQalPwsJoBe2H5186-cA-k,2534
593
+ django_spire/core/tag/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
594
+ django_spire/core/tag/tests/test_intelligence.py,sha256=qYRecu9qfRgiSdZbcuHPgCZrX_V_oC8CMoi6aiuwRTg,1073
595
+ django_spire/core/tag/tests/test_tags.py,sha256=kLpu41VQhM2fYDNR1ce-uiTMNYGcovwNho7H-Wo-Tks,3827
594
596
  django_spire/core/templates/django_spire/403.html,sha256=35OX-3z-Yi6Igx9DTAcxNwWiZ17wXdm4wYGML4U2pns,37
595
597
  django_spire/core/templates/django_spire/404.html,sha256=91sTr518M2YxQ8X3GlzDsNP6IVo3MW07tbHdcLBL8Iw,235
596
598
  django_spire/core/templates/django_spire/500.html,sha256=8N-aqCoafjq2mFcjLZv-BkAEqRh2bzJ2SqojlboS8g4,247
@@ -691,12 +693,13 @@ django_spire/core/templates/django_spire/speech/speech_synthesis.html,sha256=25H
691
693
  django_spire/core/templates/django_spire/tab/tab.html,sha256=1zSIX0Xk337VV9Qa4tvoSJlhoT2LDTfEfCwJvESNG-Q,1964
692
694
  django_spire/core/templates/django_spire/tab/element/tab_section_element.html,sha256=tEo0ENKhss74ll8HcFE9_kml35vusAfiMQHpudh3aEc,181
693
695
  django_spire/core/templates/django_spire/tab/element/tab_trigger_element.html,sha256=9VmMhfEGa3ARHerwyXojtQWyIkUj9sOPGhckcQR3h6k,442
696
+ django_spire/core/templates/django_spire/tag/element/tag.html,sha256=Zx2HyGd-A01SrfohjHhPGjYrJj3h0xH0BUNFDD5BH_4,131
694
697
  django_spire/core/templates/django_spire/wizard/wizard.html,sha256=iPkdo5O9mh3IQnhFijP9ZQXOaJDzhHGLmZo2Y49QnJ4,2266
695
698
  django_spire/core/templates/django_spire/wizard/wizard_page.html,sha256=emW5W2z_mkGERsbw3A9tFJoUOwhxa4Efr8thtZ_gHkI,75
696
699
  django_spire/core/templatetags/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
697
700
  django_spire/core/templatetags/json.py,sha256=2XY8hQZrJOSmGMblL8bLRYD9hvUSQvhYaSJvwGaKzwU,280
698
701
  django_spire/core/templatetags/message.py,sha256=y70pMv1ddttJ41c11O1S7h7v8h_gTtJVdXe67J4Ld3g,491
699
- django_spire/core/templatetags/spire_core_tags.py,sha256=_IN6HWrscCKJ8LjDRe47y5g1kvBgDAQ7tNAuD5SiuEY,4247
702
+ django_spire/core/templatetags/spire_core_tags.py,sha256=V1pRiEo9fOh938dpxTRcjuIh3ukxIYNGnrmE59r-Cg4,4575
700
703
  django_spire/core/templatetags/string_formating.py,sha256=pE5ID0-cvOKfmbAIixVXEW3LN8_XLEF_OlpztHkiILk,444
701
704
  django_spire/core/templatetags/variable_types.py,sha256=LFk9NO-LKBTBnXu04jLJ_miOKyuO-KAvqaBM8jwzg7s,686
702
705
  django_spire/core/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -817,7 +820,7 @@ django_spire/knowledge/auth/controller.py,sha256=ktTJ7gjtbYmCYESZnK97q7_fPojTASc
817
820
  django_spire/knowledge/collection/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
818
821
  django_spire/knowledge/collection/admin.py,sha256=9OKEgiSDiSHX6ZwB11l6mCx-jdF4VKfOe-SwFBdjKK4,1370
819
822
  django_spire/knowledge/collection/forms.py,sha256=7JovVxNzE67hSydDa-1JGK4U4zPyzOj605QyEl0JkP8,238
820
- django_spire/knowledge/collection/models.py,sha256=_wqLIzOHwvsVxdc-GjEZeXWKo_MOHF7DyaHCEPuaCwM,2390
823
+ django_spire/knowledge/collection/models.py,sha256=69ol2B-ytH6mJ48afFywPhENQNnM37gAsX-Grjim-g4,2387
821
824
  django_spire/knowledge/collection/querysets.py,sha256=8DWTGvo4WovXQ9n7XRLoxtyDdBUka2N-kcPUnJVOhOo,2479
822
825
  django_spire/knowledge/collection/seeding/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
823
826
  django_spire/knowledge/collection/seeding/seed.py,sha256=i4VEvScJvZ1SUV9ukKZp0qdh_owyLyVSHGgl8vIzhwQ,303
@@ -827,7 +830,7 @@ django_spire/knowledge/collection/services/factory_service.py,sha256=92DLZODSRPF
827
830
  django_spire/knowledge/collection/services/ordering_service.py,sha256=vTkSdt1lVT4VxSK3GhZibj8FPDDy5butwPkVzqmm07g,1243
828
831
  django_spire/knowledge/collection/services/processor_service.py,sha256=3ArKBndoL3HEvH_1EBqfiw7AnbFYZ0WmBgcPV8BHdLQ,911
829
832
  django_spire/knowledge/collection/services/service.py,sha256=sEamdqRcKdNcL6yz18hok0jww3Z4VRCPWrMF2QLvKGE,1830
830
- django_spire/knowledge/collection/services/tag_service.py,sha256=7EUIoTn70oAvcsX53RvKMLTZ_sySmBNgWhBvg8RCesE,1430
833
+ django_spire/knowledge/collection/services/tag_service.py,sha256=o1HnL0-du0XCGIl_8nMGMgW9AzEQE-AWbGOoBN_cQb0,1774
831
834
  django_spire/knowledge/collection/services/transformation_service.py,sha256=ME_jYURSG7at4oujTbcRzIVXyKnb75Xi6M4Nclbw6Yo,3464
832
835
  django_spire/knowledge/collection/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
833
836
  django_spire/knowledge/collection/tests/factories.py,sha256=NUu4OliEZIQL9c05RPIPdzYP3Dtn1szLZxP4Wl-kX2w,429
@@ -848,8 +851,8 @@ django_spire/knowledge/collection/views/page_views.py,sha256=jiKsIqi9pvSY5KbLLGD
848
851
  django_spire/knowledge/entry/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
849
852
  django_spire/knowledge/entry/admin.py,sha256=pY-0sYx24Su0y7sb1I2-GMCZxFEZj9oXhRckEdHNKno,1568
850
853
  django_spire/knowledge/entry/forms.py,sha256=Mhol37dMJP-pnex5IPxQVdchYcFBXnGzcWoY0SkU7lo,339
851
- django_spire/knowledge/entry/models.py,sha256=RSWXFLWAPZ43klgZvqXEzYl39g4hNIUPmX7btOrzbGk,2141
852
- django_spire/knowledge/entry/querysets.py,sha256=oVTylFT_Zx0elT5IVbYZRa0FwyGd9YaRz0vdcumfrsU,1121
854
+ django_spire/knowledge/entry/models.py,sha256=S7UV7UbWJZMyw_Tj2Y5IAJ3ShBbFp-H7i-E2Ll74IdE,2138
855
+ django_spire/knowledge/entry/querysets.py,sha256=uD7eoxGvyzTdom55xrwBzGoS7bs3dGVixioQhvM_hs8,1284
853
856
  django_spire/knowledge/entry/seeding/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
854
857
  django_spire/knowledge/entry/seeding/seed.py,sha256=n7ereq118GuqV1luNih7nuVpkrZpkBgPWt0FuE4Bl88,105
855
858
  django_spire/knowledge/entry/seeding/seeder.py,sha256=AqClwSzrFYWU59VsbUMJiN1Dh4P6Dvax-M3gqhoZoQM,2069
@@ -858,7 +861,7 @@ django_spire/knowledge/entry/services/automation_service.py,sha256=0_Ypk5cXhGvkQ
858
861
  django_spire/knowledge/entry/services/factory_service.py,sha256=bgUEHjdc9u2mxUJFy26qYOxUiJRHmhtcoH6AG3xzU0I,1379
859
862
  django_spire/knowledge/entry/services/processor_service.py,sha256=sfAM5ku7Td4k0jCe2szyoR72Bt1_OS75UKh7YPL4l2s,494
860
863
  django_spire/knowledge/entry/services/service.py,sha256=-A8_UcmQ8aLvkRNzGzTMA4faN9UWOd5pdlFlujB1YHI,1912
861
- django_spire/knowledge/entry/services/tag_service.py,sha256=AA4xDmofhuFOxa6HuKqlM9_SY-kjPWLKAnPUhvA7Is4,793
864
+ django_spire/knowledge/entry/services/tag_service.py,sha256=y5iYeWD4yi3aL4V8bbDIMvzVzqmcaqFSl5tQx5KlJtQ,792
862
865
  django_spire/knowledge/entry/services/tool_service.py,sha256=QL6w8t284LfSOJrQaF46uWInd4t413WYxcXCWsat_jE,1083
863
866
  django_spire/knowledge/entry/services/transformation_services.py,sha256=6WPQxW-_XATi8HCwshtJjoYbQFJcIdCqFaADHnTyk1U,2687
864
867
  django_spire/knowledge/entry/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -939,16 +942,12 @@ django_spire/knowledge/entry/views/template_views.py,sha256=Y-3JnslI_hj4WesN8dJb
939
942
  django_spire/knowledge/intelligence/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
940
943
  django_spire/knowledge/intelligence/router.py,sha256=4nPcIJJPHtwGgBXrLZiZaSNrfHDADrE5wCznvQOOm2s,802
941
944
  django_spire/knowledge/intelligence/bots/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
942
- django_spire/knowledge/intelligence/bots/entry_search_llm_bot.py,sha256=02fRELEyRjqRc1o_McQPWucQOTQtpIO6_v8-3OO7mLs,1689
943
- django_spire/knowledge/intelligence/decoders/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
944
- django_spire/knowledge/intelligence/decoders/collection_decoder.py,sha256=Vqh-JQukPatbxvV3NMWKvl8Np3bgRtDxQZjd2T3E0Rc,599
945
- django_spire/knowledge/intelligence/decoders/entry_decoder.py,sha256=cyywWGDlXmEeq050AEcAc4II0ItwBp8HFM1aQXfGAl4,572
945
+ django_spire/knowledge/intelligence/bots/entries_search_llm_bot.py,sha256=Pnpbu9mzEm2_vKvUNz4DIqZL_XzZx4L44LQ2vIqDPnk,1664
946
946
  django_spire/knowledge/intelligence/intel/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
947
- django_spire/knowledge/intelligence/intel/collection_intel.py,sha256=4ci6_bVUimj_33FZgQ7wCpESXrKBMxHGF0yyfrstmvI,144
948
- django_spire/knowledge/intelligence/intel/entry_intel.py,sha256=lGlGqeruV5oOu0aArGA_Bxa1pqAI7lr1MD7UATAy2Sg,445
947
+ django_spire/knowledge/intelligence/intel/entry_intel.py,sha256=7B7qLqNl39VFQKq_e5m1ShhSNgN2AV2gqesKRCnXid0,844
949
948
  django_spire/knowledge/intelligence/intel/message_intel.py,sha256=iYXdOkS1KfP3QH3-KsTSJ_BspRh1vPw-zG7uJMNOWf8,419
950
949
  django_spire/knowledge/intelligence/workflows/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
951
- django_spire/knowledge/intelligence/workflows/knowledge_workflow.py,sha256=6NjF9-ErMaEqa69C2GUAmv2h7IdbHTTLoiza-Wewgd4,1897
950
+ django_spire/knowledge/intelligence/workflows/knowledge_workflow.py,sha256=55e_zFeeKBglQ73hi3d71Zc7WLUuWO5SwvFLCP5rUDg,2449
952
951
  django_spire/knowledge/migrations/0001_initial.py,sha256=0oAx4e0Tu1wbcMwQZ4I_B2X_EGdEA9Qz_UBdVNGc3yE,5487
953
952
  django_spire/knowledge/migrations/0002_alter_entryversionblock_type.py,sha256=Eg8tLjDO0nJ3go_jgVvoqwYKFOpYUUyNtZtLI2V3IQQ,527
954
953
  django_spire/knowledge/migrations/0003_alter_collection_order_alter_entry_order_and_more.py,sha256=nIIUg1lHQ1iLbPlOulwZgzHrP1erGMYVXDaEdDXv4ik,749
@@ -973,7 +972,7 @@ django_spire/knowledge/templates/django_spire/knowledge/collection/container/det
973
972
  django_spire/knowledge/templates/django_spire/knowledge/collection/element/ellipsis_dropdown.html,sha256=o9cceexfwUSDtac4uhlUm4LimnBQrgTP6QPkpJF6DD0,1376
974
973
  django_spire/knowledge/templates/django_spire/knowledge/collection/form/form.html,sha256=gDjvFBpNQHGn4PNJBi4pBw89-IakpyrC23D9dr0xQ-c,1902
975
974
  django_spire/knowledge/templates/django_spire/knowledge/collection/item/collection_item.html,sha256=gaOqh1wxf5IcWdxWWiYyz6HWjoPyn6FohaTMIssJ67k,517
976
- django_spire/knowledge/templates/django_spire/knowledge/collection/page/display_page.html,sha256=v6lLzrubEYzVgoTKt_Oh3xAV0agUkWmyTFtAmD5uQcg,2281
975
+ django_spire/knowledge/templates/django_spire/knowledge/collection/page/display_page.html,sha256=AzYod7og_yU_lfxWIRFC2R_ga_jwH_Cr4VE07sRlGT8,2400
977
976
  django_spire/knowledge/templates/django_spire/knowledge/collection/page/form_page.html,sha256=eD190iYnmx-6u8Y0EAExDdilPtxTlS_ic6-WBfTtj2s,274
978
977
  django_spire/knowledge/templates/django_spire/knowledge/container/container.html,sha256=Fi-PL8neKrmGeLQtvhNiGoimpen86m4r9YlAS-amWXI,1220
979
978
  django_spire/knowledge/templates/django_spire/knowledge/entry/badge/entry_status_badge.html,sha256=qz7Y2ac1T4qu0Nr_Yj4BdUbQamgA6Llq7TmoXAf5Arw,381
@@ -990,9 +989,8 @@ django_spire/knowledge/templates/django_spire/knowledge/entry/modal/publish_conf
990
989
  django_spire/knowledge/templates/django_spire/knowledge/entry/page/form_page.html,sha256=EBfDjDBvo7IR6f5joTtZjzK5LtZb4rt0U1FO1HQNt88,291
991
990
  django_spire/knowledge/templates/django_spire/knowledge/entry/page/import_form_page.html,sha256=TK8Bc7mUZwsmV1Xm9FPyWz7Hws68Ijy4c55orvNoOC4,308
992
991
  django_spire/knowledge/templates/django_spire/knowledge/entry/version/container/editor_container.html,sha256=NAtXEq8UJOV9_vp3l5HIIdQp-lZhNVW4luF0Nvv8Sl8,3389
993
- django_spire/knowledge/templates/django_spire/knowledge/entry/version/page/editor_page.html,sha256=Q6bPXeIORGQMZ4Wb6YDsWWoMUKws6a-oGhl4mv7syUE,3019
994
- django_spire/knowledge/templates/django_spire/knowledge/entry/version/page/form_page.html,sha256=ufUISOfNmk45hl7F-ujtAzpHdEmUxh55odW0eyL6SMU,722
995
- django_spire/knowledge/templates/django_spire/knowledge/message/knowledge_message_intel.html,sha256=fpCJAwgxYqzJPLV63mLmUFjfEFk98t4FBX0RkSvDnzQ,698
992
+ django_spire/knowledge/templates/django_spire/knowledge/entry/version/page/editor_page.html,sha256=Gc5uYGjYJR8nwaLa0hm-5GHO3ezI9CLO0H_OLp8EvdE,3092
993
+ django_spire/knowledge/templates/django_spire/knowledge/message/knowledge_message_intel.html,sha256=sjZNgvXnOdqg068nhqo79GljR1P1XUJafExERUdBwZc,842
996
994
  django_spire/knowledge/templates/django_spire/knowledge/page/full_page.html,sha256=vz3WQ6SAL43QALRf0haaLfNkUfIQQemR0FAZQ2tznV4,1331
997
995
  django_spire/knowledge/templates/django_spire/knowledge/page/home_page.html,sha256=LMGSoPuP4N0NMX9QB1r5qJaExDvt6IKlJNp69Dt2EeQ,293
998
996
  django_spire/knowledge/templates/django_spire/knowledge/sub_navigation/element/collection_sub_navigation_ellipsis_dropdown.html,sha256=DeM7yRcjRN25eRvdOK-3Ae0kbYaMWvk7Ufbc8AZphgk,1023
@@ -1151,8 +1149,8 @@ django_spire/theme/urls/page_urls.py,sha256=S8nkKkgbhG3XHI3uMUL-piOjXIrRkuY2UlM_
1151
1149
  django_spire/theme/views/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1152
1150
  django_spire/theme/views/json_views.py,sha256=W1khC2K_EMbEzAFmMxC_P76_MFnkRH4-eVdodrRfAhw,1904
1153
1151
  django_spire/theme/views/page_views.py,sha256=pHr8iekjtR99xs7w1taj35HEo133Svq1dvDD0y0VL1c,3933
1154
- django_spire-0.21.1.dist-info/licenses/LICENSE.md,sha256=tlTbOtgKoy-xAQpUk9gPeh9O4oRXCOzoWdW3jJz0wnA,1091
1155
- django_spire-0.21.1.dist-info/METADATA,sha256=-_tFjGSVFeNqfse3Q_9dP4vkDsWPxZo3OLXF84qf-Aw,4967
1156
- django_spire-0.21.1.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
1157
- django_spire-0.21.1.dist-info/top_level.txt,sha256=xf3QV1e--ONkVpgMDQE9iqjQ1Vg4--_6C8wmO-KxPHQ,13
1158
- django_spire-0.21.1.dist-info/RECORD,,
1152
+ django_spire-0.22.0.dist-info/licenses/LICENSE.md,sha256=tlTbOtgKoy-xAQpUk9gPeh9O4oRXCOzoWdW3jJz0wnA,1091
1153
+ django_spire-0.22.0.dist-info/METADATA,sha256=jWPW3aT41-AoEvBFVxoW-pi2ppG7ccH1AxcKV3me4vk,4967
1154
+ django_spire-0.22.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
1155
+ django_spire-0.22.0.dist-info/top_level.txt,sha256=xf3QV1e--ONkVpgMDQE9iqjQ1Vg4--_6C8wmO-KxPHQ,13
1156
+ django_spire-0.22.0.dist-info/RECORD,,
@@ -1,61 +0,0 @@
1
- from django.db import models
2
- from django.db.models import QuerySet
3
-
4
- from django_spire.core.tags.models import Tag
5
- from django_spire.core.tags import tools
6
-
7
-
8
- class TagsModelMixin(models.Model):
9
- tags = models.ManyToManyField(Tag, related_name='+', null=True, blank=True, editable=False)
10
-
11
- class Meta:
12
- abstract = True
13
-
14
- @property
15
- def tag_set(self) -> set[str]:
16
- return set(self.tags.values_list('name', flat=True))
17
-
18
- @property
19
- def tag_set_simplified(self) -> set[str]:
20
- simplified_tag_words = []
21
-
22
- for tag in self.tag_set:
23
- tag_words = tag.split('-')
24
- simplified_tag_words.extend(tag_words)
25
-
26
- return set(simplified_tag_words)
27
-
28
- def add_tags_from_tag_set(self, tag_set: set[str]):
29
- self._update_global_tags_from_set(tag_set)
30
-
31
- self.tags.add(*Tag.objects.in_tag_set(tag_set))
32
-
33
- def clear_tags(self):
34
- self.tags.clear()
35
-
36
- def get_matching_tags_from_tag_set(self, tag_set: set[str]) -> QuerySet:
37
- return self.tags.in_tag_set(tag_set)
38
-
39
- def get_matching_percentage_of_tag_set(self, tag_set: set[str]) -> float:
40
- return tools.get_matching_a_percentage_from_tag_sets(tag_set, self.tag_set)
41
-
42
- def get_matching_percentage_of_model_tags_from_tag_set(self, tag_set: set[str]) -> float:
43
- return tools.get_matching_b_percentage_from_tag_sets(tag_set, self.tag_set)
44
-
45
- def has_tags_in_tag_set(self, tag_set: set[str]) -> bool:
46
- return self.tag_set.issuperset(tag_set)
47
-
48
- def remove_tags_by_tag_set(self, tag_set: set[str]):
49
- tag_objects = Tag.objects.in_tag_set(tag_set)
50
-
51
- self.tags.remove(*tag_objects)
52
-
53
- def set_tags_from_tag_set(self, tag_set: set[str]):
54
- self._update_global_tags_from_set(tag_set)
55
-
56
- tag_objects = Tag.objects.in_tag_set(tag_set)
57
- self.tags.set(tag_objects)
58
-
59
- @staticmethod
60
- def _update_global_tags_from_set(tag_set: set[str]):
61
- Tag.add_tags([Tag(name=tag) for tag in tag_set])
@@ -1,102 +0,0 @@
1
- from django.test import TestCase
2
-
3
- from django_spire.core.tags.models import Tag
4
- from django_spire.knowledge.collection.models import Collection
5
-
6
-
7
- class TestTags(TestCase):
8
- def setUp(self):
9
- self.collection = Collection.objects.create(
10
- name='Test Collection', description='Test Collection Description'
11
- )
12
-
13
- self.tag_set_a = {'apple', 'banana', 'orange'}
14
- self.tag_set_b = {'grape', 'kiwi', 'pear'}
15
- self.tag_set_c = {'lemon', 'lime', 'mango'}
16
-
17
- self.mixed_tag_set = {'apple', 'grape', 'lemon'}
18
-
19
- self.dirty_tag_set = {'HaT~', 'four* tacos', '123 hoop!!'}
20
-
21
- self.collection.add_tags_from_tag_set(self.tag_set_a)
22
- self.collection.add_tags_from_tag_set(self.tag_set_b)
23
- self.collection.add_tags_from_tag_set(self.tag_set_c)
24
-
25
- self.collection.add_tags_from_tag_set(self.mixed_tag_set)
26
-
27
- self.collection.add_tags_from_tag_set(self.dirty_tag_set)
28
-
29
- def test_tag_removal(self):
30
- self.assertIn('apple', self.collection.tag_set)
31
-
32
- self.collection.remove_tags_by_tag_set(self.mixed_tag_set)
33
-
34
- self.assertNotIn('lemon', self.collection.tag_set)
35
-
36
- self.assertIn('kiwi', self.collection.tag_set)
37
-
38
- def test_tag_add_and_set(self):
39
- self.collection.set_tags_from_tag_set(self.mixed_tag_set)
40
-
41
- self.assertIn('lemon', self.collection.tag_set)
42
-
43
- self.assertNotIn('banana', self.collection.tag_set)
44
-
45
- def test_tag_count(self):
46
- self.assertEqual(Tag.objects.count(), 12)
47
- self.assertEqual(self.collection.tags.count(), 12)
48
-
49
- def test_tag_removal(self):
50
- self.collection.remove_tags_by_tag_set(self.tag_set_a)
51
-
52
- self.assertEqual(self.collection.tags.count(), 9)
53
-
54
- def test_tag_bool_methods(self):
55
- self.collection.remove_tags_by_tag_set(self.tag_set_b)
56
-
57
- self.assertTrue(self.collection.has_tags_in_tag_set(self.tag_set_c))
58
- self.assertFalse(self.collection.has_tags_in_tag_set(self.mixed_tag_set))
59
-
60
- def test_tag_matching_methods(self):
61
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.tag_set_a)), 3)
62
-
63
- self.collection.remove_tags_by_tag_set(self.tag_set_a)
64
-
65
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.tag_set_a)), 0)
66
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.tag_set_b)), 3)
67
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.mixed_tag_set)), 2)
68
-
69
- self.collection.remove_tags_by_tag_set(self.tag_set_b)
70
-
71
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.tag_set_b)), 0)
72
-
73
- self.assertEqual(len(self.collection.get_matching_tags_from_tag_set(self.mixed_tag_set)), 1)
74
-
75
- def test_tag_metric_methods(self):
76
- self.assertAlmostEqual(
77
- self.collection.get_matching_percentage_of_tag_set(self.tag_set_a),
78
- 1.00,
79
- 2
80
- )
81
-
82
- self.assertAlmostEqual(
83
- self.collection.get_matching_percentage_of_model_tags_from_tag_set(self.tag_set_b),
84
- 0.25,
85
- 2
86
- )
87
-
88
- self.collection.remove_tags_by_tag_set(self.mixed_tag_set)
89
-
90
- self.assertAlmostEqual(
91
- self.collection.get_matching_percentage_of_tag_set(self.tag_set_a),
92
- 0.666,
93
- 2
94
- )
95
-
96
-
97
- self.assertAlmostEqual(
98
- self.collection.get_matching_percentage_of_model_tags_from_tag_set(self.tag_set_b),
99
- 0.222,
100
- 2
101
- )
102
-
@@ -1,20 +0,0 @@
1
- def get_matching_tag_set_from_tag_sets(tag_set_a: set[str], tag_set_b: set[str]) -> set[str]:
2
- return tag_set_a.intersection(tag_set_b)
3
-
4
-
5
- def get_matching_count_from_tag_sets(tag_set_a: set[str], tag_set_b: set[str]) -> int:
6
- return len(get_matching_tag_set_from_tag_sets(tag_set_a, tag_set_b))
7
-
8
-
9
- def get_matching_a_percentage_from_tag_sets(tag_set_a: set[str], tag_set_b: set[str]) -> float:
10
- try:
11
- return get_matching_count_from_tag_sets(tag_set_a, tag_set_b) / len(tag_set_a)
12
- except ZeroDivisionError:
13
- return 0.0
14
-
15
-
16
- def get_matching_b_percentage_from_tag_sets(tag_set_a: set[str], tag_set_b: set[str]) -> float:
17
- try:
18
- return get_matching_count_from_tag_sets(tag_set_a, tag_set_b) / len(tag_set_b)
19
- except ZeroDivisionError:
20
- return 0.0
@@ -1,45 +0,0 @@
1
- from __future__ import annotations
2
-
3
- from dandy import Bot, Prompt
4
-
5
- from django_spire.knowledge.entry.models import Entry
6
- from django_spire.knowledge.intelligence.intel.collection_intel import CollectionIntel
7
- from django_spire.knowledge.intelligence.intel.entry_intel import EntryIntel
8
-
9
-
10
- class EntrySearchBot(Bot):
11
- llm_role = 'Knowledge Entry Search Assistant'
12
- llm_task = 'Read through the knowledge entry the information request and return information and the block id that relevant'
13
- llm_guidelines = (
14
- Prompt()
15
- .list([
16
- 'Make sure the relevant heading text is from a heading with mark down formatting.'
17
- 'When returning the relevant heading remove any of the markdown formating characters.'
18
- ])
19
- )
20
- llm_intel_class = EntryIntel
21
-
22
- def process(self, user_input: str, entry: Entry) -> EntryIntel:
23
- entry_prompt = Prompt()
24
- entry_prompt.sub_heading('Information Request')
25
- entry_prompt.line_break()
26
- entry_prompt.text(f'{user_input}')
27
- entry_prompt.line_break()
28
- entry_prompt.sub_heading(f'Knowledge Entry: {entry.name}')
29
- entry_prompt.line_break()
30
-
31
- for version_block in entry.current_version.blocks.all():
32
- entry_prompt.text(f'{version_block.id}: {version_block.render_to_text()}')
33
-
34
- entry_intel = self.llm.prompt_to_intel(
35
- prompt=entry_prompt,
36
- exclude_fields={'entry_id', 'collection_intel'},
37
- )
38
-
39
- entry_intel.entry_id = entry.id
40
- entry_intel.collection_intel = CollectionIntel(
41
- name=entry.collection.name,
42
- collection_id=entry.collection.id,
43
- )
44
-
45
- return entry_intel
@@ -1,19 +0,0 @@
1
- from __future__ import annotations
2
-
3
- from dandy import Decoder
4
-
5
- from django_spire.knowledge.collection.models import Collection
6
-
7
-
8
- def get_collection_decoder() -> Decoder:
9
- class CollectionDecoder(Decoder):
10
- mapping_keys_description = 'Knowledge Collections Tags'
11
- mapping = {
12
- **{
13
- f'{collection.services.tag.get_aggregated_tag_set_simplified()}': collection
14
- for collection in Collection.objects.all().annotate_entry_count()
15
- },
16
- 'No Matching Knowledge Collection Tags': None,
17
- }
18
-
19
- return CollectionDecoder()
@@ -1,22 +0,0 @@
1
- from __future__ import annotations
2
-
3
- from typing import TYPE_CHECKING
4
-
5
- from dandy import Decoder
6
-
7
- if TYPE_CHECKING:
8
- from django_spire.knowledge.collection.models import Collection
9
-
10
-
11
- def get_entry_decoder(collection: Collection) -> Decoder:
12
- class EntryDecoder(Decoder):
13
- mapping_keys_description = 'Knowledge Entries Tags'
14
- mapping = {
15
- **{
16
- f'{entry.tag_set}': entry
17
- for entry in collection.entries.all()
18
- },
19
- 'No Matching Knowledge Entries': None
20
- }
21
-
22
- return EntryDecoder()
@@ -1,8 +0,0 @@
1
- from __future__ import annotations
2
-
3
- from dandy import BaseIntel
4
-
5
-
6
- class CollectionIntel(BaseIntel):
7
- name: str
8
- collection_id: int = None
@@ -1,26 +0,0 @@
1
- {% extends 'django_spire/knowledge/page/full_page.html' %}
2
-
3
- {% load static %}
4
-
5
- {% block base_body_additional_top_js %}
6
- <script type="application/javascript" src="{% static 'django_spire/knowledge/entry/version/js/managers.js' %}?v={{ DJANGO_SPIRE_VERSION }}"></script>
7
- {% endblock %}
8
-
9
- {% block knowledge_full_page_content %}
10
- <style>
11
- .block {}
12
-
13
- .action-items {
14
- opacity: 0;
15
- }
16
-
17
- .block:hover .action-items {
18
- opacity: 1;
19
- }
20
- </style>
21
- <div class="row justify-content-center">
22
- <div class="col-12 col-xl-8">
23
- {% include 'django_spire/knowledge/entry/version/container/form_container.html' %}
24
- </div>
25
- </div>
26
- {% endblock %}
File without changes
File without changes