skip to content

ORM & Data Access

The libraries that sit between your objects and the database — full ORMs, query builders, and thin drivers — across the JVM, Node, .NET, Rust, Go, and Scala. Interviewers spend time here because the data-access layer is where most production incidents start: N+1 queries, surprise lazy loads, and transactions that span more than anyone intended.

on this pageshow

explore

→ has its own guide

questions

478 · 3 sections

JPA offers four association mappings — @ManyToOne, @OneToMany, @OneToOne and @ManyToMany. Explain what each expresses, and how you would choose between them for a model of orders, customers and tags.

level: juniorimportance: must knowfreq 76%
basics
~20 s

They declare cardinality from the annotated field outward. @ManyToOne: many rows reference one (Order to Customer) and holds the foreign key. @OneToMany: the inverse collection (Customer to Orders). @OneToOne: at most one each way. @ManyToMany: many both ways, via a link table.

open as a page

In JPA, if you call EntityManager.persist() on a parent entity whose collection holds brand-new child entities, what happens to those children by default, and what does configuring cascade on that association change?

level: juniorimportance: must knowfreq 62%
basics
~20 s

By default persist applies only to the instance you pass. The new children stay transient, and at flush Hibernate typically fails with "object references an unsaved transient instance". Declaring cascade = PERSIST (or ALL) makes the provider run persist on each child too.

open as a page

In JPQL, what does the JOIN FETCH clause do, and how does it differ from writing a plain JOIN in the same query?

level: juniorimportance: must knowfreq 78%
basics
~20 s

JOIN FETCH tells the ORM to load the joined association's rows into the returned entities in the same SQL statement. A plain JOIN only lets you filter or navigate in the query; the association still loads later on access.

open as a page

In JPA, what does the @JoinColumn annotation declare, and which side of an association must carry it?

level: juniorimportance: must knowfreq 75%
basics
~20 s

@JoinColumn names the foreign-key column that stores the association. It goes on the owning side — the side whose table holds the FK, which for @ManyToOne is always the many side. The inverse side uses mappedBy instead.

open as a page

In JPA, what is the default fetch type for each of the four association annotations — @ManyToOne, @OneToOne, @OneToMany and @ManyToMany — and why does the default differ between them?

level: juniorimportance: must knowfreq 82%
basics
~20 s

To-one associations (@ManyToOne, @OneToOne) default to EAGER. To-many associations (@OneToMany, @ManyToMany) default to LAZY. The spec assumes fetching one extra row is cheap and fetching a whole collection is not. Most teams override the to-one defaults to LAZY.

open as a page

In JDBC, how should Connection, Statement and ResultSet be closed, and why?

level: juniorimportance: must knowfreq 70%
basics
~20 s

Declare each of them in a try-with-resources block so they close in reverse order even when something throws. Every one holds a scarce handle — a server-side cursor or a pooled connection — and an unclosed handle is leaked until the process ends.

open as a page

In JDBC, what does PreparedStatement do that Statement does not, and why prefer it?

level: juniorimportance: must knowfreq 85%
basics
~20 s

PreparedStatement fixes the SQL text up front with ? placeholders and supplies values afterwards through numbered typed setters, so input is never parsed as SQL. The same object can be re-executed with new values and the parsed form reused.

open as a page

In JDBC, why do applications obtain connections from a DataSource rather than DriverManager?

level: middleimportance: must knowfreq 60%
basics
~20 s

DriverManager is a static factory that opens a brand-new physical connection per call from a URL hardcoded at the call site. DataSource is an interface whose implementation is configured elsewhere, which is what allows pooled, XA-capable or instrumented connections without changing application code.

open as a page

In JDBC, how do you make several statements commit or roll back as one transaction?

level: middleimportance: must knowfreq 72%
basics
~20 s

Call setAutoCommit(false) on the Connection, run the statements, then call commit() on success and rollback() in the catch block. There is no begin() method in JDBC: turning auto-commit off is what starts the unit of work.

open as a page

How do JDBC's addBatch and executeBatch work, and what does executeBatch return?

level: middleimportance: should knowfreq 50%
basics
~20 s

On a PreparedStatement you bind parameters and call addBatch() to buffer that parameter set, then executeBatch() sends the buffered commands together. It returns an int[] of update counts, one per command, where a value may be SUCCESS_NO_INFO when the count is unknown.

open as a page

In a data-access layer that caches loaded rows, what makes a cached entry stale, and which writes leave one behind?

level: juniorimportance: must knowfreq 70%
basics
~20 s

A cached entry goes stale when the row it copies changes and nothing removes the copy. Any write the caching layer never sees can leave one behind: a set-based statement, a native statement, another service, or an operator at a console.

open as a page

What is a data-access cache that outlives a unit of work and is keyed by identifier, and which read does it serve?

level: juniorimportance: must knowfreq 60%
basics
~20 s

A shared cache holds mapped row state by type and identifier outside any single unit of work, so a load by key that hits it returns an object with no statement sent. Filtered queries still reach the database.

open as a page

What does it mean for a data-access layer to fill deferred links in identifier batches rather than one at a time?

level: juniorimportance: must knowfreq 52%
basics
~20 s

Rather than one statement per touched stand-in, the layer gathers the keys of other unfilled stand-ins of the same kind and fetches them together with a set-membership predicate, turning N secondary statements into roughly N divided by the batch size.

open as a page

When one statement fetches parents together with their child collection, why does the same parent come back repeatedly?

level: juniorimportance: must knowfreq 68%
basics
~20 s

The join returns one row per matching child, with the parent's columns repeated on every one of them. A layer that produces one result entry per row therefore hands back the same parent once per child row.

open as a page