Skip to content
HN On Hacker News ↗

GitHub - zakirullin/files.md: 🌱 Your life in plain .md files

▲ 720 points 355 comments by zakirullin 6d ago HN discussion ↗

Pangram verdict · v3.3

We believe that this document is fully human-written

1 %

AI likelihood · overall

Human
100% human-written 0% AI-generated
SEGMENTS · HUMAN 6 of 6
SEGMENTS · AI 0 of 6
WORD COUNT 1,867
PEAK AI % 1% · §4
Analyzed
May 18
backend: pangram/v3.3
Segments scanned
6 windows
avg 311 words each
Distribution
100 / 0%
human / AI fraction
Verdict
Human
Pangram v3.3

Article text · 1,867 words · 6 segments analyzed

Human AI-generated
§1 Human · 1%

A simple application for your .md files.

You can store whole your life:

📌 Notes 📝 Documents, Projects 💚 Journal, Habits ✅ Checklists, Tasks

All in plain .md files, local-first. LLM-friendly. Try it out: app.files.md (Beta) Another note taking app? Maybe. But this time:

Only necessary features, restrictions foster creativity No need to install anything, all you need is a browser Works offline Local first, you own all your files Free and open source, you can tweak it however you want Extremely simple code. One person or an LLM can fit the whole project in head Portable, no build systems, just open web/index.html Out of the box synchronization The server is just one binary (or use iCloud/Dropbox/Google Drive for sync) Telegram chatbot for on-the-go access to your files

How to use

Open app.files.md in Chrome browser Click "Install files.md" on the right side of the address bar:

Open a local folder to persist changes Occasionally hit force-refresh (Cmd+Shift+R) to get new updates.

Dump your thoughts You can use chat to quickly dump your thoughts.

It will be synchronized across all devices. Open the chat and send a message:

Choose where to save (can do later):

With this flow you can quickly save notes, journal and checklists. Save things in the chatbot Open the chat, write something and press Enter:

That's it. Telegram Bot Other messengers will follow How to grow your knowledge base Connect ideas. Let them compound. Think through.

I used app.files.md to grow my knowledge about brain and software development I added new notes to either brain or dev folders.

§2 Human · 1%

One idea per note I made connections between the relevant notes in the web app (type [) Everything is connected, just as in our brain I spent time travelling through the notes and thinking it through At some point, brain and dev notes appeared very related An interconnection between domains produced an insight I wrote an article based on that insight: Cognitive Load in Software Development

All this activity helped me to:

Think deeply (which is very important in the AI-age) Think systematically and see the bigger picture Write insightful texts

To achieve all that, you'll have to use your brain, not advanced templates or AI workflows.

Start with no structure at all, 0 folders One idea per note Every note should be understood without context Apply new knowledge immediately, don't save it for future self Link related notes Revisit your notes and think through

My friends and I have been using this simple setup for five years, and it works well. Second Brain? I'll quote I Deleted My Second Brain:

Obsidian is a brilliant piece of software. I love it, dearly. But like anything, without restraint, it can also be a trap. Markdown files in nested folders. Plugins that track your productivity. Graph views that suggest omniscience. There’s an illusion of mastery in watching your notes web into constellations. But constellations are projections. They tell stories. They do not guarantee understanding. When I first started using PKM tools, I believed I was solving a problem of forgetting. Later, I believed I was solving a problem of integration. Eventually, I realized I had created a new problem: deferral. The more my system grew, the more I deferred the work of thought to some future self who would sort, tag, distill, and extract the gold. That self never arrived.

The Second Brain is thrilling. Advanced guru templates, plugins and AI workflows... One wants to scrape the wisdom of the whole internet. There's some beauty in this neat system. Every new note brings dopamine. Second Brain gets better and better. However, the first brain never actually gets smarter. And that's an issue - in the AI age, your first brain is as valuable as ever. Use your brain to think through the notes.

§3 Human · 1%

Notes can prevent experience

Reading and taking notes can easily fool us into believing that we understand a text We think we understand, but in reality we just know At some point our "knowing" is so good, that we start feeling that we actually do it (or at least tried)

The worst thing is that we don’t let new experiences emerge because we already have knowledge. It's a knowledge barrier. Life gives us opportunities to live through new experiences, but we refuse, because "we already know". Self-help through reading and taking notes? 🧘‍ Harm caused at the emotional level must be healed at the emotional level. Not through intellectual work and taking notes. Reading without action is entertainment. A form of procrastination. No amount of self-help books can heal emotional wounds. What can help is psychotherapy, rescripting and chair work. Meditation. Healing happens by feeling. When to take notes If your goal is to:

Develop a deeper, more structured understanding of something Do research Write an article or a book

Then taking notes is perfectly fine. Files structure You don't have to think about the structure, it is predefined. Although, you're free to use whatever structure you want.

Chat: Chat.md Notes: brain/Note.md, <category>/*.md Checklists: Read.md, Watch.md, Shop.md, MyChecklist_.md Journal: journal/2024.08 August.md Tasks: Later.md Habits: habits/Ate consciously.md, habits/*.md Images: media/* (png, jpg, webp, gif) Archive: archive/*.md Config: config.json

Scheme is also available at files.md/llms.txt. You can copy-paste it into CLAUDE.md or AGENTS.md, so that your AI agent would understand the structure. Hotkeys

Hotkey Action

[ Insert a link to a file

Cmd+P / Ctrl+P Open file search modal

Cmd+N / Ctrl+N New file

Cmd+M / Ctrl+M Move file

Cmd+D / Ctrl+D Delete file

Cmd+Enter / Ctrl+Enter Open chat

Cmd+Shift+Enter / Ctrl+Shift+Enter Toggle chat dialog

Cmd+[ / Ctrl+[ Go to previous file

Cmd+] / Ctrl+] Go

§4 Human · 1%

to next file

Cmd+~ / Ctrl+~ Toggle sidebar

Cmd+B / Ctrl+B Toggle bold

Cmd+I / Ctrl+I Toggle italic

Cmd+Y / Ctrl+Y Insert checkbox

Cmd/Ctrl + Click Copy inline text / open link

Ctrl+Cmd+Space Insert emoji (macOS)

Useful scripts for your files All scripts are in cmd and can be run inside your files directory. Install Go first. Add Whoop metrics to journal go run /abs/path/to/files.md/cmd/whoop/whoop.go

Convert wikilinks to markdown links Convert [[wikilinks]] to standard [Name](/path.md) (--dry-run available): go run /abs/path/to/files.md/cmd/tomdlinks/tomdlinks.go .

Insert backlinks Adds links back to referencing files (--dry-run available): go run /abs/path/to/files.md/cmd/backlink/backlink.go

Shift journal timestamps Shift timestamps in journal files by N hours (useful after timezone change): go run /abs/path/to/files.md/cmd/shifttime/shifttime.go

Documentation Deploy on your own server Chatbot Sync flow Integration tests Repository structure

web - web app (PWA), index.html is an entrypoint web/lib - frontend libs cmd/server - entrypoint for server cmd/*/ - useful scripts for .md files server/bot.go - bot server/sync/ - sync API server code vendor - backend libs tests - E2E tests, test both the web app and the server

How to contribute

Junior developers should be able to understand the code Ideally, every PR should remove or simplify code, not add it The less code we have, the more flexible we are All dependencies are our code and responsibility. So, avoid dependencies if possible Code should be self-sufficient, so vendor and web/lib folders are included in the repository Do we really need this feature? Will it help us to do the real job, or does it just give dopamine?

Refer to this guide for more comprehensive rules.

§5 Human · 1%

Backend guidelines

We write tests We don't use get* prefix for methods No panics, errors are part of business logic If we are ignoring an error - we leave a WHY comment We wrap errors all the time, we should add method's context No iterators for client code We prefer real implementations or at least fakes over mocks and stubs Imports should only be renamed to avoid a name collision with other imports With portability in mind, everything is stored in plain .md files

Frontend guidelines

Use PATCHED keyword if you modify libs in-place It would be fantastic if, one day, we replaced CodeMirror with our own tiny implementation No build systems, in 10 years we will open /web/index.html and it should just work Don't forget that awaits between lock check and lock acquire can cause race condition Avoid flaky e2e tests. First we get negative emotions, then we stop running all the tests Most bugs are caused due to race conditions, when an async flow is interrupted mid through

Glossary

filename - a filename with extension, like "note.md" (USE THIS AS ID) header - an extension-stripped and capitalized filename, like "Note" body - file's content dir - a dir that is meant to store notes under some category, like "happiness" userID - chatID. For the most part we're only using chatID as userID (PM with the bot) ctime for file - data blocks or metadata change time: file's ownership, location, file type and permission settings changed time. Parent folder renaming won't affect, moving the file does affect, renaming the file does affect. We need this to track file's location changes, like to understand when it was moved to archive, to track task's angry level etc mtime for file - mtime (modification time) for a file refers to the time when the contents of the file were last modified. Unlike ctime, it is not affected by changes to the file's metadata, such as ownership, permissions, or renaming. We rely on that for synchronization. ctime for dir - adding or removing files or subdirectories (similar to mtime plus inode changes like renaming files)

Any file can be uniquely identified by filename and dir.

§6 Human · 1%

We only support one level of nesting. Performance The project is blazing fast :) If you're afraid of using files or mutexes unnecessarily for performance reasons, take a look at this: Mutex lock/unlock = 25 ns Read 4K randomly from SSD = 150,000 ns 1 ms = 1,000,000 ns

ADRs (Architecture Decision Records)

06.05.2026 Moved from Today.md to Chat.md. CustDev showed that users have trouble grasping "chat" concept. And besides, "open chat" phrase has meaning in both bot and webapp. 02.05.2026 Now hide-token runs synchronously on every change, previously it had 100ms debounce which caused jitter on by word removals in links and formatted texts. 06.05.2026 Merged Inbox.md and Today.md to Today.md. Inbox name is too abstract, productivity-related and GTD-ish. I want calmness and simplicity. Today is like "the page I live in chat". 23.04.2026 Moved from API_HOST, APP_HOST to API_URL, APP_URL. For different environments it's better to provide more information like desired schema in configuration. 22.04.2026 Inbox entries in the bot are now identified by a stable content hash (fs.Hash of the block with the - [ ] /- [x] marker stripped) instead of a positional index, so a button keeps pointing at the right line even if other entries are added/removed/completed in between. 06.05.2026 It was mentally taxing to see two buttons/messages "to inbox" and "to chat", it was not as mentally easy just to drop a task for chat. Because it went to inbox, and 1 more click needed. That one click was the reason adding new tasks became frustrating. I let go of two different flow, and now everything goes to inbox, and every item is inbox is a markdown checklist item. As a bonus, PWA app is now very handy as it shows tasks for chat by default. Also, maybe "inbox" is a mentally overloaded term, and "chat" sounds better.