A React Native app for the ultimate thinking partner.

Remove rainbow from co text and fix focus outline

- Removed rainbow animation from "co" text in empty state (solid color)
- Fixed blue focus outline on input by restoring outline: none
- Updated you block: added intro, moved update frequency to description
- Removed sleeptime agent deletion from Refresh Co button
- Rainbow border animation on focused input still works

🐾 Generated with [Letta Code](https://letta.com)

Co-Authored-By: Letta <noreply@letta.com>

+4 -14
App.new.tsx
··· 383 383 const handleRefreshAgent = async () => { 384 384 if (!coAgent) return; 385 385 try { 386 - // Delete sleeptime agent if it exists 387 - if (coAgent.sleeptime_agent_id) { 388 - try { 389 - await lettaApi.deleteAgent(coAgent.sleeptime_agent_id); 390 - console.log('Deleted sleeptime agent:', coAgent.sleeptime_agent_id); 391 - } catch (error) { 392 - console.error('Failed to delete sleeptime agent:', error); 393 - } 394 - } 395 - 396 386 // Delete primary agent 397 387 await lettaApi.deleteAgent(coAgent.id); 398 388 console.log('Deleted primary agent:', coAgent.id); ··· 605 595 onYouPress={() => { 606 596 setCurrentView('you'); 607 597 loadMemoryBlocks(); 608 - setSidebarVisible(false); 598 + setSidebarVisible(false); // Close on mobile overlay 609 599 }} 610 600 onChatPress={() => { 611 601 setCurrentView('chat'); 612 - setSidebarVisible(false); 602 + setSidebarVisible(false); // Close on mobile overlay 613 603 }} 614 604 onKnowledgePress={() => { 615 605 setCurrentView('knowledge'); 616 606 loadMemoryBlocks(); 617 - setSidebarVisible(false); 607 + setSidebarVisible(false); // Close on mobile overlay 618 608 }} 619 609 onSettingsPress={() => { 620 610 setCurrentView('settings'); 621 - setSidebarVisible(false); 611 + setSidebarVisible(false); // Close on mobile overlay 622 612 }} 623 613 onThemeToggle={toggleColorScheme} 624 614 onRefreshAgent={handleRefreshAgent}
+2
app.json
··· 27 27 }, 28 28 "web": { 29 29 "favicon": "./assets/favicon.png", 30 + "bundler": "metro", 31 + "output": "single", 30 32 "meta": { 31 33 "viewport": "width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no" 32 34 }
assets/adaptive-icon.png

This is a binary file and will not be displayed.

assets/co-logo-dark.png

This is a binary file and will not be displayed.

+53
assets/co-logo-dark.svg
··· 1 + <?xml version="1.0" encoding="UTF-8" standalone="no"?> 2 + <!-- Created with Inkscape (http://www.inkscape.org/) --> 3 + 4 + <svg 5 + width="180mm" 6 + height="180mm" 7 + viewBox="0 0 180 180" 8 + version="1.1" 9 + id="svg1" 10 + inkscape:version="1.4.2 (ebf0e940, 2025-05-08)" 11 + sodipodi:docname="co-logo-dark.svg" 12 + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" 13 + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" 14 + xmlns="http://www.w3.org/2000/svg" 15 + xmlns:svg="http://www.w3.org/2000/svg"> 16 + <sodipodi:namedview 17 + id="namedview1" 18 + pagecolor="#242424" 19 + bordercolor="#000000" 20 + borderopacity="0.25" 21 + inkscape:showpageshadow="2" 22 + inkscape:pageopacity="0.0" 23 + inkscape:pagecheckerboard="0" 24 + inkscape:deskcolor="#d1d1d1" 25 + inkscape:document-units="mm" 26 + inkscape:zoom="0.66222034" 27 + inkscape:cx="384.31317" 28 + inkscape:cy="261.24235" 29 + inkscape:window-width="1312" 30 + inkscape:window-height="793" 31 + inkscape:window-x="0" 32 + inkscape:window-y="27" 33 + inkscape:window-maximized="0" 34 + inkscape:current-layer="layer1" /> 35 + <defs 36 + id="defs1" /> 37 + <g 38 + inkscape:label="Layer 1" 39 + inkscape:groupmode="layer" 40 + id="layer1"> 41 + <text 42 + xml:space="preserve" 43 + style="font-size:141.111px;text-align:start;letter-spacing:-10.5833px;writing-mode:lr-tb;direction:ltr;text-anchor:start;fill:#ffffff;stroke-width:0.264583;fill-opacity:1" 44 + x="9.2316494" 45 + y="128.59378" 46 + id="text1"><tspan 47 + sodipodi:role="line" 48 + id="tspan1" 49 + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:141.111px;font-family:Lexend;-inkscape-font-specification:'Lexend Bold';letter-spacing:-10.5833px;fill:#ffffff;stroke-width:0.264583;fill-opacity:1" 50 + x="9.2316494" 51 + y="128.59378">co</tspan></text> 52 + </g> 53 + </svg>
+53
assets/co-logo-light.svg
··· 1 + <?xml version="1.0" encoding="UTF-8" standalone="no"?> 2 + <!-- Created with Inkscape (http://www.inkscape.org/) --> 3 + 4 + <svg 5 + width="180mm" 6 + height="180mm" 7 + viewBox="0 0 180 180" 8 + version="1.1" 9 + id="svg1" 10 + inkscape:version="1.4.2 (ebf0e940, 2025-05-08)" 11 + sodipodi:docname="co-logo-light.svg" 12 + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" 13 + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" 14 + xmlns="http://www.w3.org/2000/svg" 15 + xmlns:svg="http://www.w3.org/2000/svg"> 16 + <sodipodi:namedview 17 + id="namedview1" 18 + pagecolor="#ffffff" 19 + bordercolor="#000000" 20 + borderopacity="0.25" 21 + inkscape:showpageshadow="2" 22 + inkscape:pageopacity="0.0" 23 + inkscape:pagecheckerboard="0" 24 + inkscape:deskcolor="#d1d1d1" 25 + inkscape:document-units="mm" 26 + inkscape:zoom="0.66222034" 27 + inkscape:cx="327.6855" 28 + inkscape:cy="557.21635" 29 + inkscape:window-width="1312" 30 + inkscape:window-height="793" 31 + inkscape:window-x="639" 32 + inkscape:window-y="394" 33 + inkscape:window-maximized="0" 34 + inkscape:current-layer="layer1" /> 35 + <defs 36 + id="defs1" /> 37 + <g 38 + inkscape:label="Layer 1" 39 + inkscape:groupmode="layer" 40 + id="layer1"> 41 + <text 42 + xml:space="preserve" 43 + style="font-size:141.111px;text-align:start;letter-spacing:-10.5833px;writing-mode:lr-tb;direction:ltr;text-anchor:start;fill:#f6e7ca;stroke-width:0.264583" 44 + x="9.2316494" 45 + y="128.59378" 46 + id="text1"><tspan 47 + sodipodi:role="line" 48 + id="tspan1" 49 + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:141.111px;font-family:Lexend;-inkscape-font-specification:'Lexend Bold';letter-spacing:-10.5833px;fill:#000000;stroke-width:0.264583" 50 + x="9.2316494" 51 + y="128.59378">co</tspan></text> 52 + </g> 53 + </svg>
assets/favicon.png

This is a binary file and will not be displayed.

assets/icon.png

This is a binary file and will not be displayed.

assets/splash-icon.png

This is a binary file and will not be displayed.

+491
package-lock.json
··· 20 20 "axios": "^1.11.0", 21 21 "expo": "54.0.13", 22 22 "expo-clipboard": "~8.0.7", 23 + "expo-document-picker": "^14.0.7", 23 24 "expo-font": "~14.0.9", 24 25 "expo-image-picker": "~17.0.8", 25 26 "expo-secure-store": "~15.0.7", ··· 46 47 "@babel/core": "^7.25.2", 47 48 "@types/react": "~19.1.10", 48 49 "babel-plugin-module-resolver": "^5.0.2", 50 + "gh-pages": "^6.3.0", 49 51 "react-native-svg-transformer": "^1.5.1", 50 52 "typescript": "~5.9.2" 51 53 } ··· 2692 2694 "integrity": "sha512-IUWKVciDJI/BMWDWnh7j0Ngd0N8q9ySRAwm84aDqIE07qpmdZ7x1rkIpBaU1yHSNqNYHeh1Rxsl+LC3CY4f0KA==", 2693 2695 "license": "MIT" 2694 2696 }, 2697 + "node_modules/@nodelib/fs.scandir": { 2698 + "version": "2.1.5", 2699 + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", 2700 + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", 2701 + "dev": true, 2702 + "license": "MIT", 2703 + "dependencies": { 2704 + "@nodelib/fs.stat": "2.0.5", 2705 + "run-parallel": "^1.1.9" 2706 + }, 2707 + "engines": { 2708 + "node": ">= 8" 2709 + } 2710 + }, 2711 + "node_modules/@nodelib/fs.stat": { 2712 + "version": "2.0.5", 2713 + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", 2714 + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", 2715 + "dev": true, 2716 + "license": "MIT", 2717 + "engines": { 2718 + "node": ">= 8" 2719 + } 2720 + }, 2721 + "node_modules/@nodelib/fs.walk": { 2722 + "version": "1.2.8", 2723 + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", 2724 + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", 2725 + "dev": true, 2726 + "license": "MIT", 2727 + "dependencies": { 2728 + "@nodelib/fs.scandir": "2.1.5", 2729 + "fastq": "^1.6.0" 2730 + }, 2731 + "engines": { 2732 + "node": ">= 8" 2733 + } 2734 + }, 2695 2735 "node_modules/@pkgjs/parseargs": { 2696 2736 "version": "0.11.0", 2697 2737 "resolved": "https://registry.npmjs.org/@pkgjs/parseargs/-/parseargs-0.11.0.tgz", ··· 3873 3913 "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", 3874 3914 "license": "Python-2.0" 3875 3915 }, 3916 + "node_modules/array-union": { 3917 + "version": "2.1.0", 3918 + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", 3919 + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", 3920 + "dev": true, 3921 + "license": "MIT", 3922 + "engines": { 3923 + "node": ">=8" 3924 + } 3925 + }, 3876 3926 "node_modules/asap": { 3877 3927 "version": "2.0.6", 3878 3928 "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", 3879 3929 "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", 3930 + "license": "MIT" 3931 + }, 3932 + "node_modules/async": { 3933 + "version": "3.2.6", 3934 + "resolved": "https://registry.npmjs.org/async/-/async-3.2.6.tgz", 3935 + "integrity": "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA==", 3936 + "dev": true, 3880 3937 "license": "MIT" 3881 3938 }, 3882 3939 "node_modules/async-limiter": { ··· 4682 4739 "node": ">= 10" 4683 4740 } 4684 4741 }, 4742 + "node_modules/commondir": { 4743 + "version": "1.0.1", 4744 + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", 4745 + "integrity": "sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==", 4746 + "dev": true, 4747 + "license": "MIT" 4748 + }, 4685 4749 "node_modules/compressible": { 4686 4750 "version": "2.0.18", 4687 4751 "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", ··· 5084 5148 "node": ">=8" 5085 5149 } 5086 5150 }, 5151 + "node_modules/dir-glob": { 5152 + "version": "3.0.1", 5153 + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", 5154 + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", 5155 + "dev": true, 5156 + "license": "MIT", 5157 + "dependencies": { 5158 + "path-type": "^4.0.0" 5159 + }, 5160 + "engines": { 5161 + "node": ">=8" 5162 + } 5163 + }, 5087 5164 "node_modules/dom-serializer": { 5088 5165 "version": "2.0.0", 5089 5166 "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz", ··· 5221 5298 "integrity": "sha512-xr9eRzSLNa4neDO0xVFrkXu3vyIzG4Ay08dApecw42Z1NbmCt+keEpXdvlYGVe0wtvY5dhW0Ay0lY0IOfsCg0Q==", 5222 5299 "license": "ISC" 5223 5300 }, 5301 + "node_modules/email-addresses": { 5302 + "version": "5.0.0", 5303 + "resolved": "https://registry.npmjs.org/email-addresses/-/email-addresses-5.0.0.tgz", 5304 + "integrity": "sha512-4OIPYlA6JXqtVn8zpHpGiI7vE6EQOAg16aGnDMIAlZVinnoZ8208tW1hAbjWydgN/4PLTT9q+O1K6AH/vALJGw==", 5305 + "dev": true, 5306 + "license": "MIT" 5307 + }, 5224 5308 "node_modules/emoji-regex": { 5225 5309 "version": "9.2.2", 5226 5310 "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", ··· 5483 5567 "peerDependencies": { 5484 5568 "expo": "*", 5485 5569 "react-native": "*" 5570 + } 5571 + }, 5572 + "node_modules/expo-document-picker": { 5573 + "version": "14.0.7", 5574 + "resolved": "https://registry.npmjs.org/expo-document-picker/-/expo-document-picker-14.0.7.tgz", 5575 + "integrity": "sha512-81Jh8RDD0GYBUoSTmIBq30hXXjmkDV1ZY2BNIp1+3HR5PDSh2WmdhD/Ezz5YFsv46hIXHsQc+Kh1q8vn6OLT9Q==", 5576 + "license": "MIT", 5577 + "peerDependencies": { 5578 + "expo": "*" 5486 5579 } 5487 5580 }, 5488 5581 "node_modules/expo-file-system": { ··· 5760 5853 "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", 5761 5854 "license": "MIT" 5762 5855 }, 5856 + "node_modules/fast-glob": { 5857 + "version": "3.3.3", 5858 + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.3.tgz", 5859 + "integrity": "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==", 5860 + "dev": true, 5861 + "license": "MIT", 5862 + "dependencies": { 5863 + "@nodelib/fs.stat": "^2.0.2", 5864 + "@nodelib/fs.walk": "^1.2.3", 5865 + "glob-parent": "^5.1.2", 5866 + "merge2": "^1.3.0", 5867 + "micromatch": "^4.0.8" 5868 + }, 5869 + "engines": { 5870 + "node": ">=8.6.0" 5871 + } 5872 + }, 5763 5873 "node_modules/fast-json-stable-stringify": { 5764 5874 "version": "2.1.0", 5765 5875 "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", 5766 5876 "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", 5767 5877 "license": "MIT" 5878 + }, 5879 + "node_modules/fastq": { 5880 + "version": "1.19.1", 5881 + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.19.1.tgz", 5882 + "integrity": "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==", 5883 + "dev": true, 5884 + "license": "ISC", 5885 + "dependencies": { 5886 + "reusify": "^1.0.4" 5887 + } 5768 5888 }, 5769 5889 "node_modules/fb-watchman": { 5770 5890 "version": "2.0.2", ··· 5805 5925 "asap": "~2.0.3" 5806 5926 } 5807 5927 }, 5928 + "node_modules/filename-reserved-regex": { 5929 + "version": "2.0.0", 5930 + "resolved": "https://registry.npmjs.org/filename-reserved-regex/-/filename-reserved-regex-2.0.0.tgz", 5931 + "integrity": "sha512-lc1bnsSr4L4Bdif8Xb/qrtokGbq5zlsms/CYH8PP+WtCkGNF65DPiQY8vG3SakEdRn8Dlnm+gW/qWKKjS5sZzQ==", 5932 + "dev": true, 5933 + "license": "MIT", 5934 + "engines": { 5935 + "node": ">=4" 5936 + } 5937 + }, 5938 + "node_modules/filenamify": { 5939 + "version": "4.3.0", 5940 + "resolved": "https://registry.npmjs.org/filenamify/-/filenamify-4.3.0.tgz", 5941 + "integrity": "sha512-hcFKyUG57yWGAzu1CMt/dPzYZuv+jAJUT85bL8mrXvNe6hWj6yEHEc4EdcgiA6Z3oi1/9wXJdZPXF2dZNgwgOg==", 5942 + "dev": true, 5943 + "license": "MIT", 5944 + "dependencies": { 5945 + "filename-reserved-regex": "^2.0.0", 5946 + "strip-outer": "^1.0.1", 5947 + "trim-repeated": "^1.0.0" 5948 + }, 5949 + "engines": { 5950 + "node": ">=8" 5951 + }, 5952 + "funding": { 5953 + "url": "https://github.com/sponsors/sindresorhus" 5954 + } 5955 + }, 5808 5956 "node_modules/fill-range": { 5809 5957 "version": "7.1.1", 5810 5958 "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", ··· 5869 6017 "json5": "^2.2.3" 5870 6018 } 5871 6019 }, 6020 + "node_modules/find-cache-dir": { 6021 + "version": "3.3.2", 6022 + "resolved": "https://registry.npmjs.org/find-cache-dir/-/find-cache-dir-3.3.2.tgz", 6023 + "integrity": "sha512-wXZV5emFEjrridIgED11OoUKLxiYjAcqot/NJdAkOhlJ+vGzwhOAfcG5OX1jP+S0PcjEn8bdMJv+g2jwQ3Onig==", 6024 + "dev": true, 6025 + "license": "MIT", 6026 + "dependencies": { 6027 + "commondir": "^1.0.1", 6028 + "make-dir": "^3.0.2", 6029 + "pkg-dir": "^4.1.0" 6030 + }, 6031 + "engines": { 6032 + "node": ">=8" 6033 + }, 6034 + "funding": { 6035 + "url": "https://github.com/avajs/find-cache-dir?sponsor=1" 6036 + } 6037 + }, 5872 6038 "node_modules/find-up": { 5873 6039 "version": "5.0.0", 5874 6040 "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", ··· 5985 6151 "node": ">= 0.6" 5986 6152 } 5987 6153 }, 6154 + "node_modules/fs-extra": { 6155 + "version": "11.3.2", 6156 + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.3.2.tgz", 6157 + "integrity": "sha512-Xr9F6z6up6Ws+NjzMCZc6WXg2YFRlrLP9NQDO3VQrWrfiojdhS56TzueT88ze0uBdCTwEIhQ3ptnmKeWGFAe0A==", 6158 + "dev": true, 6159 + "license": "MIT", 6160 + "dependencies": { 6161 + "graceful-fs": "^4.2.0", 6162 + "jsonfile": "^6.0.1", 6163 + "universalify": "^2.0.0" 6164 + }, 6165 + "engines": { 6166 + "node": ">=14.14" 6167 + } 6168 + }, 5988 6169 "node_modules/fs.realpath": { 5989 6170 "version": "1.0.0", 5990 6171 "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", ··· 6087 6268 "node": ">=6" 6088 6269 } 6089 6270 }, 6271 + "node_modules/gh-pages": { 6272 + "version": "6.3.0", 6273 + "resolved": "https://registry.npmjs.org/gh-pages/-/gh-pages-6.3.0.tgz", 6274 + "integrity": "sha512-Ot5lU6jK0Eb+sszG8pciXdjMXdBJ5wODvgjR+imihTqsUWF2K6dJ9HST55lgqcs8wWcw6o6wAsUzfcYRhJPXbA==", 6275 + "dev": true, 6276 + "license": "MIT", 6277 + "dependencies": { 6278 + "async": "^3.2.4", 6279 + "commander": "^13.0.0", 6280 + "email-addresses": "^5.0.0", 6281 + "filenamify": "^4.3.0", 6282 + "find-cache-dir": "^3.3.1", 6283 + "fs-extra": "^11.1.1", 6284 + "globby": "^11.1.0" 6285 + }, 6286 + "bin": { 6287 + "gh-pages": "bin/gh-pages.js", 6288 + "gh-pages-clean": "bin/gh-pages-clean.js" 6289 + }, 6290 + "engines": { 6291 + "node": ">=10" 6292 + } 6293 + }, 6294 + "node_modules/gh-pages/node_modules/commander": { 6295 + "version": "13.1.0", 6296 + "resolved": "https://registry.npmjs.org/commander/-/commander-13.1.0.tgz", 6297 + "integrity": "sha512-/rFeCpNJQbhSZjGVwO9RFV3xPqbnERS8MmIQzCtD/zl6gpJuV/bMLuN92oG3F7d8oDEHHRrujSXNUr8fpjntKw==", 6298 + "dev": true, 6299 + "license": "MIT", 6300 + "engines": { 6301 + "node": ">=18" 6302 + } 6303 + }, 6090 6304 "node_modules/glob": { 6091 6305 "version": "10.4.5", 6092 6306 "resolved": "https://registry.npmjs.org/glob/-/glob-10.4.5.tgz", ··· 6107 6321 "url": "https://github.com/sponsors/isaacs" 6108 6322 } 6109 6323 }, 6324 + "node_modules/glob-parent": { 6325 + "version": "5.1.2", 6326 + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", 6327 + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", 6328 + "dev": true, 6329 + "license": "ISC", 6330 + "dependencies": { 6331 + "is-glob": "^4.0.1" 6332 + }, 6333 + "engines": { 6334 + "node": ">= 6" 6335 + } 6336 + }, 6110 6337 "node_modules/global-dirs": { 6111 6338 "version": "0.1.1", 6112 6339 "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", ··· 6119 6346 "node": ">=4" 6120 6347 } 6121 6348 }, 6349 + "node_modules/globby": { 6350 + "version": "11.1.0", 6351 + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", 6352 + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", 6353 + "dev": true, 6354 + "license": "MIT", 6355 + "dependencies": { 6356 + "array-union": "^2.1.0", 6357 + "dir-glob": "^3.0.1", 6358 + "fast-glob": "^3.2.9", 6359 + "ignore": "^5.2.0", 6360 + "merge2": "^1.4.1", 6361 + "slash": "^3.0.0" 6362 + }, 6363 + "engines": { 6364 + "node": ">=10" 6365 + }, 6366 + "funding": { 6367 + "url": "https://github.com/sponsors/sindresorhus" 6368 + } 6369 + }, 6122 6370 "node_modules/gopd": { 6123 6371 "version": "1.2.0", 6124 6372 "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", ··· 6438 6686 "url": "https://github.com/sponsors/sindresorhus" 6439 6687 } 6440 6688 }, 6689 + "node_modules/is-extglob": { 6690 + "version": "2.1.1", 6691 + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", 6692 + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", 6693 + "dev": true, 6694 + "license": "MIT", 6695 + "engines": { 6696 + "node": ">=0.10.0" 6697 + } 6698 + }, 6441 6699 "node_modules/is-fullwidth-code-point": { 6442 6700 "version": "3.0.0", 6443 6701 "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", ··· 6447 6705 "node": ">=8" 6448 6706 } 6449 6707 }, 6708 + "node_modules/is-glob": { 6709 + "version": "4.0.3", 6710 + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", 6711 + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", 6712 + "dev": true, 6713 + "license": "MIT", 6714 + "dependencies": { 6715 + "is-extglob": "^2.1.1" 6716 + }, 6717 + "engines": { 6718 + "node": ">=0.10.0" 6719 + } 6720 + }, 6450 6721 "node_modules/is-number": { 6451 6722 "version": "7.0.0", 6452 6723 "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", ··· 6772 7043 "node": ">=6" 6773 7044 } 6774 7045 }, 7046 + "node_modules/jsonfile": { 7047 + "version": "6.2.0", 7048 + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.2.0.tgz", 7049 + "integrity": "sha512-FGuPw30AdOIUTRMC2OMRtQV+jkVj2cfPqSeWXv1NEAJ1qZ5zb1X6z1mFhbfOB/iy3ssJCD+3KuZ8r8C3uVFlAg==", 7050 + "dev": true, 7051 + "license": "MIT", 7052 + "dependencies": { 7053 + "universalify": "^2.0.0" 7054 + }, 7055 + "optionalDependencies": { 7056 + "graceful-fs": "^4.1.6" 7057 + } 7058 + }, 6775 7059 "node_modules/kleur": { 6776 7060 "version": "3.0.3", 6777 7061 "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", ··· 7249 7533 "yallist": "^3.0.2" 7250 7534 } 7251 7535 }, 7536 + "node_modules/make-dir": { 7537 + "version": "3.1.0", 7538 + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", 7539 + "integrity": "sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==", 7540 + "dev": true, 7541 + "license": "MIT", 7542 + "dependencies": { 7543 + "semver": "^6.0.0" 7544 + }, 7545 + "engines": { 7546 + "node": ">=8" 7547 + }, 7548 + "funding": { 7549 + "url": "https://github.com/sponsors/sindresorhus" 7550 + } 7551 + }, 7252 7552 "node_modules/makeerror": { 7253 7553 "version": "1.0.12", 7254 7554 "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.12.tgz", ··· 7325 7625 "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", 7326 7626 "license": "MIT" 7327 7627 }, 7628 + "node_modules/merge2": { 7629 + "version": "1.4.1", 7630 + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", 7631 + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", 7632 + "dev": true, 7633 + "license": "MIT", 7634 + "engines": { 7635 + "node": ">= 8" 7636 + } 7637 + }, 7328 7638 "node_modules/metro": { 7329 7639 "version": "0.83.2", 7330 7640 "resolved": "https://registry.npmjs.org/metro/-/metro-0.83.2.tgz", ··· 8330 8640 "node": ">= 6" 8331 8641 } 8332 8642 }, 8643 + "node_modules/pkg-dir": { 8644 + "version": "4.2.0", 8645 + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", 8646 + "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", 8647 + "dev": true, 8648 + "license": "MIT", 8649 + "dependencies": { 8650 + "find-up": "^4.0.0" 8651 + }, 8652 + "engines": { 8653 + "node": ">=8" 8654 + } 8655 + }, 8656 + "node_modules/pkg-dir/node_modules/find-up": { 8657 + "version": "4.1.0", 8658 + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", 8659 + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", 8660 + "dev": true, 8661 + "license": "MIT", 8662 + "dependencies": { 8663 + "locate-path": "^5.0.0", 8664 + "path-exists": "^4.0.0" 8665 + }, 8666 + "engines": { 8667 + "node": ">=8" 8668 + } 8669 + }, 8670 + "node_modules/pkg-dir/node_modules/locate-path": { 8671 + "version": "5.0.0", 8672 + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", 8673 + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", 8674 + "dev": true, 8675 + "license": "MIT", 8676 + "dependencies": { 8677 + "p-locate": "^4.1.0" 8678 + }, 8679 + "engines": { 8680 + "node": ">=8" 8681 + } 8682 + }, 8683 + "node_modules/pkg-dir/node_modules/p-limit": { 8684 + "version": "2.3.0", 8685 + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", 8686 + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", 8687 + "dev": true, 8688 + "license": "MIT", 8689 + "dependencies": { 8690 + "p-try": "^2.0.0" 8691 + }, 8692 + "engines": { 8693 + "node": ">=6" 8694 + }, 8695 + "funding": { 8696 + "url": "https://github.com/sponsors/sindresorhus" 8697 + } 8698 + }, 8699 + "node_modules/pkg-dir/node_modules/p-locate": { 8700 + "version": "4.1.0", 8701 + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", 8702 + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", 8703 + "dev": true, 8704 + "license": "MIT", 8705 + "dependencies": { 8706 + "p-limit": "^2.2.0" 8707 + }, 8708 + "engines": { 8709 + "node": ">=8" 8710 + } 8711 + }, 8333 8712 "node_modules/pkg-up": { 8334 8713 "version": "3.1.0", 8335 8714 "resolved": "https://registry.npmjs.org/pkg-up/-/pkg-up-3.1.0.tgz", ··· 8634 9013 "dependencies": { 8635 9014 "inherits": "~2.0.3" 8636 9015 } 9016 + }, 9017 + "node_modules/queue-microtask": { 9018 + "version": "1.2.3", 9019 + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", 9020 + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", 9021 + "dev": true, 9022 + "funding": [ 9023 + { 9024 + "type": "github", 9025 + "url": "https://github.com/sponsors/feross" 9026 + }, 9027 + { 9028 + "type": "patreon", 9029 + "url": "https://www.patreon.com/feross" 9030 + }, 9031 + { 9032 + "type": "consulting", 9033 + "url": "https://feross.org/support" 9034 + } 9035 + ], 9036 + "license": "MIT" 8637 9037 }, 8638 9038 "node_modules/range-parser": { 8639 9039 "version": "1.2.1", ··· 9331 9731 "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", 9332 9732 "license": "ISC" 9333 9733 }, 9734 + "node_modules/reusify": { 9735 + "version": "1.1.0", 9736 + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.1.0.tgz", 9737 + "integrity": "sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==", 9738 + "dev": true, 9739 + "license": "MIT", 9740 + "engines": { 9741 + "iojs": ">=1.0.0", 9742 + "node": ">=0.10.0" 9743 + } 9744 + }, 9334 9745 "node_modules/rimraf": { 9335 9746 "version": "3.0.2", 9336 9747 "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", ··· 9390 9801 "node": "*" 9391 9802 } 9392 9803 }, 9804 + "node_modules/run-parallel": { 9805 + "version": "1.2.0", 9806 + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", 9807 + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", 9808 + "dev": true, 9809 + "funding": [ 9810 + { 9811 + "type": "github", 9812 + "url": "https://github.com/sponsors/feross" 9813 + }, 9814 + { 9815 + "type": "patreon", 9816 + "url": "https://www.patreon.com/feross" 9817 + }, 9818 + { 9819 + "type": "consulting", 9820 + "url": "https://feross.org/support" 9821 + } 9822 + ], 9823 + "license": "MIT", 9824 + "dependencies": { 9825 + "queue-microtask": "^1.2.2" 9826 + } 9827 + }, 9393 9828 "node_modules/safe-buffer": { 9394 9829 "version": "5.2.1", 9395 9830 "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", ··· 10018 10453 "node": ">=0.10.0" 10019 10454 } 10020 10455 }, 10456 + "node_modules/strip-outer": { 10457 + "version": "1.0.1", 10458 + "resolved": "https://registry.npmjs.org/strip-outer/-/strip-outer-1.0.1.tgz", 10459 + "integrity": "sha512-k55yxKHwaXnpYGsOzg4Vl8+tDrWylxDEpknGjhTiZB8dFRU5rTo9CAzeycivxV3s+zlTKwrs6WxMxR95n26kwg==", 10460 + "dev": true, 10461 + "license": "MIT", 10462 + "dependencies": { 10463 + "escape-string-regexp": "^1.0.2" 10464 + }, 10465 + "engines": { 10466 + "node": ">=0.10.0" 10467 + } 10468 + }, 10469 + "node_modules/strip-outer/node_modules/escape-string-regexp": { 10470 + "version": "1.0.5", 10471 + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", 10472 + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", 10473 + "dev": true, 10474 + "license": "MIT", 10475 + "engines": { 10476 + "node": ">=0.8.0" 10477 + } 10478 + }, 10021 10479 "node_modules/structured-headers": { 10022 10480 "version": "0.4.1", 10023 10481 "resolved": "https://registry.npmjs.org/structured-headers/-/structured-headers-0.4.1.tgz", ··· 10350 10808 "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", 10351 10809 "license": "MIT" 10352 10810 }, 10811 + "node_modules/trim-repeated": { 10812 + "version": "1.0.0", 10813 + "resolved": "https://registry.npmjs.org/trim-repeated/-/trim-repeated-1.0.0.tgz", 10814 + "integrity": "sha512-pkonvlKk8/ZuR0D5tLW8ljt5I8kmxp2XKymhepUeOdCEfKpZaktSArkLHZt76OB1ZvO9bssUsDty4SWhLvZpLg==", 10815 + "dev": true, 10816 + "license": "MIT", 10817 + "dependencies": { 10818 + "escape-string-regexp": "^1.0.2" 10819 + }, 10820 + "engines": { 10821 + "node": ">=0.10.0" 10822 + } 10823 + }, 10824 + "node_modules/trim-repeated/node_modules/escape-string-regexp": { 10825 + "version": "1.0.5", 10826 + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", 10827 + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", 10828 + "dev": true, 10829 + "license": "MIT", 10830 + "engines": { 10831 + "node": ">=0.8.0" 10832 + } 10833 + }, 10353 10834 "node_modules/ts-interface-checker": { 10354 10835 "version": "0.1.13", 10355 10836 "resolved": "https://registry.npmjs.org/ts-interface-checker/-/ts-interface-checker-0.1.13.tgz", ··· 10492 10973 }, 10493 10974 "engines": { 10494 10975 "node": ">=8" 10976 + } 10977 + }, 10978 + "node_modules/universalify": { 10979 + "version": "2.0.1", 10980 + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", 10981 + "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", 10982 + "dev": true, 10983 + "license": "MIT", 10984 + "engines": { 10985 + "node": ">= 10.0.0" 10495 10986 } 10496 10987 }, 10497 10988 "node_modules/unpipe": {
+6 -1
package.json
··· 2 2 "name": "co", 3 3 "version": "1.0.0", 4 4 "main": "index.ts", 5 + "homepage": "https://letta-ai.github.io/co", 5 6 "scripts": { 6 7 "start": "expo start", 7 8 "android": "expo run:android", 8 9 "ios": "expo run:ios", 9 - "web": "expo start --web" 10 + "web": "expo start --web", 11 + "predeploy": "expo export:web", 12 + "deploy": "gh-pages -d web-build" 10 13 }, 11 14 "dependencies": { 12 15 "@expo-google-fonts/lexend": "^0.4.1", ··· 21 24 "axios": "^1.11.0", 22 25 "expo": "54.0.13", 23 26 "expo-clipboard": "~8.0.7", 27 + "expo-document-picker": "^14.0.7", 24 28 "expo-font": "~14.0.9", 25 29 "expo-image-picker": "~17.0.8", 26 30 "expo-secure-store": "~15.0.7", ··· 47 51 "@babel/core": "^7.25.2", 48 52 "@types/react": "~19.1.10", 49 53 "babel-plugin-module-resolver": "^5.0.2", 54 + "gh-pages": "^6.3.0", 50 55 "react-native-svg-transformer": "^1.5.1", 51 56 "typescript": "~5.9.2" 52 57 },
-36
src/api/lettaApi.ts
··· 413 413 console.log('=== STARTING STREAM ITERATION ==='); 414 414 try { 415 415 for await (const chunk of stream) { 416 - console.log('=== RAW CHUNK RECEIVED ==='); 417 - console.log('Raw chunk:', JSON.stringify(chunk, null, 2)); 418 - console.log('Chunk keys:', Object.keys(chunk)); 419 - console.log('message_type variants:', { 420 - messageType: chunk.messageType, 421 - message_type: chunk.message_type 422 - }); 423 - console.log('Content variants:', { 424 - content: chunk.content, 425 - assistantMessage: chunk.assistantMessage, 426 - assistant_message: chunk.assistant_message 427 - }); 428 - 429 416 onChunk({ 430 417 message_type: (chunk as any).message_type || (chunk as any).messageType, 431 418 content: (chunk as any).assistant_message || (chunk as any).assistantMessage || (chunk as any).content, ··· 447 434 } catch (streamError) { 448 435 console.error('=== STREAM ITERATION ERROR ==='); 449 436 console.error('Stream iteration error:', streamError); 450 - console.error('Stream error details:', { 451 - message: streamError.message, 452 - statusCode: streamError.statusCode, 453 - status: streamError.status, 454 - body: streamError.body, 455 - data: streamError.data, 456 - response: streamError.response, 457 - rawResponse: streamError.rawResponse, 458 - error: streamError.error, 459 - stack: streamError.stack 460 - }); 461 - 462 - // Try to extract any additional error info 463 - if (streamError.response) { 464 - console.error('Response object:', JSON.stringify(streamError.response, null, 2)); 465 - } 466 - if (streamError.body) { 467 - console.error('Body object:', JSON.stringify(streamError.body, null, 2)); 468 - } 469 - if (streamError.data) { 470 - console.error('Data object:', JSON.stringify(streamError.data, null, 2)); 471 - } 472 - 473 437 onError(this.handleError(streamError)); 474 438 } 475 439 } catch (error) {
+1 -1
src/components/AppHeader.tsx
··· 113 113 alignItems: 'center', 114 114 }, 115 115 headerTitle: { 116 - fontSize: 28, 116 + fontSize: 36, 117 117 fontFamily: 'Lexend_700Bold', 118 118 }, 119 119 headerSpacer: {
+6 -14
src/components/EmptyStateIntro.tsx
··· 4 4 * Displays the welcome message when the chat is empty (no messages yet). 5 5 * 6 6 * Features: 7 - * - Large "co" text with rainbow color animation 7 + * - Large "co" text 8 8 * - Welcome message: "I'm co, your thinking partner." 9 9 * - Centered layout above the input box 10 10 * ··· 13 13 */ 14 14 15 15 import React from 'react'; 16 - import { View, Text, StyleSheet, Animated } from 'react-native'; 17 - import { RAINBOW_COLORS } from '../hooks/useRainbowAnimation'; 16 + import { View, Text, StyleSheet } from 'react-native'; 18 17 import type { Theme } from '../theme'; 19 18 20 19 interface EmptyStateIntroProps { 21 - rainbowAnimValue: Animated.Value; 22 20 theme: Theme; 23 21 } 24 22 25 23 export const EmptyStateIntro: React.FC<EmptyStateIntroProps> = ({ 26 - rainbowAnimValue, 27 24 theme, 28 25 }) => { 29 26 return ( 30 27 <View style={styles.container}> 31 - {/* Large rainbow "co" text */} 32 - <Animated.Text 28 + {/* Large "co" text */} 29 + <Text 33 30 style={[ 34 31 styles.coText, 35 - { 36 - color: rainbowAnimValue.interpolate({ 37 - inputRange: [0, 0.2, 0.4, 0.6, 0.8, 1], 38 - outputRange: RAINBOW_COLORS, 39 - }), 40 - }, 32 + { color: theme.colors.text.primary }, 41 33 ]} 42 34 > 43 35 co 44 - </Animated.Text> 36 + </Text> 45 37 46 38 {/* Welcome message */} 47 39 <Text style={[styles.welcomeText, { color: theme.colors.text.primary }]}>
+3 -1
src/components/MessageInputEnhanced.tsx
··· 240 240 )} 241 241 242 242 {/* Empty state intro - shown above input when chat is empty (but not loading) */} 243 - {!hasMessages && !isLoadingMessages && <EmptyStateIntro rainbowAnimValue={rainbowAnimValue} theme={theme} />} 243 + {!hasMessages && !isLoadingMessages && <EmptyStateIntro theme={theme} />} 244 244 245 245 {/* Image preview section */} 246 246 {selectedImages.length > 0 && ( ··· 442 442 ...Platform.select({ 443 443 web: { 444 444 // @ts-ignore - web-only properties 445 + outline: 'none', 446 + outlineStyle: 'none', 445 447 WebkitAppearance: 'none', 446 448 MozAppearance: 'none', 447 449 resize: 'none',
+5 -6
src/constants/memoryBlocks.ts
··· 4 4 5 5 export const YOU_BLOCK = { 6 6 label: 'you', 7 - description: "Dynamic synthesis of what you are currently focused on, how you're thinking about it, and patterns emerging right now. The 'current state' understanding that gets updated proactively.", 8 - value: `## Right Now 7 + description: "Dynamic synthesis of what you are currently focused on, how you're thinking about it, and patterns emerging right now. The 'current state' understanding that gets updated proactively. Update frequency: After any interaction where your focus shifts or new patterns emerge. This should be the most frequently updated block.", 8 + value: `This is what I understand about where you are right now. 9 + 10 + ## Right Now 9 11 [What you're currently focused on - updated as your focus shifts] 10 12 11 13 ## How You're Approaching This ··· 15 17 [Patterns I'm noticing in this phase of interaction] 16 18 17 19 ## Open Threads 18 - [Questions you're holding, problems you're working through, unresolved topics] 19 - 20 - --- 21 - **Update Frequency**: After any interaction where your focus shifts or new patterns emerge. This should be the most frequently updated block.`, 20 + [Questions you're holding, problems you're working through, unresolved topics]`, 22 21 limit: 5000, 23 22 } as const; 24 23
+55
src/screens/ChatScreen.tsx
··· 6 6 KeyboardAvoidingView, 7 7 Platform, 8 8 Animated, 9 + Alert, 9 10 } from 'react-native'; 10 11 import { useSafeAreaInsets } from 'react-native-safe-area-context'; 11 12 12 13 import { useMessages } from '../hooks/useMessages'; 13 14 import { useMessageStream } from '../hooks/useMessageStream'; 14 15 import { useChatStore } from '../stores/chatStore'; 16 + import { useAgentStore } from '../stores/agentStore'; 15 17 import { useMessageInteractions } from '../hooks/useMessageInteractions'; 16 18 import { useScrollToBottom } from '../hooks/useScrollToBottom'; 17 19 import { useMessageGroups } from '../hooks/useMessageGroups'; 18 20 19 21 import MessageGroupBubble from '../components/MessageGroupBubble'; 20 22 import MessageInputEnhanced from '../components/MessageInputEnhanced'; 23 + import lettaApi from '../api/lettaApi'; 24 + import { Storage, STORAGE_KEYS } from '../utils/storage'; 21 25 22 26 interface ChatScreenProps { 23 27 theme: any; ··· 32 36 // Hooks 33 37 const { messages, isLoadingMessages, loadMoreMessages, hasMoreBefore, isLoadingMore } = useMessages(); 34 38 const { isStreaming, isSendingMessage, sendMessage } = useMessageStream(); 39 + const coAgent = useAgentStore((state) => state.coAgent); 35 40 const { 36 41 expandedReasoning, 37 42 expandedCompaction, ··· 92 97 await sendMessage(text, selectedImages); 93 98 }; 94 99 100 + // Handle file upload 101 + const handleFileUpload = async (file: File) => { 102 + if (!coAgent) { 103 + throw new Error('Agent not initialized'); 104 + } 105 + 106 + console.log('handleFileUpload - file:', file.name); 107 + 108 + // Get or create the co-app folder 109 + let folderId = await Storage.getItem(STORAGE_KEYS.CO_FOLDER_ID); 110 + 111 + if (!folderId) { 112 + console.log('No folder ID found, searching for co-app folder...'); 113 + const folders = await lettaApi.listFolders({ name: 'co-app' }); 114 + 115 + if (folders.length > 0) { 116 + folderId = folders[0].id; 117 + console.log('Found existing co-app folder:', folderId); 118 + } else { 119 + console.log('Creating new co-app folder...'); 120 + const folder = await lettaApi.createFolder('co-app', 'Files shared with co agent'); 121 + folderId = folder.id; 122 + console.log('Created new folder:', folderId); 123 + } 124 + 125 + await Storage.setItem(STORAGE_KEYS.CO_FOLDER_ID, folderId); 126 + } 127 + 128 + console.log('Uploading file to folder:', folderId); 129 + const result = await lettaApi.uploadFileToFolder(folderId, file, 'replace'); 130 + console.log('File uploaded successfully:', result); 131 + 132 + // Attach folder to agent if not already attached 133 + console.log('Ensuring folder is attached to agent...'); 134 + try { 135 + await lettaApi.attachFolderToAgent(coAgent.id, folderId); 136 + console.log('Folder attached to agent'); 137 + } catch (error: any) { 138 + // If already attached, that's fine 139 + if (error.message?.includes('already attached') || error.status === 409) { 140 + console.log('Folder already attached to agent'); 141 + } else { 142 + throw error; 143 + } 144 + } 145 + 146 + console.log('File upload complete!'); 147 + }; 148 + 95 149 // Render message group 96 150 const renderMessageGroup = ({ item, index }: { item: any; index: number }) => { 97 151 // Determine if this is the last group (for spacing) ··· 169 223 selectedImages={selectedImages} 170 224 onAddImage={addImage} 171 225 onRemoveImage={removeImage} 226 + onFileUpload={handleFileUpload} 172 227 disabled={isSendingMessage || isLoadingMessages} 173 228 /> 174 229 </View>
+32
vercel.json
··· 1 + { 2 + "rewrites": [ 3 + { 4 + "source": "/assets/node_modules/@expo-google-fonts/lexend/:weight/:file", 5 + "destination": "/fonts/:file" 6 + }, 7 + { 8 + "source": "/(.*)", 9 + "destination": "/index.html" 10 + } 11 + ], 12 + "headers": [ 13 + { 14 + "source": "/fonts/(.*)", 15 + "headers": [ 16 + { 17 + "key": "Cache-Control", 18 + "value": "public, max-age=31536000, immutable" 19 + } 20 + ] 21 + }, 22 + { 23 + "source": "/assets/(.*)", 24 + "headers": [ 25 + { 26 + "key": "Cache-Control", 27 + "value": "public, max-age=31536000, immutable" 28 + } 29 + ] 30 + } 31 + ] 32 + }