Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
Backends for frontends
Search
Sponsored
·
Your Podcast. Everywhere. Effortlessly.
Share. Educate. Inspire. Entertain. You do you. We'll handle the rest.
→
Daniele Polencic
May 10, 2016
Technology
150
1
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Backends for frontends
Daniele Polencic
May 10, 2016
More Decks by Daniele Polencic
See All by Daniele Polencic
Zero to Kubernetes — Developer's Gym Singapore
danielepolencic
2
230
Scaling Microservices with Message Queues, Spring Boot and Kubernetes
danielepolencic
3
390
7 tips and tricks on how to make the most of your Kubernetes journey
danielepolencic
3
320
Deploying and Scaling Spring Boot Microservices to Amazon EKS
danielepolencic
1
710
From Zero to Forex Trading Bot Hero with Node.js and Typescript
danielepolencic
0
390
Kubernetes Chaos Engineering: Lessons Learned in Networking
danielepolencic
0
270
Deploying and Scaling Spring Boot Microservices to Kubernetes
danielepolencic
0
130
Scaling Machine Learning in the Cloud with Kubernetes
danielepolencic
0
130
From Zero to Forex Trading bot Hero
danielepolencic
0
150
Other Decks in Technology
See All in Technology
Cloudflareの向き先
chimame
1
160
プロダクションコードにおける encoding/json から encoding/json/v2 へのスムーズな移行
sansantech
PRO
1
230
DBTS2026 盛り上がってますか!?Databricksが実現するAI時代のデータ基盤
akuwano
1
200
Shared Signals Framework 仕様解説
oidfj
0
330
AWSを利用する上で知っておきたい名前解決の話 2026
nagisa53
5
3.3k
Microsoft Entra Kerberos で実現するクラウド デバイス管理
tamaiyutaro
2
660
Gifu WordPress Meetup #200 に向けて、私たちには何ができるだろうか?/ 2026-11-07 Gifu WordPress Meetup
torounit
0
250
AWS基盤改善を支える 私たちの理念と行動指針
kentosuzuki
0
140
BALLAS Technology Deck
ballas_inc
0
380
「AIチャットからもできないの?」と言われたら ~業務アプリをMCP対応するときの認証・認可の勘所
oidfj
0
270
The future of architectural work
ufried
0
190
Kiro 入門 (1 つのエージェントを、どの画面からでも) | 目指せ Kiro マスター 01
inariku
PRO
6
1.4k
Featured
See All Featured
Efficient Content Optimization with Google Search Console & Apps Script
katarinadahlin
PRO
1
980
Leadership Guide Workshop - DevTernity 2021
reverentgeek
1
430
Building AI with AI
inesmontani
PRO
1
1.4k
CoffeeScript is Beautiful & I Never Want to Write Plain JavaScript Again
sstephenson
162
16k
Navigating the moral maze — ethical principles for Al-driven product design
skipperchong
2
680
WCS-LA-2024
lcolladotor
0
990
RailsConf 2023
tenderlove
30
1.6k
A designer walks into a library…
pauljervisheath
211
25k
The Language of Interfaces
destraynor
162
27k
Optimising Largest Contentful Paint
csswizardry
37
4k
Music & Morning Musume
bryan
48
7.5k
Claude Code どこまでも/ Claude Code Everywhere
nwiizo
68
60k
Transcript
backends for frontends @danielepolencic
the good old days !
None
monolith templates cosmetic js
ajax ! revolution
None
api driven js widgets encapsulation
modern js era
None
serverless single page apps js bunsiness logic
serverless
just html, js & css
easy to deploy easy to build easy to scale
what about backend?
perfect rest api
None
everybody wins
None
!
how do you authenticate?
server side class UsersController < ApplicationController before_action :logged_in_user ... end
1. user requests page 2. redirected to login
client side UsersApi.isLoggedIn(cookie).then(user => { ... });
1. user requests page 2. wait for app to load
3. ajax request to /me 4. redirect
! are we there yet?
also1
auth server api
PUBLIC FACING AUTH SERVER
PUBLIC FACING AUTH SERVER
rest api + auth
frontend ! architecture
also2
tokens vs !!
CORS stateless CSRF JWT mobile
frontend ! backend apis
also3
little secrets
None
None
no harm, but... do you have a choice?
!
!
what about bootstrapping?
server side <body> ... <script> App.photos = new Photos([ {
id: 2, name: "My dog", filename: "IMG_0392.jpg" }, { id: 3, name: "Our house", filename: "IMG_0393.jpg" }, { id: 4, name: "My favorite food", filename: "IMG_0394.jpg" }, { id: 5, name: "His bag", filename: "IMG_0394.jpg" }, ... ]); </script> </body>
client side function AppController() { loadPhotos().then(photos => { ... });
}
1. user requests page 2. wait for app to load
3. ajax request to /photos 4. render page
! are we there yet?
… and this is the best case scenario
1. ajax request to /photos 2. ajax request to /posts
3. ajax request to /comments
!
what about aggregating calls?
server side class ClientsController < ApplicationController def fetch posts_response =
conn.get '/posts' followers_response = conn.get '/followers' ... end end <body> ... <script> App.photos = new Photos([ { id: 2, name: "My dog", filename: "IMG_0392.jpg" }, { id: 3, name: "Our house", filename: "IMG_0393.jpg" }, { id: 4, name: "My favorite food", filename: "IMG_0394.jpg" }, { id: 5, name: "His bag", filename: "IMG_0394.jpg" }, ... ]); </script> </body>
3 db queries
3 http requests server ✌ server
client side 3 http requests
! are we there yet?
SELECT * FROM Photos INNER JOIN Followers
!
!
cannot trust the user
None
client side <body> <form action="" method="post"> <div class="g-recaptcha" data-sitekey="site_key_here"></div> <input
type="submit" value="Submit" /> </form> <script src='https://www.google.com/recaptcha/api.js'></script> </body>
backend $reCaptcha = new ReCaptcha($secret); if ($_POST["g-recaptcha-response"]) { $response =
$reCaptcha->verifyResponse( $_SERVER["REMOTE_ADDR"], $_POST["g-recaptcha-response"] ); }
sadly, no client side only captcha
None
! solution !
REST SERVER
CAPTCHA API REST SERVER
client specific code in the rest api !
!
cross-origin resource sharing
fe: www.mysite.com be: api.mysite.com
nginx config # # Wide-open CORS config for nginx #
location / { if ($request_method = 'GET') { add_header 'Access-Control-Allow-Origin' '*'; add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS'; add_header 'Access-Control-Allow-Headers' 'Origin, X-Requested-With, Content-Type, Accept'; } # ... }
front-end specific code in the web server
whatch out for glitches1
cookies are not included with preflight requests
None
PUBLIC FACING AUTH SERVER
PUBLIC FACING AUTH SERVER IF PREFLIGHT
in the auth server unless is_preflight_request? do authorise_request end
client specific code in the rest api !
whatch out for glitches2
ie9 doesn't send cookies at all
None
None
client specific code in nginx !
whatch out for glitches3
None
If the 302 status code is received in response to
a request other than GET or HEAD, the user agent MUST NOT automatically redirect the request unless it can be confirmed by the user, since this might change the conditions under which the request was issued - w3
CORS REDIRECT Y U NO WORK???
!"#$...
websockets, sse, long polling batch api calls api data filter/enhance
validation
but...
just html, js & css
meanwhile your app...
it's fast !
it's easy to develop !
it's secure !
meanwhile your architecture...
AUTH SERVER REST API #2 REST API #1
AUTH SERVER REST API #2 REST API #1 FRONT-END CODE
AUTH SERVER REST API #2 REST API #1 CAPTCHA
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
PREFLIGHT
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING FRONT-END CODE
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING FRONT-END CODE
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING infrastructure coupling
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING no separation of concerns
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING hidden dependencies
just html, js & css
so what shall you do?
going back to server side rendering?
nope.
ignore and move on?
nope.
good artists copy, great artists steal — Pablo Picasso
! presentation layer !
None
None
FRONT-END CODE
does it help?
PRESENTATION LAYER
PRESENTATION LAYER same domain
!! issues no more
cors & preflight request const express = require('express'); const cors
= require('cors'); const app = express(); app.options('/products/:id', cors()); app.del('/products/:id', cors(), (req, res) => { res.json({msg: 'CORS-enabled for all origins!'}); }); app.listen(3000, () => { console.log('web server listening on port 80'); });
user authentication const express = require('express'); const passport = require('passport');
const app = express(); app.post('/login', passport.authenticate('local'), (req, res) => { res.redirect('/'); });
bootstrapping1 const express = require('express'); const app = express(); app.get('/dashboard',
(req, res) => { res.render('homepage.html', { googleAnalyticsId: '123', locale: 'en_GB' }); });
bootstrapping2 <body> ... <script> angular .module('myApp', []) .constant('GA', '{{ googleAnalyticsId
}}') .constant('locale', '{{ locale }}') </script> </body>
captcha const express = require('express'); const app = express(); const
Captcha = require('./captcha'); const captcha = new Captcha(PUBLIC_KEY, PRIVATE_KEY); app.post('/comment', (req, res) => { captcha .verify(req.body['g-recaptcha-response']) .then(() => res.send('success!')); });
api aggregation const express = require('express'); const app = express();
app.post('/posts-and-flower', (req, res) => { Promise.all([ request.get('http://service1.com/posts'), request.get('http://service2.com/flowers') ]).spread((posts, flowers) => res.json({ posts, flowers })) });
websockets const http = require('http'); const sockjs = require('sockjs'); var
echo = sockjs.createServer({...}); echo.on('connection', (conn) => { conn.on('data', (message) => { request.get(`http://service1.com/${message}`) .then(response => conn.write(response)); }); conn.on('close', () => {}); }); const server = http.createServer(); echo.installHandlers(server, {prefix:'/echo'}); server.listen(9999, '0.0.0.0');
all requests are routed through the presentation layer
API {aggregation, filtering, enhancing}, data validation, encapsulation, state, cors, credentials,
caching, bootstrapping
wait
this is not front-end
PRESENTATION LAYER
this is the new front-end
None
freedom to create api, architecture visibility, better ux, SRP and
SOC, clearer responsabilities in the team
great power great responsability
static html vs real server
deployment
AUTH SERVER REST API #2 REST API #1 CAPTCHA PREFLIGHT
CORS PREFLIGHT BOOTSTRAPPING FRONT-END CODE PRESENTATION LAYER
scalability
performance
security and testing
point of failure
no, it doesn't make sense if you're building todo apps
nothing new adapter pattern
netflix
None
None
soundcloud
None
None
spotify
None
paypal
None
uber
None
what about you?
thanks