Full Stack Interview Cheatsheet
SQL clause order
SELECT
FROM
JOIN ... ON ...
WHERE
GROUP BY
HAVING
ORDER BY
LIMITSQL quick reference
-- aggregates
COUNT(*), SUM(col), AVG(col), MAX(col), MIN(col)
-- filter after GROUP BY
HAVING COUNT(*) > 1
-- null checks
WHERE col IS NULL
WHERE col IS NOT NULL
-- conditional aggregate
SUM(CASE WHEN condition THEN amount ELSE 0 END) AS bucket
-- exclude rows based on subquery
WHERE id NOT IN (SELECT equipment_id FROM rentals WHERE ...)
-- date math (Postgres)
CURRENT_DATE
CURRENT_DATE - INTERVAL '90 days'
end_date - start_date -- gives number of days
-- params (never string format SQL)
cur.execute("SELECT * FROM t WHERE id = %s", (id,))
-- CTE
WITH name AS (
SELECT ...
)
SELECT * FROM nameFlask route patterns
# GET list
@app.route("/items", methods=["GET"])
def list_items():
status = request.args.get("status") # query param
# GET single by id (path param)
@app.route("/items/<int:item_id>", methods=["GET"])
def get_item(item_id): # passed automatically
pass
# POST create
@app.route("/items", methods=["POST"])
def create_item():
data = request.get_json()When to use each:
- Path param
/items/42→ identifying one specific resource - Query param
/items?status=active→ filtering a list - Body → creating or updating data (POST/PUT only)
Schema design rules
Always include:
id SERIAL PRIMARY KEYon every table- Foreign keys with
REFERENCES table(id) NOT NULLon required fieldsTEXTfor strings,NUMERICfor money,DATEfor dates
Naming:
- Tables: plural, lowercase (
customers,rentals) - Foreign keys:
table_id(customer_id,equipment_id)
When to split tables:
- Different data belongs in different tables
- Avoid storing derived data — calculate in queries
- Many-to-many → junction table
Common tradeoff:
- One table with a
typecolumn vs separate tables → use one table when the shape is the same, separate when fields differ significantly
React patterns
// state
const [items, setItems] = useState<Item[]>([])
// fetch on mount
useEffect(() => {
fetch(`${API}/items`)
.then(r => r.json())
.then(setItems)
}, [])
// form state (one handler for all inputs)
const [form, setForm] = useState({ col1: '', col2: '' })
function handleChange(e: React.ChangeEvent<HTMLInputElement>) {
setForm({ ...form, [e.target.name]: e.target.value })
}
// POST submit
function handleSubmit(e: React.FormEvent) {
e.preventDefault()
fetch(`${API}/items`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(form),
})
.then(r => r.json())
.then(newItem => setItems([...items, newItem]))
}
// GET with query params
const params = new URLSearchParams({ start, end })
fetch(`${API}/items?${params}`)curl
# GET
curl http://localhost:5001/items
# GET with query params (always quote the URL)
curl "http://localhost:5001/items?status=active&type=lift"
# POST
curl -X POST http://localhost:5001/items -H "Content-Type: application/json" -d '{"col1": "val1"}'
# GET path param
curl http://localhost:5001/items/42Datetime (Python)
from datetime import date, datetime, timedelta
date.today()
datetime.strptime("2026-05-01", "%Y-%m-%d") # string → date
date(2026, 5, 1).strftime("%Y-%m-%d") # date → string
date.today() - timedelta(days=90) # 90 days ago