source: Dev/branches/rest-dojo-ui/server/api.php @ 289

Last change on this file since 289 was 275, checked in by hendrikvanantwerpen, 13 years ago
  • [Server] Added PUT support to API.
  • [Client] Extended questions page with Accordion and list with actions on each row.
File size: 6.8 KB
Line 
1<?php
2
3error_reporting(E_ALL);
4ini_set('display_errors', True);
5
6require_once 'tonic/lib/tonic.php';
7require_once 'classes/master.php';
8
9use Tonic\Request as Request;
10use Tonic\Response as Response;
11use Tonic\ResponseException as ResponseException;
12use Tonic\Resource as Resource;
13
14function set_session_cookie($response, $user) {
15    $response->addHeader('Set-Cookie', 'rft_uid=' . $user->uid . '; Max-Age: 3600; Path=' . $response->request->baseUri);
16}
17
18function restore_session($response) {
19    if (isset($_COOKIE['rft_uid'])) {
20        $user = Auth::restore($_COOKIE['rft_uid']);
21        if ($user) {
22            set_session_cookie($response, $user);
23            return $user;
24        }
25    }
26    throw new ResponseException("No valid session found", Response::UNAUTHORIZED);
27}
28
29function get_clean_uri($request) {
30    return substr($request->uri, strlen($request->baseUri));
31}
32
33function add_default_headers($response) {
34    $response->addHeader('Content-Type', 'application/json');
35    $response->addHeader('Cache-Control', 'no-cache, must-revalidate');
36    $response->addHeader('Expires', 'Sat, 26 Jul 1997 05:00:00 GMT');
37}
38
39/**
40 *  @uri /login
41 */
42class LoginResource extends Resource {
43
44    function post($request) {
45        $response = new Response($request);
46
47        $user = null;
48        if (!empty($request->data)) {
49            $user = Auth::login($request->data['email'], $request->data['password']);
50            if (!$user) {
51                throw new ResponseException("Incorrect email and password", Response::UNAUTHORIZED);
52            }
53            set_session_cookie($response, $user);
54        } else {
55            $user = restore_session($response);
56        }
57        $response->body = $user;
58        return $response;
59    }
60
61}
62
63/**
64 *  @uri /register
65 */
66class RegisterResource extends Resource {
67
68    function post($request) {
69        $response = new Response($request);
70
71        $user = null;
72        if (!empty($request->data)) {
73            $user = Auth::register($request->data['email'], $request->data['password']);
74            set_session_cookie($response, $user);
75        } else {
76            throw new ResponseException("No email and password provided.",Response::BADREQUEST);
77        }
78        $response->body = $user;
79        return $response;
80    }
81
82}
83
84/**
85 * @uri /data/\w+
86 */
87class DataCollectionResource extends Resource {
88
89    function getType($request) {
90        $uri = get_clean_uri($request);
91        $path = explode('/', $uri);
92        $type = $path[2];
93        return $type;
94    }
95
96    function get($request) {
97        $response = new Response($request);
98        restore_session($response);
99
100        $type = $this->getType($request);
101        $objects = $type::get(array());
102
103        $response->body = $objects;
104        return $response;
105    }
106
107    function post($request) {
108        $response = new Response($request);
109        restore_session($response);
110
111        $type = $this->getType($request);
112        $onlyAdd = $request->ifNoneMatch('*');
113        $onlyUpdate = $request->ifMatch('*');
114
115        $object = FALSE;
116        if (isset($request->data->uid)) {
117            $objects = $type::get(array('uid' => $request->data->uid));
118            if (!empty($objects)) {
119                $object = $objects[0];
120            }
121        }
122
123        if (( $onlyUpdate && !$object ) || ( $onlyAdd && $object )) {
124            throw new ResponseException("Update/Create and existing object mismatch", Response::PRECONDITIONFAILED);
125        }
126
127        if (!$object) {
128            $object = new $type(null);
129            $response->code = Response::CREATED;
130        } else {
131            $response->code = Response::OK;
132        }
133        foreach ($request->data as $key => $val) {
134            $object->$key = $val;
135        }
136        if (!$object->save()) {
137            throw new ResponseException("Save failed", Response::INTERNALSERVERERROR);
138        }
139
140        $response->body = $object;
141        return $response;
142    }
143
144    function put($request) {
145        return $this->post($request);
146    }
147   
148}
149
150/**
151 * @uri /data/\w+/\w+
152 */
153class DataObjectResource extends Resource {
154
155    function getTypeAndUid($request) {
156        $uri = get_clean_uri($request);
157        $path = explode('/', $uri);
158        $type = $path[2];
159        $uid = $path[3];
160        return array('type' => $type, 'uid' => $uid);
161    }
162
163    function get($request) {
164        $response = new Response($request);
165        restore_session($response);
166
167        $info = $this->getTypeAndUid($request);
168        $objects = $info['type']::get(array('uid' => $info['uid']));
169        if (empty($objects)) {
170            throw new ResponseException("Object not found", Response::NOTFOUND);
171        }
172
173        $response->body = $objects[0];
174        return $response;
175    }
176
177    function post($request) {
178        $response = new Response($request);
179        restore_session($response);
180
181        $info = $this->getTypeAndUid($request);
182        $onlyAdd = $request->ifNoneMatch('*');
183        $onlyUpdate = $request->ifMatch('*');
184
185        $object = FALSE;
186        $objects = $info['type']::get(array('uid' => $info['uid']));
187        if (!empty($objects)) {
188            $object = $objects[0];
189        }
190
191        if (( $onlyUpdate && !$object ) || ( $onlyAdd && $object )) {
192            throw new ResponseException("Update/Create and existing object mismatch", Response::PRECONDITIONFAILED);
193        }
194
195        if (!$object) {
196            $object = new $info['type']($info->uid);
197            $response->code = Response::CREATED;
198        } else {
199            $response->code = Response::OK;
200        }
201        foreach ($request->data as $key => $val) {
202            $object->$key = $val;
203        }
204        if (!$object->save()) {
205            throw new ResponseException("Save failed", Response::INTERNALSERVERERROR);
206        }
207
208        $response->body = $object;
209        return $response;
210    }
211
212    function put($request) {
213        return $this->post($request);
214    }
215
216    function delete($request) {
217        restore_session(new Response($request));
218        throw new ReponseException("Delete not implemented", Response::METHODNOTALLOWED);
219    }
220
221}
222
223$request = new Request();
224$path = $request->uri;
225$idx = strrpos($path, 'api.php');
226if ($idx !== FALSE) {
227    $baseUri = substr($path, 0, $idx + 7);
228    $request->baseUri = $baseUri;
229}
230$request->data = Marshaller::unmarshall(json_decode($request->data));
231try {
232    $resource = $request->loadResource();
233    $response = $resource->exec($request);
234} catch (ResponseException $e) {
235    $response = $e->response($request);
236    $response->body = array('errorMsg' => $response->body);
237} catch (Exception $e) {
238    $response = new Response($request);
239    $response->code = Response::INTERNALSERVERERROR;
240    $response->body = array('errorMsg' => "Unhandled exception: " . $e);
241}
242add_default_headers($response);
243$response->body = json_encode(Marshaller::marshall($response->body));
244$response->output();
245
246?>
Note: See TracBrowser for help on using the repository browser.