Case study 01 / 04 Novera · creative network Active prototype
Rome · one seeded city 29 domain records Read

Case study · Creative platform prototype

A city is
not a list.

The network before the interface

Novera models Rome’s cultural scene as a connected system of people, events, places and districts — before every connection is fully exposed in the interface.

Role
Full Stack Web Developer
Status
Active prototype
Scope
Product design, domain modelling, API, frontend
Stack
Laravel 13 · Next.js 16 · React 19 · TypeScript
Enter the console Source · private repository
Field · Roma Districts 6 Abstract field: the six seeded districts over a broken radial structure. Not a geographic map. SAN LORENZO OSTIENSE PIGNETO TRASTEVERE TESTACCIO MONTI
Alba Forma · live room 01
Neri Luce · work uploaded 02
Ruins in Frequency · event 03
Seeded activity · fixed dates
01 Signal intake

Tonight in San Lorenzo

Start with something concrete: one evening, one district and one screen getting its data from the backend.

Home · aggregated response Novera home header reading “Rome is moving tonight”, with four counters: 4 artists, 2 rooms, 4 open calls, 3 spaces.
FIG 01.1 Counters computed server-side from one endpoint. 1440×900.
Live now · district signals A row of district cards: Night Archive in Pigneto, Travertine Echoes in Ostiense, Alba Forma in Ostiense and further rooms in San Lorenzo.
FIG 01.2 Rooms, drops and calls, read by district rather than by category.
Fresh signals · seeded activity Six activity rows: a listening session started, artist work uploaded, an event published, a collaboration request, an artist joining and a collective recruiting.
FIG 01.3 Every row carries a district. Timestamps read 63d — the seed has fixed dates.
Telemetry
Endpoint
GET /api/home
Rendering
React Server Component — fetched server-side
Data
One seeded city · 29 domain records
Recorded in
Laravel access log

The home is currently the only main frontend screen fed by the aggregated Laravel API. The city header, counters and activity feed all come from one endpoint, fetched and rendered by a React Server Component.

That fetch runs on the server, so it never appears in the browser’s network panel. The request is visible in the Laravel access log.

Counts shown on screen are demo-data totals, not usage metrics.

02 District field

Everything is somewhere

The district is not a tag. It is a first-class relation carried by every entity in the domain.

Coordinate field · schema map_x / map_y Select a district San Lorenzo selected 1 Artists 1 Events 1 Spaces 1 Collectives 1 Rooms 1 Calls San Lorenzo Ostiense Pigneto Trastevere Testaccio Monti
Selection summary

Referenced in

San Lorenzo

  • Artists 1
  • Events 1
  • Spaces 1
  • Collectives 1
  • Live rooms 1
  • Open calls 1

Artists, events, spaces, collectives, live rooms and open calls all hold a district reference. That single decision is what allows a scene to be read by place rather than by category.

San Lorenzo is the only district connected to all six categories in the seed. Monti has no references yet, and the field shows that.

City pulse · product surface Novera City Pulse panel: an abstract field with coloured signal points beside a list of districts with signal counts and activity bars.
FIG 02.1 The same idea in the product: an abstract field, never a map tile.

Districts carry an editorial tone and abstract layout coordinates in the schema — the field above is drawn from those map_x / map_y values, scaled to fill the frame. There is no latitude, no map tiles and no geolocation anywhere in the product.

03 Relationship instrument

Follow the connection

An artist plays an event, the event happens in a space, the space sits in a district, the district holds collectives and open calls.

Chain · domain schema Select a step District selected Foreign keys on every hop Polymorphic · activity, recommendation Artist Event Space District Collective & open call
Entity
Model
District
Relation
referenced by every domain entity

The join that turns six separate directories into one readable scene.

Novera models that chain with foreign keys on every hop, plus polymorphic references that let activity and recommendation records point to any entity.

The relationships exist in the domain model even where the current interface does not yet make them navigable.

Artist
belongsTo City, District — A profile with discipline, tags, links and skills, anchored to a district.
Event
belongsTo Space, Collective, District · hasMany OpenCall — An event knows where it happens, who organises it and which calls it opens.
Space
belongsTo City, District — A venue with type, capacity and amenities, placed in a district.
District
referenced by every domain entity — The join that turns six separate directories into one readable scene.
Collective & open call
belongsTo District · OpenCall belongsTo Collective, Event, Space — Where a scene turns from things happening into people looking for each other.
04 The imbalance, drawn

Two halves

The project currently has two uneven halves, shown in one drawing.

API side · Laravel

Finished

  • 19 read-only endpoints
  • 10 domain entities
  • API Resources with shared basics
  • Eloquent relations, incl. polymorphic
  • Shared city / district / status filters
  • One aggregated home response
1/19 Endpoints actually consumed by the frontend
Frontend side · Next.js

Highlight surfaces by data source

API-backed surface highlighted

/ and /discover Reaches Laravel
/events Local array only
/artists Local array only
/rooms Local array only
/district/[slug] Local array only
/map Local array only

Laravel exposes nineteen read-only endpoints across ten entities, with API Resources, eager-loaded relations and a shared filter layer. The Next.js app consumes exactly one of them. Everything else — the artists, events and rooms directories — runs on local arrays declared in the components themselves. They are complete interfaces over demonstration data.

The TypeScript types describing the API are written by hand, so the contract between the two halves is a convention rather than something generated or checked at runtime.

05 Measured interaction

Filtering a scene

The events directory is the clearest example of the split: demonstration data underneath, genuine interaction on top.

As shipped · three filters preselected Novera events directory as it loads, with the filter control reading three active and the chips Live Set, Tonight and Free.
FIG 05.1 The page never loads empty: Live Set, Tonight and Free are already applied.
Filtered · exhibition + this week The same directory with two active filter chips, Exhibition and This Week, above a heading reading All events 4.
FIG 05.2 Two active chips and the changed counter, in one frame.
Recorded comparison
All filters cleared
Filters · 0 active
Applied
Exhibition This week
Result
12 reduced to 4 events

The directory runs on local demonstration data, but its filtering logic is real: two active filters reduce twelve records to four. Filtering combines several axes at once — type, period, access, capacity, neighbourhood and a text query — and each control is a real toggle with its pressed state exposed to assistive technology.

This 12-to-4 result comes from the running application.

Rooms and open calls Three Novera room cards marked live — Night Archive in Pigneto, Travertine Echoes in Ostiense and Courtyard Signal in San Lorenzo — each with a listener count.
FIG 05.3 Join room, save and follow are interface affordances only. Nothing persists.
06 Limits

Modelled, not yet lived

This is where the prototype stops today.

Modelled
  • Ten domain entities
  • Nineteen read-only endpoints
  • District as a first-class relation
  • Polymorphic activity and recommendation records
  • One aggregated home response
  • Client-side event filtering
Not built yet
  • Authentication
  • Content creation
  • Applications to open calls
  • Persistent follow, save and join actions
  • Full directory-to-API integration
  • Real multi-city data
  • Calculated recommendations
  • Production deployment
City selector · interface Novera city selector dialog offering Rome, Barcelona, Berlin, Copenhagen, Bari and Global, with Rome selected.
FIG 06.1 Six cities offered by the interface. One city exists in the backend.

The interface offers a city selector, but the backend holds one seeded city and the home controller resolves Rome explicitly. It does not demonstrate multi-city support.

Recommendation records are modelled but not calculated. Their scores and reasons are demonstration content, not algorithmic output.

All photography in these screens is stock reference material, not application content.


What is finished here is a way of describing a city.
What is not finished is everything that would let people live inside it.