惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

V
V2EX
爱范儿
爱范儿
Martin Fowler
Martin Fowler
T
The Blog of Author Tim Ferriss
B
Blog RSS Feed
博客园 - 聂微东
G
GRAHAM CLULEY
Engineering at Meta
Engineering at Meta
Threat Intelligence Blog | Flashpoint
Threat Intelligence Blog | Flashpoint
WordPress大学
WordPress大学
Scott Helme
Scott Helme
AI
AI
S
Security Affairs
T
Threat Research - Cisco Blogs
M
MIT News - Artificial intelligence
T
Troy Hunt's Blog
H
Hackread – Cybersecurity News, Data Breaches, AI and More
人人都是产品经理
人人都是产品经理
AWS News Blog
AWS News Blog
T
Threatpost
Cyberwarzone
Cyberwarzone
www.infosecurity-magazine.com
www.infosecurity-magazine.com
U
Unit 42
V
Vulnerabilities – Threatpost
J
Java Code Geeks
博客园 - Franky
月光博客
月光博客
Blog — PlanetScale
Blog — PlanetScale
NISL@THU
NISL@THU
D
Docker
小众软件
小众软件
N
News and Events Feed by Topic
Microsoft Security Blog
Microsoft Security Blog
Y
Y Combinator Blog
A
Arctic Wolf
D
DataBreaches.Net
云风的 BLOG
云风的 BLOG
Forbes - Security
Forbes - Security
量子位
PCI Perspectives
PCI Perspectives
美团技术团队
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
I
InfoQ
Security Archives - TechRepublic
Security Archives - TechRepublic
有赞技术团队
有赞技术团队
腾讯CDC
P
Proofpoint News Feed
S
Security @ Cisco Blogs
G
Google Developers Blog
C
Cisco Blogs

DEV Community

Authentication Security Deep Dive: From Brute Force to Salted Hashing (With Java Examples) Why AI Systems Don’t Fail — They Drift Spilling beans for how i learn for exam😁"Reinforcement Learning Cheat Sheet" I Replaced Chrome with Safari for AI Browser Automation. Here's What Broke (and What Finally Worked) How Python Borrows Other People's Work The $40 Architecture: Processing 1 Billion API Requests with 99.99% Uptime Vibe Coding: A Workflow Guide (From Zero to SaaS) Most webhook security guides protect the wrong side. The scary part is delivery. Headless CMS for TanStack Start: Build a Blog with Cosmic EU Age Verification App "Hacked in 2 Minutes" — What Actually Happened Comfy Cloud’s delete function does not actually remove files Running AI Models on GPU Cloud Servers: A Beginner Guide Event-driven media intelligence with AWS Step Functions and Bedrock I scored 500 AI prompts across 8 quality dimensions — here's what broke How to Call Google Gemini API from Next.js (Free Tier, No Backend Needed) The Portal Protocol: Reclaiming Human Connection in the Age of AI How to Fix Your Team's Scattered Knowledge Problem With a Self-Hosted Forum Intro to tc Cloud Functors: A Graph-First Mental Model for the Modern Cloud Designing Multi-Tenant Backends With Both Ownership and Team Access I Built a Neumorphic CSS Library with 77+ Components — Here's What I Learned PostgreSQL Performance Optimization: Why Connection Pooling Is Critical at Scale Cómo construí un SaaS multi-rubro para gestionar expensas en Argentina con FastAPI + Vue 3 🚀 I Built an Ethical Hacking Scanner Tool – Open Source Project I Replaced /usage and /context in Claude Code With a Single Statusline A Pythonic Way to Handle Emails (IMAP/SMTP) with Auto-Discovery and AI-Ready Design I Collected 8.9 Million Polymarket Price Points — Here's What I Found About How Markets Really Move EcoTrack AI — Carbon Footprint Tracker & Dashboard Everyone's Using AI. No One Agrees How. 5 self-hosted ebook managers worth trying in 2026 Building Your First AI Agent with LangChain: From Chatbot to Autonomous Assistant Common SOC 2 Failures (Real World) Stop Vibe-Checking Your AI App: A Practical Guide to Evals How to Use SonarQube and SonarScanner Locally to Level Up Your Code Quality Your Next To-Do App Is Dead — I Replaced Mine with an OpenClaw AI Sign a Nostr event in 60 lines of Python using coincurve — no nostr-sdk, no nbxplorer, no rust toolchain ITGC Audit Explained Like You’re in Big 4 Patch Tuesday abril 2026: Microsoft parcha 163 vulnerabilidades y un zero-day en SharePoint Stop scraping everything: a better way to track competitor price changes Listing on MCPize + the Official MCP Registry while routing payments OUTSIDE the marketplace — how I kept 100% of my x402 revenue Building an AI-Powered Risk Intelligence System Using Serverless Architecture Why We Ripped Function Overloading Out of Our AI Toolchain Testing AI-Generated Code: How to Actually Know If It Works SaaS Churn Is Killing Your Business. Here Is What to Do About It (Without a Support Team) The Speed of AI Is No Longer Linear - And Self-Improving Models Are Why How to Implement RBAC for MCP Tools: A Practical Guide for Engineering Teams From Standard Quote to Persuasive Proposal: AI Automation for Arborists I built a CLI that scaffolds complete multi-tenant SaaS apps Axios CVE-2025–62718: The Silent SSRF Bug That Could Be Hiding in Your Node.js App Right Now The dashboard that ended our friendship Data Pipelines Explained Simply (and How to Build Them with Python) The Hidden Cost of AI Systems Nobody Talks About. undefined vs undeclared, and how typeof behaves Switching from file-based jobs to NATS/Kafka in Rust without changing code io_uring Adventures: Rust Servers That Love Syscalls Why Agentic AI is Killing the Traditional Database The POUR principles of web accessibility for developers and designers Quantum Neural Network 3D — A Deep Dive into Interactive WebGL Visualization How To Install Caveman In Codex On macOS And Windows Automation Pipeline Reliability: Why Your Workflow Breaks When Nobody Is Watching I Built an 'Open World' AI Coding Agent — It Works From ANY Folder From Freelancing to Product: A Tech Service Company's SaaS Transformation China's AI Giants: Adding Tencent Hunyuan & ByteDance Doubao to AI University (74 Providers) On the Vibe Coders and Their Lies clerk: Auto-Summarize Your Claude Code Sessions AI Weekly — 2026/04/10–04/17 | The Model Lockdown Is Here, but the Toolchain Is the Real Battleground AI 週報 — 2026/04/10–2026/04/17 模型封鎖潮來了,但工具鏈才是真戰場 Maybe this is how Open-Source apps are born... 🚀 Fine-Tune LLMs with LoRA and QLoRA: 2026 Guide tRPC v11 + Next.js App Router: End-to-End Type Safety Without the Boilerplate ShadCN UI in 2026: Why I Stopped Installing Component Libraries and Started Owning My Components SaaS Billing in React Server Components: Stripe + Supabase Without a Single `useEffect` Join our DEV Weekend Challenge — $1,000 in Prizes Across TEN winners! Submissions Due April 20 at 6:59 AM UTC. Implementing FSRS Spaced Repetition in Flutter + Supabase — Adding Memory Science to an AI Learning App "I Texted My Localhost From the Train — Claude Code Fixed the Bug Before I Got Home" I Built a Sales Prep AI and It Went Deeper Than Expected Design to Code #2: One JSON, Eleven Outputs Solving the 100M-Row Problem: A Summary Table Pattern for High-Volume Push Notification Logs Flutter Web With Wasm: What Actually Changes For Developers I Built 50 Royalty-Free Soundtracks for My Side Project in a Weekend Using AI Music Generation The Vibe Coding Security Checklist: 7 Things to Check Before You Ship Stop Letting Googlebot Guess Fix Your React App's SEO Right Desconstruindo o Streaming do LinkedIn: Como Criar um Engine de Extração de Vídeo de Alta Performance com HLS e FFmpeg (EDA Part-1) EDA (Exploratory Data Analysis) Explained With Real Life — Why Looking at Your Data Is the Most Important Step in Machine Learning Brand Relationship Management at Scale: Our 4-Touch Outreach System for 200+ Brands Why String.fromEnvironment() Might Return an Empty String in Dart JGuardrails 1.0.0 — Hardening Java LLM Apps Against Jailbreaks, Toxicity, and Prompt Injection Plan and Schedule a Full Week of Threads Content From One Claude Conversation Coding Cat Oran Ep3, Five Tables Changed Everything Updated: BFF Pattern I'm done watching freelancers get buried by 200 proposals. So I'm building the alternative. This is my first post BFS Algorithm in Java Step by Step Tutorial with Examples Tracking LLM Pricing Monthly: An Open Dataset for 22 AI Models How We Measure Content ROI on a Comparison Site: Revenue Attribution Without Perfect Data Introducing Nova AI Ops: The AI-Native Operating System for SRE Teams I built a free desktop video downloader for Windows — Grabbit How Talkie OCR Helps Vision-Impaired & Dyslexic Users Read the World Around Them VRCFaceTracking安装和iPhone面捕配置教程,有bug Even CrowdStrike Can't See Your Agents The Automation Gold Rush: What n8n Workflows and Claude Are Opening Up for Developers Right Now
Kakoune spoiled me
Rickard Andersson · 2026-06-22 · via DEV Community

I write this in an editor called Kakoune. I started using it almost exactly two months ago as an experiment because I was running into issues with NeoVim: configuration errors/warnings even though (or because) I didn't change anything, incompatible dependencies causing issues, and a few minor other issues.

These types of issues aren't really showstoppers in many cases; the problem was really the feeling I had about them. I didn't feel like I wanted to fix any of them. It was the clearest signal I could get that maybe NeoVim isn't really for me anymore. Maybe I'd just changed and it was time to move on to something else.

NeoVim but less, and my own?

At first that "something else" was just NeoVim but with all my plugins (except the ones I made myself) deleted, starting over from scratch. I know from experience with many other things that this is really the ideal for me in most cases; I simply don't want to use other people's software if I can avoid it, and sometimes the feature that other people implement is best skipped entirely.

So I looked into what I would have to do to make this work, but there was really only one major showstopper that put the breaks on the entire idea. In the interest of not being unnecessarily inflammatory: I think Lua is a poor choice for a plugin language, and I think writing Lua for NeoVim is a particularly poor experience on top of that.

So what are the alternatives here, then?

What about Emacs?

Emacs? I think Emacs is a great concept, but once you've used any Lisp I don't know that it's possible to use elisp without gritting your teeth. It's especially grating to use elisp after using something more well designed like Racket, or basically any Scheme implementation.

Helix

Some time ago I heard about Helix, which was supposed to make editing more intuitive than Vim by placing movements before verbs. I briefly tried it once but found it confusing. I wasn't ready for that shift and it seemed pointless to me at the time.

I considered Helix this time around, but it became clear that I was going to have to rely on whatever the Helix people had decided to put in the editor if I wanted to use it. This is a non-starter, because I'm just opting in to whatever, with no real recourse to change, add or remove things.

Kakoune

Back when I tried Helix I also heard that it was inspired by an editor called Kakoune. It had the same type of confusing inversion of movement-verb-order, but it also had something a lot more interesting: It's made to call other programs. That part stuck out to me a lot more than any kind of editing quirk, because it suggested that you didn't really want or need any particular blessed scripting language to be prominent.

The Kakoune manual has a very clear and telling section in its "Writing scripts" section:

Interaction with external tools from a Kakoune session is supported through the use of scripts. Once loaded by the editor (either automatically or manually), they allow extending the functionalities provided by default through commands and hooks.

Their implementation should be kept as simple as possible, as they are not meant to be generic tools themselves but a mere API to actual software.

"a mere API to actual software". Your actual software is written in other languages, because Kakoune is not trying to have you create grand cathedrals in its scripting language, it's not trying to give you a programming language that you can solve anything in, it's just trying to optimize for handling the results of other programs.

Writing "actual software" is easy

Like most programmers who've been doing this for a while I've got a bunch of languages I'm very comfortable making things in, and solving just about any problem is really just a matter of thinking about the solution's architecture, the features and attributes I want the solution to have, and the tools that are needed to create that solution. In practice, for me, this means that I'm going to pick Odin as the implementation language about 19/20 times. This is easy, straight forward, and it's what I want to do in order to have things work. I can count on zero hands the amount of times I've wanted to use an editor's scripting language to solve a problem; it has always just been a necessity because things are designed that way.

How do I use Kakoune now?

I use zero external plugins, all of the functionality I use is either shipped with Kakoune or I've written it myself. I solve the exact problems I'm actually having, which means that I don't create kitchen sink solutions like writing my own LSP clients/servers in order to solve things, because it's not actually the thing I want. I often want something more specific, and I can often solve that much more easily.

Odin Documentation Lookup

From previous work (on my livestream), I had already created a documentation lookup program, and so I just integrated that into Kakoune with tab-completion for the Odin core library folders. This was very straight forward to integrate and solves almost all of my code discovery, which is a large part of what I used to use LSP for:

define-command doc-odin -override -docstring "Look up a Odin module" -params 1 %{
    evaluate-commands %sh{
        buffer_name=$(echo "*odin-lookup-$1*" | sed 's/\//-/g' )
        echo fifo -name $buffer_name -- lookup "$ODIN_ROOT/$1"
        echo set-option buffer="$buffer_name" filetype markdown
    }
}

complete-command -menu doc-odin shell-script-candidates %{
    $kak_config/scripts/shell-complete-odin-core.sh
}

#!/usr/bin/env bash

pushd $ODIN_ROOT/
fd -t d . core vendor
popd

A build runner

With NeoVim I had resorted to creating my own build-script runner where I could pick which build script I was going to run and get the results in-editor. I recreated this in Kakoune by simply reading a JSON-file from the project directory that specified which build command to run, then an error pattern to pick up, and plugging into the already existing make integration that Kakoune has to be able to jump to positions of errors. With some basic (and eventually some not so basic) knowledge of jq this was basically just stitching Kakoune + two shell scripts together, in order to get an actual nice build/edit/rebuild workflow:

define-command pick-build-command -docstring "Allows the user to choose a build command" \
-override %{
    prompt -menu -shell-script-candidates %{
        jq "keys[]" ./build-commands.json
    } "Build command: " %{
        evaluate-commands %sh{
            $kak_config/scripts/set-build-command.sh "$kak_text"
        }
    }
}

The most interesting (and maybe somewhat unintuitive at first) thing about the above script is that it runs evaluate-commands with a %sh{ ... } block. This means that whatever the program we call outputs, we'll execute as Kakoune commands. Our set-build-command.sh script reflects this:

#!/usr/bin/env bash

BUILD_CONFIGURATION="$1"

BUILD_COMMAND=`jq ".$BUILD_CONFIGURATION.command" ./build-commands.json`
ERROR_PATTERN=$(jq --raw-output ".$BUILD_CONFIGURATION.error_pattern" ./build-commands.json)

echo "set-option global makecmd $BUILD_COMMAND"
echo "set-option global make_error_pattern \"$ERROR_PATTERN\""

rg for searching

I've created an rg command that will run rg with a specific pattern in the project, and trivially created a filetype called rg where pressing enter on a given result will open the matching line in the buffer:

define-command rg -override -params 1.. -docstring "rg from CWD" %{
    fifo -name *rg* -- rg --line-number --column %arg{@}
    set-option buffer=*rg* filetype rg 
}

define-command rg-go-to-file-line -hidden -override -params 0 %{
    execute-keys g h 3t: s \A^([^:\n]+):(\d+):(\d+)\z<ret>
    edit %reg{1} %reg{2} %reg{3}
}

The most interesting part above is that you can really do some interesting things just by stitching Kakoune commands together. In this script for going to a matching line we execute the keys for going to the beginning of a line, selecting everything between the beginning and the third colon we find on a line, then selecting the filename, line and column into registers, then editing <filename> <line> <column>.

I have a similarly Kakoune-centric solution for toggling markdown checkboxes:

define-command markdown-toggle-checkbox -override -docstring "Toggles a markdown checkbox" %{
    try %{
        execute-keys -draft x 1s '\[( )\]'<ret> r x
    } catch %{
        try %{
            execute-keys -draft x 1s '\[(x)\]'<ret> r <space>
        } catch %{
        }
    }
}

The try/catch pairs here make it so that if the text we are selecting with 1s (select inside of selection, i.e. narrow down our selection) fails, we either do a fallback or if the fallback fails we do nothing at all.

Creating a command center, just because I can

I've also done things with Kakoune that weren't strictly necessary but just because it was so easy:

  • Integrated the ddg CLI tool in order to search DuckDuckGo and get the results in-editor
  • Integrated w3m so I can just select a URL and show the web page rendered in a buffer
  • Used mpc to control music playback from the editor

Most of these types of things are just either mappings that call nop %sh{ ... } to execute something, or fifo ... -- command in order to execute something and display the results, possibly while the program is still running.

A week is not a long time to learn and love an editor

All of the things I've mentioned above I did during my first week of using Kakoune. This is in part because I forced myself to use strictly only Kakoune, and so I had to solve some of these things (and I'm happier for it) but it's also because Kakoune is a much better platform than most for people who either already have their own solutions to things, or can create them.

I can't seem to replicate this in Emacs

Disclaimer: I'm not saying Emacs is bad, but it's ultimately worse for me than Kakoune

When I had created my command center in Kakoune I was beginning to think that maybe what I really appreciated about Kakoune was the nature of what I had created: My own command center. So I decided to give Emacs one more shot. I've used Emacs for 5+ years earlier, on and off, so Emacs isn't really new to me but I had also given it up before.

I gave Emacs one week of hardcore usage where I again forced myself to use only it, and at first I was dead set on using literally no external scripts to accomplish this. Pretty soon I was disabused of this notion and resigned myself to cloning emacs-bedrock. It's not bad, but I already felt like this was somewhat of a failed experiment because of it. Nevertheless, I continued and focused on trying to implement the actual things I was interested in for my command center.

Integration points

Emacs has entirely way too many integration points. The whole program is just a set of integration points. It's incredibly confusing to make your own features for Emacs because most of your time seems to be taken up just by endless searching for the right function and/or facility to use. It's like an editor-specific version of choice/analysis paralysis. Obviously I think you can get over this, but it's quite the hurdle.

This problem is made slightly better because of Emacs' amazing lookup features, but even so I was unable in most cases to reach a point where I was confident I had found the correct integration point for almost anything. Being able to search an endless sea of functions, variables and other things is neat, but it's not as useful as already having the answer because it's more or less obvious, which is what Emacs was competing with in this case.

Where does that leave me?

Kakoune spoiled me: The ability to run other programs easily, integrate them with almost any editor facility I can think of, and to spend most of my time just writing real programs not stuck in an editor... It's too good. I feel like I can't really go back to anything else at this point. I also didn't mention in this post that you can send commands to Kakoune in order to control it. This in itself isn't necessarily new, but it did make me think about the nature of Kakoune, what program it actually is. It's a facilitator of buffer contents more than anything else, a middle-man that handles
communication to and from programs.

Taking inspiration from Kakoune

With this fresh in my mind I created a coding agent for myself that communicates with registered frontend programs via a FIFO/socket, takes commands via a FIFO/socket and can (of course) be run and interacted with entirely in Kakoune.

The configuration language for the agent also looks suspiciously like KakScript, because it's neat and obviously I had to put the inspiration on display:

define-tool bash %description{{
    Runs a command in bash
}} %parameters{
    command string! The full command with arguments
} %command{{
    bash -c "$hugin_parameter_command"
}}

define-tool tree %description{
    Gives you the file tree starting at a base path.
} %parameters{
    path string! The root path to get the file tree of
    depth integer! The depth of the printed tree, set to 2 or 3
} %command{{
    tree -L$hugin_parameter_depth "$hugin_parameter_path"
}}

define-tool pi-web-search %description{
    Research a question on the web by spawning a sub-agent.
    Provide both search terms and the precise question to answer; the sub-agent returns Markdown with source links and summaries.
    Use this when research, current information, external documentation, comparisons or source-backed facts are needed.
} %parameters{
    query string! Concise web search terms to use as the starting point for finding relevant sources
    question string! The exact research question that is to be answered. Phrase it as a concrete question and include needed context, constraints and user intent. Summaries must be relevant to this question.
} %command{{
    pi \
        --print --no-session --no-tools --no-extensions \
        --extension "/home/gonz/code/pi/gonz-pi/extensions/cursor-provider/" --no-skills \
        --no-prompt-templates --no-context-files \
        --model "cursor/composer-2.5" \
        --append-system-prompt "/home/gonz/code/odin/hugin/trunk/pi-web-search-prompt.txt" \
        "Search query: $hugin_parameter_query\nQuestion to answer: $question\nSearch the web, open relevant results, and return only the required Markdown report. each source summary must explain only what is relevant to answering the question."
}}

Other fun stuff

I also created an agent that was stuck in Kakoune and made a playlist of results running with different models.