DN 流程,在笔记内让 ai 根据当前笔记内容进行回复,内部 ai 回复框

注意注意,别把这个语句放在有隐私的笔记里面!!!

原有功能与实现教程:
思源笔记页面内实现 ai 聊天与 ai 读取笔记内容进行回复(自动)! - 链滴

让 ai 根据当前笔记内容进行回复

代码功能:
在创建日记的时候进行回复

在每天写完日记以后,让 ai 根据日记内容进行回复

image.png

//!js // Function to get context from recently updated documents (Keep as is) async function getDocumentContext() { try { let currentDocId = Query.root_id(protyle); const sqlQuery = ` select * from blocks where root_id = '${currentDocId}' order by sort ASC limit 9999 `; let blocks = await Query.sql(sqlQuery); if (blocks && blocks.length > 0) { let contextEntries = blocks.map(block => { const content = block.markdown || block.content || '[No Content]'; return `Document Path: ${block.hpath || 'N/A'}\nContent:\n---\n${content}\n---`; }); return "以下是当前文档的内容,请参考:\n==========\n" + contextEntries.join('\n\n') + "\n==========\n"; } else { return "当前文档没有内容可供参考。\n"; } } catch (error) { console.error("查询文档时出错:", error); return "查询参考文档时出现错误。\n"; } } // Function to create the UI elements (Keep as is) const ui = () => { const textarea = document.createElement('textarea'); textarea.className = "fn__block b3-text-field"; textarea.rows = 3; textarea.placeholder = "继续提问..."; const buttonContainer = document.createElement('div'); buttonContainer.style.display = 'flex'; buttonContainer.style.justifyContent = 'flex-end'; buttonContainer.style.gap = '8px'; buttonContainer.style.marginTop = '8px'; const removeLastButton = document.createElement('button'); removeLastButton.className = "b3-button"; removeLastButton.textContent = "我不会和别人说的🌹"; buttonContainer.appendChild(removeLastButton); const sendButton = document.createElement('button'); sendButton.className = "b3-button"; sendButton.textContent = "是这样的😄"; buttonContainer.appendChild(sendButton); return { textarea, buttonContainer, sendButton, removeLastButton }; } // Main chat function (Modified to fix null querySelector error) const chat = async () => { let dv = Query.DataView(protyle, item, top); const messages = dv.useState('messages', []); const msgIds = dv.useState('msgIds', []); // --- Initial Rendering Structure --- dv.addmd(`#### 向我分享你的一天吧!`); // 1. Render existing messages from state const initialMsgIds = []; messages().forEach(msg => { try { let el = dv.addmd(`**${msg.role === 'user' ? 'You' : 'GPT'}**: ${msg.content}`); if (el && el.dataset && el.dataset.id) { initialMsgIds.push(el.dataset.id); } } catch (e) { console.error("Error rendering message:", e); } }); if (msgIds().length === 0 && initialMsgIds.length > 0) { msgIds(initialMsgIds); } // 2. Add Separator dv.addmd('---'); // 3. Create UI Elements but don't store unnecessary references const { textarea, buttonContainer, sendButton, removeLastButton } = ui(); // Just add them directly without storing the references dv.addele(textarea); dv.addele(buttonContainer); // --- Function to perform AI query (Modified with better error handling) --- const performAIQuery = async (prompt, isInitialQuery = false) => { try { sendButton.disabled = true; removeLastButton.disabled = true; // Add placeholder with better error handling let respondPlaceholder; let gptMsgId = null; try { respondPlaceholder = dv.addmd(`**GPT**: 正在检索参考资料并思考... 🤔`); if (respondPlaceholder && respondPlaceholder.dataset) { gptMsgId = respondPlaceholder.dataset.id; // Add placeholder ID to state only if it's valid if (gptMsgId) { msgIds([...msgIds(), gptMsgId]); } } } catch (e) { console.error("Error adding placeholder:", e); // If we can't add a placeholder, we'll just add a new message later } // Safe function to replace or add content const updateContent = (id, content) => { try { if (id) { dv.replaceView(id, dv.md(`**GPT**: ${content}`)); } else { // If no ID, add as new message let newEl = dv.addmd(`**GPT**: ${content}`); if (newEl && newEl.dataset && newEl.dataset.id) { msgIds([...msgIds(), newEl.dataset.id]); } } } catch (e) { console.error("Error updating content:", e); // Last resort fallback - just add a new message try { dv.addmd(`**GPT**: ${content}`); } catch (e) { console.error("Failed to add fallback message:", e); } } }; const docReference = await getDocumentContext(); const prefixText = `${docReference}\n这是我的提问背景信息:`; const suffixText = "\n请基于以上参考信息,回复我的问题。注意:多用表情,尽量简短且切中要点。"; const fullPrompt = `${prefixText}\n${prompt}\n${suffixText}`; const response = await Query.gpt(fullPrompt, { stream: true, streamInterval: 3, streamMsg: (content) => { // Safely update with streaming content updateContent(gptMsgId, content); } }); // Update state with final response const gptMessage = { role: 'assistant', content: response }; const currentMessages = messages(); if (isInitialQuery) { messages([gptMessage]); } else { messages([...currentMessages, gptMessage]); } // Final update with safe function updateContent(gptMsgId, response); } catch (error) { console.error("GPT 调用或处理失败:", error); const errorMessageContent = `抱歉,处理时遇到问题: ${error.message}`; try { if (gptMsgId) { dv.replaceView(gptMsgId, dv.md(`**GPT**: ${errorMessageContent}`)); } else { dv.addmd(`**GPT**: ${errorMessageContent}`); } const errorMessage = { role: 'assistant', content: errorMessageContent }; const currentMessages = messages(); if (isInitialQuery) { messages([errorMessage]); } else { messages([...currentMessages, errorMessage]); } } catch (e) { console.error("Error handling GPT failure:", e); // Try one more time with a simple message try { dv.addmd(`**Error**: ${error.message}`); } catch (finalError) { console.error("Failed all error handling attempts:", finalError); } } } finally { // Re-enable buttons regardless of outcome try { sendButton.disabled = false; removeLastButton.disabled = false; // Safely repaint dv.repaint(); } catch (e) { console.error("Error in finally block:", e); } } }; // --- Initial Query Logic --- if (messages().length === 0) { const predefinedPrompt = "今天真是美好的一天,请你基于参考内容,激励我度过美好的一天吧!请你用满满的正能量激励我,并且要加入很多的表情,让我的心情愉快!"; try { await performAIQuery(predefinedPrompt, true); } catch (e) { console.error("Initial query failed:", e); // Try to add a fallback message dv.addmd("**System**: 初始查询失败,但你仍然可以开始对话。"); } } // --- Button Handlers --- sendButton.onclick = async () => { const userInput = textarea.value.trim(); if (!userInput) return; // 1. Add user message to state and UI with better error handling const userMessage = { role: 'user', content: userInput }; messages([...messages(), userMessage]); let userEl; let userMsgId = null; try { userEl = dv.addmd(`**You**: ${userInput}`); if (userEl && userEl.dataset) { userMsgId = userEl.dataset.id; if (userMsgId) { msgIds([...msgIds(), userMsgId]); } } } catch (e) { console.error("Error adding user message:", e); } textarea.value = ''; // 2. Perform AI query with error handling try { await performAIQuery(userInput, false); } catch (e) { console.error("Query failed:", e); dv.addmd(`**System**: 查询失败,请重试。错误: ${e.message}`); } }; // Remove last button click handler (with better error handling) removeLastButton.onclick = () => { try { const currentMessages = messages(); let currentMsgIds = [...msgIds()]; if (currentMessages.length < 2 || currentMsgIds.length < 2) return; // Update messages state first (in case view operations fail) messages(currentMessages.slice(0, -2)); // Then try to remove the views try { const lastGptId = currentMsgIds.pop(); const lastUserId = currentMsgIds.pop(); if (lastGptId) dv.removeView(lastGptId); if (lastUserId) dv.removeView(lastUserId); // Update msgIds state only after successful removal msgIds(currentMsgIds); } catch (e) { console.error("Error removing views:", e); } // Always try to repaint dv.repaint(); } catch (e) { console.error("Error in removeLastButton handler:", e); } }; // --- Final Render --- try { dv.render(); } catch (e) { console.error("Error rendering DataView:", e); } } // Execute the chat function with error handling try { return chat(); } catch (e) { console.error("Fatal error in chat function:", e); return "Error initializing chat. Please check console for details."; }
  • 思源笔记

    思源笔记是一款隐私优先的个人知识管理系统,支持完全离线使用,同时也支持端到端加密同步。

    融合块、大纲和双向链接,重构你的思维。

    26382 引用 • 109716 回帖
1 操作
TangQi 在 2025-04-20 21:14:41 更新了该帖

相关帖子

欢迎来到这里!

我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。

注册 关于
请输入回帖内容 ...

推荐标签 标签

  • RESTful

    一种软件架构设计风格而不是标准,提供了一组设计原则和约束条件,主要用于客户端和服务器交互类的软件。基于这个风格设计的软件可以更简洁,更有层次,更易于实现缓存等机制。

    30 引用 • 114 回帖 • 8 关注
  • 分享

    有什么新发现就分享给大家吧!

    248 引用 • 1794 回帖
  • 钉钉

    钉钉,专为中国企业打造的免费沟通协同多端平台, 阿里巴巴出品。

    15 引用 • 67 回帖 • 267 关注
  • jsDelivr

    jsDelivr 是一个开源的 CDN 服务,可为 npm 包、GitHub 仓库提供免费、快速并且可靠的全球 CDN 加速服务。

    5 引用 • 31 回帖 • 108 关注
  • GitHub

    GitHub 于 2008 年上线,目前,除了 Git 代码仓库托管及基本的 Web 管理界面以外,还提供了订阅、讨论组、文本渲染、在线文件编辑器、协作图谱(报表)、代码片段分享(Gist)等功能。正因为这些功能所提供的便利,又经过长期的积累,GitHub 的用户活跃度很高,在开源世界里享有深远的声望,并形成了社交化编程文化(Social Coding)。

    209 引用 • 2040 回帖 • 1 关注
  • 生活

    生活是指人类生存过程中的各项活动的总和,范畴较广,一般指为幸福的意义而存在。生活实际上是对人生的一种诠释。生活包括人类在社会中与自己息息相关的日常活动和心理影射。

    230 引用 • 1432 回帖
  • 资讯

    资讯是用户因为及时地获得它并利用它而能够在相对短的时间内给自己带来价值的信息,资讯有时效性和地域性。

    56 引用 • 85 回帖
  • Access
    1 引用 • 3 回帖 • 2 关注
  • CentOS

    CentOS(Community Enterprise Operating System)是 Linux 发行版之一,它是来自于 Red Hat Enterprise Linux 依照开放源代码规定释出的源代码所编译而成。由于出自同样的源代码,因此有些要求高度稳定的服务器以 CentOS 替代商业版的 Red Hat Enterprise Linux 使用。两者的不同在于 CentOS 并不包含封闭源代码软件。

    240 引用 • 224 回帖
  • SMTP

    SMTP(Simple Mail Transfer Protocol)即简单邮件传输协议,它是一组用于由源地址到目的地址传送邮件的规则,由它来控制信件的中转方式。SMTP 协议属于 TCP/IP 协议簇,它帮助每台计算机在发送或中转信件时找到下一个目的地。

    4 引用 • 18 回帖 • 639 关注
  • MySQL

    MySQL 是一个关系型数据库管理系统,由瑞典 MySQL AB 公司开发,目前属于 Oracle 公司。MySQL 是最流行的关系型数据库管理系统之一。

    694 引用 • 537 回帖 • 1 关注
  • SVN

    SVN 是 Subversion 的简称,是一个开放源代码的版本控制系统,相较于 RCS、CVS,它采用了分支管理系统,它的设计目标就是取代 CVS。

    29 引用 • 98 回帖 • 698 关注
  • 单点登录

    单点登录(Single Sign On)是目前比较流行的企业业务整合的解决方案之一。SSO 的定义是在多个应用系统中,用户只需要登录一次就可以访问所有相互信任的应用系统。

    9 引用 • 25 回帖 • 4 关注
  • SOHO

    为成为自由职业者在家办公而努力吧!

    7 引用 • 55 回帖 • 3 关注
  • Chrome

    Chrome 又称 Google 浏览器,是一个由谷歌公司开发的网页浏览器。该浏览器是基于其他开源软件所编写,包括 WebKit,目标是提升稳定性、速度和安全性,并创造出简单且有效率的使用者界面。

    63 引用 • 289 回帖
  • 链滴

    链滴是一个记录生活的地方。

    记录生活,连接点滴

    183 引用 • 3885 回帖
  • 996
    13 引用 • 200 回帖
  • Q&A

    提问之前请先看《提问的智慧》,好的问题比好的答案更有价值。

    10150 引用 • 46127 回帖 • 63 关注
  • WebComponents

    Web Components 是 W3C 定义的标准,它给了前端开发者扩展浏览器标签的能力,可以方便地定制可复用组件,更好的进行模块化开发,解放了前端开发者的生产力。

    1 引用 • 15 关注
  • 黑曜石

    黑曜石是一款强大的知识库工具,支持本地 Markdown 文件编辑,支持双向链接和关系图。

    A second brain, for you, forever.

    25 引用 • 254 回帖 • 1 关注
  • 友情链接

    确认过眼神后的灵魂连接,站在链在!

    24 引用 • 373 回帖
  • 快应用

    快应用 是基于手机硬件平台的新型应用形态;标准是由主流手机厂商组成的快应用联盟联合制定;快应用标准的诞生将在研发接口、能力接入、开发者服务等层面建设标准平台;以平台化的生态模式对个人开发者和企业开发者全品类开放。

    15 引用 • 127 回帖 • 1 关注
  • ZeroNet

    ZeroNet 是一个基于比特币加密技术和 BT 网络技术的去中心化的、开放开源的网络和交流系统。

    1 引用 • 21 回帖 • 650 关注
  • Bootstrap

    Bootstrap 是 Twitter 推出的一个用于前端开发的开源工具包。它由 Twitter 的设计师 Mark Otto 和 Jacob Thornton 合作开发,是一个 CSS / HTML 框架。

    18 引用 • 33 回帖 • 649 关注
  • C

    C 语言是一门通用计算机编程语言,应用广泛。C 语言的设计目标是提供一种能以简易的方式编译、处理低级存储器、产生少量的机器码以及不需要任何运行环境支持便能运行的编程语言。

    86 引用 • 165 回帖
  • 学习

    “梦想从学习开始,事业从实践起步” —— 习近平

    172 引用 • 540 回帖
  • 负能量

    上帝为你关上了一扇门,然后就去睡觉了....努力不一定能成功,但不努力一定很轻松 (° ー °〃)

    89 引用 • 1251 回帖 • 393 关注