diff --git a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.js b/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.js deleted file mode 100644 index 3b34d9d..0000000 --- a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.js +++ /dev/null @@ -1,8 +0,0 @@ -// Copyright (c) 2025, Codeventurers and contributors -// For license information, please see license.txt - -// frappe.ui.form.on("NextGenie Chat Log", { -// refresh(frm) { - -// }, -// }); diff --git a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.json b/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.json deleted file mode 100644 index bab474f..0000000 --- a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.json +++ /dev/null @@ -1,86 +0,0 @@ -{ - "actions": [], - "creation": "2025-08-27 19:48:34.122664", - "doctype": "DocType", - "engine": "InnoDB", - "field_order": [ - "sender", - "user", - "column_break_yhtw", - "chat_creation", - "is_bot", - "section_break_wkcf", - "message" - ], - "fields": [ - { - "default": "User", - "fieldname": "sender", - "fieldtype": "Select", - "in_list_view": 1, - "in_standard_filter": 1, - "label": "Sender", - "options": "User\nGenie", - "read_only": 1 - }, - { - "fieldname": "column_break_yhtw", - "fieldtype": "Column Break" - }, - { - "fieldname": "chat_creation", - "fieldtype": "Datetime", - "label": "Chat Creation" - }, - { - "depends_on": "eval: doc.sender == \"User\"", - "fieldname": "user", - "fieldtype": "Link", - "in_list_view": 1, - "in_standard_filter": 1, - "label": "User", - "options": "User" - }, - { - "default": "0", - "fieldname": "is_bot", - "fieldtype": "Check", - "label": "Is Bot?" - }, - { - "fieldname": "section_break_wkcf", - "fieldtype": "Section Break" - }, - { - "fieldname": "message", - "fieldtype": "Text", - "label": "Message" - } - ], - "in_create": 1, - "links": [], - "modified": "2025-08-30 18:12:26.480496", - "modified_by": "Administrator", - "module": "Nextgenie", - "name": "NextGenie Chat Log", - "owner": "Administrator", - "permissions": [ - { - "create": 1, - "delete": 1, - "email": 1, - "export": 1, - "print": 1, - "read": 1, - "report": 1, - "role": "System Manager", - "share": 1, - "write": 1 - } - ], - "read_only": 1, - "sort_field": "modified", - "sort_order": "DESC", - "states": [], - "track_changes": 1 -} \ No newline at end of file diff --git a/nextgenie/nextgenie/doctype/nextgenie_chat_log/test_nextgenie_chat_log.py b/nextgenie/nextgenie/doctype/nextgenie_chat_log/test_nextgenie_chat_log.py deleted file mode 100644 index d022968..0000000 --- a/nextgenie/nextgenie/doctype/nextgenie_chat_log/test_nextgenie_chat_log.py +++ /dev/null @@ -1,9 +0,0 @@ -# Copyright (c) 2025, Codeventurers and Contributors -# See license.txt - -# import frappe -from frappe.tests.utils import FrappeTestCase - - -class TestNextGenieChatLog(FrappeTestCase): - pass diff --git a/nextgenie/nextgenie/doctype/nextgenie_chat_log/__init__.py b/nextgenie/nextgenie/doctype/nextgenie_settings/__init__.py similarity index 100% rename from nextgenie/nextgenie/doctype/nextgenie_chat_log/__init__.py rename to nextgenie/nextgenie/doctype/nextgenie_settings/__init__.py diff --git a/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.js b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.js new file mode 100644 index 0000000..ac8ee17 --- /dev/null +++ b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.js @@ -0,0 +1,8 @@ +// Copyright (c) 2026, Codeventurers and contributors +// For license information, please see license.txt + +// frappe.ui.form.on("Nextgenie Settings", { +// refresh(frm) { + +// }, +// }); diff --git a/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.json b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.json new file mode 100644 index 0000000..bfdf896 --- /dev/null +++ b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.json @@ -0,0 +1,82 @@ +{ + "actions": [], + "creation": "2026-07-04 00:00:00.000000", + "doctype": "DocType", + "engine": "InnoDB", + "field_order": [ + "enabled", + "anthropic_api_key", + "column_break_model", + "model", + "max_tokens", + "section_break_prompt", + "system_prompt" + ], + "fields": [ + { + "default": "1", + "fieldname": "enabled", + "fieldtype": "Check", + "label": "Enable AI Assistant" + }, + { + "fieldname": "anthropic_api_key", + "fieldtype": "Password", + "label": "Anthropic API Key", + "mandatory_depends_on": "eval:doc.enabled" + }, + { + "fieldname": "column_break_model", + "fieldtype": "Column Break" + }, + { + "default": "claude-sonnet-5", + "fieldname": "model", + "fieldtype": "Select", + "label": "Model", + "options": "claude-opus-4-8\nclaude-sonnet-5\nclaude-haiku-4-5" + }, + { + "default": "1024", + "fieldname": "max_tokens", + "fieldtype": "Int", + "label": "Max Output Tokens" + }, + { + "fieldname": "section_break_prompt", + "fieldtype": "Section Break", + "label": "System Prompt" + }, + { + "default": "You are NextGenie, a helpful and professional HR assistant.\nYou help employees with leave management, payroll queries, attendance,\nonboarding, company policies, and HR-related questions.\nAlways be polite, concise, and accurate. If you don't know something,\nsay so and suggest contacting the HR team directly.", + "fieldname": "system_prompt", + "fieldtype": "Small Text", + "label": "System Prompt" + } + ], + "grid_page_length": 50, + "index_web_pages_for_search": 1, + "issingle": 1, + "links": [], + "modified": "2026-07-04 00:00:00.000000", + "modified_by": "Administrator", + "module": "Nextgenie", + "name": "Nextgenie Settings", + "owner": "Administrator", + "permissions": [ + { + "create": 1, + "delete": 1, + "email": 1, + "print": 1, + "read": 1, + "role": "System Manager", + "share": 1, + "write": 1 + } + ], + "row_format": "Dynamic", + "sort_field": "modified", + "sort_order": "DESC", + "states": [] +} diff --git a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.py b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.py similarity index 57% rename from nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.py rename to nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.py index 43d1e61..b8639bf 100644 --- a/nextgenie/nextgenie/doctype/nextgenie_chat_log/nextgenie_chat_log.py +++ b/nextgenie/nextgenie/doctype/nextgenie_settings/nextgenie_settings.py @@ -1,9 +1,9 @@ -# Copyright (c) 2025, Codeventurers and contributors +# Copyright (c) 2026, Codeventurers and contributors # For license information, please see license.txt # import frappe from frappe.model.document import Document -class NextGenieChatLog(Document): +class NextgenieSettings(Document): pass diff --git a/nextgenie/nextgenie/page/nextgenie/nextgenie.css b/nextgenie/nextgenie/page/nextgenie/nextgenie.css index 6731fe9..f2207ba 100644 --- a/nextgenie/nextgenie/page/nextgenie/nextgenie.css +++ b/nextgenie/nextgenie/page/nextgenie/nextgenie.css @@ -153,7 +153,9 @@ } .hist-item { - display: block; + display: flex; + align-items: center; + gap: 6px; padding: 9px 10px; border-radius: 8px; cursor: pointer; @@ -172,6 +174,34 @@ border-color: rgba(201, 168, 76, 0.2); } +.hist-item-body { + flex: 1; + min-width: 0; +} + +.hist-item-delete { + flex-shrink: 0; + border: none; + background: transparent; + color: var(--ng-tm); + font-size: 12px; + line-height: 1; + padding: 4px 6px; + border-radius: 6px; + cursor: pointer; + opacity: 0; + transition: opacity 0.15s, background 0.15s, color 0.15s; +} + +.hist-item:hover .hist-item-delete { + opacity: 1; +} + +.hist-item-delete:hover { + background: rgba(220, 60, 60, 0.12); + color: #d64545; +} + .hist-item-title { display: block; font-size: 12px; diff --git a/nextgenie/nextgenie/page/nextgenie/nextgenie.js b/nextgenie/nextgenie/page/nextgenie/nextgenie.js index 830d3b7..d8e3149 100644 --- a/nextgenie/nextgenie/page/nextgenie/nextgenie.js +++ b/nextgenie/nextgenie/page/nextgenie/nextgenie.js @@ -15,6 +15,15 @@ frappe.pages['nextgenie'].on_page_load = function (wrapper) { $(wrapper).closest('.page-wrapper').find('.page-head').hide(); }, 0); + // Hide the global Frappe navbar while on this page, restore it elsewhere + function toggleNavbar() { + var on_nextgenie = frappe.get_route()[0] === 'nextgenie'; + $('.navbar').closest('.sticky-top').toggle(!on_nextgenie); + } + + toggleNavbar(); + frappe.router.on('change', toggleNavbar); + page.main.css({ 'padding': '0', 'margin': '0' }); $(page.main).addClass('ng-page-main'); @@ -44,14 +53,53 @@ frappe.pages['nextgenie'].on_page_load = function (wrapper) { .addClass('hist-item') .toggleClass('active', s.id === activeId); - $('