SlideShare uma empresa Scribd logo
1 de 88
Guyren G Howe
guyren@relevantlogic.com
@unclouded
Brought to you by
https://github.com/gisborne/railsconf_lydb
Information Technology -
Database Language SQL
(Proposed revised text of DIS 9075)
July 1992
Postgres’ Little-Known Secret
• Postgres is a great programming platform
Novel Postgres Features
• PostGIS
• Background workers
• Full-text search
• Custom dictionaries
• Stemming
• Stop words
• Normalization
• Synonyms
• Multiple languages
• Phrase search
• Proximity search
Novel Postgres Features
• Proper type system
• Custom types
• Functions
• Automatic casts
• Tables are types
• Functions take/act as
relations
• Arrays
• JSON
• HStore
• XML
Novel Postgres Features
• Foreign Data Wrappers
• SQL Databases
• LDAP
• Elastic Search
• Redis
• MongoDB
• Cassandra, CouchDB, …
• CSV/JSON/XML/…
• git/file system/imap/twitter
• google spreadsheet
• Roll your own (Python)
• …
Novel Postgres Features
• Program in civilized languages
• Python
• Perl
• Javascript
• R
• Scheme
• C
• Java
• PHP
• sh
• …
Model All the Things
Reporting
Check out public.all_join view
CREATE OR REPLACE VIEW public.all_join AS
SELECT c.customerid,
c.firstname,
c.lastname,
c.address1,
c.address2,
c.city,
c.state,
c.zip,
c.country,
c.email,
c.phone,
c.creditcardtype,
c.creditcard,
c.creditcardexpiration,
c.username,
c.password,
c.age,
c.income,
c.gender,
o.orderid,
o.orderdate,
o.netamount,
o.tax,
o.totalamount,
ol.quantity AS qty,
p.prod_id,
p.title,
p.price,
inv.quan_in_stock,
inv.sales,
cat.categoryname AS category
FROM customers c
FULL JOIN orders o USING (customerid)
FULL JOIN orderlines ol USING (orderid)
FULL JOIN products p USING (prod_id)
FULL JOIN categories cat ON p.category_id = cat.category
FULL JOIN inventory inv USING (prod_id)
Create a Schema
CREATE SCHEMA reporting;
Create a Schema
class AddReportingSchema < ActiveRecord::Migration[5.0]
def up
execute 'CREATE SCHEMA reporting'
end
def down
execute 'DROP SCHEMA reporting'
end
end
Create a Reports View 1
CREATE VIEW
all_views AS
SELECT
c.relname AS name,
obj_description(c.oid) AS description,
ns.nspname AS namespace
FROM
pg_class c JOIN
pg_namespace ns ON c.relnamespace = ns.oid
WHERE
c.relkind = 'v'::"char"
Create a Reports View 2
CREATE VIEW
public.reports AS
SELECT
name,
description
FROM
all_views
WHERE
namespace = 'reporting'::name
Create reporting.customers ViewCREATE VIEW
reporting.customers
AS
SELECT
customerid,
lastname,
firstname,
zip,
ARRAY_AGG(prod_id ORDER BY orderdate, prod_id) AS prod_ids,
ARRAY_AGG(title ORDER BY orderdate, prod_id) AS titles,
ARRAY_AGG(category ORDER BY orderdate, prod_id) AS categories,
ARRAY_AGG(price ORDER BY orderdate, prod_id) AS prices,
SUM(totalamount) AS spent
FROM
all_join
GROUP BY
customerid, lastname, firstname, zip
View that
Add Comment to reporting.customers
COMMENT ON
VIEW
reporting.customers
IS
'Customers with products sold to them';
Create Reports Controller, Model, Route
Rails Report Index View
_report partial
Start Rails; hit /reports
Add detail View
Hit /reports/customers
Cool
Create another reportWITH
scifi_viewers AS (
SELECT customerid
FROM all_join
WHERE ((category)::text = 'Sci-Fi'::text)
),
californians AS (
SELECT customerid
FROM all_join
WHERE ((state)::text = 'CA'::text)
),
targets AS (
SELECT customerid,
firstname,
lastname,
address1,
address2,
city,
state,
zip
FROM
all_join
WHERE
customerid IN (
SELECT customerid FROM scifi_viewers
)
OR customerid IN
(SELECT customerid FROM californians)
)
…
These are
Common Table Expressions
Create another reportSELECT prod_id,
title,
price,
quan_in_stock,
sales,
sum(totalamount) AS total_amt,
count(DISTINCT orderid) AS order_ct,
array_agg(lastname ORDER BY lastname, firstname, customerid) AS lastnames,
array_agg(firstname ORDER BY lastname, firstname, customerid) AS firstnames,
array_agg(state ORDER BY lastname, firstname, customerid) AS states,
array_agg(zip ORDER BY lastname, firstname, customerid) AS zips
FROM
targets
GROUP BY
prod_id,
title,
price,
quan_in_stock,
sales
Get Jiggy Wid It
Create reporting.customers_by_state View
…
SELECT
state,
CASE
WHEN LAG(state) OVER (ORDER BY state, lastname) IS NULL
OR
LAG(state) OVER (ORDER BY state, lastname)::text <> state::text
THEN
(('{"break": [1, "'::text || state::text) || '"]}'::text)::jsonb
ELSE
NULL::jsonb
END AS _meta),
…
Copy customers and add this
WHERE (length((state)::text) > 0)
GROUP BY
customerid,
lastname,
firstname,
state,
zip
ORDER BY
state,
lastname
… also add this
What’s this?
LAG(state) OVER (ORDER BY state, lastname)
From Postgres Docs
• A window function performs a calculation across a set of table
rows that are somehow related to the current row…
• …unlike regular aggregate functions, use of a window function does
not cause rows to become grouped
Three parts
• The function
• Which rows (optional)
• Which order (optional)
LAG(
state
)
OVER (
ORDER BY
state,
lastname
)
The function:
previous value of field (state)
SQL is sets.
“Previous” is meaningless
without an order.
OVER indicates window function
SELECT
depname,
empno,
salary,
rank() OVER (
PARTITION BY
depname
ORDER BY
salary DESC
)
FROM
empsalary;
Which rows
Optional.
Without it, applies to all rows
Order required
Function Use
rank Rank within partition
row_number Number of row within partition
lag Value from preceding row
lead Value from later row
…
Order Optional
• Makes function cumulative
• Applies to rows up to or equal on ORDER BY
Without ORDER BY
SELECT
salary,
SUM(salary)
OVER ()
FROM
empsalary;
salary | sum
--------+-------
5200 | 47100
5000 | 47100
3500 | 47100
4800 | 47100
3900 | 47100
4200 | 47100
4500 | 47100
4800 | 47100
6000 | 47100
5200 | 47100
(10 rows)
With ORDER BY
SELECT
salary,
SUM(salary)
OVER (
ORDER BY
salary)
FROM
empsalary;
salary | sum
--------+-------
3500 | 3500
3900 | 7400
4200 | 11600
4500 | 16100
4800 | 25700
4800 | 25700
5000 | 30700
5200 | 41100
5200 | 41100
6000 | 47100
(10 rows)
_break partial
View that
Get More Jiggy Wid It
Create another schema
CREATE SCHEMA reporting_helpers;
Create a view
CREATE VIEW
reporting_helpers.customers_by_state_ranked
AS
SELECT
*,
rank() OVER (
PARTITION BY
c.state
ORDER BY
c.spent) AS rank
FROM
reporting.customers_by_state c
Add Javascript
CREATE EXTENSION plv8;
Create a Javascript FunctionCREATE FUNCTION
reporting.formatted_cust_by_state_bold(
c reporting_helpers.customers_by_state_ranked
)
RETURNS
reporting_helpers.customers_by_state_ranked
LANGUAGE
plv8
STRICT COST 1
AS $function$
if (c.rank == 1) {
c['_meta'] = c['_meta'] || {}
c['_meta']['raw'] = c['_meta']['raw'] || {}
c['_meta']['raw']['spent'] = c['_meta']['raw']['spent'] || {}
c['_meta']['raw']['spent'] = "<td><b>" + c.spent + "</b></td>"
}
return c
$function$
A table/view defines a type
STRICT means “functional on a given db state”
Create a Javascript Function
CREATE FUNCTION
reporting.formatted_cust_by_state_bold(
c reporting_helpers.customers_by_state_ranked
)
RETURNS
reporting_helpers.customers_by_state_ranked
LANGUAGE
plv8
STRICT COST 1
AS $function$
LANGUAGE
plv8
STRICT COST 1
AS $function$
if (c.rank == 1) {
c['_meta'] = c['meta'] || {}
c['_meta']['raw'] = c['_meta']['raw'] || {}
c['_meta']['raw']['spent'] = c['_meta']['raw']['spent'] || {}
c['_meta']['raw']['spent'] = "<td><b>" + c.spent + "</b></td>"
}
return c
$function$
Create a Javascript Function
Create View
CREATE VIEW
reporting.customers_by_state_ranked
AS
SELECT
(reporting.formatted_cust_by_state_bold(c)).*
FROM
reporting_helpers.customers_by_state_ranked c
ORDER BY
state,
lastname
SQL sucks
View that
…
This is different
• Fast
• Language Neutral
• Functional
• Relational
“Web Services Architecture”
“Web Services Architecture”
Every arrow requires:
• Route
• Controller Actions
• Tests
• Model Methods
• Tests
“Services Architecture”
“Services Architecture”
Every arrow requires:
• Model Methods
• Tests
Novel Postgres Features
• Proper type system
• Custom types
• Functions
• Automatic casts
• Tables are types
• Arrays
• JSON
• XML
Novel Postgres Features
• Foreign Data Wrappers
• SQL Databases
• LDAP
• Elastic Search
• Redis
• MongoDB
• Cassandra, CouchDB, …
• CSV/JSON/XML/…
• git/file system/imap/twitter
• google spreadsheet
• Roll your own (Python)
• …
In Console (on a Mac)
ActiveRecord::Base.connection_pool.with_connection do |connection|
c = connection.instance_variable_get(:@connection)
c.async_exec "LISTEN speak"
c.wait_for_notify do |channel, pid, payload|
p "got #{channel} #{pid} #{payload}"
`say #{payload}`
end
c.async_exec "UNLISTEN *"
end
In psql
SELECT pg_notify('speak', 'Hello from Postgres');
or another console:
ActiveRecord::Base.connection.execute("
SELECT pg_notify('speak', 'Hello from Postgres');")
Discussion
Go.
We’re hiring
California
Connecticut
Illinois
Minnesota
New Jersey
North Carolina
Ohio
Pennsylvania
Tennessee
Texas
Washington
Guyren G Howe
guyren@relevantlogic.com
@unclouded
Brought to you by
http://scriptscribe.org
https://medium.com/@gisborne

Mais conteúdo relacionado

Mais procurados

Entity Attribute Value (Eav)
Entity   Attribute   Value (Eav)Entity   Attribute   Value (Eav)
Entity Attribute Value (Eav)
Tâm
 
Appendix A Tables
Appendix A   TablesAppendix A   Tables
Appendix A Tables
LiquidHub
 

Mais procurados (20)

Postgres rules
Postgres rulesPostgres rules
Postgres rules
 
Data Exploration with Apache Drill: Day 2
Data Exploration with Apache Drill: Day 2Data Exploration with Apache Drill: Day 2
Data Exploration with Apache Drill: Day 2
 
Sparklyr
SparklyrSparklyr
Sparklyr
 
Hive Functions Cheat Sheet
Hive Functions Cheat SheetHive Functions Cheat Sheet
Hive Functions Cheat Sheet
 
Extensible Data Modeling
Extensible Data ModelingExtensible Data Modeling
Extensible Data Modeling
 
1 data types
1 data types1 data types
1 data types
 
R Programming: Numeric Functions In R
R Programming: Numeric Functions In RR Programming: Numeric Functions In R
R Programming: Numeric Functions In R
 
Abap 7.40
Abap 7.40Abap 7.40
Abap 7.40
 
Spreadsheet ml subject pivottable
Spreadsheet ml subject   pivottableSpreadsheet ml subject   pivottable
Spreadsheet ml subject pivottable
 
Introduction to DAX Language
Introduction to DAX LanguageIntroduction to DAX Language
Introduction to DAX Language
 
CREATE INDEX … USING VODKA. VODKA CONNECTING INDEXES, Олег Бартунов, Александ...
CREATE INDEX … USING VODKA. VODKA CONNECTING INDEXES, Олег Бартунов, Александ...CREATE INDEX … USING VODKA. VODKA CONNECTING INDEXES, Олег Бартунов, Александ...
CREATE INDEX … USING VODKA. VODKA CONNECTING INDEXES, Олег Бартунов, Александ...
 
Spark + Clojure for Topic Discovery - Zalando Tech Clojure/Conj Talk
Spark + Clojure for Topic Discovery - Zalando Tech Clojure/Conj TalkSpark + Clojure for Topic Discovery - Zalando Tech Clojure/Conj Talk
Spark + Clojure for Topic Discovery - Zalando Tech Clojure/Conj Talk
 
Chris Seebacher Portfolio
Chris Seebacher PortfolioChris Seebacher Portfolio
Chris Seebacher Portfolio
 
Field formatters
Field formattersField formatters
Field formatters
 
Entity Attribute Value (Eav)
Entity   Attribute   Value (Eav)Entity   Attribute   Value (Eav)
Entity Attribute Value (Eav)
 
Flink Forward San Francisco 2019: TensorFlow Extended: An end-to-end machine ...
Flink Forward San Francisco 2019: TensorFlow Extended: An end-to-end machine ...Flink Forward San Francisco 2019: TensorFlow Extended: An end-to-end machine ...
Flink Forward San Francisco 2019: TensorFlow Extended: An end-to-end machine ...
 
ACADILD:: HADOOP LESSON
ACADILD:: HADOOP LESSON ACADILD:: HADOOP LESSON
ACADILD:: HADOOP LESSON
 
Cubes - Lightweight Python OLAP (EuroPython 2012 talk)
Cubes - Lightweight Python OLAP (EuroPython 2012 talk)Cubes - Lightweight Python OLAP (EuroPython 2012 talk)
Cubes - Lightweight Python OLAP (EuroPython 2012 talk)
 
First steps in PERL
First steps in PERLFirst steps in PERL
First steps in PERL
 
Appendix A Tables
Appendix A   TablesAppendix A   Tables
Appendix A Tables
 

Semelhante a Love Your Database Railsconf 2017

PerlApp2Postgresql (2)
PerlApp2Postgresql (2)PerlApp2Postgresql (2)
PerlApp2Postgresql (2)
Jerome Eteve
 
Heroku Postgres SQL Tips, Tricks, Hacks
Heroku Postgres SQL Tips, Tricks, HacksHeroku Postgres SQL Tips, Tricks, Hacks
Heroku Postgres SQL Tips, Tricks, Hacks
Salesforce Developers
 

Semelhante a Love Your Database Railsconf 2017 (20)

PerlApp2Postgresql (2)
PerlApp2Postgresql (2)PerlApp2Postgresql (2)
PerlApp2Postgresql (2)
 
AWS November Webinar Series - Advanced Analytics with Amazon Redshift and the...
AWS November Webinar Series - Advanced Analytics with Amazon Redshift and the...AWS November Webinar Series - Advanced Analytics with Amazon Redshift and the...
AWS November Webinar Series - Advanced Analytics with Amazon Redshift and the...
 
How to generate a 100+ page website using parameterisation in R
How to generate a 100+ page website using parameterisation in RHow to generate a 100+ page website using parameterisation in R
How to generate a 100+ page website using parameterisation in R
 
MongoDB World 2018: Keynote
MongoDB World 2018: KeynoteMongoDB World 2018: Keynote
MongoDB World 2018: Keynote
 
Interactively querying Google Analytics reports from R using ganalytics
Interactively querying Google Analytics reports from R using ganalyticsInteractively querying Google Analytics reports from R using ganalytics
Interactively querying Google Analytics reports from R using ganalytics
 
Advanced SQL For Data Scientists
Advanced SQL For Data ScientistsAdvanced SQL For Data Scientists
Advanced SQL For Data Scientists
 
MongoDB Aggregation Framework
MongoDB Aggregation FrameworkMongoDB Aggregation Framework
MongoDB Aggregation Framework
 
Scaling PostgreSQL With GridSQL
Scaling PostgreSQL With GridSQLScaling PostgreSQL With GridSQL
Scaling PostgreSQL With GridSQL
 
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
 
Heroku Postgres SQL Tips, Tricks, Hacks
Heroku Postgres SQL Tips, Tricks, HacksHeroku Postgres SQL Tips, Tricks, Hacks
Heroku Postgres SQL Tips, Tricks, Hacks
 
Data infrastructure for the other 90% of companies
Data infrastructure for the other 90% of companiesData infrastructure for the other 90% of companies
Data infrastructure for the other 90% of companies
 
Hadoop Integration in Cassandra
Hadoop Integration in CassandraHadoop Integration in Cassandra
Hadoop Integration in Cassandra
 
Groovy On Trading Desk (2010)
Groovy On Trading Desk (2010)Groovy On Trading Desk (2010)
Groovy On Trading Desk (2010)
 
Enterprise Postgres
Enterprise PostgresEnterprise Postgres
Enterprise Postgres
 
Introduction to MongoDB
Introduction to MongoDBIntroduction to MongoDB
Introduction to MongoDB
 
2011 Mongo FR - MongoDB introduction
2011 Mongo FR - MongoDB introduction2011 Mongo FR - MongoDB introduction
2011 Mongo FR - MongoDB introduction
 
Scalding big ADta
Scalding big ADtaScalding big ADta
Scalding big ADta
 
Framework
FrameworkFramework
Framework
 
VSSML18. Data Transformations
VSSML18. Data TransformationsVSSML18. Data Transformations
VSSML18. Data Transformations
 
Meetup cassandra for_java_cql
Meetup cassandra for_java_cqlMeetup cassandra for_java_cql
Meetup cassandra for_java_cql
 

Último

CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICECHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
9953056974 Low Rate Call Girls In Saket, Delhi NCR
 
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdfintroduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
VishalKumarJha10
 

Último (20)

Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
 
Unveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time ApplicationsUnveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
 
How To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected WorkerHow To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected Worker
 
Software Quality Assurance Interview Questions
Software Quality Assurance Interview QuestionsSoftware Quality Assurance Interview Questions
Software Quality Assurance Interview Questions
 
call girls in Vaishali (Ghaziabad) 🔝 >༒8448380779 🔝 genuine Escort Service 🔝✔️✔️
call girls in Vaishali (Ghaziabad) 🔝 >༒8448380779 🔝 genuine Escort Service 🔝✔️✔️call girls in Vaishali (Ghaziabad) 🔝 >༒8448380779 🔝 genuine Escort Service 🔝✔️✔️
call girls in Vaishali (Ghaziabad) 🔝 >༒8448380779 🔝 genuine Escort Service 🔝✔️✔️
 
How To Use Server-Side Rendering with Nuxt.js
How To Use Server-Side Rendering with Nuxt.jsHow To Use Server-Side Rendering with Nuxt.js
How To Use Server-Side Rendering with Nuxt.js
 
Microsoft AI Transformation Partner Playbook.pdf
Microsoft AI Transformation Partner Playbook.pdfMicrosoft AI Transformation Partner Playbook.pdf
Microsoft AI Transformation Partner Playbook.pdf
 
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICECHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
 
How to Choose the Right Laravel Development Partner in New York City_compress...
How to Choose the Right Laravel Development Partner in New York City_compress...How to Choose the Right Laravel Development Partner in New York City_compress...
How to Choose the Right Laravel Development Partner in New York City_compress...
 
A Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docxA Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docx
 
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdfLearn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
 
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdfintroduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
introduction-to-automotive Andoid os-csimmonds-ndctechtown-2021.pdf
 
The Ultimate Test Automation Guide_ Best Practices and Tips.pdf
The Ultimate Test Automation Guide_ Best Practices and Tips.pdfThe Ultimate Test Automation Guide_ Best Practices and Tips.pdf
The Ultimate Test Automation Guide_ Best Practices and Tips.pdf
 
Direct Style Effect Systems - The Print[A] Example - A Comprehension Aid
Direct Style Effect Systems -The Print[A] Example- A Comprehension AidDirect Style Effect Systems -The Print[A] Example- A Comprehension Aid
Direct Style Effect Systems - The Print[A] Example - A Comprehension Aid
 
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
 
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdfAzure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
 
VTU technical seminar 8Th Sem on Scikit-learn
VTU technical seminar 8Th Sem on Scikit-learnVTU technical seminar 8Th Sem on Scikit-learn
VTU technical seminar 8Th Sem on Scikit-learn
 
Right Money Management App For Your Financial Goals
Right Money Management App For Your Financial GoalsRight Money Management App For Your Financial Goals
Right Money Management App For Your Financial Goals
 
5 Signs You Need a Fashion PLM Software.pdf
5 Signs You Need a Fashion PLM Software.pdf5 Signs You Need a Fashion PLM Software.pdf
5 Signs You Need a Fashion PLM Software.pdf
 
Diamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with PrecisionDiamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with Precision
 

Love Your Database Railsconf 2017

  • 1. Guyren G Howe guyren@relevantlogic.com @unclouded Brought to you by https://github.com/gisborne/railsconf_lydb
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9. Information Technology - Database Language SQL (Proposed revised text of DIS 9075) July 1992
  • 10.
  • 11. Postgres’ Little-Known Secret • Postgres is a great programming platform
  • 12. Novel Postgres Features • PostGIS • Background workers • Full-text search • Custom dictionaries • Stemming • Stop words • Normalization • Synonyms • Multiple languages • Phrase search • Proximity search
  • 13. Novel Postgres Features • Proper type system • Custom types • Functions • Automatic casts • Tables are types • Functions take/act as relations • Arrays • JSON • HStore • XML
  • 14. Novel Postgres Features • Foreign Data Wrappers • SQL Databases • LDAP • Elastic Search • Redis • MongoDB • Cassandra, CouchDB, … • CSV/JSON/XML/… • git/file system/imap/twitter • google spreadsheet • Roll your own (Python) • …
  • 15. Novel Postgres Features • Program in civilized languages • Python • Perl • Javascript • R • Scheme • C • Java • PHP • sh • …
  • 16. Model All the Things
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 27.
  • 28. CREATE OR REPLACE VIEW public.all_join AS SELECT c.customerid, c.firstname, c.lastname, c.address1, c.address2, c.city, c.state, c.zip, c.country, c.email, c.phone, c.creditcardtype, c.creditcard, c.creditcardexpiration, c.username, c.password, c.age, c.income, c.gender, o.orderid, o.orderdate, o.netamount, o.tax, o.totalamount, ol.quantity AS qty, p.prod_id, p.title, p.price, inv.quan_in_stock, inv.sales, cat.categoryname AS category FROM customers c FULL JOIN orders o USING (customerid) FULL JOIN orderlines ol USING (orderid) FULL JOIN products p USING (prod_id) FULL JOIN categories cat ON p.category_id = cat.category FULL JOIN inventory inv USING (prod_id)
  • 29. Create a Schema CREATE SCHEMA reporting;
  • 30. Create a Schema class AddReportingSchema < ActiveRecord::Migration[5.0] def up execute 'CREATE SCHEMA reporting' end def down execute 'DROP SCHEMA reporting' end end
  • 31.
  • 32. Create a Reports View 1 CREATE VIEW all_views AS SELECT c.relname AS name, obj_description(c.oid) AS description, ns.nspname AS namespace FROM pg_class c JOIN pg_namespace ns ON c.relnamespace = ns.oid WHERE c.relkind = 'v'::"char"
  • 33. Create a Reports View 2 CREATE VIEW public.reports AS SELECT name, description FROM all_views WHERE namespace = 'reporting'::name
  • 34. Create reporting.customers ViewCREATE VIEW reporting.customers AS SELECT customerid, lastname, firstname, zip, ARRAY_AGG(prod_id ORDER BY orderdate, prod_id) AS prod_ids, ARRAY_AGG(title ORDER BY orderdate, prod_id) AS titles, ARRAY_AGG(category ORDER BY orderdate, prod_id) AS categories, ARRAY_AGG(price ORDER BY orderdate, prod_id) AS prices, SUM(totalamount) AS spent FROM all_join GROUP BY customerid, lastname, firstname, zip
  • 36. Add Comment to reporting.customers COMMENT ON VIEW reporting.customers IS 'Customers with products sold to them';
  • 40. Start Rails; hit /reports
  • 43. Cool
  • 44. Create another reportWITH scifi_viewers AS ( SELECT customerid FROM all_join WHERE ((category)::text = 'Sci-Fi'::text) ), californians AS ( SELECT customerid FROM all_join WHERE ((state)::text = 'CA'::text) ), targets AS ( SELECT customerid, firstname, lastname, address1, address2, city, state, zip FROM all_join WHERE customerid IN ( SELECT customerid FROM scifi_viewers ) OR customerid IN (SELECT customerid FROM californians) ) … These are Common Table Expressions
  • 45. Create another reportSELECT prod_id, title, price, quan_in_stock, sales, sum(totalamount) AS total_amt, count(DISTINCT orderid) AS order_ct, array_agg(lastname ORDER BY lastname, firstname, customerid) AS lastnames, array_agg(firstname ORDER BY lastname, firstname, customerid) AS firstnames, array_agg(state ORDER BY lastname, firstname, customerid) AS states, array_agg(zip ORDER BY lastname, firstname, customerid) AS zips FROM targets GROUP BY prod_id, title, price, quan_in_stock, sales
  • 47.
  • 48. Create reporting.customers_by_state View … SELECT state, CASE WHEN LAG(state) OVER (ORDER BY state, lastname) IS NULL OR LAG(state) OVER (ORDER BY state, lastname)::text <> state::text THEN (('{"break": [1, "'::text || state::text) || '"]}'::text)::jsonb ELSE NULL::jsonb END AS _meta), … Copy customers and add this
  • 49. WHERE (length((state)::text) > 0) GROUP BY customerid, lastname, firstname, state, zip ORDER BY state, lastname … also add this
  • 50. What’s this? LAG(state) OVER (ORDER BY state, lastname)
  • 51. From Postgres Docs • A window function performs a calculation across a set of table rows that are somehow related to the current row… • …unlike regular aggregate functions, use of a window function does not cause rows to become grouped
  • 52. Three parts • The function • Which rows (optional) • Which order (optional)
  • 53. LAG( state ) OVER ( ORDER BY state, lastname ) The function: previous value of field (state) SQL is sets. “Previous” is meaningless without an order. OVER indicates window function
  • 54. SELECT depname, empno, salary, rank() OVER ( PARTITION BY depname ORDER BY salary DESC ) FROM empsalary; Which rows Optional. Without it, applies to all rows
  • 55. Order required Function Use rank Rank within partition row_number Number of row within partition lag Value from preceding row lead Value from later row …
  • 56. Order Optional • Makes function cumulative • Applies to rows up to or equal on ORDER BY
  • 57. Without ORDER BY SELECT salary, SUM(salary) OVER () FROM empsalary; salary | sum --------+------- 5200 | 47100 5000 | 47100 3500 | 47100 4800 | 47100 3900 | 47100 4200 | 47100 4500 | 47100 4800 | 47100 6000 | 47100 5200 | 47100 (10 rows)
  • 58. With ORDER BY SELECT salary, SUM(salary) OVER ( ORDER BY salary) FROM empsalary; salary | sum --------+------- 3500 | 3500 3900 | 7400 4200 | 11600 4500 | 16100 4800 | 25700 4800 | 25700 5000 | 30700 5200 | 41100 5200 | 41100 6000 | 47100 (10 rows)
  • 60.
  • 61.
  • 62.
  • 64. Get More Jiggy Wid It
  • 65. Create another schema CREATE SCHEMA reporting_helpers;
  • 66. Create a view CREATE VIEW reporting_helpers.customers_by_state_ranked AS SELECT *, rank() OVER ( PARTITION BY c.state ORDER BY c.spent) AS rank FROM reporting.customers_by_state c
  • 68. Create a Javascript FunctionCREATE FUNCTION reporting.formatted_cust_by_state_bold( c reporting_helpers.customers_by_state_ranked ) RETURNS reporting_helpers.customers_by_state_ranked LANGUAGE plv8 STRICT COST 1 AS $function$ if (c.rank == 1) { c['_meta'] = c['_meta'] || {} c['_meta']['raw'] = c['_meta']['raw'] || {} c['_meta']['raw']['spent'] = c['_meta']['raw']['spent'] || {} c['_meta']['raw']['spent'] = "<td><b>" + c.spent + "</b></td>" } return c $function$ A table/view defines a type STRICT means “functional on a given db state”
  • 69. Create a Javascript Function CREATE FUNCTION reporting.formatted_cust_by_state_bold( c reporting_helpers.customers_by_state_ranked ) RETURNS reporting_helpers.customers_by_state_ranked LANGUAGE plv8 STRICT COST 1 AS $function$
  • 70. LANGUAGE plv8 STRICT COST 1 AS $function$ if (c.rank == 1) { c['_meta'] = c['meta'] || {} c['_meta']['raw'] = c['_meta']['raw'] || {} c['_meta']['raw']['spent'] = c['_meta']['raw']['spent'] || {} c['_meta']['raw']['spent'] = "<td><b>" + c.spent + "</b></td>" } return c $function$ Create a Javascript Function
  • 73.
  • 74. This is different • Fast • Language Neutral • Functional • Relational
  • 76. “Web Services Architecture” Every arrow requires: • Route • Controller Actions • Tests • Model Methods • Tests
  • 77.
  • 79. “Services Architecture” Every arrow requires: • Model Methods • Tests
  • 80. Novel Postgres Features • Proper type system • Custom types • Functions • Automatic casts • Tables are types • Arrays • JSON • XML
  • 81. Novel Postgres Features • Foreign Data Wrappers • SQL Databases • LDAP • Elastic Search • Redis • MongoDB • Cassandra, CouchDB, … • CSV/JSON/XML/… • git/file system/imap/twitter • google spreadsheet • Roll your own (Python) • …
  • 82.
  • 83. In Console (on a Mac) ActiveRecord::Base.connection_pool.with_connection do |connection| c = connection.instance_variable_get(:@connection) c.async_exec "LISTEN speak" c.wait_for_notify do |channel, pid, payload| p "got #{channel} #{pid} #{payload}" `say #{payload}` end c.async_exec "UNLISTEN *" end
  • 84. In psql SELECT pg_notify('speak', 'Hello from Postgres'); or another console: ActiveRecord::Base.connection.execute(" SELECT pg_notify('speak', 'Hello from Postgres');")
  • 86.
  • 87. We’re hiring California Connecticut Illinois Minnesota New Jersey North Carolina Ohio Pennsylvania Tennessee Texas Washington
  • 88. Guyren G Howe guyren@relevantlogic.com @unclouded Brought to you by http://scriptscribe.org https://medium.com/@gisborne