The answer, briefly: a cross-object formula walks upwards only. It follows lookup and master-detail relationships from child to parent, up to ten relationships away, and it cannot go the other direction because the other direction returns many records rather than one. If you need a value from the child side, you need a roll-up summary, a flow, or Apex, not a formula.
The direction rule
Every relationship in Salesforce has a one side and a many side. A Contact has one Account. An Account has many Contacts. A formula returns a single value, so it can only traverse towards the one side.
From Contact, Account.Industry is valid. From Account, there is no Contacts.Industry, and there never will be, because the platform would have to decide which contact you meant. This is the single most common misunderstanding about formulas and it explains most of the questions that begin “why can I not see this field in the picker”.
Syntax
Parent fields are reached through the relationship name. For a lookup or master-detail to a standard object, that is the object name. For a custom relationship, it is the API name with __r replacing __c.
Account.Owner.Email
Project__r.Client_Manager__r.Region__c
TEXT(Opportunity.StageName)
Ten relationships away, and ten unique per object
These are two different limits and mixing them up causes confusion.
Depth. A single formula can reference a field up to ten relationships away from the object it lives on. In practice, anything past three or four levels is a sign the data model is doing something odd, and it is fragile: a change to any relationship in the chain breaks the formula.
Breadth. Across all formula fields, validation rules, workflow rules and field updates on one object, no more than ten unique relationships may be referenced. Paths already in use are free to reuse. A new path is what costs, and the counter is shared with metadata you did not write.
What you cannot reach
- Child records. Covered above. Roll-up summary fields exist for the master-detail case. Everything else is a flow, an Apex trigger, or a declarative roll-up tool.
- Fields on activities from a related record, and cross-object formulas that reference Task and Event in the general case, which have long-standing restrictions.
- The other side of a many-to-many. A junction object can reach both of its parents, but neither parent can reach through the junction to the other.
- Long text areas and multi-select picklists on the parent, in most formula contexts.
Recalculation, and the field that goes stale
A cross-object formula is evaluated when the record is read, so a change on the parent shows immediately on the child’s detail page. That is the advantage over a stored field.
Where it stops being free is reporting and list views. Filtering or sorting a large report on a cross-object formula makes the platform evaluate it for every row in scope, and there is no index to help. On a million-row object this is the difference between a report that runs and a report that times out. If a formula is used as a report filter constantly, a flow-populated plain field is the faster design even though it can drift.
Where cross-object formulas are not allowed
Several features refuse them, and the restrictions are worth knowing before you design around one:
- Roll-up summary filter criteria cannot use a formula field that contains a cross-object reference.
- A cross-object formula cannot be used as a lead conversion field mapping.
- They cannot be set as an external ID or made unique, because nothing is stored.
- Custom index requests on them are limited, so treat them as unindexed.
Frequently asked
Can a formula reference a grandparent field? Yes, chain the relationship names. Each link in the chain counts towards the object’s unique relationship allowance.
Does a cross-object formula work if the lookup is empty? It returns blank rather than erroring, so wrap comparisons in ISBLANK or BLANKVALUE if a blank would produce the wrong answer.
Can I reference a parent field the running user cannot see? Field-level security is not applied to formula results the way it is to the field itself, so a formula can expose a value the user has no direct access to. Treat that as a design decision, not an accident.
