Defining top-level scope methods in Ruby is risky
Defining methods in the top-level scope might immediately sound like a bad practice, but surprisingly, I’ve seen it appear in various Rails projects.
Sometimes, this happens unintentionally, while other times, developers do it to make methods more accessible from different parts of the application. Here, I’ll explain why this approach is problematic and how it can happen without you even noticing.
Let’s address the issue as we know best—with some code.
"When you define a method in the top-level scope, it gets added to the Object class, meaning it becomes available to every single object across your entire app. But why does this matter?" you might wonder. Here are some potential problems:
1. The most significant issue is that defining global methods in all classes contradicts the OOP paradigm, which exists for a good reason :)
2. There’s a small chance that a developer might use a globally defined method and assume its behavior based on a specific class context. While this may sound improbable, years in software development have shown me that in large systems, even the most unlikely scenarios occur.
3. Listing available methods in pry using the tab key can become painfully slow when the list is extensive. This is actually how I first discovered this issue in some projects I worked on.
How can this happen in a Rails application?
1. Helper methods in config/initializers, lib/ or lib/tasks/
You have to read few yml files and you're keen on DRY principle so you add a small `read_yml` method. Unfortunately, EVERYTHING can read ymls now.
2. Copy-paste failure
Let's say you wanted to copy include clause from another serializer, but instead of this:
you did this:
The serializer will work the same way in both cases, so there's no chance automated tests can discover this.
So, should you drop your current work and inspect your codebase? Probably not, but being aware of these details might save you some trouble in the future.
Comments
Post a Comment