Fix bad name. Changed pool to poll.
This commit is contained in:
parent
a6b849e36f
commit
28417bfeeb
|
@ -2,12 +2,12 @@
|
||||||
// Configuración de la base de datos
|
// Configuración de la base de datos
|
||||||
define('DB_TYPE', 'mysql');
|
define('DB_TYPE', 'mysql');
|
||||||
define('DB_HOST', 'localhost');
|
define('DB_HOST', 'localhost');
|
||||||
define('DB_NAME', 'pool');
|
define('DB_NAME', 'poll');
|
||||||
define('DB_USER', 'root');
|
define('DB_USER', 'root');
|
||||||
define('DB_PASS', '');
|
define('DB_PASS', '');
|
||||||
|
|
||||||
// Configuración del sitio
|
// Configuración del sitio
|
||||||
define('SITE_URL', 'https://pool.kj5.top/');
|
define('SITE_URL', 'https://poll.kj5.top/');
|
||||||
|
|
||||||
define('PRIVATE_KEY', 'AerohrejaeLohz2eojai2ba1ohCiegoh');
|
define('PRIVATE_KEY', 'AerohrejaeLohz2eojai2ba1ohCiegoh');
|
||||||
|
|
||||||
|
|
10
database.sql
10
database.sql
|
@ -4,21 +4,21 @@ CREATE TABLE users (
|
||||||
password VARCHAR(255)
|
password VARCHAR(255)
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE pools (
|
CREATE TABLE polls (
|
||||||
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
||||||
title VARCHAR(255)
|
title VARCHAR(255)
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE pool_options (
|
CREATE TABLE poll_options (
|
||||||
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
||||||
value TEXT,
|
value TEXT,
|
||||||
pool_id BIGINT,
|
poll_id BIGINT,
|
||||||
FOREIGN KEY (pool_id) REFERENCES pools(id)
|
FOREIGN KEY (poll_id) REFERENCES polls(id)
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE answers (
|
CREATE TABLE answers (
|
||||||
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
id BIGINT PRIMARY KEY AUTO_INCREMENT,
|
||||||
option_id BIGINT,
|
option_id BIGINT,
|
||||||
create_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
create_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
||||||
FOREIGN KEY (option_id) REFERENCES pool_options(id)
|
FOREIGN KEY (option_id) REFERENCES poll_options(id)
|
||||||
);
|
);
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.pool-options {
|
.poll-options {
|
||||||
display: grid;
|
display: grid;
|
||||||
gap: 10px;
|
gap: 10px;
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,18 +24,18 @@ Un sistema de encuestas con solo 3 opciones a elegir (por si acaso, es posible a
|
||||||
|
|
||||||
** Encuestas (En el hardcode solo se trabajará con la última creada)
|
** Encuestas (En el hardcode solo se trabajará con la última creada)
|
||||||
|
|
||||||
| pools |
|
| polls |
|
||||||
|-------|
|
|-------|
|
||||||
| id |
|
| id |
|
||||||
| title |
|
| title |
|
||||||
|
|
||||||
** Opciones elegibles como respuesta a la encuesta.
|
** Opciones elegibles como respuesta a la encuesta.
|
||||||
|
|
||||||
| pool_options |
|
| poll_options |
|
||||||
|--------------|
|
|--------------|
|
||||||
| id |
|
| id |
|
||||||
| value |
|
| value |
|
||||||
| pool_id |
|
| poll_id |
|
||||||
|
|
||||||
** Votos de los clientes
|
** Votos de los clientes
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,19 @@
|
||||||
|
<?php
|
||||||
|
namespace Controllers\Poll;
|
||||||
|
|
||||||
|
use Libs\HTMX;
|
||||||
|
use Requests\PollRequest;
|
||||||
|
|
||||||
|
class HomeController {
|
||||||
|
/**
|
||||||
|
* handle
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public static function handle(PollRequest $request): void
|
||||||
|
{
|
||||||
|
HTMX::render('Poll', [
|
||||||
|
'poll' => $request->poll
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,27 @@
|
||||||
|
<?php
|
||||||
|
namespace Controllers\Poll;
|
||||||
|
|
||||||
|
use Models\Poll;
|
||||||
|
use Models\PollOption;
|
||||||
|
use Requests\PollCreateRequest;
|
||||||
|
|
||||||
|
class PollCreateController {
|
||||||
|
public static function handle(PollCreateRequest $request): void
|
||||||
|
{
|
||||||
|
$poll = new Poll;
|
||||||
|
$poll->title = $request->post->title;
|
||||||
|
$poll->beginTransaction();
|
||||||
|
$poll->save();
|
||||||
|
|
||||||
|
for($i=1; $i <= 3; $i++) {
|
||||||
|
$option = new PollOption;
|
||||||
|
$option->value = $request->post->{'option'.$i};
|
||||||
|
$option->poll_id = $poll->id;
|
||||||
|
$option->save();
|
||||||
|
}
|
||||||
|
$poll->commit();
|
||||||
|
|
||||||
|
$request->saved = true;
|
||||||
|
PollFormController::handle($request);
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,12 +1,12 @@
|
||||||
<?php
|
<?php
|
||||||
namespace Controllers\Pool;
|
namespace Controllers\Poll;
|
||||||
|
|
||||||
use Libs\HTMX;
|
use Libs\HTMX;
|
||||||
use Requests\UserRequest;
|
use Requests\UserRequest;
|
||||||
|
|
||||||
class PoolFormController {
|
class PollFormController {
|
||||||
public static function handle(UserRequest $request) {
|
public static function handle(UserRequest $request) {
|
||||||
HTMX::render('PoolConfig', [
|
HTMX::render('PollConfig', [
|
||||||
'saved' => $request->saved ?? false
|
'saved' => $request->saved ?? false
|
||||||
]);
|
]);
|
||||||
}
|
}
|
|
@ -0,0 +1,14 @@
|
||||||
|
<?php
|
||||||
|
namespace Controllers\Poll;
|
||||||
|
|
||||||
|
use Libs\HTMX;
|
||||||
|
use Requests\PollRequest;
|
||||||
|
|
||||||
|
class PollResultController {
|
||||||
|
public static function handle(PollRequest $request): void
|
||||||
|
{
|
||||||
|
HTMX::render('Result', [
|
||||||
|
'poll' => $request->poll
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,17 +1,17 @@
|
||||||
<?php
|
<?php
|
||||||
namespace Controllers\Pool;
|
namespace Controllers\Poll;
|
||||||
|
|
||||||
use Models\Answer;
|
use Models\Answer;
|
||||||
use Requests\VoteRequest;
|
use Requests\VoteRequest;
|
||||||
|
|
||||||
class PoolVoteController {
|
class PollVoteController {
|
||||||
public static function handle(VoteRequest $request): void
|
public static function handle(VoteRequest $request): void
|
||||||
{
|
{
|
||||||
if (!$request->pool->isVoted()) {
|
if (!$request->poll->isVoted()) {
|
||||||
$vote = new Answer;
|
$vote = new Answer;
|
||||||
$vote->option_id = $request->option->id;
|
$vote->option_id = $request->option->id;
|
||||||
$vote->save();
|
$vote->save();
|
||||||
$request->pool->createCookie();
|
$request->poll->createCookie();
|
||||||
}
|
}
|
||||||
|
|
||||||
echo '¡Gracias por participar!';
|
echo '¡Gracias por participar!';
|
|
@ -1,19 +0,0 @@
|
||||||
<?php
|
|
||||||
namespace Controllers\Pool;
|
|
||||||
|
|
||||||
use Libs\HTMX;
|
|
||||||
use Requests\PoolRequest;
|
|
||||||
|
|
||||||
class HomeController {
|
|
||||||
/**
|
|
||||||
* handle
|
|
||||||
*
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public static function handle(PoolRequest $request): void
|
|
||||||
{
|
|
||||||
HTMX::render('Pool', [
|
|
||||||
'pool' => $request->pool
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,27 +0,0 @@
|
||||||
<?php
|
|
||||||
namespace Controllers\Pool;
|
|
||||||
|
|
||||||
use Models\Pool;
|
|
||||||
use Models\PoolOption;
|
|
||||||
use Requests\PoolCreateRequest;
|
|
||||||
|
|
||||||
class PoolCreateController {
|
|
||||||
public static function handle(PoolCreateRequest $request): void
|
|
||||||
{
|
|
||||||
$pool = new Pool;
|
|
||||||
$pool->title = $request->post->title;
|
|
||||||
$pool->beginTransaction();
|
|
||||||
$pool->save();
|
|
||||||
|
|
||||||
for($i=1; $i <= 3; $i++) {
|
|
||||||
$option = new PoolOption;
|
|
||||||
$option->value = $request->post->{'option'.$i};
|
|
||||||
$option->pool_id = $pool->id;
|
|
||||||
$option->save();
|
|
||||||
}
|
|
||||||
$pool->commit();
|
|
||||||
|
|
||||||
$request->saved = true;
|
|
||||||
PoolFormController::handle($request);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,14 +0,0 @@
|
||||||
<?php
|
|
||||||
namespace Controllers\Pool;
|
|
||||||
|
|
||||||
use Libs\HTMX;
|
|
||||||
use Requests\PoolRequest;
|
|
||||||
|
|
||||||
class PoolResultController {
|
|
||||||
public static function handle(PoolRequest $request): void
|
|
||||||
{
|
|
||||||
HTMX::render('Result', [
|
|
||||||
'pool' => $request->pool
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -4,7 +4,7 @@ namespace Models;
|
||||||
use Libs\Crypto;
|
use Libs\Crypto;
|
||||||
use Libs\Model;
|
use Libs\Model;
|
||||||
|
|
||||||
class Pool extends Model {
|
class Poll extends Model {
|
||||||
public string $title;
|
public string $title;
|
||||||
protected array $options;
|
protected array $options;
|
||||||
protected int $votes;
|
protected int $votes;
|
||||||
|
@ -20,12 +20,12 @@ class Pool extends Model {
|
||||||
/**
|
/**
|
||||||
* Devuelve las opciones de la encuesta.
|
* Devuelve las opciones de la encuesta.
|
||||||
*
|
*
|
||||||
* @return array<PoolOption>
|
* @return array<PollOption>
|
||||||
*/
|
*/
|
||||||
public function getOptions(): array
|
public function getOptions(): array
|
||||||
{
|
{
|
||||||
if (!isset($this->options))
|
if (!isset($this->options))
|
||||||
$this->options = PoolOption::where('pool_id', $this->id)->get();
|
$this->options = PollOption::where('poll_id', $this->id)->get();
|
||||||
|
|
||||||
return $this->options;
|
return $this->options;
|
||||||
}
|
}
|
||||||
|
@ -43,7 +43,7 @@ class Pool extends Model {
|
||||||
'pid' => $this->id,
|
'pid' => $this->id,
|
||||||
'exp' => time()+43200
|
'exp' => time()+43200
|
||||||
]));
|
]));
|
||||||
setcookie('POOL_VOTE', $cookieValue, time()+43200, parse_url(SITE_URL, PHP_URL_PATH));
|
setcookie('POLL_VOTE', $cookieValue, time()+43200, parse_url(SITE_URL, PHP_URL_PATH));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -53,10 +53,10 @@ class Pool extends Model {
|
||||||
*/
|
*/
|
||||||
public function isVoted(): bool
|
public function isVoted(): bool
|
||||||
{
|
{
|
||||||
if (!isset($_COOKIE['POOL_VOTE']))
|
if (!isset($_COOKIE['POLL_VOTE']))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
$cookie = json_decode(Crypto::decrypt64($_COOKIE['POOL_VOTE']));
|
$cookie = json_decode(Crypto::decrypt64($_COOKIE['POLL_VOTE']));
|
||||||
|
|
||||||
return (json_last_error() == JSON_ERROR_NONE &&
|
return (json_last_error() == JSON_ERROR_NONE &&
|
||||||
$cookie->exp > time() &&
|
$cookie->exp > time() &&
|
|
@ -3,9 +3,9 @@ namespace Models;
|
||||||
|
|
||||||
use Libs\Model;
|
use Libs\Model;
|
||||||
|
|
||||||
class PoolOption extends Model {
|
class PollOption extends Model {
|
||||||
public string $value;
|
public string $value;
|
||||||
public int $pool_id;
|
public int $poll_id;
|
||||||
protected int $votes;
|
protected int $votes;
|
||||||
|
|
||||||
public function votes(): int
|
public function votes(): int
|
|
@ -47,7 +47,7 @@ class User extends Model {
|
||||||
*/
|
*/
|
||||||
public function createLoginCookie(): void
|
public function createLoginCookie(): void
|
||||||
{
|
{
|
||||||
setcookie('POOL_LC', $this->getSessionToken(), time()+1209600, parse_url(SITE_URL, PHP_URL_PATH));
|
setcookie('POLL_LC', $this->getSessionToken(), time()+1209600, parse_url(SITE_URL, PHP_URL_PATH));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -55,7 +55,7 @@ class User extends Model {
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public static function logout(): void {
|
public static function logout(): void {
|
||||||
setcookie('POOL_LC', '', 0);
|
setcookie('POLL_LC', '', 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -65,10 +65,10 @@ class User extends Model {
|
||||||
*/
|
*/
|
||||||
public static function isLogged(): static|null
|
public static function isLogged(): static|null
|
||||||
{
|
{
|
||||||
if (!isset($_COOKIE['POOL_LC']))
|
if (!isset($_COOKIE['POLL_LC']))
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
$cookie = json_decode(Crypto::decrypt64($_COOKIE['POOL_LC']));
|
$cookie = json_decode(Crypto::decrypt64($_COOKIE['POLL_LC']));
|
||||||
|
|
||||||
if (json_last_error() == JSON_ERROR_NONE &&
|
if (json_last_error() == JSON_ERROR_NONE &&
|
||||||
isset($cookie->expire) &&
|
isset($cookie->expire) &&
|
||||||
|
|
|
@ -3,7 +3,7 @@ namespace Requests;
|
||||||
|
|
||||||
use Libs\HTMX;
|
use Libs\HTMX;
|
||||||
|
|
||||||
class PoolCreateRequest extends UserRequest {
|
class PollCreateRequest extends UserRequest {
|
||||||
public static function rules(): array
|
public static function rules(): array
|
||||||
{
|
{
|
||||||
return [
|
return [
|
|
@ -2,15 +2,15 @@
|
||||||
namespace Requests;
|
namespace Requests;
|
||||||
|
|
||||||
use Libs\Request;
|
use Libs\Request;
|
||||||
use Models\Pool;
|
use Models\Poll;
|
||||||
|
|
||||||
class PoolRequest extends Request {
|
class PollRequest extends Request {
|
||||||
public ?Pool $pool;
|
public ?Poll $poll;
|
||||||
public function validate(): bool
|
public function validate(): bool
|
||||||
{
|
{
|
||||||
$this->pool = Pool::orderBy('id', 'DESC')->getFirst();
|
$this->poll = Poll::orderBy('id', 'DESC')->getFirst();
|
||||||
|
|
||||||
if (is_null($this->pool))
|
if (is_null($this->poll))
|
||||||
return $this->onInvalid('Aún no hay una encuesta configurada.');
|
return $this->onInvalid('Aún no hay una encuesta configurada.');
|
||||||
|
|
||||||
return parent::validate();
|
return parent::validate();
|
|
@ -1,21 +1,21 @@
|
||||||
<?php
|
<?php
|
||||||
namespace Requests;
|
namespace Requests;
|
||||||
|
|
||||||
use Models\PoolOption;
|
use Models\PollOption;
|
||||||
|
|
||||||
class VoteRequest extends PoolRequest {
|
class VoteRequest extends PollRequest {
|
||||||
public ?PoolOption $option;
|
public ?PollOption $option;
|
||||||
|
|
||||||
public function validate(): bool
|
public function validate(): bool
|
||||||
{
|
{
|
||||||
if (!parent::validate())
|
if (!parent::validate())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if ($this->pool->id != $this->params->pid)
|
if ($this->poll->id != $this->params->pid)
|
||||||
return $this->onInvalid('Voto no válido.');
|
return $this->onInvalid('Voto no válido.');
|
||||||
|
|
||||||
$this->option = PoolOption::getById($this->params->vid);
|
$this->option = PollOption::getById($this->params->vid);
|
||||||
if (is_null($this->option) || $this->option->pool_id != $this->params->pid)
|
if (is_null($this->option) || $this->option->poll_id != $this->params->pid)
|
||||||
return $this->onInvalid('Voto no válido.');
|
return $this->onInvalid('Voto no válido.');
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|
|
@ -0,0 +1,16 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
use Controllers\Poll\HomeController;
|
||||||
|
use Controllers\Poll\PollCreateController;
|
||||||
|
use Controllers\Poll\PollFormController;
|
||||||
|
use Controllers\Poll\PollResultController;
|
||||||
|
use Controllers\Poll\PollVoteController;
|
||||||
|
use Libs\Router;
|
||||||
|
|
||||||
|
Router::get('/', [HomeController::class, 'handle']);
|
||||||
|
|
||||||
|
Router::get('/config', [PollFormController::class, 'handle']);
|
||||||
|
Router::post('/config', [PollCreateController::class, 'handle']);
|
||||||
|
|
||||||
|
Router::post('/poll/{pid}/vote/{vid}', [PollVoteController::class, 'handle']);
|
||||||
|
Router::get('/results', [PollResultController::class, 'handle']);
|
|
@ -1,16 +0,0 @@
|
||||||
<?php
|
|
||||||
|
|
||||||
use Controllers\Pool\HomeController;
|
|
||||||
use Controllers\Pool\PoolCreateController;
|
|
||||||
use Controllers\Pool\PoolFormController;
|
|
||||||
use Controllers\Pool\PoolResultController;
|
|
||||||
use Controllers\Pool\PoolVoteController;
|
|
||||||
use Libs\Router;
|
|
||||||
|
|
||||||
Router::get('/', [HomeController::class, 'handle']);
|
|
||||||
|
|
||||||
Router::get('/config', [PoolFormController::class, 'handle']);
|
|
||||||
Router::post('/config', [PoolCreateController::class, 'handle']);
|
|
||||||
|
|
||||||
Router::post('/pool/{pid}/vote/{vid}', [PoolVoteController::class, 'handle']);
|
|
||||||
Router::get('/results', [PoolResultController::class, 'handle']);
|
|
|
@ -2,16 +2,16 @@
|
||||||
<div class="poll-wrapper">
|
<div class="poll-wrapper">
|
||||||
<article class="center">
|
<article class="center">
|
||||||
<header>
|
<header>
|
||||||
<h1><?=htmlspecialchars($this->pool->title)?></h1>
|
<h1><?=htmlspecialchars($this->poll->title)?></h1>
|
||||||
</header>
|
</header>
|
||||||
<div class="pool-options">
|
<div class="poll-options">
|
||||||
<?php if ($this->pool->isVoted()): ?>
|
<?php if ($this->poll->isVoted()): ?>
|
||||||
¡Gracias por participar!
|
¡Gracias por participar!
|
||||||
<?php else: ?>
|
<?php else: ?>
|
||||||
<?php foreach($this->pool->getOptions() as $option): ?>
|
<?php foreach($this->poll->getOptions() as $option): ?>
|
||||||
<div role="button"
|
<div role="button"
|
||||||
hx-target=".pool-options"
|
hx-target=".poll-options"
|
||||||
hx-post="<?=$this->route('/pool/'.$this->pool->id.'/vote/'.$option->id)?>"
|
hx-post="<?=$this->route('/poll/'.$this->poll->id.'/vote/'.$option->id)?>"
|
||||||
tabindex="0">
|
tabindex="0">
|
||||||
<?=htmlspecialchars($option->value)?>
|
<?=htmlspecialchars($option->value)?>
|
||||||
</div>
|
</div>
|
|
@ -6,15 +6,15 @@
|
||||||
<!-- /nothtmx -->
|
<!-- /nothtmx -->
|
||||||
<article class="center">
|
<article class="center">
|
||||||
<header>
|
<header>
|
||||||
<h1><?=htmlspecialchars($this->pool->title)?></h1>
|
<h1><?=htmlspecialchars($this->poll->title)?></h1>
|
||||||
</header>
|
</header>
|
||||||
<div class="pool-options">
|
<div class="poll-options">
|
||||||
<?php foreach($this->pool->getOptions() as $option): ?>
|
<?php foreach($this->poll->getOptions() as $option): ?>
|
||||||
<?php
|
<?php
|
||||||
if ($option->votes() == 0)
|
if ($option->votes() == 0)
|
||||||
$percent = 0;
|
$percent = 0;
|
||||||
else
|
else
|
||||||
$percent = round(($option->votes() * 100 / $this->pool->votes()), 2);
|
$percent = round(($option->votes() * 100 / $this->poll->votes()), 2);
|
||||||
?>
|
?>
|
||||||
<label>
|
<label>
|
||||||
<strong>
|
<strong>
|
||||||
|
@ -27,7 +27,7 @@
|
||||||
</div>
|
</div>
|
||||||
<footer>
|
<footer>
|
||||||
<strong>
|
<strong>
|
||||||
Total de votos: <?=$this->pool->votes()?>
|
Total de votos: <?=$this->poll->votes()?>
|
||||||
</strong>
|
</strong>
|
||||||
</footer>
|
</footer>
|
||||||
</article>
|
</article>
|
||||||
|
|
Loading…
Reference in New Issue