48
Hackathon 16/17.03.2016

Spryker Hackathon Q1 2016

Embed Size (px)

Citation preview

Page 1: Spryker Hackathon Q1 2016

Hackathon    16/17.03.2016      

Page 2: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   2  

Introduc?on  

Page 3: Spryker Hackathon Q1 2016

About  me  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   3  

Fabian  Wesner    >=  2015    Spryker  Systems    2012  –  2014    Project  A  Ventures    2011      Rocket  Internet    2010      Zalando  

Page 4: Spryker Hackathon Q1 2016

Contact  me  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   4  

Follow  me  on  twiQer  to  get    #Spryker  updates  and    photos  from  this  hackathon.    hQps://twiQer.com/FabianWesner          Ø  This  presenta?on  is  available  on  Slideshare!  

 

Page 5: Spryker Hackathon Q1 2016

Spryker  Bird’s  eye  view  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   5  

Page 6: Spryker Hackathon Q1 2016

Code  principles  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   6  

Spryker  (pragma?cally)  follows  the    SOLID-­‐Principles,    

Principles  of  cohesion,    

and  Principles  of  Coupling.  

Spryker  welcomes  Clean  Code!  

Highly  recom

mended!  

Page 7: Spryker Hackathon Q1 2016

Code  quality  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   7  

h"ps://scru*nizer-­‐ci.com/g/spryker/spryker/?branch=develop    

Page 8: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   8  

Layered  architecture  

Page 9: Spryker Hackathon Q1 2016

Four  Layer  Architecture  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   9  

Page 10: Spryker Hackathon Q1 2016

A  bundle  in  a  nutshell  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   10  

Page 11: Spryker Hackathon Q1 2016

Zed  –  Structure  of  a  bundle  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   11  

Page 12: Spryker Hackathon Q1 2016

Zed  –  Presenta?on  layer  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   12  

Spryker  uses  Twig  templa?ng  engine.  

Page 13: Spryker Hackathon Q1 2016

Zed  –  Presenta?on  layer  –  Technologies  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16  13  

Twig  templa?ng  engine    

 

NPM  for  packaging  

 

 

Webpack  for  collec?ng  all  the  assets,  load  them,      

check  them,  compile  and  op?mize  them  

Page 14: Spryker Hackathon Q1 2016

Zed  –  Communica?on  layer  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   14  

Controller,  Tables,  Forms  and  Plugins.  

 

Powered  by  Silex  micro-­‐framework  and  some  Symfony  components    

Page 15: Spryker Hackathon Q1 2016

Zed  –  Business  layer  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   15  

The  facade  is  the  API  (entry  point)  to  this  layer.  

 

Here  you  implement  your  business  models!  

 

Guideline:  

-­‐  Every  model  implements  an  interface  

-­‐  Dependency  Injec?on  only  

 

Page 16: Spryker Hackathon Q1 2016

Zed  –  Business  layer  -­‐  Facade  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   16  

The  facade  acts  like  an  internal  API.    

The  main  responsibility  of  the  facade  is  to  hide  the  internal  implementa?on.    

class CustomerFacade extends AbstractFacade!{ !! public function updateCustomer() ! { ... } !! public function restorePassword() ! { ... } !! public function setDefaultShippingAddress() ! { ... } !!} !

Page 17: Spryker Hackathon Q1 2016

Zed  –  Business  layer  -­‐  Facade  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   17  

The  façade  of  the  current  bundle  is  available  with  

in  Controllers  and  Plugins.  

$this->getFacade() !

Page 18: Spryker Hackathon Q1 2016

Spryker  uses    

Each  bundle  ships  with  a  part  of  the  schema.  

 

QueryContainer  acts  as  API  

 

En??es  and  query  objects  are  generated.  

Zed  –  Persistence  layer  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   18  

Page 19: Spryker Hackathon Q1 2016

Zed  –  Persistence  layer  –  QueryContainer  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   19  

The  QueryContainer  contains  all  queries  of  a  bundle.  

 

QueryContainer  is  used  by  the  other  layers  with:!

$this->getQueryContainer() !

Page 20: Spryker Hackathon Q1 2016

Zed  –  Persistence  layer  –  Schema  XML  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   20  

<?xml version="1.0"?> !<database name="zed”> ! ! <table name="spy_customer" idMethod="native" phpName="SpyCustomer"> ! <column name="id_customer" required="true" type="INTEGER” /> ! <column name="email" required="true" size="255" type="VARCHAR" /> ! <column name="first_name" size="100" type="VARCHAR" /> ! <column name="last_name" size="100" type="VARCHAR" /> ! <unique> ! <unique-column name="email" /> ! </unique> ! </table> !!</database> !

Page 21: Spryker Hackathon Q1 2016

Zed  –  Persistence  layer  –En??es&Queries  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   21  

// Entity !$customerEntity = new SpyCustomer(); !$customerEntity->setFirstName('John') ! ->setFirstName('John') ! ->setLastName('Doe') ! ->save(); !!// Query object !$customerQuery = new SpyCustomerQuery(); !$customerEntity = $customerQuery!

->filterByFirstName('John') !->findOne(); !

!

Page 22: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   22  

Packaging  with  bundles  -­‐  The  modular  monolith  -­‐  

Page 23: Spryker Hackathon Q1 2016

Zed  =  Monolith?  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   23  

Zed  

Page 24: Spryker Hackathon Q1 2016

Zed  consists  of  bundles  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   24  

A  bundle  is  a  “func?onal  unit”.  

 Bundles  are  decoupled  and  provide  an  explicit  API.  

 

They  follow  the  packaging  principles!  

 

Currently  there  are  >  100  bundles.  

 

 

Managed  by      

 

Page 25: Spryker Hackathon Q1 2016

Zed  =  Modular  Monolith  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   25  

Page 26: Spryker Hackathon Q1 2016

Each  bundle  consists  of  (up  to)  4  layers  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   26  

Page 27: Spryker Hackathon Q1 2016

Connec?ng  bundles  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   27  

Page 28: Spryker Hackathon Q1 2016

Connec?ng  bundles  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   28  

Page 29: Spryker Hackathon Q1 2016

Dependency  Provider  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   29  

class CartDependencyProvider extends AbstractBundleDependencyProvider!{ !! public function provideBusinessLayerDependencies(Container $container) ! { ! $container[self::FACADE_CALCULATION] = function (Container $container)

{ ! return $container->getLocator()->calculation()->facade(); ! }; !! return $container; ! } !} !

Page 30: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   30  

Programming  with  Spryker  

Page 31: Spryker Hackathon Q1 2016

Yves  client  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   31  

Page 32: Spryker Hackathon Q1 2016

Yves  client  –  Usage  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   32  

class CartOperationHandler extends BaseHandler!{ ! public function add($sku, $quantity, $optionValueUsageIds = []) ! { ! $itemTransfer = new ItemTransfer(); ! $itemTransfer->setSku($sku); ! $itemTransfer->setQuantity($quantity); !! $this->addProductOptions($optionValueUsageIds, $itemTransfer); !! $quoteTransfer = $this->cartClient->addItem($itemTransfer); ! $this->cartClient->storeQuote($quoteTransfer); ! } !} !

Page 33: Spryker Hackathon Q1 2016

Transfer  objects  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   33  

$customerTransfer = new CustomerTransfer(); !$customerTransfer! ->setEmail('[email protected]') ! ->setFirstName('John') ! ->setLastName('Doe'); ! !echo $customerTransfer->getFirstName(); // echos 'John' !!

<transfer name="Customer"> ! <property name="email" type="string" /> ! <property name="firstName" type="string" /> ! <property name="lastName" type="string" /> !</transfer> !

Page 34: Spryker Hackathon Q1 2016

Factories  -­‐  Usage  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   34  

class CartFacade extends AbstractFacade!{ ! public function add(CartChangeTransfer $cartChangeTransfer) ! { ! return $this->getFactory()->createCartOperation() ! ->add($cartChangeTransfer); ! } ! ! public function remove(CartChangeTransfer $cartChangeTransfer) ! { ! return $this->getFactory()->createCartOperation() ! ->remove($cartChangeTransfer); ! } !

Page 35: Spryker Hackathon Q1 2016

Factories  -­‐  Example  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   35  

class CartBusinessFactory extends AbstractBusinessFactory!{ ! /** ! * @return \Spryker\Zed\Cart\Business\Model\OperationInterface! */ !

public function createCartOperation() ! { ! return new Operation( ! $this->createStorageProvider(), ! $this->getCalculatorFacade(), ! $this->getItemGrouperFacade() ! ); ! } !} !

Page 36: Spryker Hackathon Q1 2016

Dependency  Injec?on  with  Interfaces  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   36  

class Operation implements OperationInterface!{ ! protected $cartStorageProvider; ! protected $calculationFacade; ! protected $itemGrouperFacade; !! public function __construct( ! StorageProviderInterface $cartStorageProvider, ! CartToCalculationInterface $calculationFacade, ! CartToItemGrouperInterface $itemGrouperFacade, ! ) { ! $this->cartStorageProvider = $cartStorageProvider; ! $this->calculationFacade = $calculationFacade; ! $this->itemGrouperFacade = $itemGrouperFacade; ! } !} !!!

Page 37: Spryker Hackathon Q1 2016

Extension  with  Plugins  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   37  

class CalculationDependencyProvider extends SprykerCalculationDependencyProvider!{ ! protected function getCalculatorStack (Container $container) ! { ! return [ ! #Item calculators ! new ItemGrossAmountsCalculatorPlugin(), ! new ProductOptionGrossSumCalculatorPlugin(), !! #GrandTotal! new GrandTotalTotalsCalculatorPlugin(), ! new GrandTotalWithDiscountsCalculatorPlugin(), !! #TaxTotal! new TaxTotalsCalculatorPlugin(), ! ]; ! } !

Page 38: Spryker Hackathon Q1 2016

Plugin  example  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   38  

class GrandTotalTotalsCalculatorPlugin extends AbstractPlugin ! implements CalculatorPluginInterface!{ ! public function recalculate(QuoteTransfer $quoteTransfer) ! { ! $this->getFacade()->calculateGrandTotalTotals($quoteTransfer); ! } !} !

Plugins  are  the  most  important  concept  for  extension  in  Spryker.  They  are  everywhere!  

Thurday  

Page 39: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   39  

Important  concepts  

Page 40: Spryker Hackathon Q1 2016

Order  Management  in  Spryker  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   40  

Page 41: Spryker Hackathon Q1 2016

Cronjob  scheduling  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16  

Cronjobs  are  executed  via  Jenkins.  

// See jobs.php!// Send emails every 10 minutes !$jobs[] = [ ! 'name' => 'send-mails', ! 'command' => '$PHP_BIN vendor/bin/console mail:send-mail', ! 'schedule' => '*/10 * * * *', ! 'enable' => true, ! 'run_on_non_production' => true, ! 'stores' => ['DE', 'FR'], !]; !

vendor/bin/console setup:jenkins:generate!

41  

h"p://zed.de.spryker.dev:10007/  

Page 42: Spryker Hackathon Q1 2016

Mul?  store  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   42  

A  store  is  a  business  unit  Osen  a  country  shop  

 

The  code  is  shared  and  localizable  You  can  extend  classes  and  templates  for  each  store.  

One  team  ó  n  Stores  

 

Dedicated  database  per  store    

A  store  can  have  mul?ple  locales  Mul?-­‐language  

Page 43: Spryker Hackathon Q1 2016

Release  management  (Preview)  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   43  

No  global  version  for  Spryker!  Spryker  V2  

 

Each  bundle  has  a  version  number    >  100  bundles  

Seman?c  versioning  

 

Con?nuous  delivery  of  atomic  releases    Monday:    Cart  2.0.0    

 Tuesday:    Cms  3.1.0    Thursday:  Cart  2.1.0  

Page 44: Spryker Hackathon Q1 2016

Scaling  (implementa?on  example)  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   44  

Yves  load-­‐balancer  

Zed  load-­‐balancer  

Yves  phpApp  

Yves  phpApp  

Yves  phpApp  

Zed  Main  phpApp*  

Zed  phpApp  

DB  

Redis  

Elas?c  search  

scale  

read  /  write  read  /  write   write  

read  

read  

*Zed  main  server  only:    run  cronjobs  and  post  

deployment  hooks  

scale  

Master-­‐master    or  master-­‐slave  configura@on  

Page 45: Spryker Hackathon Q1 2016

Spryker  hos?ng  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   45  

Spryker  follows  The  Twelve-­‐Factor  App  methodology    Runs  on  any  cloud  environment  and  bare-­‐metal      Solu?on  partners  for  hos?ng  available  Talk  to  us      Out-­‐of-­‐the-­‐box  integra?on  with  Heroku  (coming  soon)  Seamless  con?nuous  delivery  with  Github  and  Heroku  Pipelines    

Page 46: Spryker Hackathon Q1 2016

Spryker  documenta?on  

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   46  

hQp://spryker.github.io  

Page 47: Spryker Hackathon Q1 2016

2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16   47  

A  proven  technology  built  in  real-­‐world  projects  for  ambi?ous  and  non-­‐standard  business  models.    

Page 48: Spryker Hackathon Q1 2016

Spryker  Systems  GmbH  Julie-­‐Wolshorn-­‐Strasse  1  

10115  Berlin  Germany  

[email protected]    Phone:  +49  40  328  929  631  

Fax:  +49  40  328  929  699  

www.spryker.com      www.kassenzone.de  

www.digitalkaufmann.de  www.goto.project-­‐a.com      

48  2016  Spryker  Systems  GmbH  /  Hackathon  Q1/16