Restler 3.0


Just deal with your business logic in php, restler will take care of the REST!

Turn your classes and its methods into an easily usable and better Web citizen with Restler.

  • A RESTful API server framework that is written in PHP that aids your mobile / web / desktop applications. A framework, but with a difference – Restler is all here to bend and mend to your needs
  • Writing Server made easy and light. With the light weight, Restler makes writing a server as easy as writing it with just 3 PHP files
  • Restler’s advantage is the simplicity. You can create a PHP class with some functions to expose.  If you know how to write object oriented PHP, then you already know how to use Restler. It’s action speaks for its effectiveness
  • Restler is all about being light and easy. All public methods are automatically mapped to a URL
  • Tailor-made Restler is known for the customization options. You just need to write class and add methods in PHP. It is just there!
  • Restler makes it effective and facilitates your customizing needs. It goes ahead to leverage your designing creativities. A plugin architecture is used
    • for supporting different formats like json, xml, yaml, amf, plist is used, which also means that you can add your own formats easily
    • for supporting different authentication schemes and you can add your own auth plugin
  • While designing your application, RESTful server makes use of the Web’s well known architecture to your benefit
  • You just need to simply declare the function as protected and add an authentication class
  • Most of all, an obvious benefit with Restler is, it is free and open sourced

Supported Platforms

Webserver with Apache / Nginx / IIS / lighthttpd server with PHP 5 support on:
  • Linux
  • Windows
  • Mac platforms


Live Examples

 
All you need to Test Drive Restler is just your browser.  Here you can
  • Learn by the examples
  • Find the role of each PHP file in the making
  • Quick look at the PHP files involved
  • See growing number of examples that show case every aspect of using Restler
Launch Live Examples


Target Users

  • PHP PHP developers
Developers of the following technologies,  who need a RESTful API Server
  • Web ApplicationWeb Application developers
  • FlashAdobe Flash developers
  • AIRAdobe AIR developers
  • MobileMobile developers (Android, BlackBerry, Nokia, IOS etc.,)
  • DevicesDevices & Tablet developers (iPad, Blackberry Playbook, Galaxy Tab, Motorola Xoom etc.,)


Features

 
  • Light weight
  • Flexible
  • Customizable
  • Supports HTTP request methods  GETPOSTPUT, and DELETE
  • Clients can use X-HTTP-Method-Override header
  • Two way format conversion
  • Pluggable Formatters
  • Comes with JSON, XML, YAML, AMF, and PLIST (both XML and Binary) formats
  • Pluggable Authentication schemes
  • Comes with Live Usage Examples
  • URL to Function mapping
  • URL part to Function parameter mapping
  • Supports URLEncoded format for simplified input
  • Query parameters to Function parameter mapping
  • Source code distributed under LGPL

Read More

Bugs & Issues

 
  • Is Restler not working the way it should be?
  • Found a bug?
  • Having issues with Restler?
Please let us know through GitHub issue tracker.
 Report Issues
 

If you are new to GitHub issues, you may take a look at the Introduction Video


Support

Stack Overflow is a language-independent collaboratively edited question and answer site for programmers. Support for Restler is offered by the community and us using Stack Overflow.

 
If your question is,
  • How to do this/that with restler?
  • I got this error, why?
Ask Question
and tag it with restler + php + rest + api
Or else,
  • I got this error & I'm sure it's a bug
  • I have an idea/request
Report Issue
 
 
If you are a Restler Guru and willing to help the Restler community.
Answer Questions
 

78 comments

  1. I did attend a seminar at Flash Camp Chennai, me as a PHP developer eagerly waiting for some useful tool to boost up my development work, i like your concept of ‘Restler’, when it is scheduled to go live

    Thanks,
    Narendran Srinivasan

    • Thanks for your interest. Would you like to beta test Rester? I can send you the files right away!

  2. What’s up with Restler guys?

    I would love to beta test as soon as it’s available.

    Keep us in the loop on your progress :-)

    • Thanks for your support
      I will send you the beta invite :)
      We will keep you posted on the progress
      Regards,
      Arul

  3. Hey,
    I’ve found a bug in the Restler::mapUrlToMethod function :

    In the if($found) section :
    $call->arguments=$p;
    return $call;

    The problem is that $p is not built with order:
    For instance you could have $p[1] = arg1; $p[0] = arg2;
    p = [ 1 => arg1, 0 => arg2 ]

    Hence when call_user_funct_array will be called the array given in param will not be well sorted and the args will be badly given.

    To correct this I just added after the $call->arguments=$p affectation:
    ksort($call->arguments)

    Regards,

    Thomas.

  4. Hi ,
    This is best for my development.
    But if possible how can i integrate authentication with google oauth
    class.
    Regards,
    kalpesh patel

    • I looked at the code and it should be easy to integrate google oAuth php class with Restler. I will get that example up ASAP

    • Hey Great work! I’m most def going to be using this. I’d really like to see your oAuth Example, did you ever get a chance to post this?

    • yes really interested in the oath example here too :) keep up the good work

    • Noted! will make it as quick as possible :)

  5. @Luracast :
    It always breaks when you remove ksort because in my case $p is already build to default
    var_dump($p) =>
    array(2) {
    [1]=>
    NULL
    [2]=>
    NULL
    }
    So 0 (has no default value) is the only one inserting in array when building arguments(so at the end of the array)
    So at the end of the foreach loop $p is set to :
    array(3) {
    [1]=>
    NULL
    [2]=>
    string(7) “testApp”
    [0]=>
    string(9) “access3_2″
    }

    What is good but badly ordered ;)
    For info : I have 3 args, the first one is mandatory, the two others are optional with default to null.

    Thomas

    • Thanks for making it clear, just fixed it now :)

      • An other little issue on the same part :
        Add this :
        else $p[$value] = null;
        after
        if(isset($params[$key]))$p[$value] = $params[$key];
        (mapToUrlMethod)

        Otherwise you will have issue with mandatory param not present;

    • I actually changed the code in generateMap function as shown below in the last fix

      $defaults[$position] = $param->isDefaultValueAvailable() ?
      $param->getDefaultValue() : NULL;

      Which makes sure all the parameters are available in the mapToUrl method

  6. I tried it out. Seems to work very well!

    I’m not a security expert. In the protected API example, you pass a key through the URL. Is this secure? Why don’t you pass it through POST?

    • Hi Stephen, thanks for your feedback.

      You are right! POST is better than passing it directly as a query string in the URL and there are better ways to secure the API. Here the purpose is to show how easy it is to implement your own security mechanism and to keep it simple enough to directly test it in Browser. We will soon add more complex and secure authentication examples

  7. Rune Kaagaard

    How would you return a non-error status code, say 201? Not by doing “throw new RestException(201)”, right?

    • Rune Kaagaard

      Another question. In the CRUD example – real cool example implementation, BTW – the PUT method breaks the restful spec pretty badly by not being idempotent[1]. Is that intentional? I would expect a PUT method to replace all items in the table.

      [1]: http://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol#Idempotent_methods_and_web_applications

      • Rune Kaagaard

        More questions :)

        Have you got any plans for support for versioning in the mimetype?

        What about rfc2616 cache support?

    • Very valid question. Could you help me file an issue using http://bit.ly/RestlerIssues I will release an update that can facilitate that

    • Rune Kaagaard

      Thank you for your reply. Yes could very well file an issue. Which of the questions that I asked are you referring to?

    • You can file issues for the following

      1. Unable to change the HTTP status code to non-error status code like 201
      2. CRUD example incomplete as there are no methods to replace all items in table
      3. Unable to set versioning in the MIME type
      4. There is no rfc2616 cache support

      And add your detailed explanation with the relevant links

      Thanks,
      Arul

    • Fixed it in the release today by modifying the .httaccess to turn off php errors, and minimal example to include some validation

  8. Hi, I was wondering where is the documentation for installation?

    • User guide with installation instruction will be released soon. But you need not wait for that, presentation at http://bit.ly/TakingCareOfTheREST walks you through the process. Also you can download the files and unzip them inside your localhost to try the examples yourself

    • thanks for the reply, I finally installed it on my server. However, I noticed some examples not working which you noted that it maybe due to .htaccess. I don’t have any htaccess on my server root, while my mod_rewrite is already enabled.

    • .htaccess file is available in every example folder but it may be hidden in your OS. Make sure you upload them. All examples should work with the index.php in the URL. You can try that by visiting the examples folder in the browser and test using the links provided (they include index.php in the URL)

    • Thanks! Your right, I forgot that htaccess is hidden. need to ls -alh first to see it.

  9. Just started playing with Restler, and it elminates most of the plumming I don’t want to do when getting a REST API up and running. Nice.

    And then, a small question:

    Any plans for implementing support for replying with a proper WWW-Authenticate Digest header when a 401 is encountered? Seems the the current version is not quite flexible enough to accommodate that. I can always give take shot at a patching it myself, although I have no real experience with HTTP digest authentication. :-)

    Cheers,
    Roger Kind Kristiansen

    • Current version is already capable of doing Digest Authentication. In fact Restler 1.0 includes DigestAuthentication example which you can download from https://github.com/Luracast/Restler/zipball/v1.0.20 only change you need to make to that is change isAuthenticated function to __isAuthenticated to match change in the iAuthenticate interface in 2.0

      Soon I will include more auth examples in 2.0 itself

    • Ahh, sweet. Thanks!

      On a related note: Perhaps some simple way of identifying the resource being accessed inside __isAuthenticated() would be a nice addition, so one could implement several access levels if needed.

    • Yes! but in a de-coupled way! I will post an example in GitHub Issue #3 soon

    • I see this is already in place. Nice! :-)

  10. really nice library! what mysql adapter class do you recommend to use with it?

  11. Hi, I’ve been wondering does this support PostgreSQL? Thanks.

    • It can support all, actually Restler does not interfere with, what you do inside your method. If your method can return PHP array, object or primitive types, Restler is happy serving the data :)

      So just make sure your you return associative array from PostgreSQL using pg_fetch_assoc (http://php.net/manual/en/function.pg-fetch-assoc.php) or similar

  12. Thanks for the quick reply. Glad you mentioned the return of associative array. BTW, I noticed when an Id doesn’t exists the response is false yet the HTTP status code is 200, any chance to change this to 401?

  13. Any chance of having an example on how to interact with CRUD example of Restler? A rest client maybe. Thanks.

  14. Hi,

    I was wondering why set eveything to NULL eg. function get($id=NULL), does it not override the passed parameter? thanks.

  15. i am working with utf-8 sets and got an error on a unicode character (ø) when making .xml file.

    error on line 13 at column 24: Entity ‘oslash’ not defined

    when i changed the line 119 in xmlformat from:
    $value = utf8_encode(htmlentities($value));
    to:
    $value = utf8_encode($value);

    it seems to work fine. is this a bug? and will i get similar error when inputting data?

    thanks for a pretty awesome library :)

    • Yes it is a bug, I need to replace the htmlentities() with a custom function xmlentities() as htmlentities are not recognized by xml unless they are declared in the document

  16. I love this little api, this is the cleaner, lighter and simplest restful api i have ever tried.

    Thank you for sharing this with us.

  17. GREAT Piece of code.

    Could really use an example of a username/api key mapped to a set of arrays. Think that would really give this project it’s extra umfph!

    Loving it so far.

    • Richard Pijnenburg

      You mean a form of authentication?
      I’m working on a nice thing with HTTP auth.
      It’s fairly simple.
      I can make an example if you like.

      Can you explain what kind of functionality you are looking for?

    • I modified the simpleauth.php to support a un and an apikey. Kind of the start to where I need it to go, am going to just filter against a mysql database and ensure the username + apikey combo matches.

      CODE:
      username($_GET['un'])) && ($this->pw($_GET['apikey'])))
      {
      return TRUE;
      } else {
      return FALSE;
      }
      }

      function username($un)
      {
      if($un == “abc”)
      {
      return TRUE;
      } else {
      return FALSE;
      }
      }
      function pw($pw)
      {
      if($pw == “123″)
      {
      return TRUE;
      } else {
      return FALSE;
      }
      }
      }

      /**
      * Example Usage:
      * GET:
      * api/1.0/index.php/tickets/content/80/?un=abc&apikey=123
      **/

    • Also, wanted to show a really nice example of your API being used with a desktop application. This really shows the real life practicality of your software.

      http://screencast.com/t/vYMASNjL1QP

      Great piece of code, easy to use, easy to extend.

  18. Hi,

    I found out that in the response body, whenever a url like string is passed the “/” is displayed as “/”. Ex.

    {
    “id”:1,
    “path”:”http://somewhere.com/”
    }

    Any solutions for this?

  19. Does this supports authentication like header Authentication?

    • Yes it is just a matter of implementation. Say for example the authentication example at http://help.luracast.com/restler/examples/_005_protected_api/readme.html can be modified as

      
      
      <?php
      class SimpleAuth implements iAuthenticate{
          const KEY = 'rEsTlEr2';
          function __isAuthenticated() {
              return isset($_SERVER['HTTP_AUTH_KEY']) && $_SERVER['HTTP_AUTH_KEY']==SimpleAuth::KEY ? TRUE : FALSE;
          }
          function key(){
              return SimpleAuth::KEY;
          }
      }

      Now this server will expect a custom header (AUTH_KEY) to be sent by the client for protected API

    • Thanks for that. But what I’m trying to here is validate the request by checking the Authorization header, am I wrong that HTTP_AUTH_KEY differs from header Authorization. My concern here is that Authorization header isn’t included in array of $_SERVER.

  20. prodrigues

    Hey,

    I’m using restler and i’m trying to implement some authentication by implementing iAuthenticate. The thing is, my authentication code needs to query my database to retrieve the user private key. this private key will always be provided in the url request.

    I wanted to open just one database connection to each request. So i need to pass the db connection variable to my class that implements my authentication and to the other classes that handle all the requests. But i can’t figure it out how can i pass variables to my classes.. Is it possible?If yes how?

    thks

  21. Hi,

    I’m looking at the simple BMI example and I have a question. I have modified the example and moved the bmi.php class file into a “classes” folder and the “restler” folder into a “lib” folder. When doing so and using spl_autoload_register(‘spl_autoload’) in “index.php” I get the following error:

    Fatal error: Uncaught exception ‘Exception’ with message ‘API class BMI is missing.’

    The complete code for index.php is:

    
    
    require_once 'lib/restler/restler.php';
    spl_autoload_register('spl_autoload');

    $r = new Restler();
    $r->setSupportedFormats('JsonFormat', 'XmlFormat');
    $r->addAPIClass('BMI');
    $r->handle();

    What should I modify to make it work without having all the files in the same folder?

    Regards,
    Thomas

    • You can create your own autoload function that will use the folder structure that you define. Look at restler.php for an example or else you can manually include them as shown below

      
      
      require_once 'lib/restler/restler.php';
      require_once 'classes/bmi.php';

      $r = new Restler();
      $r->setSupportedFormats('JsonFormat', 'XmlFormat');
      $r->addAPIClass('BMI');
      $r->handle();
    • Hi,

      thanks for the answer. I developed my own autoload function, now everything works great. Thanks for a great API, it just works and is very flexible.

      //Thomas

  22. Hi there,

    Its a very nice piece of code , that you have created there arul. I wanted to know how to can i use this to to help me create an api that has to authenticate before accesing a resource. Like for example i want to access http://www.xyz.com/folder/impresource.csv

  23. I am wondering if Restler handle validation on JSON request format?

    In example, I have this JSON request:

    { “id” : 1, “party_id” : , “description” : “say it here” }
    The value for party_id should invalid. Any insights? Thanks.

  24. Hi, I think I am missing something. When I setup the service NOT in the root but in a subfolder on the root, e.g. http://www.domain.com/folder/ then I get a

    {
    “error”: {
    “code”: 404,
    “message”: “Not Found”
    }
    }

    • Solved it… I had to add index.php into the url

    • Did you ever get it to work without the index.php? On one site ti works without it and another it doesn’t work…but the files are the same on both sites including the htaccess.

  25. Hi Restlers,
    thank you for your straight forward restful framework. I found a little bug.. it seems for me you can’t make get function for examples getHello in your helloworld .. say.php example. …

    keep up your good work..

    Mirael

    • get is a reserved word in Restler, both getHello and hello will map to /hello only.

      For more information on auto routing read http://help.luracast.com/restler/examples/_006_crud/readme.html

      if you really need ‘get’ as part of your url you can add a php doc comment on top of your method like

      < ?php
      class Say {
          /**
          * @url GET /gethello
          * @url GET /get/hello
          * add as many routes as you want
          */
          function hello($to='world') {
              return "Hello $to!";
          }
      }
      
      
      
  26. I have my following code to get full url path

    
    
    private function getFullCall() {
        $s = empty($_SERVER["HTTPS"]) ? '' : ($_SERVER["HTTPS"] == "on") ? "s" : "";
        $protocol = strleft(strtolower($_SERVER["SERVER_PROTOCOL"]), "/").$s;
        $port = ($_SERVER["SERVER_PORT"] == "80") ? "" : (":".$_SERVER["SERVER_PORT"]);
        return $protocol."://".$_SERVER['SERVER_NAME'].$port.$_SERVER['REQUEST_URI'];
    }
       
    private function strleft($s1, $s2) {
        return substr($s1, 0, strpos($s1, $s2));
    }

    but when i return $this->getFullCall(); it won’t give any result

    how if i want get full url api call.
    in php i can use $_SERVER['REQUEST_URI'].

    but when i use in main class, the $_SERVER['REQUEST_URI'] is don’t give a return

    • It just works for me. With the following test class

      
      
      <?php
      class Say {
          function get() {
              return $this->getFullCall();
          }
          function uri(){
              return $_SERVER ['REQUEST_URI'];
          }
          private function getFullCall() {
              $s = empty ( $_SERVER ["HTTPS"] ) ? '' : ($_SERVER ["HTTPS"] == "on") ? "s" : "";
              $protocol = $this->strleft ( strtolower ( $_SERVER ["SERVER_PROTOCOL"] ), "/" ) . $s;
              $port = ($_SERVER ["SERVER_PORT"] == "80") ? "" : (":" . $_SERVER ["SERVER_PORT"]);
              return $protocol . "://" . $_SERVER ['SERVER_NAME'] . $port . $_SERVER ['REQUEST_URI'];
          }
         
          private function strleft($s1, $s2) {
              return substr ( $s1, 0, strpos ( $s1, $s2 ) );
          }
      }

      When I access

      http://restler2.dev/test/request_details/index.php/say

      I get

      "http://restler2.dev/test/request_details/index.php/say" 

      and

      http://restler2.dev/test/request_details/index.php/say/uri

      gives

      "/test/request_details/index.php/say/uri"

      Your problem should be because of your setup. I will drop you an email and lets take it offline

      Update:-

      I sent the email and realized that you have faked your email id :( if you don’t even trust me with your email id, should I be spending my valuable time providing support?

      Regards,
      Arul

  27. Can you please post some examples of further routing?

    I’m unsure how to best lay out my API…

    I wonder if I should put the routing in the top of the API file, or the index.php?

    I also wonder what the best way to do it would be?

    perhaps an index function in my api file to do some handling? something like:

    
    
    class myapisys .........{
      function index($id = 0, $area = ""){
         if (!$id) $this-_indexfunction(); // accessed /API/myapisys/
         if ($area == "") $this__showid($id); // accessed /API/myapisys/123
         if ($area == "more") $this__showmore($id); // accessed /API/myapisys/123/more
      }

      function __indexfunction(){
         return array("answer"=&gt;"you didnt select any id");
      }
      function __showid($id){
         return array("youchose"=&gt;"details about id $id");
      }
      function __showmore($id){
         return array("youchosemore"=&gt;"some more about id $id");
      }
    }

    This would effectively be a sort of “router”…

    I also wonder how I should lay out “support files”… for example, if I have general helper functions in other classes/libs where should I put them? should I extend some class? etc? Any more complex examples?

    I was able to get some nice auth working already! I can post some examples for ppl if anyone is interested…

  28. some few more items in mind:

    1 – how do I switch output type? like XML or JSON? JSON is the most used standard anyhow, but some ppl might want to use XML occasionally? or other supported types? Would there be a way to implement something like http://site/API/mycall.json or /API/mycall.xml?

    2 – to enable POST and GET on the same functions I can use the comments for routing method, and add a route for GET and a route for POST for the same function? (Do these comments configurations make ithe system any slower? thikning about large scalability)…

    3 – Lowercase and Uppercase…whats the deal? in fucntion names, in file names, and in calls? Everything always lowercase except function names? Cant we use upper/lower to make things more readable?

    4 – any example with file upload? or idea about it?

    5 – is there any way to split the API files into further directories? Like /api/MODULE/FUNCTION I’d have 1 subdirectory for each MODULE, and one PHP for each FUNCTION? is something like this possible? adviseable?

    • 1. http://bit.ly/RestlerLiveExamples should answer that. Look at the multi-format example

      2. Yes. you can use a singe method to accept POST, GET and more

      3. Currently all URIs generated are lowercase only. Will consider the camelCase options

      4. Nothing yet, but should be fairly easy to build one. Will give it a try later

      5. Using PHPDoc comments you can mappings with more tree structure. See the answer for your previous question. Mainly http://bit.ly/sNdf0i

    • Hi Lucarest!

      Thanks for response. great so far!

      About item 5, I’m wondering a bit about how files are included? If I just add them in subdirectories it wont work…when I add the class can I use a / to define subdir?

      $r->addAPIClass(‘MyModule/SubModule1′);
      $r->addAPIClass(‘MyModule/SubModule2′);?

      something of the sort?

      Also, my system doesnt have spl_autoload, I havent been able to install it yet i plan to before production, but can you let me know the effects of this not being enabled? (I commented it).

      About item 3, I realized that in the phpdoc mappings, camelCase does work! so it basically doesnt work just for the main class names…

      Also, I’d like to understand a bit more about the files it includes, and such… I plan to have quite a few modules (classes) and dont want to load them all for all requests… want to load as few as possible to keep things quick…

    • My bad! I was doing it wrong about the XML!

      It seems to be ok, except that I think it is mishandling the accents in XML?

      Do you have any idea how I should go to fix this? I’m not sure about the standard…

      It is giving me error on the XML, for example:
      XML Parsing Error: undefined entity
      Não consigo ver acentos
      ^
      ———|
      Whereas, the JSON shows out UTF-8 properly encoded as required:
      ……”Titulo”: “Nu00e3o consigo ver acentos”,…..

    • ops… it interpreted the xml…

      should be

      <Titulo>N& atilde;o consigo ver acentos</Titulo>
      ————-^

    • Changing line 119 in xmlformat.php to remove htmlentities resovels the issue… however I’m unsure what side-effects it might bring along?

      $value = utf8_encode(htmlentities($value)); // Gives error

      $value = utf8_encode($value); // Works fine apparently

      PS: would it not be better to use simplexml builtin php to just presetn the array as xml? Is this in plans?

      Great work so far! I’ve done some great progress in just 2 days!

Trackbacks/Pingbacks

  1. TX Designs- Amazing Website Development» Page not found - [...] Restler is a multi-protocol and open source framework for exposing PHP classes and methods as a REST API. [...] …
  2. Turn PHP classes in to a RESTful API with Restler | Steve's Ramblings - [...] and add methods in PHP. It is just there!You can view live examples and download the code on the …
  3. » Transform PHP Classes & Methods Into A RESTful API – Restler - IT Mix UP: Active IT Blender - [...] Restler is a multi-protocol and open source framework for exposing PHP classes and methods as a REST API. [...] …
  4. #4 Pulse of Developer Tools with Arul - [...] Last week, I had a chance to chat with Arul, a tech developer who focuses on building developer tools. And …