Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
A Round Trip through your Presentation Layer wi...
Search
Dominique Feyer
March 31, 2017
Programming
570
0
Share
A Round Trip through your Presentation Layer with Fusion
Get a better understanding of Fluid and Fusion for your Neos CMS project
Dominique Feyer
March 31, 2017
More Decks by Dominique Feyer
See All by Dominique Feyer
content modeling from theory to Neos CMS
dfeyer
1
210
Liiptalk Neos CMS
dfeyer
1
120
Inspiring conference 2016 - Automation & external service integration
dfeyer
0
55
Inspiring Conference 2016 - architectes.ch case study
dfeyer
0
76
Neos CMS Introduction, Webmardi, Lausanne, February 2015
dfeyer
0
67
Neos CMS: Node Kingdom
dfeyer
0
120
Other Decks in Programming
See All in Programming
TAKTでAI駆動開発の品質を設計する
j5ik2o
5
670
AIとRubyの静的型付け
ukin0k0
0
520
JJUG CCC 2026 Spring: JSpecify で実現する Kotlin フレンドリーな Java API 設計
ternbusty
1
130
RTSPクライアントを自作してみた話
simotin13
0
440
New "Type" system on PicoRuby
pocke
1
430
ふつうのFeature Flag実践入門
irof
7
3.5k
今さら聞けないCancellationToken
htkym
0
220
AIチームを指揮するOSS「TAKT」活用術 / How to Use “TAKT,” an OSS Tool for Orchestrating AI Teams
nrslib
6
800
Old Dog, New Tricks: The Java 25 Reinvention - JNation
bazlur_rahman
0
140
Oxcを導入して開発体験が向上した話
yug1224
4
280
The NotImplementedError Problem in Ruby
koic
0
310
[2026年度第1回ORセミナー] 計画最適化ベンチャーと競技プログラミング人材
terryu16
0
240
Featured
See All Featured
Save Time (by Creating Custom Rails Generators)
garrettdimon
PRO
32
3.3k
Code Reviewing Like a Champion
maltzj
528
40k
Mozcon NYC 2025: Stop Losing SEO Traffic
samtorres
1
250
Being A Developer After 40
akosma
91
590k
The #1 spot is gone: here's how to win anyway
tamaranovitovic
2
1.1k
Un-Boring Meetings
codingconduct
0
310
技術選定の審美眼(2025年版) / Understanding the Spiral of Technologies 2025 edition
twada
PRO
118
120k
Become a Pro
speakerdeck
PRO
31
6k
Leading Effective Engineering Teams in the AI Era
addyosmani
9
2k
End of SEO as We Know It (SMX Advanced Version)
ipullrank
3
4.2k
First, design no harm
axbom
PRO
2
1.2k
How to Create Impact in a Changing Tech Landscape [PerfNow 2023]
tammyeverts
55
3.4k
Transcript
None
@dfeyer on twitter/slack Dominique Feyer
@dimaip on twitter/slack Dmitri Pisarev
a round trip through your presentation layer in Neos
Logicless Templates, Smart Fusion Objects
Conditions
<f:if condition="{neos:rendering.inBackend()}"> Secret stuff! </f:if>
secrectStuff = 'Secret stuff!'
[email protected]
= ${node.context.inBackend}
{secrectStuff}
Loops
<f:for each="{blogPosts}" as="blogPost"> <div class="BlogPost-teaser"> <h2>{blogPost.title}</h2> <div>{blogPost.teaser}</div> </div> </f:for>
prototype(Your.Site:BlogPostsList) < prototype(Neos.Fusion:Collection) { collection = ${blogPosts} itemName = 'node'
itemRenderer = Your.Site:BlogTeaser }
Partials
<f:render partial="Header"/> <div>Website content</div>
prototype(Your.Site:Page) { header = Your.Site:Header }
{header -> f:format.raw()} <div>Website content</div>
Layouts
<f:layout name="Layout"/> <f:section name="main"> <div class="Content">The content</div> </f:section>
prototype(Your.Site:MainPage) < prototype(Page) { @process.layout = Your.Site:Components.Layout }
prototype(Your.Site:Components.Layout) < prototype(Neos.Fusion:Template) { templatePath = .../Layout.html value = ${value}
}
structure is everything
collocate component's resources
Fusion/Components/Menu/ Menu.fusion Menu.html Menu.js Menu.css
project directory structure
Blog/ Blog.fusion Blog.html Blog.Document.fusion Blog.Comments.fusion Blog.css Components/Menu/ Menu.fusion Menu.html Menu.js
Menu.css Override.fusion Shame.fusion Root.fusion Resources/Private/Fusion
Override.fusion
prototype(Neos.Fusion:Collection) { itemName = ‘node’ }
Shame.fusion
prototype(Neos.Neos:Page) { googleAnalyticsTrackingCode = Neos.GoogleAnalytics:TrackingCode }
select rendering based on the node type
root { default { renderPath = ‘page’ } } root.blog
{ @position = ‘before default’ condition = ${q(node).is(‘[instanceof Your.Site:Blog]’)} type = ‘Your.Site:Blog.Document’ }
root { default { type = ${q(node).property(‘_nodeType') + ‘.Document’} renderPath
> } }
prototype(Your.Site:Blog.Document) < prototype(Page) { head.stylesheets.main = … body = Your.Site:Blog
} prototype(Your.Site:Blog) < prototype(Neos.Fusion:Template) { templatePath = ‘…’ main = Neos.Neos:ContentCollection { nodePath = 'main' } }
fusion prototype generator
'Neos.Neos:Node': options: fusion: prototypeGenerator: ~
'Neos.Neos:Node': options: fusion: prototypeGenerator: Your\Site\Generators\Generator
opinionated template object
prototype(Your.Site:Components.Footer) < prototype(Neos.Fusion:Template) { templatePath = ‘resource://Your.Site/Private/ Fusion/Components/Footer/Footer.html’ }
prototype(Your.Site:SimpleTemplate) { @class = ‘Your\\Site\\FusionObjects\\TemplateImplementation’ } https://gist.github.com/dfeyer/f13c5e35004493956c9fef0bbc5efb0f
prototype(Your.Site:Components.Footer) < prototype(Your.Site:SimpleTemplate) Will automatically look for template in resource://Your.Site/Private/Fusion/Components/Footer/Footer.html
more to come
fusion is just another language
Your.Site:Book is not Your.Site:Book
Your.Site:Book NodeTypes.Book.yaml
‘Your.Site:Book': superTypes: 'Neos.Neos:Document': true ‘Your.Site:SeoMixins': true ‘Your.Site:JsonLd.Document’: true
Your.Site:Book Book.fusion
prototype(Your.Site:Book) < prototype(Neos.Fusion:Template)
prototype(Your.Site:Book) { title = ${q(node).property(‘title’)} }
one node type multiple fusion prototypes
Your.Site:Book Your.Site:Book.Document Your.Site:Book.Title Your.Site:Book.QrCode Your.Site:Book.SearchResult
one fusion prototype multiple nodetypes
Your.Site:Defaut.SearchResult Your.Site:Defaut.Document Your.Site:Defaut.JsonLd.Document
composition or inheritance… again
prototype(Your.Site:Library) { ownerName = … ownerEmail = … contactName =
… contactEmail = … }
prototype(Your.Site:Library) { owner = Your.Site:Person contact = Your.Site:Person address =
Your.Site:Address }
‘Your.Site:Library': childNodes: 'owner': type: ‘Your.Site:Person' 'contact': type: 'Your.Site:Person' 'address': type:
'Your.Site:Address'
naming… again
schema.org
small objects are beautiful
Neos.Fusion:Value prototype(Your.Site:Anything) < prototype(Neos.Fusion:Value)
Query
prototype(Your.Site:AllBooks.Query) { value = ${q(site).find(...).get()} }
prototype(Your.Site:LatestBooks.Query) { value = Your.Site:AllBooks.Query { @process.latest = ${Array.slice(value,0,3} }
}
Decorator
prototype(Your.Site:Components.Article) { tagName = ‘article’ content = ${value} } prototype(Your.Site:Components.Article)
< prototype(Neos.Fusion:Tag)
prototype(Your.Site:Book.Teaser) { … @process.wrap = Your.Site:Components.Article }
Neos.Fusion:RawArray prototype(Your.Site:Anything) < prototype(Neos.Fusion:RawArray)
prototype(Your.Site:Book.Json) { title = ${q(bookNode).property(‘title’)} price = ${Price.get(bookNode)} @process.stringify =
${Json.stringify(value)} } prototype(Your.Site:Book.Json) < prototype(Neos.Fusion:RawArray)
Neos.Fusion:RawCollection Neos.Fusion:Tag
take care of your domain logic
${q(node).property('discount') > 0 ? q(node).property('price') - (q(node).property('price') * q(node).property('discount') /
100) : q(node).property(‘price’)}
‘Your.Site:Book’: class: Your\Site\Domain\Model\Book
${book.price}
start from scratch
fusion in flow application
workshop anyone ?
hijack us
demo site reboot
None
in the making https://github.com/Flowpack/fusion-bp