Merge branch 'develop'
This commit is contained in:
commit
1bf3fba756
149
README.markdown
Normal file
149
README.markdown
Normal file
@ -0,0 +1,149 @@
|
|||||||
|
```
|
||||||
|
_________.__ .__ .__ ________
|
||||||
|
/ _____/| |__ |__| _____ _____ |__| ____ \_____ \
|
||||||
|
\_____ \ | | \ | | / \ / \ | |_/ __ \ / ____/
|
||||||
|
/ \| Y \| || Y Y \| Y Y \| |\ ___/ / \
|
||||||
|
/_______ /|___| /|__||__|_| /|__|_| /|__| \___ >\_______ \
|
||||||
|
\/ \/ \/ \/ \/ \/
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
# Shimmie
|
||||||
|
|
||||||
|
[](https://travis-ci.org/shish/shimmie2)
|
||||||
|
|
||||||
|
This is the main branch of Shimmie, if you know anything at all about running
|
||||||
|
websites, this is the version to use.
|
||||||
|
|
||||||
|
Alternatively if you want a version that will never have significant changes,
|
||||||
|
check out one of the versioned branches.
|
||||||
|
|
||||||
|
# Requirements
|
||||||
|
|
||||||
|
- MySQL/MariaDB 5.1+ (with experimental support for PostgreSQL 8+ and SQLite 3)
|
||||||
|
- PHP 5.3.7+
|
||||||
|
- GD or ImageMagick
|
||||||
|
|
||||||
|
# Installation
|
||||||
|
|
||||||
|
1. Create a blank database
|
||||||
|
2. Unzip shimmie into a folder on the web host
|
||||||
|
3. Visit the folder with a web browser
|
||||||
|
4. Enter the location of the database
|
||||||
|
5. Click "install". Hopefully you'll end up at the welcome screen; if
|
||||||
|
not, you should be given instructions on how to fix any errors~
|
||||||
|
|
||||||
|
## Upgrade from 2.3.X
|
||||||
|
|
||||||
|
1. Backup your current files and database!
|
||||||
|
2. Unzip into a clean folder
|
||||||
|
3. Copy across the images, thumbs, and data folders
|
||||||
|
4. Move `old/config.php` to `new/data/config/shimmie.conf.php`
|
||||||
|
5. Edit `shimmie.conf.php` to use the new database connection format:
|
||||||
|
|
||||||
|
OLD Format:
|
||||||
|
```php
|
||||||
|
$database_dsn = "<proto>://<username>:<password>@<host>/<database>";
|
||||||
|
```
|
||||||
|
|
||||||
|
NEW Format:
|
||||||
|
```php
|
||||||
|
define("DATABASE_DSN", "<proto>:user=<username>;password=<password>;host=<host>;dbname=<database>");
|
||||||
|
```
|
||||||
|
|
||||||
|
The rest should be automatic~
|
||||||
|
|
||||||
|
If there are any errors with the upgrade process, `in_upgrade=true` will
|
||||||
|
be left in the config table and the process will be paused for the admin
|
||||||
|
to investigate.
|
||||||
|
|
||||||
|
Deleting this config entry and refreshing the page should continue the upgrade from where it left off.
|
||||||
|
|
||||||
|
|
||||||
|
### Upgrade from earlier versions
|
||||||
|
|
||||||
|
I very much recommend going via each major release in turn (eg, 2.0.6
|
||||||
|
-> 2.1.3 -> 2.2.4 -> 2.3.0 rather than 2.0.6 -> 2.3.0).
|
||||||
|
|
||||||
|
While the basic database and file formats haven't changed *completely*, it's different
|
||||||
|
enough to be a pain.
|
||||||
|
|
||||||
|
|
||||||
|
## Custom Configuration
|
||||||
|
|
||||||
|
Various aspects of Shimmie can be configured to suit your site specific needs
|
||||||
|
via the file `data/config/shimmie.conf.php` (created after installation).
|
||||||
|
|
||||||
|
Take a look at `core/sys_config.inc.php` for the available options that can
|
||||||
|
be used.
|
||||||
|
|
||||||
|
|
||||||
|
#### Custom User Classes
|
||||||
|
|
||||||
|
User classes can be added to or altered by placing them in
|
||||||
|
`data/config/user-classes.conf.php`.
|
||||||
|
|
||||||
|
For example, one can override the default anonymous "allow nothing" permissions like so:
|
||||||
|
|
||||||
|
```php
|
||||||
|
new UserClass("anonymous", "base", array(
|
||||||
|
"create_comment" => True,
|
||||||
|
"edit_image_tag" => True,
|
||||||
|
"edit_image_source" => True,
|
||||||
|
"create_image_report" => True,
|
||||||
|
));
|
||||||
|
```
|
||||||
|
|
||||||
|
For a moderator class, being a regular user who can delete images and comments:
|
||||||
|
|
||||||
|
```php
|
||||||
|
new UserClass("moderator", "user", array(
|
||||||
|
"delete_image" => True,
|
||||||
|
"delete_comment" => True,
|
||||||
|
));
|
||||||
|
```
|
||||||
|
|
||||||
|
For a list of permissions, see `core/userclass.class.php`
|
||||||
|
|
||||||
|
|
||||||
|
# Development Info
|
||||||
|
|
||||||
|
ui-* cookies are for the client-side scripts only; in some configurations
|
||||||
|
(eg with varnish cache) they will be stripped before they reach the server
|
||||||
|
|
||||||
|
shm-* CSS classes are for javascript to hook into; if you're customising
|
||||||
|
themes, be careful with these, and avoid styling them, eg:
|
||||||
|
|
||||||
|
- shm-thumb = outermost element of a thumbnail
|
||||||
|
* data-tags
|
||||||
|
* data-post-id
|
||||||
|
- shm-toggler = click this to toggle elements that match the selector
|
||||||
|
* data-toggle-sel
|
||||||
|
- shm-unlocker = click this to unlock elements that match the selector
|
||||||
|
* data-unlock-sel
|
||||||
|
- shm-clink = a link to a comment, flash the target element when clicked
|
||||||
|
* data-clink-sel
|
||||||
|
|
||||||
|
Documentation: http://shimmie.shishnet.org/doc/
|
||||||
|
|
||||||
|
Please tell me if those docs are lacking in any way, so that they can be
|
||||||
|
improved for the next person who uses them
|
||||||
|
|
||||||
|
|
||||||
|
# Contact
|
||||||
|
|
||||||
|
IRC: `#shimmie` on [Freenode](irc.freenode.net)
|
||||||
|
|
||||||
|
Email: webmaster at shishnet.org
|
||||||
|
|
||||||
|
Issue/Bug tracker: http://github.com/shish/shimmie2/issues
|
||||||
|
|
||||||
|
|
||||||
|
# Licence
|
||||||
|
|
||||||
|
All code is released under the [GNU GPL Version 2](http://www.gnu.org/licenses/gpl-2.0.html) unless mentioned otherwise.
|
||||||
|
|
||||||
|
If you give shimmie to someone else, you have to give them the source (which should be easy, as PHP
|
||||||
|
is an interpreted language...). If you want to add customisations to your own
|
||||||
|
site, then those customisations belong to you, and you can do what you want
|
||||||
|
with them.
|
133
README.txt
133
README.txt
@ -1,133 +0,0 @@
|
|||||||
|
|
||||||
_________.__ .__ .__ ________
|
|
||||||
/ _____/| |__ |__| _____ _____ |__| ____ \_____ \
|
|
||||||
\_____ \ | | \ | | / \ / \ | |_/ __ \ / ____/
|
|
||||||
/ \| Y \| || Y Y \| Y Y \| |\ ___/ / \
|
|
||||||
/_______ /|___| /|__||__|_| /|__|_| /|__| \___ >\_______ \
|
|
||||||
\/ \/ \/ \/ \/ \/
|
|
||||||
|
|
||||||
_________________________________________________________________________
|
|
||||||
|
|
||||||
|
|
||||||
Shimmie Development
|
|
||||||
~~~~~~~~~~~~~~~~~~~
|
|
||||||
This is the main branch of Shimmie, if you know anything at all about
|
|
||||||
running websites, this is the version to use. Alternatively if you want
|
|
||||||
a version that will never have significant changes, check out one of the
|
|
||||||
versioned branches.
|
|
||||||
|
|
||||||
|
|
||||||
Requirements
|
|
||||||
~~~~~~~~~~~~
|
|
||||||
MySQL/MariaDB 5.1+ (with experimental support for PostgreSQL 8+ and SQLite 3)
|
|
||||||
PHP 5.3+
|
|
||||||
GD or ImageMagick
|
|
||||||
|
|
||||||
|
|
||||||
Installation
|
|
||||||
~~~~~~~~~~~~
|
|
||||||
1) Create a blank database
|
|
||||||
2) Unzip shimmie into a folder on the web host
|
|
||||||
3) Visit the folder with a web browser
|
|
||||||
4) Enter the location of the database
|
|
||||||
5) Click "install". Hopefully you'll end up at the welcome screen; if
|
|
||||||
not, you should be given instructions on how to fix any errors~
|
|
||||||
|
|
||||||
|
|
||||||
Upgrade from 2.3.X
|
|
||||||
~~~~~~~~~~~~~~~~~~
|
|
||||||
- Backup your current files and database!
|
|
||||||
- Unzip into a clean folder
|
|
||||||
- Copy across the images, thumbs, and data folders
|
|
||||||
- Move old/config.php to new/data/config/shimmie.conf.php
|
|
||||||
- Edit shimmie.conf.php to use the new database connection format:
|
|
||||||
|
|
||||||
OLD: $database_dsn = "<proto>://<username>:<password>@<host>/<database>";
|
|
||||||
NEW: define("DATABASE_DSN", "<proto>:user=<username>;password=<password>;host=<host>;dbname=<database>");
|
|
||||||
|
|
||||||
The rest should be automatic~
|
|
||||||
|
|
||||||
If there are any errors with the upgrade process, "in_upgrade=true" will
|
|
||||||
be left in the config table and the process will be paused for the admin
|
|
||||||
to investigate. Deleting this config entry and refreshing the page should
|
|
||||||
continue the upgrade from where it left off.
|
|
||||||
|
|
||||||
|
|
||||||
Upgrade from earlier versions
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
I very much recommend going via each major release in turn (eg, 2.0.6
|
|
||||||
-> 2.1.3 -> 2.2.4 -> 2.3.0 rather than 2.0.6 -> 2.3.0). While the basic
|
|
||||||
database and file formats haven't changed *completely*, it's different
|
|
||||||
enough to be a pain.
|
|
||||||
|
|
||||||
|
|
||||||
Custom Configuration
|
|
||||||
~~~~~~~~~~~~~~~~~~~~
|
|
||||||
Various aspects of Shimmie can be configured to suit your site specific needs
|
|
||||||
via the file "data/config/shimmie.conf.php" (created after installation).
|
|
||||||
Take a look at "core/sys_config.inc.php" for the available options that can
|
|
||||||
be used.
|
|
||||||
|
|
||||||
|
|
||||||
Custom User Classes
|
|
||||||
~~~~~~~~~~~~~~~~~~~
|
|
||||||
User classes can be added to or altered by placing them in
|
|
||||||
`data/config/user-classes.conf.php`. For example, one can override the
|
|
||||||
default anonymous "allow nothing" permissions like so:
|
|
||||||
|
|
||||||
new UserClass("anonymous", "base", array(
|
|
||||||
"create_comment" => True,
|
|
||||||
"edit_image_tag" => True,
|
|
||||||
"edit_image_source" => True,
|
|
||||||
"create_image_report" => True,
|
|
||||||
));
|
|
||||||
|
|
||||||
For a moderator class, being a regular user who can delete images and
|
|
||||||
comments:
|
|
||||||
|
|
||||||
new UserClass("moderator", "user", array(
|
|
||||||
"delete_image" => True,
|
|
||||||
"delete_comment" => True,
|
|
||||||
));
|
|
||||||
|
|
||||||
For a list of permissions, see core/userclass.class.php
|
|
||||||
|
|
||||||
|
|
||||||
Development Info
|
|
||||||
~~~~~~~~~~~~~~~~
|
|
||||||
ui-* cookies are for the client-side scripts only; in some configurations
|
|
||||||
(eg with varnish cache) they will be stripped before they reach the server
|
|
||||||
|
|
||||||
shm-* CSS classes are for javascript to hook into; if you're customising
|
|
||||||
themes, be careful with these, and avoid styling them, eg:
|
|
||||||
|
|
||||||
- shm-thumb = outermost element of a thumbnail
|
|
||||||
- data-tags
|
|
||||||
- data-post-id
|
|
||||||
- shm-toggler = click this to toggle elements that match the selector
|
|
||||||
- data-toggle-sel
|
|
||||||
- shm-unlocker = click this to unlock elements that match the selector
|
|
||||||
- data-unlock-sel
|
|
||||||
- shm-clink = a link to a comment, flash the target element when clicked
|
|
||||||
- data-clink-sel
|
|
||||||
|
|
||||||
http://shimmie.shishnet.org/doc/
|
|
||||||
|
|
||||||
Please tell me if those docs are lacking in any way, so that they can be
|
|
||||||
improved for the next person who uses them
|
|
||||||
|
|
||||||
|
|
||||||
Contact
|
|
||||||
~~~~~~~
|
|
||||||
#shimmie on Freenode -- IRC
|
|
||||||
webmaster at shishnet.org -- email
|
|
||||||
https://github.com/shish/shimmie2/issues -- bug tracker
|
|
||||||
|
|
||||||
|
|
||||||
Licence
|
|
||||||
~~~~~~~
|
|
||||||
All code is GPLv2 unless mentioned otherwise; ie, if you give shimmie to
|
|
||||||
someone else, you have to give them the source (which should be easy, as PHP
|
|
||||||
is an interpreted language...). If you want to add customisations to your own
|
|
||||||
site, then those customisations belong to you, and you can do what you want
|
|
||||||
with them.
|
|
@ -56,7 +56,7 @@ class BaseThemelet {
|
|||||||
$h_tip = html_escape($image->get_tooltip());
|
$h_tip = html_escape($image->get_tooltip());
|
||||||
$h_tags = strtolower($image->get_tag_list());
|
$h_tags = strtolower($image->get_tag_list());
|
||||||
|
|
||||||
$extArr = array_flip(array('swf', 'svg', 'mp4', 'ogv', 'webm', 'flv')); //List of thumbless filetypes
|
$extArr = array_flip(array('swf', 'svg')); //List of thumbless filetypes
|
||||||
if(!isset($extArr[$image->ext])){
|
if(!isset($extArr[$image->ext])){
|
||||||
$tsize = get_thumbnail_size($image->width, $image->height);
|
$tsize = get_thumbnail_size($image->width, $image->height);
|
||||||
}else{
|
}else{
|
||||||
|
@ -1,17 +1,20 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A basic chunk of a page
|
* Class Block
|
||||||
|
*
|
||||||
|
* A basic chunk of a page.
|
||||||
*/
|
*/
|
||||||
class Block {
|
class Block {
|
||||||
/**
|
/**
|
||||||
* The block's title
|
* The block's title.
|
||||||
*
|
*
|
||||||
* @var string
|
* @var string
|
||||||
*/
|
*/
|
||||||
public $header;
|
public $header;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The content
|
* The content of the block.
|
||||||
*
|
*
|
||||||
* @var string
|
* @var string
|
||||||
*/
|
*/
|
||||||
@ -19,7 +22,7 @@ class Block {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Where the block should be placed. The default theme supports
|
* Where the block should be placed. The default theme supports
|
||||||
* "main" and "left", other themes can add their own areas
|
* "main" and "left", other themes can add their own areas.
|
||||||
*
|
*
|
||||||
* @var string
|
* @var string
|
||||||
*/
|
*/
|
||||||
@ -35,7 +38,9 @@ class Block {
|
|||||||
public $position;
|
public $position;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var int
|
* A unique ID for the block.
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
*/
|
*/
|
||||||
public $id;
|
public $id;
|
||||||
|
|
||||||
@ -46,7 +51,7 @@ class Block {
|
|||||||
* @param string $body
|
* @param string $body
|
||||||
* @param string $section
|
* @param string $section
|
||||||
* @param int $position
|
* @param int $position
|
||||||
* @param null|int $id
|
* @param null|int $id A unique ID for the block (generated automatically if null).
|
||||||
*/
|
*/
|
||||||
public function __construct($header, $body, /*string*/ $section="main", /*int*/ $position=50, $id=null) {
|
public function __construct($header, $body, /*string*/ $section="main", /*int*/ $position=50, $id=null) {
|
||||||
$this->header = $header;
|
$this->header = $header;
|
||||||
@ -77,9 +82,12 @@ class Block {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class NavBlock
|
||||||
|
*
|
||||||
* A generic navigation block with a link to the main page.
|
* A generic navigation block with a link to the main page.
|
||||||
*
|
*
|
||||||
* Used because "new NavBlock()" is easier than "new Block('Navigation', ..."
|
* Used because "new NavBlock()" is easier than "new Block('Navigation', ..."
|
||||||
|
*
|
||||||
*/
|
*/
|
||||||
class NavBlock extends Block {
|
class NavBlock extends Block {
|
||||||
public function __construct() {
|
public function __construct() {
|
||||||
|
@ -1,94 +1,237 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* an abstract interface for altering a name:value pair list
|
* Interface Config
|
||||||
|
*
|
||||||
|
* An abstract interface for altering a name:value pair list.
|
||||||
*/
|
*/
|
||||||
interface Config {
|
interface Config {
|
||||||
/**
|
/**
|
||||||
* Save the list of name:value pairs to wherever they came from,
|
* Save the list of name:value pairs to wherever they came from,
|
||||||
* so that the next time a page is loaded it will use the new
|
* so that the next time a page is loaded it will use the new
|
||||||
* configuration
|
* configuration.
|
||||||
|
*
|
||||||
|
* @param null|string $name
|
||||||
|
* @return mixed|void
|
||||||
*/
|
*/
|
||||||
public function save(/*string*/ $name=null);
|
public function save(/*string*/ $name=null);
|
||||||
|
|
||||||
/** @name set_*
|
//@{ /*--------------------------------- SET ------------------------------------------------------*/
|
||||||
* Set a configuration option to a new value, regardless
|
/**
|
||||||
* of what the value is at the moment
|
* Set a configuration option to a new value, regardless of what the value is at the moment.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|int $value
|
||||||
|
* @return void
|
||||||
*/
|
*/
|
||||||
//@{
|
|
||||||
public function set_int(/*string*/ $name, $value);
|
public function set_int(/*string*/ $name, $value);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set a configuration option to a new value, regardless of what the value is at the moment.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_string(/*string*/ $name, $value);
|
public function set_string(/*string*/ $name, $value);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set a configuration option to a new value, regardless of what the value is at the moment.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|bool|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_bool(/*string*/ $name, $value);
|
public function set_bool(/*string*/ $name, $value);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set a configuration option to a new value, regardless of what the value is at the moment.
|
||||||
|
* @param string $name
|
||||||
|
* @param array $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_array(/*string*/ $name, $value);
|
public function set_array(/*string*/ $name, $value);
|
||||||
//@}
|
//@} /*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
/** @name set_default_*
|
//@{ /*-------------------------------- SET DEFAULT -----------------------------------------------*/
|
||||||
* Set a configuration option to a new value, if there is no
|
/**
|
||||||
* value currently. Extensions should generally call these
|
* Set a configuration option to a new value, if there is no value currently.
|
||||||
* from their InitExtEvent handlers. This has the advantage
|
*
|
||||||
* that the values will show up in the "advanced" setup page
|
* Extensions should generally call these from their InitExtEvent handlers.
|
||||||
* where they can be modified, while calling get_* with a
|
* This has the advantage that the values will show up in the "advanced" setup
|
||||||
* "default" paramater won't show up.
|
* page where they can be modified, while calling get_* with a "default"
|
||||||
|
* parameter won't show up.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param int $value
|
||||||
|
* @return void
|
||||||
*/
|
*/
|
||||||
//@{
|
|
||||||
public function set_default_int(/*string*/ $name, $value);
|
public function set_default_int(/*string*/ $name, $value);
|
||||||
public function set_default_string(/*string*/ $name, $value);
|
|
||||||
public function set_default_bool(/*string*/ $name, $value);
|
|
||||||
public function set_default_array(/*string*/ $name, $value);
|
|
||||||
//@}
|
|
||||||
|
|
||||||
/** @name get_*
|
/**
|
||||||
* pick a value out of the table by name, cast to the
|
* Set a configuration option to a new value, if there is no value currently.
|
||||||
* appropritate data type
|
*
|
||||||
|
* Extensions should generally call these from their InitExtEvent handlers.
|
||||||
|
* This has the advantage that the values will show up in the "advanced" setup
|
||||||
|
* page where they can be modified, while calling get_* with a "default"
|
||||||
|
* parameter won't show up.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param string|null $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function set_default_string(/*string*/ $name, $value);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set a configuration option to a new value, if there is no value currently.
|
||||||
|
*
|
||||||
|
* Extensions should generally call these from their InitExtEvent handlers.
|
||||||
|
* This has the advantage that the values will show up in the "advanced" setup
|
||||||
|
* page where they can be modified, while calling get_* with a "default"
|
||||||
|
* parameter won't show up.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param bool|string|null $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function set_default_bool(/*string*/ $name, $value);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set a configuration option to a new value, if there is no value currently.
|
||||||
|
*
|
||||||
|
* Extensions should generally call these from their InitExtEvent handlers.
|
||||||
|
* This has the advantage that the values will show up in the "advanced" setup
|
||||||
|
* page where they can be modified, while calling get_* with a "default"
|
||||||
|
* parameter won't show up.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param array $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function set_default_array(/*string*/ $name, $value);
|
||||||
|
//@} /*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
//@{ /*--------------------------------- GET ------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Pick a value out of the table by name, cast to the appropriate data type.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|int $default
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
//@{
|
|
||||||
public function get_int(/*string*/ $name, $default=null);
|
public function get_int(/*string*/ $name, $default=null);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pick a value out of the table by name, cast to the appropriate data type.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $default
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function get_string(/*string*/ $name, $default=null);
|
public function get_string(/*string*/ $name, $default=null);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pick a value out of the table by name, cast to the appropriate data type.
|
||||||
|
* @param string $name
|
||||||
|
* @param null|bool|string $default
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
public function get_bool(/*string*/ $name, $default=null);
|
public function get_bool(/*string*/ $name, $default=null);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pick a value out of the table by name, cast to the appropriate data type.
|
||||||
|
* @param string $name
|
||||||
|
* @param array|null $default
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_array(/*string*/ $name, $default=array());
|
public function get_array(/*string*/ $name, $default=array());
|
||||||
//@}
|
//@} /*--------------------------------------------------------------------------------------------*/
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class BaseConfig
|
||||||
|
*
|
||||||
* Common methods for manipulating the list, loading and saving is
|
* Common methods for manipulating the list, loading and saving is
|
||||||
* left to the concrete implementation
|
* left to the concrete implementation
|
||||||
*/
|
*/
|
||||||
abstract class BaseConfig implements Config {
|
abstract class BaseConfig implements Config {
|
||||||
var $values = array();
|
var $values = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param int|null $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_int(/*string*/ $name, $value) {
|
public function set_int(/*string*/ $name, $value) {
|
||||||
$this->values[$name] = parse_shorthand_int($value);
|
$this->values[$name] = parse_shorthand_int($value);
|
||||||
$this->save($name);
|
$this->save($name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_string(/*string*/ $name, $value) {
|
public function set_string(/*string*/ $name, $value) {
|
||||||
$this->values[$name] = $value;
|
$this->values[$name] = $value;
|
||||||
$this->save($name);
|
$this->save($name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param bool|null|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_bool(/*string*/ $name, $value) {
|
public function set_bool(/*string*/ $name, $value) {
|
||||||
$this->values[$name] = (($value == 'on' || $value === true) ? 'Y' : 'N');
|
$this->values[$name] = (($value == 'on' || $value === true) ? 'Y' : 'N');
|
||||||
$this->save($name);
|
$this->save($name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param array $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_array(/*string*/ $name, $value) {
|
public function set_array(/*string*/ $name, $value) {
|
||||||
assert(isset($value) && is_array($value));
|
assert(isset($value) && is_array($value));
|
||||||
$this->values[$name] = implode(",", $value);
|
$this->values[$name] = implode(",", $value);
|
||||||
$this->save($name);
|
$this->save($name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param int $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_default_int(/*string*/ $name, $value) {
|
public function set_default_int(/*string*/ $name, $value) {
|
||||||
if(is_null($this->get($name))) {
|
if(is_null($this->get($name))) {
|
||||||
$this->values[$name] = parse_shorthand_int($value);
|
$this->values[$name] = parse_shorthand_int($value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_default_string(/*string*/ $name, $value) {
|
public function set_default_string(/*string*/ $name, $value) {
|
||||||
if(is_null($this->get($name))) {
|
if(is_null($this->get($name))) {
|
||||||
$this->values[$name] = $value;
|
$this->values[$name] = $value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param bool|null|string $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_default_bool(/*string*/ $name, $value) {
|
public function set_default_bool(/*string*/ $name, $value) {
|
||||||
if(is_null($this->get($name))) {
|
if(is_null($this->get($name))) {
|
||||||
$this->values[$name] = (($value == 'on' || $value === true) ? 'Y' : 'N');
|
$this->values[$name] = (($value == 'on' || $value === true) ? 'Y' : 'N');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param array $value
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function set_default_array(/*string*/ $name, $value) {
|
public function set_default_array(/*string*/ $name, $value) {
|
||||||
assert(isset($value) && is_array($value));
|
assert(isset($value) && is_array($value));
|
||||||
if(is_null($this->get($name))) {
|
if(is_null($this->get($name))) {
|
||||||
@ -96,19 +239,47 @@ abstract class BaseConfig implements Config {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|int $default
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_int(/*string*/ $name, $default=null) {
|
public function get_int(/*string*/ $name, $default=null) {
|
||||||
return (int)($this->get($name, $default));
|
return (int)($this->get($name, $default));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $default
|
||||||
|
* @return null|string
|
||||||
|
*/
|
||||||
public function get_string(/*string*/ $name, $default=null) {
|
public function get_string(/*string*/ $name, $default=null) {
|
||||||
return $this->get($name, $default);
|
return $this->get($name, $default);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|bool|string $default
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
public function get_bool(/*string*/ $name, $default=null) {
|
public function get_bool(/*string*/ $name, $default=null) {
|
||||||
return bool_escape($this->get($name, $default));
|
return bool_escape($this->get($name, $default));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param array $default
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_array(/*string*/ $name, $default=array()) {
|
public function get_array(/*string*/ $name, $default=array()) {
|
||||||
return explode(",", $this->get($name, ""));
|
return explode(",", $this->get($name, ""));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|mixed $default
|
||||||
|
* @return null|mixed
|
||||||
|
*/
|
||||||
private function get(/*string*/ $name, $default=null) {
|
private function get(/*string*/ $name, $default=null) {
|
||||||
if(isset($this->values[$name])) {
|
if(isset($this->values[$name])) {
|
||||||
return $this->values[$name];
|
return $this->values[$name];
|
||||||
@ -121,13 +292,19 @@ abstract class BaseConfig implements Config {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* For testing, mostly
|
* Class HardcodeConfig
|
||||||
|
*
|
||||||
|
* For testing, mostly.
|
||||||
*/
|
*/
|
||||||
class HardcodeConfig extends BaseConfig {
|
class HardcodeConfig extends BaseConfig {
|
||||||
public function __construct($dict) {
|
public function __construct($dict) {
|
||||||
$this->values = $dict;
|
$this->values = $dict;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param null|string $name
|
||||||
|
* @return mixed|void
|
||||||
|
*/
|
||||||
public function save(/*string*/ $name=null) {
|
public function save(/*string*/ $name=null) {
|
||||||
// static config is static
|
// static config is static
|
||||||
}
|
}
|
||||||
@ -135,6 +312,8 @@ class HardcodeConfig extends BaseConfig {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class StaticConfig
|
||||||
|
*
|
||||||
* Loads the config list from a PHP file; the file should be in the format:
|
* Loads the config list from a PHP file; the file should be in the format:
|
||||||
*
|
*
|
||||||
* <?php
|
* <?php
|
||||||
@ -143,6 +322,10 @@ class HardcodeConfig extends BaseConfig {
|
|||||||
* ?>
|
* ?>
|
||||||
*/
|
*/
|
||||||
class StaticConfig extends BaseConfig {
|
class StaticConfig extends BaseConfig {
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @throws Exception
|
||||||
|
*/
|
||||||
public function __construct($filename) {
|
public function __construct($filename) {
|
||||||
if(file_exists($filename)) {
|
if(file_exists($filename)) {
|
||||||
require_once $filename;
|
require_once $filename;
|
||||||
@ -158,6 +341,10 @@ class StaticConfig extends BaseConfig {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param null|string $name
|
||||||
|
* @return mixed|void
|
||||||
|
*/
|
||||||
public function save(/*string*/ $name=null) {
|
public function save(/*string*/ $name=null) {
|
||||||
// static config is static
|
// static config is static
|
||||||
}
|
}
|
||||||
@ -165,6 +352,8 @@ class StaticConfig extends BaseConfig {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class DatabaseConfig
|
||||||
|
*
|
||||||
* Loads the config list from a table in a given database, the table should
|
* Loads the config list from a table in a given database, the table should
|
||||||
* be called config and have the schema:
|
* be called config and have the schema:
|
||||||
*
|
*
|
||||||
@ -176,10 +365,13 @@ class StaticConfig extends BaseConfig {
|
|||||||
* \endcode
|
* \endcode
|
||||||
*/
|
*/
|
||||||
class DatabaseConfig extends BaseConfig {
|
class DatabaseConfig extends BaseConfig {
|
||||||
|
/** @var \Database|null */
|
||||||
var $database = null;
|
var $database = null;
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Load the config table from a database
|
* Load the config table from a database.
|
||||||
|
*
|
||||||
|
* @param Database $database
|
||||||
*/
|
*/
|
||||||
public function __construct(Database $database) {
|
public function __construct(Database $database) {
|
||||||
$this->database = $database;
|
$this->database = $database;
|
||||||
@ -197,8 +389,11 @@ class DatabaseConfig extends BaseConfig {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Save the current values as the new config table
|
* Save the current values as the new config table.
|
||||||
|
*
|
||||||
|
* @param null|string $name
|
||||||
|
* @return mixed|void
|
||||||
*/
|
*/
|
||||||
public function save(/*string*/ $name=null) {
|
public function save(/*string*/ $name=null) {
|
||||||
if(is_null($name)) {
|
if(is_null($name)) {
|
||||||
@ -217,7 +412,13 @@ class DatabaseConfig extends BaseConfig {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class MockConfig
|
||||||
|
*/
|
||||||
class MockConfig extends HardcodeConfig {
|
class MockConfig extends HardcodeConfig {
|
||||||
|
/**
|
||||||
|
* @param array $config
|
||||||
|
*/
|
||||||
public function __construct($config=array()) {
|
public function __construct($config=array()) {
|
||||||
$config["db_version"] = "999";
|
$config["db_version"] = "999";
|
||||||
$config["anon_id"] = "0";
|
$config["anon_id"] = "0";
|
||||||
|
@ -2,41 +2,70 @@
|
|||||||
/** @privatesection */
|
/** @privatesection */
|
||||||
// Querylet {{{
|
// Querylet {{{
|
||||||
class Querylet {
|
class Querylet {
|
||||||
var $sql;
|
/** @var string */
|
||||||
var $variables;
|
public $sql;
|
||||||
|
/** @var array */
|
||||||
|
public $variables;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $sql
|
||||||
|
* @param array $variables
|
||||||
|
*/
|
||||||
public function __construct($sql, $variables=array()) {
|
public function __construct($sql, $variables=array()) {
|
||||||
$this->sql = $sql;
|
$this->sql = $sql;
|
||||||
$this->variables = $variables;
|
$this->variables = $variables;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \Querylet $querylet
|
||||||
|
*/
|
||||||
public function append($querylet) {
|
public function append($querylet) {
|
||||||
assert(!is_null($querylet));
|
assert(!is_null($querylet));
|
||||||
$this->sql .= $querylet->sql;
|
$this->sql .= $querylet->sql;
|
||||||
$this->variables = array_merge($this->variables, $querylet->variables);
|
$this->variables = array_merge($this->variables, $querylet->variables);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $sql
|
||||||
|
*/
|
||||||
public function append_sql($sql) {
|
public function append_sql($sql) {
|
||||||
$this->sql .= $sql;
|
$this->sql .= $sql;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param mixed $var
|
||||||
|
*/
|
||||||
public function add_variable($var) {
|
public function add_variable($var) {
|
||||||
$this->variables[] = $var;
|
$this->variables[] = $var;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
class TagQuerylet {
|
|
||||||
var $tag;
|
|
||||||
var $positive;
|
|
||||||
|
|
||||||
|
class TagQuerylet {
|
||||||
|
/** @var string */
|
||||||
|
public $tag;
|
||||||
|
/** @var bool */
|
||||||
|
public $positive;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $tag
|
||||||
|
* @param bool $positive
|
||||||
|
*/
|
||||||
public function __construct($tag, $positive) {
|
public function __construct($tag, $positive) {
|
||||||
$this->tag = $tag;
|
$this->tag = $tag;
|
||||||
$this->positive = $positive;
|
$this->positive = $positive;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
class ImgQuerylet {
|
|
||||||
var $qlet;
|
|
||||||
var $positive;
|
|
||||||
|
|
||||||
|
class ImgQuerylet {
|
||||||
|
/** @var \Querylet */
|
||||||
|
public $qlet;
|
||||||
|
/** @var bool */
|
||||||
|
public $positive;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \Querylet $qlet
|
||||||
|
* @param bool $positive
|
||||||
|
*/
|
||||||
public function __construct($qlet, $positive) {
|
public function __construct($qlet, $positive) {
|
||||||
$this->qlet = $qlet;
|
$this->qlet = $qlet;
|
||||||
$this->positive = $positive;
|
$this->positive = $positive;
|
||||||
@ -45,25 +74,46 @@ class ImgQuerylet {
|
|||||||
// }}}
|
// }}}
|
||||||
// {{{ db engines
|
// {{{ db engines
|
||||||
class DBEngine {
|
class DBEngine {
|
||||||
|
/** @var null|string */
|
||||||
public $name = null;
|
public $name = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \PDO $db
|
||||||
|
*/
|
||||||
public function init($db) {}
|
public function init($db) {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $scoreql
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($scoreql) {
|
public function scoreql_to_sql($scoreql) {
|
||||||
return $scoreql;
|
return $scoreql;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function create_table_sql($name, $data) {
|
public function create_table_sql($name, $data) {
|
||||||
return 'CREATE TABLE '.$name.' ('.$data.')';
|
return 'CREATE TABLE '.$name.' ('.$data.')';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
class MySQL extends DBEngine {
|
class MySQL extends DBEngine {
|
||||||
|
/** @var string */
|
||||||
public $name = "mysql";
|
public $name = "mysql";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \PDO $db
|
||||||
|
*/
|
||||||
public function init($db) {
|
public function init($db) {
|
||||||
$db->exec("SET NAMES utf8;");
|
$db->exec("SET NAMES utf8;");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($data) {
|
public function scoreql_to_sql($data) {
|
||||||
$data = str_replace("SCORE_AIPK", "INTEGER PRIMARY KEY auto_increment", $data);
|
$data = str_replace("SCORE_AIPK", "INTEGER PRIMARY KEY auto_increment", $data);
|
||||||
$data = str_replace("SCORE_INET", "VARCHAR(45)", $data);
|
$data = str_replace("SCORE_INET", "VARCHAR(45)", $data);
|
||||||
@ -77,6 +127,11 @@ class MySQL extends DBEngine {
|
|||||||
return $data;
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function create_table_sql($name, $data) {
|
public function create_table_sql($name, $data) {
|
||||||
$data = $this->scoreql_to_sql($data);
|
$data = $this->scoreql_to_sql($data);
|
||||||
$ctes = "ENGINE=InnoDB DEFAULT CHARSET='utf8'";
|
$ctes = "ENGINE=InnoDB DEFAULT CHARSET='utf8'";
|
||||||
@ -84,12 +139,20 @@ class MySQL extends DBEngine {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
class PostgreSQL extends DBEngine {
|
class PostgreSQL extends DBEngine {
|
||||||
|
/** @var string */
|
||||||
public $name = "pgsql";
|
public $name = "pgsql";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \PDO $db
|
||||||
|
*/
|
||||||
public function init($db) {
|
public function init($db) {
|
||||||
$db->exec("SET application_name TO 'shimmie [{$_SERVER['REMOTE_ADDR']}]';");
|
$db->exec("SET application_name TO 'shimmie [{$_SERVER['REMOTE_ADDR']}]';");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($data) {
|
public function scoreql_to_sql($data) {
|
||||||
$data = str_replace("SCORE_AIPK", "SERIAL PRIMARY KEY", $data);
|
$data = str_replace("SCORE_AIPK", "SERIAL PRIMARY KEY", $data);
|
||||||
$data = str_replace("SCORE_INET", "INET", $data);
|
$data = str_replace("SCORE_INET", "INET", $data);
|
||||||
@ -103,6 +166,11 @@ class PostgreSQL extends DBEngine {
|
|||||||
return $data;
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function create_table_sql($name, $data) {
|
public function create_table_sql($name, $data) {
|
||||||
$data = $this->scoreql_to_sql($data);
|
$data = $this->scoreql_to_sql($data);
|
||||||
return 'CREATE TABLE '.$name.' ('.$data.')';
|
return 'CREATE TABLE '.$name.' ('.$data.')';
|
||||||
@ -123,8 +191,12 @@ function _concat($a, $b) { return $a . $b; }
|
|||||||
function _lower($a) { return strtolower($a); }
|
function _lower($a) { return strtolower($a); }
|
||||||
|
|
||||||
class SQLite extends DBEngine {
|
class SQLite extends DBEngine {
|
||||||
|
/** @var string */
|
||||||
public $name = "sqlite";
|
public $name = "sqlite";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \PDO $db
|
||||||
|
*/
|
||||||
public function init($db) {
|
public function init($db) {
|
||||||
ini_set('sqlite.assoc_case', 0);
|
ini_set('sqlite.assoc_case', 0);
|
||||||
$db->exec("PRAGMA foreign_keys = ON;");
|
$db->exec("PRAGMA foreign_keys = ON;");
|
||||||
@ -138,6 +210,10 @@ class SQLite extends DBEngine {
|
|||||||
$db->sqliteCreateFunction('lower', '_lower', 1);
|
$db->sqliteCreateFunction('lower', '_lower', 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($data) {
|
public function scoreql_to_sql($data) {
|
||||||
$data = str_replace("SCORE_AIPK", "INTEGER PRIMARY KEY", $data);
|
$data = str_replace("SCORE_AIPK", "INTEGER PRIMARY KEY", $data);
|
||||||
$data = str_replace("SCORE_INET", "VARCHAR(45)", $data);
|
$data = str_replace("SCORE_INET", "VARCHAR(45)", $data);
|
||||||
@ -150,6 +226,11 @@ class SQLite extends DBEngine {
|
|||||||
return $data;
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param string $data
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function create_table_sql($name, $data) {
|
public function create_table_sql($name, $data) {
|
||||||
$data = $this->scoreql_to_sql($data);
|
$data = $this->scoreql_to_sql($data);
|
||||||
$cols = array();
|
$cols = array();
|
||||||
@ -187,22 +268,38 @@ class NoCache implements CacheEngine {
|
|||||||
public function get_misses() {return 0;}
|
public function get_misses() {return 0;}
|
||||||
}
|
}
|
||||||
class MemcacheCache implements CacheEngine {
|
class MemcacheCache implements CacheEngine {
|
||||||
var $memcache=null, $hits=0, $misses=0;
|
/** @var \Memcache|null */
|
||||||
|
public $memcache=null;
|
||||||
|
/** @var int */
|
||||||
|
private $hits=0;
|
||||||
|
/** @var int */
|
||||||
|
private $misses=0;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $args
|
||||||
|
*/
|
||||||
public function __construct($args) {
|
public function __construct($args) {
|
||||||
$hp = explode(":", $args);
|
$hp = explode(":", $args);
|
||||||
if(class_exists("Memcache")) {
|
if(class_exists("Memcache")) {
|
||||||
$this->memcache = new Memcache;
|
$this->memcache = new Memcache;
|
||||||
@$this->memcache->pconnect($hp[0], $hp[1]);
|
@$this->memcache->pconnect($hp[0], $hp[1]);
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
|
print "no memcache"; exit;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $key
|
||||||
|
* @return array|bool|string
|
||||||
|
*/
|
||||||
public function get($key) {
|
public function get($key) {
|
||||||
assert(!is_null($key));
|
assert(!is_null($key));
|
||||||
if((DEBUG_CACHE === true) || (is_null(DEBUG_CACHE) && @$_GET['DEBUG_CACHE'])) {
|
|
||||||
file_put_contents("data/cache.log", "Cache lookup: $key\n", FILE_APPEND);
|
|
||||||
}
|
|
||||||
$val = $this->memcache->get($key);
|
$val = $this->memcache->get($key);
|
||||||
|
if((DEBUG_CACHE === true) || (is_null(DEBUG_CACHE) && @$_GET['DEBUG_CACHE'])) {
|
||||||
|
$hit = $val === false ? "miss" : "hit";
|
||||||
|
file_put_contents("data/cache.log", "Cache $hit: $key\n", FILE_APPEND);
|
||||||
|
}
|
||||||
if($val !== false) {
|
if($val !== false) {
|
||||||
$this->hits++;
|
$this->hits++;
|
||||||
return $val;
|
return $val;
|
||||||
@ -213,19 +310,35 @@ class MemcacheCache implements CacheEngine {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $key
|
||||||
|
* @param mixed $val
|
||||||
|
* @param int $time
|
||||||
|
*/
|
||||||
public function set($key, $val, $time=0) {
|
public function set($key, $val, $time=0) {
|
||||||
assert(!is_null($key));
|
assert(!is_null($key));
|
||||||
$this->memcache->set($key, $val, false, $time);
|
$this->memcache->set($key, $val, false, $time);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $key
|
||||||
|
*/
|
||||||
public function delete($key) {
|
public function delete($key) {
|
||||||
assert(!is_null($key));
|
assert(!is_null($key));
|
||||||
$this->memcache->delete($key);
|
$this->memcache->delete($key);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_hits() {return $this->hits;}
|
public function get_hits() {return $this->hits;}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_misses() {return $this->misses;}
|
public function get_misses() {return $this->misses;}
|
||||||
}
|
}
|
||||||
|
|
||||||
class APCCache implements CacheEngine {
|
class APCCache implements CacheEngine {
|
||||||
var $hits=0, $misses=0;
|
var $hits=0, $misses=0;
|
||||||
|
|
||||||
@ -267,25 +380,29 @@ class APCCache implements CacheEngine {
|
|||||||
*/
|
*/
|
||||||
class Database {
|
class Database {
|
||||||
/**
|
/**
|
||||||
* The PDO database connection object, for anyone who wants direct access
|
* The PDO database connection object, for anyone who wants direct access.
|
||||||
|
* @var null|PDO
|
||||||
*/
|
*/
|
||||||
private $db = null;
|
private $db = null;
|
||||||
|
public $dbtime = 0.0;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Meta info about the database engine
|
* Meta info about the database engine.
|
||||||
* @var DBEngine
|
* @var DBEngine|null
|
||||||
*/
|
*/
|
||||||
private $engine = null;
|
private $engine = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The currently active cache engine
|
* The currently active cache engine.
|
||||||
* @var CacheEngine
|
* @var CacheEngine|null
|
||||||
*/
|
*/
|
||||||
public $cache = null;
|
public $cache = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A boolean flag to track if we already have an active transaction.
|
* A boolean flag to track if we already have an active transaction.
|
||||||
* (ie: True if beginTransaction() already called)
|
* (ie: True if beginTransaction() already called)
|
||||||
|
*
|
||||||
|
* @var bool
|
||||||
*/
|
*/
|
||||||
public $transaction = false;
|
public $transaction = false;
|
||||||
|
|
||||||
@ -364,6 +481,10 @@ class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
* @throws SCoreException
|
||||||
|
*/
|
||||||
public function commit() {
|
public function commit() {
|
||||||
if(!is_null($this->db)) {
|
if(!is_null($this->db)) {
|
||||||
if ($this->transaction === true) {
|
if ($this->transaction === true) {
|
||||||
@ -376,6 +497,10 @@ class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
* @throws SCoreException
|
||||||
|
*/
|
||||||
public function rollback() {
|
public function rollback() {
|
||||||
if(!is_null($this->db)) {
|
if(!is_null($this->db)) {
|
||||||
if ($this->transaction === true) {
|
if ($this->transaction === true) {
|
||||||
@ -388,23 +513,39 @@ class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $input
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function escape($input) {
|
public function escape($input) {
|
||||||
if(is_null($this->db)) $this->connect_db();
|
if(is_null($this->db)) $this->connect_db();
|
||||||
return $this->db->Quote($input);
|
return $this->db->Quote($input);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $input
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($input) {
|
public function scoreql_to_sql($input) {
|
||||||
if(is_null($this->engine)) $this->connect_engine();
|
if(is_null($this->engine)) $this->connect_engine();
|
||||||
return $this->engine->scoreql_to_sql($input);
|
return $this->engine->scoreql_to_sql($input);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return null|string
|
||||||
|
*/
|
||||||
public function get_driver_name() {
|
public function get_driver_name() {
|
||||||
if(is_null($this->engine)) $this->connect_engine();
|
if(is_null($this->engine)) $this->connect_engine();
|
||||||
return $this->engine->name;
|
return $this->engine->name;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return an PDO resultset
|
* Execute an SQL query and return an PDO result-set.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return PDOStatement
|
||||||
|
* @throws SCoreException
|
||||||
*/
|
*/
|
||||||
public function execute($query, $args=array()) {
|
public function execute($query, $args=array()) {
|
||||||
try {
|
try {
|
||||||
@ -433,54 +574,88 @@ class Database {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return a 2D array
|
* Execute an SQL query and return a 2D array.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function get_all($query, $args=array()) {
|
public function get_all($query, $args=array()) {
|
||||||
return $this->execute($query, $args)->fetchAll();
|
$_start = microtime(true);
|
||||||
|
$data = $this->execute($query, $args)->fetchAll();
|
||||||
|
$this->dbtime += microtime(true) - $_start;
|
||||||
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return a single row
|
* Execute an SQL query and return a single row.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return mixed|null
|
||||||
*/
|
*/
|
||||||
public function get_row($query, $args=array()) {
|
public function get_row($query, $args=array()) {
|
||||||
|
$_start = microtime(true);
|
||||||
$row = $this->execute($query, $args)->fetch();
|
$row = $this->execute($query, $args)->fetch();
|
||||||
|
$this->dbtime += microtime(true) - $_start;
|
||||||
return $row ? $row : null;
|
return $row ? $row : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return the first column of each row
|
* Execute an SQL query and return the first column of each row.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function get_col($query, $args=array()) {
|
public function get_col($query, $args=array()) {
|
||||||
|
$_start = microtime(true);
|
||||||
$stmt = $this->execute($query, $args);
|
$stmt = $this->execute($query, $args);
|
||||||
$res = array();
|
$res = array();
|
||||||
foreach($stmt as $row) {
|
foreach($stmt as $row) {
|
||||||
$res[] = $row[0];
|
$res[] = $row[0];
|
||||||
}
|
}
|
||||||
|
$this->dbtime += microtime(true) - $_start;
|
||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return the the first row => the second rown
|
* Execute an SQL query and return the the first row => the second rown.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function get_pairs($query, $args=array()) {
|
public function get_pairs($query, $args=array()) {
|
||||||
|
$_start = microtime(true);
|
||||||
$stmt = $this->execute($query, $args);
|
$stmt = $this->execute($query, $args);
|
||||||
$res = array();
|
$res = array();
|
||||||
foreach($stmt as $row) {
|
foreach($stmt as $row) {
|
||||||
$res[$row[0]] = $row[1];
|
$res[$row[0]] = $row[1];
|
||||||
}
|
}
|
||||||
|
$this->dbtime += microtime(true) - $_start;
|
||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute an SQL query and return a single value
|
* Execute an SQL query and return a single value.
|
||||||
|
*
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return mixed
|
||||||
*/
|
*/
|
||||||
public function get_one($query, $args=array()) {
|
public function get_one($query, $args=array()) {
|
||||||
|
$_start = microtime(true);
|
||||||
$row = $this->execute($query, $args)->fetch();
|
$row = $this->execute($query, $args)->fetch();
|
||||||
|
$this->dbtime += microtime(true) - $_start;
|
||||||
return $row[0];
|
return $row[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* get the ID of the last inserted row
|
* Get the ID of the last inserted row.
|
||||||
|
*
|
||||||
|
* @param string|null $seq
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function get_last_insert_id($seq) {
|
public function get_last_insert_id($seq) {
|
||||||
if($this->engine->name == "pgsql") {
|
if($this->engine->name == "pgsql") {
|
||||||
@ -492,15 +667,20 @@ class Database {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a table from pseudo-SQL
|
* Create a table from pseudo-SQL.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param string $data
|
||||||
*/
|
*/
|
||||||
public function create_table($name, $data) {
|
public function create_table($name, $data) {
|
||||||
if(is_null($this->engine)) $this->connect_engine();
|
if(is_null($this->engine)) { $this->connect_engine(); }
|
||||||
$this->execute($this->engine->create_table_sql($name, $data));
|
$this->execute($this->engine->create_table_sql($name, $data));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the number of tables present in the current database.
|
* Returns the number of tables present in the current database.
|
||||||
|
*
|
||||||
|
* @return int|null
|
||||||
*/
|
*/
|
||||||
public function count_tables() {
|
public function count_tables() {
|
||||||
if(is_null($this->db) || is_null($this->engine)) $this->connect_db();
|
if(is_null($this->db) || is_null($this->engine)) $this->connect_db();
|
||||||
@ -525,14 +705,26 @@ class Database {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class MockDatabase extends Database {
|
class MockDatabase extends Database {
|
||||||
|
/** @var int */
|
||||||
var $query_id = 0;
|
var $query_id = 0;
|
||||||
|
/** @var array */
|
||||||
var $responses = array();
|
var $responses = array();
|
||||||
|
/** @var \NoCache|null */
|
||||||
var $cache = null;
|
var $cache = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $responses
|
||||||
|
*/
|
||||||
public function __construct($responses = array()) {
|
public function __construct($responses = array()) {
|
||||||
$this->cache = new NoCache();
|
$this->cache = new NoCache();
|
||||||
$this->responses = $responses;
|
$this->responses = $responses;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $params
|
||||||
|
* @return PDOStatement
|
||||||
|
*/
|
||||||
public function execute($query, $params=array()) {
|
public function execute($query, $params=array()) {
|
||||||
log_debug("mock-database",
|
log_debug("mock-database",
|
||||||
"QUERY: " . $query .
|
"QUERY: " . $query .
|
||||||
@ -542,13 +734,51 @@ class MockDatabase extends Database {
|
|||||||
return $this->responses[$this->query_id++];
|
return $this->responses[$this->query_id++];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array|PDOStatement
|
||||||
|
*/
|
||||||
public function get_all($query, $args=array()) {return $this->execute($query, $args);}
|
public function get_all($query, $args=array()) {return $this->execute($query, $args);}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return mixed|null|PDOStatement
|
||||||
|
*/
|
||||||
public function get_row($query, $args=array()) {return $this->execute($query, $args);}
|
public function get_row($query, $args=array()) {return $this->execute($query, $args);}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array|PDOStatement
|
||||||
|
*/
|
||||||
public function get_col($query, $args=array()) {return $this->execute($query, $args);}
|
public function get_col($query, $args=array()) {return $this->execute($query, $args);}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return array|PDOStatement
|
||||||
|
*/
|
||||||
public function get_pairs($query, $args=array()) {return $this->execute($query, $args);}
|
public function get_pairs($query, $args=array()) {return $this->execute($query, $args);}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $query
|
||||||
|
* @param array $args
|
||||||
|
* @return mixed|PDOStatement
|
||||||
|
*/
|
||||||
public function get_one($query, $args=array()) {return $this->execute($query, $args);}
|
public function get_one($query, $args=array()) {return $this->execute($query, $args);}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param null|string $seq
|
||||||
|
* @return int|string
|
||||||
|
*/
|
||||||
public function get_last_insert_id($seq) {return $this->query_id;}
|
public function get_last_insert_id($seq) {return $this->query_id;}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $sql
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function scoreql_to_sql($sql) {return $sql;}
|
public function scoreql_to_sql($sql) {return $sql;}
|
||||||
public function create_table($name, $def) {}
|
public function create_table($name, $def) {}
|
||||||
public function connect_engine() {}
|
public function connect_engine() {}
|
||||||
|
@ -1,21 +1,40 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class Email
|
||||||
|
*
|
||||||
|
* A generic email.
|
||||||
|
*/
|
||||||
class Email {
|
class Email {
|
||||||
/**
|
/** @var string */
|
||||||
* A generic email.
|
|
||||||
*/
|
|
||||||
public $to;
|
public $to;
|
||||||
|
/** @var string */
|
||||||
public $subject;
|
public $subject;
|
||||||
|
/** @var string */
|
||||||
public $header;
|
public $header;
|
||||||
|
/** @var null|string */
|
||||||
public $style;
|
public $style;
|
||||||
|
/** @var null|string */
|
||||||
public $header_img;
|
public $header_img;
|
||||||
|
/** @var null|string */
|
||||||
public $sitename;
|
public $sitename;
|
||||||
|
/** @var null|string */
|
||||||
public $sitedomain;
|
public $sitedomain;
|
||||||
|
/** @var null|string */
|
||||||
public $siteemail;
|
public $siteemail;
|
||||||
|
/** @var string */
|
||||||
public $date;
|
public $date;
|
||||||
|
/** @var string */
|
||||||
public $body;
|
public $body;
|
||||||
|
/** @var null|string */
|
||||||
public $footer;
|
public $footer;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $to
|
||||||
|
* @param string $subject
|
||||||
|
* @param string $header
|
||||||
|
* @param string $body
|
||||||
|
*/
|
||||||
public function __construct($to, $subject, $header, $body) {
|
public function __construct($to, $subject, $header, $body) {
|
||||||
global $config;
|
global $config;
|
||||||
$this->to = $to;
|
$this->to = $to;
|
||||||
|
@ -26,8 +26,19 @@ class InitExtEvent extends Event {}
|
|||||||
* $event->get_arg(0) = "42"
|
* $event->get_arg(0) = "42"
|
||||||
*/
|
*/
|
||||||
class PageRequestEvent extends Event {
|
class PageRequestEvent extends Event {
|
||||||
|
/**
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
public $args;
|
public $args;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var int
|
||||||
|
*/
|
||||||
public $arg_count;
|
public $arg_count;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var int
|
||||||
|
*/
|
||||||
public $part_count;
|
public $part_count;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -90,7 +101,7 @@ class PageRequestEvent extends Event {
|
|||||||
* Get the n th argument of the page request (if it exists.)
|
* Get the n th argument of the page request (if it exists.)
|
||||||
*
|
*
|
||||||
* @param int $n
|
* @param int $n
|
||||||
* @return string|null The argmuent (string) or NULL
|
* @return string|null The argument (string) or NULL
|
||||||
*/
|
*/
|
||||||
public function get_arg(/*int*/ $n) {
|
public function get_arg(/*int*/ $n) {
|
||||||
$offset = $this->part_count + $n;
|
$offset = $this->part_count + $n;
|
||||||
@ -154,9 +165,19 @@ class PageRequestEvent extends Event {
|
|||||||
* Sent when index.php is called from the command line
|
* Sent when index.php is called from the command line
|
||||||
*/
|
*/
|
||||||
class CommandEvent extends Event {
|
class CommandEvent extends Event {
|
||||||
|
/**
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
public $cmd = "help";
|
public $cmd = "help";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
public $args = array();
|
public $args = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string[] $args
|
||||||
|
*/
|
||||||
public function __construct(/*array(string)*/ $args) {
|
public function __construct(/*array(string)*/ $args) {
|
||||||
global $user;
|
global $user;
|
||||||
|
|
||||||
@ -215,19 +236,28 @@ class CommandEvent extends Event {
|
|||||||
class TextFormattingEvent extends Event {
|
class TextFormattingEvent extends Event {
|
||||||
/**
|
/**
|
||||||
* For reference
|
* For reference
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
*/
|
*/
|
||||||
var $original;
|
public $original;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* with formatting applied
|
* with formatting applied
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
*/
|
*/
|
||||||
var $formatted;
|
public $formatted;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* with formatting removed
|
* with formatting removed
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
*/
|
*/
|
||||||
var $stripped;
|
public $stripped;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
*/
|
||||||
public function __construct(/*string*/ $text) {
|
public function __construct(/*string*/ $text) {
|
||||||
$h_text = html_escape(trim($text));
|
$h_text = html_escape(trim($text));
|
||||||
$this->original = $h_text;
|
$this->original = $h_text;
|
||||||
@ -244,36 +274,44 @@ class LogEvent extends Event {
|
|||||||
/**
|
/**
|
||||||
* a category, normally the extension name
|
* a category, normally the extension name
|
||||||
*
|
*
|
||||||
* @return string
|
* @var string
|
||||||
*/
|
*/
|
||||||
var $section;
|
public $section;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* See python...
|
* See python...
|
||||||
*
|
*
|
||||||
* @return int
|
* @var int
|
||||||
*/
|
*/
|
||||||
var $priority = 0;
|
public $priority = 0;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Free text to be logged
|
* Free text to be logged
|
||||||
*
|
*
|
||||||
* @return text
|
* @var string
|
||||||
*/
|
*/
|
||||||
var $message;
|
public $message;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The time that the event was created
|
* The time that the event was created
|
||||||
*
|
*
|
||||||
* @return int
|
* @var int
|
||||||
*/
|
*/
|
||||||
var $time;
|
public $time;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Extra data to be held separate
|
* Extra data to be held separate
|
||||||
|
*
|
||||||
|
* @var array
|
||||||
*/
|
*/
|
||||||
var $args;
|
public $args;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $section
|
||||||
|
* @param int $priority
|
||||||
|
* @param string $message
|
||||||
|
* @param array $args
|
||||||
|
*/
|
||||||
public function __construct($section, $priority, $message, $args) {
|
public function __construct($section, $priority, $message, $args) {
|
||||||
$this->section = $section;
|
$this->section = $section;
|
||||||
$this->priority = $priority;
|
$this->priority = $priority;
|
||||||
|
@ -1,11 +1,16 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A base exception to be caught by the upper levels
|
* Class SCoreException
|
||||||
|
*
|
||||||
|
* A base exception to be caught by the upper levels.
|
||||||
*/
|
*/
|
||||||
class SCoreException extends Exception {}
|
class SCoreException extends Exception {}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A fairly common, generic exception
|
* Class PermissionDeniedException
|
||||||
|
*
|
||||||
|
* A fairly common, generic exception.
|
||||||
*/
|
*/
|
||||||
class PermissionDeniedException extends SCoreException {}
|
class PermissionDeniedException extends SCoreException {}
|
||||||
|
|
||||||
|
@ -70,6 +70,8 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class Extension
|
||||||
|
*
|
||||||
* send_event(BlahEvent()) -> onBlah($event)
|
* send_event(BlahEvent()) -> onBlah($event)
|
||||||
*
|
*
|
||||||
* Also loads the theme object into $this->theme if available
|
* Also loads the theme object into $this->theme if available
|
||||||
@ -96,7 +98,11 @@ abstract class Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find the theme object for a given extension
|
* Find the theme object for a given extension.
|
||||||
|
*
|
||||||
|
* @param Extension $class
|
||||||
|
* @param bool $fatal
|
||||||
|
* @return bool
|
||||||
*/
|
*/
|
||||||
private function get_theme_object(Extension $class, $fatal=true) {
|
private function get_theme_object(Extension $class, $fatal=true) {
|
||||||
$base = get_class($class);
|
$base = get_class($class);
|
||||||
@ -114,7 +120,9 @@ abstract class Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Override this to change the priority of the extension,
|
* Override this to change the priority of the extension,
|
||||||
* lower numbered ones will recieve events first
|
* lower numbered ones will recieve events first.
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
public function get_priority() {
|
public function get_priority() {
|
||||||
return 50;
|
return 50;
|
||||||
@ -122,23 +130,43 @@ abstract class Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Several extensions have this in common, make a common API
|
* Class FormatterExtension
|
||||||
|
*
|
||||||
|
* Several extensions have this in common, make a common API.
|
||||||
*/
|
*/
|
||||||
abstract class FormatterExtension extends Extension {
|
abstract class FormatterExtension extends Extension {
|
||||||
|
/**
|
||||||
|
* @param TextFormattingEvent $event
|
||||||
|
*/
|
||||||
public function onTextFormatting(TextFormattingEvent $event) {
|
public function onTextFormatting(TextFormattingEvent $event) {
|
||||||
$event->formatted = $this->format($event->formatted);
|
$event->formatted = $this->format($event->formatted);
|
||||||
$event->stripped = $this->strip($event->stripped);
|
$event->stripped = $this->strip($event->stripped);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
abstract public function format(/*string*/ $text);
|
abstract public function format(/*string*/ $text);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
abstract public function strip(/*string*/ $text);
|
abstract public function strip(/*string*/ $text);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class DataHandlerExtension
|
||||||
|
*
|
||||||
* This too is a common class of extension with many methods in common,
|
* This too is a common class of extension with many methods in common,
|
||||||
* so we have a base class to extend from
|
* so we have a base class to extend from.
|
||||||
*/
|
*/
|
||||||
abstract class DataHandlerExtension extends Extension {
|
abstract class DataHandlerExtension extends Extension {
|
||||||
|
/**
|
||||||
|
* @param DataUploadEvent $event
|
||||||
|
* @throws UploadException
|
||||||
|
*/
|
||||||
public function onDataUpload(DataUploadEvent $event) {
|
public function onDataUpload(DataUploadEvent $event) {
|
||||||
$supported_ext = $this->supported_ext($event->type);
|
$supported_ext = $this->supported_ext($event->type);
|
||||||
$check_contents = $this->check_contents($event->tmpname);
|
$check_contents = $this->check_contents($event->tmpname);
|
||||||
@ -202,6 +230,9 @@ abstract class DataHandlerExtension extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param ThumbnailGenerationEvent $event
|
||||||
|
*/
|
||||||
public function onThumbnailGeneration(ThumbnailGenerationEvent $event) {
|
public function onThumbnailGeneration(ThumbnailGenerationEvent $event) {
|
||||||
if($this->supported_ext($event->type)) {
|
if($this->supported_ext($event->type)) {
|
||||||
if (method_exists($this, 'create_thumb_force') && $event->force == true) {
|
if (method_exists($this, 'create_thumb_force') && $event->force == true) {
|
||||||
@ -213,6 +244,9 @@ abstract class DataHandlerExtension extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param DisplayingImageEvent $event
|
||||||
|
*/
|
||||||
public function onDisplayingImage(DisplayingImageEvent $event) {
|
public function onDisplayingImage(DisplayingImageEvent $event) {
|
||||||
global $page;
|
global $page;
|
||||||
if($this->supported_ext($event->image->ext)) {
|
if($this->supported_ext($event->image->ext)) {
|
||||||
@ -229,9 +263,29 @@ abstract class DataHandlerExtension extends Extension {
|
|||||||
protected function setup() {}
|
protected function setup() {}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
abstract protected function supported_ext($ext);
|
abstract protected function supported_ext($ext);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $tmpname
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
abstract protected function check_contents($tmpname);
|
abstract protected function check_contents($tmpname);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param array $metadata
|
||||||
|
* @return Image|null
|
||||||
|
*/
|
||||||
abstract protected function create_image_from_data($filename, $metadata);
|
abstract protected function create_image_from_data($filename, $metadata);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
abstract protected function create_thumb($hash);
|
abstract protected function create_thumb($hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -31,15 +31,38 @@ $order_sql = null; // this feels ugly
|
|||||||
require_once "lib/flexihash.php";
|
require_once "lib/flexihash.php";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An object representing an entry in the images table. As of 2.2, this no
|
* Class Image
|
||||||
* longer necessarily represents an image per se, but could be a video,
|
*
|
||||||
* sound file, or any other supported upload type.
|
* An object representing an entry in the images table.
|
||||||
|
*
|
||||||
|
* As of 2.2, this no longer necessarily represents an
|
||||||
|
* image per se, but could be a video, sound file, or any
|
||||||
|
* other supported upload type.
|
||||||
*/
|
*/
|
||||||
class Image {
|
class Image {
|
||||||
|
/** @var null|int */
|
||||||
public $id = null;
|
public $id = null;
|
||||||
public $height, $width;
|
|
||||||
public $hash, $filesize;
|
/** @var int */
|
||||||
public $filename, $ext;
|
public $height;
|
||||||
|
|
||||||
|
/** @var int */
|
||||||
|
public $width;
|
||||||
|
|
||||||
|
/** @var string */
|
||||||
|
public $hash;
|
||||||
|
|
||||||
|
public $filesize;
|
||||||
|
|
||||||
|
/** @var string */
|
||||||
|
public $filename;
|
||||||
|
|
||||||
|
/** @var string */
|
||||||
|
public $ext;
|
||||||
|
|
||||||
|
/** @var string[]|null */
|
||||||
|
public $tag_array;
|
||||||
|
|
||||||
public $owner_id, $owner_ip;
|
public $owner_id, $owner_ip;
|
||||||
public $posted, $posted_timestamp;
|
public $posted, $posted_timestamp;
|
||||||
public $source;
|
public $source;
|
||||||
@ -47,7 +70,9 @@ class Image {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* One will very rarely construct an image directly, more common
|
* One will very rarely construct an image directly, more common
|
||||||
* would be to use Image::by_id, Image::by_hash, etc
|
* would be to use Image::by_id, Image::by_hash, etc.
|
||||||
|
*
|
||||||
|
* @param null|mixed $row
|
||||||
*/
|
*/
|
||||||
public function __construct($row=null) {
|
public function __construct($row=null) {
|
||||||
if(!is_null($row)) {
|
if(!is_null($row)) {
|
||||||
@ -66,7 +91,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find an image by ID
|
* Find an image by ID.
|
||||||
*
|
*
|
||||||
* @param int $id
|
* @param int $id
|
||||||
* @return Image
|
* @return Image
|
||||||
@ -79,7 +104,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find an image by hash
|
* Find an image by hash.
|
||||||
*
|
*
|
||||||
* @param string $hash
|
* @param string $hash
|
||||||
* @return Image
|
* @return Image
|
||||||
@ -92,9 +117,9 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Pick a random image out of a set
|
* Pick a random image out of a set.
|
||||||
*
|
*
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @return Image
|
* @return Image
|
||||||
*/
|
*/
|
||||||
public static function by_random($tags=array()) {
|
public static function by_random($tags=array()) {
|
||||||
@ -112,9 +137,9 @@ class Image {
|
|||||||
*
|
*
|
||||||
* @param int $start
|
* @param int $start
|
||||||
* @param int $limit
|
* @param int $limit
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @throws SCoreException
|
* @throws SCoreException
|
||||||
* @return Array
|
* @return Image[]
|
||||||
*/
|
*/
|
||||||
public static function find_images(/*int*/ $start, /*int*/ $limit, $tags=array()) {
|
public static function find_images(/*int*/ $start, /*int*/ $limit, $tags=array()) {
|
||||||
assert(is_numeric($start));
|
assert(is_numeric($start));
|
||||||
@ -153,7 +178,7 @@ class Image {
|
|||||||
/**
|
/**
|
||||||
* Count the number of image results for a given search
|
* Count the number of image results for a given search
|
||||||
*
|
*
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @return mixed
|
* @return mixed
|
||||||
*/
|
*/
|
||||||
public static function count_images($tags=array()) {
|
public static function count_images($tags=array()) {
|
||||||
@ -185,7 +210,7 @@ class Image {
|
|||||||
/**
|
/**
|
||||||
* Count the number of pages for a given search
|
* Count the number of pages for a given search
|
||||||
*
|
*
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @return float
|
* @return float
|
||||||
*/
|
*/
|
||||||
public static function count_pages($tags=array()) {
|
public static function count_pages($tags=array()) {
|
||||||
@ -205,7 +230,7 @@ class Image {
|
|||||||
* Rather than simply $this_id + 1, one must take into account
|
* Rather than simply $this_id + 1, one must take into account
|
||||||
* deleted images and search queries
|
* deleted images and search queries
|
||||||
*
|
*
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @param bool $next
|
* @param bool $next
|
||||||
* @return Image
|
* @return Image
|
||||||
*/
|
*/
|
||||||
@ -239,7 +264,7 @@ class Image {
|
|||||||
/**
|
/**
|
||||||
* The reverse of get_next
|
* The reverse of get_next
|
||||||
*
|
*
|
||||||
* @param array $tags
|
* @param string[] $tags
|
||||||
* @return Image
|
* @return Image
|
||||||
*/
|
*/
|
||||||
public function get_prev($tags=array()) {
|
public function get_prev($tags=array()) {
|
||||||
@ -269,7 +294,9 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get this image's tags as an array
|
* Get this image's tags as an array.
|
||||||
|
*
|
||||||
|
* @return string[]
|
||||||
*/
|
*/
|
||||||
public function get_tag_array() {
|
public function get_tag_array() {
|
||||||
global $database;
|
global $database;
|
||||||
@ -349,7 +376,7 @@ class Image {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the tooltip for this image, formatted according to the
|
* Get the tooltip for this image, formatted according to the
|
||||||
* configured template
|
* configured template.
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -378,7 +405,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Figure out where the full size image is on disk
|
* Figure out where the full size image is on disk.
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -387,7 +414,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Figure out where the thumbnail is on disk
|
* Figure out where the thumbnail is on disk.
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -396,7 +423,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the original filename
|
* Get the original filename.
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -405,7 +432,7 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the image's mime type
|
* Get the image's mime type.
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -480,7 +507,9 @@ class Image {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the tags for this image
|
* Set the tags for this image.
|
||||||
|
*
|
||||||
|
* @param string[] $tags
|
||||||
*/
|
*/
|
||||||
public function set_tags($tags) {
|
public function set_tags($tags) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -505,6 +534,11 @@ class Image {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(mb_strlen($tag, 'UTF-8') > 255){
|
||||||
|
flash_message("The tag below is longer than 255 characters, please use a shorter tag.\n$tag\n");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
$id = $database->get_one(
|
$id = $database->get_one(
|
||||||
$database->scoreql_to_sql(
|
$database->scoreql_to_sql(
|
||||||
"SELECT id FROM tags WHERE SCORE_STRNORM(tag) = SCORE_STRNORM(:tag)"
|
"SELECT id FROM tags WHERE SCORE_STRNORM(tag) = SCORE_STRNORM(:tag)"
|
||||||
@ -533,7 +567,7 @@ class Image {
|
|||||||
array("tag"=>$tag));
|
array("tag"=>$tag));
|
||||||
}
|
}
|
||||||
|
|
||||||
log_info("core_image", "Tags for Image #{$this->id} set to: ".implode(" ", $tags), false, array("image_id" => $this->id));
|
log_info("core_image", "Tags for Image #{$this->id} set to: ".implode(" ", $tags), null, array("image_id" => $this->id));
|
||||||
$database->cache->delete("image-{$this->id}-tags");
|
$database->cache->delete("image-{$this->id}-tags");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -564,7 +598,7 @@ class Image {
|
|||||||
/**
|
/**
|
||||||
* Someone please explain this
|
* Someone please explain this
|
||||||
*
|
*
|
||||||
* @param $tmpl
|
* @param string $tmpl
|
||||||
* @param string $_escape
|
* @param string $_escape
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
@ -637,6 +671,10 @@ class Image {
|
|||||||
return $tmpl;
|
return $tmpl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string[] $terms
|
||||||
|
* @return \Querylet
|
||||||
|
*/
|
||||||
private static function build_search_querylet($terms) {
|
private static function build_search_querylet($terms) {
|
||||||
assert(is_array($terms));
|
assert(is_array($terms));
|
||||||
global $database;
|
global $database;
|
||||||
@ -666,6 +704,9 @@ class Image {
|
|||||||
* C) Runs really slow on bad databases:
|
* C) Runs really slow on bad databases:
|
||||||
* All the subqueries are executed every time for every row in the
|
* All the subqueries are executed every time for every row in the
|
||||||
* images table. Yes, MySQL does suck this much.
|
* images table. Yes, MySQL does suck this much.
|
||||||
|
*
|
||||||
|
* @param string[] $terms
|
||||||
|
* @return \Querylet
|
||||||
*/
|
*/
|
||||||
private static function build_accurate_search_querylet($terms) {
|
private static function build_accurate_search_querylet($terms) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -932,16 +973,22 @@ class Image {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// more than one positive tag, or more than zero negative tags
|
// more than one positive tag, and zero or more negative tags
|
||||||
else {
|
else if($positive_tag_count >= 1) {
|
||||||
$tag_id_array = array();
|
$tag_id_array = array();
|
||||||
$tags_ok = true;
|
$tags_ok = true;
|
||||||
|
|
||||||
|
$x = 0;
|
||||||
foreach($tag_search->variables as $tag) {
|
foreach($tag_search->variables as $tag) {
|
||||||
$tag_ids = $database->get_col("SELECT id FROM tags WHERE tag LIKE :tag", array("tag"=>$tag));
|
$tag_ids = $database->get_col("SELECT id FROM tags WHERE tag LIKE :tag", array("tag"=>$tag));
|
||||||
$tag_id_array = array_merge($tag_id_array, $tag_ids);
|
$tag_id_array = array_merge($tag_id_array, $tag_ids);
|
||||||
$tags_ok = count($tag_ids) > 0;
|
|
||||||
|
$tags_ok = count($tag_ids) > 0 || !$tag_querylets[$x]->positive;
|
||||||
if(!$tags_ok) break;
|
if(!$tags_ok) break;
|
||||||
|
|
||||||
|
$x++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if($tags_ok) {
|
if($tags_ok) {
|
||||||
$tag_id_list = join(', ', $tag_id_array);
|
$tag_id_list = join(', ', $tag_id_array);
|
||||||
|
|
||||||
@ -977,15 +1024,27 @@ class Image {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//zero positive tags and one or more negative tags
|
||||||
|
//TODO: This isn't currently implemented. SEE: https://github.com/shish/shimmie2/issues/66
|
||||||
|
else{
|
||||||
|
$query = new Querylet("
|
||||||
|
SELECT images.*
|
||||||
|
FROM images
|
||||||
|
WHERE 1=0
|
||||||
|
");
|
||||||
|
}
|
||||||
$tag_n = 0;
|
$tag_n = 0;
|
||||||
return $query;
|
return $query;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class Tag
|
||||||
|
*
|
||||||
* A class for organising the tag related functions.
|
* A class for organising the tag related functions.
|
||||||
*
|
*
|
||||||
* All the methods are static, one should never actually use a tag object.
|
* All the methods are static, one should never actually use a tag object.
|
||||||
|
*
|
||||||
*/
|
*/
|
||||||
class Tag {
|
class Tag {
|
||||||
/**
|
/**
|
||||||
@ -1003,7 +1062,11 @@ class Tag {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Turn any string or array into a valid tag array
|
* Turn any string or array into a valid tag array.
|
||||||
|
*
|
||||||
|
* @param string|string[] $tags
|
||||||
|
* @param bool $tagme
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
public static function explode($tags, $tagme=true) {
|
public static function explode($tags, $tagme=true) {
|
||||||
assert(is_string($tags) || is_array($tags));
|
assert(is_string($tags) || is_array($tags));
|
||||||
@ -1033,7 +1096,7 @@ class Tag {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param $tags
|
* @param string|string[] $tags
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public static function implode($tags) {
|
public static function implode($tags) {
|
||||||
@ -1073,6 +1136,10 @@ class Tag {
|
|||||||
return $negative ? "-$newtag" : $newtag;
|
return $negative ? "-$newtag" : $newtag;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $tag
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public static function resolve_wildcard($tag) {
|
public static function resolve_wildcard($tag) {
|
||||||
// if there is no wildcard, return the tag
|
// if there is no wildcard, return the tag
|
||||||
if(strpos($tag, "*") === false) {
|
if(strpos($tag, "*") === false) {
|
||||||
@ -1102,8 +1169,8 @@ class Tag {
|
|||||||
/**
|
/**
|
||||||
* This function takes a list (array) of tags and changes any tags that have aliases
|
* This function takes a list (array) of tags and changes any tags that have aliases
|
||||||
*
|
*
|
||||||
* @param array $tags Array of tags
|
* @param string[] $tags Array of tags
|
||||||
* @return array of tags
|
* @return array
|
||||||
*/
|
*/
|
||||||
public static function resolve_aliases($tags) {
|
public static function resolve_aliases($tags) {
|
||||||
assert(is_array($tags));
|
assert(is_array($tags));
|
||||||
@ -1139,7 +1206,11 @@ class Tag {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Move a file from PHP's temporary area into shimmie's image storage
|
* Move a file from PHP's temporary area into shimmie's image storage
|
||||||
* hierarchy, or throw an exception trying
|
* hierarchy, or throw an exception trying.
|
||||||
|
*
|
||||||
|
* @param DataUploadEvent $event
|
||||||
|
* @return bool
|
||||||
|
* @throws UploadException
|
||||||
*/
|
*/
|
||||||
function move_upload_to_archive(DataUploadEvent $event) {
|
function move_upload_to_archive(DataUploadEvent $event) {
|
||||||
$target = warehouse_path("images", $event->hash);
|
$target = warehouse_path("images", $event->hash);
|
||||||
|
@ -28,28 +28,32 @@
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class Page
|
||||||
|
*
|
||||||
* A data structure for holding all the bits of data that make up a page.
|
* A data structure for holding all the bits of data that make up a page.
|
||||||
*
|
*
|
||||||
* The various extensions all add whatever they want to this structure,
|
* The various extensions all add whatever they want to this structure,
|
||||||
* then Layout turns it into HTML
|
* then Layout turns it into HTML.
|
||||||
*/
|
*/
|
||||||
class Page {
|
class Page {
|
||||||
/** @name Overall */
|
/** @name Overall */
|
||||||
//@{
|
//@{
|
||||||
/** @private */
|
/** @var string */
|
||||||
var $mode = "page";
|
public $mode = "page";
|
||||||
/** @private */
|
/** @var string */
|
||||||
var $type = "text/html; charset=utf-8";
|
public $type = "text/html; charset=utf-8";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set what this page should do; "page", "data", or "redirect".
|
* Set what this page should do; "page", "data", or "redirect".
|
||||||
|
* @param string $mode
|
||||||
*/
|
*/
|
||||||
public function set_mode($mode) {
|
public function set_mode($mode) {
|
||||||
$this->mode = $mode;
|
$this->mode = $mode;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the page's MIME type
|
* Set the page's MIME type.
|
||||||
|
* @param string $type
|
||||||
*/
|
*/
|
||||||
public function set_type($type) {
|
public function set_type($type) {
|
||||||
$this->type = $type;
|
$this->type = $type;
|
||||||
@ -61,20 +65,23 @@ class Page {
|
|||||||
/** @name "data" mode */
|
/** @name "data" mode */
|
||||||
//@{
|
//@{
|
||||||
|
|
||||||
/** @private */
|
/** @var string */
|
||||||
var $data = "";
|
private $data = "";
|
||||||
/** @private */
|
|
||||||
var $filename = null;
|
/** @var string */
|
||||||
|
private $filename = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the raw data to be sent
|
* Set the raw data to be sent.
|
||||||
|
* @param string $data
|
||||||
*/
|
*/
|
||||||
public function set_data($data) {
|
public function set_data($data) {
|
||||||
$this->data = $data;
|
$this->data = $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the recommended download filename
|
* Set the recommended download filename.
|
||||||
|
* @param string $filename
|
||||||
*/
|
*/
|
||||||
public function set_filename($filename) {
|
public function set_filename($filename) {
|
||||||
$this->filename = $filename;
|
$this->filename = $filename;
|
||||||
@ -86,12 +93,13 @@ class Page {
|
|||||||
/** @name "redirect" mode */
|
/** @name "redirect" mode */
|
||||||
//@{
|
//@{
|
||||||
|
|
||||||
/** @private */
|
/** @var string */
|
||||||
var $redirect = "";
|
private $redirect = "";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the URL to redirect to (remember to use make_link() if linking
|
* Set the URL to redirect to (remember to use make_link() if linking
|
||||||
* to a page in the same site)
|
* to a page in the same site).
|
||||||
|
* @param string $redirect
|
||||||
*/
|
*/
|
||||||
public function set_redirect($redirect) {
|
public function set_redirect($redirect) {
|
||||||
$this->redirect = $redirect;
|
$this->redirect = $redirect;
|
||||||
@ -103,55 +111,75 @@ class Page {
|
|||||||
/** @name "page" mode */
|
/** @name "page" mode */
|
||||||
//@{
|
//@{
|
||||||
|
|
||||||
/** @privatesection */
|
/** @var string */
|
||||||
var $title = "";
|
public $title = "";
|
||||||
var $heading = "";
|
|
||||||
var $subheading = "";
|
/** @var string */
|
||||||
var $quicknav = "";
|
public $heading = "";
|
||||||
var $html_headers = array();
|
|
||||||
var $http_headers = array();
|
/** @var string */
|
||||||
var $blocks = array();
|
public $subheading = "";
|
||||||
/** @publicsection */
|
|
||||||
|
/** @var string */
|
||||||
|
public $quicknav = "";
|
||||||
|
|
||||||
|
/** @var string[] */
|
||||||
|
public $html_headers = array();
|
||||||
|
|
||||||
|
/** @var string[] */
|
||||||
|
public $http_headers = array();
|
||||||
|
|
||||||
|
/** @var Block[] */
|
||||||
|
public $blocks = array();
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the window title
|
* Set the window title.
|
||||||
|
* @param string $title
|
||||||
*/
|
*/
|
||||||
public function set_title($title) {
|
public function set_title($title) {
|
||||||
$this->title = $title;
|
$this->title = $title;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the main heading
|
* Set the main heading.
|
||||||
|
* @param string $heading
|
||||||
*/
|
*/
|
||||||
public function set_heading($heading) {
|
public function set_heading($heading) {
|
||||||
$this->heading = $heading;
|
$this->heading = $heading;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the sub heading
|
* Set the sub heading.
|
||||||
|
* @param string $subheading
|
||||||
*/
|
*/
|
||||||
public function set_subheading($subheading) {
|
public function set_subheading($subheading) {
|
||||||
$this->subheading = $subheading;
|
$this->subheading = $subheading;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a line to the HTML head section
|
* Add a line to the HTML head section.
|
||||||
|
* @param string $line
|
||||||
|
* @param int $position
|
||||||
*/
|
*/
|
||||||
public function add_html_header($line, $position=50) {
|
public function add_html_header($line, $position=50) {
|
||||||
while(isset($this->html_headers[$position])) $position++;
|
while(isset($this->html_headers[$position])) $position++;
|
||||||
$this->html_headers[$position] = $line;
|
$this->html_headers[$position] = $line;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a http header to be sent to the client.
|
* Add a http header to be sent to the client.
|
||||||
|
* @param string $line
|
||||||
|
* @param int $position
|
||||||
*/
|
*/
|
||||||
public function add_http_header($line, $position=50) {
|
public function add_http_header($line, $position=50) {
|
||||||
while(isset($this->http_headers[$position])) $position++;
|
while(isset($this->http_headers[$position])) $position++;
|
||||||
$this->http_headers[$position] = $line;
|
$this->http_headers[$position] = $line;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all the HTML headers that are currently set and return as a string.
|
* Get all the HTML headers that are currently set and return as a string.
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function get_all_html_headers() {
|
public function get_all_html_headers() {
|
||||||
$data = '';
|
$data = '';
|
||||||
@ -162,14 +190,15 @@ class Page {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Removes all currently set HTML headers. (Be careful..)
|
* Removes all currently set HTML headers (Be careful..).
|
||||||
*/
|
*/
|
||||||
public function delete_all_html_headers() {
|
public function delete_all_html_headers() {
|
||||||
$this->html_headers = array();
|
$this->html_headers = array();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a Block of data
|
* Add a Block of data to the page.
|
||||||
|
* @param Block $block
|
||||||
*/
|
*/
|
||||||
public function add_block(Block $block) {
|
public function add_block(Block $block) {
|
||||||
$this->blocks[] = $block;
|
$this->blocks[] = $block;
|
||||||
@ -180,7 +209,7 @@ class Page {
|
|||||||
// ==============================================
|
// ==============================================
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Display the page according to the mode and data given
|
* Display the page according to the mode and data given.
|
||||||
*/
|
*/
|
||||||
public function display() {
|
public function display() {
|
||||||
global $page, $user;
|
global $page, $user;
|
||||||
@ -263,7 +292,7 @@ class Page {
|
|||||||
$css_files[] = $css;
|
$css_files[] = $css;
|
||||||
$css_latest = max($css_latest, filemtime($css));
|
$css_latest = max($css_latest, filemtime($css));
|
||||||
}
|
}
|
||||||
$css_cache_file = data_path("cache/style.$css_latest.css");
|
$css_cache_file = data_path("cache/style.$theme_name.$css_latest.css");
|
||||||
if(!file_exists($css_cache_file)) {
|
if(!file_exists($css_cache_file)) {
|
||||||
$css_data = "";
|
$css_data = "";
|
||||||
foreach($css_files as $file) {
|
foreach($css_files as $file) {
|
||||||
@ -283,7 +312,7 @@ class Page {
|
|||||||
$js_files[] = $js;
|
$js_files[] = $js;
|
||||||
$js_latest = max($js_latest, filemtime($js));
|
$js_latest = max($js_latest, filemtime($js));
|
||||||
}
|
}
|
||||||
$js_cache_file = data_path("cache/script.$js_latest.js");
|
$js_cache_file = data_path("cache/script.$theme_name.$js_latest.js");
|
||||||
if(!file_exists($js_cache_file)) {
|
if(!file_exists($js_cache_file)) {
|
||||||
$js_data = "";
|
$js_data = "";
|
||||||
foreach($js_files as $file) {
|
foreach($js_files as $file) {
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
<?php
|
<?php
|
||||||
|
require_once "lib/password.php";
|
||||||
|
|
||||||
/** @private */
|
/** @private */
|
||||||
function _new_user($row) {
|
function _new_user($row) {
|
||||||
return new User($row);
|
return new User($row);
|
||||||
@ -6,9 +8,11 @@ function _new_user($row) {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class User
|
||||||
|
*
|
||||||
* An object representing a row in the "users" table.
|
* An object representing a row in the "users" table.
|
||||||
*
|
*
|
||||||
* The currently logged in user will always be accessible via the global variable $user
|
* The currently logged in user will always be accessible via the global variable $user.
|
||||||
*/
|
*/
|
||||||
class User {
|
class User {
|
||||||
/** @var int */
|
/** @var int */
|
||||||
@ -22,10 +26,11 @@ class User {
|
|||||||
|
|
||||||
public $join_date;
|
public $join_date;
|
||||||
|
|
||||||
|
/** @var string */
|
||||||
public $passhash;
|
public $passhash;
|
||||||
|
|
||||||
/** @var UserClass */
|
/** @var UserClass */
|
||||||
var $class;
|
public $class;
|
||||||
|
|
||||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||||
* Initialisation *
|
* Initialisation *
|
||||||
@ -38,7 +43,9 @@ class User {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* One will very rarely construct a user directly, more common
|
* One will very rarely construct a user directly, more common
|
||||||
* would be to use User::by_id, User::by_session, etc
|
* would be to use User::by_id, User::by_session, etc.
|
||||||
|
*
|
||||||
|
* @param mixed $row
|
||||||
*/
|
*/
|
||||||
public function __construct($row) {
|
public function __construct($row) {
|
||||||
global $_user_classes;
|
global $_user_classes;
|
||||||
@ -60,7 +67,7 @@ class User {
|
|||||||
*/
|
*/
|
||||||
public static function by_session(/*string*/ $name, /*string*/ $session) {
|
public static function by_session(/*string*/ $name, /*string*/ $session) {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
$row = $database->cache->get("user-session-$name-$session");
|
$row = $database->cache->get("user-session:$name-$session");
|
||||||
if(!$row) {
|
if(!$row) {
|
||||||
if($database->get_driver_name() === "mysql") {
|
if($database->get_driver_name() === "mysql") {
|
||||||
$query = "SELECT * FROM users WHERE name = :name AND md5(concat(pass, :ip)) = :sess";
|
$query = "SELECT * FROM users WHERE name = :name AND md5(concat(pass, :ip)) = :sess";
|
||||||
@ -69,7 +76,7 @@ class User {
|
|||||||
$query = "SELECT * FROM users WHERE name = :name AND md5(pass || :ip) = :sess";
|
$query = "SELECT * FROM users WHERE name = :name AND md5(pass || :ip) = :sess";
|
||||||
}
|
}
|
||||||
$row = $database->get_row($query, array("name"=>$name, "ip"=>get_session_ip($config), "sess"=>$session));
|
$row = $database->get_row($query, array("name"=>$name, "ip"=>get_session_ip($config), "sess"=>$session));
|
||||||
$database->cache->set("user-session-$name-$session", $row, 600);
|
$database->cache->set("user-session:$name-$session", $row, 600);
|
||||||
}
|
}
|
||||||
return is_null($row) ? null : new User($row);
|
return is_null($row) ? null : new User($row);
|
||||||
}
|
}
|
||||||
@ -104,18 +111,23 @@ class User {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Construct a User by name and hash.
|
* Construct a User by name and password.
|
||||||
* @param string $name
|
* @param string $name
|
||||||
* @param string $hash
|
* @param string $pass
|
||||||
* @return null|User
|
* @return null|User
|
||||||
*/
|
*/
|
||||||
public static function by_name_and_hash(/*string*/ $name, /*string*/ $hash) {
|
public static function by_name_and_pass(/*string*/ $name, /*string*/ $pass) {
|
||||||
assert(is_string($name));
|
assert(is_string($name));
|
||||||
assert(is_string($hash));
|
assert(is_string($pass));
|
||||||
assert(strlen($hash) == 32);
|
$user = User::by_name($name);
|
||||||
global $database;
|
if($user) {
|
||||||
$row = $database->get_row($database->scoreql_to_sql("SELECT * FROM users WHERE SCORE_STRNORM(name) = SCORE_STRNORM(:name) AND pass = :hash"), array("name"=>$name, "hash"=>$hash));
|
if($user->passhash == md5(strtolower($name) . $pass)) {
|
||||||
return is_null($row) ? null : new User($row);
|
$user->set_password($pass);
|
||||||
|
}
|
||||||
|
if(password_verify($pass, $user->passhash)) {
|
||||||
|
return $user;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -145,7 +157,7 @@ class User {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test if this user is anonymous (not logged in)
|
* Test if this user is anonymous (not logged in).
|
||||||
*
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
@ -155,7 +167,7 @@ class User {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test if this user is logged in
|
* Test if this user is logged in.
|
||||||
*
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
@ -165,7 +177,7 @@ class User {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test if this user is an administrator
|
* Test if this user is an administrator.
|
||||||
*
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
@ -188,11 +200,14 @@ class User {
|
|||||||
*/
|
*/
|
||||||
public function set_password(/*string*/ $password) {
|
public function set_password(/*string*/ $password) {
|
||||||
global $database;
|
global $database;
|
||||||
$hash = md5(strtolower($this->name) . $password);
|
$this->passhash = password_hash($password, PASSWORD_BCRYPT);
|
||||||
$database->Execute("UPDATE users SET pass=:hash WHERE id=:id", array("hash"=>$hash, "id"=>$this->id));
|
$database->Execute("UPDATE users SET pass=:hash WHERE id=:id", array("hash"=>$this->passhash, "id"=>$this->id));
|
||||||
log_info("core-user", 'Set password for '.$this->name);
|
log_info("core-user", 'Set password for '.$this->name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $address
|
||||||
|
*/
|
||||||
public function set_email(/*string*/ $address) {
|
public function set_email(/*string*/ $address) {
|
||||||
global $database;
|
global $database;
|
||||||
$database->Execute("UPDATE users SET email=:email WHERE id=:id", array("email"=>$address, "id"=>$this->id));
|
$database->Execute("UPDATE users SET email=:email WHERE id=:id", array("email"=>$address, "id"=>$this->id));
|
||||||
@ -201,7 +216,8 @@ class User {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a snippet of HTML which will render the user's avatar, be that
|
* Get a snippet of HTML which will render the user's avatar, be that
|
||||||
* a local file, a remote file, a gravatar, a something else, etc
|
* a local file, a remote file, a gravatar, a something else, etc.
|
||||||
|
*
|
||||||
* @return String of HTML
|
* @return String of HTML
|
||||||
*/
|
*/
|
||||||
public function get_avatar_html() {
|
public function get_avatar_html() {
|
||||||
@ -224,14 +240,14 @@ class User {
|
|||||||
* Get an auth token to be used in POST forms
|
* Get an auth token to be used in POST forms
|
||||||
*
|
*
|
||||||
* password = secret, avoid storing directly
|
* password = secret, avoid storing directly
|
||||||
* passhash = md5(password), so someone who gets to the database can't get passwords
|
* passhash = bcrypt(password), so someone who gets to the database can't get passwords
|
||||||
* sesskey = md5(passhash . IP), so if it gets sniffed it can't be used from another IP,
|
* sesskey = md5(passhash . IP), so if it gets sniffed it can't be used from another IP,
|
||||||
* and it can't be used to get the passhash to generate new sesskeys
|
* and it can't be used to get the passhash to generate new sesskeys
|
||||||
* authtok = md5(sesskey, salt), presented to the user in web forms, to make sure that
|
* authtok = md5(sesskey, salt), presented to the user in web forms, to make sure that
|
||||||
* the form was generated within the session. Salted and re-hashed so that
|
* the form was generated within the session. Salted and re-hashed so that
|
||||||
* reading a web page from the user's cache doesn't give access to the session key
|
* reading a web page from the user's cache doesn't give access to the session key
|
||||||
*
|
*
|
||||||
* @return String containing auth token (MD5sum)
|
* @return string A string containing auth token (MD5sum)
|
||||||
*/
|
*/
|
||||||
public function get_auth_token() {
|
public function get_auth_token() {
|
||||||
global $config;
|
global $config;
|
||||||
|
@ -1,11 +1,34 @@
|
|||||||
<?php
|
<?php
|
||||||
|
/**
|
||||||
|
* @global UserClass[] $_user_classes
|
||||||
|
*/
|
||||||
$_user_classes = array();
|
$_user_classes = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class UserClass
|
||||||
|
*/
|
||||||
class UserClass {
|
class UserClass {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var null|string
|
||||||
|
*/
|
||||||
public $name = null;
|
public $name = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var \UserClass|null
|
||||||
|
*/
|
||||||
public $parent = null;
|
public $parent = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
public $abilities = array();
|
public $abilities = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $parent
|
||||||
|
* @param array $abilities
|
||||||
|
*/
|
||||||
public function __construct($name, $parent=null, $abilities=array()) {
|
public function __construct($name, $parent=null, $abilities=array()) {
|
||||||
global $_user_classes;
|
global $_user_classes;
|
||||||
|
|
||||||
|
@ -124,6 +124,12 @@ function no_escape($input) {
|
|||||||
return $input;
|
return $input;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param array $attrs
|
||||||
|
* @param array $children
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
function xml_tag($name, $attrs=array(), $children=array()) {
|
function xml_tag($name, $attrs=array(), $children=array()) {
|
||||||
$xml = "<$name ";
|
$xml = "<$name ";
|
||||||
foreach($attrs as $k => $v) {
|
foreach($attrs as $k => $v) {
|
||||||
@ -427,6 +433,10 @@ function make_form($target, $method="POST", $multipart=False, $form_id="", $onsu
|
|||||||
return '<form action="'.$target.'" method="'.$method.'" '.$extra.'>'.$auth;
|
return '<form action="'.$target.'" method="'.$method.'" '.$extra.'>'.$auth;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $file The filename
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
function mtimefile($file) {
|
function mtimefile($file) {
|
||||||
$data_href = get_base_href();
|
$data_href = get_base_href();
|
||||||
$mtime = filemtime($file);
|
$mtime = filemtime($file);
|
||||||
@ -445,8 +455,11 @@ function get_theme() {
|
|||||||
return $theme;
|
return $theme;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* like glob, with support for matching very long patterns with braces
|
* Like glob, with support for matching very long patterns with braces.
|
||||||
|
*
|
||||||
|
* @param string $pattern
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
function zglob($pattern) {
|
function zglob($pattern) {
|
||||||
$results = array();
|
$results = array();
|
||||||
@ -470,6 +483,9 @@ function zglob($pattern) {
|
|||||||
* CAPTCHA abstraction *
|
* CAPTCHA abstraction *
|
||||||
\* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
\* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
function captcha_get_html() {
|
function captcha_get_html() {
|
||||||
global $config, $user;
|
global $config, $user;
|
||||||
|
|
||||||
@ -492,6 +508,9 @@ function captcha_get_html() {
|
|||||||
return $captcha;
|
return $captcha;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
function captcha_check() {
|
function captcha_check() {
|
||||||
global $config, $user;
|
global $config, $user;
|
||||||
|
|
||||||
@ -593,7 +612,10 @@ function getMimeType($file, $ext="", $list=false) {
|
|||||||
return 'application/octet-stream';
|
return 'application/octet-stream';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $mime_type
|
||||||
|
* @return bool|string
|
||||||
|
*/
|
||||||
function getExtension ($mime_type){
|
function getExtension ($mime_type){
|
||||||
if(empty($mime_type)){
|
if(empty($mime_type)){
|
||||||
return false;
|
return false;
|
||||||
@ -608,7 +630,7 @@ function getExtension ($mime_type){
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
function _version_check() {
|
function _version_check() {
|
||||||
$min_version = "5.3.0";
|
$min_version = "5.3.7";
|
||||||
if(version_compare(PHP_VERSION, $min_version) == -1) {
|
if(version_compare(PHP_VERSION, $min_version) == -1) {
|
||||||
print "
|
print "
|
||||||
Currently SCore Engine doesn't support versions of PHP lower than $min_version --
|
Currently SCore Engine doesn't support versions of PHP lower than $min_version --
|
||||||
@ -762,6 +784,11 @@ function get_prefixed_cookie(/*string*/ $name) {
|
|||||||
* The counterpart for get_prefixed_cookie, this works like php's
|
* The counterpart for get_prefixed_cookie, this works like php's
|
||||||
* setcookie method, but prepends the site-wide cookie prefix to
|
* setcookie method, but prepends the site-wide cookie prefix to
|
||||||
* the $name argument before doing anything.
|
* the $name argument before doing anything.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param string $value
|
||||||
|
* @param int $time
|
||||||
|
* @param string $path
|
||||||
*/
|
*/
|
||||||
function set_prefixed_cookie($name, $value, $time, $path) {
|
function set_prefixed_cookie($name, $value, $time, $path) {
|
||||||
global $config;
|
global $config;
|
||||||
@ -770,13 +797,16 @@ function set_prefixed_cookie($name, $value, $time, $path) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set (or extend) a flash-message cookie
|
* Set (or extend) a flash-message cookie.
|
||||||
*
|
*
|
||||||
* This can optionally be done at the same time as saving a log message with log_*()
|
* This can optionally be done at the same time as saving a log message with log_*()
|
||||||
*
|
*
|
||||||
* Generally one should flash a message in onPageRequest and log a message wherever
|
* Generally one should flash a message in onPageRequest and log a message wherever
|
||||||
* the action actually takes place (eg onWhateverElse) - but much of the time, actions
|
* the action actually takes place (eg onWhateverElse) - but much of the time, actions
|
||||||
* are taken from within onPageRequest...
|
* are taken from within onPageRequest...
|
||||||
|
*
|
||||||
|
* @param string $text
|
||||||
|
* @param string $type
|
||||||
*/
|
*/
|
||||||
function flash_message(/*string*/ $text, /*string*/ $type="info") {
|
function flash_message(/*string*/ $text, /*string*/ $type="info") {
|
||||||
$current = get_prefixed_cookie("flash_message");
|
$current = get_prefixed_cookie("flash_message");
|
||||||
@ -816,10 +846,9 @@ function get_base_href() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A shorthand way to send a TextFormattingEvent and get the
|
* A shorthand way to send a TextFormattingEvent and get the results.
|
||||||
* results
|
|
||||||
*
|
*
|
||||||
* @param $string
|
* @param string $string
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
function format_text(/*string*/ $string) {
|
function format_text(/*string*/ $string) {
|
||||||
@ -828,6 +857,12 @@ function format_text(/*string*/ $string) {
|
|||||||
return $tfe->formatted;
|
return $tfe->formatted;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $base
|
||||||
|
* @param string $hash
|
||||||
|
* @param bool $create
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
function warehouse_path(/*string*/ $base, /*string*/ $hash, /*bool*/ $create=true) {
|
function warehouse_path(/*string*/ $base, /*string*/ $hash, /*bool*/ $create=true) {
|
||||||
$ab = substr($hash, 0, 2);
|
$ab = substr($hash, 0, 2);
|
||||||
$cd = substr($hash, 2, 2);
|
$cd = substr($hash, 2, 2);
|
||||||
@ -841,12 +876,21 @@ function warehouse_path(/*string*/ $base, /*string*/ $hash, /*bool*/ $create=tru
|
|||||||
return $pa;
|
return $pa;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
function data_path($filename) {
|
function data_path($filename) {
|
||||||
$filename = "data/" . $filename;
|
$filename = "data/" . $filename;
|
||||||
if(!file_exists(dirname($filename))) mkdir(dirname($filename), 0755, true);
|
if(!file_exists(dirname($filename))) mkdir(dirname($filename), 0755, true);
|
||||||
return $filename;
|
return $filename;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $url
|
||||||
|
* @param string $mfile
|
||||||
|
* @return array|bool
|
||||||
|
*/
|
||||||
function transload($url, $mfile) {
|
function transload($url, $mfile) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -935,15 +979,37 @@ if (!function_exists('http_parse_headers')) { #http://www.php.net/manual/en/func
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function findHeader ($headers, $name){
|
||||||
|
//HTTP Headers can sometimes be lowercase which will cause issues.
|
||||||
|
//In cases like these, we need to make sure to check for them if the camelcase version does not exist.
|
||||||
|
$header = FALSE;
|
||||||
|
|
||||||
|
if(array_key_exists($name, $headers)){
|
||||||
|
$header = $headers[$name];
|
||||||
|
}else{
|
||||||
|
$headers = array_change_key_case($headers);
|
||||||
|
if(array_key_exists(strtolower($name), $headers)){
|
||||||
|
$header = $headers[strtolower($name)];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $header;
|
||||||
|
}
|
||||||
|
|
||||||
$_included = array();
|
$_included = array();
|
||||||
/**
|
/**
|
||||||
* Get the active contents of a .php file
|
* Get the active contents of a .php file
|
||||||
|
*
|
||||||
|
* @param string $fname
|
||||||
|
* @return string|null
|
||||||
*/
|
*/
|
||||||
function manual_include($fname) {
|
function manual_include($fname) {
|
||||||
if(!file_exists($fname)) return;
|
|
||||||
|
|
||||||
global $_included;
|
global $_included;
|
||||||
if(in_array($fname, $_included)) return;
|
|
||||||
|
if(!file_exists($fname)) return null;
|
||||||
|
|
||||||
|
if(in_array($fname, $_included)) return null;
|
||||||
|
|
||||||
$_included[] = $fname;
|
$_included[] = $fname;
|
||||||
|
|
||||||
print "$fname\n";
|
print "$fname\n";
|
||||||
@ -990,6 +1056,12 @@ define("SCORE_LOG_NOTSET", 0);
|
|||||||
* $flash = null (default) - log to server only, no flash message
|
* $flash = null (default) - log to server only, no flash message
|
||||||
* $flash = true - show the message to the user as well
|
* $flash = true - show the message to the user as well
|
||||||
* $flash = "some string" - log the message, flash the string
|
* $flash = "some string" - log the message, flash the string
|
||||||
|
*
|
||||||
|
* @param string $section
|
||||||
|
* @param int $priority
|
||||||
|
* @param string $message
|
||||||
|
* @param null|bool|string $flash
|
||||||
|
* @param array $args
|
||||||
*/
|
*/
|
||||||
function log_msg(/*string*/ $section, /*int*/ $priority, /*string*/ $message, $flash=null, $args=array()) {
|
function log_msg(/*string*/ $section, /*int*/ $priority, /*string*/ $message, $flash=null, $args=array()) {
|
||||||
send_event(new LogEvent($section, $priority, $message, $args));
|
send_event(new LogEvent($section, $priority, $message, $args));
|
||||||
@ -1012,10 +1084,13 @@ function log_warning( /*string*/ $section, /*string*/ $message, $flash=null, $ar
|
|||||||
function log_error( /*string*/ $section, /*string*/ $message, $flash=null, $args=array()) {log_msg($section, SCORE_LOG_ERROR, $message, $flash, $args);}
|
function log_error( /*string*/ $section, /*string*/ $message, $flash=null, $args=array()) {log_msg($section, SCORE_LOG_ERROR, $message, $flash, $args);}
|
||||||
function log_critical(/*string*/ $section, /*string*/ $message, $flash=null, $args=array()) {log_msg($section, SCORE_LOG_CRITICAL, $message, $flash, $args);}
|
function log_critical(/*string*/ $section, /*string*/ $message, $flash=null, $args=array()) {log_msg($section, SCORE_LOG_CRITICAL, $message, $flash, $args);}
|
||||||
|
|
||||||
/**
|
|
||||||
* Get a unique ID for this request, useful for grouping log messages
|
|
||||||
*/
|
|
||||||
$_request_id = null;
|
$_request_id = null;
|
||||||
|
/**
|
||||||
|
* Get a unique ID for this request, useful for grouping log messages.
|
||||||
|
*
|
||||||
|
* @return null|string
|
||||||
|
*/
|
||||||
function get_request_id() {
|
function get_request_id() {
|
||||||
global $_request_id;
|
global $_request_id;
|
||||||
if(!$_request_id) {
|
if(!$_request_id) {
|
||||||
@ -1197,7 +1272,11 @@ function full_copy($source, $target) {
|
|||||||
$_event_listeners = array();
|
$_event_listeners = array();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Register an Extension
|
* Register an Extension.
|
||||||
|
*
|
||||||
|
* @param Extension $extension
|
||||||
|
* @param int $pos
|
||||||
|
* @param array $events
|
||||||
*/
|
*/
|
||||||
function add_event_listener(Extension $extension, $pos=50, $events=array()) {
|
function add_event_listener(Extension $extension, $pos=50, $events=array()) {
|
||||||
global $_event_listeners;
|
global $_event_listeners;
|
||||||
@ -1214,7 +1293,9 @@ function add_event_listener(Extension $extension, $pos=50, $events=array()) {
|
|||||||
$_event_count = 0;
|
$_event_count = 0;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Send an event to all registered Extensions
|
* Send an event to all registered Extensions.
|
||||||
|
*
|
||||||
|
* @param Event $event
|
||||||
*/
|
*/
|
||||||
function send_event(Event $event) {
|
function send_event(Event $event) {
|
||||||
global $_event_listeners, $_event_count;
|
global $_event_listeners, $_event_count;
|
||||||
@ -1227,7 +1308,9 @@ function send_event(Event $event) {
|
|||||||
ksort($my_event_listeners);
|
ksort($my_event_listeners);
|
||||||
foreach($my_event_listeners as $listener) {
|
foreach($my_event_listeners as $listener) {
|
||||||
ctx_log_start(get_class($listener));
|
ctx_log_start(get_class($listener));
|
||||||
$listener->$method_name($event);
|
if(method_exists($listener, $method_name)) {
|
||||||
|
$listener->$method_name($event);
|
||||||
|
}
|
||||||
ctx_log_endok();
|
ctx_log_endok();
|
||||||
}
|
}
|
||||||
$_event_count++;
|
$_event_count++;
|
||||||
@ -1248,7 +1331,7 @@ $_load_start = microtime(true);
|
|||||||
* Collects some debug information (execution time, memory usage, queries, etc)
|
* Collects some debug information (execution time, memory usage, queries, etc)
|
||||||
* and formats it to stick in the footer of the page.
|
* and formats it to stick in the footer of the page.
|
||||||
*
|
*
|
||||||
* @return String of debug info to add to the page.
|
* @return string debug info to add to the page.
|
||||||
*/
|
*/
|
||||||
function get_debug_info() {
|
function get_debug_info() {
|
||||||
global $config, $_event_count, $database, $_execs, $_load_start;
|
global $config, $_event_count, $database, $_execs, $_load_start;
|
||||||
@ -1261,12 +1344,13 @@ function get_debug_info() {
|
|||||||
else {
|
else {
|
||||||
$commit = " (".$config->get_string("commit_hash").")";
|
$commit = " (".$config->get_string("commit_hash").")";
|
||||||
}
|
}
|
||||||
$time = sprintf("%5.2f", microtime(true) - $_load_start);
|
$time = sprintf("%.2f", microtime(true) - $_load_start);
|
||||||
|
$dbtime = sprintf("%.2f", $database->dbtime);
|
||||||
$i_files = count(get_included_files());
|
$i_files = count(get_included_files());
|
||||||
$hits = $database->cache->get_hits();
|
$hits = $database->cache->get_hits();
|
||||||
$miss = $database->cache->get_misses();
|
$miss = $database->cache->get_misses();
|
||||||
|
|
||||||
$debug = "<br>Took $time seconds and {$i_mem}MB of RAM";
|
$debug = "<br>Took $time seconds (db:$dbtime) and {$i_mem}MB of RAM";
|
||||||
$debug .= "; Used $i_files files and $_execs queries";
|
$debug .= "; Used $i_files files and $_execs queries";
|
||||||
$debug .= "; Sent $_event_count events";
|
$debug .= "; Sent $_event_count events";
|
||||||
$debug .= "; $hits cache hits and $miss misses";
|
$debug .= "; $hits cache hits and $miss misses";
|
||||||
@ -1282,6 +1366,10 @@ function get_debug_info() {
|
|||||||
|
|
||||||
/** @privatesection */
|
/** @privatesection */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array|string $arr
|
||||||
|
* @return array|string
|
||||||
|
*/
|
||||||
function _stripslashes_r($arr) {
|
function _stripslashes_r($arr) {
|
||||||
return is_array($arr) ? array_map('_stripslashes_r', $arr) : stripslashes($arr);
|
return is_array($arr) ? array_map('_stripslashes_r', $arr) : stripslashes($arr);
|
||||||
}
|
}
|
||||||
@ -1325,6 +1413,10 @@ function _sanitise_environment() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $_theme
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
function _get_themelet_files($_theme) {
|
function _get_themelet_files($_theme) {
|
||||||
$base_themelets = array();
|
$base_themelets = array();
|
||||||
if(file_exists('themes/'.$_theme.'/custompage.class.php')) $base_themelets[] = 'themes/'.$_theme.'/custompage.class.php';
|
if(file_exists('themes/'.$_theme.'/custompage.class.php')) $base_themelets[] = 'themes/'.$_theme.'/custompage.class.php';
|
||||||
@ -1407,6 +1499,7 @@ function _load_extensions() {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Used to display fatal errors to the web user.
|
* Used to display fatal errors to the web user.
|
||||||
|
* @param Exception $e
|
||||||
*/
|
*/
|
||||||
function _fatal_error(Exception $e) {
|
function _fatal_error(Exception $e) {
|
||||||
$version = VERSION;
|
$version = VERSION;
|
||||||
@ -1438,6 +1531,9 @@ function _fatal_error(Exception $e) {
|
|||||||
*
|
*
|
||||||
* Necessary because various servers and various clients
|
* Necessary because various servers and various clients
|
||||||
* think that / is special...
|
* think that / is special...
|
||||||
|
*
|
||||||
|
* @param string $str
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
function _decaret($str) {
|
function _decaret($str) {
|
||||||
$out = "";
|
$out = "";
|
||||||
@ -1456,6 +1552,9 @@ function _decaret($str) {
|
|||||||
return $out;
|
return $out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return User
|
||||||
|
*/
|
||||||
function _get_user() {
|
function _get_user() {
|
||||||
global $config;
|
global $config;
|
||||||
$user = null;
|
$user = null;
|
||||||
|
@ -17,22 +17,33 @@
|
|||||||
* <br>Download the contents of the database in plain text format, useful
|
* <br>Download the contents of the database in plain text format, useful
|
||||||
* for backups.
|
* for backups.
|
||||||
* <p>Image dump:
|
* <p>Image dump:
|
||||||
* <br>Download all the images as a .zip file
|
* <br>Download all the images as a .zip file (Requires ZipArchive)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sent when the admin page is ready to be added to
|
* Sent when the admin page is ready to be added to
|
||||||
*/
|
*/
|
||||||
class AdminBuildingEvent extends Event {
|
class AdminBuildingEvent extends Event {
|
||||||
var $page;
|
/** @var \Page */
|
||||||
|
public $page;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
*/
|
||||||
public function __construct(Page $page) {
|
public function __construct(Page $page) {
|
||||||
$this->page = $page;
|
$this->page = $page;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class AdminActionEvent extends Event {
|
class AdminActionEvent extends Event {
|
||||||
var $action;
|
/** @var string */
|
||||||
var $redirect = true;
|
public $action;
|
||||||
|
/** @var bool */
|
||||||
|
public $redirect = true;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $action
|
||||||
|
*/
|
||||||
public function __construct(/*string*/ $action) {
|
public function __construct(/*string*/ $action) {
|
||||||
$this->action = $action;
|
$this->action = $action;
|
||||||
}
|
}
|
||||||
|
@ -12,6 +12,12 @@ class AdminPageTheme extends Themelet {
|
|||||||
$page->add_block(new NavBlock());
|
$page->add_block(new NavBlock());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param string $action
|
||||||
|
* @param bool $protected
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function button(/*string*/ $name, /*string*/ $action, /*boolean*/ $protected=false) {
|
protected function button(/*string*/ $name, /*string*/ $action, /*boolean*/ $protected=false) {
|
||||||
$c_protected = $protected ? " protected" : "";
|
$c_protected = $protected ? " protected" : "";
|
||||||
$html = make_form(make_link("admin/$action"), "POST", false, null, null, "admin$c_protected");
|
$html = make_form(make_link("admin/$action"), "POST", false, null, null, "admin$c_protected");
|
||||||
@ -39,7 +45,8 @@ class AdminPageTheme extends Themelet {
|
|||||||
$html = "";
|
$html = "";
|
||||||
$html .= $this->button("All tags to lowercase", "lowercase_all_tags", true);
|
$html .= $this->button("All tags to lowercase", "lowercase_all_tags", true);
|
||||||
$html .= $this->button("Recount tag use", "recount_tag_use", false);
|
$html .= $this->button("Recount tag use", "recount_tag_use", false);
|
||||||
$html .= $this->button("Download all images", "download_all_images", false);
|
if(class_exists('ZipArchive'))
|
||||||
|
$html .= $this->button("Download all images", "download_all_images", false);
|
||||||
$html .= $this->button("Download database contents", "database_dump", false);
|
$html .= $this->button("Download database contents", "database_dump", false);
|
||||||
if($database->get_driver_name() == "mysql")
|
if($database->get_driver_name() == "mysql")
|
||||||
$html .= $this->button("Reset image IDs", "reset_image_ids", true);
|
$html .= $this->button("Reset image IDs", "reset_image_ids", true);
|
||||||
|
@ -11,9 +11,15 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class AddAliasEvent extends Event {
|
class AddAliasEvent extends Event {
|
||||||
var $oldtag;
|
/** @var string */
|
||||||
var $newtag;
|
public $oldtag;
|
||||||
|
/** @var string */
|
||||||
|
public $newtag;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $oldtag
|
||||||
|
* @param string $newtag
|
||||||
|
*/
|
||||||
public function __construct($oldtag, $newtag) {
|
public function __construct($oldtag, $newtag) {
|
||||||
$this->oldtag = trim($oldtag);
|
$this->oldtag = trim($oldtag);
|
||||||
$this->newtag = trim($newtag);
|
$this->newtag = trim($newtag);
|
||||||
@ -124,6 +130,10 @@ class AliasEditor extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Database $database
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function get_alias_csv(Database $database) {
|
private function get_alias_csv(Database $database) {
|
||||||
$csv = "";
|
$csv = "";
|
||||||
$aliases = $database->get_pairs("SELECT oldtag, newtag FROM aliases ORDER BY newtag");
|
$aliases = $database->get_pairs("SELECT oldtag, newtag FROM aliases ORDER BY newtag");
|
||||||
@ -133,6 +143,10 @@ class AliasEditor extends Extension {
|
|||||||
return $csv;
|
return $csv;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Database $database
|
||||||
|
* @param string $csv
|
||||||
|
*/
|
||||||
private function add_alias_csv(Database $database, /*string*/ $csv) {
|
private function add_alias_csv(Database $database, /*string*/ $csv) {
|
||||||
$csv = str_replace("\r", "\n", $csv);
|
$csv = str_replace("\r", "\n", $csv);
|
||||||
foreach(explode("\n", $csv) as $line) {
|
foreach(explode("\n", $csv) as $line) {
|
||||||
@ -148,9 +162,15 @@ class AliasEditor extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// add alias *after* mass tag editing, else the MTE will
|
/**
|
||||||
// search for the images and be redirected to the alias,
|
* Get the priority for this extension.
|
||||||
// missing out the images tagged with the oldtag
|
*
|
||||||
|
* Add alias *after* mass tag editing, else the MTE will
|
||||||
|
* search for the images and be redirected to the alias,
|
||||||
|
* missing out the images tagged with the old tag.
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_priority() {return 60;}
|
public function get_priority() {return 60;}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,11 +1,14 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class AliasEditorTheme extends Themelet {
|
class AliasEditorTheme extends Themelet {
|
||||||
/*
|
/**
|
||||||
* Show a page of aliases:
|
* Show a page of aliases.
|
||||||
*
|
*
|
||||||
* $aliases = an array of ($old_tag => $new_tag)
|
* Note: $can_manage = whether things like "add new alias" should be shown
|
||||||
* $can_manage = whether things like "add new alias" should be shown
|
*
|
||||||
|
* @param array $aliases An array of ($old_tag => $new_tag)
|
||||||
|
* @param int $pageNumber
|
||||||
|
* @param int $totalPages
|
||||||
*/
|
*/
|
||||||
public function display_aliases($aliases, $pageNumber, $totalPages) {
|
public function display_aliases($aliases, $pageNumber, $totalPages) {
|
||||||
global $page, $user;
|
global $page, $user;
|
||||||
|
@ -9,14 +9,22 @@
|
|||||||
* Simply enable this extention in the extention manager to enable arrow key navigation.
|
* Simply enable this extention in the extention manager to enable arrow key navigation.
|
||||||
*/
|
*/
|
||||||
class ArrowkeyNavigation extends Extension {
|
class ArrowkeyNavigation extends Extension {
|
||||||
# Adds functionality for post/view on images
|
/**
|
||||||
|
* Adds functionality for post/view on images.
|
||||||
|
*
|
||||||
|
* @param DisplayingImageEvent $event
|
||||||
|
*/
|
||||||
public function onDisplayingImage(DisplayingImageEvent $event) {
|
public function onDisplayingImage(DisplayingImageEvent $event) {
|
||||||
$prev_url = make_http(make_link("post/prev/".$event->image->id));
|
$prev_url = make_http(make_link("post/prev/".$event->image->id));
|
||||||
$next_url = make_http(make_link("post/next/".$event->image->id));
|
$next_url = make_http(make_link("post/next/".$event->image->id));
|
||||||
$this->add_arrowkeys_code($prev_url, $next_url);
|
$this->add_arrowkeys_code($prev_url, $next_url);
|
||||||
}
|
}
|
||||||
|
|
||||||
# Adds functionality for post/list
|
/**
|
||||||
|
* Adds functionality for post/list.
|
||||||
|
*
|
||||||
|
* @param PageRequestEvent $event
|
||||||
|
*/
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
if($event->page_matches("post/list")) {
|
if($event->page_matches("post/list")) {
|
||||||
$pageinfo = $this->get_list_pageinfo($event);
|
$pageinfo = $this->get_list_pageinfo($event);
|
||||||
@ -26,7 +34,12 @@ class ArrowkeyNavigation extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
# adds the javascript to the page with the given urls
|
/**
|
||||||
|
* Adds the javascript to the page with the given urls.
|
||||||
|
*
|
||||||
|
* @param string $prev_url
|
||||||
|
* @param string $next_url
|
||||||
|
*/
|
||||||
private function add_arrowkeys_code($prev_url, $next_url) {
|
private function add_arrowkeys_code($prev_url, $next_url) {
|
||||||
global $page;
|
global $page;
|
||||||
|
|
||||||
@ -41,8 +54,13 @@ class ArrowkeyNavigation extends Extension {
|
|||||||
</script>", 60);
|
</script>", 60);
|
||||||
}
|
}
|
||||||
|
|
||||||
# returns info about the current page number
|
/**
|
||||||
private function get_list_pageinfo($event) {
|
* Returns info about the current page number.
|
||||||
|
*
|
||||||
|
* @param PageRequestEvent $event
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
private function get_list_pageinfo(PageRequestEvent $event) {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
|
|
||||||
// get the amount of images per page
|
// get the amount of images per page
|
||||||
|
@ -9,9 +9,19 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class AuthorSetEvent extends Event {
|
class AuthorSetEvent extends Event {
|
||||||
var $image, $user, $author;
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
/** @var \User */
|
||||||
|
public $user;
|
||||||
|
/** @var string */
|
||||||
|
public $author;
|
||||||
|
|
||||||
public function __construct(Image $image, User $user, /*string*/ $author)
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param User $user
|
||||||
|
* @param string $author
|
||||||
|
*/
|
||||||
|
public function __construct(Image $image, User $user, /*string*/ $author)
|
||||||
{
|
{
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
@ -937,9 +947,12 @@ class Artists extends Extension {
|
|||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE GET THE ID OF THE ARTIST
|
* HERE WE GET THE ID OF THE ARTIST.
|
||||||
*/
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @return string|int
|
||||||
|
*/
|
||||||
private function get_artist_id($name){
|
private function get_artist_id($name){
|
||||||
global $database;
|
global $database;
|
||||||
$artistID = $database->get_row("SELECT id FROM artists WHERE name = ?"
|
$artistID = $database->get_row("SELECT id FROM artists WHERE name = ?"
|
||||||
@ -1203,7 +1216,8 @@ class Artists extends Extension {
|
|||||||
/*
|
/*
|
||||||
* HERE WE GET THE INFO OF THE ALIAS
|
* HERE WE GET THE INFO OF THE ALIAS
|
||||||
*/
|
*/
|
||||||
private function get_alias($artistID){
|
private function get_alias($artistID)
|
||||||
|
{
|
||||||
if (!is_numeric($artistID)) return;
|
if (!is_numeric($artistID)) return;
|
||||||
|
|
||||||
global $database;
|
global $database;
|
||||||
|
@ -1,6 +1,10 @@
|
|||||||
<?php
|
<?php
|
||||||
class ArtistsTheme extends Themelet {
|
class ArtistsTheme extends Themelet {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $author
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function get_author_editor_html(/*string*/ $author) {
|
public function get_author_editor_html(/*string*/ $author) {
|
||||||
$h_author = html_escape($author);
|
$h_author = html_escape($author);
|
||||||
return "
|
return "
|
||||||
@ -14,6 +18,11 @@ class ArtistsTheme extends Themelet {
|
|||||||
";
|
";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $mode
|
||||||
|
* @param null|int $artistID
|
||||||
|
* @param bool $is_admin
|
||||||
|
*/
|
||||||
public function sidebar_options(/*string*/ $mode, $artistID=NULL, $is_admin=FALSE){
|
public function sidebar_options(/*string*/ $mode, $artistID=NULL, $is_admin=FALSE){
|
||||||
global $page, $user;
|
global $page, $user;
|
||||||
|
|
||||||
|
@ -69,24 +69,27 @@ xanax
|
|||||||
$sb = new SetupBlock("Banned Phrases");
|
$sb = new SetupBlock("Banned Phrases");
|
||||||
$sb->add_label("One per line, lines that start with slashes are treated as regex<br/>");
|
$sb->add_label("One per line, lines that start with slashes are treated as regex<br/>");
|
||||||
$sb->add_longtext_option("banned_words");
|
$sb->add_longtext_option("banned_words");
|
||||||
|
$failed = array();
|
||||||
|
foreach($this->get_words() as $word) {
|
||||||
|
if($word[0] == '/') {
|
||||||
|
if(preg_match($word, "") === false) {
|
||||||
|
$failed[] = $word;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if($failed) {
|
||||||
|
$sb->add_label("Failed regexes: ".join(", ", $failed));
|
||||||
|
}
|
||||||
$event->panel->add_block($sb);
|
$event->panel->add_block($sb);
|
||||||
}
|
}
|
||||||
|
|
||||||
private function test_text($comment, $ex) {
|
private function test_text($comment, $ex) {
|
||||||
global $config;
|
|
||||||
|
|
||||||
$banned = $config->get_string("banned_words");
|
|
||||||
$comment = strtolower($comment);
|
$comment = strtolower($comment);
|
||||||
|
|
||||||
foreach(explode("\n", $banned) as $word) {
|
foreach($this->get_words() as $word) {
|
||||||
$word = trim(strtolower($word));
|
if($word[0] == '/') {
|
||||||
if(strlen($word) == 0) {
|
|
||||||
// line is blank
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
else if($word[0] == '/') {
|
|
||||||
// lines that start with slash are regex
|
// lines that start with slash are regex
|
||||||
if(preg_match($word, $comment)) {
|
if(preg_match($word, $comment) === 1) {
|
||||||
throw $ex;
|
throw $ex;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -99,6 +102,23 @@ xanax
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function get_words() {
|
||||||
|
global $config;
|
||||||
|
$words = array();
|
||||||
|
|
||||||
|
$banned = $config->get_string("banned_words");
|
||||||
|
foreach(explode("\n", $banned) as $word) {
|
||||||
|
$word = trim(strtolower($word));
|
||||||
|
if(strlen($word) == 0) {
|
||||||
|
// line is blank
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
$words[] = $word;
|
||||||
|
}
|
||||||
|
|
||||||
|
return $words;
|
||||||
|
}
|
||||||
|
|
||||||
public function get_priority() {return 30;}
|
public function get_priority() {return 30;}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -26,6 +26,10 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class BBCode extends FormatterExtension {
|
class BBCode extends FormatterExtension {
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function format(/*string*/ $text) {
|
public function format(/*string*/ $text) {
|
||||||
$text = $this->extract_code($text);
|
$text = $this->extract_code($text);
|
||||||
foreach(array(
|
foreach(array(
|
||||||
@ -35,6 +39,7 @@ class BBCode extends FormatterExtension {
|
|||||||
}
|
}
|
||||||
$text = preg_replace('!^>>([^\d].+)!', '<blockquote><small>$1</small></blockquote>', $text);
|
$text = preg_replace('!^>>([^\d].+)!', '<blockquote><small>$1</small></blockquote>', $text);
|
||||||
$text = preg_replace('!>>(\d+)(#c?\d+)?!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('post/view/$1$2').'">>>$1$2</a>', $text);
|
$text = preg_replace('!>>(\d+)(#c?\d+)?!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('post/view/$1$2').'">>>$1$2</a>', $text);
|
||||||
|
$text = preg_replace('!\[anchor=(.*?)\](.*?)\[/anchor\]!s', '<span class="anchor">$2 <a class="alink" href="#bb-$1" name="bb-$1" title="link to this anchor"> ¶ </a></span>', $text); // add "bb-" to avoid clashing with eg #top
|
||||||
$text = preg_replace('!\[url=site://(.*?)(#c\d+)?\](.*?)\[/url\]!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('$1$2').'">$3</a>', $text);
|
$text = preg_replace('!\[url=site://(.*?)(#c\d+)?\](.*?)\[/url\]!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('$1$2').'">$3</a>', $text);
|
||||||
$text = preg_replace('!\[url\]site://(.*?)(#c\d+)?\[/url\]!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('$1$2').'">$1$2</a>', $text);
|
$text = preg_replace('!\[url\]site://(.*?)(#c\d+)?\[/url\]!s', '<a class="shm-clink" data-clink-sel="$2" href="'.make_link('$1$2').'">$1$2</a>', $text);
|
||||||
$text = preg_replace('!\[url=((?:https?|ftp|irc|mailto)://.*?)\](.*?)\[/url\]!s', '<a href="$1">$2</a>', $text);
|
$text = preg_replace('!\[url=((?:https?|ftp|irc|mailto)://.*?)\](.*?)\[/url\]!s', '<a href="$1">$2</a>', $text);
|
||||||
@ -62,6 +67,10 @@ class BBCode extends FormatterExtension {
|
|||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function strip(/*string*/ $text) {
|
public function strip(/*string*/ $text) {
|
||||||
foreach(array(
|
foreach(array(
|
||||||
"b", "i", "u", "s", "sup", "sub", "h1", "h2", "h3", "h4",
|
"b", "i", "u", "s", "sup", "sub", "h1", "h2", "h3", "h4",
|
||||||
@ -69,6 +78,7 @@ class BBCode extends FormatterExtension {
|
|||||||
) as $el) {
|
) as $el) {
|
||||||
$text = preg_replace("!\[$el\](.*?)\[/$el\]!s", '$1', $text);
|
$text = preg_replace("!\[$el\](.*?)\[/$el\]!s", '$1', $text);
|
||||||
}
|
}
|
||||||
|
$text = preg_replace("!\[anchor=(.*?)\](.*?)\[/anchor\]!s", '$2', $text);
|
||||||
$text = preg_replace("!\[url=(.*?)\](.*?)\[/url\]!s", '$2', $text);
|
$text = preg_replace("!\[url=(.*?)\](.*?)\[/url\]!s", '$2', $text);
|
||||||
$text = preg_replace("!\[img\](.*?)\[/img\]!s", "", $text);
|
$text = preg_replace("!\[img\](.*?)\[/img\]!s", "", $text);
|
||||||
$text = preg_replace("!\[\[([^\|\]]+)\|([^\]]+)\]\]!s", '$2', $text);
|
$text = preg_replace("!\[\[([^\|\]]+)\|([^\]]+)\]\]!s", '$2', $text);
|
||||||
@ -81,7 +91,10 @@ class BBCode extends FormatterExtension {
|
|||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return mixed
|
||||||
|
*/
|
||||||
private function filter_spoiler(/*string*/ $text) {
|
private function filter_spoiler(/*string*/ $text) {
|
||||||
return str_replace(
|
return str_replace(
|
||||||
array("[spoiler]","[/spoiler]"),
|
array("[spoiler]","[/spoiler]"),
|
||||||
@ -89,6 +102,10 @@ class BBCode extends FormatterExtension {
|
|||||||
$text);
|
$text);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function strip_spoiler(/*string*/ $text) {
|
private function strip_spoiler(/*string*/ $text) {
|
||||||
$l1 = strlen("[spoiler]");
|
$l1 = strlen("[spoiler]");
|
||||||
$l2 = strlen("[/spoiler]");
|
$l2 = strlen("[/spoiler]");
|
||||||
@ -110,6 +127,10 @@ class BBCode extends FormatterExtension {
|
|||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function extract_code(/*string*/ $text) {
|
private function extract_code(/*string*/ $text) {
|
||||||
# at the end of this function, the only code! blocks should be
|
# at the end of this function, the only code! blocks should be
|
||||||
# the ones we've added -- others may contain malicious content,
|
# the ones we've added -- others may contain malicious content,
|
||||||
@ -137,6 +158,10 @@ class BBCode extends FormatterExtension {
|
|||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function insert_code(/*string*/ $text) {
|
private function insert_code(/*string*/ $text) {
|
||||||
$l1 = strlen("[code!]");
|
$l1 = strlen("[code!]");
|
||||||
$l2 = strlen("[/code!]");
|
$l2 = strlen("[/code!]");
|
||||||
|
@ -8,3 +8,9 @@ BLOCKQUOTE {
|
|||||||
padding: 8px;
|
padding: 8px;
|
||||||
background: #DDD;
|
background: #DDD;
|
||||||
}
|
}
|
||||||
|
.anchor A.alink {
|
||||||
|
visibility: hidden;
|
||||||
|
}
|
||||||
|
.anchor:hover A.alink {
|
||||||
|
visibility: visible;
|
||||||
|
}
|
||||||
|
@ -71,6 +71,12 @@ class BBCodeUnitTest extends UnitTestCase {
|
|||||||
"<a href=\"mailto:spam@shishnet.org\">spam@shishnet.org</a>");
|
"<a href=\"mailto:spam@shishnet.org\">spam@shishnet.org</a>");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function testAnchor() {
|
||||||
|
$this->assertEqual(
|
||||||
|
$this->filter("[anchor=rules]Rules[/anchor]"),
|
||||||
|
'<span class="anchor">Rules <a class="alink" href="#bb-rules" name="bb-rules" title="link to this anchor"> ¶ </a></span>');
|
||||||
|
}
|
||||||
|
|
||||||
private function filter($in) {
|
private function filter($in) {
|
||||||
$bb = new BBCode();
|
$bb = new BBCode();
|
||||||
return $bb->format($in);
|
return $bb->format($in);
|
||||||
|
@ -32,7 +32,7 @@ class Blocks extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $config, $database, $page, $user;
|
global $database, $page, $user;
|
||||||
|
|
||||||
$blocks = $database->cache->get("blocks");
|
$blocks = $database->cache->get("blocks");
|
||||||
if($blocks === false) {
|
if($blocks === false) {
|
||||||
|
@ -4,7 +4,6 @@ $kioskMode = false;
|
|||||||
|
|
||||||
include '../php/filestorage.class.php';
|
include '../php/filestorage.class.php';
|
||||||
include '../preferences.php';
|
include '../preferences.php';
|
||||||
include '../php/json.class.php';
|
|
||||||
include '../php/functions.php';
|
include '../php/functions.php';
|
||||||
include '../php/yshout.class.php';
|
include '../php/yshout.class.php';
|
||||||
include '../php/ajaxcall.class.php';
|
include '../php/ajaxcall.class.php';
|
||||||
@ -41,7 +40,7 @@ function doLogin() {
|
|||||||
'html' => cp()
|
'html' => cp()
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -53,7 +52,7 @@ function doLogin() {
|
|||||||
} else
|
} else
|
||||||
$result['error'] = 'invalid';
|
$result['error'] = 'invalid';
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
function doLogout() {
|
function doLogout() {
|
||||||
@ -63,7 +62,7 @@ function doLogout() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
function doUnban() {
|
function doUnban() {
|
||||||
@ -74,7 +73,7 @@ function doUnban() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -92,7 +91,7 @@ function doUnban() {
|
|||||||
$result['error'] = 'notbanned';
|
$result['error'] = 'notbanned';
|
||||||
|
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
function doUnbanAll() {
|
function doUnbanAll() {
|
||||||
@ -103,7 +102,7 @@ function doUnbanAll() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -116,7 +115,7 @@ function doUnbanAll() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -128,7 +127,7 @@ function doSetPreference() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -150,7 +149,7 @@ function doSetPreference() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -162,7 +161,7 @@ function doResetPreferences() {
|
|||||||
'error' => false
|
'error' => false
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -177,7 +176,7 @@ function doResetPreferences() {
|
|||||||
'prefs' => $prefs
|
'prefs' => $prefs
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($result);
|
echo json_encode($result);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* CP Display */
|
/* CP Display */
|
||||||
@ -456,4 +455,3 @@ function about() {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
?>
|
|
@ -3,7 +3,6 @@
|
|||||||
|
|
||||||
include '../php/filestorage.class.php';
|
include '../php/filestorage.class.php';
|
||||||
include '../preferences.php';
|
include '../preferences.php';
|
||||||
include '../php/json.class.php';
|
|
||||||
include '../php/functions.php';
|
include '../php/functions.php';
|
||||||
include '../php/yshout.class.php';
|
include '../php/yshout.class.php';
|
||||||
|
|
||||||
|
@ -2,9 +2,7 @@
|
|||||||
$null = null;
|
$null = null;
|
||||||
include 'php/filestorage.class.php';
|
include 'php/filestorage.class.php';
|
||||||
include 'preferences.php';
|
include 'preferences.php';
|
||||||
include 'php/json.class.php';
|
|
||||||
include 'php/functions.php';
|
include 'php/functions.php';
|
||||||
include 'php/yshout.class.php';
|
include 'php/yshout.class.php';
|
||||||
include 'php/ajaxcall.class.php';
|
include 'php/ajaxcall.class.php';
|
||||||
|
|
||||||
?>
|
|
||||||
|
@ -95,7 +95,7 @@
|
|||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function doUnban() {
|
function doUnban() {
|
||||||
@ -115,7 +115,7 @@
|
|||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function doDelete() {
|
function doDelete() {
|
||||||
@ -132,7 +132,7 @@
|
|||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function banSelf() {
|
function banSelf() {
|
||||||
@ -143,7 +143,7 @@
|
|||||||
$send = array();
|
$send = array();
|
||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function unbanSelf() {
|
function unbanSelf() {
|
||||||
@ -158,7 +158,7 @@
|
|||||||
$send['error'] = 'admin';
|
$send['error'] = 'admin';
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function reload() {
|
function reload() {
|
||||||
@ -168,7 +168,7 @@
|
|||||||
$posts = $ys->latestPosts($prefs['truncate']);
|
$posts = $ys->latestPosts($prefs['truncate']);
|
||||||
$this->setSessTimestamp($posts);
|
$this->setSessTimestamp($posts);
|
||||||
$this->updates['posts'] = $posts;
|
$this->updates['posts'] = $posts;
|
||||||
echo jsonEncode($this->updates);
|
echo json_encode($this->updates);
|
||||||
}
|
}
|
||||||
|
|
||||||
function initSession() {
|
function initSession() {
|
||||||
@ -186,7 +186,7 @@
|
|||||||
'banned' => true
|
'banned' => true
|
||||||
);
|
);
|
||||||
|
|
||||||
echo jsonEncode($this->updates);
|
echo json_encode($this->updates);
|
||||||
}
|
}
|
||||||
|
|
||||||
function sendUpdates() {
|
function sendUpdates() {
|
||||||
@ -199,7 +199,7 @@
|
|||||||
|
|
||||||
$this->updates['posts'] = $posts;
|
$this->updates['posts'] = $posts;
|
||||||
|
|
||||||
echo jsonEncode($this->updates);
|
echo json_encode($this->updates);
|
||||||
}
|
}
|
||||||
|
|
||||||
function setSessTimestamp(&$posts) {
|
function setSessTimestamp(&$posts) {
|
||||||
@ -231,7 +231,7 @@
|
|||||||
if ($ys->banned(ip()))
|
if ($ys->banned(ip()))
|
||||||
$this->updates['banned'] = true;
|
$this->updates['banned'] = true;
|
||||||
|
|
||||||
echo jsonEncode($this->updates);
|
echo json_encode($this->updates);
|
||||||
}
|
}
|
||||||
|
|
||||||
function cleanPrefs($prefs) {
|
function cleanPrefs($prefs) {
|
||||||
@ -253,7 +253,7 @@
|
|||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
|
|
||||||
function clearLogs() {
|
function clearLogs() {
|
||||||
@ -277,7 +277,7 @@
|
|||||||
$send['error'] = false;
|
$send['error'] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
echo jsonEncode($send);
|
echo json_encode($send);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -45,19 +45,6 @@
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
function jsonEncode(&$array) {
|
|
||||||
if ($array) {
|
|
||||||
$json = new Services_JSON(SERVICES_JSON_LOOSE_TYPE);
|
|
||||||
return $json->encode($array);
|
|
||||||
} else
|
|
||||||
return 'ar';
|
|
||||||
}
|
|
||||||
|
|
||||||
function jsonDecode($encoded) {
|
|
||||||
$json = new Services_JSON(SERVICES_JSON_LOOSE_TYPE);
|
|
||||||
return $json->decode($encoded);
|
|
||||||
}
|
|
||||||
|
|
||||||
function validIP($ip) {
|
function validIP($ip) {
|
||||||
if ($ip == long2ip(ip2long($ip)))
|
if ($ip == long2ip(ip2long($ip)))
|
||||||
return true;
|
return true;
|
||||||
|
@ -1,805 +0,0 @@
|
|||||||
<?php
|
|
||||||
/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Converts to and from JSON format.
|
|
||||||
*
|
|
||||||
* JSON (JavaScript Object Notation) is a lightweight data-interchange
|
|
||||||
* format. It is easy for humans to read and write. It is easy for machines
|
|
||||||
* to parse and generate. It is based on a subset of the JavaScript
|
|
||||||
* Programming Language, Standard ECMA-262 3rd Edition - December 1999.
|
|
||||||
* This feature can also be found in Python. JSON is a text format that is
|
|
||||||
* completely language independent but uses conventions that are familiar
|
|
||||||
* to programmers of the C-family of languages, including C, C++, C#, Java,
|
|
||||||
* JavaScript, Perl, TCL, and many others. These properties make JSON an
|
|
||||||
* ideal data-interchange language.
|
|
||||||
*
|
|
||||||
* This package provides a simple encoder and decoder for JSON notation. It
|
|
||||||
* is intended for use with client-side Javascript applications that make
|
|
||||||
* use of HTTPRequest to perform server communication functions - data can
|
|
||||||
* be encoded into JSON notation for use in a client-side javascript, or
|
|
||||||
* decoded from incoming Javascript requests. JSON format is native to
|
|
||||||
* Javascript, and can be directly eval()'ed with no further parsing
|
|
||||||
* overhead
|
|
||||||
*
|
|
||||||
* All strings should be in ASCII or UTF-8 format!
|
|
||||||
*
|
|
||||||
* LICENSE: Redistribution and use in source and binary forms, with or
|
|
||||||
* without modification, are permitted provided that the following
|
|
||||||
* conditions are met: Redistributions of source code must retain the
|
|
||||||
* above copyright notice, this list of conditions and the following
|
|
||||||
* disclaimer. Redistributions in binary form must reproduce the above
|
|
||||||
* copyright notice, this list of conditions and the following disclaimer
|
|
||||||
* in the documentation and/or other materials provided with the
|
|
||||||
* distribution.
|
|
||||||
*
|
|
||||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
|
||||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
|
||||||
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
|
|
||||||
* NO EVENT SHALL CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
||||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
|
||||||
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
|
||||||
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
|
||||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
|
|
||||||
* TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
|
|
||||||
* USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
|
|
||||||
* DAMAGE.
|
|
||||||
*
|
|
||||||
* @category
|
|
||||||
* @package Services_JSON
|
|
||||||
* @author Michal Migurski <mike-json@teczno.com>
|
|
||||||
* @author Matt Knapp <mdknapp[at]gmail[dot]com>
|
|
||||||
* @author Brett Stimmerman <brettstimmerman[at]gmail[dot]com>
|
|
||||||
* @copyright 2005 Michal Migurski
|
|
||||||
* @version CVS: $Id: JSON.php,v 1.30 2006/03/08 16:10:20 migurski Exp $
|
|
||||||
* @license http://www.opensource.org/licenses/bsd-license.php
|
|
||||||
* @link http://pear.php.net/pepr/pepr-proposal-show.php?id=198
|
|
||||||
*/
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Marker constant for Services_JSON::decode(), used to flag stack state
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_SLICE', 1);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Marker constant for Services_JSON::decode(), used to flag stack state
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_IN_STR', 2);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Marker constant for Services_JSON::decode(), used to flag stack state
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_IN_ARR', 3);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Marker constant for Services_JSON::decode(), used to flag stack state
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_IN_OBJ', 4);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Marker constant for Services_JSON::decode(), used to flag stack state
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_IN_CMT', 5);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Behavior switch for Services_JSON::decode()
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_LOOSE_TYPE', 16);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Behavior switch for Services_JSON::decode()
|
|
||||||
*/
|
|
||||||
define('SERVICES_JSON_SUPPRESS_ERRORS', 32);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Converts to and from JSON format.
|
|
||||||
*
|
|
||||||
* Brief example of use:
|
|
||||||
*
|
|
||||||
* <code>
|
|
||||||
* // create a new instance of Services_JSON
|
|
||||||
* $json = new Services_JSON();
|
|
||||||
*
|
|
||||||
* // convert a complexe value to JSON notation, and send it to the browser
|
|
||||||
* $value = array('foo', 'bar', array(1, 2, 'baz'), array(3, array(4)));
|
|
||||||
* $output = $json->encode($value);
|
|
||||||
*
|
|
||||||
* print($output);
|
|
||||||
* // prints: ["foo","bar",[1,2,"baz"],[3,[4]]]
|
|
||||||
*
|
|
||||||
* // accept incoming POST data, assumed to be in JSON notation
|
|
||||||
* $input = file_get_contents('php://input', 1000000);
|
|
||||||
* $value = $json->decode($input);
|
|
||||||
* </code>
|
|
||||||
*/
|
|
||||||
class Services_JSON
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* constructs a new JSON instance
|
|
||||||
*
|
|
||||||
* @param int $use object behavior flags; combine with boolean-OR
|
|
||||||
*
|
|
||||||
* possible values:
|
|
||||||
* - SERVICES_JSON_LOOSE_TYPE: loose typing.
|
|
||||||
* "{...}" syntax creates associative arrays
|
|
||||||
* instead of objects in decode().
|
|
||||||
* - SERVICES_JSON_SUPPRESS_ERRORS: error suppression.
|
|
||||||
* Values which can't be encoded (e.g. resources)
|
|
||||||
* appear as NULL instead of throwing errors.
|
|
||||||
* By default, a deeply-nested resource will
|
|
||||||
* bubble up with an error, so all return values
|
|
||||||
* from encode() should be checked with isError()
|
|
||||||
*/
|
|
||||||
function Services_JSON($use = 0)
|
|
||||||
{
|
|
||||||
$this->use = $use;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* convert a string from one UTF-16 char to one UTF-8 char
|
|
||||||
*
|
|
||||||
* Normally should be handled by mb_convert_encoding, but
|
|
||||||
* provides a slower PHP-only method for installations
|
|
||||||
* that lack the multibye string extension.
|
|
||||||
*
|
|
||||||
* @param string $utf16 UTF-16 character
|
|
||||||
* @return string UTF-8 character
|
|
||||||
* @access private
|
|
||||||
*/
|
|
||||||
function utf162utf8($utf16)
|
|
||||||
{
|
|
||||||
// oh please oh please oh please oh please oh please
|
|
||||||
if(function_exists('mb_convert_encoding')) {
|
|
||||||
return mb_convert_encoding($utf16, 'UTF-8', 'UTF-16');
|
|
||||||
}
|
|
||||||
|
|
||||||
$bytes = (ord($utf16{0}) << 8) | ord($utf16{1});
|
|
||||||
|
|
||||||
switch(true) {
|
|
||||||
case ((0x7F & $bytes) == $bytes):
|
|
||||||
// this case should never be reached, because we are in ASCII range
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return chr(0x7F & $bytes);
|
|
||||||
|
|
||||||
case (0x07FF & $bytes) == $bytes:
|
|
||||||
// return a 2-byte UTF-8 character
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return chr(0xC0 | (($bytes >> 6) & 0x1F))
|
|
||||||
. chr(0x80 | ($bytes & 0x3F));
|
|
||||||
|
|
||||||
case (0xFFFF & $bytes) == $bytes:
|
|
||||||
// return a 3-byte UTF-8 character
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return chr(0xE0 | (($bytes >> 12) & 0x0F))
|
|
||||||
. chr(0x80 | (($bytes >> 6) & 0x3F))
|
|
||||||
. chr(0x80 | ($bytes & 0x3F));
|
|
||||||
}
|
|
||||||
|
|
||||||
// ignoring UTF-32 for now, sorry
|
|
||||||
return '';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* convert a string from one UTF-8 char to one UTF-16 char
|
|
||||||
*
|
|
||||||
* Normally should be handled by mb_convert_encoding, but
|
|
||||||
* provides a slower PHP-only method for installations
|
|
||||||
* that lack the multibye string extension.
|
|
||||||
*
|
|
||||||
* @param string $utf8 UTF-8 character
|
|
||||||
* @return string UTF-16 character
|
|
||||||
* @access private
|
|
||||||
*/
|
|
||||||
function utf82utf16($utf8)
|
|
||||||
{
|
|
||||||
// oh please oh please oh please oh please oh please
|
|
||||||
if(function_exists('mb_convert_encoding')) {
|
|
||||||
return mb_convert_encoding($utf8, 'UTF-16', 'UTF-8');
|
|
||||||
}
|
|
||||||
|
|
||||||
switch(strlen($utf8)) {
|
|
||||||
case 1:
|
|
||||||
// this case should never be reached, because we are in ASCII range
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return $utf8;
|
|
||||||
|
|
||||||
case 2:
|
|
||||||
// return a UTF-16 character from a 2-byte UTF-8 char
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return chr(0x07 & (ord($utf8{0}) >> 2))
|
|
||||||
. chr((0xC0 & (ord($utf8{0}) << 6))
|
|
||||||
| (0x3F & ord($utf8{1})));
|
|
||||||
|
|
||||||
case 3:
|
|
||||||
// return a UTF-16 character from a 3-byte UTF-8 char
|
|
||||||
// see: http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
return chr((0xF0 & (ord($utf8{0}) << 4))
|
|
||||||
| (0x0F & (ord($utf8{1}) >> 2)))
|
|
||||||
. chr((0xC0 & (ord($utf8{1}) << 6))
|
|
||||||
| (0x7F & ord($utf8{2})));
|
|
||||||
}
|
|
||||||
|
|
||||||
// ignoring UTF-32 for now, sorry
|
|
||||||
return '';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* encodes an arbitrary variable into JSON format
|
|
||||||
*
|
|
||||||
* @param mixed $var any number, boolean, string, array, or object to be encoded.
|
|
||||||
* see argument 1 to Services_JSON() above for array-parsing behavior.
|
|
||||||
* if var is a strng, note that encode() always expects it
|
|
||||||
* to be in ASCII or UTF-8 format!
|
|
||||||
*
|
|
||||||
* @return mixed JSON string representation of input var or an error if a problem occurs
|
|
||||||
* @access public
|
|
||||||
*/
|
|
||||||
function encode($var)
|
|
||||||
{
|
|
||||||
switch (gettype($var)) {
|
|
||||||
case 'boolean':
|
|
||||||
return $var ? 'true' : 'false';
|
|
||||||
|
|
||||||
case 'NULL':
|
|
||||||
return 'null';
|
|
||||||
|
|
||||||
case 'integer':
|
|
||||||
return (int) $var;
|
|
||||||
|
|
||||||
case 'double':
|
|
||||||
case 'float':
|
|
||||||
return (float) $var;
|
|
||||||
|
|
||||||
case 'string':
|
|
||||||
// STRINGS ARE EXPECTED TO BE IN ASCII OR UTF-8 FORMAT
|
|
||||||
$ascii = '';
|
|
||||||
$strlen_var = strlen($var);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Iterate over every character in the string,
|
|
||||||
* escaping with a slash or encoding to UTF-8 where necessary
|
|
||||||
*/
|
|
||||||
for ($c = 0; $c < $strlen_var; ++$c) {
|
|
||||||
|
|
||||||
$ord_var_c = ord($var{$c});
|
|
||||||
|
|
||||||
switch (true) {
|
|
||||||
case $ord_var_c == 0x08:
|
|
||||||
$ascii .= '\b';
|
|
||||||
break;
|
|
||||||
case $ord_var_c == 0x09:
|
|
||||||
$ascii .= '\t';
|
|
||||||
break;
|
|
||||||
case $ord_var_c == 0x0A:
|
|
||||||
$ascii .= '\n';
|
|
||||||
break;
|
|
||||||
case $ord_var_c == 0x0C:
|
|
||||||
$ascii .= '\f';
|
|
||||||
break;
|
|
||||||
case $ord_var_c == 0x0D:
|
|
||||||
$ascii .= '\r';
|
|
||||||
break;
|
|
||||||
|
|
||||||
case $ord_var_c == 0x22:
|
|
||||||
case $ord_var_c == 0x2F:
|
|
||||||
case $ord_var_c == 0x5C:
|
|
||||||
// double quote, slash, slosh
|
|
||||||
$ascii .= '\\'.$var{$c};
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c >= 0x20) && ($ord_var_c <= 0x7F)):
|
|
||||||
// characters U-00000000 - U-0000007F (same as ASCII)
|
|
||||||
$ascii .= $var{$c};
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c & 0xE0) == 0xC0):
|
|
||||||
// characters U-00000080 - U-000007FF, mask 110XXXXX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$char = pack('C*', $ord_var_c, ord($var{$c + 1}));
|
|
||||||
$c += 1;
|
|
||||||
$utf16 = $this->utf82utf16($char);
|
|
||||||
$ascii .= sprintf('\u%04s', bin2hex($utf16));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c & 0xF0) == 0xE0):
|
|
||||||
// characters U-00000800 - U-0000FFFF, mask 1110XXXX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$char = pack('C*', $ord_var_c,
|
|
||||||
ord($var{$c + 1}),
|
|
||||||
ord($var{$c + 2}));
|
|
||||||
$c += 2;
|
|
||||||
$utf16 = $this->utf82utf16($char);
|
|
||||||
$ascii .= sprintf('\u%04s', bin2hex($utf16));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c & 0xF8) == 0xF0):
|
|
||||||
// characters U-00010000 - U-001FFFFF, mask 11110XXX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$char = pack('C*', $ord_var_c,
|
|
||||||
ord($var{$c + 1}),
|
|
||||||
ord($var{$c + 2}),
|
|
||||||
ord($var{$c + 3}));
|
|
||||||
$c += 3;
|
|
||||||
$utf16 = $this->utf82utf16($char);
|
|
||||||
$ascii .= sprintf('\u%04s', bin2hex($utf16));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c & 0xFC) == 0xF8):
|
|
||||||
// characters U-00200000 - U-03FFFFFF, mask 111110XX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$char = pack('C*', $ord_var_c,
|
|
||||||
ord($var{$c + 1}),
|
|
||||||
ord($var{$c + 2}),
|
|
||||||
ord($var{$c + 3}),
|
|
||||||
ord($var{$c + 4}));
|
|
||||||
$c += 4;
|
|
||||||
$utf16 = $this->utf82utf16($char);
|
|
||||||
$ascii .= sprintf('\u%04s', bin2hex($utf16));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case (($ord_var_c & 0xFE) == 0xFC):
|
|
||||||
// characters U-04000000 - U-7FFFFFFF, mask 1111110X
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$char = pack('C*', $ord_var_c,
|
|
||||||
ord($var{$c + 1}),
|
|
||||||
ord($var{$c + 2}),
|
|
||||||
ord($var{$c + 3}),
|
|
||||||
ord($var{$c + 4}),
|
|
||||||
ord($var{$c + 5}));
|
|
||||||
$c += 5;
|
|
||||||
$utf16 = $this->utf82utf16($char);
|
|
||||||
$ascii .= sprintf('\u%04s', bin2hex($utf16));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return '"'.$ascii.'"';
|
|
||||||
|
|
||||||
case 'array':
|
|
||||||
/*
|
|
||||||
* As per JSON spec if any array key is not an integer
|
|
||||||
* we must treat the the whole array as an object. We
|
|
||||||
* also try to catch a sparsely populated associative
|
|
||||||
* array with numeric keys here because some JS engines
|
|
||||||
* will create an array with empty indexes up to
|
|
||||||
* max_index which can cause memory issues and because
|
|
||||||
* the keys, which may be relevant, will be remapped
|
|
||||||
* otherwise.
|
|
||||||
*
|
|
||||||
* As per the ECMA and JSON specification an object may
|
|
||||||
* have any string as a property. Unfortunately due to
|
|
||||||
* a hole in the ECMA specification if the key is a
|
|
||||||
* ECMA reserved word or starts with a digit the
|
|
||||||
* parameter is only accessible using ECMAScript's
|
|
||||||
* bracket notation.
|
|
||||||
*/
|
|
||||||
|
|
||||||
// treat as a JSON object
|
|
||||||
if (is_array($var) && count($var) && (array_keys($var) !== range(0, sizeof($var) - 1))) {
|
|
||||||
$properties = array_map(array($this, 'name_value'),
|
|
||||||
array_keys($var),
|
|
||||||
array_values($var));
|
|
||||||
|
|
||||||
foreach($properties as $property) {
|
|
||||||
if(Services_JSON::isError($property)) {
|
|
||||||
return $property;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return '{' . join(',', $properties) . '}';
|
|
||||||
}
|
|
||||||
|
|
||||||
// treat it like a regular array
|
|
||||||
$elements = array_map(array($this, 'encode'), $var);
|
|
||||||
|
|
||||||
foreach($elements as $element) {
|
|
||||||
if(Services_JSON::isError($element)) {
|
|
||||||
return $element;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return '[' . join(',', $elements) . ']';
|
|
||||||
|
|
||||||
case 'object':
|
|
||||||
$vars = get_object_vars($var);
|
|
||||||
|
|
||||||
$properties = array_map(array($this, 'name_value'),
|
|
||||||
array_keys($vars),
|
|
||||||
array_values($vars));
|
|
||||||
|
|
||||||
foreach($properties as $property) {
|
|
||||||
if(Services_JSON::isError($property)) {
|
|
||||||
return $property;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return '{' . join(',', $properties) . '}';
|
|
||||||
|
|
||||||
default:
|
|
||||||
return ($this->use & SERVICES_JSON_SUPPRESS_ERRORS)
|
|
||||||
? 'null'
|
|
||||||
: new Services_JSON_Error(gettype($var)." can not be encoded as JSON string");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* array-walking function for use in generating JSON-formatted name-value pairs
|
|
||||||
*
|
|
||||||
* @param string $name name of key to use
|
|
||||||
* @param mixed $value reference to an array element to be encoded
|
|
||||||
*
|
|
||||||
* @return string JSON-formatted name-value pair, like '"name":value'
|
|
||||||
* @access private
|
|
||||||
*/
|
|
||||||
function name_value($name, $value)
|
|
||||||
{
|
|
||||||
$encoded_value = $this->encode($value);
|
|
||||||
|
|
||||||
if(Services_JSON::isError($encoded_value)) {
|
|
||||||
return $encoded_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $this->encode(strval($name)) . ':' . $encoded_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* reduce a string by removing leading and trailing comments and whitespace
|
|
||||||
*
|
|
||||||
* @param $str string string value to strip of comments and whitespace
|
|
||||||
*
|
|
||||||
* @return string string value stripped of comments and whitespace
|
|
||||||
* @access private
|
|
||||||
*/
|
|
||||||
function reduce_string($str)
|
|
||||||
{
|
|
||||||
$str = preg_replace(array(
|
|
||||||
|
|
||||||
// eliminate single line comments in '// ...' form
|
|
||||||
'#^\s*//(.+)$#m',
|
|
||||||
|
|
||||||
// eliminate multi-line comments in '/* ... */' form, at start of string
|
|
||||||
'#^\s*/\*(.+)\*/#Us',
|
|
||||||
|
|
||||||
// eliminate multi-line comments in '/* ... */' form, at end of string
|
|
||||||
'#/\*(.+)\*/\s*$#Us'
|
|
||||||
|
|
||||||
), '', $str);
|
|
||||||
|
|
||||||
// eliminate extraneous space
|
|
||||||
return trim($str);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* decodes a JSON string into appropriate variable
|
|
||||||
*
|
|
||||||
* @param string $str JSON-formatted string
|
|
||||||
*
|
|
||||||
* @return mixed number, boolean, string, array, or object
|
|
||||||
* corresponding to given JSON input string.
|
|
||||||
* See argument 1 to Services_JSON() above for object-output behavior.
|
|
||||||
* Note that decode() always returns strings
|
|
||||||
* in ASCII or UTF-8 format!
|
|
||||||
* @access public
|
|
||||||
*/
|
|
||||||
function decode($str)
|
|
||||||
{
|
|
||||||
$str = $this->reduce_string($str);
|
|
||||||
|
|
||||||
switch (strtolower($str)) {
|
|
||||||
case 'true':
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case 'false':
|
|
||||||
return false;
|
|
||||||
|
|
||||||
case 'null':
|
|
||||||
return null;
|
|
||||||
|
|
||||||
default:
|
|
||||||
$m = array();
|
|
||||||
|
|
||||||
if (is_numeric($str)) {
|
|
||||||
// Lookie-loo, it's a number
|
|
||||||
|
|
||||||
// This would work on its own, but I'm trying to be
|
|
||||||
// good about returning integers where appropriate:
|
|
||||||
// return (float)$str;
|
|
||||||
|
|
||||||
// Return float or int, as appropriate
|
|
||||||
return ((float)$str == (integer)$str)
|
|
||||||
? (integer)$str
|
|
||||||
: (float)$str;
|
|
||||||
|
|
||||||
} elseif (preg_match('/^("|\').*(\1)$/s', $str, $m) && $m[1] == $m[2]) {
|
|
||||||
// STRINGS RETURNED IN UTF-8 FORMAT
|
|
||||||
$delim = substr($str, 0, 1);
|
|
||||||
$chrs = substr($str, 1, -1);
|
|
||||||
$utf8 = '';
|
|
||||||
$strlen_chrs = strlen($chrs);
|
|
||||||
|
|
||||||
for ($c = 0; $c < $strlen_chrs; ++$c) {
|
|
||||||
|
|
||||||
$substr_chrs_c_2 = substr($chrs, $c, 2);
|
|
||||||
$ord_chrs_c = ord($chrs{$c});
|
|
||||||
|
|
||||||
switch (true) {
|
|
||||||
case $substr_chrs_c_2 == '\b':
|
|
||||||
$utf8 .= chr(0x08);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
case $substr_chrs_c_2 == '\t':
|
|
||||||
$utf8 .= chr(0x09);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
case $substr_chrs_c_2 == '\n':
|
|
||||||
$utf8 .= chr(0x0A);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
case $substr_chrs_c_2 == '\f':
|
|
||||||
$utf8 .= chr(0x0C);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
case $substr_chrs_c_2 == '\r':
|
|
||||||
$utf8 .= chr(0x0D);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case $substr_chrs_c_2 == '\\"':
|
|
||||||
case $substr_chrs_c_2 == '\\\'':
|
|
||||||
case $substr_chrs_c_2 == '\\\\':
|
|
||||||
case $substr_chrs_c_2 == '\\/':
|
|
||||||
if (($delim == '"' && $substr_chrs_c_2 != '\\\'') ||
|
|
||||||
($delim == "'" && $substr_chrs_c_2 != '\\"')) {
|
|
||||||
$utf8 .= $chrs{++$c};
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case preg_match('/\\\u[0-9A-F]{4}/i', substr($chrs, $c, 6)):
|
|
||||||
// single, escaped unicode character
|
|
||||||
$utf16 = chr(hexdec(substr($chrs, ($c + 2), 2)))
|
|
||||||
. chr(hexdec(substr($chrs, ($c + 4), 2)));
|
|
||||||
$utf8 .= $this->utf162utf8($utf16);
|
|
||||||
$c += 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c >= 0x20) && ($ord_chrs_c <= 0x7F):
|
|
||||||
$utf8 .= $chrs{$c};
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c & 0xE0) == 0xC0:
|
|
||||||
// characters U-00000080 - U-000007FF, mask 110XXXXX
|
|
||||||
//see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$utf8 .= substr($chrs, $c, 2);
|
|
||||||
++$c;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c & 0xF0) == 0xE0:
|
|
||||||
// characters U-00000800 - U-0000FFFF, mask 1110XXXX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$utf8 .= substr($chrs, $c, 3);
|
|
||||||
$c += 2;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c & 0xF8) == 0xF0:
|
|
||||||
// characters U-00010000 - U-001FFFFF, mask 11110XXX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$utf8 .= substr($chrs, $c, 4);
|
|
||||||
$c += 3;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c & 0xFC) == 0xF8:
|
|
||||||
// characters U-00200000 - U-03FFFFFF, mask 111110XX
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$utf8 .= substr($chrs, $c, 5);
|
|
||||||
$c += 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ($ord_chrs_c & 0xFE) == 0xFC:
|
|
||||||
// characters U-04000000 - U-7FFFFFFF, mask 1111110X
|
|
||||||
// see http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8
|
|
||||||
$utf8 .= substr($chrs, $c, 6);
|
|
||||||
$c += 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
return $utf8;
|
|
||||||
|
|
||||||
} elseif (preg_match('/^\[.*\]$/s', $str) || preg_match('/^\{.*\}$/s', $str)) {
|
|
||||||
// array, or object notation
|
|
||||||
|
|
||||||
if ($str{0} == '[') {
|
|
||||||
$stk = array(SERVICES_JSON_IN_ARR);
|
|
||||||
$arr = array();
|
|
||||||
} else {
|
|
||||||
if ($this->use & SERVICES_JSON_LOOSE_TYPE) {
|
|
||||||
$stk = array(SERVICES_JSON_IN_OBJ);
|
|
||||||
$obj = array();
|
|
||||||
} else {
|
|
||||||
$stk = array(SERVICES_JSON_IN_OBJ);
|
|
||||||
$obj = new stdClass();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_SLICE,
|
|
||||||
'where' => 0,
|
|
||||||
'delim' => false));
|
|
||||||
|
|
||||||
$chrs = substr($str, 1, -1);
|
|
||||||
$chrs = $this->reduce_string($chrs);
|
|
||||||
|
|
||||||
if ($chrs == '') {
|
|
||||||
if (reset($stk) == SERVICES_JSON_IN_ARR) {
|
|
||||||
return $arr;
|
|
||||||
|
|
||||||
} else {
|
|
||||||
return $obj;
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//print("\nparsing {$chrs}\n");
|
|
||||||
|
|
||||||
$strlen_chrs = strlen($chrs);
|
|
||||||
|
|
||||||
for ($c = 0; $c <= $strlen_chrs; ++$c) {
|
|
||||||
|
|
||||||
$top = end($stk);
|
|
||||||
$substr_chrs_c_2 = substr($chrs, $c, 2);
|
|
||||||
|
|
||||||
if (($c == $strlen_chrs) || (($chrs{$c} == ',') && ($top['what'] == SERVICES_JSON_SLICE))) {
|
|
||||||
// found a comma that is not inside a string, array, etc.,
|
|
||||||
// OR we've reached the end of the character list
|
|
||||||
$slice = substr($chrs, $top['where'], ($c - $top['where']));
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_SLICE, 'where' => ($c + 1), 'delim' => false));
|
|
||||||
//print("Found split at {$c}: ".substr($chrs, $top['where'], (1 + $c - $top['where']))."\n");
|
|
||||||
|
|
||||||
if (reset($stk) == SERVICES_JSON_IN_ARR) {
|
|
||||||
// we are in an array, so just push an element onto the stack
|
|
||||||
array_push($arr, $this->decode($slice));
|
|
||||||
|
|
||||||
} elseif (reset($stk) == SERVICES_JSON_IN_OBJ) {
|
|
||||||
// we are in an object, so figure
|
|
||||||
// out the property name and set an
|
|
||||||
// element in an associative array,
|
|
||||||
// for now
|
|
||||||
$parts = array();
|
|
||||||
|
|
||||||
if (preg_match('/^\s*(["\'].*[^\\\]["\'])\s*:\s*(\S.*),?$/Uis', $slice, $parts)) {
|
|
||||||
// "name":value pair
|
|
||||||
$key = $this->decode($parts[1]);
|
|
||||||
$val = $this->decode($parts[2]);
|
|
||||||
|
|
||||||
if ($this->use & SERVICES_JSON_LOOSE_TYPE) {
|
|
||||||
$obj[$key] = $val;
|
|
||||||
} else {
|
|
||||||
$obj->$key = $val;
|
|
||||||
}
|
|
||||||
} elseif (preg_match('/^\s*(\w+)\s*:\s*(\S.*),?$/Uis', $slice, $parts)) {
|
|
||||||
// name:value pair, where name is unquoted
|
|
||||||
$key = $parts[1];
|
|
||||||
$val = $this->decode($parts[2]);
|
|
||||||
|
|
||||||
if ($this->use & SERVICES_JSON_LOOSE_TYPE) {
|
|
||||||
$obj[$key] = $val;
|
|
||||||
} else {
|
|
||||||
$obj->$key = $val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
} elseif ((($chrs{$c} == '"') || ($chrs{$c} == "'")) && ($top['what'] != SERVICES_JSON_IN_STR)) {
|
|
||||||
// found a quote, and we are not inside a string
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_IN_STR, 'where' => $c, 'delim' => $chrs{$c}));
|
|
||||||
//print("Found start of string at {$c}\n");
|
|
||||||
|
|
||||||
} elseif (($chrs{$c} == $top['delim']) &&
|
|
||||||
($top['what'] == SERVICES_JSON_IN_STR) &&
|
|
||||||
(($chrs{$c - 1} != '\\') ||
|
|
||||||
($chrs{$c - 1} == '\\' && $chrs{$c - 2} == '\\'))) {
|
|
||||||
// found a quote, we're in a string, and it's not escaped
|
|
||||||
array_pop($stk);
|
|
||||||
//print("Found end of string at {$c}: ".substr($chrs, $top['where'], (1 + 1 + $c - $top['where']))."\n");
|
|
||||||
|
|
||||||
} elseif (($chrs{$c} == '[') &&
|
|
||||||
in_array($top['what'], array(SERVICES_JSON_SLICE, SERVICES_JSON_IN_ARR, SERVICES_JSON_IN_OBJ))) {
|
|
||||||
// found a left-bracket, and we are in an array, object, or slice
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_IN_ARR, 'where' => $c, 'delim' => false));
|
|
||||||
//print("Found start of array at {$c}\n");
|
|
||||||
|
|
||||||
} elseif (($chrs{$c} == ']') && ($top['what'] == SERVICES_JSON_IN_ARR)) {
|
|
||||||
// found a right-bracket, and we're in an array
|
|
||||||
array_pop($stk);
|
|
||||||
//print("Found end of array at {$c}: ".substr($chrs, $top['where'], (1 + $c - $top['where']))."\n");
|
|
||||||
|
|
||||||
} elseif (($chrs{$c} == '{') &&
|
|
||||||
in_array($top['what'], array(SERVICES_JSON_SLICE, SERVICES_JSON_IN_ARR, SERVICES_JSON_IN_OBJ))) {
|
|
||||||
// found a left-brace, and we are in an array, object, or slice
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_IN_OBJ, 'where' => $c, 'delim' => false));
|
|
||||||
//print("Found start of object at {$c}\n");
|
|
||||||
|
|
||||||
} elseif (($chrs{$c} == '}') && ($top['what'] == SERVICES_JSON_IN_OBJ)) {
|
|
||||||
// found a right-brace, and we're in an object
|
|
||||||
array_pop($stk);
|
|
||||||
//print("Found end of object at {$c}: ".substr($chrs, $top['where'], (1 + $c - $top['where']))."\n");
|
|
||||||
|
|
||||||
} elseif (($substr_chrs_c_2 == '/*') &&
|
|
||||||
in_array($top['what'], array(SERVICES_JSON_SLICE, SERVICES_JSON_IN_ARR, SERVICES_JSON_IN_OBJ))) {
|
|
||||||
// found a comment start, and we are in an array, object, or slice
|
|
||||||
array_push($stk, array('what' => SERVICES_JSON_IN_CMT, 'where' => $c, 'delim' => false));
|
|
||||||
$c++;
|
|
||||||
//print("Found start of comment at {$c}\n");
|
|
||||||
|
|
||||||
} elseif (($substr_chrs_c_2 == '*/') && ($top['what'] == SERVICES_JSON_IN_CMT)) {
|
|
||||||
// found a comment end, and we're in one now
|
|
||||||
array_pop($stk);
|
|
||||||
$c++;
|
|
||||||
|
|
||||||
for ($i = $top['where']; $i <= $c; ++$i)
|
|
||||||
$chrs = substr_replace($chrs, ' ', $i, 1);
|
|
||||||
|
|
||||||
//print("Found end of comment at {$c}: ".substr($chrs, $top['where'], (1 + $c - $top['where']))."\n");
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if (reset($stk) == SERVICES_JSON_IN_ARR) {
|
|
||||||
return $arr;
|
|
||||||
|
|
||||||
} elseif (reset($stk) == SERVICES_JSON_IN_OBJ) {
|
|
||||||
return $obj;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @todo Ultimately, this should just call PEAR::isError()
|
|
||||||
*/
|
|
||||||
function isError($data, $code = null)
|
|
||||||
{
|
|
||||||
if (class_exists('pear')) {
|
|
||||||
return PEAR::isError($data, $code);
|
|
||||||
} elseif (is_object($data) && (get_class($data) == 'services_json_error' ||
|
|
||||||
is_subclass_of($data, 'services_json_error'))) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (class_exists('PEAR_Error')) {
|
|
||||||
|
|
||||||
class Services_JSON_Error extends PEAR_Error
|
|
||||||
{
|
|
||||||
function Services_JSON_Error($message = 'unknown error', $code = null,
|
|
||||||
$mode = null, $options = null, $userinfo = null)
|
|
||||||
{
|
|
||||||
parent::PEAR_Error($message, $code, $mode, $options, $userinfo);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @todo Ultimately, this class shall be descended from PEAR_Error
|
|
||||||
*/
|
|
||||||
class Services_JSON_Error
|
|
||||||
{
|
|
||||||
function Services_JSON_Error($message = 'unknown error', $code = null,
|
|
||||||
$mode = null, $options = null, $userinfo = null)
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
?>
|
|
@ -246,7 +246,6 @@ class YShout {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,8 +1,10 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
error_reporting(E_ALL);
|
error_reporting(E_ALL);
|
||||||
ob_start();
|
ob_start();
|
||||||
set_error_handler('errorOccurred');
|
set_error_handler('errorOccurred');
|
||||||
include 'include.php';
|
include 'include.php';
|
||||||
|
|
||||||
if (isset($_POST['reqFor']))
|
if (isset($_POST['reqFor']))
|
||||||
switch($_POST['reqFor']) {
|
switch($_POST['reqFor']) {
|
||||||
case 'shout':
|
case 'shout':
|
||||||
@ -20,20 +22,17 @@ if (isset($_POST['reqFor']))
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
exit;
|
exit;
|
||||||
|
} else {
|
||||||
|
include 'example.html';
|
||||||
}
|
}
|
||||||
else
|
|
||||||
include 'example.html';
|
|
||||||
|
|
||||||
function errorOccurred($num, $str, $file, $line) {
|
function errorOccurred($num, $str, $file, $line) {
|
||||||
$err = array (
|
$err = array (
|
||||||
'yError' => "$str. \n File: $file \n Line: $line"
|
'yError' => "$str. \n File: $file \n Line: $line"
|
||||||
);
|
);
|
||||||
|
|
||||||
if (function_exists('jsonEncode'))
|
echo json_encode($err);
|
||||||
echo jsonEncode($err);
|
|
||||||
else
|
|
||||||
echo $err['yError'];
|
|
||||||
exit;
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
?>
|
|
@ -12,8 +12,18 @@
|
|||||||
require_once "lib/akismet.class.php";
|
require_once "lib/akismet.class.php";
|
||||||
|
|
||||||
class CommentPostingEvent extends Event {
|
class CommentPostingEvent extends Event {
|
||||||
var $image_id, $user, $comment;
|
/** @var int */
|
||||||
|
public $image_id;
|
||||||
|
/** @var \User */
|
||||||
|
public $user;
|
||||||
|
/** @var string */
|
||||||
|
public $comment;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param \User $user
|
||||||
|
* @param string $comment
|
||||||
|
*/
|
||||||
public function __construct($image_id, $user, $comment) {
|
public function __construct($image_id, $user, $comment) {
|
||||||
$this->image_id = $image_id;
|
$this->image_id = $image_id;
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
@ -27,8 +37,12 @@ class CommentPostingEvent extends Event {
|
|||||||
* and what should be kept?
|
* and what should be kept?
|
||||||
*/
|
*/
|
||||||
class CommentDeletionEvent extends Event {
|
class CommentDeletionEvent extends Event {
|
||||||
var $comment_id;
|
/** @var int */
|
||||||
|
public $comment_id;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $comment_id
|
||||||
|
*/
|
||||||
public function __construct($comment_id) {
|
public function __construct($comment_id) {
|
||||||
$this->comment_id = $comment_id;
|
$this->comment_id = $comment_id;
|
||||||
}
|
}
|
||||||
@ -54,11 +68,18 @@ class Comment {
|
|||||||
$this->posted = $row['posted'];
|
$this->posted = $row['posted'];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \User $user
|
||||||
|
* @return mixed
|
||||||
|
*/
|
||||||
public static function count_comments_by_user($user) {
|
public static function count_comments_by_user($user) {
|
||||||
global $database;
|
global $database;
|
||||||
return $database->get_one("SELECT COUNT(*) AS count FROM comments WHERE owner_id=:owner_id", array("owner_id"=>$user->id));
|
return $database->get_one("SELECT COUNT(*) AS count FROM comments WHERE owner_id=:owner_id", array("owner_id"=>$user->id));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return null|User
|
||||||
|
*/
|
||||||
public function get_owner() {
|
public function get_owner() {
|
||||||
if(empty($this->owner)) $this->owner = User::by_id($this->owner_id);
|
if(empty($this->owner)) $this->owner = User::by_id($this->owner_id);
|
||||||
return $this->owner;
|
return $this->owner;
|
||||||
@ -265,19 +286,20 @@ class CommentList extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onSearchTermParse(SearchTermParseEvent $event) {
|
public function onSearchTermParse(SearchTermParseEvent $event) {
|
||||||
|
global $database;
|
||||||
|
|
||||||
$matches = array();
|
$matches = array();
|
||||||
|
|
||||||
if(preg_match("/^comments([:]?<|[:]?>|[:]?<=|[:]?>=|[:|=])(\d+)$/i", $event->term, $matches)) {
|
if(preg_match("/^comments([:]?<|[:]?>|[:]?<=|[:]?>=|[:|=])(\d+)$/i", $event->term, $matches)) {
|
||||||
$cmp = ltrim($matches[1], ":") ?: "=";
|
$cmp = ltrim($matches[1], ":") ?: "=";
|
||||||
$comments = $matches[2];
|
$comments = $matches[2];
|
||||||
$event->add_querylet(new Querylet("images.id IN (SELECT DISTINCT image_id FROM comments GROUP BY image_id HAVING count(image_id) $cmp $comments)"));
|
$event->add_querylet(new Querylet("images.id IN (SELECT DISTINCT image_id FROM comments GROUP BY image_id HAVING count(image_id) $cmp $comments)"));
|
||||||
}
|
}
|
||||||
else if(preg_match("/^commented_by[=|:](.*)$/i", $event->term, $matches)) {
|
else if(preg_match("/^commented_by[=|:](.*)$/i", $event->term, $matches)) {
|
||||||
global $database;
|
|
||||||
$user = User::by_name($matches[1]);
|
$user = User::by_name($matches[1]);
|
||||||
if(!is_null($user)) {
|
if(!is_null($user)) {
|
||||||
$user_id = $user->id;
|
$user_id = $user->id;
|
||||||
}
|
} else {
|
||||||
else {
|
|
||||||
$user_id = -1;
|
$user_id = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -290,13 +312,18 @@ class CommentList extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// page building {{{
|
// page building {{{
|
||||||
|
/**
|
||||||
|
* @param int $current_page
|
||||||
|
*/
|
||||||
private function build_page(/*int*/ $current_page) {
|
private function build_page(/*int*/ $current_page) {
|
||||||
global $page, $config, $database, $user;
|
global $database, $user;
|
||||||
|
|
||||||
if(class_exists("Ratings")) {
|
if(class_exists("Ratings")) {
|
||||||
$user_ratings = Ratings::get_user_privs($user);
|
$user_ratings = Ratings::get_user_privs($user);
|
||||||
|
} else {
|
||||||
|
$user_ratings = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
$where = SPEED_HAX ? "WHERE posted > now() - interval '24 hours'" : "";
|
$where = SPEED_HAX ? "WHERE posted > now() - interval '24 hours'" : "";
|
||||||
|
|
||||||
$total_pages = $database->cache->get("comment_pages");
|
$total_pages = $database->cache->get("comment_pages");
|
||||||
@ -341,8 +368,12 @@ class CommentList extends Extension {
|
|||||||
// }}}
|
// }}}
|
||||||
|
|
||||||
// get comments {{{
|
// get comments {{{
|
||||||
|
/**
|
||||||
|
* @param int $count
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
private function get_recent_comments($count) {
|
private function get_recent_comments($count) {
|
||||||
global $config, $database;
|
global $database;
|
||||||
$rows = $database->get_all("
|
$rows = $database->get_all("
|
||||||
SELECT
|
SELECT
|
||||||
users.id as user_id, users.name as user_name, users.email as user_email, users.class as user_class,
|
users.id as user_id, users.name as user_name, users.email as user_email, users.class as user_class,
|
||||||
@ -361,8 +392,14 @@ class CommentList extends Extension {
|
|||||||
return $comments;
|
return $comments;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $user_id
|
||||||
|
* @param int $count
|
||||||
|
* @param int $offset
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
private function get_user_comments(/*int*/ $user_id, /*int*/ $count, /*int*/ $offset=0) {
|
private function get_user_comments(/*int*/ $user_id, /*int*/ $count, /*int*/ $offset=0) {
|
||||||
global $config, $database;
|
global $database;
|
||||||
$rows = $database->get_all("
|
$rows = $database->get_all("
|
||||||
SELECT
|
SELECT
|
||||||
users.id as user_id, users.name as user_name, users.email as user_email, users.class as user_class,
|
users.id as user_id, users.name as user_name, users.email as user_email, users.class as user_class,
|
||||||
@ -382,8 +419,12 @@ class CommentList extends Extension {
|
|||||||
return $comments;
|
return $comments;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
private function get_comments(/*int*/ $image_id) {
|
private function get_comments(/*int*/ $image_id) {
|
||||||
global $config, $database;
|
global $database;
|
||||||
$i_image_id = int_escape($image_id);
|
$i_image_id = int_escape($image_id);
|
||||||
$rows = $database->get_all("
|
$rows = $database->get_all("
|
||||||
SELECT
|
SELECT
|
||||||
@ -425,6 +466,9 @@ class CommentList extends Extension {
|
|||||||
return (count($result) >= $max);
|
return (count($result) >= $max);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function hash_match() {
|
private function hash_match() {
|
||||||
return ($_POST['hash'] == $this->get_hash());
|
return ($_POST['hash'] == $this->get_hash());
|
||||||
}
|
}
|
||||||
@ -440,6 +484,10 @@ class CommentList extends Extension {
|
|||||||
return md5($_SERVER['REMOTE_ADDR'] . date("%Y%m%d"));
|
return md5($_SERVER['REMOTE_ADDR'] . date("%Y%m%d"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function is_spam_akismet(/*string*/ $text) {
|
private function is_spam_akismet(/*string*/ $text) {
|
||||||
global $config, $user;
|
global $config, $user;
|
||||||
if(strlen($config->get_string('comment_wordpress_key')) > 0) {
|
if(strlen($config->get_string('comment_wordpress_key')) > 0) {
|
||||||
@ -478,11 +526,22 @@ class CommentList extends Extension {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param int $comment
|
||||||
|
* @return null
|
||||||
|
*/
|
||||||
private function is_dupe(/*int*/ $image_id, /*string*/ $comment) {
|
private function is_dupe(/*int*/ $image_id, /*string*/ $comment) {
|
||||||
global $database;
|
global $database;
|
||||||
return ($database->get_row("SELECT * FROM comments WHERE image_id=:image_id AND comment=:comment", array("image_id"=>$image_id, "comment"=>$comment)));
|
return ($database->get_row("SELECT * FROM comments WHERE image_id=:image_id AND comment=:comment", array("image_id"=>$image_id, "comment"=>$comment)));
|
||||||
}
|
}
|
||||||
// do some checks
|
// do some checks
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $pagenum
|
||||||
|
* @param int $maxpage
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
private function sanity_check_pagenumber(/*int*/ $pagenum, /*int*/ $maxpage){
|
private function sanity_check_pagenumber(/*int*/ $pagenum, /*int*/ $maxpage){
|
||||||
if (!is_numeric($pagenum)){
|
if (!is_numeric($pagenum)){
|
||||||
$pagenum=1;
|
$pagenum=1;
|
||||||
@ -496,6 +555,12 @@ class CommentList extends Extension {
|
|||||||
return $pagenum;
|
return $pagenum;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param User $user
|
||||||
|
* @param string $comment
|
||||||
|
* @throws CommentPostingException
|
||||||
|
*/
|
||||||
private function add_comment_wrapper(/*int*/ $image_id, User $user, /*string*/ $comment) {
|
private function add_comment_wrapper(/*int*/ $image_id, User $user, /*string*/ $comment) {
|
||||||
global $database, $config;
|
global $database, $config;
|
||||||
|
|
||||||
|
@ -18,8 +18,12 @@ class CommentListTheme extends Themelet {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Display a page with a list of images, and for each image,
|
* Display a page with a list of images, and for each image, the image's comments.
|
||||||
* the image's comments
|
*
|
||||||
|
* @param array $images
|
||||||
|
* @param int $page_number
|
||||||
|
* @param int $total_pages
|
||||||
|
* @param bool $can_post
|
||||||
*/
|
*/
|
||||||
public function display_comment_list($images, $page_number, $total_pages, $can_post) {
|
public function display_comment_list($images, $page_number, $total_pages, $can_post) {
|
||||||
global $config, $page, $user;
|
global $config, $page, $user;
|
||||||
@ -119,9 +123,9 @@ class CommentListTheme extends Themelet {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add some comments to the page, probably in a sidebar
|
* Add some comments to the page, probably in a sidebar.
|
||||||
*
|
*
|
||||||
* $comments = an array of Comment objects to be shown
|
* @param \Comment[] $comments An array of Comment objects to be shown
|
||||||
*/
|
*/
|
||||||
public function display_recent_comments($comments) {
|
public function display_recent_comments($comments) {
|
||||||
global $page;
|
global $page;
|
||||||
@ -136,7 +140,11 @@ class CommentListTheme extends Themelet {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Show comments for an image
|
* Show comments for an image.
|
||||||
|
*
|
||||||
|
* @param Image $image
|
||||||
|
* @param \Comment[] $comments
|
||||||
|
* @param bool $postbox
|
||||||
*/
|
*/
|
||||||
public function display_image_comments(Image $image, $comments, $postbox) {
|
public function display_image_comments(Image $image, $comments, $postbox) {
|
||||||
global $page;
|
global $page;
|
||||||
@ -153,9 +161,12 @@ class CommentListTheme extends Themelet {
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Show comments made by a user
|
* Show comments made by a user.
|
||||||
|
*
|
||||||
|
* @param \Comment[] $comments
|
||||||
|
* @param \User $user
|
||||||
*/
|
*/
|
||||||
public function display_recent_user_comments($comments, $user) {
|
public function display_recent_user_comments($comments, User $user) {
|
||||||
global $page;
|
global $page;
|
||||||
$html = "";
|
$html = "";
|
||||||
foreach($comments as $comment) {
|
foreach($comments as $comment) {
|
||||||
@ -170,7 +181,13 @@ class CommentListTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Comments", $html, "left", 70, "comment-list-user"));
|
$page->add_block(new Block("Comments", $html, "left", 70, "comment-list-user"));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function display_all_user_comments($comments, $page_number, $total_pages, $user) {
|
/**
|
||||||
|
* @param \Comment[] $comments
|
||||||
|
* @param int $page_number
|
||||||
|
* @param int $total_pages
|
||||||
|
* @param \User $user
|
||||||
|
*/
|
||||||
|
public function display_all_user_comments($comments, $page_number, $total_pages, User $user) {
|
||||||
global $page;
|
global $page;
|
||||||
|
|
||||||
assert(is_numeric($page_number));
|
assert(is_numeric($page_number));
|
||||||
@ -203,7 +220,12 @@ class CommentListTheme extends Themelet {
|
|||||||
$this->display_paginator($page, "comment/beta-search/{$user->name}", null, $page_number, $total_pages);
|
$this->display_paginator($page, "comment/beta-search/{$user->name}", null, $page_number, $total_pages);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function comment_to_html($comment, $trim=false) {
|
/**
|
||||||
|
* @param \Comment $comment
|
||||||
|
* @param bool $trim
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function comment_to_html(Comment $comment, $trim=false) {
|
||||||
global $config, $user;
|
global $config, $user;
|
||||||
|
|
||||||
$tfe = new TextFormattingEvent($comment->comment);
|
$tfe = new TextFormattingEvent($comment->comment);
|
||||||
@ -276,6 +298,10 @@ class CommentListTheme extends Themelet {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function build_postbox(/*int*/ $image_id) {
|
protected function build_postbox(/*int*/ $image_id) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
|
@ -30,6 +30,12 @@ class CronUploader extends Extension {
|
|||||||
*/
|
*/
|
||||||
private $root_dir = "";
|
private $root_dir = "";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Key used to identify uploader
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
private $upload_key = "";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Checks if the cron upload page has been accessed
|
* Checks if the cron upload page has been accessed
|
||||||
* and initializes the upload.
|
* and initializes the upload.
|
||||||
@ -39,10 +45,10 @@ class CronUploader extends Extension {
|
|||||||
global $config, $user;
|
global $config, $user;
|
||||||
|
|
||||||
if ($event->page_matches ( "cron_upload" )) {
|
if ($event->page_matches ( "cron_upload" )) {
|
||||||
$key = $config->get_string ( "cron_uploader_key", "" );
|
$this->upload_key = $config->get_string ( "cron_uploader_key", "" );
|
||||||
|
|
||||||
// If the key is in the url, upload
|
// If the key is in the url, upload
|
||||||
if ($key != "" && $event->get_arg ( 0 ) == $key) {
|
if ($this->upload_key != "" && $event->get_arg ( 0 ) == $this->upload_key) {
|
||||||
// log in as admin
|
// log in as admin
|
||||||
$this->process_upload(); // Start upload
|
$this->process_upload(); // Start upload
|
||||||
}
|
}
|
||||||
@ -67,8 +73,8 @@ class CronUploader extends Extension {
|
|||||||
$uploaded_dirinfo = $this->scan_dir($uploaded_dir);
|
$uploaded_dirinfo = $this->scan_dir($uploaded_dir);
|
||||||
$failed_dirinfo = $this->scan_dir($failed_dir);
|
$failed_dirinfo = $this->scan_dir($failed_dir);
|
||||||
|
|
||||||
$cron_url = make_http(make_link("/cron_upload/" . $config->get_string('cron_uploader_key', 'invalid key' )));
|
$cron_url = make_http(make_link("/cron_upload/" . $this->upload_key));
|
||||||
$cron_cmd = "curl -f $cron_url";
|
$cron_cmd = "curl --silent $cron_url";
|
||||||
$log_path = $this->root_dir . "/uploads.log";
|
$log_path = $this->root_dir . "/uploads.log";
|
||||||
|
|
||||||
$info_html = "<b>Information</b>
|
$info_html = "<b>Information</b>
|
||||||
@ -135,19 +141,21 @@ class CronUploader extends Extension {
|
|||||||
public function onInitExt(InitExtEvent $event) {
|
public function onInitExt(InitExtEvent $event) {
|
||||||
global $config;
|
global $config;
|
||||||
// Set default values
|
// Set default values
|
||||||
$key = $this->generate_key ();
|
if ($config->get_string("cron_uploader_key", "")) {
|
||||||
|
$this->upload_key = $this->generate_key ();
|
||||||
|
|
||||||
$config->set_default_int ( 'cron_uploader_count', 1 );
|
$config->set_default_int ( 'cron_uploader_count', 1 );
|
||||||
$config->set_default_string ( 'cron_uploader_key', $key );
|
$config->set_default_string ( 'cron_uploader_key', $this->upload_key );
|
||||||
$this->set_dir();
|
$this->set_dir();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onSetupBuilding(SetupBuildingEvent $event) {
|
public function onSetupBuilding(SetupBuildingEvent $event) {
|
||||||
global $config;
|
global $config;
|
||||||
$this->set_dir();
|
$this->set_dir();
|
||||||
|
|
||||||
$cron_url = make_http(make_link("/cron_upload/" . $config->get_string('cron_uploader_key', 'invalid key' )));
|
$cron_url = make_http(make_link("/cron_upload/" . $this->upload_key));
|
||||||
$cron_cmd = "wget $cron_url";
|
$cron_cmd = "curl --silent $cron_url";
|
||||||
$documentation_link = make_http(make_link("cron_upload"));
|
$documentation_link = make_http(make_link("cron_upload"));
|
||||||
|
|
||||||
$sb = new SetupBlock ( "Cron Uploader" );
|
$sb = new SetupBlock ( "Cron Uploader" );
|
||||||
@ -194,11 +202,11 @@ class CronUploader extends Extension {
|
|||||||
|
|
||||||
// Make the directory if it doesn't exist yet
|
// Make the directory if it doesn't exist yet
|
||||||
if (!is_dir($dir . "/queue/"))
|
if (!is_dir($dir . "/queue/"))
|
||||||
mkdir ( $dir . "/queue/", 0755, true );
|
mkdir ( $dir . "/queue/", 0775, true );
|
||||||
if (!is_dir($dir . "/uploaded/"))
|
if (!is_dir($dir . "/uploaded/"))
|
||||||
mkdir ( $dir . "/uploaded/", 0755, true );
|
mkdir ( $dir . "/uploaded/", 0775, true );
|
||||||
if (!is_dir($dir . "/failed_to_upload/"))
|
if (!is_dir($dir . "/failed_to_upload/"))
|
||||||
mkdir ( $dir . "/failed_to_upload/", 0755, true );
|
mkdir ( $dir . "/failed_to_upload/", 0775, true );
|
||||||
|
|
||||||
$this->root_dir = $dir;
|
$this->root_dir = $dir;
|
||||||
return $dir;
|
return $dir;
|
||||||
@ -242,6 +250,7 @@ class CronUploader extends Extension {
|
|||||||
// Throw exception if there's nothing in the queue
|
// Throw exception if there's nothing in the queue
|
||||||
if (count($this->image_queue) == 0) {
|
if (count($this->image_queue) == 0) {
|
||||||
$this->add_upload_info("Your queue is empty so nothing could be uploaded.");
|
$this->add_upload_info("Your queue is empty so nothing could be uploaded.");
|
||||||
|
$this->handle_log();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -289,10 +298,9 @@ class CronUploader extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// move file to correct dir
|
// move file to correct dir
|
||||||
$newPath = $newDir . $filename;
|
rename($path, $newDir.$filename);
|
||||||
rename($path, $newPath);
|
|
||||||
|
|
||||||
$this->add_upload_info($info . "Image \"$filename\" moved from queue to \"$newPath\".");
|
$this->add_upload_info($info . "Image \"$filename\" moved from queue to \"$newDir\".");
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -420,8 +420,7 @@ class DanbooruApi extends Extension {
|
|||||||
// Code borrowed from /ext/user
|
// Code borrowed from /ext/user
|
||||||
$name = $_REQUEST['login'];
|
$name = $_REQUEST['login'];
|
||||||
$pass = $_REQUEST['password'];
|
$pass = $_REQUEST['password'];
|
||||||
$hash = md5( strtolower($name) . $pass );
|
$duser = User::by_name_and_pass($name, $pass);
|
||||||
$duser = User::by_name_and_hash($name, $hash);
|
|
||||||
if(!is_null($duser)) {
|
if(!is_null($duser)) {
|
||||||
$user = $duser;
|
$user = $duser;
|
||||||
} else
|
} else
|
||||||
|
@ -13,18 +13,32 @@
|
|||||||
* add more emoticons by uploading images into that folder.
|
* add more emoticons by uploading images into that folder.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class Emoticons
|
||||||
|
*/
|
||||||
class Emoticons extends FormatterExtension {
|
class Emoticons extends FormatterExtension {
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function format(/*string*/ $text) {
|
public function format(/*string*/ $text) {
|
||||||
$data_href = get_base_href();
|
$data_href = get_base_href();
|
||||||
$text = preg_replace("/:([a-z]*?):/s", "<img src='$data_href/ext/emoticons/default/\\1.gif'>", $text);
|
$text = preg_replace("/:([a-z]*?):/s", "<img src='$data_href/ext/emoticons/default/\\1.gif'>", $text);
|
||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function strip(/*string*/ $text) {
|
public function strip(/*string*/ $text) {
|
||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class EmoticonList
|
||||||
|
*/
|
||||||
class EmoticonList extends Extension {
|
class EmoticonList extends Extension {
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
if($event->page_matches("emote/list")) {
|
if($event->page_matches("emote/list")) {
|
||||||
|
@ -1,5 +1,8 @@
|
|||||||
<?php
|
<?php
|
||||||
class EmoticonListTheme extends Themelet {
|
class EmoticonListTheme extends Themelet {
|
||||||
|
/**
|
||||||
|
* @param array $list
|
||||||
|
*/
|
||||||
public function display_emotes(/*array*/ $list) {
|
public function display_emotes(/*array*/ $list) {
|
||||||
global $page;
|
global $page;
|
||||||
$data_href = get_base_href();
|
$data_href = get_base_href();
|
||||||
|
@ -81,6 +81,10 @@ class ExtensionInfo {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $fname
|
||||||
|
* @return bool|null
|
||||||
|
*/
|
||||||
private function is_enabled(/*string*/ $fname) {
|
private function is_enabled(/*string*/ $fname) {
|
||||||
$core = explode(",", CORE_EXTS);
|
$core = explode(",", CORE_EXTS);
|
||||||
$extra = explode(",", EXTRA_EXTS);
|
$extra = explode(",", EXTRA_EXTS);
|
||||||
@ -150,7 +154,10 @@ class ExtManager extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param bool $all
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
private function get_extensions(/*bool*/ $all) {
|
private function get_extensions(/*bool*/ $all) {
|
||||||
$extensions = array();
|
$extensions = array();
|
||||||
if($all) {
|
if($all) {
|
||||||
|
@ -14,8 +14,18 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class FavoriteSetEvent extends Event {
|
class FavoriteSetEvent extends Event {
|
||||||
var $image_id, $user, $do_set;
|
/** @var int */
|
||||||
|
public $image_id;
|
||||||
|
/** @var \User */
|
||||||
|
public $user;
|
||||||
|
/** @var bool */
|
||||||
|
public $do_set;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param User $user
|
||||||
|
* @param bool $do_set
|
||||||
|
*/
|
||||||
public function __construct(/*int*/ $image_id, User $user, /*boolean*/ $do_set) {
|
public function __construct(/*int*/ $image_id, User $user, /*boolean*/ $do_set) {
|
||||||
assert(is_numeric($image_id));
|
assert(is_numeric($image_id));
|
||||||
assert(is_bool($do_set));
|
assert(is_bool($do_set));
|
||||||
@ -172,6 +182,11 @@ class Favorites extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param int $user_id
|
||||||
|
* @param bool $do_set
|
||||||
|
*/
|
||||||
private function add_vote(/*int*/ $image_id, /*int*/ $user_id, /*bool*/ $do_set) {
|
private function add_vote(/*int*/ $image_id, /*int*/ $user_id, /*bool*/ $do_set) {
|
||||||
global $database;
|
global $database;
|
||||||
if ($do_set) {
|
if ($do_set) {
|
||||||
@ -187,7 +202,11 @@ class Favorites extends Extension {
|
|||||||
"UPDATE images SET favorites=(SELECT COUNT(*) FROM user_favorites WHERE image_id=:image_id) WHERE id=:user_id",
|
"UPDATE images SET favorites=(SELECT COUNT(*) FROM user_favorites WHERE image_id=:image_id) WHERE id=:user_id",
|
||||||
array("image_id"=>$image_id, "user_id"=>$user_id));
|
array("image_id"=>$image_id, "user_id"=>$user_id));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
private function list_persons_who_have_favorited(Image $image) {
|
private function list_persons_who_have_favorited(Image $image) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
|
@ -60,13 +60,13 @@ class Featured extends Extension {
|
|||||||
global $config, $database, $page, $user;
|
global $config, $database, $page, $user;
|
||||||
$fid = $config->get_int("featured_id");
|
$fid = $config->get_int("featured_id");
|
||||||
if($fid > 0) {
|
if($fid > 0) {
|
||||||
$image = $database->cache->get("featured_image_object-$fid");
|
$image = $database->cache->get("featured_image_object:$fid");
|
||||||
if($image === false) {
|
if($image === false) {
|
||||||
$image = Image::by_id($fid);
|
$image = Image::by_id($fid);
|
||||||
if($image) { // make sure the object is fully populated before saving
|
if($image) { // make sure the object is fully populated before saving
|
||||||
$image->get_tag_array();
|
$image->get_tag_array();
|
||||||
}
|
}
|
||||||
$database->cache->set("featured_image_object-$fid", $image, 600);
|
$database->cache->set("featured_image_object:$fid", $image, 600);
|
||||||
}
|
}
|
||||||
if(!is_null($image)) {
|
if(!is_null($image)) {
|
||||||
if(class_exists("Ratings")) {
|
if(class_exists("Ratings")) {
|
||||||
|
@ -1,26 +1,37 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class FeaturedTheme extends Themelet {
|
class FeaturedTheme extends Themelet {
|
||||||
/*
|
/**
|
||||||
* Show $text on the $page
|
* Show $text on the $page.
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
*/
|
*/
|
||||||
public function display_featured(Page $page, Image $image) {
|
public function display_featured(Page $page, Image $image) {
|
||||||
$page->add_block(new Block("Featured Image", $this->build_featured_html($image), "left", 3));
|
$page->add_block(new Block("Featured Image", $this->build_featured_html($image), "left", 3));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function get_buttons_html(/*int*/ $image_id) {
|
public function get_buttons_html(/*int*/ $image_id) {
|
||||||
global $user;
|
global $user;
|
||||||
return "
|
return "
|
||||||
".make_form(make_link("featured_image/set"))."
|
".make_form(make_link("featured_image/set"))."
|
||||||
".$user->get_auth_html()."
|
".$user->get_auth_html()."
|
||||||
<input type='hidden' name='image_id' value='$image_id'>
|
<input type='hidden' name='image_id' value='{$image_id}'>
|
||||||
<input type='submit' value='Feature This'>
|
<input type='submit' value='Feature This'>
|
||||||
</form>
|
</form>
|
||||||
";
|
";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param null|string $query
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function build_featured_html(Image $image, $query=null) {
|
public function build_featured_html(Image $image, $query=null) {
|
||||||
global $config;
|
|
||||||
$i_id = int_escape($image->id);
|
$i_id = int_escape($image->id);
|
||||||
$h_view_link = make_link("post/view/$i_id", $query);
|
$h_view_link = make_link("post/view/$i_id", $query);
|
||||||
$h_thumb_link = $image->get_thumb_link();
|
$h_thumb_link = $image->get_thumb_link();
|
||||||
@ -29,7 +40,7 @@ class FeaturedTheme extends Themelet {
|
|||||||
|
|
||||||
return "
|
return "
|
||||||
<a href='$h_view_link'>
|
<a href='$h_view_link'>
|
||||||
<img id='thumb_$i_id' title='$h_tip' alt='$h_tip' class='highlighted' style='height: {$tsize[1]}px; width: {$tsize[0]}px;' src='$h_thumb_link'>
|
<img id='thumb_{$i_id}' title='{$h_tip}' alt='{$h_tip}' class='highlighted' style='height: {$tsize[1]}px; width: {$tsize[0]}px;' src='{$h_thumb_link}'>
|
||||||
</a>
|
</a>
|
||||||
";
|
";
|
||||||
}
|
}
|
||||||
|
@ -39,7 +39,10 @@ class ArchiveFileHandler extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function supported_ext($ext) {
|
private function supported_ext($ext) {
|
||||||
$exts = array("zip");
|
$exts = array("zip");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
|
@ -7,15 +7,29 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class FlashFileHandler extends DataHandlerExtension {
|
class FlashFileHandler extends DataHandlerExtension {
|
||||||
|
/**
|
||||||
|
* @param string $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function create_thumb($hash) {
|
protected function create_thumb($hash) {
|
||||||
copy("ext/handle_flash/thumb.jpg", warehouse_path("thumbs", $hash));
|
copy("ext/handle_flash/thumb.jpg", warehouse_path("thumbs", $hash));
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function supported_ext($ext) {
|
protected function supported_ext($ext) {
|
||||||
$exts = array("swf");
|
$exts = array("swf");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param array $metadata
|
||||||
|
* @return Image|null
|
||||||
|
*/
|
||||||
protected function create_image_from_data(/*string*/ $filename, /*array*/ $metadata) {
|
protected function create_image_from_data(/*string*/ $filename, /*array*/ $metadata) {
|
||||||
$image = new Image();
|
$image = new Image();
|
||||||
|
|
||||||
@ -35,6 +49,10 @@ class FlashFileHandler extends DataHandlerExtension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function check_contents(/*string*/ $file) {
|
protected function check_contents(/*string*/ $file) {
|
||||||
if (!file_exists($file)) return false;
|
if (!file_exists($file)) return false;
|
||||||
|
|
||||||
|
@ -49,12 +49,20 @@ class IcoFileHandler extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function supported_ext($ext) {
|
private function supported_ext($ext) {
|
||||||
$exts = array("ico", "ani", "cur");
|
$exts = array("ico", "ani", "cur");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $filename
|
||||||
|
* @param $metadata
|
||||||
|
* @return Image
|
||||||
|
*/
|
||||||
private function create_image_from_data($filename, $metadata) {
|
private function create_image_from_data($filename, $metadata) {
|
||||||
$image = new Image();
|
$image = new Image();
|
||||||
|
|
||||||
@ -77,6 +85,10 @@ class IcoFileHandler extends Extension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function check_contents($file) {
|
private function check_contents($file) {
|
||||||
if(!file_exists($file)) return false;
|
if(!file_exists($file)) return false;
|
||||||
$fp = fopen($file, "r");
|
$fp = fopen($file, "r");
|
||||||
@ -85,6 +97,10 @@ class IcoFileHandler extends Extension {
|
|||||||
return ($header['null'] == 0 && ($header['type'] == 0 || $header['type'] == 1));
|
return ($header['null'] == 0 && ($header['type'] == 0 || $header['type'] == 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function create_thumb($hash) {
|
private function create_thumb($hash) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
|
@ -6,15 +6,29 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class MP3FileHandler extends DataHandlerExtension {
|
class MP3FileHandler extends DataHandlerExtension {
|
||||||
|
/**
|
||||||
|
* @param string $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function create_thumb($hash) {
|
protected function create_thumb($hash) {
|
||||||
copy("ext/handle_mp3/thumb.jpg", warehouse_path("thumbs", $hash));
|
copy("ext/handle_mp3/thumb.jpg", warehouse_path("thumbs", $hash));
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function supported_ext($ext) {
|
protected function supported_ext($ext) {
|
||||||
$exts = array("mp3");
|
$exts = array("mp3");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param array $metadata
|
||||||
|
* @return Image|null
|
||||||
|
*/
|
||||||
protected function create_image_from_data($filename, $metadata) {
|
protected function create_image_from_data($filename, $metadata) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -47,6 +61,10 @@ class MP3FileHandler extends DataHandlerExtension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function check_contents($file) {
|
protected function check_contents($file) {
|
||||||
if (file_exists($file)) {
|
if (file_exists($file)) {
|
||||||
require_once('lib/getid3/getid3/getid3.php');
|
require_once('lib/getid3/getid3/getid3.php');
|
||||||
|
@ -7,12 +7,21 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class PixelFileHandler extends DataHandlerExtension {
|
class PixelFileHandler extends DataHandlerExtension {
|
||||||
|
/**
|
||||||
|
* @param string $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function supported_ext($ext) {
|
protected function supported_ext($ext) {
|
||||||
$exts = array("jpg", "jpeg", "gif", "png");
|
$exts = array("jpg", "jpeg", "gif", "png");
|
||||||
$ext = (($pos = strpos($ext,'?')) !== false) ? substr($ext,0,$pos) : $ext;
|
$ext = (($pos = strpos($ext,'?')) !== false) ? substr($ext,0,$pos) : $ext;
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param array $metadata
|
||||||
|
* @return Image|null
|
||||||
|
*/
|
||||||
protected function create_image_from_data(/*string*/ $filename, /*array*/ $metadata) {
|
protected function create_image_from_data(/*string*/ $filename, /*array*/ $metadata) {
|
||||||
$image = new Image();
|
$image = new Image();
|
||||||
|
|
||||||
@ -32,6 +41,10 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function check_contents(/*string*/ $file) {
|
protected function check_contents(/*string*/ $file) {
|
||||||
$valid = Array(IMAGETYPE_PNG, IMAGETYPE_GIF, IMAGETYPE_JPEG);
|
$valid = Array(IMAGETYPE_PNG, IMAGETYPE_GIF, IMAGETYPE_JPEG);
|
||||||
if(!file_exists($file)) return false;
|
if(!file_exists($file)) return false;
|
||||||
@ -41,6 +54,10 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function create_thumb(/*string*/ $hash) {
|
protected function create_thumb(/*string*/ $hash) {
|
||||||
$outname = warehouse_path("thumbs", $hash);
|
$outname = warehouse_path("thumbs", $hash);
|
||||||
if(file_exists($outname)) {
|
if(file_exists($outname)) {
|
||||||
@ -49,6 +66,10 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
return $this->create_thumb_force($hash);
|
return $this->create_thumb_force($hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function create_thumb_force(/*string*/ $hash) {
|
protected function create_thumb_force(/*string*/ $hash) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -69,7 +90,10 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
|
|
||||||
return $ok;
|
return $ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param ImageAdminBlockBuildingEvent $event
|
||||||
|
*/
|
||||||
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
||||||
$event->add_part("
|
$event->add_part("
|
||||||
<form>
|
<form>
|
||||||
@ -83,14 +107,22 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
", 20);
|
", 20);
|
||||||
|
|
||||||
$u_ilink = $event->image->get_image_link();
|
$u_ilink = $event->image->get_image_link();
|
||||||
|
$nu_enabled = (strpos($u_ilink, '?') !== false ? "<input type='hidden' name='q' value='image/{$event->image->id}.{$event->image->ext}' />" : "");
|
||||||
$event->add_part("
|
$event->add_part("
|
||||||
<form action='{$u_ilink}'>
|
<form action='{$u_ilink}'>
|
||||||
|
$nu_enabled
|
||||||
<input type='submit' value='Image Only'>
|
<input type='submit' value='Image Only'>
|
||||||
</form>
|
</form>
|
||||||
", 21);
|
", 21);
|
||||||
}
|
}
|
||||||
|
|
||||||
// IM thumber {{{
|
// IM thumber {{{
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $inname
|
||||||
|
* @param string $outname
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function make_thumb_convert(/*string*/ $inname, /*string*/ $outname) {
|
private function make_thumb_convert(/*string*/ $inname, /*string*/ $outname) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -124,6 +156,11 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
// epeg thumber {{{
|
// epeg thumber {{{
|
||||||
|
/**
|
||||||
|
* @param string $inname
|
||||||
|
* @param string $outname
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function make_thumb_epeg(/*string*/ $inname, /*string*/ $outname) {
|
private function make_thumb_epeg(/*string*/ $inname, /*string*/ $outname) {
|
||||||
global $config;
|
global $config;
|
||||||
$w = $config->get_int("thumb_width");
|
$w = $config->get_int("thumb_width");
|
||||||
@ -132,6 +169,11 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
// GD thumber {{{
|
// GD thumber {{{
|
||||||
|
/**
|
||||||
|
* @param string $inname
|
||||||
|
* @param string $outname
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function make_thumb_gd(/*string*/ $inname, /*string*/ $outname) {
|
private function make_thumb_gd(/*string*/ $inname, /*string*/ $outname) {
|
||||||
global $config;
|
global $config;
|
||||||
$thumb = $this->get_thumb($inname);
|
$thumb = $this->get_thumb($inname);
|
||||||
@ -140,6 +182,10 @@ class PixelFileHandler extends DataHandlerExtension {
|
|||||||
return $ok;
|
return $ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $tmpname
|
||||||
|
* @return resource
|
||||||
|
*/
|
||||||
private function get_thumb(/*string*/ $tmpname) {
|
private function get_thumb(/*string*/ $tmpname) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
|
@ -51,11 +51,20 @@ class SVGFileHandler extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function supported_ext($ext) {
|
private function supported_ext($ext) {
|
||||||
$exts = array("svg");
|
$exts = array("svg");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $filename
|
||||||
|
* @param $metadata
|
||||||
|
* @return Image
|
||||||
|
*/
|
||||||
private function create_image_from_data($filename, $metadata) {
|
private function create_image_from_data($filename, $metadata) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -75,21 +84,30 @@ class SVGFileHandler extends Extension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function check_contents($file) {
|
private function check_contents($file) {
|
||||||
if(!file_exists($file)) return false;
|
if(!file_exists($file)) return false;
|
||||||
|
|
||||||
$msp = new MiniSVGParser($file);
|
$msp = new MiniSVGParser($file);
|
||||||
return $msp->valid;
|
return bool_escape($msp->valid);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class MiniSVGParser {
|
class MiniSVGParser {
|
||||||
var $valid=false, $width=0, $height=0;
|
/** @var bool */
|
||||||
|
public $valid=false;
|
||||||
|
/** @var int */
|
||||||
|
public $width=0;
|
||||||
|
/** @var int */
|
||||||
|
public $height=0;
|
||||||
|
|
||||||
function __construct($file) {
|
function __construct($file) {
|
||||||
$xml_parser = xml_parser_create();
|
$xml_parser = xml_parser_create();
|
||||||
xml_set_element_handler($xml_parser, array($this, "startElement"), array($this, "endElement"));
|
xml_set_element_handler($xml_parser, array($this, "startElement"), array($this, "endElement"));
|
||||||
$this->valid = xml_parse($xml_parser, file_get_contents($file), true);
|
$this->valid = bool_escape(xml_parse($xml_parser, file_get_contents($file), true));
|
||||||
xml_parser_free($xml_parser);
|
xml_parser_free($xml_parser);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
/*
|
/*
|
||||||
* Name: Handle Video
|
* Name: Handle Video
|
||||||
* Author: velocity37 <velocity37@gmail.com>
|
* Author: velocity37 <velocity37@gmail.com>
|
||||||
|
* Modified By: Shish <webmaster@shishnet.org>, jgen <jeffgenovy@gmail.com>
|
||||||
* License: GPLv2
|
* License: GPLv2
|
||||||
* Description: Handle FLV, MP4, OGV and WEBM video files.
|
* Description: Handle FLV, MP4, OGV and WEBM video files.
|
||||||
* Documentation:
|
* Documentation:
|
||||||
@ -17,17 +18,88 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class VideoFileHandler extends DataHandlerExtension {
|
class VideoFileHandler extends DataHandlerExtension {
|
||||||
protected function create_thumb($hash) {
|
public function onInitExt(InitExtEvent $event) {
|
||||||
copy("ext/handle_video/thumb.jpg", warehouse_path("thumbs", $hash));
|
global $config;
|
||||||
|
$config->set_default_string('video_thumb_engine', 'static');
|
||||||
|
$config->set_default_string('thumb_ffmpeg_path', '');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function onSetupBuilding(SetupBuildingEvent $event) {
|
||||||
|
global $config;
|
||||||
|
|
||||||
|
$thumbers = array();
|
||||||
|
$thumbers['None'] = "static";
|
||||||
|
$thumbers['ffmpeg'] = "ffmpeg";
|
||||||
|
|
||||||
|
$sb = new SetupBlock("Video Thumbnail Options");
|
||||||
|
|
||||||
|
$sb->add_choice_option("video_thumb_engine", $thumbers, "Engine: ");
|
||||||
|
|
||||||
|
//if($config->get_string("video_thumb_engine") == "ffmpeg") {
|
||||||
|
$sb->add_label("<br>Path to ffmpeg: ");
|
||||||
|
$sb->add_text_option("thumb_ffmpeg_path");
|
||||||
|
//}
|
||||||
|
$event->panel->add_block($sb);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $hash
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
protected function create_thumb($hash) {
|
||||||
|
global $config;
|
||||||
|
|
||||||
|
// this is never used...
|
||||||
|
//$q = $config->get_int("thumb_quality");
|
||||||
|
|
||||||
|
$ok = false;
|
||||||
|
|
||||||
|
switch($config->get_string("video_thumb_engine"))
|
||||||
|
{
|
||||||
|
default:
|
||||||
|
case 'static':
|
||||||
|
$outname = warehouse_path("thumbs", $hash);
|
||||||
|
copy("ext/handle_video/thumb.jpg", $outname);
|
||||||
|
$ok = true;
|
||||||
|
break;
|
||||||
|
case 'ffmpeg':
|
||||||
|
$ffmpeg = escapeshellarg($config->get_string("thumb_ffmpeg_path"));
|
||||||
|
|
||||||
|
$w = (int)$config->get_int("thumb_width");
|
||||||
|
$h = (int)$config->get_int("thumb_height");
|
||||||
|
$inname = escapeshellarg(warehouse_path("images", $hash));
|
||||||
|
$outname = escapeshellarg(warehouse_path("thumbs", $hash));
|
||||||
|
|
||||||
|
$cmd = escapeshellcmd("{$ffmpeg} -i {$inname} -vf scale='if(gt(a,{$w}/{$h}),{$w},-1)':'if(gt(a,{$w}/{$h}),-1,{$h})' -ss 00:00:00.0 -f image2 -vframes 1 {$outname}");
|
||||||
|
|
||||||
|
exec($cmd, $output, $ret);
|
||||||
|
|
||||||
|
// TODO: We should really check the result of the exec to see if it really succeeded.
|
||||||
|
$ok = true;
|
||||||
|
|
||||||
|
log_debug('handle_video', "Generating thumbnail with command `$cmd`, returns $ret");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return $ok;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $ext
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function supported_ext($ext) {
|
protected function supported_ext($ext) {
|
||||||
$exts = array("flv", "mp4", "m4v", "ogv", "webm");
|
$exts = array("flv", "mp4", "m4v", "ogv", "webm");
|
||||||
return in_array(strtolower($ext), $exts);
|
return in_array(strtolower($ext), $exts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param array $metadata
|
||||||
|
* @return Image|null
|
||||||
|
*/
|
||||||
protected function create_image_from_data($filename, $metadata) {
|
protected function create_image_from_data($filename, $metadata) {
|
||||||
global $config;
|
//global $config;
|
||||||
|
|
||||||
$image = new Image();
|
$image = new Image();
|
||||||
|
|
||||||
@ -67,12 +139,21 @@ class VideoFileHandler extends DataHandlerExtension {
|
|||||||
return $image;
|
return $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $file
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
protected function check_contents($file) {
|
protected function check_contents($file) {
|
||||||
if (file_exists($file)) {
|
if (file_exists($file)) {
|
||||||
require_once('lib/getid3/getid3/getid3.php');
|
require_once('lib/getid3/getid3/getid3.php');
|
||||||
$getID3 = new getID3;
|
$getID3 = new getID3;
|
||||||
$ThisFileInfo = $getID3->analyze($file);
|
$ThisFileInfo = $getID3->analyze($file);
|
||||||
if (isset($ThisFileInfo['mime_type']) && ($ThisFileInfo['mime_type'] == "video/webm" || $ThisFileInfo['mime_type'] == "video/quicktime" || $ThisFileInfo['mime_type'] == "application/ogg" || $ThisFileInfo['mime_type'] == 'video/x-flv')) {
|
if (isset($ThisFileInfo['mime_type']) && (
|
||||||
|
$ThisFileInfo['mime_type'] == "video/webm" ||
|
||||||
|
$ThisFileInfo['mime_type'] == "video/quicktime" ||
|
||||||
|
$ThisFileInfo['mime_type'] == "application/ogg" ||
|
||||||
|
$ThisFileInfo['mime_type'] == 'video/x-flv')
|
||||||
|
) {
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,27 +7,38 @@ class VideoFileHandlerTheme extends Themelet {
|
|||||||
$ext = strtolower($image->get_ext());
|
$ext = strtolower($image->get_ext());
|
||||||
|
|
||||||
if ($ext == "mp4") {
|
if ($ext == "mp4") {
|
||||||
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br><script language='JavaScript' type='text/javascript'>
|
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br/>
|
||||||
|
<script language='JavaScript' type='text/javascript'>
|
||||||
if( navigator.userAgent.match(/Firefox/i) ||
|
if( navigator.userAgent.match(/Firefox/i) ||
|
||||||
navigator.userAgent.match(/Opera/i) ||
|
navigator.userAgent.match(/Opera/i) ||
|
||||||
(navigator.userAgent.match(/MSIE/i) && parseFloat(navigator.appVersion.split('MSIE')[1]) < 9)){
|
(navigator.userAgent.match(/MSIE/i) && parseFloat(navigator.appVersion.split('MSIE')[1]) < 9)){
|
||||||
document.write(\"<object data='$data_href/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'><param value='#000000' name='bgcolor'><param name='allowFullScreen' value='true'><param value='high' name='quality'><param value='opaque' name='wmode'><param value='source=$ilink&type=video&streamtype=file&controltype=0' name='flashvars'></object>\");
|
document.write(\"<object data='{$data_href}/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'><param value='#000000' name='bgcolor'><param name='allowFullScreen' value='true'><param value='high' name='quality'><param value='opaque' name='wmode'><param value='source=$ilink&type=video&streamtype=file&controltype=0' name='flashvars'></object>\");
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
document.write(\"<video controls='controls' autoplay='autoplay'>\");
|
document.write(\"<video controls autoplay loop'>\");
|
||||||
document.write(\"<source src='" . make_link("/image/" . $image->id) . "' type='video/mp4' />\");
|
document.write(\"<source src='" . make_link("/image/" . $image->id) . "' type='video/mp4' />\");
|
||||||
document.write(\"<object data='$data_href/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'><param value='#000000' name='bgcolor'><param name='allowFullScreen' value='true'><param value='high' name='quality'><param value='opaque' name='wmode'><param value='source=$ilink&type=video&streamtype=file&controltype=0' name='flashvars'></object>\");
|
document.write(\"<object data='{$data_href}/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'><param value='#000000' name='bgcolor'><param name='allowFullScreen' value='true'><param value='high' name='quality'><param value='opaque' name='wmode'><param value='source=$ilink&type=video&streamtype=file&controltype=0' name='flashvars'></object>\");
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
<noscript>Javascript appears to be disabled. Please enable it and try again.</noscript>";
|
<noscript>Javascript appears to be disabled. Please enable it and try again.</noscript>";
|
||||||
} elseif ($ext == "flv") {
|
} elseif ($ext == "flv") {
|
||||||
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br><object data='$data_href/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'><param value='#000000' name='bgcolor'><param name='allowFullScreen' value='true'><param value='high' name='quality'><param value='opaque' name='wmode'><param value='source=$ilink&type=video&streamtype=file&controltype=0' name='flashvars'></object>";
|
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br/>
|
||||||
|
<object data='{$data_href}/lib/Jaris/bin/JarisFLVPlayer.swf' id='VideoPlayer' type='application/x-shockwave-flash' height='" . strval($image->height + 1). "px' width='" . strval($image->width) . "px'>
|
||||||
|
<param value='#000000' name='bgcolor'>
|
||||||
|
<param name='allowFullScreen' value='true'>
|
||||||
|
<param value='high' name='quality'>
|
||||||
|
<param value='opaque' name='wmode'>
|
||||||
|
<param value='source={$ilink}&type=video&streamtype=file&controltype=0' name='flashvars'>
|
||||||
|
</object>";
|
||||||
} elseif ($ext == "ogv") {
|
} elseif ($ext == "ogv") {
|
||||||
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br><video controls='controls' autoplay='autoplay'>
|
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br/>
|
||||||
|
<video controls autoplay loop>
|
||||||
<source src='" . make_link("/image/" . $image->id) . "' type='video/ogg' />
|
<source src='" . make_link("/image/" . $image->id) . "' type='video/ogg' />
|
||||||
</video>";
|
</video>";
|
||||||
} elseif ($ext == "webm") {
|
} elseif ($ext == "webm") {
|
||||||
$html = "Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br><video controls='controls' autoplay='autoplay'>
|
$ie_only = "<!--[if IE]><p>To view webm files with IE, please <a href='http://tools.google.com/dlpage/webmmf/' target='_blank'>download this plugin</a>.</p><![endif]-->";
|
||||||
|
$html = $ie_only ."Video not playing? <a href='" . $image->parse_link_template(make_link('image/$id/$id%20-%20$tags.$ext')) . "'>Click here</a> to download the file.<br/>
|
||||||
|
<video controls autoplay loop>
|
||||||
<source src='" . make_link("/image/" . $image->id) . "' type='video/webm' />
|
<source src='" . make_link("/image/" . $image->id) . "' type='video/webm' />
|
||||||
</video>";
|
</video>";
|
||||||
}
|
}
|
||||||
|
@ -12,15 +12,17 @@
|
|||||||
* An image is being added to the database.
|
* An image is being added to the database.
|
||||||
*/
|
*/
|
||||||
class ImageAdditionEvent extends Event {
|
class ImageAdditionEvent extends Event {
|
||||||
var $user, $image;
|
var $user;
|
||||||
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Inserts a new image into the database with its associated
|
* Inserts a new image into the database with its associated
|
||||||
* information. Also calls TagSetEvent to set the tags for
|
* information. Also calls TagSetEvent to set the tags for
|
||||||
* this new image.
|
* this new image.
|
||||||
*
|
*
|
||||||
* @sa TagSetEvent
|
* @see TagSetEvent
|
||||||
* @param $image Image The new image to add.
|
* @param Image $image The new image to add.
|
||||||
*/
|
*/
|
||||||
public function __construct(Image $image) {
|
public function __construct(Image $image) {
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
@ -39,14 +41,16 @@ class ImageAdditionException extends SCoreException {
|
|||||||
* An image is being deleted.
|
* An image is being deleted.
|
||||||
*/
|
*/
|
||||||
class ImageDeletionEvent extends Event {
|
class ImageDeletionEvent extends Event {
|
||||||
var $image;
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Deletes an image.
|
* Deletes an image.
|
||||||
|
*
|
||||||
* Used by things like tags and comments handlers to
|
* Used by things like tags and comments handlers to
|
||||||
* clean out related rows in their tables.
|
* clean out related rows in their tables.
|
||||||
*
|
*
|
||||||
* @param $image Image The image being deleted
|
* @param Image $image The image being deleted.
|
||||||
*/
|
*/
|
||||||
public function __construct(Image $image) {
|
public function __construct(Image $image) {
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
@ -57,18 +61,20 @@ class ImageDeletionEvent extends Event {
|
|||||||
* An image is being replaced.
|
* An image is being replaced.
|
||||||
*/
|
*/
|
||||||
class ImageReplaceEvent extends Event {
|
class ImageReplaceEvent extends Event {
|
||||||
var $id, $image;
|
/** @var int */
|
||||||
|
public $id;
|
||||||
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Replaces an image.
|
* Replaces an image.
|
||||||
|
*
|
||||||
* Updates an existing ID in the database to use a new image
|
* Updates an existing ID in the database to use a new image
|
||||||
* file, leaving the tags and such unchanged. Also removes
|
* file, leaving the tags and such unchanged. Also removes
|
||||||
* the old image file and thumbnail from the disk.
|
* the old image file and thumbnail from the disk.
|
||||||
*
|
*
|
||||||
* @param $id
|
* @param int $id The ID of the image to replace.
|
||||||
* The ID of the image to replace
|
* @param Image $image The image object of the new image to use.
|
||||||
* @param $image
|
|
||||||
* The image object of the new image to use
|
|
||||||
*/
|
*/
|
||||||
public function __construct(/*int*/ $id, Image $image) {
|
public function __construct(/*int*/ $id, Image $image) {
|
||||||
$this->id = $id;
|
$this->id = $id;
|
||||||
@ -77,8 +83,12 @@ class ImageReplaceEvent extends Event {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class ImageReplaceException extends SCoreException {
|
class ImageReplaceException extends SCoreException {
|
||||||
var $error;
|
/** @var string */
|
||||||
|
public $error;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $error
|
||||||
|
*/
|
||||||
public function __construct(/*string*/ $error) {
|
public function __construct(/*string*/ $error) {
|
||||||
$this->error = $error;
|
$this->error = $error;
|
||||||
}
|
}
|
||||||
@ -88,14 +98,19 @@ class ImageReplaceException extends SCoreException {
|
|||||||
* Request a thumbnail be made for an image object.
|
* Request a thumbnail be made for an image object.
|
||||||
*/
|
*/
|
||||||
class ThumbnailGenerationEvent extends Event {
|
class ThumbnailGenerationEvent extends Event {
|
||||||
var $hash, $type, $force;
|
/** @var string */
|
||||||
|
public $hash;
|
||||||
|
/** @var string */
|
||||||
|
public $type;
|
||||||
|
/** @var bool */
|
||||||
|
public $force;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Request a thumbnail be made for an image object
|
* Request a thumbnail be made for an image object
|
||||||
*
|
*
|
||||||
* @param $hash string The unique hash of the image
|
* @param string $hash The unique hash of the image
|
||||||
* @param $type string The type of the image
|
* @param string $type The type of the image
|
||||||
* @param $force boolean Regenerate the thumbnail even if one already exists
|
* @param bool $force Regenerate the thumbnail even if one already exists
|
||||||
*/
|
*/
|
||||||
public function __construct($hash, $type, $force=false) {
|
public function __construct($hash, $type, $force=false) {
|
||||||
$this->hash = $hash;
|
$this->hash = $hash;
|
||||||
@ -112,14 +127,27 @@ class ThumbnailGenerationEvent extends Event {
|
|||||||
* $image -- the image who's link is being parsed
|
* $image -- the image who's link is being parsed
|
||||||
*/
|
*/
|
||||||
class ParseLinkTemplateEvent extends Event {
|
class ParseLinkTemplateEvent extends Event {
|
||||||
var $link, $original, $image;
|
/** @var string */
|
||||||
|
public $link;
|
||||||
|
/** @var string */
|
||||||
|
public $original;
|
||||||
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $link The formatted link
|
||||||
|
* @param Image $image The image who's link is being parsed
|
||||||
|
*/
|
||||||
public function __construct($link, Image $image) {
|
public function __construct($link, Image $image) {
|
||||||
$this->link = $link;
|
$this->link = $link;
|
||||||
$this->original = $link;
|
$this->original = $link;
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $needle
|
||||||
|
* @param string $replace
|
||||||
|
*/
|
||||||
public function replace($needle, $replace) {
|
public function replace($needle, $replace) {
|
||||||
$this->link = str_replace($needle, $replace, $this->link);
|
$this->link = str_replace($needle, $replace, $this->link);
|
||||||
}
|
}
|
||||||
@ -189,8 +217,7 @@ class ImageIO extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
||||||
global $user;
|
global $user, $config;
|
||||||
global $config;
|
|
||||||
|
|
||||||
if($user->can("delete_image")) {
|
if($user->can("delete_image")) {
|
||||||
$event->add_part($this->theme->get_deleter_html($event->image->id));
|
$event->add_part($this->theme->get_deleter_html($event->image->id));
|
||||||
@ -277,6 +304,11 @@ class ImageIO extends Extension {
|
|||||||
|
|
||||||
|
|
||||||
// add image {{{
|
// add image {{{
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return null
|
||||||
|
* @throws ImageAdditionException
|
||||||
|
*/
|
||||||
private function add_image(Image $image) {
|
private function add_image(Image $image) {
|
||||||
global $page, $user, $database, $config;
|
global $page, $user, $database, $config;
|
||||||
|
|
||||||
@ -346,6 +378,10 @@ class ImageIO extends Extension {
|
|||||||
// }}} end add
|
// }}} end add
|
||||||
|
|
||||||
// fetch image {{{
|
// fetch image {{{
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param string $type
|
||||||
|
*/
|
||||||
private function send_file($image_id, $type) {
|
private function send_file($image_id, $type) {
|
||||||
global $config;
|
global $config;
|
||||||
global $database;
|
global $database;
|
||||||
@ -398,6 +434,11 @@ class ImageIO extends Extension {
|
|||||||
// }}} end fetch
|
// }}} end fetch
|
||||||
|
|
||||||
// replace image {{{
|
// replace image {{{
|
||||||
|
/**
|
||||||
|
* @param int $id
|
||||||
|
* @param Image $image
|
||||||
|
* @throws ImageReplaceException
|
||||||
|
*/
|
||||||
private function replace_image($id, $image) {
|
private function replace_image($id, $image) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
|
@ -159,23 +159,39 @@
|
|||||||
* Signal that a search term needs parsing
|
* Signal that a search term needs parsing
|
||||||
*/
|
*/
|
||||||
class SearchTermParseEvent extends Event {
|
class SearchTermParseEvent extends Event {
|
||||||
var $term = null;
|
/** @var null|string */
|
||||||
var $context = null;
|
public $term = null;
|
||||||
var $querylets = array();
|
/** @var null|array */
|
||||||
|
public $context = null;
|
||||||
|
/** @var \Querylet[] */
|
||||||
|
public $querylets = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string|null $term
|
||||||
|
* @param array|null $context
|
||||||
|
*/
|
||||||
public function __construct($term, $context) {
|
public function __construct($term, $context) {
|
||||||
$this->term = $term;
|
$this->term = $term;
|
||||||
$this->context = $context;
|
$this->context = $context;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
public function is_querylet_set() {
|
public function is_querylet_set() {
|
||||||
return (count($this->querylets) > 0);
|
return (count($this->querylets) > 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return \Querylet[]
|
||||||
|
*/
|
||||||
public function get_querylets() {
|
public function get_querylets() {
|
||||||
return $this->querylets;
|
return $this->querylets;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param \Querylet $q
|
||||||
|
*/
|
||||||
public function add_querylet($q) {
|
public function add_querylet($q) {
|
||||||
$this->querylets[] = $q;
|
$this->querylets[] = $q;
|
||||||
}
|
}
|
||||||
@ -185,13 +201,23 @@ class SearchTermParseException extends SCoreException {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class PostListBuildingEvent extends Event {
|
class PostListBuildingEvent extends Event {
|
||||||
var $search_terms = null;
|
/** @var null|array */
|
||||||
var $parts = array();
|
public $search_terms = null;
|
||||||
|
|
||||||
|
/** @var array */
|
||||||
|
public $parts = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array|null $search
|
||||||
|
*/
|
||||||
public function __construct($search) {
|
public function __construct($search) {
|
||||||
$this->search_terms = $search;
|
$this->search_terms = $search;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $html
|
||||||
|
* @param int $position
|
||||||
|
*/
|
||||||
public function add_control(/*string*/ $html, /*int*/ $position=50) {
|
public function add_control(/*string*/ $html, /*int*/ $position=50) {
|
||||||
while(isset($this->parts[$position])) $position++;
|
while(isset($this->parts[$position])) $position++;
|
||||||
$this->parts[$position] = $html;
|
$this->parts[$position] = $html;
|
||||||
@ -234,10 +260,10 @@ class Index extends Extension {
|
|||||||
#log_debug("index", "Search for ".implode(" ", $search_terms), false, array("terms"=>$search_terms));
|
#log_debug("index", "Search for ".implode(" ", $search_terms), false, array("terms"=>$search_terms));
|
||||||
$total_pages = Image::count_pages($search_terms);
|
$total_pages = Image::count_pages($search_terms);
|
||||||
if(SPEED_HAX && $count_search_terms === 0 && ($page_number < 10)) { // extra caching for the first few post/list pages
|
if(SPEED_HAX && $count_search_terms === 0 && ($page_number < 10)) { // extra caching for the first few post/list pages
|
||||||
$images = $database->cache->get("post-list-$page_number");
|
$images = $database->cache->get("post-list:$page_number");
|
||||||
if(!$images) {
|
if(!$images) {
|
||||||
$images = Image::find_images(($page_number-1)*$page_size, $page_size, $search_terms);
|
$images = Image::find_images(($page_number-1)*$page_size, $page_size, $search_terms);
|
||||||
$database->cache->set("post-list-$page_number", $images, 600);
|
$database->cache->set("post-list:$page_number", $images, 600);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
@ -28,37 +28,13 @@ and of course start organising your images :-)
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function display_page(Page $page, $images) {
|
public function display_page(Page $page, $images) {
|
||||||
global $config;
|
$this->display_page_header($page, $images);
|
||||||
|
|
||||||
if(count($this->search_terms) == 0) {
|
|
||||||
$query = null;
|
|
||||||
$page_title = $config->get_string('title');
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$search_string = implode(' ', $this->search_terms);
|
|
||||||
$query = url_escape($search_string);
|
|
||||||
$page_title = html_escape($search_string);
|
|
||||||
if(count($images) > 0) {
|
|
||||||
$page->set_subheading("Page {$this->page_number} / {$this->total_pages}");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if($this->page_number > 1 || count($this->search_terms) > 0) {
|
|
||||||
// $page_title .= " / $page_number";
|
|
||||||
}
|
|
||||||
|
|
||||||
$nav = $this->build_navigation($this->page_number, $this->total_pages, $this->search_terms);
|
$nav = $this->build_navigation($this->page_number, $this->total_pages, $this->search_terms);
|
||||||
$page->set_title($page_title);
|
|
||||||
$page->set_heading($page_title);
|
|
||||||
$page->add_block(new Block("Navigation", $nav, "left", 0));
|
$page->add_block(new Block("Navigation", $nav, "left", 0));
|
||||||
|
|
||||||
if(count($images) > 0) {
|
if(count($images) > 0) {
|
||||||
if($query) {
|
$this->display_page_images($page, $images);
|
||||||
$page->add_block(new Block("Images", $this->build_table($images, "#search=$query"), "main", 10, "image-list"));
|
|
||||||
$this->display_paginator($page, "post/list/$query", null, $this->page_number, $this->total_pages);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$page->add_block(new Block("Images", $this->build_table($images, null), "main", 10, "image-list"));
|
|
||||||
$this->display_paginator($page, "post/list", null, $this->page_number, $this->total_pages);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
$this->display_error(404, "No Images Found", "No images were found to match the search criteria");
|
$this->display_error(404, "No Images Found", "No images were found to match the search criteria");
|
||||||
@ -105,5 +81,36 @@ and of course start organising your images :-)
|
|||||||
$table .= "</div>";
|
$table .= "</div>";
|
||||||
return $table;
|
return $table;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected function display_page_header(Page $page, $images) {
|
||||||
|
global $config;
|
||||||
|
|
||||||
|
if (count($this->search_terms) == 0) {
|
||||||
|
$page_title = $config->get_string('title');
|
||||||
|
} else {
|
||||||
|
$search_string = implode(' ', $this->search_terms);
|
||||||
|
$page_title = html_escape($search_string);
|
||||||
|
if (count($images) > 0) {
|
||||||
|
$page->set_subheading("Page {$this->page_number} / {$this->total_pages}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ($this->page_number > 1 || count($this->search_terms) > 0) {
|
||||||
|
// $page_title .= " / $page_number";
|
||||||
|
}
|
||||||
|
|
||||||
|
$page->set_title($page_title);
|
||||||
|
$page->set_heading($page_title);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected function display_page_images(Page $page, $images) {
|
||||||
|
if (count($this->search_terms) > 0) {
|
||||||
|
$query = url_escape(implode(' ', $this->search_terms));
|
||||||
|
$page->add_block(new Block("Images", $this->build_table($images, "#search=$query"), "main", 10, "image-list"));
|
||||||
|
$this->display_paginator($page, "post/list/$query", null, $this->page_number, $this->total_pages);
|
||||||
|
} else {
|
||||||
|
$page->add_block(new Block("Images", $this->build_table($images, null), "main", 10, "image-list"));
|
||||||
|
$this->display_paginator($page, "post/list", null, $this->page_number, $this->total_pages);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
BIN
ext/notes/border-h.gif
Normal file
BIN
ext/notes/border-h.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 72 B |
BIN
ext/notes/border-v.gif
Normal file
BIN
ext/notes/border-v.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 72 B |
@ -109,7 +109,7 @@ class Notes extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("note/updated"));
|
$page->set_redirect(make_link("note/updated"));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "add_note":
|
case "add_note":
|
||||||
@ -118,7 +118,7 @@ class Notes extends Extension {
|
|||||||
$this->add_new_note();
|
$this->add_new_note();
|
||||||
|
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "add_request":
|
case "add_request":
|
||||||
@ -127,7 +127,7 @@ class Notes extends Extension {
|
|||||||
$this->add_note_request();
|
$this->add_note_request();
|
||||||
|
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "nuke_notes":
|
case "nuke_notes":
|
||||||
@ -136,7 +136,7 @@ class Notes extends Extension {
|
|||||||
$this->nuke_notes();
|
$this->nuke_notes();
|
||||||
|
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "nuke_requests":
|
case "nuke_requests":
|
||||||
@ -145,7 +145,7 @@ class Notes extends Extension {
|
|||||||
$this->nuke_requests();
|
$this->nuke_requests();
|
||||||
|
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
$page->set_redirect(make_link("post/view/".$_POST["image_id"]));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "edit_note":
|
case "edit_note":
|
||||||
@ -238,18 +238,21 @@ class Notes extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE GET ALL NOTES FOR DISPLAYED IMAGE
|
* HERE WE GET ALL NOTES FOR DISPLAYED IMAGE.
|
||||||
|
*
|
||||||
|
* @param int $imageID
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
private function get_notes($imageID) {
|
private function get_notes($imageID) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
return $database->get_all(
|
return $database->get_all(
|
||||||
"SELECT * ".
|
"SELECT * ".
|
||||||
"FROM notes ".
|
"FROM notes ".
|
||||||
"WHERE enable = ? AND image_id = ? ".
|
"WHERE enable = ? AND image_id = ? ".
|
||||||
"ORDER BY date ASC"
|
"ORDER BY date ASC"
|
||||||
, array('1', $imageID));
|
, array('1', $imageID));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -345,7 +348,6 @@ class Notes extends Extension {
|
|||||||
|
|
||||||
$this->add_history(1, $noteID, $imageID, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText);
|
$this->add_history(1, $noteID, $imageID, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -353,7 +355,7 @@ class Notes extends Extension {
|
|||||||
*/
|
*/
|
||||||
private function delete_note()
|
private function delete_note()
|
||||||
{
|
{
|
||||||
global $user;
|
global $user;
|
||||||
|
|
||||||
$imageID = int_escape($_POST["image_id"]);
|
$imageID = int_escape($_POST["image_id"]);
|
||||||
$noteID = int_escape($_POST["note_id"]);
|
$noteID = int_escape($_POST["note_id"]);
|
||||||
@ -399,28 +401,27 @@ class Notes extends Extension {
|
|||||||
|
|
||||||
log_info("notes", "Requests deleted from {$image_id} by {$user->name}");
|
log_info("notes", "Requests deleted from {$image_id} by {$user->name}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* HERE WE ALL IMAGES THAT HAVE NOTES
|
|
||||||
*/
|
|
||||||
private function get_notes_list($event) {
|
|
||||||
$pageNumber = $event->get_arg(1);
|
|
||||||
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
|
||||||
$pageNumber = 0;
|
|
||||||
else if ($pageNumber <= 0)
|
|
||||||
$pageNumber = 0;
|
|
||||||
else
|
|
||||||
$pageNumber--;
|
|
||||||
|
|
||||||
global $config;
|
/**
|
||||||
|
* HERE WE ALL IMAGES THAT HAVE NOTES
|
||||||
|
* @param PageRequestEvent $event
|
||||||
|
*/
|
||||||
|
private function get_notes_list(PageRequestEvent $event) {
|
||||||
|
global $database, $config;
|
||||||
|
|
||||||
|
$pageNumber = $event->get_arg(1);
|
||||||
|
|
||||||
|
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
||||||
|
$pageNumber = 0;
|
||||||
|
else if ($pageNumber <= 0)
|
||||||
|
$pageNumber = 0;
|
||||||
|
else
|
||||||
|
$pageNumber--;
|
||||||
|
|
||||||
$notesPerPage = $config->get_int('notesNotesPerPage');
|
$notesPerPage = $config->get_int('notesNotesPerPage');
|
||||||
|
|
||||||
|
|
||||||
//$result = $database->get_all("SELECT * FROM pool_images WHERE pool_id=?", array($poolID));
|
//$result = $database->get_all("SELECT * FROM pool_images WHERE pool_id=?", array($poolID));
|
||||||
global $database;
|
|
||||||
$get_notes = "
|
$get_notes = "
|
||||||
SELECT DISTINCT image_id ".
|
SELECT DISTINCT image_id ".
|
||||||
"FROM notes ".
|
"FROM notes ".
|
||||||
@ -440,26 +441,26 @@ class Notes extends Extension {
|
|||||||
|
|
||||||
$this->theme->display_note_list($images, $pageNumber + 1, $totalPages);
|
$this->theme->display_note_list($images, $pageNumber + 1, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* HERE WE GET ALL NOTE REQUESTS
|
|
||||||
*/
|
|
||||||
private function get_notes_requests($event) {
|
|
||||||
$pageNumber = $event->get_arg(1);
|
|
||||||
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
|
||||||
$pageNumber = 0;
|
|
||||||
else if ($pageNumber <= 0)
|
|
||||||
$pageNumber = 0;
|
|
||||||
else
|
|
||||||
$pageNumber--;
|
|
||||||
|
|
||||||
global $config;
|
/**
|
||||||
|
* HERE WE GET ALL NOTE REQUESTS
|
||||||
|
* @param PageRequestEvent $event
|
||||||
|
*/
|
||||||
|
private function get_notes_requests(PageRequestEvent $event) {
|
||||||
|
global $config;
|
||||||
|
|
||||||
|
$pageNumber = $event->get_arg(1);
|
||||||
|
|
||||||
|
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
||||||
|
$pageNumber = 0;
|
||||||
|
else if ($pageNumber <= 0)
|
||||||
|
$pageNumber = 0;
|
||||||
|
else
|
||||||
|
$pageNumber--;
|
||||||
|
|
||||||
$requestsPerPage = $config->get_int('notesRequestsPerPage');
|
$requestsPerPage = $config->get_int('notesRequestsPerPage');
|
||||||
|
|
||||||
|
|
||||||
//$result = $database->get_all("SELECT * FROM pool_images WHERE pool_id=?", array($poolID));
|
//$result = $database->get_all("SELECT * FROM pool_images WHERE pool_id=?", array($poolID));
|
||||||
global $database;
|
global $database;
|
||||||
$get_requests = "
|
$get_requests = "
|
||||||
@ -501,13 +502,13 @@ class Notes extends Extension {
|
|||||||
(?, ?, ?, ?, ?, ?, now(), ?, ?, ?, ?, ?)",
|
(?, ?, ?, ?, ?, ?, now(), ?, ?, ?, ?, ?)",
|
||||||
array($noteEnable, $noteID, $reviewID, $imageID, $userID, $_SERVER['REMOTE_ADDR'], $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText));
|
array($noteEnable, $noteID, $reviewID, $imageID, $userID, $_SERVER['REMOTE_ADDR'], $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE GET ALL HISTORIES.
|
||||||
* HERE WE GET ALL HISTORIES.
|
* @param PageRequestEvent $event
|
||||||
*/
|
*/
|
||||||
private function get_histories($event){
|
private function get_histories(PageRequestEvent $event){
|
||||||
$pageNumber = $event->get_arg(1);
|
$pageNumber = $event->get_arg(1);
|
||||||
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
||||||
$pageNumber = 0;
|
$pageNumber = 0;
|
||||||
@ -533,13 +534,13 @@ class Notes extends Extension {
|
|||||||
|
|
||||||
$this->theme->display_histories($histories, $pageNumber + 1, $totalPages);
|
$this->theme->display_histories($histories, $pageNumber + 1, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE THE HISTORY FOR A SPECIFIC NOTE.
|
||||||
* HERE WE THE HISTORY FOR A SPECIFIC NOTE.
|
* @param PageRequestEvent $event
|
||||||
*/
|
*/
|
||||||
private function get_history($event){
|
private function get_history(PageRequestEvent $event){
|
||||||
$noteID = $event->get_arg(1);
|
$noteID = $event->get_arg(1);
|
||||||
$pageNumber = $event->get_arg(2);
|
$pageNumber = $event->get_arg(2);
|
||||||
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
if(is_null($pageNumber) || !is_numeric($pageNumber))
|
||||||
@ -566,14 +567,14 @@ class Notes extends Extension {
|
|||||||
|
|
||||||
$this->theme->display_history($histories, $pageNumber + 1, $totalPages);
|
$this->theme->display_history($histories, $pageNumber + 1, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HERE GO BACK IN HISTORY AND SET THE OLD NOTE. IF WAS REMOVED WE RE-ADD IT.
|
||||||
/*
|
* @param int $noteID
|
||||||
* HERE GO BACK IN HISTORY AND SET THE OLD NOTE. IF WAS REMOVED WE READD IT.
|
* @param int $reviewID
|
||||||
*/
|
*/
|
||||||
private function revert_history($noteID, $reviewID){
|
private function revert_history($noteID, $reviewID){
|
||||||
global $user, $database;
|
global $database;
|
||||||
|
|
||||||
$history = $database->get_row("SELECT * FROM note_histories WHERE note_id = ? AND review_id = ?",array($noteID, $reviewID));
|
$history = $database->get_row("SELECT * FROM note_histories WHERE note_id = ? AND review_id = ?",array($noteID, $reviewID));
|
||||||
|
|
||||||
@ -596,7 +597,6 @@ class Notes extends Extension {
|
|||||||
"WHERE image_id = ? AND id = ?", array(1, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText, $imageID, $noteID));
|
"WHERE image_id = ? AND id = ?", array(1, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText, $imageID, $noteID));
|
||||||
|
|
||||||
$this->add_history($noteEnable, $noteID, $imageID, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText);
|
$this->add_history($noteEnable, $noteID, $imageID, $noteX1, $noteY1, $noteHeight, $noteWidth, $noteText);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,7 +2,9 @@
|
|||||||
|
|
||||||
$(function() {
|
$(function() {
|
||||||
if(window.notes) {
|
if(window.notes) {
|
||||||
$('#main_image').imgNotes({notes: window.notes});
|
$('#main_image').load(function(){
|
||||||
|
$('#main_image').imgNotes({notes: window.notes});
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
$('#cancelnote').click(function(){
|
$('#cancelnote').click(function(){
|
||||||
|
@ -33,3 +33,45 @@
|
|||||||
#noteform textarea, #noteEditForm textarea {
|
#noteform textarea, #noteEditForm textarea {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* imgAreaSelect default style
|
||||||
|
*/
|
||||||
|
|
||||||
|
.imgareaselect-border1 {
|
||||||
|
background: url(border-v.gif) repeat-y left top;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-border2 {
|
||||||
|
background: url(border-h.gif) repeat-x left top;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-border3 {
|
||||||
|
background: url(border-v.gif) repeat-y right top;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-border4 {
|
||||||
|
background: url(border-h.gif) repeat-x left bottom;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-border1, .imgareaselect-border2,
|
||||||
|
.imgareaselect-border3, .imgareaselect-border4 {
|
||||||
|
filter: alpha(opacity=50);
|
||||||
|
opacity: 0.5;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-handle {
|
||||||
|
background-color: #fff;
|
||||||
|
border: solid 1px #000;
|
||||||
|
filter: alpha(opacity=50);
|
||||||
|
opacity: 0.5;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-outer {
|
||||||
|
/*background-color: #000;*/
|
||||||
|
filter: alpha(opacity=50);
|
||||||
|
opacity: 0.5;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imgareaselect-selection {
|
||||||
|
}
|
@ -284,6 +284,11 @@ class NumericScore extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param int $user_id
|
||||||
|
* @param int $score
|
||||||
|
*/
|
||||||
private function add_vote(/*int*/ $image_id, /*int*/ $user_id, /*int*/ $score) {
|
private function add_vote(/*int*/ $image_id, /*int*/ $user_id, /*int*/ $score) {
|
||||||
global $database;
|
global $database;
|
||||||
$database->execute(
|
$database->execute(
|
||||||
|
@ -58,7 +58,7 @@ class NumericScoreTheme extends Themelet {
|
|||||||
<input type='submit' value='Delete all votes by this user'>
|
<input type='submit' value='Delete all votes by this user'>
|
||||||
</form>
|
</form>
|
||||||
";
|
";
|
||||||
$page->add_block(new Block("Votes", $html, "main", 60));
|
$page->add_block(new Block("Votes", $html, "main", 80));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function view_popular($images, $dte) {
|
public function view_popular($images, $dte) {
|
||||||
|
@ -197,7 +197,7 @@ class PrivMsg extends Extension {
|
|||||||
private function count_pms(User $user) {
|
private function count_pms(User $user) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
$count = $database->cache->get("pm-count-{$user->id}");
|
$count = $database->cache->get("pm-count:{$user->id}");
|
||||||
if(is_null($count) || $count === false) {
|
if(is_null($count) || $count === false) {
|
||||||
$count = $database->get_one("
|
$count = $database->get_one("
|
||||||
SELECT count(*)
|
SELECT count(*)
|
||||||
@ -205,7 +205,7 @@ class PrivMsg extends Extension {
|
|||||||
WHERE to_id = :to_id
|
WHERE to_id = :to_id
|
||||||
AND is_read = :is_read
|
AND is_read = :is_read
|
||||||
", array("to_id" => $user->id, "is_read" => "N"));
|
", array("to_id" => $user->id, "is_read" => "N"));
|
||||||
$database->cache->set("pm-count-{$user->id}", $count, 600);
|
$database->cache->set("pm-count:{$user->id}", $count, 600);
|
||||||
}
|
}
|
||||||
return $count;
|
return $count;
|
||||||
}
|
}
|
||||||
|
@ -39,7 +39,7 @@ class PrivMsgTheme extends Themelet {
|
|||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
";
|
";
|
||||||
$page->add_block(new Block("Private Messages", $html, "main", 10, "private-messages"));
|
$page->add_block(new Block("Private Messages", $html, "main", 40, "private-messages"));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function display_composer(Page $page, User $from, User $to, $subject="") {
|
public function display_composer(Page $page, User $from, User $to, $subject="") {
|
||||||
@ -59,7 +59,7 @@ $auth
|
|||||||
</table>
|
</table>
|
||||||
</form>
|
</form>
|
||||||
EOD;
|
EOD;
|
||||||
$page->add_block(new Block("Write a PM", $html, "main", 20));
|
$page->add_block(new Block("Write a PM", $html, "main", 50));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function display_message(Page $page, User $from, User $to, PM $pm) {
|
public function display_message(Page $page, User $from, User $to, PM $pm) {
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
/**
|
/**
|
||||||
* Name: Pools System
|
* Name: Pools System
|
||||||
* Author: Sein Kraft <mail@seinkraft.info>, jgen <jgen.tech@gmail.com>
|
* Author: Sein Kraft <mail@seinkraft.info>, jgen <jgen.tech@gmail.com>, Daku <admin@codeanimu.net>
|
||||||
* License: GPLv2
|
* License: GPLv2
|
||||||
* Description: Allow users to create groups of images and order them.
|
* Description: Allow users to create groups of images and order them.
|
||||||
* Documentation: This extension allows users to created named groups of
|
* Documentation: This extension allows users to created named groups of
|
||||||
@ -13,8 +13,12 @@
|
|||||||
* This class is just a wrapper around SCoreException.
|
* This class is just a wrapper around SCoreException.
|
||||||
*/
|
*/
|
||||||
class PoolCreationException extends SCoreException {
|
class PoolCreationException extends SCoreException {
|
||||||
var $error;
|
/** @var string */
|
||||||
|
public $error;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $error
|
||||||
|
*/
|
||||||
public function __construct($error) {
|
public function __construct($error) {
|
||||||
$this->error = $error;
|
$this->error = $error;
|
||||||
}
|
}
|
||||||
@ -76,6 +80,13 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
$config->set_int("ext_pools_version", 2);
|
$config->set_int("ext_pools_version", 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($config->get_int("ext_pools_version") < 3){
|
||||||
|
$config->set_bool("poolsShowNavLinks","N"); //A $config->rename() function would be nice here...
|
||||||
|
$config->set_bool("poolsAutoIncrementOrder","N");
|
||||||
|
|
||||||
|
$config->set_int("ext_pools_version", 3);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add a block to the Board Config / Setup
|
// Add a block to the Board Config / Setup
|
||||||
@ -86,19 +97,20 @@ class Pools extends Extension {
|
|||||||
$sb->add_int_option("poolsListsPerPage", "<br>Index list items per page: ");
|
$sb->add_int_option("poolsListsPerPage", "<br>Index list items per page: ");
|
||||||
$sb->add_int_option("poolsUpdatedPerPage", "<br>Updated list items per page: ");
|
$sb->add_int_option("poolsUpdatedPerPage", "<br>Updated list items per page: ");
|
||||||
$sb->add_bool_option("poolsInfoOnViewImage", "<br>Show pool info on image: ");
|
$sb->add_bool_option("poolsInfoOnViewImage", "<br>Show pool info on image: ");
|
||||||
$sb->add_bool_option("poolsShowNextLink", "<br>Show 'Next' link when viewing pool images: ");
|
$sb->add_bool_option("poolsShowNavLinks", "<br>Show 'Prev' & 'Next' links when viewing pool images: ");
|
||||||
|
$sb->add_bool_option("poolsAutoIncrementOrder", "<br>Autoincrement order when post is added to pool:");
|
||||||
//$sb->add_bool_option("poolsAdderOnViewImage", "<br>Show pool adder on image: ");
|
//$sb->add_bool_option("poolsAdderOnViewImage", "<br>Show pool adder on image: ");
|
||||||
|
|
||||||
$event->panel->add_block($sb);
|
$event->panel->add_block($sb);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $config, $page, $user;
|
global $page, $user;
|
||||||
|
|
||||||
if ($event->page_matches("pool")) {
|
if ($event->page_matches("pool")) {
|
||||||
|
|
||||||
$pool_id = 0;
|
$pool_id = 0;
|
||||||
$pool = array();
|
$pool = array();
|
||||||
|
|
||||||
// Check if we have pool id, since this is most often the case.
|
// Check if we have pool id, since this is most often the case.
|
||||||
if (isset($_POST["pool_id"])) {
|
if (isset($_POST["pool_id"])) {
|
||||||
$pool_id = int_escape($_POST["pool_id"]);
|
$pool_id = int_escape($_POST["pool_id"]);
|
||||||
@ -220,8 +232,8 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
case "nuke":
|
case "nuke":
|
||||||
// Completely remove the given pool.
|
// Completely remove the given pool.
|
||||||
// -> Only admins and owners may do this
|
// -> Only admins and owners may do this
|
||||||
if($user->is_admin() || $user->id == $pool['user_id']) {
|
if($user->is_admin() || $user->id == $pool['user_id']) {
|
||||||
$this->nuke_pool($pool_id);
|
$this->nuke_pool($pool_id);
|
||||||
$page->set_mode("redirect");
|
$page->set_mode("redirect");
|
||||||
$page->set_redirect(make_link("pool/list"));
|
$page->set_redirect(make_link("pool/list"));
|
||||||
@ -249,30 +261,27 @@ class Pools extends Extension {
|
|||||||
* to the Next image in the pool.
|
* to the Next image in the pool.
|
||||||
*/
|
*/
|
||||||
public function onDisplayingImage(DisplayingImageEvent $event) {
|
public function onDisplayingImage(DisplayingImageEvent $event) {
|
||||||
global $config, $database, $page;
|
global $config;
|
||||||
|
|
||||||
if($config->get_bool("poolsInfoOnViewImage")) {
|
if($config->get_bool("poolsInfoOnViewImage")) {
|
||||||
$imageID = $event->image->id;
|
$imageID = $event->image->id;
|
||||||
$poolsIDs = $this->get_pool_id($imageID);
|
$poolsIDs = $this->get_pool_id($imageID);
|
||||||
|
|
||||||
$show_next = $config->get_bool("poolsShowNextLink", false);
|
|
||||||
|
|
||||||
$linksPools = array();
|
$show_nav = $config->get_bool("poolsShowNavLinks", false);
|
||||||
|
|
||||||
|
$navInfo = array();
|
||||||
foreach($poolsIDs as $poolID) {
|
foreach($poolsIDs as $poolID) {
|
||||||
$pools = $this->get_pool($poolID['pool_id']);
|
$pool = $this->get_single_pool($poolID['pool_id']);
|
||||||
foreach ($pools as $pool){
|
|
||||||
$linksPools[] = "<a href='".make_link("pool/view/".$pool['id'])."'>".html_escape($pool['title'])."</a>";
|
$navInfo[$pool['id']] = array();
|
||||||
|
$navInfo[$pool['id']]['info'] = $pool;
|
||||||
// Optionally show a link the Next image in the Pool.
|
|
||||||
if ($show_next) {
|
// Optionally show a link the Prev/Next image in the Pool.
|
||||||
$next_image_in_pool = $this->get_next_post($pool, $imageID);
|
if ($show_nav) {
|
||||||
if (!empty($next_image_in_pool)) {
|
$navInfo[$pool['id']]['nav'] = $this->get_nav_posts($pool, $imageID);
|
||||||
$linksPools[] = '<a href="'.make_link('post/view/'.$next_image_in_pool).'" class="pools_next_img">Next</a>';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
$this->theme->pool_info($linksPools);
|
$this->theme->pool_info($navInfo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -316,19 +325,24 @@ class Pools extends Extension {
|
|||||||
public function onTagTermParse(TagTermParseEvent $event) {
|
public function onTagTermParse(TagTermParseEvent $event) {
|
||||||
$matches = array();
|
$matches = array();
|
||||||
|
|
||||||
if(preg_match("/^pool[=|:](.*)$/i", $event->term, $matches)) {
|
if(preg_match("/^pool[=|:]([^:]*|lastcreated):?([0-9]*)$/i", $event->term, $matches)) {
|
||||||
global $user;
|
global $user;
|
||||||
$poolTag = (string) str_replace("_", " ", $matches[1]);
|
$poolTag = (string) str_replace("_", " ", $matches[1]);
|
||||||
|
|
||||||
$pool = null;
|
$pool = null;
|
||||||
if(ctype_digit($poolTag)){ //If only digits, assume PoolID
|
if($poolTag == 'lastcreated'){
|
||||||
|
$pool = $this->get_last_userpool($user->id);
|
||||||
|
}
|
||||||
|
elseif(ctype_digit($poolTag)){ //If only digits, assume PoolID
|
||||||
$pool = $this->get_single_pool($poolTag);
|
$pool = $this->get_single_pool($poolTag);
|
||||||
}else{ //assume PoolTitle
|
}else{ //assume PoolTitle
|
||||||
$pool = $this->get_single_pool_from_title($poolTag);
|
$pool = $this->get_single_pool_from_title($poolTag);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if($pool ? $this->have_permission($user, $pool) : FALSE){
|
if($pool ? $this->have_permission($user, $pool) : FALSE){
|
||||||
$this->add_post($pool['id'], $event->id, true);
|
$image_order = ($matches[2] ?: 0);
|
||||||
|
$this->add_post($pool['id'], $event->id, true, $image_order);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -338,10 +352,14 @@ class Pools extends Extension {
|
|||||||
/* ------------------------------------------------- */
|
/* ------------------------------------------------- */
|
||||||
/* -------------- Private Functions -------------- */
|
/* -------------- Private Functions -------------- */
|
||||||
/* ------------------------------------------------- */
|
/* ------------------------------------------------- */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if the given user has permission to edit/change the pool.
|
* Check if the given user has permission to edit/change the pool.
|
||||||
|
*
|
||||||
* TODO: Should the user variable be global?
|
* TODO: Should the user variable be global?
|
||||||
|
*
|
||||||
|
* @param \User $user
|
||||||
|
* @param array $pool
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
private function have_permission($user, $pool) {
|
private function have_permission($user, $pool) {
|
||||||
@ -353,9 +371,12 @@ class Pools extends Extension {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE GET THE LIST OF POOLS
|
* HERE WE GET THE LIST OF POOLS.
|
||||||
|
*
|
||||||
|
* @param \Page $page
|
||||||
|
* @param int $pageNumber
|
||||||
*/
|
*/
|
||||||
private function list_pools(Page $page, /*int*/ $pageNumber) {
|
private function list_pools(Page $page, /*int*/ $pageNumber) {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
@ -399,8 +420,11 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE CREATE A NEW POOL
|
* HERE WE CREATE A NEW POOL
|
||||||
|
*
|
||||||
|
* @return mixed
|
||||||
|
* @throws PoolCreationException
|
||||||
*/
|
*/
|
||||||
private function add_pool() {
|
private function add_pool() {
|
||||||
global $user, $database;
|
global $user, $database;
|
||||||
@ -431,8 +455,11 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve information about pools given multiple pool IDs.
|
* Retrieve information about pools given multiple pool IDs.
|
||||||
* @param $poolID Array of integers
|
*
|
||||||
* @return 2D Array
|
* TODO: What is the difference between this and get_single_pool() other than the db query?
|
||||||
|
*
|
||||||
|
* @param int $poolID Array of integers
|
||||||
|
* @return array
|
||||||
*/
|
*/
|
||||||
private function get_pool(/*int*/ $poolID) {
|
private function get_pool(/*int*/ $poolID) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -441,8 +468,8 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve information about a pool given a pool ID.
|
* Retrieve information about a pool given a pool ID.
|
||||||
* @param $poolID Integer
|
* @param int $poolID the pool id
|
||||||
* @return 2D array (with only 1 element in the one dimension)
|
* @return array Array with only 1 element in the one dimension
|
||||||
*/
|
*/
|
||||||
private function get_single_pool(/*int*/ $poolID) {
|
private function get_single_pool(/*int*/ $poolID) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -451,8 +478,8 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve information about a pool given a pool title.
|
* Retrieve information about a pool given a pool title.
|
||||||
* @param $poolTitle Integer
|
* @param string $poolTitle
|
||||||
* @return 2D array (with only 1 element in the one dimension)
|
* @return array Array (with only 1 element in the one dimension)
|
||||||
*/
|
*/
|
||||||
private function get_single_pool_from_title(/*string*/ $poolTitle) {
|
private function get_single_pool_from_title(/*string*/ $poolTitle) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -461,32 +488,44 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all of the pool IDs that an image is in, given an image ID.
|
* Get all of the pool IDs that an image is in, given an image ID.
|
||||||
* @param $imageID Integer
|
* @param int $imageID Integer ID for the image
|
||||||
* @return 2D array
|
* @return array
|
||||||
*/
|
*/
|
||||||
private function get_pool_id(/*int*/ $imageID) {
|
private function get_pool_id(/*int*/ $imageID) {
|
||||||
global $database;
|
global $database;
|
||||||
return $database->get_all("SELECT pool_id FROM pool_images WHERE image_id=:iid", array("iid"=>$imageID));
|
return $database->get_all("SELECT pool_id FROM pool_images WHERE image_id=:iid", array("iid"=>$imageID));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve information about the last pool the given userID created
|
||||||
|
* @param int $userID
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
private function get_last_userpool(/*int*/ $userID){
|
||||||
|
global $database;
|
||||||
|
return $database->get_row("SELECT * FROM pools WHERE user_id=:uid ORDER BY id DESC", array("uid"=>$userID));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE GET THE IMAGES FROM THE TAG ON IMPORT
|
* HERE WE GET THE IMAGES FROM THE TAG ON IMPORT
|
||||||
|
* @param int $pool_id
|
||||||
*/
|
*/
|
||||||
private function import_posts(/*int*/ $pool_id) {
|
private function import_posts(/*int*/ $pool_id) {
|
||||||
global $page, $config, $database;
|
global $page, $config;
|
||||||
|
|
||||||
$poolsMaxResults = $config->get_int("poolsMaxImportResults", 1000);
|
$poolsMaxResults = $config->get_int("poolsMaxImportResults", 1000);
|
||||||
|
|
||||||
$images = $images = Image::find_images(0, $poolsMaxResults, Tag::explode($_POST["pool_tag"]));
|
$images = $images = Image::find_images(0, $poolsMaxResults, Tag::explode($_POST["pool_tag"]));
|
||||||
$this->theme->pool_result($page, $images, $pool_id);
|
$this->theme->pool_result($page, $images, $this->get_pool($pool_id));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE ADD CHECKED IMAGES FROM POOL AND UPDATE THE HISTORY
|
* HERE WE ADD CHECKED IMAGES FROM POOL AND UPDATE THE HISTORY
|
||||||
*
|
*
|
||||||
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
private function add_posts() {
|
private function add_posts() {
|
||||||
global $database;
|
global $database;
|
||||||
@ -503,11 +542,10 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
$images .= " ".$imageID;
|
$images .= " ".$imageID;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!strlen($images) == 0) {
|
if(!strlen($images) == 0) {
|
||||||
$count = $database->get_one("SELECT COUNT(*) FROM pool_images WHERE pool_id=:pid", array("pid"=>$poolID));
|
$count = int_escape($database->get_one("SELECT COUNT(*) FROM pool_images WHERE pool_id=:pid", array("pid"=>$poolID)));
|
||||||
$this->add_history($poolID, 1, $images, $count);
|
$this->add_history($poolID, 1, $images, $count);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -517,11 +555,12 @@ class Pools extends Extension {
|
|||||||
WHERE id=:pid",
|
WHERE id=:pid",
|
||||||
array("pid"=>$poolID)
|
array("pid"=>$poolID)
|
||||||
);
|
);
|
||||||
return $poolID;
|
return $poolID;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
private function order_posts() {
|
private function order_posts() {
|
||||||
global $database;
|
global $database;
|
||||||
@ -541,11 +580,12 @@ class Pools extends Extension {
|
|||||||
return $poolID;
|
return $poolID;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
|
||||||
* HERE WE REMOVE CHECKED IMAGES FROM POOL AND UPDATE THE HISTORY
|
* HERE WE REMOVE CHECKED IMAGES FROM POOL AND UPDATE THE HISTORY
|
||||||
*
|
*
|
||||||
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
* TODO: Fix this so that the pool ID and images are passed as Arguments to the function.
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
private function remove_posts() {
|
private function remove_posts() {
|
||||||
global $database;
|
global $database;
|
||||||
@ -563,8 +603,9 @@ class Pools extends Extension {
|
|||||||
return $poolID;
|
return $poolID;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Allows editing of pool description.
|
* Allows editing of pool description.
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
private function edit_description() {
|
private function edit_description() {
|
||||||
global $database;
|
global $database;
|
||||||
@ -580,8 +621,8 @@ class Pools extends Extension {
|
|||||||
* Used by add_posts()
|
* Used by add_posts()
|
||||||
*
|
*
|
||||||
* @see add_posts()
|
* @see add_posts()
|
||||||
* @param $poolID integer
|
* @param int $poolID
|
||||||
* @param $imageID integer
|
* @param int $imageID
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
private function check_post(/*int*/ $poolID, /*int*/ $imageID) {
|
private function check_post(/*int*/ $poolID, /*int*/ $imageID) {
|
||||||
@ -591,26 +632,49 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the next successive image from a pool, given a pool ID and an image ID.
|
* Gets the previous and next successive images from a pool, given a pool ID and an image ID.
|
||||||
*
|
*
|
||||||
* @param $pool Array for the given pool
|
* @param array $pool Array for the given pool
|
||||||
* @param $imageID Integer
|
* @param int $imageID Integer
|
||||||
* @return Integer which is the next Image ID or NULL if none.
|
* @return array Array returning two elements (prev, next) in 1 dimension. Each returns ImageID or NULL if none.
|
||||||
*/
|
*/
|
||||||
private function get_next_post(/*array*/ $pool, /*int*/ $imageID) {
|
private function get_nav_posts(/*array*/ $pool, /*int*/ $imageID) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
if (empty($pool) || empty($imageID))
|
if (empty($pool) || empty($imageID))
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
$result = $database->get_one("
|
$result = $database->get_row("
|
||||||
SELECT image_id
|
SELECT (
|
||||||
FROM pool_images
|
SELECT image_id
|
||||||
WHERE pool_id=:pid
|
FROM pool_images
|
||||||
AND image_order > (SELECT image_order FROM pool_images WHERE pool_id=:pid AND image_id =:iid LIMIT 1 )
|
WHERE pool_id = :pid
|
||||||
ORDER BY image_order ASC LIMIT 1",
|
AND image_order < (
|
||||||
|
SELECT image_order
|
||||||
|
FROM pool_images
|
||||||
|
WHERE pool_id = :pid
|
||||||
|
AND image_id = :iid
|
||||||
|
LIMIT 1
|
||||||
|
)
|
||||||
|
ORDER BY image_order DESC LIMIT 1
|
||||||
|
) AS prev,
|
||||||
|
(
|
||||||
|
SELECT image_id
|
||||||
|
FROM pool_images
|
||||||
|
WHERE pool_id = :pid
|
||||||
|
AND image_order > (
|
||||||
|
SELECT image_order
|
||||||
|
FROM pool_images
|
||||||
|
WHERE pool_id = :pid
|
||||||
|
AND image_id = :iid
|
||||||
|
LIMIT 1
|
||||||
|
)
|
||||||
|
ORDER BY image_order ASC LIMIT 1
|
||||||
|
) AS next
|
||||||
|
|
||||||
|
LIMIT 1",
|
||||||
array("pid"=>$pool['id'], "iid"=>$imageID) );
|
array("pid"=>$pool['id'], "iid"=>$imageID) );
|
||||||
|
|
||||||
if (empty($result)) {
|
if (empty($result)) {
|
||||||
// assume that we are at the end of the pool
|
// assume that we are at the end of the pool
|
||||||
return null;
|
return null;
|
||||||
@ -621,6 +685,9 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve all the images in a pool, given a pool ID.
|
* Retrieve all the images in a pool, given a pool ID.
|
||||||
|
*
|
||||||
|
* @param PageRequestEvent $event
|
||||||
|
* @param int $poolID
|
||||||
*/
|
*/
|
||||||
private function get_posts($event, /*int*/ $poolID) {
|
private function get_posts($event, /*int*/ $poolID) {
|
||||||
global $config, $user, $database;
|
global $config, $user, $database;
|
||||||
@ -684,8 +751,8 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* This function gets the current order of images from a given pool.
|
* This function gets the current order of images from a given pool.
|
||||||
* @param $poolID integer
|
* @param int $poolID
|
||||||
* @return Array of image objects.
|
* @return \Image[] Array of image objects.
|
||||||
*/
|
*/
|
||||||
private function edit_posts(/*int*/ $poolID) {
|
private function edit_posts(/*int*/ $poolID) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -702,8 +769,11 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* WE GET THE ORDER OF THE IMAGES BUT HERE WE SEND KEYS ADDED IN ARRAY TO GET THE ORDER IN THE INPUT VALUE
|
* WE GET THE ORDER OF THE IMAGES BUT HERE WE SEND KEYS ADDED IN ARRAY TO GET THE ORDER IN THE INPUT VALUE.
|
||||||
|
*
|
||||||
|
* @param int $poolID
|
||||||
|
* @return \Image[]
|
||||||
*/
|
*/
|
||||||
private function edit_order(/*int*/ $poolID) {
|
private function edit_order(/*int*/ $poolID) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -726,8 +796,10 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE NUKE ENTIRE POOL. WE REMOVE POOLS AND POSTS FROM REMOVED POOL AND HISTORIES ENTRIES FROM REMOVED POOL
|
* HERE WE NUKE ENTIRE POOL. WE REMOVE POOLS AND POSTS FROM REMOVED POOL AND HISTORIES ENTRIES FROM REMOVED POOL.
|
||||||
|
*
|
||||||
|
* @param int $poolID
|
||||||
*/
|
*/
|
||||||
private function nuke_pool(/*int*/ $poolID) {
|
private function nuke_pool(/*int*/ $poolID) {
|
||||||
global $user, $database;
|
global $user, $database;
|
||||||
@ -744,10 +816,13 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE ADD A HISTORY ENTRY.
|
||||||
* HERE WE ADD A HISTORY ENTRY
|
*
|
||||||
* FOR $action 1 (one) MEANS ADDED, 0 (zero) MEANS REMOVED
|
* @param int $poolID
|
||||||
|
* @param int $action Action=1 (one) MEANS ADDED, Action=0 (zero) MEANS REMOVED
|
||||||
|
* @param string $images
|
||||||
|
* @param int $count
|
||||||
*/
|
*/
|
||||||
private function add_history(/*int*/ $poolID, $action, $images, $count) {
|
private function add_history(/*int*/ $poolID, $action, $images, $count) {
|
||||||
global $user, $database;
|
global $user, $database;
|
||||||
@ -758,9 +833,9 @@ class Pools extends Extension {
|
|||||||
array("pid"=>$poolID, "uid"=>$user->id, "act"=>$action, "img"=>$images, "count"=>$count));
|
array("pid"=>$poolID, "uid"=>$user->id, "act"=>$action, "img"=>$images, "count"=>$count));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE GET THE HISTORY LIST.
|
||||||
* HERE WE GET THE HISTORY LIST
|
* @param int $pageNumber
|
||||||
*/
|
*/
|
||||||
private function get_history(/*int*/ $pageNumber) {
|
private function get_history(/*int*/ $pageNumber) {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
@ -772,7 +847,6 @@ class Pools extends Extension {
|
|||||||
else
|
else
|
||||||
$pageNumber--;
|
$pageNumber--;
|
||||||
|
|
||||||
|
|
||||||
$historiesPerPage = $config->get_int("poolsUpdatedPerPage");
|
$historiesPerPage = $config->get_int("poolsUpdatedPerPage");
|
||||||
|
|
||||||
$history = $database->get_all("
|
$history = $database->get_all("
|
||||||
@ -792,10 +866,9 @@ class Pools extends Extension {
|
|||||||
$this->theme->show_history($history, $pageNumber + 1, $totalPages);
|
$this->theme->show_history($history, $pageNumber + 1, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HERE GO BACK IN HISTORY AND ADD OR REMOVE POSTS TO POOL.
|
||||||
/*
|
* @param int $historyID
|
||||||
* HERE GO BACK IN HISTORY AND ADD OR REMOVE POSTS TO POOL
|
|
||||||
*/
|
*/
|
||||||
private function revert_history(/*int*/ $historyID) {
|
private function revert_history(/*int*/ $historyID) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -810,8 +883,8 @@ class Pools extends Extension {
|
|||||||
|
|
||||||
if($entry['action'] == 0) {
|
if($entry['action'] == 0) {
|
||||||
// READ ENTRIES
|
// READ ENTRIES
|
||||||
foreach($images as $image) {
|
foreach($images as $image) {
|
||||||
$imageID = $image;
|
$imageID = $image;
|
||||||
$this->add_post($poolID, $imageID);
|
$this->add_post($poolID, $imageID);
|
||||||
|
|
||||||
$imageArray .= " ".$imageID;
|
$imageArray .= " ".$imageID;
|
||||||
@ -821,7 +894,7 @@ class Pools extends Extension {
|
|||||||
else if($entry['action'] == 1) {
|
else if($entry['action'] == 1) {
|
||||||
// DELETE ENTRIES
|
// DELETE ENTRIES
|
||||||
foreach($images as $image) {
|
foreach($images as $image) {
|
||||||
$imageID = $image;
|
$imageID = $image;
|
||||||
$this->delete_post($poolID, $imageID);
|
$this->delete_post($poolID, $imageID);
|
||||||
|
|
||||||
$imageArray .= " ".$imageID;
|
$imageArray .= " ".$imageID;
|
||||||
@ -838,20 +911,31 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HERE WE ADD A SIMPLE POST FROM POOL.
|
||||||
/*
|
* USED WITH FOREACH IN revert_history() & onTagTermParse().
|
||||||
* HERE WE ADD A SIMPLE POST FROM POOL
|
*
|
||||||
* USED WITH FOREACH IN revert_history() & onTagTermParse()
|
* @param int $poolID
|
||||||
|
* @param int $imageID
|
||||||
|
* @param bool $history
|
||||||
|
* @param int $imageOrder
|
||||||
*/
|
*/
|
||||||
private function add_post(/*int*/ $poolID, /*int*/ $imageID, $history=false) {
|
private function add_post(/*int*/ $poolID, /*int*/ $imageID, $history=false, $imageOrder=0) {
|
||||||
global $database;
|
global $database, $config;
|
||||||
|
|
||||||
if(!$this->check_post($poolID, $imageID)) {
|
if(!$this->check_post($poolID, $imageID)) {
|
||||||
|
if($config->get_bool("poolsAutoIncrementOrder") && $imageOrder === 0){
|
||||||
|
$imageOrder = $database->get_one("
|
||||||
|
SELECT CASE WHEN image_order IS NOT NULL THEN MAX(image_order) + 1 ELSE 0 END
|
||||||
|
FROM pool_images
|
||||||
|
WHERE pool_id = :pid",
|
||||||
|
array("pid"=>$poolID));
|
||||||
|
}
|
||||||
|
|
||||||
$database->execute("
|
$database->execute("
|
||||||
INSERT INTO pool_images (pool_id, image_id)
|
INSERT INTO pool_images (pool_id, image_id, image_order)
|
||||||
VALUES (:pid, :iid)",
|
VALUES (:pid, :iid, :ord)",
|
||||||
array("pid"=>$poolID, "iid"=>$imageID));
|
array("pid"=>$poolID, "iid"=>$imageID, "ord"=>$imageOrder));
|
||||||
}
|
}
|
||||||
|
|
||||||
$database->execute("UPDATE pools SET posts=(SELECT COUNT(*) FROM pool_images WHERE pool_id=:pid) WHERE id=:pid", array("pid"=>$poolID));
|
$database->execute("UPDATE pools SET posts=(SELECT COUNT(*) FROM pool_images WHERE pool_id=:pid) WHERE id=:pid", array("pid"=>$poolID));
|
||||||
@ -862,11 +946,13 @@ class Pools extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HERE WE REMOVE A SIMPLE POST FROM POOL.
|
||||||
/*
|
* USED WITH FOREACH IN revert_history() & onTagTermParse().
|
||||||
* HERE WE REMOVE A SIMPLE POST FROM POOL
|
*
|
||||||
* USED WITH FOREACH IN revert_history() & onTagTermParse()
|
* @param int $poolID
|
||||||
|
* @param int $imageID
|
||||||
|
* @param bool $history
|
||||||
*/
|
*/
|
||||||
private function delete_post(/*int*/ $poolID, /*int*/ $imageID, $history=false) {
|
private function delete_post(/*int*/ $poolID, /*int*/ $imageID, $history=false) {
|
||||||
global $database;
|
global $database;
|
||||||
|
13
ext/pools/style.css
Normal file
13
ext/pools/style.css
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
.pools_next_img {
|
||||||
|
display: block;
|
||||||
|
font-size: 77%;
|
||||||
|
text-align: right;
|
||||||
|
float: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pools_prev_img {
|
||||||
|
display: block;
|
||||||
|
font-size: 77%;
|
||||||
|
text-align: left;
|
||||||
|
float: left;
|
||||||
|
}
|
@ -3,14 +3,39 @@
|
|||||||
class PoolsTheme extends Themelet {
|
class PoolsTheme extends Themelet {
|
||||||
/**
|
/**
|
||||||
* Adds a block to the panel with information on the pool(s) the image is in.
|
* Adds a block to the panel with information on the pool(s) the image is in.
|
||||||
|
* @param array Multidimensional array containing pool id, info & nav IDs.
|
||||||
*/
|
*/
|
||||||
public function pool_info($linksPools) {
|
public function pool_info(/*array*/ $navIDs) {
|
||||||
global $page;
|
global $page;
|
||||||
|
|
||||||
|
$linksPools = array();
|
||||||
|
foreach($navIDs as $poolID => $pool){
|
||||||
|
$linksPools[] = "<a href='".make_link("pool/view/".$poolID)."'>".html_escape($pool['info']['title'])."</a>";
|
||||||
|
|
||||||
|
if (array_key_exists('nav', $pool)){
|
||||||
|
$navlinks = "";
|
||||||
|
if (!empty($pool['nav']['prev'])) {
|
||||||
|
$navlinks .= '<a href="'.make_link('post/view/'.$pool['nav']['prev']).'" class="pools_prev_img">Prev</a>';
|
||||||
|
}
|
||||||
|
if (!empty($pool['nav']['next'])) {
|
||||||
|
$navlinks .= '<a href="'.make_link('post/view/'.$pool['nav']['next']).'" class="pools_next_img">Next</a>';
|
||||||
|
}
|
||||||
|
if(!empty($navlinks)){
|
||||||
|
$linksPools[] = $navlinks;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if(count($linksPools) > 0) {
|
if(count($linksPools) > 0) {
|
||||||
$page->add_block(new Block("Pools", implode("<br>", $linksPools), "left"));
|
$page->add_block(new Block("Pools", implode("<br>", $linksPools), "left"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param array $pools
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function get_adder_html(Image $image, /*array*/ $pools) {
|
public function get_adder_html(Image $image, /*array*/ $pools) {
|
||||||
$h = "";
|
$h = "";
|
||||||
foreach($pools as $pool) {
|
foreach($pools as $pool) {
|
||||||
@ -27,9 +52,13 @@ class PoolsTheme extends Themelet {
|
|||||||
return $editor;
|
return $editor;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE SHOWS THE LIST OF POOLS.
|
||||||
* HERE WE SHOWS THE LIST OF POOLS
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $pools
|
||||||
|
* @param int $pageNumber
|
||||||
|
* @param int $totalPages
|
||||||
*/
|
*/
|
||||||
public function list_pools(Page $page, /*array*/ $pools, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
public function list_pools(Page $page, /*array*/ $pools, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
||||||
global $user;
|
global $user;
|
||||||
@ -58,12 +87,6 @@ class PoolsTheme extends Themelet {
|
|||||||
|
|
||||||
$html .= "</tbody></table>";
|
$html .= "</tbody></table>";
|
||||||
|
|
||||||
$nav_html = '
|
|
||||||
<a href="'.make_link().'">Index</a>
|
|
||||||
<br><a href="'.make_link("pool/new").'">Create Pool</a>
|
|
||||||
<br><a href="'.make_link("pool/updated").'">Pool Changes</a>
|
|
||||||
';
|
|
||||||
|
|
||||||
$order_html = '
|
$order_html = '
|
||||||
<select id="order_pool">
|
<select id="order_pool">
|
||||||
<option value="created">Recently created</option>
|
<option value="created">Recently created</option>
|
||||||
@ -73,17 +96,16 @@ class PoolsTheme extends Themelet {
|
|||||||
</select>
|
</select>
|
||||||
';
|
';
|
||||||
|
|
||||||
$blockTitle = "Pools";
|
$this->display_top(null, "Pools");
|
||||||
$page->set_title(html_escape($blockTitle));
|
|
||||||
$page->set_heading(html_escape($blockTitle));
|
|
||||||
$page->add_block(new Block($blockTitle, $html, "main", 10));
|
|
||||||
$page->add_block(new Block("Navigation", $nav_html, "left", 10));
|
|
||||||
$page->add_block(new Block("Order By", $order_html, "left", 15));
|
$page->add_block(new Block("Order By", $order_html, "left", 15));
|
||||||
|
|
||||||
|
$page->add_block(new Block("Pools", $html, "main", 10));
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
$this->display_paginator($page, "pool/list", null, $pageNumber, $totalPages);
|
$this->display_paginator($page, "pool/list", null, $pageNumber, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* HERE WE DISPLAY THE NEW POOL COMPOSER
|
* HERE WE DISPLAY THE NEW POOL COMPOSER
|
||||||
*/
|
*/
|
||||||
@ -99,18 +121,31 @@ class PoolsTheme extends Themelet {
|
|||||||
</form>
|
</form>
|
||||||
";
|
";
|
||||||
|
|
||||||
$blockTitle = "Create Pool";
|
$this->display_top(null, "Create Pool");
|
||||||
$page->set_title(html_escape($blockTitle));
|
|
||||||
$page->set_heading(html_escape($blockTitle));
|
|
||||||
$page->add_block(new Block("Create Pool", $create_html, "main", 20));
|
$page->add_block(new Block("Create Pool", $create_html, "main", 20));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $pools
|
||||||
|
* @param string $heading
|
||||||
|
* @param bool $check_all
|
||||||
|
*/
|
||||||
private function display_top(/*array*/ $pools, /*string*/ $heading, $check_all=false) {
|
private function display_top(/*array*/ $pools, /*string*/ $heading, $check_all=false) {
|
||||||
global $page, $user;
|
global $page, $user;
|
||||||
|
|
||||||
$page->set_title($heading);
|
$page->set_title($heading);
|
||||||
$page->set_heading($heading);
|
$page->set_heading($heading);
|
||||||
|
|
||||||
|
$nav_html = '<a href="'.make_link().'">Index</a>';
|
||||||
|
$poolnav_html = '
|
||||||
|
<a href="'.make_link("pool/list").'">Pool Index</a>
|
||||||
|
<br><a href="'.make_link("pool/new").'">Create Pool</a>
|
||||||
|
<br><a href="'.make_link("pool/updated").'">Pool Changes</a>
|
||||||
|
';
|
||||||
|
|
||||||
|
$page->add_block(new Block($nav_html, null, "left", 5));
|
||||||
|
$page->add_block(new Block("Pool Navigation", $poolnav_html, "left", 10));
|
||||||
|
|
||||||
if(count($pools) == 1) {
|
if(count($pools) == 1) {
|
||||||
$pool = $pools[0];
|
$pool = $pools[0];
|
||||||
if($pool['public'] == "Y" || $user->is_admin()) {// IF THE POOL IS PUBLIC OR IS ADMIN SHOW EDIT PANEL
|
if($pool['public'] == "Y" || $user->is_admin()) {// IF THE POOL IS PUBLIC OR IS ADMIN SHOW EDIT PANEL
|
||||||
@ -122,36 +157,15 @@ class PoolsTheme extends Themelet {
|
|||||||
$bb = new BBCode();
|
$bb = new BBCode();
|
||||||
$page->add_block(new Block(html_escape($pool['title']), $bb->format($pool['description']), "main", 10));
|
$page->add_block(new Block(html_escape($pool['title']), $bb->format($pool['description']), "main", 10));
|
||||||
}
|
}
|
||||||
else {
|
|
||||||
$pool_info = '
|
|
||||||
<table id="poolsList" class="zebra">
|
|
||||||
<thead><tr>
|
|
||||||
<th class="left">Title</th>
|
|
||||||
<th class="left">Description</th>
|
|
||||||
</tr></thead><tbody>';
|
|
||||||
|
|
||||||
foreach($pools as $pool) {
|
|
||||||
$pool_info .= "<tr>".
|
|
||||||
"<td class='left'>".html_escape($pool['title'])."</td>".
|
|
||||||
"<td class='left'>".html_escape($pool['description'])."</td>".
|
|
||||||
"</tr>";
|
|
||||||
|
|
||||||
// this will make disasters if more than one pool comes in the parameter
|
|
||||||
if($pool['public'] == "Y" || $user->is_admin()) {// IF THE POOL IS PUBLIC OR IS ADMIN SHOW EDIT PANEL
|
|
||||||
if(!$user->is_anonymous()) {// IF THE USER IS REGISTERED AND LOGGED IN SHOW EDIT PANEL
|
|
||||||
$this->sidebar_options($page, $pool, $check_all);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$pool_info .= "</tbody></table>";
|
|
||||||
$page->add_block(new Block($heading, $pool_info, "main", 10));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE DISPLAY THE POOL WITH TITLE DESCRIPTION AND IMAGES WITH PAGINATION.
|
||||||
* HERE WE DISPLAY THE POOL WITH TITLE DESCRIPTION AND IMAGES WITH PAGINATION
|
*
|
||||||
|
* @param array $pools
|
||||||
|
* @param array $images
|
||||||
|
* @param int $pageNumber
|
||||||
|
* @param int $totalPages
|
||||||
*/
|
*/
|
||||||
public function view_pool(/*array*/ $pools, /*array*/ $images, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
public function view_pool(/*array*/ $pools, /*array*/ $images, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
||||||
global $user, $page;
|
global $user, $page;
|
||||||
@ -164,20 +178,17 @@ class PoolsTheme extends Themelet {
|
|||||||
$pool_images .= "\n".$thumb_html."\n";
|
$pool_images .= "\n".$thumb_html."\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
$nav_html = '
|
$page->add_block(new Block("Viewing Posts", $pool_images, "main", 30));
|
||||||
<a href="'.make_link().'">Index</a>
|
|
||||||
<br><a href="'.make_link("pool/new").'">Create Pool</a>
|
|
||||||
<br><a href="'.make_link("pool/updated").'">Pool Changes</a>
|
|
||||||
';
|
|
||||||
|
|
||||||
$page->add_block(new Block("Navigation", $nav_html, "left", 10));
|
|
||||||
$page->add_block(new Block("Viewing Posts", $pool_images, "main", 30));
|
|
||||||
$this->display_paginator($page, "pool/view/".$pools[0]['id'], null, $pageNumber, $totalPages);
|
$this->display_paginator($page, "pool/view/".$pools[0]['id'], null, $pageNumber, $totalPages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE DISPLAY THE POOL OPTIONS ON SIDEBAR BUT WE HIDE REMOVE OPTION IF THE USER IS NOT THE OWNER OR ADMIN
|
* HERE WE DISPLAY THE POOL OPTIONS ON SIDEBAR BUT WE HIDE REMOVE OPTION IF THE USER IS NOT THE OWNER OR ADMIN.
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $pool
|
||||||
|
* @param bool $check_all
|
||||||
*/
|
*/
|
||||||
public function sidebar_options(Page $page, $pool, /*bool*/ $check_all) {
|
public function sidebar_options(Page $page, $pool, /*bool*/ $check_all) {
|
||||||
global $user;
|
global $user;
|
||||||
@ -223,12 +234,7 @@ class PoolsTheme extends Themelet {
|
|||||||
<script language='javascript' type='text/javascript'>
|
<script language='javascript' type='text/javascript'>
|
||||||
<!--
|
<!--
|
||||||
function setAll(value) {
|
function setAll(value) {
|
||||||
var a=new Array();
|
$('[name=\"check[]\"]').attr('checked', value);
|
||||||
a=document.getElementsByName('check[]');
|
|
||||||
var p=0;
|
|
||||||
for(i=0;i<a.length;i++){
|
|
||||||
a[i].checked = value;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
//-->
|
//-->
|
||||||
</script>
|
</script>
|
||||||
@ -236,27 +242,23 @@ class PoolsTheme extends Themelet {
|
|||||||
<input type='button' name='UnCheckAll' value='Uncheck All' onClick='setAll(false)'>
|
<input type='button' name='UnCheckAll' value='Uncheck All' onClick='setAll(false)'>
|
||||||
";
|
";
|
||||||
}
|
}
|
||||||
$page->add_block(new Block("Manage Pool", $editor, "left", 10));
|
$page->add_block(new Block("Manage Pool", $editor, "left", 15));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE DISPLAY THE RESULT OF THE SEARCH ON IMPORT
|
* HERE WE DISPLAY THE RESULT OF THE SEARCH ON IMPORT.
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $images
|
||||||
|
* @param array $pool
|
||||||
*/
|
*/
|
||||||
public function pool_result(Page $page, /*array*/ $images, /*int*/ $pool_id) {
|
public function pool_result(Page $page, /*array*/ $images, /*array*/ $pool) {
|
||||||
// TODO: this could / should be done using jQuery
|
|
||||||
|
$this->display_top($pool, "Importing Posts", true);
|
||||||
$pool_images = "
|
$pool_images = "
|
||||||
<script language='javascript' type='text/javascript'>
|
<script language='javascript' type='text/javascript'>
|
||||||
<!--
|
<!--
|
||||||
function setAll(value) {
|
|
||||||
var a=new Array();
|
|
||||||
a=document.getElementsByName('check[]');
|
|
||||||
var p=0;
|
|
||||||
for(i=0;i<a.length;i++) {
|
|
||||||
a[i].checked = value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function confirm_action() {
|
function confirm_action() {
|
||||||
return confirm('Are you sure you want to add selected posts to this pool?');
|
return confirm('Are you sure you want to add selected posts to this pool?');
|
||||||
}
|
}
|
||||||
@ -273,25 +275,23 @@ class PoolsTheme extends Themelet {
|
|||||||
'<input name="check[]" type="checkbox" value="'.$image->id.'" />'.
|
'<input name="check[]" type="checkbox" value="'.$image->id.'" />'.
|
||||||
'</span>';
|
'</span>';
|
||||||
}
|
}
|
||||||
|
|
||||||
$pool_images .= "<br>".
|
$pool_images .= "<br>".
|
||||||
"<input type='submit' name='edit' id='edit_pool_add_btn' value='Add Selected' onclick='return confirm_action()'/>".
|
"<input type='submit' name='edit' id='edit_pool_add_btn' value='Add Selected' onclick='return confirm_action()'/>".
|
||||||
"<input type='hidden' name='pool_id' value='".$pool_id."'>".
|
"<input type='hidden' name='pool_id' value='".$pool[0]['id']."'>".
|
||||||
"</form>";
|
"</form>";
|
||||||
|
|
||||||
$page->add_block(new Block("Import", $pool_images, "main", 10));
|
$page->add_block(new Block("Import", $pool_images, "main", 30));
|
||||||
|
|
||||||
$editor = "
|
|
||||||
<input type='button' name='CheckAll' value='Check All' onClick='setAll(true)'>
|
|
||||||
<input type='button' name='UnCheckAll' value='Uncheck All' onClick='setAll(false)'>
|
|
||||||
";
|
|
||||||
|
|
||||||
$page->add_block(new Block("Manage Pool", $editor, "left", 10));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE DISPLAY THE POOL ORDERER
|
* HERE WE DISPLAY THE POOL ORDERER.
|
||||||
* WE LIST ALL IMAGES ON POOL WITHOUT PAGINATION AND WITH A TEXT INPUT TO SET A NUMBER AND CHANGE THE ORDER
|
* WE LIST ALL IMAGES ON POOL WITHOUT PAGINATION AND WITH A TEXT INPUT TO SET A NUMBER AND CHANGE THE ORDER
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $pools
|
||||||
|
* @param array $images
|
||||||
*/
|
*/
|
||||||
public function edit_order(Page $page, /*array*/ $pools, /*array*/ $images) {
|
public function edit_order(Page $page, /*array*/ $pools, /*array*/ $images) {
|
||||||
global $user;
|
global $user;
|
||||||
@ -318,16 +318,19 @@ class PoolsTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Sorting Posts", $pool_images, "main", 30));
|
$page->add_block(new Block("Sorting Posts", $pool_images, "main", 30));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
/*
|
* HERE WE DISPLAY THE POOL EDITOR.
|
||||||
* HERE WE DISPLAY THE POOL EDITOR
|
*
|
||||||
* WE LIST ALL IMAGES ON POOL WITHOUT PAGINATION AND WITH
|
* WE LIST ALL IMAGES ON POOL WITHOUT PAGINATION AND WITH
|
||||||
* A CHECKBOX TO SELECT WHICH IMAGE WE WANT TO REMOVE
|
* A CHECKBOX TO SELECT WHICH IMAGE WE WANT TO REMOVE
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $pools
|
||||||
|
* @param array $images
|
||||||
*/
|
*/
|
||||||
public function edit_pool(Page $page, /*array*/ $pools, /*array*/ $images) {
|
public function edit_pool(Page $page, /*array*/ $pools, /*array*/ $images) {
|
||||||
global $user;
|
global $user;
|
||||||
|
|
||||||
|
|
||||||
/* EDIT POOL DESCRIPTION */
|
/* EDIT POOL DESCRIPTION */
|
||||||
$desc_html = "
|
$desc_html = "
|
||||||
".make_form(make_link("pool/edit_description"))."
|
".make_form(make_link("pool/edit_description"))."
|
||||||
@ -362,8 +365,12 @@ class PoolsTheme extends Themelet {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* HERE WE DISPLAY THE HISTORY LIST
|
* HERE WE DISPLAY THE HISTORY LIST.
|
||||||
|
*
|
||||||
|
* @param array $histories
|
||||||
|
* @param int $pageNumber
|
||||||
|
* @param int $totalPages
|
||||||
*/
|
*/
|
||||||
public function show_history($histories, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
public function show_history($histories, /*int*/ $pageNumber, /*int*/ $totalPages) {
|
||||||
global $page;
|
global $page;
|
||||||
@ -393,7 +400,7 @@ class PoolsTheme extends Themelet {
|
|||||||
$images = explode(" ", $images);
|
$images = explode(" ", $images);
|
||||||
|
|
||||||
$image_link = "";
|
$image_link = "";
|
||||||
foreach ($images as $image) {
|
foreach ($images as $image) {
|
||||||
$image_link .= "<a href='".make_link("post/view/".$image)."'>".$prefix.$image." </a>";
|
$image_link .= "<a href='".make_link("post/view/".$image)."'>".$prefix.$image." </a>";
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -409,15 +416,7 @@ class PoolsTheme extends Themelet {
|
|||||||
|
|
||||||
$html .= "</tbody></table>";
|
$html .= "</tbody></table>";
|
||||||
|
|
||||||
$nav_html = '
|
$this->display_top(null, "Recent Changes");
|
||||||
<a href="'.make_link().'">Index</a>
|
|
||||||
<br><a href="'.make_link("pool/new").'">Create Pool</a>
|
|
||||||
<br><a href="'.make_link("pool/updated").'">Pool Changes</a>
|
|
||||||
';
|
|
||||||
|
|
||||||
$page->set_title("Recent Changes");
|
|
||||||
$page->set_heading("Recent Changes");
|
|
||||||
$page->add_block(new Block("Navigation", $nav_html, "left", 10));
|
|
||||||
$page->add_block(new Block("Recent Changes", $html, "main", 10));
|
$page->add_block(new Block("Recent Changes", $html, "main", 10));
|
||||||
|
|
||||||
$this->display_paginator($page, "pool/updated", null, $pageNumber, $totalPages);
|
$this->display_paginator($page, "pool/updated", null, $pageNumber, $totalPages);
|
||||||
|
@ -1,9 +1,12 @@
|
|||||||
<?php
|
<?php
|
||||||
class QRImageTheme extends Themelet {
|
class QRImageTheme extends Themelet {
|
||||||
|
/**
|
||||||
|
* @param string $link
|
||||||
|
*/
|
||||||
public function links_block($link) {
|
public function links_block($link) {
|
||||||
global $page;
|
global $page;
|
||||||
$page->add_block( new Block(
|
$page->add_block( new Block(
|
||||||
"QR Code","<img alt='QR Code' src='http://chart.apis.google.com/chart?chs=150x150&cht=qr&chl=$link' />","left",50));
|
"QR Code","<img alt='QR Code' src='http://chart.apis.google.com/chart?chs=150x150&cht=qr&chl={$link}' />","left",50));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -22,7 +22,8 @@
|
|||||||
|
|
||||||
class RandomImage extends Extension {
|
class RandomImage extends Extension {
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $config, $database, $page, $user;
|
global $page;
|
||||||
|
|
||||||
if($event->page_matches("random_image")) {
|
if($event->page_matches("random_image")) {
|
||||||
$action = '';
|
$action = '';
|
||||||
if($event->count_args() == 1) {
|
if($event->count_args() == 1) {
|
||||||
@ -34,7 +35,7 @@ class RandomImage extends Extension {
|
|||||||
$search_terms = explode(' ', $event->get_arg(1));
|
$search_terms = explode(' ', $event->get_arg(1));
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
# FIXME: throw exception
|
throw new SCoreException("Error: too many arguments.");
|
||||||
}
|
}
|
||||||
$image = Image::by_random($search_terms);
|
$image = Image::by_random($search_terms);
|
||||||
|
|
||||||
|
@ -1,12 +1,24 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class RandomImageTheme extends Themelet {
|
class RandomImageTheme extends Themelet
|
||||||
public function display_random(Page $page, Image $image) {
|
{
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
|
*/
|
||||||
|
public function display_random(Page $page, Image $image)
|
||||||
|
{
|
||||||
$page->add_block(new Block("Random Image", $this->build_random_html($image), "left", 8));
|
$page->add_block(new Block("Random Image", $this->build_random_html($image), "left", 8));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function build_random_html(Image $image, $query=null) {
|
/**
|
||||||
global $config;
|
* @param Image $image
|
||||||
|
* @param null|string $query
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function build_random_html(Image $image, $query = null)
|
||||||
|
{
|
||||||
|
|
||||||
$i_id = int_escape($image->id);
|
$i_id = int_escape($image->id);
|
||||||
$h_view_link = make_link("post/view/$i_id", $query);
|
$h_view_link = make_link("post/view/$i_id", $query);
|
||||||
$h_thumb_link = $image->get_thumb_link();
|
$h_thumb_link = $image->get_thumb_link();
|
||||||
@ -14,14 +26,14 @@ class RandomImageTheme extends Themelet {
|
|||||||
$tsize = get_thumbnail_size($image->width, $image->height);
|
$tsize = get_thumbnail_size($image->width, $image->height);
|
||||||
|
|
||||||
return "
|
return "
|
||||||
<center><div>
|
<center><div>
|
||||||
|
|
||||||
<a href='$h_view_link' style='position: relative; height: {$tsize[1]}px; width: {$tsize[0]}px;'>
|
<a href='$h_view_link' style='position: relative; height: {$tsize[1]}px; width: {$tsize[0]}px;'>
|
||||||
<img id='thumb_rand_$i_id' title='$h_tip' alt='$h_tip' class='highlighted' style='height: {$tsize[1]}px; width: {$tsize[0]}px;' src='$h_thumb_link'>
|
<img id='thumb_rand_$i_id' title='$h_tip' alt='$h_tip' class='highlighted' style='height: {$tsize[1]}px; width: {$tsize[0]}px;' src='$h_thumb_link'>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
</div></center>
|
</div></center>
|
||||||
";
|
";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
/* needed for access to build_thumb_html */
|
/* needed for access to build_thumb_html */
|
||||||
class RandomListTheme extends Themelet {}
|
class RandomListTheme extends Themelet {}
|
||||||
?>
|
|
||||||
|
@ -20,10 +20,18 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class RatingSetEvent extends Event {
|
class RatingSetEvent extends Event {
|
||||||
var $image, $rating;
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
|
/** @var string */
|
||||||
|
public $rating;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param string $rating
|
||||||
|
*/
|
||||||
public function __construct(Image $image, /*char*/ $rating) {
|
public function __construct(Image $image, /*char*/ $rating) {
|
||||||
assert(in_array($rating, array("s", "q", "e", "u")));
|
assert(in_array($rating, array("s", "q", "e", "u")));
|
||||||
|
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
$this->rating = $rating;
|
$this->rating = $rating;
|
||||||
}
|
}
|
||||||
@ -31,6 +39,9 @@ class RatingSetEvent extends Event {
|
|||||||
|
|
||||||
class Ratings extends Extension {
|
class Ratings extends Extension {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_priority() {return 50;}
|
public function get_priority() {return 50;}
|
||||||
|
|
||||||
public function onInitExt(InitExtEvent $event) {
|
public function onInitExt(InitExtEvent $event) {
|
||||||
@ -69,7 +80,7 @@ class Ratings extends Extension {
|
|||||||
|
|
||||||
|
|
||||||
public function onDisplayingImage(DisplayingImageEvent $event) {
|
public function onDisplayingImage(DisplayingImageEvent $event) {
|
||||||
global $user, $database, $page;
|
global $user, $page;
|
||||||
/**
|
/**
|
||||||
* Deny images upon insufficient permissions.
|
* Deny images upon insufficient permissions.
|
||||||
**/
|
**/
|
||||||
@ -97,15 +108,13 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
||||||
global $user;
|
|
||||||
|
|
||||||
if($this->can_rate() && isset($_POST["rating"])) {
|
if($this->can_rate() && isset($_POST["rating"])) {
|
||||||
send_event(new RatingSetEvent($event->image, $_POST['rating']));
|
send_event(new RatingSetEvent($event->image, $_POST['rating']));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onParseLinkTemplate(ParseLinkTemplateEvent $event) {
|
public function onParseLinkTemplate(ParseLinkTemplateEvent $event) {
|
||||||
$event->replace('$rating', $this->theme->rating_to_name($event->image->rating));
|
$event->replace('$rating', $this->rating_to_human($event->image->rating));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onSearchTermParse(SearchTermParseEvent $event) {
|
public function onSearchTermParse(SearchTermParseEvent $event) {
|
||||||
@ -125,11 +134,11 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $database, $user, $page;
|
global $user, $page;
|
||||||
|
|
||||||
if ($event->page_matches("admin/bulk_rate")) {
|
if ($event->page_matches("admin/bulk_rate")) {
|
||||||
if(!$user->is_admin()) {
|
if(!$user->is_admin()) {
|
||||||
throw PermissionDeniedException();
|
throw new PermissionDeniedException();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
$n = 0;
|
$n = 0;
|
||||||
@ -154,9 +163,14 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static function get_user_privs($user) {
|
/**
|
||||||
|
* @param \User $user
|
||||||
|
* @return null|string
|
||||||
|
*/
|
||||||
|
public static function get_user_privs(User $user) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
if($user->is_anonymous()) {
|
if($user->is_anonymous()) {
|
||||||
$sqes = $config->get_string("ext_rating_anon_privs");
|
$sqes = $config->get_string("ext_rating_anon_privs");
|
||||||
}
|
}
|
||||||
@ -169,6 +183,10 @@ class Ratings extends Extension {
|
|||||||
return $sqes;
|
return $sqes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $sqes
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public static function privs_to_sql(/*string*/ $sqes) {
|
public static function privs_to_sql(/*string*/ $sqes) {
|
||||||
$arr = array();
|
$arr = array();
|
||||||
$length = strlen($sqes);
|
$length = strlen($sqes);
|
||||||
@ -179,6 +197,10 @@ class Ratings extends Extension {
|
|||||||
return $set;
|
return $set;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $rating
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public static function rating_to_human(/*string*/ $rating) {
|
public static function rating_to_human(/*string*/ $rating) {
|
||||||
switch($rating) {
|
switch($rating) {
|
||||||
case "s": return "Safe";
|
case "s": return "Safe";
|
||||||
@ -188,7 +210,11 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME: this is a bit ugly and guessey, should have proper options
|
/**
|
||||||
|
* FIXME: this is a bit ugly and guessey, should have proper options
|
||||||
|
*
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function can_rate() {
|
private function can_rate() {
|
||||||
global $config, $user;
|
global $config, $user;
|
||||||
if($user->is_anonymous() && $config->get_string("ext_rating_anon_privs") == "sqeu") return false;
|
if($user->is_anonymous() && $config->get_string("ext_rating_anon_privs") == "sqeu") return false;
|
||||||
@ -197,6 +223,10 @@ class Ratings extends Extension {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param $context
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function no_rating_query($context) {
|
private function no_rating_query($context) {
|
||||||
foreach($context as $term) {
|
foreach($context as $term) {
|
||||||
if(preg_match("/^rating[=|:]/", $term)) {
|
if(preg_match("/^rating[=|:]/", $term)) {
|
||||||
@ -207,8 +237,7 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private function install() {
|
private function install() {
|
||||||
global $database;
|
global $database, $config;
|
||||||
global $config;
|
|
||||||
|
|
||||||
if($config->get_int("ext_ratings2_version") < 1) {
|
if($config->get_int("ext_ratings2_version") < 1) {
|
||||||
$database->Execute("ALTER TABLE images ADD COLUMN rating CHAR(1) NOT NULL DEFAULT 'u'");
|
$database->Execute("ALTER TABLE images ADD COLUMN rating CHAR(1) NOT NULL DEFAULT 'u'");
|
||||||
@ -227,11 +256,16 @@ class Ratings extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param string $rating
|
||||||
|
* @param string $old_rating
|
||||||
|
*/
|
||||||
private function set_rating(/*int*/ $image_id, /*string*/ $rating, /*string*/ $old_rating) {
|
private function set_rating(/*int*/ $image_id, /*string*/ $rating, /*string*/ $old_rating) {
|
||||||
global $database;
|
global $database;
|
||||||
if($old_rating != $rating){
|
if($old_rating != $rating){
|
||||||
$database->Execute("UPDATE images SET rating=? WHERE id=?", array($rating, $image_id));
|
$database->Execute("UPDATE images SET rating=? WHERE id=?", array($rating, $image_id));
|
||||||
log_info("rating", "Rating for Image #{$image_id} set to: ".$this->theme->rating_to_name($rating));
|
log_info("rating", "Rating for Image #{$image_id} set to: ".$this->rating_to_human($rating));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,11 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class RatingsTheme extends Themelet {
|
class RatingsTheme extends Themelet {
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param string $rating
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
public function get_rater_html(/*int*/ $image_id, /*string*/ $rating) {
|
public function get_rater_html(/*int*/ $image_id, /*string*/ $rating) {
|
||||||
$s_checked = $rating == 's' ? " checked" : "";
|
$s_checked = $rating == 's' ? " checked" : "";
|
||||||
$q_checked = $rating == 'q' ? " checked" : "";
|
$q_checked = $rating == 'q' ? " checked" : "";
|
||||||
@ -34,15 +39,6 @@ class RatingsTheme extends Themelet {
|
|||||||
";
|
";
|
||||||
$page->add_block(new Block("List Controls", $html, "left"));
|
$page->add_block(new Block("List Controls", $html, "left"));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function rating_to_name(/*string*/ $rating) {
|
|
||||||
switch($rating) {
|
|
||||||
case 's': return "Safe";
|
|
||||||
case 'q': return "Questionable";
|
|
||||||
case 'e': return "Explicit";
|
|
||||||
default: return "Unknown";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
|
|
||||||
class RegenThumb extends Extension {
|
class RegenThumb extends Extension {
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $config, $database, $page, $user;
|
global $page, $user;
|
||||||
|
|
||||||
if($event->page_matches("regen_thumb") && $user->can("delete_image") && isset($_POST['image_id'])) {
|
if($event->page_matches("regen_thumb") && $user->can("delete_image") && isset($_POST['image_id'])) {
|
||||||
$image = Image::by_id(int_escape($_POST['image_id']));
|
$image = Image::by_id(int_escape($_POST['image_id']));
|
||||||
|
@ -1,8 +1,11 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class RegenThumbTheme extends Themelet {
|
class RegenThumbTheme extends Themelet {
|
||||||
/*
|
/**
|
||||||
* Show a form which offers to regenerate the thumb of an image with ID #$image_id
|
* Show a form which offers to regenerate the thumb of an image with ID #$image_id
|
||||||
|
*
|
||||||
|
* @param int|string $image_id
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function get_buttons_html($image_id) {
|
public function get_buttons_html($image_id) {
|
||||||
return "
|
return "
|
||||||
@ -13,8 +16,11 @@ class RegenThumbTheme extends Themelet {
|
|||||||
";
|
";
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Show a link to the new thumbnail
|
* Show a link to the new thumbnail.
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
*/
|
*/
|
||||||
public function display_results(Page $page, Image $image) {
|
public function display_results(Page $page, Image $image) {
|
||||||
$page->set_title("Thumbnail Regenerated");
|
$page->set_title("Thumbnail Regenerated");
|
||||||
|
@ -21,7 +21,6 @@ class Relationships extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
||||||
global $user;
|
|
||||||
if(isset($_POST['tag_edit__tags']) ? !preg_match('/parent[=|:]/', $_POST["tag_edit__tags"]) : TRUE) { //Ignore tag_edit__parent if tags contain parent metatag
|
if(isset($_POST['tag_edit__tags']) ? !preg_match('/parent[=|:]/', $_POST["tag_edit__tags"]) : TRUE) { //Ignore tag_edit__parent if tags contain parent metatag
|
||||||
if (isset($_POST["tag_edit__parent"]) ? ctype_digit($_POST["tag_edit__parent"]) : FALSE) {
|
if (isset($_POST["tag_edit__parent"]) ? ctype_digit($_POST["tag_edit__parent"]) : FALSE) {
|
||||||
$this->set_parent($event->image->id, (int) $_POST["tag_edit__parent"]);
|
$this->set_parent($event->image->id, (int) $_POST["tag_edit__parent"]);
|
||||||
@ -91,6 +90,10 @@ class Relationships extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $imageID
|
||||||
|
* @param int $parentID
|
||||||
|
*/
|
||||||
private function set_parent(/*int*/ $imageID, /*int*/ $parentID){
|
private function set_parent(/*int*/ $imageID, /*int*/ $parentID){
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
@ -100,6 +103,10 @@ class Relationships extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $parentID
|
||||||
|
* @param int $childID
|
||||||
|
*/
|
||||||
private function set_child(/*int*/ $parentID, /*int*/ $childID){
|
private function set_child(/*int*/ $parentID, /*int*/ $childID){
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
@ -109,6 +116,9 @@ class Relationships extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $imageID
|
||||||
|
*/
|
||||||
private function remove_parent(/*int*/ $imageID){
|
private function remove_parent(/*int*/ $imageID){
|
||||||
global $database;
|
global $database;
|
||||||
$parentID = $database->get_one("SELECT parent_id FROM images WHERE id = :iid", array("iid"=>$imageID));
|
$parentID = $database->get_one("SELECT parent_id FROM images WHERE id = :iid", array("iid"=>$imageID));
|
||||||
|
@ -1,6 +1,9 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class RelationshipsTheme extends Themelet {
|
class RelationshipsTheme extends Themelet {
|
||||||
|
/**
|
||||||
|
* @param \Image $image
|
||||||
|
*/
|
||||||
public function relationship_info($image) {
|
public function relationship_info($image) {
|
||||||
global $page, $database;
|
global $page, $database;
|
||||||
|
|
||||||
@ -25,6 +28,7 @@ class RelationshipsTheme extends Themelet {
|
|||||||
|
|
||||||
public function get_parent_editor_html(Image $image) {
|
public function get_parent_editor_html(Image $image) {
|
||||||
global $user;
|
global $user;
|
||||||
|
|
||||||
$h_parent_id = $image->parent_id;
|
$h_parent_id = $image->parent_id;
|
||||||
$s_parent_id = $h_parent_id ?: "None.";
|
$s_parent_id = $h_parent_id ?: "None.";
|
||||||
|
|
||||||
|
@ -10,18 +10,30 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class RemoveReportedImageEvent extends Event {
|
class RemoveReportedImageEvent extends Event {
|
||||||
var $id;
|
/** @var int */
|
||||||
|
public $id;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $id
|
||||||
|
*/
|
||||||
public function __construct($id) {
|
public function __construct($id) {
|
||||||
$this->id = $id;
|
$this->id = $id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class AddReportedImageEvent extends Event {
|
class AddReportedImageEvent extends Event {
|
||||||
var $reporter_id;
|
/** @var int */
|
||||||
var $image_id;
|
public $reporter_id;
|
||||||
var $reason;
|
/** @var int */
|
||||||
|
public $image_id;
|
||||||
|
/** @var string */
|
||||||
|
public $reason;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @param int $reporter_id
|
||||||
|
* @param string $reason
|
||||||
|
*/
|
||||||
public function __construct($image_id, $reporter_id, $reason) {
|
public function __construct($image_id, $reporter_id, $reason) {
|
||||||
$this->reporter_id = $reporter_id;
|
$this->reporter_id = $reporter_id;
|
||||||
$this->image_id = $image_id;
|
$this->image_id = $image_id;
|
||||||
@ -89,7 +101,7 @@ class ReportImage extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onDisplayingImage(DisplayingImageEvent $event) {
|
public function onDisplayingImage(DisplayingImageEvent $event) {
|
||||||
global $config, $user, $page;
|
global $user, $page;
|
||||||
if($user->can('create_image_report')) {
|
if($user->can('create_image_report')) {
|
||||||
$reps = $this->get_reporters($event->image);
|
$reps = $this->get_reporters($event->image);
|
||||||
$this->theme->display_image_banner($event->image, $reps);
|
$this->theme->display_image_banner($event->image, $reps);
|
||||||
@ -112,8 +124,8 @@ class ReportImage extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected function install() {
|
protected function install() {
|
||||||
global $database;
|
global $database, $config;
|
||||||
global $config;
|
|
||||||
if($config->get_int("ext_report_image_version") < 1) {
|
if($config->get_int("ext_report_image_version") < 1) {
|
||||||
$database->create_table("image_reports", "
|
$database->create_table("image_reports", "
|
||||||
id SCORE_AIPK,
|
id SCORE_AIPK,
|
||||||
@ -127,8 +139,13 @@ class ReportImage extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_reporters(Image $image) {
|
public function get_reporters(Image $image) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
return $database->get_col("
|
return $database->get_col("
|
||||||
SELECT users.name
|
SELECT users.name
|
||||||
FROM image_reports
|
FROM image_reports
|
||||||
@ -137,8 +154,12 @@ class ReportImage extends Extension {
|
|||||||
", array("image_id" => $image->id));
|
", array("image_id" => $image->id));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_reported_images() {
|
public function get_reported_images() {
|
||||||
global $config, $database;
|
global $database;
|
||||||
|
|
||||||
$all_reports = $database->get_all("
|
$all_reports = $database->get_all("
|
||||||
SELECT image_reports.*, users.name AS reporter_name
|
SELECT image_reports.*, users.name AS reporter_name
|
||||||
FROM image_reports
|
FROM image_reports
|
||||||
@ -160,6 +181,9 @@ class ReportImage extends Extension {
|
|||||||
return $reports;
|
return $reports;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return mixed
|
||||||
|
*/
|
||||||
public function count_reported_images() {
|
public function count_reported_images() {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
|
@ -11,6 +11,10 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
class ReportImageTheme extends Themelet {
|
class ReportImageTheme extends Themelet {
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $reports
|
||||||
|
*/
|
||||||
public function display_reported_images(Page $page, $reports) {
|
public function display_reported_images(Page $page, $reports) {
|
||||||
global $config;
|
global $config;
|
||||||
|
|
||||||
@ -57,11 +61,14 @@ class ReportImageTheme extends Themelet {
|
|||||||
$page->set_heading("Reported Images");
|
$page->set_heading("Reported Images");
|
||||||
$page->add_block(new NavBlock());
|
$page->add_block(new NavBlock());
|
||||||
$page->add_block(new Block("Reported Images", $html));
|
$page->add_block(new Block("Reported Images", $html));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param array $reporters
|
||||||
|
*/
|
||||||
public function display_image_banner(Image $image, /*array*/ $reporters) {
|
public function display_image_banner(Image $image, /*array*/ $reporters) {
|
||||||
global $config, $page;
|
global $page;
|
||||||
|
|
||||||
$i_image = int_escape($image->id);
|
$i_image = int_escape($image->id);
|
||||||
$html = "";
|
$html = "";
|
||||||
|
@ -33,7 +33,7 @@ class ResizeImage extends Extension {
|
|||||||
$config->set_default_bool('resize_enabled', true);
|
$config->set_default_bool('resize_enabled', true);
|
||||||
$config->set_default_bool('resize_upload', false);
|
$config->set_default_bool('resize_upload', false);
|
||||||
$config->set_default_int('resize_default_width', 0);
|
$config->set_default_int('resize_default_width', 0);
|
||||||
$config->set_default_int('resize_default_height', 0);
|
$config->set_default_int('resize_default_height', 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
public function onImageAdminBlockBuilding(ImageAdminBlockBuildingEvent $event) {
|
||||||
@ -153,11 +153,16 @@ class ResizeImage extends Extension {
|
|||||||
|
|
||||||
// Private functions
|
// Private functions
|
||||||
/* ----------------------------- */
|
/* ----------------------------- */
|
||||||
|
|
||||||
/*
|
/**
|
||||||
This function could be made much smaller by using the ImageReplaceEvent
|
* This function could be made much smaller by using the ImageReplaceEvent
|
||||||
ie: Pretend that we are replacing the image with a resized copy.
|
* ie: Pretend that we are replacing the image with a resized copy.
|
||||||
*/
|
*
|
||||||
|
* @param Image $image_obj
|
||||||
|
* @param int $width
|
||||||
|
* @param int $height
|
||||||
|
* @throws ImageResizeException
|
||||||
|
*/
|
||||||
private function resize_image(Image $image_obj, /*int*/ $width, /*int*/ $height) {
|
private function resize_image(Image $image_obj, /*int*/ $width, /*int*/ $height) {
|
||||||
global $config, $user, $page, $database;
|
global $config, $user, $page, $database;
|
||||||
|
|
||||||
|
@ -16,8 +16,12 @@
|
|||||||
* This class is just a wrapper around SCoreException.
|
* This class is just a wrapper around SCoreException.
|
||||||
*/
|
*/
|
||||||
class ImageRotateException extends SCoreException {
|
class ImageRotateException extends SCoreException {
|
||||||
var $error;
|
/** @var string */
|
||||||
|
public $error;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $error
|
||||||
|
*/
|
||||||
public function __construct($error) {
|
public function __construct($error) {
|
||||||
$this->error = $error;
|
$this->error = $error;
|
||||||
}
|
}
|
||||||
@ -100,11 +104,15 @@ class RotateImage extends Extension {
|
|||||||
|
|
||||||
// Private functions
|
// Private functions
|
||||||
/* ----------------------------- */
|
/* ----------------------------- */
|
||||||
|
|
||||||
/*
|
/**
|
||||||
This function could be made much smaller by using the ImageReplaceEvent
|
* This function could be made much smaller by using the ImageReplaceEvent
|
||||||
ie: Pretend that we are replacing the image with a rotated copy.
|
* ie: Pretend that we are replacing the image with a rotated copy.
|
||||||
*/
|
*
|
||||||
|
* @param int $image_id
|
||||||
|
* @param int $deg
|
||||||
|
* @throws ImageRotateException
|
||||||
|
*/
|
||||||
private function rotate_image(/*int*/ $image_id, /*int*/ $deg) {
|
private function rotate_image(/*int*/ $image_id, /*int*/ $deg) {
|
||||||
global $config, $user, $page, $database;
|
global $config, $user, $page, $database;
|
||||||
|
|
||||||
|
@ -1,12 +1,13 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class RotateImageTheme extends Themelet {
|
class RotateImageTheme extends Themelet {
|
||||||
/*
|
/**
|
||||||
* Display a link to rotate an image
|
* Display a link to rotate an image.
|
||||||
|
*
|
||||||
|
* @param int $image_id
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function get_rotate_html(/*int*/ $image_id) {
|
public function get_rotate_html(/*int*/ $image_id) {
|
||||||
global $user, $config;
|
|
||||||
|
|
||||||
$html = "
|
$html = "
|
||||||
".make_form(make_link('rotate/'.$image_id), 'POST')."
|
".make_form(make_link('rotate/'.$image_id), 'POST')."
|
||||||
<input type='hidden' name='image_id' value='$image_id'>
|
<input type='hidden' name='image_id' value='$image_id'>
|
||||||
@ -17,7 +18,14 @@ class RotateImageTheme extends Themelet {
|
|||||||
|
|
||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Display the error.
|
||||||
|
*
|
||||||
|
* @param Page $page
|
||||||
|
* @param string $title
|
||||||
|
* @param string $message
|
||||||
|
*/
|
||||||
public function display_rotate_error(Page $page, /*string*/ $title, /*string*/ $message) {
|
public function display_rotate_error(Page $page, /*string*/ $title, /*string*/ $message) {
|
||||||
$page->set_title("Rotate Image");
|
$page->set_title("Rotate Image");
|
||||||
$page->set_heading("Rotate Image");
|
$page->set_heading("Rotate Image");
|
||||||
|
@ -33,6 +33,11 @@ class RSS_Images extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $images
|
||||||
|
* @param array $search_terms
|
||||||
|
* @param int $page_number
|
||||||
|
*/
|
||||||
private function do_rss($images, $search_terms, /*int*/ $page_number) {
|
private function do_rss($images, $search_terms, /*int*/ $page_number) {
|
||||||
global $page;
|
global $page;
|
||||||
global $config;
|
global $config;
|
||||||
@ -78,6 +83,10 @@ class RSS_Images extends Extension {
|
|||||||
$page->set_data($xml);
|
$page->set_data($xml);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function thumb(Image $image) {
|
private function thumb(Image $image) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
|
@ -12,8 +12,12 @@
|
|||||||
* activated; new config options are in $_POST
|
* activated; new config options are in $_POST
|
||||||
*/
|
*/
|
||||||
class ConfigSaveEvent extends Event {
|
class ConfigSaveEvent extends Event {
|
||||||
var $config;
|
/** @var \Config */
|
||||||
|
public $config;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Config $config
|
||||||
|
*/
|
||||||
public function __construct(Config $config) {
|
public function __construct(Config $config) {
|
||||||
$this->config = $config;
|
$this->config = $config;
|
||||||
}
|
}
|
||||||
@ -24,8 +28,12 @@ class ConfigSaveEvent extends Event {
|
|||||||
* Sent when the setup page is ready to be added to
|
* Sent when the setup page is ready to be added to
|
||||||
*/
|
*/
|
||||||
class SetupBuildingEvent extends Event {
|
class SetupBuildingEvent extends Event {
|
||||||
var $panel;
|
/** @var \SetupPanel */
|
||||||
|
public $panel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param SetupPanel $panel
|
||||||
|
*/
|
||||||
public function __construct(SetupPanel $panel) {
|
public function __construct(SetupPanel $panel) {
|
||||||
$this->panel = $panel;
|
$this->panel = $panel;
|
||||||
}
|
}
|
||||||
@ -35,8 +43,12 @@ class SetupBuildingEvent extends Event {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class SetupPanel {
|
class SetupPanel {
|
||||||
var $blocks = array();
|
/** @var \SetupBlock[] */
|
||||||
|
public $blocks = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param SetupBlock $block
|
||||||
|
*/
|
||||||
public function add_block(SetupBlock $block) {
|
public function add_block(SetupBlock $block) {
|
||||||
$this->blocks[] = $block;
|
$this->blocks[] = $block;
|
||||||
}
|
}
|
||||||
@ -46,9 +58,14 @@ class SetupPanel {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class SetupBlock extends Block {
|
class SetupBlock extends Block {
|
||||||
var $header;
|
/** @var string */
|
||||||
var $body;
|
public $header;
|
||||||
|
/** @var string */
|
||||||
|
public $body;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $title
|
||||||
|
*/
|
||||||
public function __construct($title) {
|
public function __construct($title) {
|
||||||
$this->header = $title;
|
$this->header = $title;
|
||||||
$this->section = "main";
|
$this->section = "main";
|
||||||
@ -56,20 +73,31 @@ class SetupBlock extends Block {
|
|||||||
$this->body = "";
|
$this->body = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
*/
|
||||||
public function add_label($text) {
|
public function add_label($text) {
|
||||||
$this->body .= $text;
|
$this->body .= $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $label
|
||||||
|
*/
|
||||||
public function add_text_option($name, $label=null) {
|
public function add_text_option($name, $label=null) {
|
||||||
global $config;
|
global $config;
|
||||||
$val = html_escape($config->get_string($name));
|
$val = html_escape($config->get_string($name));
|
||||||
if(!is_null($label)) {
|
if(!is_null($label)) {
|
||||||
$this->body .= "<label for='$name'>$label</label>";
|
$this->body .= "<label for='{$name}'>{$label}</label>";
|
||||||
}
|
}
|
||||||
$this->body .= "<input type='text' id='$name' name='_config_$name' value='$val'>\n";
|
$this->body .= "<input type='text' id='{$name}' name='_config_{$name}' value='{$val}'>\n";
|
||||||
$this->body .= "<input type='hidden' name='_type_$name' value='string'>\n";
|
$this->body .= "<input type='hidden' name='_type_{$name}' value='string'>\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $label
|
||||||
|
*/
|
||||||
public function add_longtext_option($name, $label=null) {
|
public function add_longtext_option($name, $label=null) {
|
||||||
global $config;
|
global $config;
|
||||||
$val = html_escape($config->get_string($name));
|
$val = html_escape($config->get_string($name));
|
||||||
@ -81,6 +109,10 @@ class SetupBlock extends Block {
|
|||||||
$this->body .= "<input type='hidden' name='_type_$name' value='string'>\n";
|
$this->body .= "<input type='hidden' name='_type_$name' value='string'>\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $label
|
||||||
|
*/
|
||||||
public function add_bool_option($name, $label=null) {
|
public function add_bool_option($name, $label=null) {
|
||||||
global $config;
|
global $config;
|
||||||
$checked = $config->get_bool($name) ? " checked" : "";
|
$checked = $config->get_bool($name) ? " checked" : "";
|
||||||
@ -97,6 +129,10 @@ class SetupBlock extends Block {
|
|||||||
// $this->body .= "<input type='hidden' id='$name' name='$name' value='$val'>";
|
// $this->body .= "<input type='hidden' id='$name' name='$name' value='$val'>";
|
||||||
// }
|
// }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $label
|
||||||
|
*/
|
||||||
public function add_int_option($name, $label=null) {
|
public function add_int_option($name, $label=null) {
|
||||||
global $config;
|
global $config;
|
||||||
$val = html_escape($config->get_string($name));
|
$val = html_escape($config->get_string($name));
|
||||||
@ -107,6 +143,10 @@ class SetupBlock extends Block {
|
|||||||
$this->body .= "<input type='hidden' name='_type_$name' value='int'>\n";
|
$this->body .= "<input type='hidden' name='_type_$name' value='int'>\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $name
|
||||||
|
* @param null|string $label
|
||||||
|
*/
|
||||||
public function add_shorthand_int_option($name, $label=null) {
|
public function add_shorthand_int_option($name, $label=null) {
|
||||||
global $config;
|
global $config;
|
||||||
$val = to_shorthand_int($config->get_string($name));
|
$val = to_shorthand_int($config->get_string($name));
|
||||||
|
@ -42,7 +42,7 @@ class _SafeImage {
|
|||||||
$this->posted = $img->posted_timestamp;
|
$this->posted = $img->posted_timestamp;
|
||||||
$this->source = $img->source;
|
$this->source = $img->source;
|
||||||
$this->owner_id = $img->owner_id;
|
$this->owner_id = $img->owner_id;
|
||||||
$this->tags = $img->tag_array;
|
$this->tags = $img->get_tag_array();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -19,7 +19,7 @@
|
|||||||
* For Shimmie2 specific extensions, there is a ShimmieWebTestCase class which
|
* For Shimmie2 specific extensions, there is a ShimmieWebTestCase class which
|
||||||
* includes functions to upload and delete images.
|
* includes functions to upload and delete images.
|
||||||
*
|
*
|
||||||
* For a quick guide on the spcifics of how to write tests, see \ref wut
|
* For a quick guide on the specifics of how to write tests, see \ref wut
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* \page wut Writing Unit Tests
|
* \page wut Writing Unit Tests
|
||||||
@ -88,19 +88,24 @@ define('ADMIN_NAME', "demo");
|
|||||||
define('ADMIN_PASS', "demo");
|
define('ADMIN_PASS', "demo");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A set of common SCore activities to test
|
* Class SCoreWebTestCase
|
||||||
|
*
|
||||||
|
* A set of common SCore activities to test.
|
||||||
*/
|
*/
|
||||||
class SCoreWebTestCase extends WebTestCase {
|
class SCoreWebTestCase extends WebTestCase {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Click on a link or a button
|
* Click on a link or a button.
|
||||||
|
* @param string $text
|
||||||
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function click($text) {
|
public function click($text) {
|
||||||
return parent::click($text);
|
return parent::click($text);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Click the virtual browser's back button
|
* Click the virtual browser's back button.
|
||||||
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function back() {
|
public function back() {
|
||||||
return parent::back();
|
return parent::back();
|
||||||
@ -165,9 +170,16 @@ class SCoreWebTestCase extends WebTestCase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A set of common Shimmie activities to test
|
* Class ShimmieWebTestCase
|
||||||
|
*
|
||||||
|
* A set of common Shimmie activities to test.
|
||||||
*/
|
*/
|
||||||
class ShimmieWebTestCase extends SCoreWebTestCase {
|
class ShimmieWebTestCase extends SCoreWebTestCase {
|
||||||
|
/**
|
||||||
|
* @param string $filename
|
||||||
|
* @param string|string[] $tags
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
protected function post_image($filename, $tags) {
|
protected function post_image($filename, $tags) {
|
||||||
$image_id = -1;
|
$image_id = -1;
|
||||||
$this->setMaximumRedirects(0);
|
$this->setMaximumRedirects(0);
|
||||||
@ -195,6 +207,9 @@ class ShimmieWebTestCase extends SCoreWebTestCase {
|
|||||||
return $image_id;
|
return $image_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
*/
|
||||||
protected function delete_image($image_id) {
|
protected function delete_image($image_id) {
|
||||||
if($image_id > 0) {
|
if($image_id > 0) {
|
||||||
$this->get_page('post/view/'.$image_id);
|
$this->get_page('post/view/'.$image_id);
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Name: XML Sitemap
|
* Name: XML Sitemap
|
||||||
* Author: Sein Kraft <mail@seinkraft.info>
|
* Author: Sein Kraft <mail@seinkraft.info>
|
||||||
@ -9,159 +10,181 @@
|
|||||||
* Documentation:
|
* Documentation:
|
||||||
*/
|
*/
|
||||||
|
|
||||||
class XMLSitemap extends Extension {
|
class XMLSitemap extends Extension
|
||||||
private $sitemap_queue = "";
|
{
|
||||||
private $sitemap_filepath = ""; // set onPageRequest
|
private $sitemap_queue = "";
|
||||||
|
private $sitemap_filepath = ""; // set onPageRequest
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
|
||||||
if($event->page_matches("sitemap.xml"))
|
public function onPageRequest(PageRequestEvent $event)
|
||||||
{
|
{
|
||||||
global $config;
|
if ($event->page_matches("sitemap.xml")) {
|
||||||
|
global $config;
|
||||||
$this->sitemap_filepath = $_SERVER['DOCUMENT_ROOT']."/data/cache/sitemap.xml";
|
|
||||||
// determine if new sitemap needs to be generated
|
$this->sitemap_filepath = $_SERVER['DOCUMENT_ROOT'] . "/data/cache/sitemap.xml";
|
||||||
if ($this->new_sitemap_needed())
|
// determine if new sitemap needs to be generated
|
||||||
{
|
if ($this->new_sitemap_needed()) {
|
||||||
// determine which type of sitemap to generate
|
// determine which type of sitemap to generate
|
||||||
if ($config->get_bool("sitemap_generatefull",false))
|
if ($config->get_bool("sitemap_generatefull", false)) {
|
||||||
$this->handle_full_sitemap(); // default false until cache fixed
|
$this->handle_full_sitemap(); // default false until cache fixed
|
||||||
else
|
} else {
|
||||||
$this->handle_smaller_sitemap();
|
$this->handle_smaller_sitemap();
|
||||||
}
|
}
|
||||||
else $this->display_existing_sitemap();
|
} else $this->display_existing_sitemap();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onSetupBuilding(SetupBuildingEvent $event) {
|
public function onSetupBuilding(SetupBuildingEvent $event)
|
||||||
|
{
|
||||||
$sb = new SetupBlock("Sitemap");
|
$sb = new SetupBlock("Sitemap");
|
||||||
|
|
||||||
$sb->add_bool_option("sitemap_generatefull", "Generate full sitemap");
|
$sb->add_bool_option("sitemap_generatefull", "Generate full sitemap");
|
||||||
$sb->add_label("<br>(Enabled: every image and tag in sitemap, generation takes longer)");
|
$sb->add_label("<br>(Enabled: every image and tag in sitemap, generation takes longer)");
|
||||||
$sb->add_label("<br>(Disabled: only display the last 50 uploads in the sitemap)");
|
$sb->add_label("<br>(Disabled: only display the last 50 uploads in the sitemap)");
|
||||||
|
|
||||||
$event->panel->add_block($sb);
|
$event->panel->add_block($sb);
|
||||||
}
|
}
|
||||||
|
|
||||||
// sitemap with only the latest 50 images
|
|
||||||
private function handle_smaller_sitemap()
|
|
||||||
{
|
|
||||||
/* --- Add latest images to sitemap with higher priority --- */
|
|
||||||
$latestimages = Image::find_images(0, 50, array());
|
|
||||||
$latestimages_urllist = array();
|
|
||||||
foreach($latestimages as $arrayid => $image)
|
|
||||||
// create url from image id's
|
|
||||||
$latestimages_urllist[$arrayid] = "post/view/$image->id";
|
|
||||||
$this->add_sitemap_queue($latestimages_urllist, "monthly", "0.8", date("Y-m-d", $image->posted_timestamp));
|
|
||||||
|
|
||||||
/* --- Display page --- */
|
|
||||||
// when sitemap is ok, display it from the file
|
|
||||||
$this->generate_display_sitemap();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Full sitemap
|
|
||||||
private function handle_full_sitemap()
|
|
||||||
{
|
|
||||||
global $database, $config;
|
|
||||||
|
|
||||||
// add index
|
// sitemap with only the latest 50 images
|
||||||
$index = array();
|
private function handle_smaller_sitemap()
|
||||||
$index[0] = $config->get_string("front_page");
|
{
|
||||||
$this->add_sitemap_queue($index, "weekly", "1");
|
/* --- Add latest images to sitemap with higher priority --- */
|
||||||
|
$latestimages = Image::find_images(0, 50, array());
|
||||||
|
$latestimages_urllist = array();
|
||||||
|
foreach ($latestimages as $arrayid => $image) {
|
||||||
|
// create url from image id's
|
||||||
|
$latestimages_urllist[$arrayid] = "post/view/$image->id";
|
||||||
|
}
|
||||||
|
|
||||||
/* --- Add 20 most used tags --- */
|
$this->add_sitemap_queue($latestimages_urllist, "monthly", "0.8", date("Y-m-d", $image->posted_timestamp));
|
||||||
$popular_tags = $database->get_all("SELECT tag, count FROM tags ORDER BY `count` DESC LIMIT 0,20");
|
|
||||||
foreach($popular_tags as $arrayid => $tag) {
|
|
||||||
$tag = $tag['tag'];
|
|
||||||
$popular_tags[$arrayid] = "post/list/$tag/";
|
|
||||||
}
|
|
||||||
$this->add_sitemap_queue($popular_tags, "monthly", "0.9" /* not sure how to deal with date here */);
|
|
||||||
|
|
||||||
/* --- Add latest images to sitemap with higher priority --- */
|
/* --- Display page --- */
|
||||||
$latestimages = Image::find_images(0, 50, array());
|
// when sitemap is ok, display it from the file
|
||||||
$latestimages_urllist = array();
|
$this->generate_display_sitemap();
|
||||||
foreach($latestimages as $arrayid => $image)
|
}
|
||||||
// create url from image id's
|
|
||||||
$latestimages_urllist[$arrayid] = "post/view/$image->id";
|
|
||||||
$this->add_sitemap_queue($latestimages_urllist, "monthly", "0.8", date("Y-m-d", $image->posted_timestamp));
|
|
||||||
|
|
||||||
/* --- Add other tags --- */
|
// Full sitemap
|
||||||
$other_tags = $database->get_all("SELECT tag, count FROM tags ORDER BY `count` DESC LIMIT 21,10000000");
|
private function handle_full_sitemap()
|
||||||
foreach($other_tags as $arrayid => $tag) {
|
{
|
||||||
$tag = $tag['tag'];
|
global $database, $config;
|
||||||
// create url from tags (tagme ignored)
|
|
||||||
if ($tag != "tagme")
|
|
||||||
$other_tags[$arrayid] = "post/list/$tag/";
|
|
||||||
}
|
|
||||||
$this->add_sitemap_queue($other_tags, "monthly", "0.7" /* not sure how to deal with date here */);
|
|
||||||
|
|
||||||
/* --- Add all other images to sitemap with lower priority --- */
|
// add index
|
||||||
$otherimages = Image::find_images(51, 10000000, array());
|
$index = array();
|
||||||
foreach($otherimages as $arrayid => $image)
|
$index[0] = $config->get_string("front_page");
|
||||||
// create url from image id's
|
$this->add_sitemap_queue($index, "weekly", "1");
|
||||||
$otherimages[$arrayid] = "post/view/$image->id";
|
|
||||||
$this->add_sitemap_queue($otherimages, "monthly", "0.6", date("Y-m-d", $image->posted_timestamp));
|
/* --- Add 20 most used tags --- */
|
||||||
|
$popular_tags = $database->get_all("SELECT tag, count FROM tags ORDER BY `count` DESC LIMIT 0,20");
|
||||||
|
foreach ($popular_tags as $arrayid => $tag) {
|
||||||
/* --- Display page --- */
|
$tag = $tag['tag'];
|
||||||
// when sitemap is ok, display it from the file
|
$popular_tags[$arrayid] = "post/list/$tag/";
|
||||||
$this->generate_display_sitemap();
|
}
|
||||||
}
|
$this->add_sitemap_queue($popular_tags, "monthly", "0.9" /* not sure how to deal with date here */);
|
||||||
|
|
||||||
// Adds an array of urls to the sitemap with the given information
|
/* --- Add latest images to sitemap with higher priority --- */
|
||||||
private function add_sitemap_queue(/*array(urls)*/ $urls, $changefreq="monthly", $priority="0.5", $date="2013-02-01") {
|
$latestimages = Image::find_images(0, 50, array());
|
||||||
foreach($urls as $url) {
|
$latestimages_urllist = array();
|
||||||
$link = make_http(make_link("$url"));
|
foreach ($latestimages as $arrayid => $image) {
|
||||||
$this->sitemap_queue .= "
|
// create url from image id's
|
||||||
|
$latestimages_urllist[$arrayid] = "post/view/$image->id";
|
||||||
|
}
|
||||||
|
$this->add_sitemap_queue($latestimages_urllist, "monthly", "0.8", date("Y-m-d", $image->posted_timestamp));
|
||||||
|
|
||||||
|
/* --- Add other tags --- */
|
||||||
|
$other_tags = $database->get_all("SELECT tag, count FROM tags ORDER BY `count` DESC LIMIT 21,10000000");
|
||||||
|
foreach ($other_tags as $arrayid => $tag) {
|
||||||
|
$tag = $tag['tag'];
|
||||||
|
// create url from tags (tagme ignored)
|
||||||
|
if ($tag != "tagme")
|
||||||
|
$other_tags[$arrayid] = "post/list/$tag/";
|
||||||
|
}
|
||||||
|
$this->add_sitemap_queue($other_tags, "monthly", "0.7" /* not sure how to deal with date here */);
|
||||||
|
|
||||||
|
/* --- Add all other images to sitemap with lower priority --- */
|
||||||
|
$otherimages = Image::find_images(51, 10000000, array());
|
||||||
|
foreach ($otherimages as $arrayid => $image) {
|
||||||
|
// create url from image id's
|
||||||
|
$otherimages[$arrayid] = "post/view/$image->id";
|
||||||
|
}
|
||||||
|
$this->add_sitemap_queue($otherimages, "monthly", "0.6", date("Y-m-d", $image->posted_timestamp));
|
||||||
|
|
||||||
|
|
||||||
|
/* --- Display page --- */
|
||||||
|
// when sitemap is ok, display it from the file
|
||||||
|
$this->generate_display_sitemap();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds an array of urls to the sitemap with the given information.
|
||||||
|
*
|
||||||
|
* @param array $urls
|
||||||
|
* @param string $changefreq
|
||||||
|
* @param string $priority
|
||||||
|
* @param string $date
|
||||||
|
*/
|
||||||
|
private function add_sitemap_queue( /*array(urls)*/ $urls, $changefreq = "monthly",
|
||||||
|
$priority = "0.5", $date = "2013-02-01")
|
||||||
|
{
|
||||||
|
foreach ($urls as $url) {
|
||||||
|
$link = make_http(make_link("$url"));
|
||||||
|
$this->sitemap_queue .= "
|
||||||
<url>
|
<url>
|
||||||
<loc>$link</loc>
|
<loc>$link</loc>
|
||||||
<lastmod>$date</lastmod>
|
<lastmod>$date</lastmod>
|
||||||
<changefreq>$changefreq</changefreq>
|
<changefreq>$changefreq</changefreq>
|
||||||
<priority>$priority</priority>
|
<priority>$priority</priority>
|
||||||
</url>";
|
</url>";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// sets sitemap with entries in sitemap_queue
|
|
||||||
private function generate_display_sitemap()
|
|
||||||
{
|
|
||||||
global $page;
|
|
||||||
|
|
||||||
$xml = "<"."?xml version=\"1.0\" encoding=\"utf-8\"?".">
|
|
||||||
<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\">
|
|
||||||
$this->sitemap_queue
|
|
||||||
</urlset>";
|
|
||||||
|
|
||||||
// Generate new sitemap
|
|
||||||
file_put_contents($this->sitemap_filepath, $xml);
|
|
||||||
$page->set_mode("data");
|
|
||||||
$page->set_type("application/xml");
|
|
||||||
$page->set_data($xml);
|
|
||||||
}
|
|
||||||
|
|
||||||
// returns true if a new sitemap is needed
|
|
||||||
private function new_sitemap_needed()
|
|
||||||
{
|
|
||||||
$sitemap_generation_interval = 86400; // allow new site map every day
|
|
||||||
$last_generated_time = filemtime($this->sitemap_filepath);
|
|
||||||
|
|
||||||
// if file doesn't exist, return true
|
|
||||||
if ($last_generated_time == false) return true;
|
|
||||||
|
|
||||||
// if it's been a day since last sitemap creation, return true
|
|
||||||
if ($last_generated_time + $sitemap_generation_interval < time())
|
|
||||||
return true;
|
|
||||||
else return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private function display_existing_sitemap()
|
|
||||||
{
|
|
||||||
global $page;
|
|
||||||
|
|
||||||
$xml = file_get_contents($this->sitemap_filepath);
|
// sets sitemap with entries in sitemap_queue
|
||||||
|
private function generate_display_sitemap()
|
||||||
$page->set_mode("data");
|
{
|
||||||
$page->set_type("application/xml");
|
global $page;
|
||||||
$page->set_data($xml);
|
|
||||||
}
|
$xml = "<" . "?xml version=\"1.0\" encoding=\"utf-8\"?" . ">
|
||||||
|
<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\">
|
||||||
|
$this->sitemap_queue
|
||||||
|
</urlset>";
|
||||||
|
|
||||||
|
// Generate new sitemap
|
||||||
|
file_put_contents($this->sitemap_filepath, $xml);
|
||||||
|
$page->set_mode("data");
|
||||||
|
$page->set_type("application/xml");
|
||||||
|
$page->set_data($xml);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns true if a new sitemap is needed.
|
||||||
|
*
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
private function new_sitemap_needed()
|
||||||
|
{
|
||||||
|
$sitemap_generation_interval = 86400; // allow new site map every day
|
||||||
|
$last_generated_time = filemtime($this->sitemap_filepath);
|
||||||
|
|
||||||
|
// if file doesn't exist, return true
|
||||||
|
if ($last_generated_time == false) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// if it's been a day since last sitemap creation, return true
|
||||||
|
if ($last_generated_time + $sitemap_generation_interval < time()) {
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private function display_existing_sitemap()
|
||||||
|
{
|
||||||
|
global $page;
|
||||||
|
|
||||||
|
$xml = file_get_contents($this->sitemap_filepath);
|
||||||
|
|
||||||
|
$page->set_mode("data");
|
||||||
|
$page->set_type("application/xml");
|
||||||
|
$page->set_data($xml);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -112,9 +112,10 @@ class Source_History extends Extension {
|
|||||||
$config->set_int("ext_source_history_version", 3);
|
$config->set_int("ext_source_history_version", 3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* this function is called when a revert request is received
|
* This function is called when a revert request is received.
|
||||||
|
* @param int $revert_id
|
||||||
*/
|
*/
|
||||||
private function process_revert_request($revert_id) {
|
private function process_revert_request($revert_id) {
|
||||||
global $page;
|
global $page;
|
||||||
@ -201,7 +202,11 @@ class Source_History extends Extension {
|
|||||||
// output results
|
// output results
|
||||||
$this->theme->display_revert_ip_results();
|
$this->theme->display_revert_ip_results();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $revert_id
|
||||||
|
* @return mixed|null
|
||||||
|
*/
|
||||||
public function get_source_history_from_revert(/*int*/ $revert_id) {
|
public function get_source_history_from_revert(/*int*/ $revert_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_row("
|
$row = $database->get_row("
|
||||||
@ -212,6 +217,10 @@ class Source_History extends Extension {
|
|||||||
return ($row ? $row : null);
|
return ($row ? $row : null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_source_history_from_id(/*int*/ $image_id) {
|
public function get_source_history_from_id(/*int*/ $image_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_all("
|
$row = $database->get_all("
|
||||||
@ -224,6 +233,10 @@ class Source_History extends Extension {
|
|||||||
return ($row ? $row : array());
|
return ($row ? $row : array());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $page_id
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_global_source_history($page_id) {
|
public function get_global_source_history($page_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_all("
|
$row = $database->get_all("
|
||||||
@ -235,9 +248,13 @@ class Source_History extends Extension {
|
|||||||
", array("offset" => ($page_id-1)*100));
|
", array("offset" => ($page_id-1)*100));
|
||||||
return ($row ? $row : array());
|
return ($row ? $row : array());
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* This function attempts to revert all changes by a given IP within an (optional) timeframe.
|
* This function attempts to revert all changes by a given IP within an (optional) timeframe.
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param string $ip
|
||||||
|
* @param string $date
|
||||||
*/
|
*/
|
||||||
public function process_revert_all_changes($name, $ip, $date) {
|
public function process_revert_all_changes($name, $ip, $date) {
|
||||||
global $database;
|
global $database;
|
||||||
@ -331,9 +348,11 @@ class Source_History extends Extension {
|
|||||||
|
|
||||||
log_info("source_history", 'Reverted '.count($result).' edits.');
|
log_info("source_history", 'Reverted '.count($result).' edits.');
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* this function is called just before an images source is changed
|
* This function is called just before an images source is changed.
|
||||||
|
* @param Image $image
|
||||||
|
* @param string $source
|
||||||
*/
|
*/
|
||||||
private function add_source_history($image, $source) {
|
private function add_source_history($image, $source) {
|
||||||
global $database, $config, $user;
|
global $database, $config, $user;
|
||||||
|
@ -2,6 +2,11 @@
|
|||||||
class Source_HistoryTheme extends Themelet {
|
class Source_HistoryTheme extends Themelet {
|
||||||
var $messages = array();
|
var $messages = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param int $image_id
|
||||||
|
* @param array $history
|
||||||
|
*/
|
||||||
public function display_history_page(Page $page, /*int*/ $image_id, /*array*/ $history) {
|
public function display_history_page(Page $page, /*int*/ $image_id, /*array*/ $history) {
|
||||||
global $user;
|
global $user;
|
||||||
$start_string = "
|
$start_string = "
|
||||||
@ -45,6 +50,11 @@ class Source_HistoryTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Source History", $history_html, "main", 10));
|
$page->add_block(new Block("Source History", $history_html, "main", 10));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $history
|
||||||
|
* @param int $page_number
|
||||||
|
*/
|
||||||
public function display_global_page(Page $page, /*array*/ $history, /*int*/ $page_number) {
|
public function display_global_page(Page $page, /*array*/ $history, /*int*/ $page_number) {
|
||||||
$start_string = "
|
$start_string = "
|
||||||
<div style='text-align: left'>
|
<div style='text-align: left'>
|
||||||
@ -93,8 +103,9 @@ class Source_HistoryTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Navigation", $nav, "left"));
|
$page->add_block(new Block("Navigation", $nav, "left"));
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Add a section to the admin page.
|
* Add a section to the admin page.
|
||||||
|
* @param string $validation_msg
|
||||||
*/
|
*/
|
||||||
public function display_admin_block(/*string*/ $validation_msg='') {
|
public function display_admin_block(/*string*/ $validation_msg='') {
|
||||||
global $page;
|
global $page;
|
||||||
@ -129,7 +140,11 @@ class Source_HistoryTheme extends Themelet {
|
|||||||
$html = implode($this->messages, "\n");
|
$html = implode($this->messages, "\n");
|
||||||
$page->add_block(new Block("Bulk Revert Results", $html));
|
$page->add_block(new Block("Bulk Revert Results", $html));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $title
|
||||||
|
* @param string $body
|
||||||
|
*/
|
||||||
public function add_status(/*string*/ $title, /*string*/ $body) {
|
public function add_status(/*string*/ $title, /*string*/ $body) {
|
||||||
$this->messages[] = '<p><b>'. $title .'</b><br>'. $body .'</p>';
|
$this->messages[] = '<p><b>'. $title .'</b><br>'. $body .'</p>';
|
||||||
}
|
}
|
||||||
|
@ -23,6 +23,7 @@ class StatsDInterface extends Extension {
|
|||||||
$time = microtime(true) - $_load_start;
|
$time = microtime(true) - $_load_start;
|
||||||
StatsDInterface::$stats["shimmie.$type.hits"] = "1|c";
|
StatsDInterface::$stats["shimmie.$type.hits"] = "1|c";
|
||||||
StatsDInterface::$stats["shimmie.$type.time"] = "$time|ms";
|
StatsDInterface::$stats["shimmie.$type.time"] = "$time|ms";
|
||||||
|
StatsDInterface::$stats["shimmie.$type.time-db"] = "{$database->dbtime}|ms";
|
||||||
StatsDInterface::$stats["shimmie.$type.memory"] = memory_get_peak_usage(true)."|c";
|
StatsDInterface::$stats["shimmie.$type.memory"] = memory_get_peak_usage(true)."|c";
|
||||||
StatsDInterface::$stats["shimmie.$type.files"] = count(get_included_files())."|c";
|
StatsDInterface::$stats["shimmie.$type.files"] = count(get_included_files())."|c";
|
||||||
StatsDInterface::$stats["shimmie.$type.queries"] = $_execs."|c";
|
StatsDInterface::$stats["shimmie.$type.queries"] = $_execs."|c";
|
||||||
@ -76,6 +77,9 @@ class StatsDInterface extends Extension {
|
|||||||
StatsDInterface::$stats["shimmie.events.info-sets"] = "1|c";
|
StatsDInterface::$stats["shimmie.events.info-sets"] = "1|c";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
public function get_priority() {return 99;}
|
public function get_priority() {return 99;}
|
||||||
|
|
||||||
|
|
||||||
|
@ -23,7 +23,14 @@
|
|||||||
* </ul>
|
* </ul>
|
||||||
* <li>Pools
|
* <li>Pools
|
||||||
* <ul>
|
* <ul>
|
||||||
* <li>pool=(PoolID, PoolTitle) -- add post to pool (if exists)
|
* <li>pool=(PoolID, PoolTitle, lastcreated) -- add post to pool (if exists)
|
||||||
|
* <li>pool=(PoolID, PoolTitle, lastcreated):(PoolOrder) -- add post to pool (if exists) with set pool order
|
||||||
|
* <ul>
|
||||||
|
* <li>pool=50 -- add post to pool with ID of 50
|
||||||
|
* <li>pool=10:25 -- add post to pool with ID of 10 and with order 25
|
||||||
|
* <li>pool=This_is_a_Pool -- add post to pool with a title of "This is a Pool"
|
||||||
|
* <li>pool=lastcreated -- add post to the last pool the user created
|
||||||
|
* </ul>
|
||||||
* </ul>
|
* </ul>
|
||||||
* <li>Post Relationships
|
* <li>Post Relationships
|
||||||
* <ul>
|
* <ul>
|
||||||
@ -40,9 +47,15 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class OwnerSetEvent extends Event {
|
class OwnerSetEvent extends Event {
|
||||||
var $image;
|
/** @var \Image */
|
||||||
var $owner;
|
public $image;
|
||||||
|
/** @var \User */
|
||||||
|
public $owner;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param User $owner
|
||||||
|
*/
|
||||||
public function __construct(Image $image, User $owner) {
|
public function __construct(Image $image, User $owner) {
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
$this->owner = $owner;
|
$this->owner = $owner;
|
||||||
@ -57,9 +70,15 @@ class OwnerSetEvent extends Event {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class SourceSetEvent extends Event {
|
class SourceSetEvent extends Event {
|
||||||
var $image;
|
/** @var \Image */
|
||||||
var $source;
|
public $image;
|
||||||
|
/** @var string */
|
||||||
|
public $source;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param string $source
|
||||||
|
*/
|
||||||
public function __construct(Image $image, $source) {
|
public function __construct(Image $image, $source) {
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
$this->source = $source;
|
$this->source = $source;
|
||||||
@ -74,7 +93,8 @@ class SourceSetEvent extends Event {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class TagSetEvent extends Event {
|
class TagSetEvent extends Event {
|
||||||
var $image;
|
/** @var \Image */
|
||||||
|
public $image;
|
||||||
var $tags;
|
var $tags;
|
||||||
|
|
||||||
public function __construct(Image $image, $tags) {
|
public function __construct(Image $image, $tags) {
|
||||||
@ -90,9 +110,15 @@ class TagSetEvent extends Event {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
class LockSetEvent extends Event {
|
class LockSetEvent extends Event {
|
||||||
var $image;
|
/** @var \Image */
|
||||||
var $locked;
|
public $image;
|
||||||
|
/** @var bool */
|
||||||
|
public $locked;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @param bool $locked
|
||||||
|
*/
|
||||||
public function __construct(Image $image, $locked) {
|
public function __construct(Image $image, $locked) {
|
||||||
assert(is_bool($locked));
|
assert(is_bool($locked));
|
||||||
$this->image = $image;
|
$this->image = $image;
|
||||||
@ -107,13 +133,17 @@ class LockSetEvent extends Event {
|
|||||||
class TagTermParseEvent extends Event {
|
class TagTermParseEvent extends Event {
|
||||||
var $term = null;
|
var $term = null;
|
||||||
var $id = null;
|
var $id = null;
|
||||||
var $metatag = false;
|
/** @var bool */
|
||||||
|
public $metatag = false;
|
||||||
|
|
||||||
public function __construct($term, $id) {
|
public function __construct($term, $id) {
|
||||||
$this->term = $term;
|
$this->term = $term;
|
||||||
$this->id = $id;
|
$this->id = $id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
public function is_metatag() {
|
public function is_metatag() {
|
||||||
return $this->metatag;
|
return $this->metatag;
|
||||||
}
|
}
|
||||||
@ -150,10 +180,14 @@ class TagEdit extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
public function onImageInfoSet(ImageInfoSetEvent $event) {
|
||||||
global $user, $page;
|
global $user;
|
||||||
if($user->can("edit_image_owner")) {
|
if($user->can("edit_image_owner")) {
|
||||||
$owner = User::by_name($_POST['tag_edit__owner']);
|
$owner = User::by_name($_POST['tag_edit__owner']);
|
||||||
send_event(new OwnerSetEvent($event->image, $owner));
|
if ($owner instanceof User) {
|
||||||
|
send_event(new OwnerSetEvent($event->image, $owner));
|
||||||
|
} else {
|
||||||
|
throw new NullUserException("Error: No user with that name was found.");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if($this->can_tag($event->image) && isset($_POST['tag_edit__tags'])) {
|
if($this->can_tag($event->image) && isset($_POST['tag_edit__tags'])) {
|
||||||
send_event(new TagSetEvent($event->image, $_POST['tag_edit__tags']));
|
send_event(new TagSetEvent($event->image, $_POST['tag_edit__tags']));
|
||||||
@ -205,13 +239,15 @@ class TagEdit extends Extension {
|
|||||||
$this->theme->display_mass_editor();
|
$this->theme->display_mass_editor();
|
||||||
}
|
}
|
||||||
|
|
||||||
// When an alias is added, oldtag becomes inaccessable
|
/**
|
||||||
|
* When an alias is added, oldtag becomes inaccessible.
|
||||||
|
* @param AddAliasEvent $event
|
||||||
|
*/
|
||||||
public function onAddAlias(AddAliasEvent $event) {
|
public function onAddAlias(AddAliasEvent $event) {
|
||||||
$this->mass_tag_edit($event->oldtag, $event->newtag);
|
$this->mass_tag_edit($event->oldtag, $event->newtag);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function onImageInfoBoxBuilding(ImageInfoBoxBuildingEvent $event) {
|
public function onImageInfoBoxBuilding(ImageInfoBoxBuildingEvent $event) {
|
||||||
global $user;
|
|
||||||
$event->add_part($this->theme->get_user_editor_html($event->image), 39);
|
$event->add_part($this->theme->get_user_editor_html($event->image), 39);
|
||||||
$event->add_part($this->theme->get_tag_editor_html($event->image), 40);
|
$event->add_part($this->theme->get_tag_editor_html($event->image), 40);
|
||||||
$event->add_part($this->theme->get_source_editor_html($event->image), 41);
|
$event->add_part($this->theme->get_source_editor_html($event->image), 41);
|
||||||
@ -229,19 +265,30 @@ class TagEdit extends Extension {
|
|||||||
if(!empty($matches)) $event->metatag = true;
|
if(!empty($matches)) $event->metatag = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function can_tag(Image $image) {
|
private function can_tag(Image $image) {
|
||||||
global $config, $user;
|
global $user;
|
||||||
return ($user->can("edit_image_tag") || !$image->is_locked());
|
return ($user->can("edit_image_tag") || !$image->is_locked());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
private function can_source(Image $image) {
|
private function can_source(Image $image) {
|
||||||
global $config, $user;
|
global $user;
|
||||||
return ($user->can("edit_image_source") || !$image->is_locked());
|
return ($user->can("edit_image_source") || !$image->is_locked());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $search
|
||||||
|
* @param string $replace
|
||||||
|
*/
|
||||||
private function mass_tag_edit($search, $replace) {
|
private function mass_tag_edit($search, $replace) {
|
||||||
global $database;
|
global $database;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$search_set = Tag::explode(strtolower($search), false);
|
$search_set = Tag::explode(strtolower($search), false);
|
||||||
$replace_set = Tag::explode(strtolower($replace), false);
|
$replace_set = Tag::explode(strtolower($replace), false);
|
||||||
@ -296,10 +343,11 @@ class TagEdit extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string|string[] $tags
|
||||||
|
* @param string $source
|
||||||
|
*/
|
||||||
private function mass_source_edit($tags, $source) {
|
private function mass_source_edit($tags, $source) {
|
||||||
global $database;
|
|
||||||
global $config;
|
|
||||||
|
|
||||||
$tags = Tag::explode($tags);
|
$tags = Tag::explode($tags);
|
||||||
|
|
||||||
$last_id = -1;
|
$last_id = -1;
|
||||||
|
@ -99,6 +99,10 @@ class TagEditTheme extends Themelet {
|
|||||||
";
|
";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $source
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function format_source(/*string*/ $source) {
|
protected function format_source(/*string*/ $source) {
|
||||||
if(!empty($source)) {
|
if(!empty($source)) {
|
||||||
if(!startsWith($source, "http://") && !startsWith($source, "https://")) {
|
if(!startsWith($source, "http://") && !startsWith($source, "https://")) {
|
||||||
|
@ -51,7 +51,11 @@ class TagEditCloud extends Extension {
|
|||||||
$event->panel->add_block($sb);
|
$event->panel->add_block($sb);
|
||||||
}
|
}
|
||||||
|
|
||||||
private function build_tag_map($image) {
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
private function build_tag_map(Image $image) {
|
||||||
global $database, $config;
|
global $database, $config;
|
||||||
|
|
||||||
$html = "";
|
$html = "";
|
||||||
@ -75,23 +79,26 @@ class TagEditCloud extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$tag_data = null;
|
||||||
|
|
||||||
switch($sort_method){
|
switch($sort_method){
|
||||||
case 'a':
|
case 'a':
|
||||||
case 'p':
|
case 'p':
|
||||||
$tag_data = $database->get_all("SELECT tag, FLOOR(LN(LN(count - :tag_min1 + 1)+1)*150)/200 AS scaled, count
|
default:
|
||||||
FROM tags WHERE count >= :tag_min2 ORDER BY ".($sort_method == 'a' ? "tag" : "count DESC")." LIMIT :limit",
|
$tag_data = $database->get_all("SELECT tag, FLOOR(LN(LN(count - :tag_min1 + 1)+1)*150)/200 AS scaled, count
|
||||||
array("tag_min1" => $tags_min, "tag_min2" => $tags_min, "limit" => $max_count));
|
FROM tags WHERE count >= :tag_min2 ORDER BY ".($sort_method == 'a' ? "tag" : "count DESC")." LIMIT :limit",
|
||||||
break;
|
|
||||||
case 'r':
|
|
||||||
$relevant_tags = array_diff($image->get_tag_array(),$ignore_tags);
|
|
||||||
if(count($relevant_tags) > 0) {
|
|
||||||
$relevant_tags = implode(",",array_map(array($database,"escape"),$relevant_tags));
|
|
||||||
$tag_data = $database->get_all("SELECT t2.tag AS tag, COUNT(image_id) AS count, FLOOR(LN(LN(COUNT(image_id) - :tag_min1 + 1)+1)*150)/200 AS scaled
|
|
||||||
FROM image_tags it1 JOIN image_tags it2 USING(image_id) JOIN tags t1 ON it1.tag_id = t1.id JOIN tags t2 ON it2.tag_id = t2.id
|
|
||||||
WHERE t1.count >= :tag_min2 AND t1.tag IN($relevant_tags) GROUP BY t2.tag ORDER BY count DESC LIMIT :limit",
|
|
||||||
array("tag_min1" => $tags_min, "tag_min2" => $tags_min, "limit" => $max_count));
|
array("tag_min1" => $tags_min, "tag_min2" => $tags_min, "limit" => $max_count));
|
||||||
}
|
break;
|
||||||
break;
|
case 'r':
|
||||||
|
$relevant_tags = array_diff($image->get_tag_array(),$ignore_tags);
|
||||||
|
if(count($relevant_tags) > 0) {
|
||||||
|
$relevant_tags = implode(",",array_map(array($database,"escape"),$relevant_tags));
|
||||||
|
$tag_data = $database->get_all("SELECT t2.tag AS tag, COUNT(image_id) AS count, FLOOR(LN(LN(COUNT(image_id) - :tag_min1 + 1)+1)*150)/200 AS scaled
|
||||||
|
FROM image_tags it1 JOIN image_tags it2 USING(image_id) JOIN tags t1 ON it1.tag_id = t1.id JOIN tags t2 ON it2.tag_id = t2.id
|
||||||
|
WHERE t1.count >= :tag_min2 AND t1.tag IN($relevant_tags) GROUP BY t2.tag ORDER BY count DESC LIMIT :limit",
|
||||||
|
array("tag_min1" => $tags_min, "tag_min2" => $tags_min, "limit" => $max_count));
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
$counter = 1;
|
$counter = 1;
|
||||||
@ -115,15 +122,15 @@ class TagEditCloud extends Extension {
|
|||||||
$size = sprintf("%.2f", max($row['scaled'],0.5));
|
$size = sprintf("%.2f", max($row['scaled'],0.5));
|
||||||
$js = htmlspecialchars('tageditcloud_toggle_tag(this,'.json_encode($full_tag).')',ENT_QUOTES); //Ugly, but it works
|
$js = htmlspecialchars('tageditcloud_toggle_tag(this,'.json_encode($full_tag).')',ENT_QUOTES); //Ugly, but it works
|
||||||
|
|
||||||
if(array_search($row['tag'],$image->tag_array) !== FALSE) {
|
if(array_search($row['tag'],$image->get_tag_array()) !== FALSE) {
|
||||||
if($used_first) {
|
if($used_first) {
|
||||||
$precloud .= " <span onclick='$js' class='tag-selected' style='font-size: ${size}em$color' title='${row['count']}'>$h_tag</span> \n";
|
$precloud .= " <span onclick='{$js}' class='tag-selected' style='font-size: ${size}em$color' title='${row['count']}'>{$h_tag}</span> \n";
|
||||||
continue;
|
continue;
|
||||||
} else {
|
} else {
|
||||||
$entry = " <span onclick='$js' class='tag-selected' style='font-size: ${size}em$color' title='${row['count']}'>$h_tag</span> \n";
|
$entry = " <span onclick='{$js}' class='tag-selected' style='font-size: ${size}em$color' title='${row['count']}'>{$h_tag}</span> \n";
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
$entry = " <span onclick='$js' style='font-size: ${size}em$color' title='${row['count']}'>$h_tag</span> \n";
|
$entry = " <span onclick='{$js}' style='font-size: ${size}em$color' title='${row['count']}'>{$h_tag}</span> \n";
|
||||||
}
|
}
|
||||||
|
|
||||||
if($counter++ <= $def_count) {
|
if($counter++ <= $def_count) {
|
||||||
@ -134,24 +141,28 @@ class TagEditCloud extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if($precloud != '') {
|
if($precloud != '') {
|
||||||
$html .= "<div id='tagcloud_set'>$precloud</div>";
|
$html .= "<div id='tagcloud_set'>{$precloud}</div>";
|
||||||
}
|
}
|
||||||
|
|
||||||
if($postcloud != '') {
|
if($postcloud != '') {
|
||||||
$postcloud = "<div id='tagcloud_extra' style='display: none;'>$postcloud</div>";
|
$postcloud = "<div id='tagcloud_extra' style='display: none;'>{$postcloud}</div>";
|
||||||
}
|
}
|
||||||
|
|
||||||
$html .= "<div id='tagcloud_unset'>$cloud$postcloud</div>";
|
$html .= "<div id='tagcloud_unset'>{$cloud}{$postcloud}</div>";
|
||||||
|
|
||||||
if($sort_method != 'a' && $counter > $def_count) {
|
if($sort_method != 'a' && $counter > $def_count) {
|
||||||
$rem = $counter - $def_count;
|
$rem = $counter - $def_count;
|
||||||
$html .= "</div><br>[<span onclick='tageditcloud_toggle_extra(this);' style='color: #0000EF; font-weight:bold;'>show $rem more tags</span>]";
|
$html .= "</div><br>[<span onclick='tageditcloud_toggle_extra(this);' style='color: #0000EF; font-weight:bold;'>show {$rem} more tags</span>]";
|
||||||
}
|
}
|
||||||
|
|
||||||
return "<div id='tageditcloud' class='tageditcloud'>$html</div>"; // FIXME: stupidasallhell
|
return "<div id='tageditcloud' class='tageditcloud'>{$html}</div>"; // FIXME: stupidasallhell
|
||||||
}
|
}
|
||||||
|
|
||||||
private function can_tag($image) {
|
/**
|
||||||
|
* @param Image $image
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
private function can_tag(Image $image) {
|
||||||
global $user;
|
global $user;
|
||||||
return ($user->can("edit_image_tag") && (!$image->is_locked() || $user->can("edit_image_lock")));
|
return ($user->can("edit_image_tag") && (!$image->is_locked() || $user->can("edit_image_lock")));
|
||||||
}
|
}
|
||||||
|
@ -24,7 +24,7 @@ class Tag_History extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public function onPageRequest(PageRequestEvent $event) {
|
public function onPageRequest(PageRequestEvent $event) {
|
||||||
global $config, $page, $user;
|
global $page, $user;
|
||||||
|
|
||||||
if($event->page_matches("tag_history/revert")) {
|
if($event->page_matches("tag_history/revert")) {
|
||||||
// this is a request to revert to a previous version of the tags
|
// this is a request to revert to a previous version of the tags
|
||||||
@ -112,9 +112,12 @@ class Tag_History extends Extension {
|
|||||||
$config->set_int("ext_tag_history_version", 3);
|
$config->set_int("ext_tag_history_version", 3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* this function is called when a revert request is received
|
* This function is called when a revert request is received.
|
||||||
|
*
|
||||||
|
* @param int $revert_id
|
||||||
|
* @throws ImageDoesNotExist
|
||||||
*/
|
*/
|
||||||
private function process_revert_request($revert_id) {
|
private function process_revert_request($revert_id) {
|
||||||
global $page;
|
global $page;
|
||||||
@ -199,7 +202,11 @@ class Tag_History extends Extension {
|
|||||||
// output results
|
// output results
|
||||||
$this->theme->display_revert_ip_results();
|
$this->theme->display_revert_ip_results();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $revert_id
|
||||||
|
* @return mixed|null
|
||||||
|
*/
|
||||||
public function get_tag_history_from_revert(/*int*/ $revert_id) {
|
public function get_tag_history_from_revert(/*int*/ $revert_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_row("
|
$row = $database->get_row("
|
||||||
@ -210,6 +217,10 @@ class Tag_History extends Extension {
|
|||||||
return ($row ? $row : null);
|
return ($row ? $row : null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $image_id
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_tag_history_from_id(/*int*/ $image_id) {
|
public function get_tag_history_from_id(/*int*/ $image_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_all("
|
$row = $database->get_all("
|
||||||
@ -222,6 +233,10 @@ class Tag_History extends Extension {
|
|||||||
return ($row ? $row : array());
|
return ($row ? $row : array());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $page_id
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function get_global_tag_history($page_id) {
|
public function get_global_tag_history($page_id) {
|
||||||
global $database;
|
global $database;
|
||||||
$row = $database->get_all("
|
$row = $database->get_all("
|
||||||
@ -327,17 +342,20 @@ class Tag_History extends Extension {
|
|||||||
|
|
||||||
log_info("tag_history", 'Reverted '.count($result).' edits.');
|
log_info("tag_history", 'Reverted '.count($result).' edits.');
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* this function is called just before an images tag are changed
|
* This function is called just before an images tag are changed.
|
||||||
|
*
|
||||||
|
* @param Image $image
|
||||||
|
* @param string|string[] $tags
|
||||||
*/
|
*/
|
||||||
private function add_tag_history($image, $tags) {
|
private function add_tag_history(Image $image, $tags) {
|
||||||
global $database, $config, $user;
|
global $database, $config, $user;
|
||||||
|
|
||||||
$new_tags = Tag::implode($tags);
|
$new_tags = Tag::implode($tags);
|
||||||
$old_tags = Tag::implode($image->get_tag_array());
|
$old_tags = Tag::implode($image->get_tag_array());
|
||||||
|
|
||||||
if($new_tags == $old_tags) return;
|
if($new_tags == $old_tags) { return; }
|
||||||
|
|
||||||
if(empty($old_tags)) {
|
if(empty($old_tags)) {
|
||||||
/* no old tags, so we are probably adding the image for the first time */
|
/* no old tags, so we are probably adding the image for the first time */
|
||||||
@ -348,7 +366,7 @@ class Tag_History extends Extension {
|
|||||||
}
|
}
|
||||||
|
|
||||||
$allowed = $config->get_int("history_limit");
|
$allowed = $config->get_int("history_limit");
|
||||||
if($allowed == 0) return;
|
if($allowed == 0) { return; }
|
||||||
|
|
||||||
// if the image has no history, make one with the old tags
|
// if the image has no history, make one with the old tags
|
||||||
$entries = $database->get_one("SELECT COUNT(*) FROM tag_histories WHERE image_id = ?", array($image->id));
|
$entries = $database->get_one("SELECT COUNT(*) FROM tag_histories WHERE image_id = ?", array($image->id));
|
||||||
@ -368,7 +386,7 @@ class Tag_History extends Extension {
|
|||||||
$entries++;
|
$entries++;
|
||||||
|
|
||||||
// if needed remove oldest one
|
// if needed remove oldest one
|
||||||
if($allowed == -1) return;
|
if($allowed == -1) { return; }
|
||||||
if($entries > $allowed) {
|
if($entries > $allowed) {
|
||||||
// TODO: Make these queries better
|
// TODO: Make these queries better
|
||||||
/*
|
/*
|
||||||
|
@ -7,6 +7,11 @@
|
|||||||
class Tag_HistoryTheme extends Themelet {
|
class Tag_HistoryTheme extends Themelet {
|
||||||
var $messages = array();
|
var $messages = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param int $image_id
|
||||||
|
* @param array $history
|
||||||
|
*/
|
||||||
public function display_history_page(Page $page, /*int*/ $image_id, /*array*/ $history) {
|
public function display_history_page(Page $page, /*int*/ $image_id, /*array*/ $history) {
|
||||||
global $user;
|
global $user;
|
||||||
$start_string = "
|
$start_string = "
|
||||||
@ -57,6 +62,11 @@ class Tag_HistoryTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Tag History", $history_html, "main", 10));
|
$page->add_block(new Block("Tag History", $history_html, "main", 10));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param array $history
|
||||||
|
* @param int $page_number
|
||||||
|
*/
|
||||||
public function display_global_page(Page $page, /*array*/ $history, /*int*/ $page_number) {
|
public function display_global_page(Page $page, /*array*/ $history, /*int*/ $page_number) {
|
||||||
$start_string = "
|
$start_string = "
|
||||||
<div style='text-align: left'>
|
<div style='text-align: left'>
|
||||||
@ -105,8 +115,10 @@ class Tag_HistoryTheme extends Themelet {
|
|||||||
$page->add_block(new Block("Navigation", $nav, "left"));
|
$page->add_block(new Block("Navigation", $nav, "left"));
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Add a section to the admin page.
|
* Add a section to the admin page.
|
||||||
|
*
|
||||||
|
* @param string $validation_msg
|
||||||
*/
|
*/
|
||||||
public function display_admin_block(/*string*/ $validation_msg='') {
|
public function display_admin_block(/*string*/ $validation_msg='') {
|
||||||
global $page;
|
global $page;
|
||||||
@ -141,7 +153,11 @@ class Tag_HistoryTheme extends Themelet {
|
|||||||
$html = implode($this->messages, "\n");
|
$html = implode($this->messages, "\n");
|
||||||
$page->add_block(new Block("Bulk Revert Results", $html));
|
$page->add_block(new Block("Bulk Revert Results", $html));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $title
|
||||||
|
* @param string $body
|
||||||
|
*/
|
||||||
public function add_status(/*string*/ $title, /*string*/ $body) {
|
public function add_status(/*string*/ $title, /*string*/ $body) {
|
||||||
$this->messages[] = '<p><b>'. $title .'</b><br>'. $body .'</p>';
|
$this->messages[] = '<p><b>'. $title .'</b><br>'. $body .'</p>';
|
||||||
}
|
}
|
||||||
|
@ -121,6 +121,10 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
// misc {{{
|
// misc {{{
|
||||||
|
/**
|
||||||
|
* @param string $tag
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function tag_link(/*string*/ $tag) {
|
private function tag_link(/*string*/ $tag) {
|
||||||
$u_tag = url_escape($tag);
|
$u_tag = url_escape($tag);
|
||||||
return make_link("post/list/$u_tag/1");
|
return make_link("post/list/$u_tag/1");
|
||||||
@ -129,7 +133,8 @@ class TagList extends Extension {
|
|||||||
/**
|
/**
|
||||||
* Get the minimum number of times a tag needs to be used
|
* Get the minimum number of times a tag needs to be used
|
||||||
* in order to be considered in the tag list.
|
* in order to be considered in the tag list.
|
||||||
* @retval int
|
*
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
private function get_tags_min() {
|
private function get_tags_min() {
|
||||||
if(isset($_GET['mincount'])) {
|
if(isset($_GET['mincount'])) {
|
||||||
@ -141,6 +146,9 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function get_starts_with() {
|
private function get_starts_with() {
|
||||||
global $config;
|
global $config;
|
||||||
if(isset($_GET['starts_with'])) {
|
if(isset($_GET['starts_with'])) {
|
||||||
@ -156,6 +164,9 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_az() {
|
private function build_az() {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
@ -179,6 +190,10 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
// maps {{{
|
// maps {{{
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_navigation() {
|
private function build_navigation() {
|
||||||
$h_index = "<a href='".make_link()."'>Index</a>";
|
$h_index = "<a href='".make_link()."'>Index</a>";
|
||||||
$h_map = "<a href='".make_link("tags/map")."'>Map</a>";
|
$h_map = "<a href='".make_link("tags/map")."'>Map</a>";
|
||||||
@ -189,6 +204,9 @@ class TagList extends Extension {
|
|||||||
return "$h_index<br> <br>$h_map<br>$h_alphabetic<br>$h_popularity<br>$h_cats<br> <br>$h_all";
|
return "$h_index<br> <br>$h_map<br>$h_alphabetic<br>$h_popularity<br>$h_cats<br> <br>$h_all";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_tag_map() {
|
private function build_tag_map() {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
|
|
||||||
@ -226,6 +244,9 @@ class TagList extends Extension {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_tag_alphabetic() {
|
private function build_tag_alphabetic() {
|
||||||
global $config, $database;
|
global $config, $database;
|
||||||
|
|
||||||
@ -279,6 +300,9 @@ class TagList extends Extension {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_tag_popularity() {
|
private function build_tag_popularity() {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
@ -318,6 +342,9 @@ class TagList extends Extension {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
private function build_tag_list() {
|
private function build_tag_list() {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
@ -344,9 +371,12 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
// blocks {{{
|
// blocks {{{
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
|
*/
|
||||||
private function add_related_block(Page $page, Image $image) {
|
private function add_related_block(Page $page, Image $image) {
|
||||||
global $database;
|
global $database, $config;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$query = "
|
$query = "
|
||||||
SELECT t3.tag AS tag, t3.count AS calc_count, it3.tag_id
|
SELECT t3.tag AS tag, t3.count AS calc_count, it3.tag_id
|
||||||
@ -376,9 +406,12 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
|
*/
|
||||||
private function add_split_tags_block(Page $page, Image $image) {
|
private function add_split_tags_block(Page $page, Image $image) {
|
||||||
global $database;
|
global $database;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$query = "
|
$query = "
|
||||||
SELECT tags.tag, tags.count as calc_count
|
SELECT tags.tag, tags.count as calc_count
|
||||||
@ -395,9 +428,12 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param Image $image
|
||||||
|
*/
|
||||||
private function add_tags_block(Page $page, Image $image) {
|
private function add_tags_block(Page $page, Image $image) {
|
||||||
global $database;
|
global $database;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$query = "
|
$query = "
|
||||||
SELECT tags.tag, tags.count as calc_count
|
SELECT tags.tag, tags.count as calc_count
|
||||||
@ -414,9 +450,11 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
*/
|
||||||
private function add_popular_block(Page $page) {
|
private function add_popular_block(Page $page) {
|
||||||
global $database;
|
global $database, $config;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$tags = $database->cache->get("popular_tags");
|
$tags = $database->cache->get("popular_tags");
|
||||||
if(empty($tags)) {
|
if(empty($tags)) {
|
||||||
@ -437,9 +475,12 @@ class TagList extends Extension {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Page $page
|
||||||
|
* @param string[] $search
|
||||||
|
*/
|
||||||
private function add_refine_block(Page $page, /*array(string)*/ $search) {
|
private function add_refine_block(Page $page, /*array(string)*/ $search) {
|
||||||
global $database;
|
global $database, $config;
|
||||||
global $config;
|
|
||||||
|
|
||||||
$wild_tags = Tag::explode($search);
|
$wild_tags = Tag::explode($search);
|
||||||
$str_search = Tag::implode($search);
|
$str_search = Tag::implode($search);
|
||||||
|
@ -1,13 +1,23 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
class TagListTheme extends Themelet {
|
class TagListTheme extends Themelet {
|
||||||
var $heading = "";
|
/** @var string */
|
||||||
var $list = "";
|
public $heading = "";
|
||||||
|
/** @var string|string[] */
|
||||||
|
public $list = "";
|
||||||
|
|
||||||
|
public $navigation;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $text
|
||||||
|
*/
|
||||||
public function set_heading($text) {
|
public function set_heading($text) {
|
||||||
$this->heading = $text;
|
$this->heading = $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string|string[] $list
|
||||||
|
*/
|
||||||
public function set_tag_list($list) {
|
public function set_tag_list($list) {
|
||||||
$this->list = $list;
|
$this->list = $list;
|
||||||
}
|
}
|
||||||
@ -219,6 +229,11 @@ class TagListTheme extends Themelet {
|
|||||||
return array($category, $display_html);
|
return array($category, $display_html);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $tag
|
||||||
|
* @param string[] $tags
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function ars(/*string*/ $tag, /*array(string)*/ $tags) {
|
protected function ars(/*string*/ $tag, /*array(string)*/ $tags) {
|
||||||
assert(is_array($tags));
|
assert(is_array($tags));
|
||||||
|
|
||||||
@ -234,6 +249,11 @@ class TagListTheme extends Themelet {
|
|||||||
return $html;
|
return $html;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $tags
|
||||||
|
* @param string $tag
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function get_remove_link($tags, $tag) {
|
protected function get_remove_link($tags, $tag) {
|
||||||
if(!in_array($tag, $tags) && !in_array("-$tag", $tags)) {
|
if(!in_array($tag, $tags) && !in_array("-$tag", $tags)) {
|
||||||
return "";
|
return "";
|
||||||
@ -245,6 +265,11 @@ class TagListTheme extends Themelet {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $tags
|
||||||
|
* @param string $tag
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function get_add_link($tags, $tag) {
|
protected function get_add_link($tags, $tag) {
|
||||||
if(in_array($tag, $tags)) {
|
if(in_array($tag, $tags)) {
|
||||||
return "";
|
return "";
|
||||||
@ -256,6 +281,11 @@ class TagListTheme extends Themelet {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array $tags
|
||||||
|
* @param string $tag
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function get_subtract_link($tags, $tag) {
|
protected function get_subtract_link($tags, $tag) {
|
||||||
if(in_array("-$tag", $tags)) {
|
if(in_array("-$tag", $tags)) {
|
||||||
return "";
|
return "";
|
||||||
@ -267,6 +297,10 @@ class TagListTheme extends Themelet {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param string $tag
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
protected function tag_link($tag) {
|
protected function tag_link($tag) {
|
||||||
$u_tag = url_escape($tag);
|
$u_tag = url_escape($tag);
|
||||||
return make_link("post/list/$u_tag/1");
|
return make_link("post/list/$u_tag/1");
|
||||||
|
@ -132,10 +132,13 @@ class Tips extends Extension {
|
|||||||
$this->theme->showAll($url, $tips);
|
$this->theme->showAll($url, $tips);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $tipID
|
||||||
|
*/
|
||||||
private function setStatus($tipID) {
|
private function setStatus($tipID) {
|
||||||
global $database;
|
global $database;
|
||||||
|
|
||||||
$tip = $database->get_row("SELECT * FROM tips WHERE id = ? ", array($tipID));
|
$tip = $database->get_row("SELECT * FROM tips WHERE id = ? ", array(int_escape($tipID)));
|
||||||
|
|
||||||
if (bool_escape($tip['enable'])) {
|
if (bool_escape($tip['enable'])) {
|
||||||
$enable = "N";
|
$enable = "N";
|
||||||
@ -143,12 +146,15 @@ class Tips extends Extension {
|
|||||||
$enable = "Y";
|
$enable = "Y";
|
||||||
}
|
}
|
||||||
|
|
||||||
$database->execute("UPDATE tips SET enable = ? WHERE id = ?", array ($enable, $tipID));
|
$database->execute("UPDATE tips SET enable = ? WHERE id = ?", array ($enable, int_escape($tipID)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param int $tipID
|
||||||
|
*/
|
||||||
private function deleteTip($tipID) {
|
private function deleteTip($tipID) {
|
||||||
global $database;
|
global $database;
|
||||||
$database->execute("DELETE FROM tips WHERE id = ?", array($tipID));
|
$database->execute("DELETE FROM tips WHERE id = ?", array(int_escape($tipID)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,24 +0,0 @@
|
|||||||
<?php
|
|
||||||
/*
|
|
||||||
* Name: Tweet!
|
|
||||||
* Author: Shish <webmaster@shishnet.org>
|
|
||||||
* Link: http://code.shishnet.org/shimmie2/
|
|
||||||
* License: GPLv2
|
|
||||||
* Description: Show a twitter feed with the Sea of Clouds script
|
|
||||||
*/
|
|
||||||
|
|
||||||
class TwitterSoc extends Extension {
|
|
||||||
public function onPostListBuilding(PostListBuildingEvent $event) {
|
|
||||||
global $config, $page;
|
|
||||||
if(strlen($config->get_string("twitter_soc_username")) > 0) {
|
|
||||||
$this->theme->display_feed($page, $config->get_string("twitter_soc_username"));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public function onSetupBuilding(SetupBuildingEvent $event) {
|
|
||||||
$sb = new SetupBlock("Tweet!");
|
|
||||||
$sb->add_text_option("twitter_soc_username", "Username ");
|
|
||||||
$event->panel->add_block($sb);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user