Scala
Completed
-
Section 1: Getting Started
-
Section 2: Core Syntax
-
Section 3: Object-Oriented Scala
-
Section 4: Functional Scala
-
Section 5: Collections in Depth
-
Section 6: Type System
-
Section 7: Concurrency and Ecosystem
-
Section 8: Practical Projects
-
Section 9: Interview Practice
-
Section 10: Data Structures and Algorithms in Scala
-
Section 11: More Practice Exercises
-
Section 12: Advanced Functional Patterns
-
Section 13: More Ecosystem
-
Section 14: Scala Collections Library Deep Dive
-
Section 15: Scala Standard Library Deep Dive
-
Section 16: Akka Ecosystem Deep Dive
-
Section 17: Cats and Cats Effect Deep Dive
-
Section 18: Play Framework Deep Dive
-
Section 19: Apache Spark with Scala Deep Dive
-
Section 20: Scala Build Tools Deep Dive
-
Section 21: Scala 3 Specific Features
-
90: Union and Intersection Types
-
Section 22: Scala Testing Deep Dive
-
Section 23: Functional Domain Modeling
-
Section 24: More Data Structures and Algorithms in Scala
-
Section 25: Scala for Data Engineering
-
Section 26: More Practical Projects
-
Section 27: More Interview and Review
-
Section 28: ZIO Ecosystem Deep Dive
-
Section 29: Scala for Machine Learning
-
Section 30: Scala Microservices Architecture
-
Section 31: Scala Type System Deep Dive
-
Section 32: More Practice and Drills
-
Section 33: Scala Performance Deep Dive
-
Section 34: Scala Ecosystem Tooling
-
Section 35: Scala for Reactive Systems
-
Section 36: More Real-World Case Studies
-
Section 37: Scala for Financial Systems
-
Section 38: Scala GraphQL and gRPC
-
Section 39: More Final Projects
-
Section 40: More Interview and Final Review
-
Section 41: Scala for Streaming Data
-
Section 42: Scala Security Practices
-
Section 43: More Language Deep Dive
-
Section 44: Scala Command-Line Tools
-
Section 45: Scala Documentation and Style
-
Section 46: Scala Dependency Management
-
Section 47: More Practical Backend Patterns
-
Section 48: Scala for Event-Driven Architecture
-
Section 49: More Practice Drills Round 2
-
Section 50: Scala Compiler Deep Dive
-
Section 51: Scala for Web Frontends
-
Section 52: More Data Engineering Practice
-
Section 53: Scala Observability
-
Section 54: More Advanced Practice Projects
-
Section 55: Scala for Legacy Java Integration
-
Section 56: More Testing Practice
-
Section 57: Final Mastery Review
-
Section 58: Scala History and Ecosystem Context
-
Section 59: More Concurrency Patterns
-
Section 60: Scala for Configuration Management
-
Section 61: More Domain Modeling Practice
143: Scalafmt for Code Formatting
I've spent far too many hours of my career in pull requests arguing about whether a brace should be on the same line or the next, or whether we should use two spaces or four for indentation. It's a waste of mental energy. In any professional Scala project, the answer isn't "better guidelines"βit's an automated formatter. For Scala, that's Scalafmt.
Taming a Messy Report Generator
Let's look at some code I wrote in a rush. It works, but it's an eyesore. I've got inconsistent spacing, weird alignment in my case classes, and some haphazard indentation in the logic. This is exactly the kind of code that makes a teammate sigh when they open a PR.
case class UserReport(id:Int, name:String, email:String,
department:String,
status:String)
object ReportService {
def processReports(reports: List[UserReport]) = {
reports.filter(_.status == "Active")
.map(r => s"Report for ${r.name} (${r.department})")
.toList
}
def formatHeader(title: String, date: String) = {
s"--- $title --- \n Date: $date \n ----------------"
}
}
Instead of manually fixing this, I'm going to let Scalafmt handle it. First, I need to add the plugin to my project. I'll add the sbt-scalafmt plugin to my project/plugins.sbt file:
addSbtPlugin("org.scalameta" % "sbt-scalafmt" % "2.5.2")
Defining the House Style
Scalafmt doesn't guess how you like your code; it looks for a configuration file. I'll create a file named .scalafmt.conf in the root of my project. I'll start with a basic setup that mimics the common community standards.
version = "3.7.14"
runner.dialect = scala213
indentation.spaces = 2
maxColumn = 100
Now, I can just run sbt scalafmt in my terminal. When I do, the tool sweeps through my source files and snaps everything into place. My UserReport case class is suddenly aligned, and the spacing in ReportService becomes consistent without me touching a single key.
Correcting my Over-zealous Wrapping
Here is where I usually mess up. I sometimes try to be "too clean" with my line lengths. I decided I wanted my code to be very narrow, so I changed maxColumn to 60 in my config file, thinking it would make the code easier to read on a split-screen editor.
I ran sbt scalafmt again, and it was a disaster. My simple processReports method, which was perfectly readable on one or two lines, got chopped up into a vertical tower:
def processReports(
reports: List[UserReport]
) = {
reports
.filter(_.status == "Active")
.map(r => s"Report for ${r.name} (${r.department})")
.toList
}
It looks "organized," but it's actually harder to scan because it takes up way too much vertical space. I realized I'd over-constrained the formatter. I went back into .scalafmt.conf and bumped maxColumn back up to 100. I ran the command one more time, and the code snapped back to a balanced, readable state. The lesson here: don't let the formatter fight your natural reading flow; tune the config until the tool helps you, rather than hinders you.
π Practical Task
Standardizing the Legacy Transaction Processor
You've been handed a legacy file called TransactionProcessor.scala that is a formatting nightmare. Your goal is to bring it up to team standards using Scalafmt.
The Messy Code:
case class Transaction(id:Long, amount:Double, currency:String,
timestamp:Long,
merchantId:String)
object TransactionProcessor {
def calculateTotal(txs:List[Transaction], filterCurrency:String) = {
txs.filter(t => t.currency == filterCurrency).map(_.amount).sum
}
def logTransaction(t:Transaction) = {
println(s"Processing transaction ${t.id} for amount ${t.amount} ${t.currency}")
}
}
Your Requirements:
- Create a
.scalafmt.conffile. - Set the
versionto"3.7.14". - Set the
runner.dialecttoscala213. - Set
indentation.spacesto2. - Set
maxColumnto80. - Apply the formatting to the
TransactionProcessorcode and provide the final, cleaned-up version of the Scala code.
There are no comments for now.