Алексей Злобин «scala in goozy»
TRANSCRIPT
![Page 1: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/1.jpg)
Scala in Goozy
Alexey ZlobinE-Legion
![Page 2: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/2.jpg)
Index
1. Goozy overview2. Scala's place3. Lift4. Cake pattern in scale5. Scalaz and other fancy stuff6. Summary
![Page 3: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/3.jpg)
What is Goozy?
A social network built around the concept of sticky note
● A note could be left anywhere in the Web.
● It is associated with particular page element.
Central UI concept: user's related feed with all new notes and comments
![Page 4: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/4.jpg)
Top-level architecture
![Page 5: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/5.jpg)
Scala's place
API server
Main functions:● Storage access● Background tasks (feed writing, e-mails)● Email sending● Text indexing
![Page 6: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/6.jpg)
Why scala?
● Fast● Сoncise● Expressive● Advanced OO● Some functional stuff
○ Simple concurrency● All Java legacy
available
![Page 7: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/7.jpg)
The team
● 2 persons● Strong Java background● Fancy about technologies● Love to try new things
![Page 8: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/8.jpg)
Lift
Utilized features:● REST● JSON serialisation
That's it...
![Page 9: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/9.jpg)
Lift: issuesLocalisation performance
● Hand-made localisation on standard resource bundles gave 4 times throughput improvement.
Very memory-consuming JSON serialisation.● Not so efficient PrettyPrinter is used● Functional-styled string escaping
Poor code style● Extremely long map-match-if hierarchies● Mutable, difficult to debug LiftRules design
![Page 10: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/10.jpg)
Lift: shift from
Some plans about migration to less sophisticated framework...
Ideally small and simple enough to be completely rewritten in case of any issue.
But we have a strong dependency from Boot and configuration
And there is some aspect-like hooks on HTTP processing, which are unportable.
![Page 11: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/11.jpg)
Goozy API logical structure
Application is composed from three layers.
Each layer consists from several similar components. Like UserStorage, GroupStorage, etc.
![Page 12: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/12.jpg)
Conceptual problems
● Components of each level depend from each other● Components most likely have several dependencies
from the previous level● A lot of common stuff inside a level
○ Every storage needs a DB connection○ Every service needs an entire storage system and
access to text indexes○ Etc...
![Page 13: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/13.jpg)
The solution: cake pattern
● Each logically closed piece of functionality is represented as component
● Dependencies are expressed as self-type
● Common features expressed as mix-ins
● Common combinations of functionality are expressed as mix-ins of several components
![Page 14: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/14.jpg)
Cake pattern: consequences
+ All top-level architecture is expressed in one less than 100 LOC file
+ Compile-time dependency checks
+ The biggest file is around 1000 LOC
- Long dependency lists● Poor design?
- Implicit dependency on mix-in order (linearisation strikes back)
● Prefer def and lazy
- A bit unclear how to deal with several dependencies of the same type but different runtime implementation
![Page 15: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/15.jpg)
scalaz.ValidationOne sweet morning I sent a link to the colleague...
On the next morning we had a new dependency and totally refactored request parameters analysis.
Now everything is validated.
![Page 16: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/16.jpg)
Validation: pros and cons+ Comprehensible error aggregation and reporting
+ The only imaginable way to deal with 20+ request parameters with 2-3 constraints on each
+ Unified approach to request validation and runtime error handling
+ Type-level check for correct error handling
- Monads and Applicatives cause massive brain damage
- Complicated error reports from the compiler
- You can't just ignore possibility of runtime exception
![Page 17: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/17.jpg)
Validations and exceptionsProblem: exceptions are here
Solution: catch'em and convert!
![Page 18: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/18.jpg)
Error handling: big picture
![Page 19: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/19.jpg)
Lessons
1. Always prefer simple tools2. Options and Eithers (Validations): they really work
○ It is possible to live with both exceptions and eithers○ Performance consequences are not clear○ Some times I had to use things far behind my
understanding (sequence, traverse)3. Server-side testing is difficult
○ Testing approach should be established before any code is written
![Page 20: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/20.jpg)
References
1. http://www.assembla.com/spaces/liftweb/wiki/REST_Web_Services - REST support in Lift
2. http://jonasboner.com/2008/10/06/real-world-scala-dependency-injection-di.html - complete cake pattern intro
3. https://gist.github.com/970717 - easy Validation example
![Page 21: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/21.jpg)
Testing
A lot of features
Very quickly evolved at the beginning
We needed to exclude possibility of regression
![Page 22: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/22.jpg)
Testing: solution
● Integration testing from the client point of view● All test deal only with the http interface● Every case is a short (5-10 reqs.) scenario● Every case is wrapped into JUnit test for convenience
![Page 23: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/23.jpg)
Testing: logical architecture
1. JUnit wrapper2. Scenario3. Library of available
operation on http interface4. Groovy's HTTPBuilder
![Page 24: Алексей Злобин «Scala in Goozy»](https://reader035.vdocuments.site/reader035/viewer/2022062319/55859aefd8b42aca7b8b5062/html5/thumbnails/24.jpg)
Integration testing: problems
Groovy1. Dynamic typing2. Not obvious ways to do simple things3. One extra language in project
Execution time