SlideShare a Scribd company logo
Maarten van Vliet
Backend developer @ Awkward
Email: maarten@awkward.co
Github: maartenvanvliet
Recursive
Common Table Expressions
and Ecto
PRESENTATION
By Maarten van Vliet
First:
an introduction to the problem
What is Sketch?
An intuitive vector editor for the
Mac. It’s used primarily by screen
designers who create websites,
icons, and user interfaces for
desktop and mobile devices.
Sketch Cloud
Sketch Cloud is a platform that allows
you to share documents easily and with
everyone. Many more features are
coming!
Sketch Cloud uses a GraphQL API built in
Elixir, we call it SketchQL
Prototyping
Sketch’s Prototyping features makes
it easy to create interactive
workflows and preview your designs
as your users will see them.
Released last year in Sketch and
Sketch Cloud
A user can now create a prototype in
the Sketch, upload it to Cloud and
interactively play with it
Prototyping Cloud
Building prototyping was challenging
• Fluent transitions across browsers
• Converting Sketch Prototypes to the
web
• And, there are simple prototypes such
as this one
And complex prototypes…
Problems
We needed to fluently transition from
one screen to the next for prototyping in
the browser.
This meant: (deep) preloading the
relations of one screen (artboard) with
all other artboards
So, when A is loaded, we need to load B
and C, but also D!
Simplest solution
Recursively query database for related
artboards from application
1. First query for artboard A
2. Query for artboards directly related to
A, returns [B, C]
3. Query for artboards directly related to
[B, C], but leave out already found
artboards [A], this returns [D]
4. Query for artboards directly related to
[D], but leave out already found
artboards [A, B, C], returns []
5. We stop when an empty set is
returned.
Problem:lots of queries
Solution:
Recursive Common
Table Expressions!
• Last year we migrated Sketch Cloud to
Mariadb 10.2

• Introduced support for (Recursive) Common
Table Expressions

• (R)CTE's are also available in Mysql 8.0
(since 2018), and Postgres 8.4 (since 2009)

• But what are they?
Common Table Expressions
A CTE is a temporary resultset
Think of it as a database view only
created and visible for one query.
Useful for making subqueries easier
to read
You can have multiple in one query
WITH FirstUser AS (
  SELECT * FROM Users WHERE id = 1
)
SELECT * FROM FirstUser
— Equivalent to query with subquery
SELECT * FROM
(SELECT * FROM Users WHERE id = 1) AS F;
CTE’s can also do
recursion!
Recursive CTE’s are useful for querying
hierarchies, e.g. tables with a parent_id
column, so a row has can have a parent
or children
E.g. a CMS with pages, where a page can
have children
Pages:
WITH RECURSIVE PageGraph AS (
SELECT
P.id,
P.parent_id
FROM
Pages P
WHERE
P.parent_id IS NULL —start id
UNION
SELECT
P.id,
P.parent_id
FROM
Pages P
JOIN PageGraph PG
ON P.parent_id = PG.id
)
SELECT * FROM PageGraph
Id parent_id Name
1 NULL Page 1
2 1 Subpage 1
3 1 Subpage 2
4 2 Subpage 3
Dealing with cycles
How to deal with cycles? Hierarchies
with “loops” in them. E.g. page A has
page B as a parent, and page B has page
A as a parent
WITH RECURSIVE PageGraph AS (
SELECT
P.id,
P.parent_id
FROM
Pages P
WHERE
P.id = 1 #start id
UNION
SELECT
P.id,
P.parent_id
FROM
Pages P
JOIN PageGraph PG
ON P.parent_id = PG.id
)
SELECT * FROM PageGraph
Id parent_id Name
1 2 Page 1
2 1 Page 2
Union removes duplicates!
Back to the problem
In steps:
• First get artboards related to A, and
store them in “to”, returns [B, C]
• UNION this with the artboards where
the id matches those of [B, C]
• Get related artboards of [B, C], returns
[D]
• Again, UNION and get related
artboards of [D], returns [A].
• Nothing new found, so stop
WITH RECURSIVE RelatedArtboards AS (
SELECT
— A.id AS "from",
F.DestinationArtboardId AS "to"
FROM
Artboards A
JOIN Layers L ON L.ArtboardId = A.id
JOIN Flows F ON F.id = L.FlowId
WHERE
A.id = #Start ID, in this case Artboard A
UNION
SELECT
— A.id AS "from",
F.DestinationArtboardId AS "to"
FROM
Artboards A
JOIN Layers L ON L.ArtboardId = A.id
JOIN Flows F ON F.id = L.FlowId
JOIN RelatedArtboards ON A.id = RelatedArtboards.to
WHERE
A.id = RelatedArtboards.to
)
SELECT
R.to
FROM
RelatedArtboards R
From To
A B
A C
B D
C D
D A
Now we only need one query to load
all artboards for a prototype!
But how to use this in Elixir/Ecto?
Not supported in the query builder, yet…
Still open 😢
Once merged:
page_tree_initial_query =
Page
|> where([p], is_nil(p.parent_id))
page_tree_recursion_query =
Page
|> join(:inner, [p], pt in "page_tree", on: p.parent_id == pt.id)
page_tree_query =
page_tree_initial_queryv
|> union(^page_tree_recursion_query)
Page
|> recursive_ctes(true)
|> with_cte("page_tree", as: ^page_tree_query)
|> Repo.all
Until then…
Fragments gives us the
ability to extend Ecto
defmacro with_related_artboards(artboard_id) do
quote do
fragment(
"""
(
WITH RECURSIVE RelatedArtboards AS (
SELECT
F.DestinationArtboardId AS "to"
FROM
Artboards A
JOIN Layers L ON L.ArtboardId = A.id
JOIN Flows F ON F.id = L.FlowId
WHERE
A.id = ?
UNION
SELECT
F.DestinationArtboardId AS "to"
FROM
Artboards A
JOIN Layers L ON L.ArtboardId = A.id
JOIN Flows F ON F.id = L.FlowId
JOIN RelatedArtboards ON A.id = RelatedArtboards.to
WHERE
A.id = RelatedArtboards.to
)
SELECT
RelatedArtboards.to
FROM
RelatedArtboards
WHERE RelatedArtboards.to IS NOT NULL
)
""",
unquote(artboard_id)
)
end
end
import Sketchql.Utils.RelatedArtboards
artboard_id = 1
Artboard
|> join(:inner, [a], ra in with_related_artboards(^artboard_id)
|> Repo.all()
So, this will return a list of
%Artboard{} Ecto.Schema structs
related to the artboard with id 1.
• Keep composability of queries
🎉 Conclusion
• With one query leveraging Ecto and
RCTE ’s we can query all artboards
related to the current one, no matter
how deep.
• In the app we also paginate these
calls. This way we can render much
larger prototypes in Sketch Cloud
• It really pays off to dive deep into the
tools your database can provide such
as RCTE’s.
• Ecto’s extensibility is great! Where we
could not use its native features we
could use SQL to make up for it

More Related Content

What's hot

Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapas
Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapasKomparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapas
Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapasTihana Lapas
 
Understanding and Improving Code Generation
Understanding and Improving Code GenerationUnderstanding and Improving Code Generation
Understanding and Improving Code Generation
Databricks
 
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
HostedbyConfluent
 
Integrating Splunk into your Spring Applications
Integrating Splunk into your Spring ApplicationsIntegrating Splunk into your Spring Applications
Integrating Splunk into your Spring Applications
Damien Dallimore
 
Non blocking io with netty
Non blocking io with nettyNon blocking io with netty
Non blocking io with netty
Zauber
 
Openstack 101
Openstack 101Openstack 101
Openstack 101
Kamesh Pemmaraju
 
OpenNMS - My Notes
OpenNMS - My NotesOpenNMS - My Notes
OpenNMS - My Notes
ashrawi92
 
Introducing the Apache Flink Kubernetes Operator
Introducing the Apache Flink Kubernetes OperatorIntroducing the Apache Flink Kubernetes Operator
Introducing the Apache Flink Kubernetes Operator
Flink Forward
 
Solving PostgreSQL wicked problems
Solving PostgreSQL wicked problemsSolving PostgreSQL wicked problems
Solving PostgreSQL wicked problems
Alexander Korotkov
 
Getting up to speed with Kafka Connect: from the basics to the latest feature...
Getting up to speed with Kafka Connect: from the basics to the latest feature...Getting up to speed with Kafka Connect: from the basics to the latest feature...
Getting up to speed with Kafka Connect: from the basics to the latest feature...
HostedbyConfluent
 
Efficiently Building Machine Learning Models for Predictive Maintenance in th...
Efficiently Building Machine Learning Models for Predictive Maintenance in th...Efficiently Building Machine Learning Models for Predictive Maintenance in th...
Efficiently Building Machine Learning Models for Predictive Maintenance in th...
Databricks
 
KSQL Intro
KSQL IntroKSQL Intro
KSQL Intro
confluent
 
Flink in Zalando's World of Microservices
Flink in Zalando's World of Microservices  Flink in Zalando's World of Microservices
Flink in Zalando's World of Microservices
Zalando Technology
 
When apache pulsar meets apache flink
When apache pulsar meets apache flinkWhen apache pulsar meets apache flink
When apache pulsar meets apache flink
StreamNative
 
Changelog Stream Processing with Apache Flink
Changelog Stream Processing with Apache FlinkChangelog Stream Processing with Apache Flink
Changelog Stream Processing with Apache Flink
Flink Forward
 
從零開始做架構圖
從零開始做架構圖從零開始做架構圖
從零開始做架構圖
Philip Zheng
 
與大師對談: 轉移到微服務架構必經之路 ~ 系統與資料庫重構
與大師對談: 轉移到微服務架構必經之路~ 系統與資料庫重構與大師對談: 轉移到微服務架構必經之路~ 系統與資料庫重構
與大師對談: 轉移到微服務架構必經之路 ~ 系統與資料庫重構
Andrew Wu
 
Enterprise Integration Patterns with Apache Camel
Enterprise Integration Patterns with Apache CamelEnterprise Integration Patterns with Apache Camel
Enterprise Integration Patterns with Apache Camel
Ioan Eugen Stan
 
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
HostedbyConfluent
 
HTML5 WebSocket Introduction
HTML5 WebSocket IntroductionHTML5 WebSocket Introduction
HTML5 WebSocket Introduction
Marcelo Jabali
 

What's hot (20)

Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapas
Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapasKomparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapas
Komparativna analiza poslovnih informacijskih sustava otvorenog koda_tlapas
 
Understanding and Improving Code Generation
Understanding and Improving Code GenerationUnderstanding and Improving Code Generation
Understanding and Improving Code Generation
 
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
Bringing Kafka Without Zookeeper Into Production with Colin McCabe | Kafka Su...
 
Integrating Splunk into your Spring Applications
Integrating Splunk into your Spring ApplicationsIntegrating Splunk into your Spring Applications
Integrating Splunk into your Spring Applications
 
Non blocking io with netty
Non blocking io with nettyNon blocking io with netty
Non blocking io with netty
 
Openstack 101
Openstack 101Openstack 101
Openstack 101
 
OpenNMS - My Notes
OpenNMS - My NotesOpenNMS - My Notes
OpenNMS - My Notes
 
Introducing the Apache Flink Kubernetes Operator
Introducing the Apache Flink Kubernetes OperatorIntroducing the Apache Flink Kubernetes Operator
Introducing the Apache Flink Kubernetes Operator
 
Solving PostgreSQL wicked problems
Solving PostgreSQL wicked problemsSolving PostgreSQL wicked problems
Solving PostgreSQL wicked problems
 
Getting up to speed with Kafka Connect: from the basics to the latest feature...
Getting up to speed with Kafka Connect: from the basics to the latest feature...Getting up to speed with Kafka Connect: from the basics to the latest feature...
Getting up to speed with Kafka Connect: from the basics to the latest feature...
 
Efficiently Building Machine Learning Models for Predictive Maintenance in th...
Efficiently Building Machine Learning Models for Predictive Maintenance in th...Efficiently Building Machine Learning Models for Predictive Maintenance in th...
Efficiently Building Machine Learning Models for Predictive Maintenance in th...
 
KSQL Intro
KSQL IntroKSQL Intro
KSQL Intro
 
Flink in Zalando's World of Microservices
Flink in Zalando's World of Microservices  Flink in Zalando's World of Microservices
Flink in Zalando's World of Microservices
 
When apache pulsar meets apache flink
When apache pulsar meets apache flinkWhen apache pulsar meets apache flink
When apache pulsar meets apache flink
 
Changelog Stream Processing with Apache Flink
Changelog Stream Processing with Apache FlinkChangelog Stream Processing with Apache Flink
Changelog Stream Processing with Apache Flink
 
從零開始做架構圖
從零開始做架構圖從零開始做架構圖
從零開始做架構圖
 
與大師對談: 轉移到微服務架構必經之路 ~ 系統與資料庫重構
與大師對談: 轉移到微服務架構必經之路~ 系統與資料庫重構與大師對談: 轉移到微服務架構必經之路~ 系統與資料庫重構
與大師對談: 轉移到微服務架構必經之路 ~ 系統與資料庫重構
 
Enterprise Integration Patterns with Apache Camel
Enterprise Integration Patterns with Apache CamelEnterprise Integration Patterns with Apache Camel
Enterprise Integration Patterns with Apache Camel
 
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
Tradeoffs in Distributed Systems Design: Is Kafka The Best? (Ben Stopford and...
 
HTML5 WebSocket Introduction
HTML5 WebSocket IntroductionHTML5 WebSocket Introduction
HTML5 WebSocket Introduction
 

Similar to Using Recursive Common Table Expressions with Ecto

Exploring SharePoint with F#
Exploring SharePoint with F#Exploring SharePoint with F#
Exploring SharePoint with F#
Talbott Crowell
 
MapInfo Professional 12.0 and SQL Server 2008
MapInfo Professional 12.0 and SQL Server 2008MapInfo Professional 12.0 and SQL Server 2008
MapInfo Professional 12.0 and SQL Server 2008
Peter Horsbøll Møller
 
Intro to-html-backbone-angular
Intro to-html-backbone-angularIntro to-html-backbone-angular
Intro to-html-backbone-angular
zonathen
 
Web+Dev+Syllabus.pdf
Web+Dev+Syllabus.pdfWeb+Dev+Syllabus.pdf
Web+Dev+Syllabus.pdf
MohammadAhmad589157
 
Plone For Developers - World Plone Day, 2009
Plone For Developers - World Plone Day, 2009Plone For Developers - World Plone Day, 2009
Plone For Developers - World Plone Day, 2009
Core Software Group
 
Hexagonal architecture in PHP
Hexagonal architecture in PHPHexagonal architecture in PHP
Hexagonal architecture in PHP
Paulo Victor Gomes
 
F# for functional enthusiasts
F# for functional enthusiastsF# for functional enthusiasts
F# for functional enthusiasts
Jack Fox
 
Daniel Egan Msdn Tech Days Oc Day2
Daniel Egan Msdn Tech Days Oc Day2Daniel Egan Msdn Tech Days Oc Day2
Daniel Egan Msdn Tech Days Oc Day2
Daniel Egan
 
Designing well known websites with ADF Rich Faces
Designing well known websites with ADF Rich FacesDesigning well known websites with ADF Rich Faces
Designing well known websites with ADF Rich Faces
maikorocha
 
Android | Busy Java Developers Guide to Android: UI | Ted Neward
Android | Busy Java Developers Guide to Android: UI | Ted NewardAndroid | Busy Java Developers Guide to Android: UI | Ted Neward
Android | Busy Java Developers Guide to Android: UI | Ted Neward
JAX London
 
Evolve Your Code
Evolve Your CodeEvolve Your Code
Evolve Your Code
RookieOne
 
Progressive EPiServer Development
Progressive EPiServer DevelopmentProgressive EPiServer Development
Progressive EPiServer Development
joelabrahamsson
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
shaojung
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
shaojung
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
shaojung
 
Extreme Swift
Extreme SwiftExtreme Swift
Extreme Swift
Movel
 
Intro To Spring Python
Intro To Spring PythonIntro To Spring Python
Intro To Spring Python
gturnquist
 
Automating SolidWorks with Excel
Automating SolidWorks with ExcelAutomating SolidWorks with Excel
Automating SolidWorks with Excel
Razorleaf Corporation
 
iOS App Development with F# and Xamarin
iOS App Development with F# and XamariniOS App Development with F# and Xamarin
iOS App Development with F# and Xamarin
Rachel Reese
 
Plug-in Architectures
Plug-in ArchitecturesPlug-in Architectures
Plug-in Architectures
elliando dias
 

Similar to Using Recursive Common Table Expressions with Ecto (20)

Exploring SharePoint with F#
Exploring SharePoint with F#Exploring SharePoint with F#
Exploring SharePoint with F#
 
MapInfo Professional 12.0 and SQL Server 2008
MapInfo Professional 12.0 and SQL Server 2008MapInfo Professional 12.0 and SQL Server 2008
MapInfo Professional 12.0 and SQL Server 2008
 
Intro to-html-backbone-angular
Intro to-html-backbone-angularIntro to-html-backbone-angular
Intro to-html-backbone-angular
 
Web+Dev+Syllabus.pdf
Web+Dev+Syllabus.pdfWeb+Dev+Syllabus.pdf
Web+Dev+Syllabus.pdf
 
Plone For Developers - World Plone Day, 2009
Plone For Developers - World Plone Day, 2009Plone For Developers - World Plone Day, 2009
Plone For Developers - World Plone Day, 2009
 
Hexagonal architecture in PHP
Hexagonal architecture in PHPHexagonal architecture in PHP
Hexagonal architecture in PHP
 
F# for functional enthusiasts
F# for functional enthusiastsF# for functional enthusiasts
F# for functional enthusiasts
 
Daniel Egan Msdn Tech Days Oc Day2
Daniel Egan Msdn Tech Days Oc Day2Daniel Egan Msdn Tech Days Oc Day2
Daniel Egan Msdn Tech Days Oc Day2
 
Designing well known websites with ADF Rich Faces
Designing well known websites with ADF Rich FacesDesigning well known websites with ADF Rich Faces
Designing well known websites with ADF Rich Faces
 
Android | Busy Java Developers Guide to Android: UI | Ted Neward
Android | Busy Java Developers Guide to Android: UI | Ted NewardAndroid | Busy Java Developers Guide to Android: UI | Ted Neward
Android | Busy Java Developers Guide to Android: UI | Ted Neward
 
Evolve Your Code
Evolve Your CodeEvolve Your Code
Evolve Your Code
 
Progressive EPiServer Development
Progressive EPiServer DevelopmentProgressive EPiServer Development
Progressive EPiServer Development
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
 
Web Application Introduction
Web Application  IntroductionWeb Application  Introduction
Web Application Introduction
 
Extreme Swift
Extreme SwiftExtreme Swift
Extreme Swift
 
Intro To Spring Python
Intro To Spring PythonIntro To Spring Python
Intro To Spring Python
 
Automating SolidWorks with Excel
Automating SolidWorks with ExcelAutomating SolidWorks with Excel
Automating SolidWorks with Excel
 
iOS App Development with F# and Xamarin
iOS App Development with F# and XamariniOS App Development with F# and Xamarin
iOS App Development with F# and Xamarin
 
Plug-in Architectures
Plug-in ArchitecturesPlug-in Architectures
Plug-in Architectures
 

Recently uploaded

Finale of the Year: Apply for Next One!
Finale of the Year: Apply for Next One!Finale of the Year: Apply for Next One!
Finale of the Year: Apply for Next One!
GDSC PJATK
 
Ocean lotus Threat actors project by John Sitima 2024 (1).pptx
Ocean lotus Threat actors project by John Sitima 2024 (1).pptxOcean lotus Threat actors project by John Sitima 2024 (1).pptx
Ocean lotus Threat actors project by John Sitima 2024 (1).pptx
SitimaJohn
 
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
Tatiana Kojar
 
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Jeffrey Haguewood
 
UI5 Controls simplified - UI5con2024 presentation
UI5 Controls simplified - UI5con2024 presentationUI5 Controls simplified - UI5con2024 presentation
UI5 Controls simplified - UI5con2024 presentation
Wouter Lemaire
 
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success StoryDriving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Safe Software
 
Nordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptxNordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptx
MichaelKnudsen27
 
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdfMonitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Tosin Akinosho
 
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdfHow to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
Chart Kalyan
 
Trusted Execution Environment for Decentralized Process Mining
Trusted Execution Environment for Decentralized Process MiningTrusted Execution Environment for Decentralized Process Mining
Trusted Execution Environment for Decentralized Process Mining
LucaBarbaro3
 
Introduction of Cybersecurity with OSS at Code Europe 2024
Introduction of Cybersecurity with OSS  at Code Europe 2024Introduction of Cybersecurity with OSS  at Code Europe 2024
Introduction of Cybersecurity with OSS at Code Europe 2024
Hiroshi SHIBATA
 
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdfNunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
flufftailshop
 
GraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracyGraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracy
Tomaz Bratanic
 
Operating System Used by Users in day-to-day life.pptx
Operating System Used by Users in day-to-day life.pptxOperating System Used by Users in day-to-day life.pptx
Operating System Used by Users in day-to-day life.pptx
Pravash Chandra Das
 
Programming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup SlidesProgramming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup Slides
Zilliz
 
Columbus Data & Analytics Wednesdays - June 2024
Columbus Data & Analytics Wednesdays - June 2024Columbus Data & Analytics Wednesdays - June 2024
Columbus Data & Analytics Wednesdays - June 2024
Jason Packer
 
GenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizationsGenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizations
kumardaparthi1024
 
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
alexjohnson7307
 
Recommendation System using RAG Architecture
Recommendation System using RAG ArchitectureRecommendation System using RAG Architecture
Recommendation System using RAG Architecture
fredae14
 
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
saastr
 

Recently uploaded (20)

Finale of the Year: Apply for Next One!
Finale of the Year: Apply for Next One!Finale of the Year: Apply for Next One!
Finale of the Year: Apply for Next One!
 
Ocean lotus Threat actors project by John Sitima 2024 (1).pptx
Ocean lotus Threat actors project by John Sitima 2024 (1).pptxOcean lotus Threat actors project by John Sitima 2024 (1).pptx
Ocean lotus Threat actors project by John Sitima 2024 (1).pptx
 
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
Skybuffer AI: Advanced Conversational and Generative AI Solution on SAP Busin...
 
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
 
UI5 Controls simplified - UI5con2024 presentation
UI5 Controls simplified - UI5con2024 presentationUI5 Controls simplified - UI5con2024 presentation
UI5 Controls simplified - UI5con2024 presentation
 
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success StoryDriving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success Story
 
Nordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptxNordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptx
 
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdfMonitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdf
 
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdfHow to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
 
Trusted Execution Environment for Decentralized Process Mining
Trusted Execution Environment for Decentralized Process MiningTrusted Execution Environment for Decentralized Process Mining
Trusted Execution Environment for Decentralized Process Mining
 
Introduction of Cybersecurity with OSS at Code Europe 2024
Introduction of Cybersecurity with OSS  at Code Europe 2024Introduction of Cybersecurity with OSS  at Code Europe 2024
Introduction of Cybersecurity with OSS at Code Europe 2024
 
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdfNunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
Nunit vs XUnit vs MSTest Differences Between These Unit Testing Frameworks.pdf
 
GraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracyGraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracy
 
Operating System Used by Users in day-to-day life.pptx
Operating System Used by Users in day-to-day life.pptxOperating System Used by Users in day-to-day life.pptx
Operating System Used by Users in day-to-day life.pptx
 
Programming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup SlidesProgramming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup Slides
 
Columbus Data & Analytics Wednesdays - June 2024
Columbus Data & Analytics Wednesdays - June 2024Columbus Data & Analytics Wednesdays - June 2024
Columbus Data & Analytics Wednesdays - June 2024
 
GenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizationsGenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizations
 
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
leewayhertz.com-AI in predictive maintenance Use cases technologies benefits ...
 
Recommendation System using RAG Architecture
Recommendation System using RAG ArchitectureRecommendation System using RAG Architecture
Recommendation System using RAG Architecture
 
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
Overcoming the PLG Trap: Lessons from Canva's Head of Sales & Head of EMEA Da...
 

Using Recursive Common Table Expressions with Ecto

  • 1. Maarten van Vliet Backend developer @ Awkward Email: maarten@awkward.co Github: maartenvanvliet
  • 2. Recursive Common Table Expressions and Ecto PRESENTATION By Maarten van Vliet
  • 4. What is Sketch? An intuitive vector editor for the Mac. It’s used primarily by screen designers who create websites, icons, and user interfaces for desktop and mobile devices.
  • 5. Sketch Cloud Sketch Cloud is a platform that allows you to share documents easily and with everyone. Many more features are coming! Sketch Cloud uses a GraphQL API built in Elixir, we call it SketchQL
  • 6. Prototyping Sketch’s Prototyping features makes it easy to create interactive workflows and preview your designs as your users will see them. Released last year in Sketch and Sketch Cloud A user can now create a prototype in the Sketch, upload it to Cloud and interactively play with it
  • 7. Prototyping Cloud Building prototyping was challenging • Fluent transitions across browsers • Converting Sketch Prototypes to the web • And, there are simple prototypes such as this one
  • 9. Problems We needed to fluently transition from one screen to the next for prototyping in the browser. This meant: (deep) preloading the relations of one screen (artboard) with all other artboards So, when A is loaded, we need to load B and C, but also D!
  • 10. Simplest solution Recursively query database for related artboards from application 1. First query for artboard A 2. Query for artboards directly related to A, returns [B, C] 3. Query for artboards directly related to [B, C], but leave out already found artboards [A], this returns [D] 4. Query for artboards directly related to [D], but leave out already found artboards [A, B, C], returns [] 5. We stop when an empty set is returned. Problem:lots of queries
  • 11. Solution: Recursive Common Table Expressions! • Last year we migrated Sketch Cloud to Mariadb 10.2 • Introduced support for (Recursive) Common Table Expressions • (R)CTE's are also available in Mysql 8.0 (since 2018), and Postgres 8.4 (since 2009) • But what are they?
  • 12. Common Table Expressions A CTE is a temporary resultset Think of it as a database view only created and visible for one query. Useful for making subqueries easier to read You can have multiple in one query WITH FirstUser AS (   SELECT * FROM Users WHERE id = 1 ) SELECT * FROM FirstUser — Equivalent to query with subquery SELECT * FROM (SELECT * FROM Users WHERE id = 1) AS F;
  • 13. CTE’s can also do recursion! Recursive CTE’s are useful for querying hierarchies, e.g. tables with a parent_id column, so a row has can have a parent or children E.g. a CMS with pages, where a page can have children Pages: WITH RECURSIVE PageGraph AS ( SELECT P.id, P.parent_id FROM Pages P WHERE P.parent_id IS NULL —start id UNION SELECT P.id, P.parent_id FROM Pages P JOIN PageGraph PG ON P.parent_id = PG.id ) SELECT * FROM PageGraph Id parent_id Name 1 NULL Page 1 2 1 Subpage 1 3 1 Subpage 2 4 2 Subpage 3
  • 14. Dealing with cycles How to deal with cycles? Hierarchies with “loops” in them. E.g. page A has page B as a parent, and page B has page A as a parent WITH RECURSIVE PageGraph AS ( SELECT P.id, P.parent_id FROM Pages P WHERE P.id = 1 #start id UNION SELECT P.id, P.parent_id FROM Pages P JOIN PageGraph PG ON P.parent_id = PG.id ) SELECT * FROM PageGraph Id parent_id Name 1 2 Page 1 2 1 Page 2 Union removes duplicates!
  • 15. Back to the problem In steps: • First get artboards related to A, and store them in “to”, returns [B, C] • UNION this with the artboards where the id matches those of [B, C] • Get related artboards of [B, C], returns [D] • Again, UNION and get related artboards of [D], returns [A]. • Nothing new found, so stop WITH RECURSIVE RelatedArtboards AS ( SELECT — A.id AS "from", F.DestinationArtboardId AS "to" FROM Artboards A JOIN Layers L ON L.ArtboardId = A.id JOIN Flows F ON F.id = L.FlowId WHERE A.id = #Start ID, in this case Artboard A UNION SELECT — A.id AS "from", F.DestinationArtboardId AS "to" FROM Artboards A JOIN Layers L ON L.ArtboardId = A.id JOIN Flows F ON F.id = L.FlowId JOIN RelatedArtboards ON A.id = RelatedArtboards.to WHERE A.id = RelatedArtboards.to ) SELECT R.to FROM RelatedArtboards R From To A B A C B D C D D A
  • 16. Now we only need one query to load all artboards for a prototype! But how to use this in Elixir/Ecto?
  • 17. Not supported in the query builder, yet… Still open 😢
  • 18. Once merged: page_tree_initial_query = Page |> where([p], is_nil(p.parent_id)) page_tree_recursion_query = Page |> join(:inner, [p], pt in "page_tree", on: p.parent_id == pt.id) page_tree_query = page_tree_initial_queryv |> union(^page_tree_recursion_query) Page |> recursive_ctes(true) |> with_cte("page_tree", as: ^page_tree_query) |> Repo.all
  • 19. Until then… Fragments gives us the ability to extend Ecto defmacro with_related_artboards(artboard_id) do quote do fragment( """ ( WITH RECURSIVE RelatedArtboards AS ( SELECT F.DestinationArtboardId AS "to" FROM Artboards A JOIN Layers L ON L.ArtboardId = A.id JOIN Flows F ON F.id = L.FlowId WHERE A.id = ? UNION SELECT F.DestinationArtboardId AS "to" FROM Artboards A JOIN Layers L ON L.ArtboardId = A.id JOIN Flows F ON F.id = L.FlowId JOIN RelatedArtboards ON A.id = RelatedArtboards.to WHERE A.id = RelatedArtboards.to ) SELECT RelatedArtboards.to FROM RelatedArtboards WHERE RelatedArtboards.to IS NOT NULL ) """, unquote(artboard_id) ) end end import Sketchql.Utils.RelatedArtboards artboard_id = 1 Artboard |> join(:inner, [a], ra in with_related_artboards(^artboard_id) |> Repo.all() So, this will return a list of %Artboard{} Ecto.Schema structs related to the artboard with id 1. • Keep composability of queries
  • 20. 🎉 Conclusion • With one query leveraging Ecto and RCTE ’s we can query all artboards related to the current one, no matter how deep. • In the app we also paginate these calls. This way we can render much larger prototypes in Sketch Cloud • It really pays off to dive deep into the tools your database can provide such as RCTE’s. • Ecto’s extensibility is great! Where we could not use its native features we could use SQL to make up for it