Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Graph Databases and PHP

Graph Databases and PHP

Traditional relational databases — ironically — are not that good at the complex relationships some modern applications need.

Multiple joins and complex sub-queries can gradually take a toll on performance.

Graph Databases, on the other hand, are all about relationships. In this talk we will look at using the popular Neo4j graph database with PHP to build efficient relational data for OmNomHub: not your average recipe site.

Michelle Sanver

February 18, 2017
Tweet

More Decks by Michelle Sanver

Other Decks in Programming

Transcript

  1. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs \o/ A graph is an easy way

    to visualise connected data. Michelle Graphs likes
  2. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs vs. Relational databases Relational question: Average age

    of everyone in this list? Graph question: Who in here is likely going to the next DrupalCon?
  3. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs vs. Relational databases Spaghetti Pasta group Italian

    group Recipes Groups RecipeToGroup Spaghetti:Italian Spaghetti:Pasta Pasta group Spaghetti Italian group
  4. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs vs. Relational databases SET @entityid = '3';

    SELECT ea.attribute_id, ea.attribute_code, eav.value AS 'value', 'varchar' AS 'type' FROM catalog_category_entity e JOIN catalog_category_entity_varchar eav ON e.entity_id = eav.entity_id JOIN eav_attribute ea ON eav.attribute_id = ea.attribute_id WHERE e.entity_id = @entityid UNION SELECT ea.attribute_id, ea.attribute_code, eav.value AS 'value', 'int' AS 'type' FROM catalog_category_entity e JOIN catalog_category_entity_int eav ON e.entity_id = eav.entity_id JOIN eav_attribute ea ON eav.attribute_id = ea.attribute_id WHERE e.entity_id = @entityid UNION
  5. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs vs. Relational databases SELECT ea.attribute_id, ea.attribute_code, eav.value

    AS 'value', 'decimal' AS 'type' FROM catalog_category_entity e JOIN catalog_category_entity_decimal eav ON e.entity_id = eav.entity_id JOIN eav_attribute ea ON eav.attribute_id = ea.attribute_id WHERE e.entity_id = @entityid UNION selecting ea.attribute_id, ea.attribute_code, eav.value AS 'value', 'datetim 'type' FROM catalog_category_entity e JOIN catalog_category_entity_datetime eav ON e.entity_id = eav.entity_id JOIN eav_attribute ea ON eav.attribute_id = ea.attribute_id WHERE e.entity_id = @entityid UNION SELECT ea.attribute_id, ea.attribute_code, eav.value AS 'value', 'text' AS FROM catalog_category_entity e JOIN catalog_category_entity_text eav ON e.entity_id = eav.entity_id JOIN eav_attribute ea ON eav.attribute_id = ea.attribute_id WHERE e.entity_id = @entityid
  6. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Graphs and Neo4j (Node) { Properties } As

    many as you want Name: Michelle Nick: geekie Name: Cees-Jan Nick: WyriHaximus
  7. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j architecture Disks File System Cache Record Files

    Object Cache Cypher Core API Traversal API Transaction Management Transaction Log
  8. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j architecture Disks File System Cache Record Files

    Object Cache Cypher Core API Traversal API Transaction Management Transaction Log
  9. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j architecture Disks File System Cache Record Files

    Object Cache Cypher Core API Traversal API Transaction Management Transaction Log
  10. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j architecture Disks File System Cache Record Files

    Object Cache Cypher Core API Traversal API Transaction Management Transaction Log
  11. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j architecture Disks File System Cache Record Files

    Object Cache Cypher Core API Traversal API Transaction Management Transaction Log
  12. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP There is an actively maintained

    Drupal module for Drupal 7 and 8. https://www.drupal.org/project/neo4j
  13. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP $client = ClientBuilder::create()
 ->addConnection('bolt', 'bolt://neo4j:password@localhost:7687')


    ->build(); 
 $query = "MATCH (n:User) RETURN n";
 $result = $client->run($query);
 
 foreach ($result->getRecords() as $record) {
 echo(count($record->value('name'));
 }

  14. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP $client = ClientBuilder::create()
 ->addConnection('bolt', 'bolt://neo4j:password@localhost:7687')


    ->build(); 
 $query = "MATCH (n:User) RETURN n";
 $result = $client->run($query);
 
 foreach ($result->getRecords() as $record) {
 echo(count($record->value('name'));
 }

  15. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP $client = ClientBuilder::create()
 ->addConnection('bolt', 'bolt://neo4j:password@localhost:7687')


    ->build(); 
 $query = "MATCH (n:User) RETURN n";
 $result = $client->run($query);
 
 foreach ($result->getRecords() as $record) {
 echo(count($record->value('name'));
 }

  16. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP $client = ClientBuilder::create()
 ->addConnection('bolt', 'bolt://neo4j:password@localhost:7687')


    ->build(); 
 $query = "MATCH (n:User) RETURN n";
 $result = $client->run($query);
 
 foreach ($result->getRecords() as $record) {
 echo(count($record->value('name'));
 }

  17. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP /**
 * @OGM\GraphId()
 * @var

    int
 */
 protected $id;
 
 /**
 * @OGM\Property(type="string")
 * @var string
 */
 protected $recipeName;
 
 /**
 * @OGM\Relationship(type="FORKED", direction="OUTGOING", targetEntity="User", collection=true)
 * @var ArrayCollection|User[]
 */
 protected $users;
  18. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP /**
 * @OGM\GraphId()
 * @var

    int
 */
 protected $id;
 
 /**
 * @OGM\Property(type="string")
 * @var string
 */
 protected $recipeName;
 
 /**
 * @OGM\Relationship(type="FORKED", direction="OUTGOING", targetEntity="User", collection=true)
 * @var ArrayCollection|User[]
 */
 protected $users;
  19. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP /**
 * @OGM\GraphId()
 * @var

    int
 */
 protected $id;
 
 /**
 * @OGM\Property(type="string")
 * @var string
 */
 protected $recipeName;
 
 /**
 * @OGM\Relationship(type="FORKED", direction="OUTGOING", targetEntity="User", collection=true)
 * @var ArrayCollection|User[]
 */
 protected $users;
  20. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP /**
 * @OGM\GraphId()
 * @var

    int
 */
 protected $id;
 
 /**
 * @OGM\Property(type="string")
 * @var string
 */
 protected $recipeName;
 
 /**
 * @OGM\Relationship(type="FORKED", direction="OUTGOING", targetEntity="User", collection=true)
 * @var ArrayCollection|User[]
 */
 protected $users;
  21. (Michelle)-[:LOVES]->(Neo4j) @michellesanver Neo4j in PHP It is well documented https://neo4j.com/developer/php/

    https://github.com/graphaware/neo4j-php-client https://github.com/graphaware/neo4j-php-ogm