Code From Scratch Series

Blog — Code From Scratch

Deep technical articles on Android engineering, Kotlin internals, and software systems. Based on the Code From Scratch YouTube series.

92articles
Android
Kotlin
Systems

Filter by category

92 articles

Code From Scratch / roman-tsisyk.com

Android

Activity lifecycle

Learn how Android calls onCreate, onStart, onResume, onPause, onStop and onDestroy, and how to keep user state across rotation with onSaveInstanceState.

Read →
Android

Android platform overview

See how Android is built in layers, what the four app components do, how apps run on ART in isolated processes, and what the manifest and permissions declare.

Read →
Concurrency

Channels

Learn how Kotlin coroutines pass data through channels: send and receive, rendezvous, buffered, unlimited and conflated types, closing, and for-loop consumers.

Read →
Kotlin

Classes and objects

Learn to define Kotlin classes with primary and secondary constructors, init blocks, custom accessors, data classes, object singletons and companion objects.

Read →
Data & Types

Collections

Learn what lists, sets and maps are, when each one fits, which operations they share, and why your code must handle empty and nested collections.

Read →
Data & Types

Composite types

Learn how records, tuples and choice types combine simple values into data models, why compilers check every case, and why composition often beats inheritance.

Read →
Kotlin

Control flow in Kotlin

Learn how if and when work as expressions in Kotlin, how for loops use ranges, until, step and downTo, and when to use while, do-while, break and continue.

Read →
Concurrency

Coroutine context and dispatchers

Learn what CoroutineContext holds, how Dispatchers.Main, IO and Default differ, how withContext switches threads, and how child coroutines inherit context.

Read →
Data & Types

Data and types

Learn how programs represent real-world information as data, how types define valid values and operations, and how static and dynamic typing catch type errors.

Read →
Data & Types

Data validation

Learn where to validate input data, which checks to apply, why you fail fast with clear errors, and how invariants, sanitization and defense in depth help.

Read →
Foundations

Decisions and branches

Learn how a program checks a true or false condition against current state, takes one branch, skips the other, and handles three outcomes with chained checks.

Read →
Android

Dependency injection

Learn why injected dependencies make Android classes testable, and how Hilt wires them with @Inject, @Provides modules, scopes and @HiltViewModel.

Read →
Concurrency

Error handling in coroutines

See how exceptions propagate in Kotlin coroutines, why you rethrow CancellationException, and how CoroutineExceptionHandler, SupervisorJob and Flow catch work.

Read →
Foundations

Errors and failure

Learn the difference between bugs and expected failures, why failure is part of program behavior, how testing detects it, and how to ask what could go wrong.

Read →
Kotlin

Extension functions

Learn to add functions and properties to existing Kotlin types without inheritance, how the receiver works, why members win, and how nullable receivers help.

Read →
Concurrency

Flow basics

Learn how Kotlin Flow returns many values over time, why a cold flow runs again for each collector, and how flow builders, emit, collect and backpressure work.

Read →
Concurrency

Flow operators

Learn how intermediate and terminal Kotlin Flow operators build pipelines, from map, filter and take to combine, zip, flatMapConcat, toList and reduce.

Read →
Kotlin

Functions

Learn to declare Kotlin functions with fun, typed parameters and return types, write single-expression functions, and use default values and named arguments.

Read →
Execution Model

How code actually executes

Follow Kotlin code from source to CPU: JVM bytecode, D8 and DEX, JIT and AOT compilation in ART, and the fetch, decode, execute loop with registers and the ALU.

Read →
Data & Types

Immutability

Learn how immutable data differs from mutable data, why it makes aliasing and concurrency safe, what it costs, and when local mutation is still fine.

Read →
Kotlin

Inheritance and interfaces

Learn why Kotlin classes are final by default, how open, override and abstract work, how one class implements many interfaces, and when sealed classes fit.

Read →
Foundations

Input and output

Learn how input becomes the initial state of a program, how output comes from its final state, and why the boundary between program and world shapes design.

Read →
Concurrency

Introduction to coroutines

Learn how Kotlin coroutines suspend without blocking threads, how launch, async and await start work, and how scopes give structured concurrency without leaks.

Read →
Android

Jetpack Compose basics

Learn declarative UI in Jetpack Compose: composable functions, Text and Button, Column, Row and Box layouts, why modifier order matters, and previews.

Read →
Kotlin

Kotlin collections

Learn Kotlin read-only and mutable List, Set and Map, how to create and query them, and how filter, map, groupBy, partition, fold and destructuring work.

Read →
Kotlin

Kotlin fundamentals

Learn what Kotlin is, how static typing and null safety catch errors early, and how Kotlin runs on the JVM, as native code and as JavaScript.

Read →
Kotlin

Kotlin type system

Learn how Kotlin nullable types work, and how safe calls, the Elvis operator, the not-null assertion, smart casts, safe casts and let handle null values.

Read →
Kotlin

Lambdas and higher-order functions

See how Kotlin treats functions as values: lambda syntax, function types, higher-order functions, trailing lambdas, implicit it, receivers and labeled returns.

Read →
Data & Types

Modeling with data

See how to turn real-world concepts into data structures: essential attributes, types, relationships, choice types, optional fields and a bookstore model.

Read →
Foundations

Naming and abstraction

See how names hide details and levels of abstraction keep programs understandable, what makes a good name, and when you must look below an abstraction.

Read →
Android

Navigation

Set up navigation in Jetpack Compose with NavController and NavHost, pass arguments in routes, control the back stack with popUpTo and keep screens decoupled.

Read →
Android

Network requests

Make HTTP calls on Android with Retrofit suspend functions, parse JSON with kotlinx.serialization, check Response status codes and handle network errors.

Read →
Data & Types

Null and absence

See why null causes crashes, how nullable and optional types make absence visible, and how to handle missing values with checks, defaults and early failure.

Read →
Data & Types

Primitive types

See how integers, floating-point numbers, booleans and characters work, how bit size sets range and precision, and why overflow and conversions cause bugs.

Read →
Foundations

Repetition

See how repetition runs the same instructions many times, how a termination condition ends a loop, and how accumulation and invariants keep loops correct.

Read →
Android

Repository pattern

See how an Android Repository hides network and database sources behind an interface, keeps one source of truth and makes ViewModels easy to test with fakes.

Read →
Android

Room database

Store data locally on Android with Room: define entities, DAOs and the database class, run suspend queries, observe tables with Flow and write migrations.

Read →
Kotlin

Scope functions

Compare the five Kotlin scope functions by how they access the object, as this or it, and what they return, then see when to use let, run, with, apply and also.

Read →
Foundations

Sequence and order

See how sequential execution works, why each instruction depends on the state left by earlier ones, and how dependencies decide the correct order of your code.

Read →
Kotlin

Sequences

Compare eager Kotlin collections with lazy sequences: how to create them, intermediate and terminal operations, early termination, and when to avoid them.

Read →
Concurrency

Shared state problems

See what breaks when threads share mutable state: race conditions, data races, lost updates from non-atomic steps, stale values from caches and CPU reordering.

Read →
Foundations

State and change

See how a program moves through many states one instruction at a time, how to trace each state transition, and how invariants help you verify code.

Read →
Android

State in Compose

See how state drives Jetpack Compose UI: keep values with remember and mutableStateOf, understand recomposition, and hoist state to make composables stateless.

Read →
Concurrency

Structured concurrency

See how Kotlin coroutines form parent-child trees: scopes set lifetimes, cancellation flows down, failures flow up, and supervisorScope isolates child failures.

Read →
Concurrency

Suspend functions

See what the suspend modifier means in Kotlin, where you can call them, why suspension frees the thread unlike Thread.sleep, and how calls run in order.

Read →
Concurrency

Synchronization

Protect shared data in Kotlin and Java with locks and synchronized blocks, avoid deadlocks with a fixed lock order, and choose between volatile and atomics.

Read →
Android

Testing on Android

Compare unit and instrumented tests on Android, test ViewModels with fakes, test coroutines with runTest, write Compose UI tests and follow the test pyramid.

Read →
Android Runtime

The main thread, Looper, and Handler

The Android main thread is a loop over a MessageQueue. Learn how Looper, Handler, Choreographer, HandlerThread, IdleHandler and Dispatchers.Main work with it.

Read →
Concurrency

Threads

See what a thread is, how to create, start and join threads in Kotlin, how threads share memory, when to use ThreadLocal, and why threads cost memory and time.

Read →
Kotlin

Variables and values

See how Kotlin declares variables with val, var and const val, how type inference works, when to write the type, and how scope and naming keep code clear.

Read →
Android

ViewModel

See how an Android ViewModel keeps UI state through configuration changes, exposes it with StateFlow, runs work in viewModelScope and feeds Compose screens.

Read →
Android

Views and layouts

See how the Android View tree works, which Views and layouts to use, how XML attributes size Views, and how type-safe view binding replaces findViewById.

Read →
Networking

What happens when you call an API

Follow one Retrofit call from Kotlin to the server and back: DNS, TCP handshake, TLS 1.3, server time, download, and how OkHttp pooling and HTTP/2 cut latency.

Read →
Foundations

What is a program?

Build a mental model of a program: a description of computation that turns initial state into final state through instructions, shown with a Kotlin example.

Read →
Concurrency

What is concurrency

See what concurrency is, how it differs from parallelism, why it helps responsiveness and throughput, and why interleaving and race conditions make it hard.

Read →
Architecture

When NOT to abstract

Abstraction has costs. Learn when to skip one-line repositories, pass-through use cases and one-implementation interfaces, and how the Rule of Three helps.

Read →
Performance

Where time is actually spent

Learn to profile in Android Studio and Perfetto, read flame charts, choose sampling or instrumentation, and see why IO, not algorithms, usually dominates.

Read →

No articles

There are no articles in this category yet.