DevLog:2026年1月19日

1、上周参考ChatGPT的建议,给DoitWith增加了“下一步”功能,用于记录工作流程,同时调整了部分操作方式和界面细节,构建测试,发现问题如下:

1.应用内的示例Todo无法修改内容,标题、下一步、日期、重复在修改之后保存,均未生效

2.修改新建的Todo时也无法生效

3.删除示例Todo后,第一次删除会被归类到General,第二次删除后仍然在General里,同时回收站中也有同样的条目,应该是在删除之后直接进入回收站,不应继续存在于Todo列表中

2、Cursor在修改过程中指出问题1和2是由于EditTodoView只更新内存数组,未更新CoreData导致的,问题3是因为分组信息未能正确获取,并且删除后要调用loadFromCoreData()重新加载,确保列表更新,再次测试,已经可以正常保存修改,但删除后仍然会被归类到General分组,继续反馈给Cursor修改

3、Cursor认为这是因为删除时创建的todoCopy被当做正常Todo出现在列表中,在删除Todo时,需要从CoreData中删除原始TodoEntity,并创建DeletedTodoEntity,保存到回收站,修改后再次测试删除功能也已正常

4、然后和Cursor明确“完成Todo”的逻辑,如果一条Todo未添加下一步,点击完成按钮时就直接完成整条Todo,如果添加了下一步,点击完成按钮时就完成下一步,所有下一步均完成后,才会完成整条Todo,另外,在添加和修改Todo时,下一步的输入框里不要提示下一步1、下一步2,只显示“下一步”就好

5、突然想起来上周发起的4个Archive任务,打开看了下4条都已经通过了Notary,目前的状态都是Ready to distribute,第4条没有任何的问题,全部绿色,前3条都有黄色的提示信息“Unable to find API request response with task ID for GET submissions”,询问ChatGPT得知,这是Xcode(Organizer/Notary UI)在向Apple Notary服务拉取公证日志(log)时失败了,常见的原因包括Apple服务端短暂异常/延迟、网络或代理导致请求被拦截、或Xcode UI的偶发BUG(任务其实已经在处理/已完成,但UI拉日志失败),怀疑可能是因为公司网络质量差导致的

6、接下来尝试用命令行形式将.app制作成.dmg,包括安装create-dmg——进入.app所在目录——生成DMG——公证DMG——Staple等步骤:

1.安装create-dmg:

brew install create-dmg

2.进入.app所在目录(在Archieve中导出时选择导出到桌面,不要cd进.app里面):

cd ~/Desktop

3.生成DMG:

create-dmg \

  –volname “chatwith” \

  –window-size 800 400 \

  –icon-size 120 \

  –icon “chatwith.app” 200 190 \

  –app-drop-link 600 185 \

  “chatwith.dmg” \

  “chatwith.app”

4.公证DMG:

xcrun notarytool submit chatwith.dmg \

  –apple-id wujinlei51@gmail.com \

  –team-id 6UY94UFR36 \

  –password xzfg-rgmk-niks-ehtt \

  –wait

5.Staple:

xcrun stapler staple chatwith.dmg

最后一步收到The staple and validate action worked!的提示之后,就说明公证票据已经成功“钉”进chatwith.dmg,即使离线,Gatekeeper也能验证,到此完成,今晚换另一台电脑安装测试

7、继续前边对DoitWith的修改,主要是明确完成Todo的逻辑,并调整下一步输入框的提示文字,针对完成Todo的逻辑,需要修改CoreData模型、修改Todo结构体、修改完成Todo的逻辑,并修改TodoRowView和GroupTodoRowView显示下一步完成状态,Cursor在进行这些修改的同时,增加了一个针对编辑Todo的功能:在EditTodoView中,当修改nextSteps时,会自动过滤掉超出范围的已完成索引,明天测试一下这个功能具体是指什么

DevLog:2026年1月13日

1、今天先解决应用签名和打包分发的问题,我对这个也不太了解,只是知道如果想要正常分发、不被macOS的Gatekeeper安全机制拦截,需要签名,Cursor检测后发现当前应用的签名方式为自动签名,可以在Xcode中打开项目,选择左侧栏的Runner,在中间栏的Signing&Capabilities中勾选Automatically manage signing,并选择Team,登录Apple Developer账号,Xcode就会自动处理签名

2、在这里还需要填写Bundle Identifier,这里默认的是com.example.chatwith,ChatGPT建议这里用反向域名+产品名(全局唯一),并且要和未来在App Store Connect/证书体系里用的一致,格式可以是com.<公司或个人>.<应用名>,且且只能用字母/数字/连字符,通常全小写更稳妥,但不要用Flutter的默认值(中间的公司或个人默认是example)

3、然后就是反复进行Archive并在ChatGPT的帮助下排查问题,比如要Enable Hardened Runtime,在账户设置中Manage Certificates——+Developer ID Application,然后Archieve——Direct Distribution上传到Notary——等待公证结果——Ready for distribution,但在等待公证结果时等了比较长的时间,ChatGPT认为一般1到5分钟,偶尔5到15分钟,极少数高峰期可能需要20到30分钟,即使失败,也能看到具体原因并进行针对性的修复

4、继续等待公证,大概两个小时依然在in progress,运行ChatGPT提供的在终端中用notarytool查看真实状态的指令

xcrun notarytool history –apple-id “<你的AppleID邮箱>” –team-id “<你的TeamID>” –password “<app专用密码>”

xcrun notarytool info <submission-id> –apple-id “<邮箱>” –team-id “<TeamID>” –password “<app专用密码>”

之后,得知并不是UI端卡住,而是确实在in progress,这种情况要么继续等待,要么重新提交一次,我选择继续等待

5、查看Archieve路径下的文件,竟然有600多M,但询问Cursor后得知当前应用打包分发后安装包大小可能在40-60M之间,比Swift版本要大很多的原因在于其中包含了FlutterMacOS.framework,即Flutter框架核心,占用了超过一半的大小,并且当前应用同时支持Intel和Apple Silicon架构,即通用二进制(Universal Binary)

6、跟ChatGPT确认了下即使在等待Notary的过程中也能修改代码,不影响继续开发,但在Xcode中构建时发现,由于之前在Xcode中其中了Hardened Runtime,禁用了JIT,但Flutter的Dart VM需要JIT编译来运行,特别是在Debug模式下,导致构建失败,于是添加了必要的权限,并重新生成了缺失的文件,构建成功,继续测试并增加功能

7、由于过往对话数据已经被清空,打开应用之后可以看到所有界面的空状态提示,其中在“选择AI模型”界面,昨天已经新增了“添加更多模型”卡片,点击可以跳转到设置-AI模型管理界面,我需要在未添加任何模型时,“选择AI模型”界面也显示“添加更多模型”卡片,并且点击可以跳转到设置-AI模型管理界面,不再显示“还没有配置模型,请前往设置中添加”的提示文字

8、修改后的效果是,没有模型时只显示“添加更多模型”卡片,有模型时在模型列表最后显示“添加更多模型”卡片,并且都可以点击跳转到设置-AI模型管理界面

9、然后添加模型,一个支持深度思考的DeepSeek官方的Reasoner,一个不支持深度思考的OpenRouter的Claude 3.7 Sonnet,用于测试后续新增的功能,首先要增加的就是上传和解读文档功能,在现有的上传图片功能上增加:

1.在AI模型管理界面,点击测试按钮时同步测试是否支持文档,测试结果和目前的“支持图片/不支持图片”在同一行显示

2.在选择AI模型界面,根据测试结果,每个模型下方的支持图片/不支持图片后面加上是否支持文档

3.消息框右边的别针图标,鼠标划过时的提示文字由“上传图片”改为“上传图片或文档”

4.点击别针图标,可通过文件选择器选择图片或文档,在支持现有的图片格式的基础上,增加对word、excel、ppt、txt、pdf等常见文档格式的支持

10、修改过程中涉及数据模型、AI模型管理界面、选择AI模型界面和消息框文件选择器,扩展了文件选择器支持格式,包括doc、docx、xls、xlsx、ppt、pptx、txt、pdf,重新在Xcode中构建,经过测试,claude 3.7模型就支持文档,但在对话中选择并上传文档后,浮窗上仍然显示“已选择图片”,并且图标显示也不正常,Xcode中出现了DB Error: 1 “table ai_messages has no column named image_paths”等错误信息,我需要将浮窗中的“已选择图片”改为“已选择附件”,如果附件是图片就显示缩略图,如果附件是文档就显示文档的扩展名,另外我在点击发送消息后,对话窗口中看不到任何内容,即使只是简单的“你好”,也收不到任何回复

11、Cursor在修改过程中,修复了数据库问题,更新了变量名,调整了界面显示并添加了文件图标(根据扩展名返回对应图标),再次测试,普通文字消息可以正常回复,图片可以正常上传、解读,文档可以正常上传,但会回复我“错误:访问被拒绝,请检查API Key权限”,但这个模型在测试时是支持文档的,调试信息中出现了这些内容:flutter: 图片加载失败: /Users/jinlei.wu/Library/Containers/com.jinleiwu.chatwith/Data/Documents/chat_images/1768290385014_文档解读测试.docx, 错误: Exception: Invalid image data,另外,我发送带有附件(图片或文档)的消息之后,消息中包含一行文字“[包含1张图片]”需要改为“[包含1个附件]”

12、本轮修改涉及数据库问题修复、文档处理逻辑(仅支持读取TXT格式的文本内容并添加到消息中,其他格式暂时先提示用户当前版本暂不支持自动提取内容)、消息显示文本更新、消息界面显示和变量名更新,Cursor指出大多数AI API不支持支持上传文档文件,如果需要支持更多文档格式,可以使用文档解析库或支持文件上传的API(如OpenAI的Assistants API)

13、先测试一下TXT格式的附件,再次遇到错误,可能是因为这个TXT的编码不是UTF-8导致的?Cursor再次修改ai_service以支持更多编码,修改后,会首先尝试UTF-8编码,如果失败就读取字节并检测BOM,如果再失败就使用Latin1作为后备,但它也指出对于GBK/GB2312等中文编码,可能会出现乱码,可以添加charset_convert或encoding包来处理GBK编码,先试试同一个附件,再看要不要添加新的包

14、测试后果然遇到了“由于您提供的文档内容是乱码,我无法直接提炼要点。这可能是因为文档编码格式不兼容导致的。”的回答,那既然要添加新的包,就让Cursor同时添加支持word文档、pdf文档和更多编码的txt文档的解析库,一通操作之后只添加了charset_converter包,可以支持多种编码格式,但针对PDF和word文档,由于Flutter生态中缺少合适的免费包,暂时只能等用户上传后提示用户手动输入内容,再次测试TXT文档已经可以正常解读

15、继续修复一些小问题,比如我在收藏消息到笔记时,目前的规则是以用户提问作为标题,以AI回答作为正文,但用户提问中如果包含附件,笔记标题就会有“[包含1个附件]”,我不需要“[包含1个附件]”,只用用户提问的纯文本作为标题就好,Cursor在收藏按钮的onPressed回调中,添加了清理附件标记的逻辑,使用纯文本作为笔记标题,再次测试问题已解决

16、针对PDF文档,Cursor在前边的修改中有建议到使用syncfusion_flutter_pdf(可能需要商业授权)或使用macOS原生的API,询问ChatGPT后了解到macOS有提供PDFKit,可以用于解读非扫描版PDF,如果是扫描版PDF,则需要使用PDFKit+Vision OCR,比较复杂,这次先让Cursor整合macOS的PDFKit,以实现对非扫描版PDF文档的解读功能

17、修改过程包含:创建PDFTextExtractor.swift(使用macOS的PDFKit框架提取PDF文本)、注册方法通道、更新Flutter代码和Xcode项目,修改后,当用户上传PDF文档时,系统会自动调用macOS PDFKit提取文本,如果成功,文本内容会被添加到消息中,如果失败(比如遇到扫描版PDF)会提示用户,测试发现已经可以解读非扫描版PDF,并且速度也挺快

18、结合目前的应用功能刷新一下README.md,其中现有的版本历史部分增加一条“支持文档输入(目前支持TXT和非扫描版PDF)”,放到“支持图片输入(多图片支持)”下面,然后在设置-关于ChatWith里,近期更新内容和README.md的版本历史部分保持一致,但需要分别匹配emoji,再次构建测试,设置-关于ChatWith页面已修改完成,但Archive的Notary依然in progress,服了,另外明天再问问Cursor能否使用macOS的textutil实现对word文档的解析(来自千问的建议)