AI tools are quickly becoming part of everyday software development.
And Cursor is one of the more ambitious ones out there.
It’s built to do more than autocomplete. It reads your codebase, makes large-scale changes, runs terminal commands, and even refactors entire projects.
But with that level of control comes a big question – how well does it actually work in real-world dev environments?
We spent time working directly in Cursor to see what it’s like to build, refactor, and review code with it by your side.
In this article, we’ll walk you through the key features, real examples of how it performs, and the trade-offs you should know before using it in your workflow
Let’s dive in!
Table of Contents
Key Cursor features
First, we’ll start with an overview of Cursor’s main features and functionalities.
Reading and understanding your codebase
Cursor doesn’t start from scratch. It reads your codebase first.
It scans the project to understand how files connect and looks at folder structure, dependencies, and naming patterns. That context makes a big difference.
When asked to generate backend logic, it uses the right packages automatically. Not just generic imports – it grabs the actual ones already used in the project.
In one case, it installed frontend and backend dependencies without being told exactly which ones to use – it figured it out from the code itself.
This makes small prompts go further.
You don’t have to explain everything, Cursor already knows your project’s setup.
But if your code is messy or inconsistent, that context can also mislead it.
Cursor can only work with what it sees. The GIGO (garbage in, garbage out) principle still holds.
So, writing clean code helps it help you.
Reading documentation
Cursor also gives you a way to add more context manually.
There’s a feature called “docs” where you can input extra information like product specs, logic overviews, or rules on how the app should behave.
You just open the “new doc” tab and reference it by link or URL.
This works especially well when the codebase alone doesn’t tell the full story.
For example, when generating frontend components that followed a specific UX rule, Cursor did much better after being shown a short doc explaining that rule.
Without that doc, it missed the mark. But with it, it nailed the flow.
It’s like giving it a cheat sheet. You can’t expect great results if you don’t give it what it needs to understand the goal.
If your code has weird business logic or domain-specific quirks, this feature is essential.
Agent mode
Agent mode is where Cursor starts to feel less like an assistant and more like a teammate.
With a single prompt, it can update multiple files across your codebase.
For example, when asked to refactor a Go service, it didn’t just touch the main file – it created a proper structure, split logic into smaller, focused files, and rewrote the imports.
It wasn’t just cosmetic cleanup. These were structural changes that made the code easier to work with.
You could take what Cursor wrote, tweak a few lines, and push to production.
But this kind of power has a flip side.
Sometimes, it makes changes in places you didn’t expect.
It might jump into related files or update shared logic that wasn’t explicitly mentioned. That can be helpful, or a mess, depending on what you’re working on.
The big takeaway here? You need to review everything. Don’t trust it blindly.
Agent mode can do a lot with very little input, but that doesn’t mean it always should.
Terminal command execution (YOLO mode)
Cursor can also execute terminal commands directly inside its interface.
That’s not a joke. You type a command, and it runs it, right there.
It installs packages, updates configs, runs scripts, and spits out the terminal output on screen.
And it works. But it also earned the nickname “Yolo Edition” for a reason.
By default, there’s nothing stopping it from doing whatever it wants in the terminal. That’s very risky.
How to build & scale engineering teams. Revealed by experts.
It could accidentally run a command that changes file permissions, wipes something, or pushes a bad commit.
Luckily, there’s a way to limit this.
You can set rules that require manual approval before any terminal command is executed.
Once these restrictions are in place, Cursor respects them. It’ll ask before running anything, which makes this feature way more usable – and less terrifying.
It’s powerful, especially when you’re spinning up environments or installing dependencies.
But you need to handle it with care. This isn’t a sandbox – it’s your actual terminal.
Single and multi-file refactoring
Refactoring is one area where Cursor really shines.
Feed it a large, bloated file and ask it to break things up – and it does exactly that.
It separates logic into packages, applies naming conventions from your codebase, and even drops in useful comments.
For example, we turned a messy prototype all-in-one Go file into a tidy, multi-file service with handlers, utilities, and routing logic cleanly split apart.
It didn’t just guess, it followed our existing patterns.
It’s also great for cleanup work. You can ask it to:
Restructure a component
Extract a helper
Turn repeated logic into a reusable function
In most cases, it gets the structure right and writes clean, idiomatic code.
It won’t always make perfect design decisions. But it will give you a solid starting point.
And if you’re working against a deadline, that alone makes it worth using.
Cursor won’t replace your judgment. But for speeding up the boring parts of refactoring? It’s a game-changer.
Potential for web search and repo integration
This part is still early, but it’s worth mentioning.
There’s talk about Cursor supporting web search.
That would let it look up missing pieces online, like documentation or usage examples. In theory, it could search public APIs or StackOverflow-style content.
Even more interesting is the mention of repo integration.
Cursor might soon be able to pull context from private repositories, not just the one you’re working in. That would open up a lot of possibilities.
Imagine giving it access to both frontend and backend repos and asking it to build a feature that spans both. Or referencing a shared component library that lives in a separate repo.
Right now, this isn’t fully implemented.
But it’s clear the goal is to make Cursor smarter by letting it see more than just one code folder.
When that happens, the line between “assistant” and “collaborator” will get even blurrier.
Cursor limitations and challenges
Next, we’ll cover some limitations and challenges you should be aware of when using Cursor.
Errors and inconsistencies in output
Cursor isn’t magic. It gets things wrong.
For example, when working in a folder with nested submodules, it failed to detect the right context.
It edited the wrong file and missed key dependencies. Nothing broke immediately, but the logic was off.
Same goes for reused prompts.
The exact same request on two different days gave different results. One time it added a new helper function. The next time, it reused an existing one.
That kind of unpredictability can make it hard to trust.
Sometimes, Cursor invents functions that don’t exist in your codebase.
You’ll see a call to something like getUserData(), but it’s not defined anywhere. It’s just assuming.
That’s not always a problem if you know what to look for. But if you’re moving fast, it’s easy to miss.
So, while Cursor can help you code faster, it can also leave you cleaning up weird mistakes later.
Merge conflict handling
Merge conflicts are a part of real-world development, especially in larger teams.
Any tool that can’t handle them reliably isn’t ready to replace your main workflow just yet.
It’s unclear whether Cursor can fully resolve tricky conflicts like .pbxproj files on iOS.
That said, Cursor does offer some early tools to help.
When it detects a merge conflict, it can highlight the differences and suggest AI-generated resolutions. You can review those and either accept the suggestions or edit them manually.
It’s a decent first step. But not a full replacement for mature tools like IntelliJ or GitKraken, which let you resolve conflicts visually – “accept left,” “accept right,” or both – without leaving the IDE.
The Cursor community has already asked for these kinds of features, so the demand is clear.
Until they land, though, expect to handle your bigger or more sensitive merges elsewhere.
Cursor is moving in the right direction, but for now, it’s still better at writing code than resolving your trickiest conflicts.
Issues with image handling
Cursor doesn’t handle images out of the box.
In one test, a prompt asked it to fetch a specific image from a URL. It wrote the code to use the image but didn’t actually download it.
Turns out, it can do it, but only if you tell it to do it explicitly.
You have to add a line like “download this image and save it to /assets”.
Without that, it just assumes the file is already there.
Not a huge issue, but something to remember when working with assets.
Terminal command risks
Cursor can execute real terminal commands. That’s impressive – but it can also go very wrong.
In one example, it ran a terminal command that modified Git settings and committed changes, all without a confirmation.
It did what it was told. But it didn’t ask if it should.
That’s the risk.
If you don’t set up “Cursor Rules” to block or confirm terminal commands, Cursor gets full control. And that’s not something you want on day one.
It can run npm install. Or rm -rf. Or anything in between.
Once you add rules to require approval, things get safer.
Cursor paused before running anything and asked first. That made the feature way more useful.
The terminal is one of its best features. It’s also the one most likely to wreck your project if you’re not careful.
Lack of feedback during processing
One thing that stands out: Cursor doesn’t always tell you what it’s doing.
You’ll see a loading bar. That’s about it.
When it’s slow, there’s no detailed output.
You don’t know if it’s thinking, stuck, or waiting for something. And that can be frustrating, especially when you’re mid-task.
In one case, after giving a long prompt, the interface just sat there. No errors. No output. Just spinning. Eventually, it worked.
But if something goes wrong, you won’t always know why. There’s no real-time feedback or debug log.
That’s a limitation. It’s not a dealbreaker, but it does slow down your workflow if you’re trying to move fast.
Treat Cursor like a teammate that’s bad at giving status updates.
You’ll get something useful eventually. But don’t expect detailed progress along the way.
How to work with Cursor
Finally, we’ll give you some tips on how to successfully work with Cursor and make the most of it.
Choose the right AI model
Cursor doesn’t lock you into one AI model.
You can pick what works best for your task. We used Claude when demoing Cursor and it performed well.
You can plug them in via API or even run them locally, if that’s your thing.
That sounds like full control. But there’s a catch.
Even with local models, Cursor still relies on its own backend for some parts of the workflow. Specifically, the way it processes prompts and manages context.
So if you’re expecting a fully offline setup, you won’t get it. Cursor’s backend still plays a role in how everything runs.
Still, choosing your model gives you more flexibility.
You can tailor your setup based on accuracy, speed, or cost. And that’s a big plus if you’re working on a specific type of project, like mobile, backend, or ML.
The real win here? You’re not boxed in. You can shape Cursor to fit your specific needs and the way you work.
Write clear prompts
Cursor doesn’t read your mind. If your prompt is vague, it’ll guess.
And that guess might be wrong. Clear, specific prompts get the best results.
You should think like a product manager writing a ticket. You’re not chatting, you’re giving instructions.
For example, a prompt like: “Add user authentication” will give you a generic result.
A prompt like this is much better: “Add JWT-based user authentication using Go. Use the existing auth middleware and update the /login route. Save the token in local storage.”
That prompt gave back working code and respected the folder structure. It even followed the naming pattern used elsewhere in the repo.
Too much fluff slows it down. Cursor isn’t looking for a story, it’s looking for clarity.
Short sentences and clear actions. That’s how you get it to do real work.
Review before accepting code changes
Cursor shows you every change before it applies them.
You’ll see modified files. And inside those, you’ll see modified blocks.
You can approve or reject changes line by line. That’s a good thing, because Cursor can go off-script.
When using agent mode, it sometimes edits helper files, even if your prompt didn’t mention them. That’s not a bug, it’s how it tries to connect the dots.
But if you’re not careful, it might rewrite something critical.
One prompt changed multiple files and almost broke a build because it edited a shared utility incorrectly.
Luckily, the changes were easy to spot. File-level review would’ve missed it, but block-level saved the day.
Bottom line: never accept everything at once.
Review every change like you would a pull request from a new hire.
Define rules to manage AI behavior
Cursor gives you ways to rein it in.
There’s a feature called Cursor Rules.
You can use it to set hard limits on what the AI is allowed to do. Think of it like a safety net for your project.
For example, if you don’t want Cursor to run any terminal commands without asking, you can create a rule for that: “Don’t execute terminal commands without permission.”
That was all it took.
From that point on, every time Cursor tried to run something, it paused.
It showed the command and waited for user approval. This turned the terminal from a risk into a controlled tool.
You can also create your own rules from scratch.
The interface has an “add new rule” option. You write the description, define the restriction, and that’s it.
Rules don’t make Cursor perfect. But they give you a buffer.
You’re no longer relying on it to just “do the right thing.” You’re telling it what’s off-limits.
That alone makes Cursor way more usable in real-world projects.
Cursor vs. GitHub Copilot: how do they compare?
If you’ve used GitHub Copilot, you might be wondering how Cursor stacks up.
Both tools aim to help you write better code faster – but they approach the problem differently.
Here’s a quick side-by-side breakdown:
Cursor vs. GitHub Copilot: comparison
Feature
Cursor
GitHub Copilot
Codebase awareness
Understands your whole codebase
Single file focus
Edits and code generation
Multi-file edits and generation
Line-by-line suggestions
Chat support
Chat interface with context
No interactive chat
Platform
Built on VSCode
IDE plugin only
Pricing
Free for individual use
Paid subscription
Language support
Supports all major languages
Limited language support
Copilot is simpler and more lightweight, but less powerful when it comes to full-project tasks.
Cursor offers deeper context awareness and more flexibility for larger projects, so it’s more useful in a professional environment.
And it can explain complex code blocks in simple terms, making it perfect for both juniors and seniors.
We’ve tested both – and for real-world software development, we definitely recommend Cursor.
It does more of the heavy lifting, especially when you’re working on something bigger than a single function.
Cursor pros and cons
But as much as we like Cursor, it’s not without its flaws.
Here’s a quick overview of its pros and cons:
Pros
Increased productivity
Context-aware assistance
Powerful code generation
Customizable setup
Useful learning tool
Cons
Learning curve
Cluttered UI
Occasional inaccuracies
No full local-only mode
Still, the pros easily outweigh the cons – especially if you’re working on complex projects where speed and structure matter.
Just take the time to set it up right, and you’ll get a lot out of it.
Cursor free vs. paid plans: is it worth it?
Cursor offers a free version that gives you a taste of its capabilities.
You get access to core features like autocomplete, chat, and basic agent functionalities.
However, there are limits.
Free users are limited to 50 slow premium requests and 2000 code completions per month. And once they run out, you have to wait for your next reset date.
So if you use them all up in one day, you’ll have to wait a month for it to reset or upgrade to a paid plan before you can use Cursor again.
Skilled in React Native, iOS and backend, Toni has a demonstrated knowledge of the information technology and services industry, with plenty of hands-on experience to back it up. He’s also an experienced Cloud engineer in Amazon Web Services (AWS), passionate about leveraging cloud technologies to improve the agility and efficiency of businesses.
One of Toni’s most special traits is his talent for online shopping. In fact, our delivery guy is convinced that ‘Toni Vujević’ is a pseudonym for all DECODErs.