GithubHelp home page GithubHelp logo

atomgraph / core-php Goto Github PK

View Code? Open in Web Editor NEW
26.0 9.0 4.0 414 KB

Generic Jena-compatible PHP Linked Data management library. Apache license.

Home Page: https://atomgraph.com

PHP 96.90% JavaScript 3.10%
linked-data rdf php api

core-php's Introduction

Requirements

PHP 5.3 or later. Might work on earlier PHP 5.x versions. Java version is in the works.

Description

Graphity is a fully object-oriented PHP framework for building flexible RESTful, Semantic Web, and/or Linked Data web applications.

Graphity tries not to invent new conventions, but instead to combine existing ones. It is based on W3C standards and reuses Java APIs where possible.

JAX-RS

Supports JAX-RS-style RESTful API:

  • resource annotations like @Path and @GET
  • UriBuilder for building URIs out of components (includes implementation in JavaScript)
  • ResponseBuilder for building Response objects

Further implementation of missing JAX-RS features is planned.

RDF API

Supports Jena-style object-oriented RDF API:

  • Model
    • RDF/XML (DOM) serialization
    • Turtle serialization
  • Statement
  • Resource
  • Literal

Utilities

Includes utility classes for dealing with SPARQL, RDF/XML, and XSLT:

  • Repository for remote SPARQL 1.1 endpoint access
  • QueryBuilder for building SPARQL queries
  • RDFForm for reading requests in RDF/POST encoding
  • MultipartParser and MultipartRequest for reading multipart/form-data requests (PHP port of O'Reilly's Multipart classes)
  • XSLTBuilder for building XSLT transformations (PHP's XSL extension must be enabled)
  • DOM2Model for converting RDF/XML to Model (reverse of Model::toDOM())

Usage

To create a Graphity PHP application, you need to follow similar steps as in creating JAX-RS webapp, plus some extra steps because of PHP's interpreted and per-request nature:

  1. Checkout or extract graphity-core into /lib/graphity-core or similar folder in your project. We recommend choosing the latest version tag on GitHub.

    We strongly recommend Maven Standard Directory Layout, as it will be easier to share reusable resources with the Java version in the future. It is used in the following examples.

  2. Create some resource class that imports and extends Graphity\Resource, for example:

    namespace My;
    
    use Graphity\Response;
    use Graphity\ResponseBuilder;
    use Graphity\View\ContentType;
    
    class Resource extends \Graphity\Resource
    

    We strongly recommend using PHP namespaces with the standard folder layout. In Maven structure, that would be within the src/main/php folder. It is used in the following examples.

  3. Annotate the class with @Path and methods with @GET/@POST etc., for example:

    namespace My;
    
    use Graphity\Response;
    use Graphity\ResponseBuilder;
    use Graphity\View\ContentType;
    
    /**
     * @Path("/hello")
     */
    class Resource extends \Graphity\Resource
    {
    
        /**
         * @GET
         * @Produces("text/html")
         */
        public function getResponse()
        {
            return ResponseBuilder::newInstance()->
                entity("<html>Hello ". $this->getRequest()->getParameter("what") ."!</html>")->
                status(Response::SC_OK)->
                type(ContentType::TEXT_HTML)->
                build();
        }
    }
    

    This class would match GET requests on /hello path and print a statement depending on the what query parameter value.

    PHP annotations must be embedded in /* */ comment blocks.

    @Produces/@Consumes annotations are not yet fully supported, but we recommend adding them for future compatibility.

  4. Run /lib/graphity-core/bin/route_mapper.php specifying the root folder of your namespace and the location of your route map file, for example (paths are relative to project root in this case):

    $ php lib/graphity-core/bin/route_mapper.php src/main/php/My src/main/php/routes.php
    

    This should scan your resource classes and generate a route map file, which is used internally by Graphity to match request URIs against JAX-RS annotations. This does not happen dynamically (as of yet), you have to re-map routes with route_mapper.php every time your annotations change.

  5. Implement a subclass of Graphity\Application:

     namespace My;
    
     class Application extends \Graphity\Application
     {
    
         public function __construct()
         {
             parent::__construct(include(dirname(dirname(__FILE__)) . "/routes.php"));
    
             $loader = new \Graphity\Loader("My", dirname(dirname(__FILE__)));
             $loader->register();
         }
    
     }
    

    This class initializes route map and Graphity\Loader and can be used for custom initializations.

  6. Make an entry point to your Application like index.php and put it under src/main/webapp:

     define('ROOTDIR', dirname(dirname(dirname(dirname(__FILE__)))));
    
     require_once(ROOTDIR . '/lib/graphity-core/src/main/php/Graphity/Application.php');
     require_once(ROOTDIR . '/src/main/php/My/Application.php');
    
     $app = new My\Application();
     $app->run();
    

    The Graphity\Application::run() method will do the processing for you, executing the whole HTTP workflow from receiving a Graphity\Request to writing out a Graphity\Response. Later you might want to override it with My\Application::run() method to include a try/catch block for Graphity\WebApplicationException handling.

    Both Application superclass and subclass need to be included here to bootstrap the framework.

    This should be the single and only entry point to your Graphity web application.

  7. Fix URL rewriting by adding .htaccess configuration under src/main/webapp:

     RewriteEngine On
     RewriteCond %{REQUEST_FILENAME} !-f
     RewriteCond %{REQUEST_URI} !\.(js|ico|gif|jpg|png|css|swf)$ [NC]
     RewriteRule ^(.*)$ index.php/$1 [L]
    

    Requests with multipart/form-data content type should not be accessed via PHP's $_FILE or similar methods, and instead used with Graphity's MultipartRequest and MultipartParser classes. The following instructions make this possible by setting request content type to multipart/form-data-alternate before it is passed to PHP, and can be placed in vhost.conf:

     <Location />
         SetEnvIf Content-Type ^(multipart/form-data)(.*) NEW_CONTENT_TYPE=multipart/form-data-alternate$2 OLD_CONTENT_TYPE=$1$2
         RequestHeader set Content-Type %{NEW_CONTENT_TYPE}e env=NEW_CONTENT_TYPE
     </Location>
    
  8. Ready? Launch! Open http://localhost/hello?what=world in your browser and you should see Hello world! printed out for you. Naturally the base URI in this example depends on your webserver and/or virtual host configuration.

Documentation

We need to do some work on this... Check out our issues so far.

Papers & presentations

W3C "Linked Enterprise Data Patterns" workshop

License

Graphity core is licensed under Apache License 2.0.

Libraries

Graphity PHP core uses following 3rd party libraries:

  1. Addendum (for annotation parsing)

core-php's People

Contributors

namedgraph avatar saleksandras avatar seporaitis avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

core-php's Issues

Create a QueryBuilder class

Example code interface should be something like:

$query = QueryBuilder::newInstance()->construct($model)->where($whatToSelect)->build();
$model = $repository->query($query);
$query = QueryBuilder::newInstance()->insert($model)->graph($someUri)->build();
$repository->insert($query);

Discussion is needed about how to implement complex queries (queries inside queries, selection form multiple graphs, etc.).

RDFForm

RDFForm to extend MultipartRequest? That probably calls for rewrite of MR methods as well

Implement Graphity\RDFResource

Implement Graphity\RDFResource that would:

  • extend Graphity\Resource
  • implement Rdf\Resource
  • contain Rdf\Model
  • convert DOM from describe() into Model
  • implement getModel() on on top of that

DOM2Model

Implement DOMDocument (RDF/XML) to Rdf\Model parser

From XSLTView to XSLTBuilder

This will allow to get rid of the whole View class hierarchy and write compact code like this:

            fwrite($this->getWriter(),
                XSLTBuilder::fromStylesheetURI(ROOTDIR . "/src/main/webapp/WEB-INF/xsl/RSSView.xsl")->
                document($this->doc)->
                parameter("", "uri", $resource->getURI())->
                parameter("", "base-uri", $resource->getBaseURI())->
                parameter("", "view", Model\HeltNormalt::NS . get_class($this))->
                parameter("", "php-os", php_uname("s"))->
                build()->
                saveXML());

group-sort-triples.xsl

Make group-triples.xsl not only group triples in RDF/XML by subject, but also sort by subject/property/object URI

Rdf\ package needs interfaces

We need interfaces like Rdf\ResourceInterface for classes like Graphity\Exception to implement (since they already are extending another class)

group-triples.xsl

group-triples.xsl produces incorrect RDF/XML (xml:lang becomes rdf:lang?)

method(Foo $foo) vs method(FooInterface $foo)

Find wrong type usages, where class name is used where interface is supposed to be, usually in method parameter type-hinting like here:
public function __construct(Request $request, Router $router)

Update README file

Add information:

  • About Graphity itself
  • How to bootstrap
  • Production usage
  • About authors
  • How to contribute
  • License information

Newlines in Turtle serialization

There seems to be a problem with quotes after newlines:
[2916] 400 Parse error: [line: 7, col: 220] Broken token (newline): @da .
http://local.heltnormalt.dk/rydforsiden/2012/01/04 http://purl.org/dc/elements/1.1/description """Er du i besiddelse af bryster skal disse tjekkes inden 12. marts i år, oplyser sundhedsminister Astrid Krag (SF)
"Efter episoder med farlige brystimplantater i omkringliggende lande, har vi simpelthen valgt at alle danske bryster nu skal gennemgås nøje - også selvom man ikke har implantater - bare for at være på den sikre side""""@da

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.