<?php namespace HashOver;

// Copyright (C) 2010-2021 Jacob Barkdull
// This file is part of HashOver.
//
// HashOver is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// HashOver is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with HashOver. If not, see <http://www.gnu.org/licenses/>.
//
//--------------------
//
// Script Description:
//
// This script reads a given comment file, retrieves the like count,
// increases the count by one, then writes the file. Assuming the
// visitor hasn't already liked the given comment before and the
// visitor isn't the comment's original poster.


// Check if request is for JSONP
if (isset ($_GET['jsonp'])) {
// If so, setup HashOver for JavaScript
require ('javascript-setup.php');
} else {
// If not, setup HashOver for JSON
require ('json-setup.php');
}

// Sets cookie indicating what comment was liked
function set_like (&$hashover, $like_hash, $set, &$likes)
{
// Set cookie
$hashover->cookies->set ($like_hash, $set, mktime (0, 0, 0, 11, 26, 3468));

// Increase like count
$likes = $likes + 1;
}

// Decreases a like/dislike count
function like_decrease (&$likes)
{
if ($likes > 0) {
$likes = $likes - 1;
}
}

// Likes or dislikes a comment
function liker ($action, $like_hash, &$hashover, &$comment)
{
// Get the comment array key based on given action
$key = ($action === 'like') ? 'likes' : 'dislikes';
$set = ($action === 'like') ? 'liked' : 'disliked';

// Get like cookie
$like_cookie = $hashover->cookies->getValue ($like_hash);

// Check that a like/dislike cookie is not already set
if ($like_cookie === '') {
// If so, set the cookie and increase the like/dislike count
set_like ($hashover, $like_hash, $set, $comment[$key]);
} else {
// If not, we're unliking/un-disliking the comment
$opposite_key = ($action === 'like') ? 'dislikes' : 'likes';
$opposite_set = ($action === 'like') ? 'disliked' : 'liked';

// Check if the user has liked the comment
if ($like_cookie === $set) {
// If so, expire the like cookie
$hashover->cookies->expireCookie ($like_hash);

// And decrease the like count
like_decrease ($comment[$key]);
}

// Check if the user has disliked the comment
if ($like_cookie === $opposite_set) {
// If so, expire the dislike cookie
set_like ($hashover, $like_hash, $set, $comment[$key]);

// And decrease the dislike count
like_decrease ($comment[$opposite_key]);
}
}
}

// Returns comment data or error
function get_json_response ($hashover)
{
// Initial JSON data
$data = array ();

// Get comment from POST/GET data
$key = $hashover->setup->getRequest ('comment', null);

// Get action from POST/GET data
$action = $hashover->setup->getRequest ('action', null);

// Return error if we're missing necessary post data
if ($key === null or $action === null) {
return array ('error' => 'No action.');
}

// Sanitize file path
$file = str_replace ('../', '', $key);

// Store references to some long variables
$thread = $hashover->setup->threadName;

// Read comment
$comment = $hashover->thread->data->read ($file, $thread);

// Return error message if failed to read comment
if ($comment === false) {
return array ('error' => 'Failed to read file: "' . $file . '"');
}

// Name of the cookie used to indicate liked comments
$like_hash = md5 ($hashover->setup->domain . $thread . '/' . $key);

// Action: like or dislike
$action = ($action !== 'dislike') ? 'like' : 'dislike';

// Like or dislike the comment
liker ($action, $like_hash, $hashover, $comment);

// Attempt to save file with updated like count
if ($hashover->thread->data->save ($file, $comment, true, $thread)) {
// If successful, add number of likes to JSON
if (isset ($comment['likes'])) {
$data['likes'] = $comment['likes'];
}

// And add dislikes to JSON as well
if (isset ($comment['dislikes'])) {
$data['dislikes'] = $comment['dislikes'];
}
} else {
// If failed, add error message to JSON
$data['error'] = 'Failed to save comment file!';
}

// And return JSON data
return $data;
}

try {
// Instanciate HashOver class
$hashover = new \HashOver ('json');

// Throw exception if requested by remote server
$hashover->setup->refererCheck ();

// Set page URL from POST/GET data
$hashover->setup->setPageURL ('request');

// Initiate comment processing
$hashover->initiate ();

// Get JSON response
$data = get_json_response ($hashover);

// Return JSON or JSONP function call
echo Misc::jsonData ($data);

} catch (
\Exception $error) {
echo Misc::displayException ($error, 'json');
}