bitbucket -> github

This commit is contained in:
Gnieark 2017-05-05 21:46:14 +02:00
parent 954195b57f
commit 803b36ed3d
21 changed files with 953 additions and 519 deletions

View File

@ -2,12 +2,9 @@
Plugin dotclear ouvrant une API REST/JSON Plugin dotclear ouvrant une API REST/JSON
Interface d'administration commencée C'est en cours de développement et est loin d'être fini.
Dégrossi les specs / documentation de l'API (swagger).
Elles seront modifiées au fur et à mesure du développement de l'API.
Pour le moment les specifications Swagger sont basées sur la structure de la base de données.
A terme, elles seront basées plus sur les fonctions de dotclear.
PS: Des que l'architecture de ce plugin sera plus développée, je poursuivrai son dev sur Bitbucket. Les spécifications swagger seront modifiées au fur et à mesure du développement de l'API.
Pour le moment elles sont basées sur la structure de la base de données et ne sont pas exhaustives.
A terme, elles seront basées plus sur les fonctions de dotclear.

View File

@ -3,7 +3,7 @@
if (!defined('DC_CONTEXT_ADMIN')) { return; } if (!defined('DC_CONTEXT_ADMIN')) { return; }
$_menu['Blog']->addItem(__('Rest API'), $_menu['Blog']->addItem(__('Rest API'),
'plugin.php?p=rest', 'plugin.php?p=rest',
urldecode(dcPage::getPF('rest/rest_api_256x256.png')), urldecode(dcPage::getPF('rest/rest_api_256x256.png')),
preg_match('/plugin.php\?p=rest(&.*)?$/',$_SERVER['REQUEST_URI']), preg_match('/plugin.php\?p=rest(&.*)?$/',$_SERVER['REQUEST_URI']),
$core->auth->check('contentadmin',$core->blog->id)); $core->auth->check('contentadmin',$core->blog->id));

View File

@ -12,12 +12,12 @@
if (!defined('DC_RC_PATH')) { return; } if (!defined('DC_RC_PATH')) { return; }
$this->registerModule( $this->registerModule(
/* Name */ "rest", /* Name */ "rest",
/* Description*/ "A JSON/REST API for Dotclear", /* Description*/ "A JSON/REST API for Dotclear",
/* Author */ "Gnieark (hope some others contributors)", /* Author */ "Gnieark (hope some others contributors)",
/* Version */ '0.0.1', /* Version */ '0.0.1',
array( array(
'permissions' => 'usage,contentadmin', 'permissions' => 'usage,contentadmin',
'type' => 'plugin', 'type' => 'plugin',
) )
); );

View File

@ -5,4 +5,6 @@ $__autoload['ApiKey'] = dirname(__FILE__).'/inc/class.rest.key.php';
$__autoload['restAuth'] = dirname(__FILE__).'/inc/class.rest.auth.php'; $__autoload['restAuth'] = dirname(__FILE__).'/inc/class.rest.auth.php';
$__autoload['RestQuery'] = dirname(__FILE__).'/inc/class.rest.query.php'; $__autoload['RestQuery'] = dirname(__FILE__).'/inc/class.rest.query.php';
$__autoload['RestQueryGetBlogs'] = dirname(__FILE__).'/inc/class.rest.query.get.blogs.php'; $__autoload['RestQueryGetBlogs'] = dirname(__FILE__).'/inc/class.rest.query.get.blogs.php';
$__autoload['RestQueryGetSpecs'] = dirname(__FILE__).'/inc/class.rest.query.get.specs.php'; $__autoload['RestQueryGetBlog'] = dirname(__FILE__).'/inc/class.rest.query.get.blog.php';
$__autoload['RestQueryGetSpecs'] = dirname(__FILE__).'/inc/class.rest.query.get.specs.php';
$__autoload['RestQueryPostBlogs'] = dirname(__FILE__).'/inc/class.rest.query.post.blogs.php';

View File

@ -5,110 +5,116 @@ $core->url->register('rest','rest','^rest(?:/(.*))?$',array('rest','getResponse'
class rest extends dcUrlHandlers class rest extends dcUrlHandlers
{ {
/** /**
* Create the "good" RestQuery instance * Create the "good" RestQuery instance
* Input: $httpMethod: String (POST/GET/PATCH etc...) * Input: $httpMethod: String (POST/GET/PATCH etc...)
* $args Url arguments * $args Url arguments
* $user dcAuth object * $user dcAuth object
* $body Body of the input query. String * $body Body of the input query. String
* Output: object RestQuery * Output: object RestQuery
*/ */
private function restFactoryQuery($httpMethod,$args,$user,$body){ private function restFactoryQuery($httpMethod,$args,$body){
//définir la methode API (pas HTML) appelée
//définir la methode API (pas HTML) appelée switch($httpMethod){
switch($httpMethod){ case "GET":
case "GET": if($args == 'blogs'){
if($args == 'blogs'){ $queryObj = new RestQueryGetBlogs();
$queryObj = new RestQueryGetBlogs($user); break;
break; }elseif($args == 'specs'){
}elseif($args == 'specs'){ $queryObj = new RestQueryGetSpecs();
$queryObj = new RestQueryGetSpecs($user); break;
break; }elseif(preg_match('^blogs/(.+)$', $args )){
} $queryObj = new RestQueryGetBlog($args);
break; break;
case "POST":
}
break;
case "PUT": ///blogs/{blog-id}
break;
break;
case "PATCH": case "POST":
if($args == 'blogs'){
break; $queryObj = new RestQueryPostBlogs($body);
}
case "DELETE":
break;
break; case "PUT":
default:
$this->response_code = RestQuery::get_full_code_header(400); break;
$this->response_message = array(
"error" => "Unrecoknized method", case "PATCH":
"code" => 400
); break;
return;
break; case "DELETE":
}
break;
return $queryObj; default:
$queryObj = new RestQuery();
} break;
}
return $queryObj;
}
public static function getResponse($args) public static function getResponse($args)
{ {
global $core; global $core;
$active = (boolean)$core->blog->settings->rest->rest_active; $active = (boolean)$core->blog->settings->rest->rest_active;
if (!$active){ if (!$active){
self::p404(); self::p404();
return; return;
} }
error_log($args);
//coors headers
//exception pour la documentation if($core->blog->settings->rest->rest_send_cors_headers){
if($args == "documentation"){ header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST, PATCH, PUT, DELETE');
header('Access-Control-Allow-Headers: Content-Type, authorization, x_dc_key');
}
//exception pour la documentation
if($args == "documentation"){
include (dirname(__FILE__).'/documentation/swagger-ui-dist/index.php'); include (dirname(__FILE__).'/documentation/swagger-ui-dist/index.php');
return; return;
} }
header('Content-Type: application/json');
//coors headers
if($core->blog->settings->rest->rest_send_cors_headers){ //user authentification (facultative at this step)
header('Access-Control-Allow-Origin: *'); $apiKey = rest::get_api_key_sended();
header('Access-Control-Allow-Methods: GET, POST, PATCH, PUT, DELETE'); //$user = false;
header('Access-Control-Allow-Headers: Content-Type, authorization, x_dc_key'); if($apiKey){
} $core->auth = new restAuth($core);
header('Content-Type: application/json'); if($core->auth->checkUser('','',$apiKey) === false){
header(RestQuery::get_full_code_header(403));
//user authentification (facultative at this step) echo json_encode(array(
$apiKey = rest::get_api_key_sended(); "error" => "Wrong API Key",
$user = false; "code" => 403
if($apiKey){ ));
$user = new restAuth($core); return;
if($user->checkUser('','',$apiKey) === false){ }
header(RestQuery::get_full_code_header(403)); }else{
echo json_encode(array( $core->auth = false;
"error" => "Wrong API Key", }
"code" => 403 $r = rest::restFactoryQuery($_SERVER['REQUEST_METHOD'],$args,file_get_contents('php://input'));
)); header($r->response_code);
return; echo json_encode($r->response_message);
}
} }
$r = rest::restFactoryQuery($_SERVER['REQUEST_METHOD'],$args,$user,file_get_contents('php://input')); private function get_api_key_sended()
header($r->response_code); {
echo json_encode($r->response_message); //to do: test it on nginx
$headers = apache_request_headers();
} if(isset($headers['x_dc_key'])){
return $headers['x_dc_key'];
private function get_api_key_sended() }else{
{ return false;
//to do: test it on nginx }
$headers = apache_request_headers(); }
if(isset($headers['x_dc_key'])){
return $headers['x_dc_key']; }
}else{
return false;
}
}
}

View File

@ -2,18 +2,27 @@ swagger: '2.0'
info: info:
title: Dotclear API title: Dotclear API
description: Manage your(s) blogs with this API description: Manage your(s) blogs with this API
version: "0.0.1" version: 0.0.1
# the domain of the service
host: dotclear.localhost host: dotclear.localhost
# array of all schemes that your API supports
schemes: schemes:
- http - http
# will be prefixed to all paths basePath: /dotclear/index.php?rest
# (part of plugin url)
basePath: /dotclear/index.php?rest/
produces: produces:
- application/json - application/json
paths: paths:
/specs:
get:
summary: Get this API SWAGGER documentation
responses:
'200':
description: swagger.json
schema:
title: doc
type: string
default:
description: Unexpected error
schema:
$ref: '#/definitions/Error'
/blogs: /blogs:
get: get:
summary: Get list of availables blogs summary: Get list of availables blogs
@ -23,13 +32,12 @@ paths:
required: false required: false
type: string type: string
responses: responses:
200: '200':
description: array serving blogs properties description: array serving blogs properties
schema: schema:
title: blogs
type: array type: array
items: items:
$ref: '#/definitions/blog' type: string
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
@ -48,7 +56,7 @@ paths:
$ref: '#/definitions/blog' $ref: '#/definitions/blog'
required: true required: true
responses: responses:
200: '200':
description: array containing the new blog's identifiant description: array containing the new blog's identifiant
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
@ -56,7 +64,7 @@ paths:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
/blogs/{blog-id}: '/blogs/{blog-id}':
get: get:
summary: Get a blog poperties summary: Get a blog poperties
parameters: parameters:
@ -69,11 +77,13 @@ paths:
type: string type: string
required: true required: true
responses: responses:
200: '200':
description: array containing blog properties. This list of attributes is not exhaustive. description: >-
array containing blog properties. This list of attributes is not
exhaustive.
schema: schema:
$ref: '#/definitions/blogProperties' $ref: '#/definitions/blogProperties'
404: '404':
description: this blog id does not exists description: this blog id does not exists
default: default:
description: Unexpected error description: Unexpected error
@ -97,18 +107,20 @@ paths:
schema: schema:
$ref: '#/definitions/blogProperties' $ref: '#/definitions/blogProperties'
responses: responses:
200: '200':
description: array containing the edited blog's identifiant description: array containing the edited blog's identifiant
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this blog id does not exists description: this blog id does not exists
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
put: put:
summary: Overwrite blog Properties (if a parameter is not set, his value will be erased by de default value) summary: >-
Overwrite blog Properties (if a parameter is not set, his value will be
erased by de default value)
parameters: parameters:
- name: x_dc_key - name: x_dc_key
in: header in: header
@ -125,17 +137,16 @@ paths:
schema: schema:
$ref: '#/definitions/blogProperties' $ref: '#/definitions/blogProperties'
responses: responses:
200: '200':
description: array containing the edited blog's identifiant description: array containing the edited blog's identifiant
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this blog id does not exists description: this blog id does not exists
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
delete: delete:
summary: Delete this blog summary: Delete this blog
parameters: parameters:
@ -148,18 +159,17 @@ paths:
type: string type: string
required: true required: true
responses: responses:
200: '200':
description: array containing the deleted blog's identifiant description: array containing the deleted blog's identifiant
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this blog id does not exists description: this blog id does not exists
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
'/{blog-id}/posts':
/{blog-id}/posts:
get: get:
summary: Get list of posts summary: Get list of posts
parameters: parameters:
@ -184,16 +194,17 @@ paths:
items: items:
type: string type: string
required: false required: false
description: Fields you want to get. If unset, fields are post_id, post_url, post_status, post_title, post_date description: >-
Fields you want to get. If unset, fields are post_id, post_url,
post_status, post_title, post_date
responses: responses:
200: '200':
description: list of posts description: list of posts
schema: schema:
title: posts title: posts
type: array type: array
items: items:
$ref: '#/definitions/dc_post' $ref: '#/definitions/dc_post'
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
@ -211,11 +222,13 @@ paths:
required: true required: true
- name: properties - name: properties
in: body in: body
description: Some non required fields you don't define will be set (default value) by the API description: >-
Some non required fields you don't define will be set (default
value) by the API
schema: schema:
$ref: '#/definitions/new_dc_post' $ref: '#/definitions/new_dc_post'
responses: responses:
200: '200':
description: Id of newly created post description: Id of newly created post
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
@ -223,8 +236,7 @@ paths:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
'/{blog-id}/posts/{post-id}':
/{blog-id}/posts/{post-id}:
get: get:
summary: Get a post entry summary: Get a post entry
parameters: parameters:
@ -253,11 +265,11 @@ paths:
items: items:
type: string type: string
required: false required: false
description: Fields you want to get. If unset, all available fields will be get. description: 'Fields you want to get. If unset, all available fields will be get.'
responses: responses:
200: '200':
description: The post values description: The post values
schema: schema:
$ref: '#/definitions/dc_post' $ref: '#/definitions/dc_post'
default: default:
description: Unexpected error description: Unexpected error
@ -283,16 +295,16 @@ paths:
schema: schema:
$ref: '#/definitions/dc_post' $ref: '#/definitions/dc_post'
responses: responses:
200: '200':
description: array containing the updated post's id description: array containing the updated post's id
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this post does not exists description: this post does not exists
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
put: put:
summary: Update full blog properties. Unsetted parameters will be erased summary: Update full blog properties. Unsetted parameters will be erased
parameters: parameters:
@ -313,11 +325,11 @@ paths:
schema: schema:
$ref: '#/definitions/new_dc_post' $ref: '#/definitions/new_dc_post'
responses: responses:
200: '200':
description: array containing the updated post's id description: array containing the updated post's id
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this post does not exists description: this post does not exists
default: default:
description: Unexpected error description: Unexpected error
@ -339,17 +351,17 @@ paths:
type: string type: string
required: true required: true
responses: responses:
200: '200':
description: array containing the deleted post's id description: array containing the deleted post's id
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
404: '404':
description: this post does not exists description: this post does not exists
default: default:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
/{blog-id}/categories: '/{blog-id}/categories':
get: get:
summary: Get list of available categories summary: Get list of available categories
parameters: parameters:
@ -362,7 +374,7 @@ paths:
type: string type: string
required: true required: true
responses: responses:
200: '200':
description: array containing the categories properties description: array containing the categories properties
schema: schema:
title: categories title: categories
@ -388,9 +400,8 @@ paths:
in: body in: body
schema: schema:
$ref: '#/definitions/new_category' $ref: '#/definitions/new_category'
responses: responses:
200: '200':
description: array containing the created category id description: array containing the created category id
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
@ -398,8 +409,7 @@ paths:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
'/{blog-id}/categories/{cat-id}':
/{blog-id}/categories/{cat-id}:
get: get:
summary: get one category properties summary: get one category properties
parameters: parameters:
@ -416,7 +426,7 @@ paths:
type: string type: string
required: true required: true
responses: responses:
200: '200':
description: array containing the created category properties description: array containing the created category properties
schema: schema:
$ref: '#/definitions/category' $ref: '#/definitions/category'
@ -440,7 +450,7 @@ paths:
schema: schema:
$ref: '#/definitions/category' $ref: '#/definitions/category'
responses: responses:
200: '200':
description: array containing the modified category id description: array containing the modified category id
schema: schema:
$ref: '#/definitions/Ids' $ref: '#/definitions/Ids'
@ -448,13 +458,6 @@ paths:
description: Unexpected error description: Unexpected error
schema: schema:
$ref: '#/definitions/Error' $ref: '#/definitions/Error'
definitions: definitions:
blog: blog:
type: object type: object
@ -469,14 +472,12 @@ definitions:
type: string type: string
blog_url: blog_url:
type: string type: string
description: blog_desc:
type: string type: string
blog_status: lang:
type: string
blog_timezone:
type: string type: string
enum:
- En ligne
- Hors ligne
- Retiré
url_scan: url_scan:
type: string type: string
enum: enum:
@ -497,7 +498,7 @@ definitions:
type: string type: string
url: url:
type: string type: string
description: description:
type: string type: string
author: author:
type: string type: string
@ -799,7 +800,6 @@ definitions:
type: integer type: integer
temporary: temporary:
type: boolean type: boolean
Error: Error:
type: object type: object
properties: properties:
@ -809,4 +809,4 @@ definitions:
message: message:
type: string type: string
fields: fields:
type: string type: string

View File

@ -0,0 +1,93 @@
<!-- HTML for static distribution bundle build -->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Swagger UI</title>
<link href="https://fonts.googleapis.com/css?family=Open+Sans:400,700|Source+Code+Pro:300,600|Titillium+Web:400,600,700" rel="stylesheet">
<link rel="stylesheet" type="text/css" href="./swagger-ui.css" >
<link rel="icon" type="image/png" href="./favicon-32x32.png" sizes="32x32" />
<link rel="icon" type="image/png" href="./favicon-16x16.png" sizes="16x16" />
<style>
html
{
box-sizing: border-box;
overflow: -moz-scrollbars-vertical;
overflow-y: scroll;
}
*,
*:before,
*:after
{
box-sizing: inherit;
}
body {
margin:0;
background: #fafafa;
}
</style>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" style="position:absolute;width:0;height:0">
<defs>
<symbol viewBox="0 0 20 20" id="unlocked">
<path d="M15.8 8H14V5.6C14 2.703 12.665 1 10 1 7.334 1 6 2.703 6 5.6V6h2v-.801C8 3.754 8.797 3 10 3c1.203 0 2 .754 2 2.199V8H4c-.553 0-1 .646-1 1.199V17c0 .549.428 1.139.951 1.307l1.197.387C5.672 18.861 6.55 19 7.1 19h5.8c.549 0 1.428-.139 1.951-.307l1.196-.387c.524-.167.953-.757.953-1.306V9.199C17 8.646 16.352 8 15.8 8z"></path>
</symbol>
<symbol viewBox="0 0 20 20" id="locked">
<path d="M15.8 8H14V5.6C14 2.703 12.665 1 10 1 7.334 1 6 2.703 6 5.6V8H4c-.553 0-1 .646-1 1.199V17c0 .549.428 1.139.951 1.307l1.197.387C5.672 18.861 6.55 19 7.1 19h5.8c.549 0 1.428-.139 1.951-.307l1.196-.387c.524-.167.953-.757.953-1.306V9.199C17 8.646 16.352 8 15.8 8zM12 8H8V5.199C8 3.754 8.797 3 10 3c1.203 0 2 .754 2 2.199V8z"/>
</symbol>
<symbol viewBox="0 0 20 20" id="close">
<path d="M14.348 14.849c-.469.469-1.229.469-1.697 0L10 11.819l-2.651 3.029c-.469.469-1.229.469-1.697 0-.469-.469-.469-1.229 0-1.697l2.758-3.15-2.759-3.152c-.469-.469-.469-1.228 0-1.697.469-.469 1.228-.469 1.697 0L10 8.183l2.651-3.031c.469-.469 1.228-.469 1.697 0 .469.469.469 1.229 0 1.697l-2.758 3.152 2.758 3.15c.469.469.469 1.229 0 1.698z"/>
</symbol>
<symbol viewBox="0 0 20 20" id="large-arrow">
<path d="M13.25 10L6.109 2.58c-.268-.27-.268-.707 0-.979.268-.27.701-.27.969 0l7.83 7.908c.268.271.268.709 0 .979l-7.83 7.908c-.268.271-.701.27-.969 0-.268-.269-.268-.707 0-.979L13.25 10z"/>
</symbol>
<symbol viewBox="0 0 20 20" id="large-arrow-down">
<path d="M17.418 6.109c.272-.268.709-.268.979 0s.271.701 0 .969l-7.908 7.83c-.27.268-.707.268-.979 0l-7.908-7.83c-.27-.268-.27-.701 0-.969.271-.268.709-.268.979 0L10 13.25l7.418-7.141z"/>
</symbol>
<symbol viewBox="0 0 24 24" id="jump-to">
<path d="M19 7v4H5.83l3.58-3.59L8 6l-6 6 6 6 1.41-1.41L5.83 13H21V7z"/>
</symbol>
<symbol viewBox="0 0 24 24" id="expand">
<path d="M10 18h4v-2h-4v2zM3 6v2h18V6H3zm3 7h12v-2H6v2z"/>
</symbol>
</defs>
</svg>
<div id="swagger-ui"></div>
<script src="./swagger-ui-bundle.js"> </script>
<script src="./swagger-ui-standalone-preset.js"> </script>
<script>
window.onload = function() {
// Build a system
const ui = SwaggerUIBundle({
url: "http://dotclear.localhost/dotclear/index.php?rest/specs",
dom_id: '#swagger-ui',
presets: [
SwaggerUIBundle.presets.apis,
SwaggerUIStandalonePreset
],
plugins: [
SwaggerUIBundle.plugins.DownloadUrl
],
layout: "StandaloneLayout"
})
window.ui = ui
}
</script>
</body>
</html>

View File

@ -1,4 +1,3 @@
<!-- HTML for static distribution bundle build -->
<!DOCTYPE html> <!DOCTYPE html>
<html lang="en"> <html lang="en">
<head> <head>

File diff suppressed because one or more lines are too long

View File

@ -1 +1 @@
{"version":3,"file":"swagger-ui-bundle.js","sources":["webpack:///swagger-ui-bundle.js"],"mappings":"AAAA;AAu/FA;AA6+FA;;;;;;;;;;;;;;;;;;;;;;;;;;AAmTA;;;;;;AAoIA;AAi7FA;AAmtCA;AAi0IA;AA2pJA;AA+uFA;AA2rGA;AAgiFA;AA0rFA;AAk9CA;AA2hDA;AA4rCA;AAi6EA;;;;;AA2gCA;AA02JA;;;;;;;;;;;;;;AAuyEA;AA4mIA;AAquJA;AAwsHA;AA2mGA;AAiiEA;AAq4DA;AA+2DA;AAqlBA;;;;;;AAilFA;AAs1FA;;;;;AAy3CA;AA2qFA;AAw2CA;AAwkCA;AAs/CA;AA4kFA;AAy1FA;;;;;;;;;AAm5CA;AA2zIA;AAk4DA;AAolDA","sourceRoot":""} {"version":3,"file":"swagger-ui-bundle.js","sources":["webpack:///swagger-ui-bundle.js"],"mappings":"AAAA;AAu/FA;AA6+FA;;;;;;;;;;;;;;;;;;;;;;;;;;AAoTA;;;;;;AAoIA;AAi7FA;AAmtCA;AAi0IA;AA2pJA;AA+uFA;AA2rGA;AAgiFA;AA0rFA;AAk9CA;AA2hDA;AA4rCA;AAi6EA;;;;;AA2gCA;AA02JA;;;;;;;;;;;;;;AAuyEA;AA4mIA;AAquJA;AAwsHA;AA2mGA;AAiiEA;AAq4DA;AA+2DA;AAqlBA;;;;;;AAilFA;AAs1FA;;;;;AAy3CA;AA2qFA;AAw2CA;AAwkCA;AAs/CA;AA4kFA;AAy1FA;;;;;;;;;AAm5CA;AA2zIA;AAk4DA;AAolDA","sourceRoot":""}

File diff suppressed because one or more lines are too long

View File

@ -1 +1 @@
{"version":3,"file":"swagger-ui.js","sources":["webpack:///swagger-ui.js"],"mappings":"AAAA;;;;;;AAwxCA;AAoyHA;AAuxHA;AAy4FA;AA2sCA;AAmgCA;AA0iCA;AA+3BA","sourceRoot":""} {"version":3,"file":"swagger-ui.js","sources":["webpack:///swagger-ui.js"],"mappings":"AAAA;;;;;;AAyxCA;AAoyHA;AAuxHA;AAy4FA;AA2sCA;AAmgCA;AA0iCA;AA+3BA","sourceRoot":""}

View File

@ -9,11 +9,31 @@
"schemes": [ "schemes": [
"http" "http"
], ],
"basePath": "/dotclear/index.php?rest/", "basePath": "/dotclear/index.php?rest",
"produces": [ "produces": [
"application/json" "application/json"
], ],
"paths": { "paths": {
"/specs": {
"get": {
"summary": "Get this API SWAGGER documentation",
"responses": {
"200": {
"description": "swagger.json",
"schema": {
"title": "doc",
"type": "string"
}
},
"default": {
"description": "Unexpected error",
"schema": {
"$ref": "#/definitions/Error"
}
}
}
}
},
"/blogs": { "/blogs": {
"get": { "get": {
"summary": "Get list of availables blogs", "summary": "Get list of availables blogs",
@ -29,10 +49,9 @@
"200": { "200": {
"description": "array serving blogs properties", "description": "array serving blogs properties",
"schema": { "schema": {
"title": "blogs",
"type": "array", "type": "array",
"items": { "items": {
"$ref": "#/definitions/blog" "type": "string"
} }
} }
}, },
@ -695,16 +714,14 @@
"blog_url": { "blog_url": {
"type": "string" "type": "string"
}, },
"description": { "blog_desc": {
"type": "string" "type": "string"
}, },
"blog_status": { "lang": {
"type": "string", "type": "string"
"enum": [ },
"En ligne", "blog_timezone": {
"Hors ligne", "type": "string"
"Retiré"
]
}, },
"url_scan": { "url_scan": {
"type": "string", "type": "string",

View File

@ -2,84 +2,122 @@
class restAuth extends dcAuth class restAuth extends dcAuth
{ {
# L'utilisateur n'a pas le droit de changer son mot de passe # L'utilisateur n'a pas le droit de changer son mot de passe
protected $allow_pass_change = false; protected $allow_pass_change = false;
/** /**
* Méthode de vérification de la clef d'api_key * Méthode de vérification de la clef d'api_key
* Remplace la méthode chekUser (id: password) * Remplace la méthode chekUser (id: password)
* Only use $user_key (all others parameters are for compatibility with the parent function) * Only use $user_key (all others parameters are for compatibility with the parent function)
* input: $user_key STRING * input: $user_key STRING
* output: boolean * output: boolean
*/ */
public function checkUser($user_id, $pwd = NULL, $user_key = NULL, $check_blog = true) public function checkUser($user_id, $pwd = NULL, $user_key = NULL, $check_blog = true)
{ {
global $core; global $core;
//Check for the user api key $hashedKey = $core->auth->crypt($user_key);
$sqlStr = " SELECT setting_id //Check for the user api key
FROM dc_setting $sqlStr = " SELECT setting_id
WHERE setting_ns='rest' FROM dc_setting
AND setting_id LIKE 'rest_key_%' WHERE setting_ns='rest'
AND setting_value = md5('".$core->con->escape($user_key)."');"; AND setting_id LIKE 'rest_key_%'
AND setting_value = '".$core->con->escape($hashedKey)."';";
try {
$rs = $core->con->select($sqlStr); try {
} catch (Exception $e) { $rs = $core->con->select($sqlStr);
$err = $e->getMessage(); } catch (Exception $e) {
return false; $err = $e->getMessage();
} return false;
}
if ($rs->isEmpty()) { if ($rs->isEmpty()) {
sleep(rand(2,5)); sleep(rand(2,5));
return false; return false;
} }
//get the user ID from the previous query //get the user ID from the previous query
$userId = explode("_", $rs->setting_id)[2]; $userId = explode("_", $rs->setting_id)[2];
//get USER infos //get USER infos
$strReq = 'SELECT user_id, user_super, user_pwd, user_change_pwd, '. $strReq = 'SELECT user_id, user_super, user_pwd, user_change_pwd, '.
'user_name, user_firstname, user_displayname, user_email, '. 'user_name, user_firstname, user_displayname, user_email, '.
'user_url, user_default_blog, user_options, '. 'user_url, user_default_blog, user_options, '.
'user_lang, user_tz, user_post_status, user_creadt, user_upddt '. 'user_lang, user_tz, user_post_status, user_creadt, user_upddt '.
'FROM '.$this->con->escapeSystem($this->user_table).' '. 'FROM '.$core->con->escapeSystem($this->user_table).' '.
"WHERE user_id = '".$this->con->escape($userId)."'"; "WHERE user_id = '".$core->con->escape($userId)."'";
try { try {
$rs = $core->con->select($strReq); $rs = $core->con->select($strReq);
} catch (Exception $e) { } catch (Exception $e) {
$err = $e->getMessage(); $err = $e->getMessage();
return false; return false;
} }
if ($rs->isEmpty()) { if ($rs->isEmpty()) {
sleep(rand(2,5)); sleep(rand(2,5));
return false; return false;
} }
$this->user_id = $rs->user_id; $this->user_id = $rs->user_id;
$this->user_change_pwd = (boolean) $rs->user_change_pwd; $this->user_change_pwd = (boolean) $rs->user_change_pwd;
$this->user_admin = (boolean) $rs->user_super; $this->user_admin = (boolean) $rs->user_super;
$this->user_info['user_pwd'] = $rs->user_pwd; $this->user_info['user_pwd'] = $rs->user_pwd;
$this->user_info['user_name'] = $rs->user_name; $this->user_info['user_name'] = $rs->user_name;
$this->user_info['user_firstname'] = $rs->user_firstname; $this->user_info['user_firstname'] = $rs->user_firstname;
$this->user_info['user_displayname'] = $rs->user_displayname; $this->user_info['user_displayname'] = $rs->user_displayname;
$this->user_info['user_email'] = $rs->user_email; $this->user_info['user_email'] = $rs->user_email;
$this->user_info['user_url'] = $rs->user_url; $this->user_info['user_url'] = $rs->user_url;
$this->user_info['user_default_blog'] = $rs->user_default_blog; $this->user_info['user_default_blog'] = $rs->user_default_blog;
$this->user_info['user_lang'] = $rs->user_lang; $this->user_info['user_lang'] = $rs->user_lang;
$this->user_info['user_tz'] = $rs->user_tz; $this->user_info['user_tz'] = $rs->user_tz;
$this->user_info['user_post_status'] = $rs->user_post_status; $this->user_info['user_post_status'] = $rs->user_post_status;
$this->user_info['user_creadt'] = $rs->user_creadt; $this->user_info['user_creadt'] = $rs->user_creadt;
$this->user_info['user_upddt'] = $rs->user_upddt; $this->user_info['user_upddt'] = $rs->user_upddt;
$this->user_info['user_cn'] = dcUtils::getUserCN($rs->user_id, $rs->user_name, $this->user_info['user_cn'] = dcUtils::getUserCN($rs->user_id, $rs->user_name,
$rs->user_firstname, $rs->user_displayname); $rs->user_firstname, $rs->user_displayname);
//$this->user_options = array_merge($this->core->userDefaults(),$rs->options());
$this->user_prefs = new dcPrefs($this->core,$this->user_id); //$this->user_options = array_merge($this->core->userDefaults(),$rs->options());
return true; $this->user_prefs = new dcPrefs($this->core,$this->user_id);
} return true;
}
//return user permission for all blogs
//[blog_id] => permission
public function getAllPermissions()
{
global $core;
//conserve the value
static $blogs = false;
if($blogs !== false){
return $blogs;
}
if ($this->user_admin) { //user_admin == super admin
$strReq = 'SELECT blog_id '.
'from '.$this->blog_table;
$rs = $core->con->select($strReq);
while ($rs->fetch())
{
$blogs[$rs->blog_id] = 'admin';
}
return $blogs;
}
$strReq = 'SELECT blog_id, permissions '.
'FROM '.$this->perm_table.' '.
"WHERE user_id = '".$this->con->escape($this->user_id)."' ".
"AND (permissions LIKE '%|usage|%' OR permissions LIKE '%|admin|%' OR permissions LIKE '%|contentadmin|%') ";
$rs = $this->con->select($strReq);
while ($rs->fetch()){
$blogs[$rs->blog_id] = $this->parsePermissions($rs->permissions);
}
return $blogs;
}
} }

View File

@ -1,91 +1,90 @@
<?php <?php
class ApiKey class ApiKey
{ {
public $key; public $key;
public function __construct(){ public function __construct(){
$this->key = ''; $this->key = '';
} }
public function new_key($dcUserId) public function new_key($dcUserId)
{ {
$this->key = $this->rand_str(); $this->key = $this->rand_str();
$this -> put_dc_setting_user_key($dcUserId); $this -> put_dc_setting_user_key($dcUserId);
return $this->key; return $this->key;
} }
public function set_key($key) public function set_key($key)
{ {
$this->key = $key; $this->key = $key;
} }
public function get_dc_admin_form($dcUserId) public function get_dc_admin_form($dcUserId)
{ {
global $core; global $core;
//tester si une clef d'API a été générée //tester si une clef d'API a été générée
if($this->dc_is_key_setting_set($dcUserId)){
if($this->dc_is_key_setting_set($dcUserId)){ $infoFormApiKey = __('Your api key has already been created.');
$infoFormApiKey = __('Your api key has already been created.'); $buttonFormApiKey = __('Erase existing API key and generate a new one for').' '.$dcUserId;
$buttonFormApiKey = __('Erase existing API key and generate a new one for').' '.$dcUserId; }else{
}else{ $infoFormApiKey = __('No API key found.');
$infoFormApiKey = __('No API key found.'); $buttonFormApiKey = __('Generate a API key for').' '.$dcUserId;
$buttonFormApiKey = __('Generate a API key for').' '.$dcUserId; }
}
if($this->key == ''){
if($this->key == ''){ $infoKey = $infoFormApiKey;
$infoKey = $infoFormApiKey; }else{
}else{ $infoKey = '<p class="info">'.__('The api key is').':<input type ="texte" value="'.$this->key.'"/><br/>'.
$infoKey = '<p class="info">'.__('The api key is').':<input type ="texte" value="'.$this->key.'"/><br/>'. __('Copy and paste it, You will cannot see it again.').'</p>';
__('Copy and paste it, You will cannot see it again.').'</p>'; }
}
return '<form method="post" action="'.http::getSelfURI().'">'.
return '<form method="post" action="'.http::getSelfURI().'">'. $infoKey.
$infoKey. '<p><input type="submit" name="resetApiKey" value="'.$buttonFormApiKey.'"/></p>'.
'<p><input type="submit" name="resetApiKey" value="'.$buttonFormApiKey.'"/></p>'. $core->formNonce().
$core->formNonce(). '</form>';
'</form>'; }
}
private function dc_is_key_setting_set($dcUserId)
private function dc_is_key_setting_set($dcUserId) {
{ global $core;
global $core;
$apiKeyName = $this->get_dc_setting_api_name($dcUserId);
$apiKeyName = $this->get_dc_setting_api_name($dcUserId); $currentHashedKey = $core->blog->settings->rest->{$apiKeyName};
$currentHashedKey = $core->blog->settings->rest->{$apiKeyName}; if(empty($currentHashedKey)){
if(empty($currentHashedKey)){ return false;
return false; }else{
}else{ return true;
return true; }
} }
}
private function put_dc_setting_user_key($dcUserId)
private function put_dc_setting_user_key($dcUserId) {
{ global $core;
global $core;
if ($this->key == ''){
if ($this->key == ''){ //don't save an empty key
//don't save an empty key return false;
return false; }
} $hashedKey = $core->auth->crypt($this->key);
$hash = md5($this->key); $core->blog->settings->rest->put(
$core->blog->settings->rest->put( $this->get_dc_setting_api_name($dcUserId),
$this->get_dc_setting_api_name($dcUserId), $hashedKey,
$hash, 'string'
'string' );
); return $hashedKey;
return $hash; }
}
private function get_dc_setting_api_name($dcUserId)
private function get_dc_setting_api_name($dcUserId) {
{ return 'rest_key_'.$dcUserId;
return 'rest_key_'.$dcUserId; }
}
private function rand_str($length = 32, $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890')
private function rand_str($length = 32, $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890') {
{
$chars_length = (strlen($chars) - 1); $chars_length = (strlen($chars) - 1);
$string = $chars{rand(0, $chars_length)}; $string = $chars{rand(0, $chars_length)};
for ($i = 1; $i < $length; $i = strlen($string)){ for ($i = 1; $i < $length; $i = strlen($string)){
@ -93,5 +92,5 @@ class ApiKey
if ($r != $string{$i - 1}) $string .= $r; if ($r != $string{$i - 1}) $string .= $r;
} }
return $string; return $string;
} }
} }

View File

@ -0,0 +1,27 @@
<?php
/*
*Methode permettant de retourner des informations sur un blog particulier
*/
class RestQueryGetBlog extends RestQuery
{
public function __construct(){
global $core;
}
/*
* ça se complique niveau droits
*
* SI L'utilisateur n'est pas authentifié
* le blog est hors ligne
* -> 404
* l'API n'est pas publique
* -> refus
* l'API est publique
* -> OK, mais on ne retourne pas les infos techniques
* L'utilisateur est authentifié
* n'est pas admin (du blog en question)
* -> OK, mais on ne retourne pas les infos techniques
* est admin
* -> L'API retourne le maximum d'infos
*/
}

View File

@ -2,17 +2,25 @@
class RestQueryGetBlogs extends RestQuery class RestQueryGetBlogs extends RestQuery
{ {
public function __construct($user){ public function __construct(){
if($user === false){
//need To be authentified global $core;
$this->response_code = 403; $this->blog_id = false; //this method doesn't depend on a bolg_id
$this->response_message = array('code' => 403, 'error' => 'get Blogs methods requires to be authentified'); $this->required_perms = 'none'; //I want user have an account
return;
} if($this->is_allowed() === false){
//error_log(json_encode($user->findUserBlog())); //need To be authentified
$this->response_code = 403;
$this->response_message = array('code' => 403, 'error' => 'get Blogs methods requires to be authentified');
} return;
}
//list the blogs the user can access
$blgs = $core->auth->getAllPermissions();
$ret = array();
foreach($blgs as $key=>$value){
$ret[] = $key;
}
$this->response_code = 200;
$this->response_message = $ret;
}
} }

View File

@ -1,19 +1,27 @@
<?php <?php
class RestQueryGetSpecs extends RestQuery class RestQueryGetSpecs extends RestQuery
{ {
public function __construct($user){ public function __construct(){
global $core; global $core;
$this->response_code = 200; $this->response_code = 200;
$specs = json_decode(file_get_contents(dirname(__FILE__).'/../documentation/swagger.json'),true); $this->required_perms = 'unauth';
//change some parameters
$url = parse_url($core->blog->url.$core->url->getBase('rest')); if($this->is_allowed() === false){
$specs['host'] = $url['host']; $this->response_code = 403;
$specs['schemes'] = $url['scheme']; $this->response_message = array('code' => 403, 'error' => 'this method is not open');
preg_match('/https?:\/\/[^\/]*(\/.*)/',$core->blog->url.$core->url->getBase('rest'),$end); return;
$specs['basePath'] = $end[1]; }
$this->response_message = $specs;
return; $specs = json_decode(file_get_contents(dirname(__FILE__).'/../documentation/swagger.json'),true);
//change some parameters
} $url = parse_url($core->blog->url.$core->url->getBase('rest'));
$specs['host'] = $url['host'];
$specs['schemes'] = $url['scheme'];
preg_match('/https?:\/\/[^\/]*(\/.*)/',$core->blog->url.$core->url->getBase('rest'),$end);
$specs['basePath'] = $end[1];
$this->response_message = $specs;
return;
}
} }

View File

@ -1,72 +1,215 @@
<?php <?php
class RestQuery{ class RestQuery{
public $response_code; public $response_code;
public $response_message; //array public $response_message; //array
public $blog_id;
public function get_full_code_header($code){ protected $required_perms = 'admin'; //must be changed by the childs class
static $codes = array( /*
100 =>"Continue", should be:
101 =>"Switching Protocols", 'admin'
102 =>"Processing", 'usage'
200 =>"OK", 'publish'
201 =>"Created", 'delete'
202 =>"Accepted", 'contentadmin'
203 =>"Non-Authoritative Information", 'categories'
204 =>"No Content", 'media'
205 =>"Reset Content", 'media_admin'
206 =>"Partial Content", 'none' //must be have an account (without any rights)
207 =>"Multi-Status", 'unauth' //Open to the world
210 =>"Content Different", */
226 =>"IM Used",
300 =>"Multiple Choices", public function __construct()
301 =>"Moved Permanently", {
302 =>"Moved Temporarily",
303 =>"See Other", $this->response_code = RestQuery::get_full_code_header(400);
304 =>"Not Modified", $this->response_message = array(
305 =>"Use Proxy", "error" => "Unrecoknized method",
306 =>"(aucun)", "code" => 400
307 =>"Temporary Redirect", );
308 =>"Permanent Redirect", }
310 =>"Too many Redirects", /**
400 =>"Bad Request", * Check if required fields are set
401 =>"Unauthorized", * $strict => Go on error if a additionnal field is given
402 =>"Payment Required", */
403 =>"Forbidden", protected function check_for_required_fields($arrayToCheck,$fieldsRequired,$fieldsOptionals = '')
404 =>"Not Found", {
405 =>"Method Not Allowed", if ($fieldsOptionals == ''){
406 =>"Not Acceptable", $fieldsOptionals == array();
407 =>"Proxy Authentication Required", }
408 =>"Request Time-out",
409 =>"Conflict", $fieldsSetted = array_keys($arrayToCheck);
410 =>"Gone",
411 =>"Length Required", if($fieldsOptionals == ''){
412 =>"Precondition Failed", if(empty(array_diff($fieldsSetted,$fieldsRequired))){
413 =>"Request Entity Too Large", return true;
414 =>"Request-URI Too Long", }else{
415 =>"Unsupported Media Type", $this->response_code = RestQuery::get_full_code_header(400);
416 =>"Requested range unsatisfiable", $this->response_message = array(
417 =>"Expectation failed", "error" => "Only and each of following parameters ".
418 =>"Im a teapot", implode(", ",$fieldsRequired)." are required",
421 =>"Bad mapping / Misdirected Request", "code" => 400
422 =>"Unprocessable entity", );
423 =>"Locked", return false;
424 =>"Method failure", }
425 =>"Unordered Collection", }else{
426 =>"Upgrade Required", //check if all required fields are set
428 =>"Precondition Required", foreach($fieldsRequired as $key){
429 =>"Too Many Requests", if(!isset($arrayToCheck[$key])){
431 =>"Request Header Fields Too Large", $this->response_code = RestQuery::get_full_code_header(400);
449 =>"Retry With", $this->response_message = array(
450 =>"Blocked by Windows Parental Controls", "error" => "field ".$key." is needed",
451 =>"Unavailable For Legal Reasons", "code" => 400
456 =>"Unrecoverable Error" );
); return false;
}
if(isset($codes[$code])){ }
return "HTTP/1.0 ".$code." ".$codes[$code]; //check if a field is not in required and in fieldsOptionals
}else{ foreach($fieldsSetted as $keyToTest){
return "HTTP/1.0 ".$code." Something wrong happened"; if((!in_array($keyToTest,$fieldsRequired)) && (!in_array($keyToTest,$fieldsOptionals))){
} $this->response_message = array(
} "error" => "Unwanted field '".$keyToTest."'",
"code" => 400
);
return false;
}
}
return true;
}
}
protected function body_to_array($body){
if($ret = json_decode($body,true)){
return $ret;
}else{
$this->response_code = 301;
$this->response_message = array(
'error' => 'Can\'t parse input JSON',
'code' => 400
);
return false;
}
}
protected function is_allowed()
{
global $core;
if($core->auth){
$perms = $core->auth->getAllPermissions();
}
switch($this->required_perms){
case 'unauth':
//on verifie quand même que l'API est ouverte
if((!$core->blog->settings->rest->rest_is_open) && ($core->auth === false)){
return false;
}else{
return true;
}
break;
//to do
case 'none':
//user must be valid
if($core->auth === false){
return false;
}else{
return true;
}
break;
case 'media_admin':
break;
case 'media':
break;
case 'categories':
break;
case 'contentadmin':
break;
case 'delete':
break;
case 'publish':
break;
case 'usage':
break;
case 'admin':
if($core->auth === false){
return false;
}
if ($core->auth->isSuperAdmin()){
return true;
}else{
return false;
}
break;
}
}
public function get_full_code_header($code){
static $codes = array(
100 =>"Continue",
101 =>"Switching Protocols",
102 =>"Processing",
200 =>"OK",
201 =>"Created",
202 =>"Accepted",
203 =>"Non-Authoritative Information",
204 =>"No Content",
205 =>"Reset Content",
206 =>"Partial Content",
207 =>"Multi-Status",
210 =>"Content Different",
226 =>"IM Used",
300 =>"Multiple Choices",
301 =>"Moved Permanently",
302 =>"Moved Temporarily",
303 =>"See Other",
304 =>"Not Modified",
305 =>"Use Proxy",
306 =>"(aucun)",
307 =>"Temporary Redirect",
308 =>"Permanent Redirect",
310 =>"Too many Redirects",
400 =>"Bad Request",
401 =>"Unauthorized",
402 =>"Payment Required",
403 =>"Forbidden",
404 =>"Not Found",
405 =>"Method Not Allowed",
406 =>"Not Acceptable",
407 =>"Proxy Authentication Required",
408 =>"Request Time-out",
409 =>"Conflict",
410 =>"Gone",
411 =>"Length Required",
412 =>"Precondition Failed",
413 =>"Request Entity Too Large",
414 =>"Request-URI Too Long",
415 =>"Unsupported Media Type",
416 =>"Requested range unsatisfiable",
417 =>"Expectation failed",
418 =>"Im a teapot",
421 =>"Bad mapping / Misdirected Request",
422 =>"Unprocessable entity",
423 =>"Locked",
424 =>"Method failure",
425 =>"Unordered Collection",
426 =>"Upgrade Required",
428 =>"Precondition Required",
429 =>"Too Many Requests",
431 =>"Request Header Fields Too Large",
449 =>"Retry With",
450 =>"Blocked by Windows Parental Controls",
451 =>"Unavailable For Legal Reasons",
456 =>"Unrecoverable Error"
);
if(isset($codes[$code])){
return "HTTP/1.0 ".$code." ".$codes[$code];
}else{
return "HTTP/1.0 ".$code." Something wrong happened";
}
}
} }

View File

@ -0,0 +1,97 @@
<?php
class RestQueryPostBlogs extends RestQuery
{
public function __construct($body)
{
global $core;
$this->blog_id = false; //this method doesn't depend on a bolg_id
$this->required_perms = 'admin'; //I want user have an account
if($this->is_allowed() === false){
//need To be authentified
$this->response_code = 403;
$this->response_message = array('code' => 403, 'error' => 'You need to be admin to create a new blog');
return;
}
$inputArray = $this-> body_to_array($body);
if ($inputArray === false){
return false;
}
//permit optional description
if(!isset($inputArray['blog_desc'])){
$inputArray["blog_desc"] = '';
}
//check if parameters are set
if(!$this->check_for_required_fields( $inputArray, array('blog_id','blog_url','blog_name','blog_desc'),
array('lang','blog_timezone','url_scan')) ){
return;
}
//Following lines are same as admin/blog.php
$cur = $core->con->openCursor($core->prefix.'blog');
$blog_id = $cur->blog_id = $inputArray['blog_id'];
$blog_url = $cur->blog_url = $inputArray['blog_url'];
$blog_name = $cur->blog_name = $inputArray['blog_name'];
$blog_desc = $cur->blog_desc = $inputArray['blog_desc'];
try
{
# --BEHAVIOR-- adminBeforeBlogCreate
$core->callBehavior('adminBeforeBlogCreate',$cur,$blog_id);
$core->addBlog($cur);
# Default settings and override some
$core->blogDefaults($cur->blog_id);
$blog_settings = new dcSettings($core,$cur->blog_id);
$blog_settings->addNamespace('system');
if(isset($inputArray['lang'])){
$blog_settings->system->put('lang',$inputArray['lang']);
}else{
$blog_settings->system->put('lang',$core->auth->getInfo('user_lang'));
}
if(isset($inputArray['blog_timezone'])){
$blog_settings->system->put('blog_timezone',$inputArray['blog_timezone']);
}else{
$blog_settings->system->put('blog_timezone',$core->auth->getInfo('user_tz'));
}
if(isset($inputArray['url_scan'])){
$blog_settings->system->put('url_scan',$inputArray['url_scan']);
}elseif(substr($blog_url,-1) == '?') {
$blog_settings->system->put('url_scan','query_string');
} else {
$blog_settings->system->put('url_scan','path_info');
}
# --BEHAVIOR-- adminAfterBlogCreate
$core->callBehavior('adminAfterBlogCreate',$cur,$blog_id,$blog_settings);
//cool
$this->response_code = 200;
$this->response_message = array(
'code' => 200,
'message' => 'Successfully created blog'.$blog_id
);
}
catch (Exception $e)
{
$this->response_code = 500;
$this->response_message = array(
'code' => 500,
'message' => $e->getMessage()
);
}
return;
}
}

114
index.php
View File

@ -8,16 +8,16 @@ $apiKey = new ApiKey;
// Setting default parameters if missing configuration // Setting default parameters if missing configuration
$core->blog->settings->addNamespace('rest'); $core->blog->settings->addNamespace('rest');
if (is_null($core->blog->settings->rest->rest_active)) { if (is_null($core->blog->settings->rest->rest_active)) {
try { try {
$core->blog->settings->rest->put('rest_active',false,'boolean',true); $core->blog->settings->rest->put('rest_active',false,'boolean',true);
$core->blog->settings->rest->put('rest_is_open',false,'boolean',true); $core->blog->settings->rest->put('rest_is_open',false,'boolean',true);
$core->blog->settings->rest->put('rest_send_cors_headers',true,'boolean',true); $core->blog->settings->rest->put('rest_send_cors_headers',true,'boolean',true);
$core->blog->triggerBlog(); $core->blog->triggerBlog();
http::redirect($p_url); http::redirect($p_url);
} }
catch (Exception $e) { catch (Exception $e) {
$core->error->add($e->getMessage()); $core->error->add($e->getMessage());
} }
} }
// Getting current parameters // Getting current parameters
$active = (boolean)$core->blog->settings->rest->rest_active; $active = (boolean)$core->blog->settings->rest->rest_active;
@ -26,70 +26,70 @@ $sendHeaders =(boolean)$core->blog->settings->rest->rest_send_cors_headers;
//Sousmission Formulaire parametres //Sousmission Formulaire parametres
if ((!empty($_POST['saveconfig'])) && ($core->auth->isSuperAdmin())) { if ((!empty($_POST['saveconfig'])) && ($core->auth->isSuperAdmin())) {
try try
{ {
$core->blog->settings->addNameSpace('rest'); $core->blog->settings->addNameSpace('rest');
$active = (empty($_POST['active'])) ? false : true; $active = (empty($_POST['active'])) ? false : true;
$core->blog->settings->rest->put('rest_active',$active,'boolean'); $core->blog->settings->rest->put('rest_active',$active,'boolean');
$openApi = (empty($_POST['open'])) ? false : true; $openApi = (empty($_POST['open'])) ? false : true;
$core->blog->settings->rest->put('rest_is_open',$openApi,'boolean'); $core->blog->settings->rest->put('rest_is_open',$openApi,'boolean');
$sendHeaders = (empty($_POST['sendHeaders'])) ? false : true; $sendHeaders = (empty($_POST['sendHeaders'])) ? false : true;
$core->blog->settings->rest->put('rest_send_cors_headers',$sendHeaders,'boolean'); $core->blog->settings->rest->put('rest_send_cors_headers',$sendHeaders,'boolean');
dcPage::addSuccessNotice(__('Configuration successfully updated.')); dcPage::addSuccessNotice(__('Configuration successfully updated.'));
http::redirect($p_url); http::redirect($p_url);
}catch (Exception $e) }catch (Exception $e)
{ {
$core->error->add($e->getMessage()); $core->error->add($e->getMessage());
} }
} }
//Sousmission Formulaire Reset API Key //Sousmission Formulaire Reset API Key
if(!empty($_POST['resetApiKey'])){ if(!empty($_POST['resetApiKey'])){
$core->blog->settings->addNameSpace('rest'); $core->blog->settings->addNameSpace('rest');
$apiKey -> new_key($core->auth->userID()); $apiKey -> new_key($core->auth->userID());
dcPage::addSuccessNotice(__('Your new key is').' '.$apiKey->key); dcPage::addSuccessNotice(__('Your new key is').' '.$apiKey->key);
} }
?> ?>
<html> <html>
<head> <head>
<title>Rest API config</title> <title>Rest API config</title>
</head> </head>
<body> <body>
<h2>Documentation</h2> <h2>Documentation</h2>
<p><a href="<?php echo $core->blog->url."rest/documentation"; ?>">Go to the Swagger documentation</a></p> <p><a href="<?php echo $core->blog->url."rest/documentation"; ?>">Go to the Swagger documentation</a></p>
<h2><?php echo __('Your API key');?></h2> <h2><?php echo __('Your API key');?></h2>
<?php echo $apiKey-> get_dc_admin_form($core->auth->userID()); ?> <?php echo $apiKey-> get_dc_admin_form($core->auth->userID()); ?>
<?php <?php
//Seulement si administrateur: //Seulement si administrateur:
if($core->auth->isSuperAdmin()): if($core->auth->isSuperAdmin()):
?> ?>
<h2><?php echo __('Rest API configuration'); ?></h2> <h2><?php echo __('Rest API configuration'); ?></h2>
<form method="post" action="<?php http::getSelfURI(); ?>"> <form method="post" action="<?php http::getSelfURI(); ?>">
<p> <p>
<?php echo form::checkbox('active', 1, $active); ?> <?php echo form::checkbox('active', 1, $active); ?>
<label class="classic" for="active">&nbsp;<?php echo __('Enable REST API');?></label> <label class="classic" for="active">&nbsp;<?php echo __('Enable REST API');?></label>
</p> </p>
<p> <p>
<?php echo form::checkbox('open', 1, $openApi); ?> <?php echo form::checkbox('open', 1, $openApi); ?>
<label class="classic" for="open">&nbsp;<?php echo __('API is open');?></label> <label class="classic" for="open">&nbsp;<?php echo __('API is open');?></label>
</p> </p>
<p class="info"><?php echo __("If checked, few methods as GET will be allowed to externals users without API key. <p class="info"><?php echo __("If checked, few methods as GET will be allowed to externals users without API key.
However, they won't be able to request for non public content."); ?></p> However, they won't be able to request for non public content."); ?></p>
<?php echo $core->formNonce(); ?> <?php echo $core->formNonce(); ?>
<p> <p>
<?php echo form::checkbox('sendHeaders', 1, $sendHeaders); ?> <?php echo form::checkbox('sendHeaders', 1, $sendHeaders); ?>
<label class="classic" for="sendHeaders">&nbsp;<?php echo __('Send Coors headers');?></label> <label class="classic" for="sendHeaders">&nbsp;<?php echo __('Send Coors headers');?></label>
</p> </p>
<p> <p>
<input type="submit" name="saveconfig" value="<?php echo __('Save configuration'); ?>" /> <input type="submit" name="saveconfig" value="<?php echo __('Save configuration'); ?>" />
</p> </p>
</from> </from>
<?php <?php
endif; endif;
?> ?>