Laravel voting system
I have written a voting class in Laravel. It uses the voting sites API to check if the user has voted today. A user is only allowed to vote once every day.
All votes reset at midnight (i.e. 12:00 AM Chicago time) and I create a cookie to not bother wasting a curl response till then, so the cookie expires when a new vote is allowed.
The API returns response codes: 2 means the user hasn't voted for them in the past 24 hours, and 3 means they have voted for them in the past 24 hours. Just think of 2 as 0 and 3 as 1 in a false/true situation.
The reason I am asking this question is I don't think I am handling cookies the best way I can. Could anyone advise a better way to create them? I wasn't sure how to do it without a response, as Laravel says you have to send it with a response.
If the user needs to vote, they are sent to the voting page. For now I've just put a temp link as http://need2vote.com until I finish the class.
<?php
namespace AppHttpControllers;
use AppHttpControllersController;
use Auth;
use Redirect;
use IlluminateSupportFacadesRoute;
use Cookie;
use IlluminateHttpRequest;
use Config;
class VotingController extends Controller
{
protected $pageUsername;
protected $requestTimeout;
protected $usingCloudflare;
protected $apiUrl;
public function __construct()
{
$this->pageUsername = Config::get('voting.username');
$this->requestTimeout = Config::get('voting.timeout');
$this->usingCloudflare = true;
$this->apiUrl = Config::get('voting.api_url');
}
public function checkVote(Request $request)
{
if (Config::get('voting.enabled') == false) {
return;
}
if ($this->isVoteCookieSet()) {
return;
}
$urlRequest = $this->apiUrl . 'user=' . $this->pageUsername . '&ip=' . $request->ip();
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
if ($result == 3) {
$this->redirectToVote();
}
else {
$this->setVoteCookie();
}
}
private function makeCurlRequest($url, $timeout)
{
if (function_exists('curl_version'))
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($curl, CURLOPT_TIMEOUT, $timeout);
$requestData = curl_exec($curl);
curl_close($curl);
}
else
{
$requestData = stream_context_create(array('http' => array('timeout' => $timeout)));
return file_get_contents($url, 0, $requestData);
}
return $requestData;
}
public function redirectToVote() {
header('Location: http://needtovote.com');
exit();
}
private function setVoteCookie() {
$rankingsResetTime = $this->getVoteResetTime();
setcookie('vote_timestamp', $rankingsResetTime, $rankingsResetTime);
}
private function isVoteCookieSet() {
if (isset($_COOKIE['voting_timestamp'])) {
if ($_COOKIE['voting_timestamp'] == $this->getVoteResetTime()) {
return true;
}
else{
setcookie('voting_timestamp', '');
return false;
}
}
return false;
}
private function getVoteResetTime() {
$serverDefaultTime = date_default_timezone_get();
date_default_timezone_set('America/Chicago');
$rankingsResetTime = mktime(0, 0, 0, date('n'), date('j') + 1);
date_default_timezone_set($serverDefaultTime);
return $rankingsResetTime;
}
}
php laravel controller curl
bumped to the homepage by Community♦ yesterday
This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
add a comment |
I have written a voting class in Laravel. It uses the voting sites API to check if the user has voted today. A user is only allowed to vote once every day.
All votes reset at midnight (i.e. 12:00 AM Chicago time) and I create a cookie to not bother wasting a curl response till then, so the cookie expires when a new vote is allowed.
The API returns response codes: 2 means the user hasn't voted for them in the past 24 hours, and 3 means they have voted for them in the past 24 hours. Just think of 2 as 0 and 3 as 1 in a false/true situation.
The reason I am asking this question is I don't think I am handling cookies the best way I can. Could anyone advise a better way to create them? I wasn't sure how to do it without a response, as Laravel says you have to send it with a response.
If the user needs to vote, they are sent to the voting page. For now I've just put a temp link as http://need2vote.com until I finish the class.
<?php
namespace AppHttpControllers;
use AppHttpControllersController;
use Auth;
use Redirect;
use IlluminateSupportFacadesRoute;
use Cookie;
use IlluminateHttpRequest;
use Config;
class VotingController extends Controller
{
protected $pageUsername;
protected $requestTimeout;
protected $usingCloudflare;
protected $apiUrl;
public function __construct()
{
$this->pageUsername = Config::get('voting.username');
$this->requestTimeout = Config::get('voting.timeout');
$this->usingCloudflare = true;
$this->apiUrl = Config::get('voting.api_url');
}
public function checkVote(Request $request)
{
if (Config::get('voting.enabled') == false) {
return;
}
if ($this->isVoteCookieSet()) {
return;
}
$urlRequest = $this->apiUrl . 'user=' . $this->pageUsername . '&ip=' . $request->ip();
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
if ($result == 3) {
$this->redirectToVote();
}
else {
$this->setVoteCookie();
}
}
private function makeCurlRequest($url, $timeout)
{
if (function_exists('curl_version'))
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($curl, CURLOPT_TIMEOUT, $timeout);
$requestData = curl_exec($curl);
curl_close($curl);
}
else
{
$requestData = stream_context_create(array('http' => array('timeout' => $timeout)));
return file_get_contents($url, 0, $requestData);
}
return $requestData;
}
public function redirectToVote() {
header('Location: http://needtovote.com');
exit();
}
private function setVoteCookie() {
$rankingsResetTime = $this->getVoteResetTime();
setcookie('vote_timestamp', $rankingsResetTime, $rankingsResetTime);
}
private function isVoteCookieSet() {
if (isset($_COOKIE['voting_timestamp'])) {
if ($_COOKIE['voting_timestamp'] == $this->getVoteResetTime()) {
return true;
}
else{
setcookie('voting_timestamp', '');
return false;
}
}
return false;
}
private function getVoteResetTime() {
$serverDefaultTime = date_default_timezone_get();
date_default_timezone_set('America/Chicago');
$rankingsResetTime = mktime(0, 0, 0, date('n'), date('j') + 1);
date_default_timezone_set($serverDefaultTime);
return $rankingsResetTime;
}
}
php laravel controller curl
bumped to the homepage by Community♦ yesterday
This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
You might provide more information about who's responsible for settingvoting.usernameand so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.
– Quuxplusone
Feb 1 '18 at 1:55
add a comment |
I have written a voting class in Laravel. It uses the voting sites API to check if the user has voted today. A user is only allowed to vote once every day.
All votes reset at midnight (i.e. 12:00 AM Chicago time) and I create a cookie to not bother wasting a curl response till then, so the cookie expires when a new vote is allowed.
The API returns response codes: 2 means the user hasn't voted for them in the past 24 hours, and 3 means they have voted for them in the past 24 hours. Just think of 2 as 0 and 3 as 1 in a false/true situation.
The reason I am asking this question is I don't think I am handling cookies the best way I can. Could anyone advise a better way to create them? I wasn't sure how to do it without a response, as Laravel says you have to send it with a response.
If the user needs to vote, they are sent to the voting page. For now I've just put a temp link as http://need2vote.com until I finish the class.
<?php
namespace AppHttpControllers;
use AppHttpControllersController;
use Auth;
use Redirect;
use IlluminateSupportFacadesRoute;
use Cookie;
use IlluminateHttpRequest;
use Config;
class VotingController extends Controller
{
protected $pageUsername;
protected $requestTimeout;
protected $usingCloudflare;
protected $apiUrl;
public function __construct()
{
$this->pageUsername = Config::get('voting.username');
$this->requestTimeout = Config::get('voting.timeout');
$this->usingCloudflare = true;
$this->apiUrl = Config::get('voting.api_url');
}
public function checkVote(Request $request)
{
if (Config::get('voting.enabled') == false) {
return;
}
if ($this->isVoteCookieSet()) {
return;
}
$urlRequest = $this->apiUrl . 'user=' . $this->pageUsername . '&ip=' . $request->ip();
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
if ($result == 3) {
$this->redirectToVote();
}
else {
$this->setVoteCookie();
}
}
private function makeCurlRequest($url, $timeout)
{
if (function_exists('curl_version'))
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($curl, CURLOPT_TIMEOUT, $timeout);
$requestData = curl_exec($curl);
curl_close($curl);
}
else
{
$requestData = stream_context_create(array('http' => array('timeout' => $timeout)));
return file_get_contents($url, 0, $requestData);
}
return $requestData;
}
public function redirectToVote() {
header('Location: http://needtovote.com');
exit();
}
private function setVoteCookie() {
$rankingsResetTime = $this->getVoteResetTime();
setcookie('vote_timestamp', $rankingsResetTime, $rankingsResetTime);
}
private function isVoteCookieSet() {
if (isset($_COOKIE['voting_timestamp'])) {
if ($_COOKIE['voting_timestamp'] == $this->getVoteResetTime()) {
return true;
}
else{
setcookie('voting_timestamp', '');
return false;
}
}
return false;
}
private function getVoteResetTime() {
$serverDefaultTime = date_default_timezone_get();
date_default_timezone_set('America/Chicago');
$rankingsResetTime = mktime(0, 0, 0, date('n'), date('j') + 1);
date_default_timezone_set($serverDefaultTime);
return $rankingsResetTime;
}
}
php laravel controller curl
I have written a voting class in Laravel. It uses the voting sites API to check if the user has voted today. A user is only allowed to vote once every day.
All votes reset at midnight (i.e. 12:00 AM Chicago time) and I create a cookie to not bother wasting a curl response till then, so the cookie expires when a new vote is allowed.
The API returns response codes: 2 means the user hasn't voted for them in the past 24 hours, and 3 means they have voted for them in the past 24 hours. Just think of 2 as 0 and 3 as 1 in a false/true situation.
The reason I am asking this question is I don't think I am handling cookies the best way I can. Could anyone advise a better way to create them? I wasn't sure how to do it without a response, as Laravel says you have to send it with a response.
If the user needs to vote, they are sent to the voting page. For now I've just put a temp link as http://need2vote.com until I finish the class.
<?php
namespace AppHttpControllers;
use AppHttpControllersController;
use Auth;
use Redirect;
use IlluminateSupportFacadesRoute;
use Cookie;
use IlluminateHttpRequest;
use Config;
class VotingController extends Controller
{
protected $pageUsername;
protected $requestTimeout;
protected $usingCloudflare;
protected $apiUrl;
public function __construct()
{
$this->pageUsername = Config::get('voting.username');
$this->requestTimeout = Config::get('voting.timeout');
$this->usingCloudflare = true;
$this->apiUrl = Config::get('voting.api_url');
}
public function checkVote(Request $request)
{
if (Config::get('voting.enabled') == false) {
return;
}
if ($this->isVoteCookieSet()) {
return;
}
$urlRequest = $this->apiUrl . 'user=' . $this->pageUsername . '&ip=' . $request->ip();
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
if ($result == 3) {
$this->redirectToVote();
}
else {
$this->setVoteCookie();
}
}
private function makeCurlRequest($url, $timeout)
{
if (function_exists('curl_version'))
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($curl, CURLOPT_TIMEOUT, $timeout);
$requestData = curl_exec($curl);
curl_close($curl);
}
else
{
$requestData = stream_context_create(array('http' => array('timeout' => $timeout)));
return file_get_contents($url, 0, $requestData);
}
return $requestData;
}
public function redirectToVote() {
header('Location: http://needtovote.com');
exit();
}
private function setVoteCookie() {
$rankingsResetTime = $this->getVoteResetTime();
setcookie('vote_timestamp', $rankingsResetTime, $rankingsResetTime);
}
private function isVoteCookieSet() {
if (isset($_COOKIE['voting_timestamp'])) {
if ($_COOKIE['voting_timestamp'] == $this->getVoteResetTime()) {
return true;
}
else{
setcookie('voting_timestamp', '');
return false;
}
}
return false;
}
private function getVoteResetTime() {
$serverDefaultTime = date_default_timezone_get();
date_default_timezone_set('America/Chicago');
$rankingsResetTime = mktime(0, 0, 0, date('n'), date('j') + 1);
date_default_timezone_set($serverDefaultTime);
return $rankingsResetTime;
}
}
php laravel controller curl
php laravel controller curl
edited Feb 8 '18 at 22:06
Sᴀᴍ Onᴇᴌᴀ
8,42261854
8,42261854
asked Feb 1 '18 at 1:29
begoing
191
191
bumped to the homepage by Community♦ yesterday
This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
bumped to the homepage by Community♦ yesterday
This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
You might provide more information about who's responsible for settingvoting.usernameand so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.
– Quuxplusone
Feb 1 '18 at 1:55
add a comment |
You might provide more information about who's responsible for settingvoting.usernameand so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.
– Quuxplusone
Feb 1 '18 at 1:55
You might provide more information about who's responsible for setting
voting.username and so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.– Quuxplusone
Feb 1 '18 at 1:55
You might provide more information about who's responsible for setting
voting.username and so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.– Quuxplusone
Feb 1 '18 at 1:55
add a comment |
1 Answer
1
active
oldest
votes
The Question
Could anyone advise a better way to create [cookies]?
Like your code already uses, setcookie() is the traditional way of setting cookies. And yes, since the cookie data is sent in a header, there must be a response, otherwise the browser/user won't really be able to receive the cookie.
General Feedback
Passing instance/member variables to method
Why pass $this->timeout to makeCurlRequest from the checkVote method? If the method was called outside this class (and the scope of the method changed to protected for sub-classes or public for anywhere else in the code) then it might make sense to accept that parameter.
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
Since that method is not static, it could simply refer to $this->requestTimeout instead of accepting the parameter for it.
Misleading Method Name
The method makeCurlRequest appears to check if the curl function curl_version() exists and then either makes a cURL request or utilizes file_get_contents(). Thus the method might not always make a cURL request and a better name might be makeRequest. The code in the block when the curl_version() function does exist could be moved to a new method called makeCurlRequest.
return from makeCurlRequest()
The method makeCurlRequest has two return statements. One is in the else block, and the other is at the end of the method - i.e. return $requestData;. That variable,$requestData, appears to be the response from the API when the curl_version() function exists (and thus the cURL request is made), yet in the else block, $requestData is assigned a resource from stream_context_create(). While this code likely functions correctly, it could be confusing to a teammate who had to update it. A more appropriate name for the return value from the call to stream_context_create() might be something like $streamContext. Then it might be simpler to either assign the return value from the call to file_get_contents() to $requestData and utilize the return of that variable at the end of the method, or when making the curl request, return the response at the end of that block.
Redundant return false
In isVoteCookieSet() There is an else block to the nested if statement that contains return false;. That could be removed, since the last line of the method does the same thing.
Constants for Response codes
It would be wise to define (class) constants for the response codes, like the ones below. While there currently appears to only be one place in your code where that value appears, there may arise a need to have it appear in other logic and thus it would be useful to reuse the constant(s). Then if the value would ever need to be updated (e.g. if the API ever changes) then it can be updated in your code in one spot.
const RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS = 3;
const RESPONSE_VOTE_NOT_PLACED_IN_PAST_24_HOURS = 2;
That way, the code lines like below:
if ($result == 3) {
Can be updated like this:
if ($result == self::RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS) {
Which would hopefully allow somebody else reading your code to have a better idea of what that logic means. Though if those names are too long, feel free to shorten them.
add a comment |
Your Answer
StackExchange.ifUsing("editor", function () {
return StackExchange.using("mathjaxEditing", function () {
StackExchange.MarkdownEditor.creationCallbacks.add(function (editor, postfix) {
StackExchange.mathjaxEditing.prepareWmdForMathJax(editor, postfix, [["\$", "\$"]]);
});
});
}, "mathjax-editing");
StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "196"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: false,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: null,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f186489%2flaravel-voting-system%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
The Question
Could anyone advise a better way to create [cookies]?
Like your code already uses, setcookie() is the traditional way of setting cookies. And yes, since the cookie data is sent in a header, there must be a response, otherwise the browser/user won't really be able to receive the cookie.
General Feedback
Passing instance/member variables to method
Why pass $this->timeout to makeCurlRequest from the checkVote method? If the method was called outside this class (and the scope of the method changed to protected for sub-classes or public for anywhere else in the code) then it might make sense to accept that parameter.
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
Since that method is not static, it could simply refer to $this->requestTimeout instead of accepting the parameter for it.
Misleading Method Name
The method makeCurlRequest appears to check if the curl function curl_version() exists and then either makes a cURL request or utilizes file_get_contents(). Thus the method might not always make a cURL request and a better name might be makeRequest. The code in the block when the curl_version() function does exist could be moved to a new method called makeCurlRequest.
return from makeCurlRequest()
The method makeCurlRequest has two return statements. One is in the else block, and the other is at the end of the method - i.e. return $requestData;. That variable,$requestData, appears to be the response from the API when the curl_version() function exists (and thus the cURL request is made), yet in the else block, $requestData is assigned a resource from stream_context_create(). While this code likely functions correctly, it could be confusing to a teammate who had to update it. A more appropriate name for the return value from the call to stream_context_create() might be something like $streamContext. Then it might be simpler to either assign the return value from the call to file_get_contents() to $requestData and utilize the return of that variable at the end of the method, or when making the curl request, return the response at the end of that block.
Redundant return false
In isVoteCookieSet() There is an else block to the nested if statement that contains return false;. That could be removed, since the last line of the method does the same thing.
Constants for Response codes
It would be wise to define (class) constants for the response codes, like the ones below. While there currently appears to only be one place in your code where that value appears, there may arise a need to have it appear in other logic and thus it would be useful to reuse the constant(s). Then if the value would ever need to be updated (e.g. if the API ever changes) then it can be updated in your code in one spot.
const RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS = 3;
const RESPONSE_VOTE_NOT_PLACED_IN_PAST_24_HOURS = 2;
That way, the code lines like below:
if ($result == 3) {
Can be updated like this:
if ($result == self::RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS) {
Which would hopefully allow somebody else reading your code to have a better idea of what that logic means. Though if those names are too long, feel free to shorten them.
add a comment |
The Question
Could anyone advise a better way to create [cookies]?
Like your code already uses, setcookie() is the traditional way of setting cookies. And yes, since the cookie data is sent in a header, there must be a response, otherwise the browser/user won't really be able to receive the cookie.
General Feedback
Passing instance/member variables to method
Why pass $this->timeout to makeCurlRequest from the checkVote method? If the method was called outside this class (and the scope of the method changed to protected for sub-classes or public for anywhere else in the code) then it might make sense to accept that parameter.
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
Since that method is not static, it could simply refer to $this->requestTimeout instead of accepting the parameter for it.
Misleading Method Name
The method makeCurlRequest appears to check if the curl function curl_version() exists and then either makes a cURL request or utilizes file_get_contents(). Thus the method might not always make a cURL request and a better name might be makeRequest. The code in the block when the curl_version() function does exist could be moved to a new method called makeCurlRequest.
return from makeCurlRequest()
The method makeCurlRequest has two return statements. One is in the else block, and the other is at the end of the method - i.e. return $requestData;. That variable,$requestData, appears to be the response from the API when the curl_version() function exists (and thus the cURL request is made), yet in the else block, $requestData is assigned a resource from stream_context_create(). While this code likely functions correctly, it could be confusing to a teammate who had to update it. A more appropriate name for the return value from the call to stream_context_create() might be something like $streamContext. Then it might be simpler to either assign the return value from the call to file_get_contents() to $requestData and utilize the return of that variable at the end of the method, or when making the curl request, return the response at the end of that block.
Redundant return false
In isVoteCookieSet() There is an else block to the nested if statement that contains return false;. That could be removed, since the last line of the method does the same thing.
Constants for Response codes
It would be wise to define (class) constants for the response codes, like the ones below. While there currently appears to only be one place in your code where that value appears, there may arise a need to have it appear in other logic and thus it would be useful to reuse the constant(s). Then if the value would ever need to be updated (e.g. if the API ever changes) then it can be updated in your code in one spot.
const RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS = 3;
const RESPONSE_VOTE_NOT_PLACED_IN_PAST_24_HOURS = 2;
That way, the code lines like below:
if ($result == 3) {
Can be updated like this:
if ($result == self::RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS) {
Which would hopefully allow somebody else reading your code to have a better idea of what that logic means. Though if those names are too long, feel free to shorten them.
add a comment |
The Question
Could anyone advise a better way to create [cookies]?
Like your code already uses, setcookie() is the traditional way of setting cookies. And yes, since the cookie data is sent in a header, there must be a response, otherwise the browser/user won't really be able to receive the cookie.
General Feedback
Passing instance/member variables to method
Why pass $this->timeout to makeCurlRequest from the checkVote method? If the method was called outside this class (and the scope of the method changed to protected for sub-classes or public for anywhere else in the code) then it might make sense to accept that parameter.
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
Since that method is not static, it could simply refer to $this->requestTimeout instead of accepting the parameter for it.
Misleading Method Name
The method makeCurlRequest appears to check if the curl function curl_version() exists and then either makes a cURL request or utilizes file_get_contents(). Thus the method might not always make a cURL request and a better name might be makeRequest. The code in the block when the curl_version() function does exist could be moved to a new method called makeCurlRequest.
return from makeCurlRequest()
The method makeCurlRequest has two return statements. One is in the else block, and the other is at the end of the method - i.e. return $requestData;. That variable,$requestData, appears to be the response from the API when the curl_version() function exists (and thus the cURL request is made), yet in the else block, $requestData is assigned a resource from stream_context_create(). While this code likely functions correctly, it could be confusing to a teammate who had to update it. A more appropriate name for the return value from the call to stream_context_create() might be something like $streamContext. Then it might be simpler to either assign the return value from the call to file_get_contents() to $requestData and utilize the return of that variable at the end of the method, or when making the curl request, return the response at the end of that block.
Redundant return false
In isVoteCookieSet() There is an else block to the nested if statement that contains return false;. That could be removed, since the last line of the method does the same thing.
Constants for Response codes
It would be wise to define (class) constants for the response codes, like the ones below. While there currently appears to only be one place in your code where that value appears, there may arise a need to have it appear in other logic and thus it would be useful to reuse the constant(s). Then if the value would ever need to be updated (e.g. if the API ever changes) then it can be updated in your code in one spot.
const RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS = 3;
const RESPONSE_VOTE_NOT_PLACED_IN_PAST_24_HOURS = 2;
That way, the code lines like below:
if ($result == 3) {
Can be updated like this:
if ($result == self::RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS) {
Which would hopefully allow somebody else reading your code to have a better idea of what that logic means. Though if those names are too long, feel free to shorten them.
The Question
Could anyone advise a better way to create [cookies]?
Like your code already uses, setcookie() is the traditional way of setting cookies. And yes, since the cookie data is sent in a header, there must be a response, otherwise the browser/user won't really be able to receive the cookie.
General Feedback
Passing instance/member variables to method
Why pass $this->timeout to makeCurlRequest from the checkVote method? If the method was called outside this class (and the scope of the method changed to protected for sub-classes or public for anywhere else in the code) then it might make sense to accept that parameter.
$result = $this->makeCurlRequest($urlRequest, $this->requestTimeout);
Since that method is not static, it could simply refer to $this->requestTimeout instead of accepting the parameter for it.
Misleading Method Name
The method makeCurlRequest appears to check if the curl function curl_version() exists and then either makes a cURL request or utilizes file_get_contents(). Thus the method might not always make a cURL request and a better name might be makeRequest. The code in the block when the curl_version() function does exist could be moved to a new method called makeCurlRequest.
return from makeCurlRequest()
The method makeCurlRequest has two return statements. One is in the else block, and the other is at the end of the method - i.e. return $requestData;. That variable,$requestData, appears to be the response from the API when the curl_version() function exists (and thus the cURL request is made), yet in the else block, $requestData is assigned a resource from stream_context_create(). While this code likely functions correctly, it could be confusing to a teammate who had to update it. A more appropriate name for the return value from the call to stream_context_create() might be something like $streamContext. Then it might be simpler to either assign the return value from the call to file_get_contents() to $requestData and utilize the return of that variable at the end of the method, or when making the curl request, return the response at the end of that block.
Redundant return false
In isVoteCookieSet() There is an else block to the nested if statement that contains return false;. That could be removed, since the last line of the method does the same thing.
Constants for Response codes
It would be wise to define (class) constants for the response codes, like the ones below. While there currently appears to only be one place in your code where that value appears, there may arise a need to have it appear in other logic and thus it would be useful to reuse the constant(s). Then if the value would ever need to be updated (e.g. if the API ever changes) then it can be updated in your code in one spot.
const RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS = 3;
const RESPONSE_VOTE_NOT_PLACED_IN_PAST_24_HOURS = 2;
That way, the code lines like below:
if ($result == 3) {
Can be updated like this:
if ($result == self::RESPONSE_VOTE_PLACED_IN_PAST_24_HOURS) {
Which would hopefully allow somebody else reading your code to have a better idea of what that logic means. Though if those names are too long, feel free to shorten them.
edited Feb 9 '18 at 6:25
answered Feb 8 '18 at 21:43
Sᴀᴍ Onᴇᴌᴀ
8,42261854
8,42261854
add a comment |
add a comment |
Thanks for contributing an answer to Code Review Stack Exchange!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
Use MathJax to format equations. MathJax reference.
To learn more, see our tips on writing great answers.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f186489%2flaravel-voting-system%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
You might provide more information about who's responsible for setting
voting.usernameand so on. If those values come from the browser client (via query parameters or cookie values), then it's super easy for anyone to vote as many times as they want. Also, do you want users to be able to vote multiple times by clearing their cookies in between, or not? This will affect how you use cookies in your design.– Quuxplusone
Feb 1 '18 at 1:55