mirror of
https://github.com/kevachat/webapp.git
synced 2025-01-10 23:08:14 +00:00
implement rooms list
This commit is contained in:
parent
4e0fc8f3ca
commit
5ffd0a3bc2
7
.env
7
.env
@ -50,17 +50,14 @@ APP_KEVACOIN_EXPLORER_URL=https://keva.one/explorer/address/
|
||||
APP_KEVACOIN_BOOST_ADDRESS=EDIT_ME
|
||||
|
||||
# Allowed room namespaces, separated with | (must be owned to accept posts)
|
||||
APP_KEVACOIN_ROOM_NAMESPACES=EDIT_ME
|
||||
APP_KEVACOIN_ROOM_NAMESPACES_PINNED=EDIT_ME
|
||||
|
||||
# Allowed room namespaces for read only (e.g. project news) separated with |
|
||||
APP_KEVACOIN_ROOM_NAMESPACES_READONLY=EDIT_ME
|
||||
APP_KEVACOIN_ROOM_NAMESPACES_READONLY=
|
||||
|
||||
# Redirect from index page to default room
|
||||
APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT=EDIT_ME
|
||||
|
||||
# Allow users to read external node rooms
|
||||
APP_KEVACOIN_ROOM_NAMESPACES_EXTERNAL=
|
||||
|
||||
# Online session expiration timeout
|
||||
APP_SESSION_ONLINE_TIMEOUT=900
|
||||
|
||||
|
@ -47,8 +47,8 @@ Application package contain settings preset, just few steps required to launch:
|
||||
* Copy `rpcuser` to `env`.`APP_KEVACOIN_USERNAME` and `rpcpassword` to `env`.`APP_KEVACOIN_PASSWORD`
|
||||
* Generate new address using CLI `kevacoin-cli getnewaddress` and copy to `env`.`APP_KEVACOIN_BOOST_ADDRESS`
|
||||
* Send few coins to this address and wait for new block to continue
|
||||
* Create namespace for the chat room with `kevacoin-cli keva_namespace "sandbox"` and add it hash to `env`.`APP_KEVACOIN_ROOM_NAMESPACES`
|
||||
* Also Provide at least one namespace for default chat room to `env`.`APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT` (for homepage redirects)
|
||||
* Create at least one room namespace with Web UI or CLI `kevacoin-cli keva_namespace "sandbox"`
|
||||
* Provide at least one namespace for default chat room to `env`.`APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT` (for homepage redirects)
|
||||
|
||||
## Contribution
|
||||
|
||||
|
@ -15,9 +15,8 @@ parameters:
|
||||
app.kevacoin.port: '%env(APP_KEVACOIN_PORT)%'
|
||||
app.kevacoin.username: '%env(APP_KEVACOIN_USERNAME)%'
|
||||
app.kevacoin.password: '%env(APP_KEVACOIN_PASSWORD)%'
|
||||
app.kevacoin.room.namespaces: '%env(APP_KEVACOIN_ROOM_NAMESPACES)%'
|
||||
app.kevacoin.room.namespaces.pinned: '%env(APP_KEVACOIN_ROOM_NAMESPACES_PINNED)%'
|
||||
app.kevacoin.room.namespaces.readonly: '%env(APP_KEVACOIN_ROOM_NAMESPACES_READONLY)%'
|
||||
app.kevacoin.room.namespaces.external: '%env(APP_KEVACOIN_ROOM_NAMESPACES_EXTERNAL)%'
|
||||
app.kevacoin.room.namespace.default: '%env(APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT)%'
|
||||
app.kevacoin.boost.address: '%env(APP_KEVACOIN_BOOST_ADDRESS)%'
|
||||
app.kevacoin.explorer.url: '%env(APP_KEVACOIN_EXPLORER_URL)%'
|
||||
|
@ -127,7 +127,7 @@ main ul li span > svg
|
||||
float: right;
|
||||
}
|
||||
|
||||
main > sup > a > svg
|
||||
main a > svg
|
||||
{
|
||||
fill: var(--color-warning);
|
||||
}
|
||||
|
@ -95,7 +95,7 @@ class ModuleController extends AbstractController
|
||||
);
|
||||
}
|
||||
|
||||
public function room(
|
||||
public function rooms(
|
||||
Request $request
|
||||
): Response
|
||||
{
|
||||
@ -108,9 +108,9 @@ class ModuleController extends AbstractController
|
||||
);
|
||||
|
||||
return $this->render(
|
||||
'default/module/room.html.twig',
|
||||
'default/module/rooms.html.twig',
|
||||
[
|
||||
'list' => (array) explode('|', $this->getParameter('app.kevacoin.room.namespaces')),
|
||||
'list' => (array) explode('|', $this->getParameter('app.kevacoin.room.namespaces.pinned')),
|
||||
'form' =>
|
||||
[
|
||||
'namespace' =>
|
||||
@ -168,11 +168,6 @@ class ModuleController extends AbstractController
|
||||
|
||||
'enabled' =>
|
||||
(
|
||||
in_array(
|
||||
$request->get('namespace'),
|
||||
explode('|', $this->getParameter('app.kevacoin.room.namespaces'))
|
||||
)
|
||||
&&
|
||||
!in_array(
|
||||
$request->get('namespace'),
|
||||
explode('|', $this->getParameter('app.kevacoin.room.namespaces.readonly'))
|
||||
|
@ -31,6 +31,106 @@ class RoomController extends AbstractController
|
||||
);
|
||||
}
|
||||
|
||||
#[Route(
|
||||
'/room/list',
|
||||
name: 'room_list',
|
||||
methods:
|
||||
[
|
||||
'GET'
|
||||
]
|
||||
)]
|
||||
public function list(
|
||||
?Request $request
|
||||
): Response
|
||||
{
|
||||
// Connect kevacoin
|
||||
$client = new \Kevachat\Kevacoin\Client(
|
||||
$this->getParameter('app.kevacoin.protocol'),
|
||||
$this->getParameter('app.kevacoin.host'),
|
||||
$this->getParameter('app.kevacoin.port'),
|
||||
$this->getParameter('app.kevacoin.username'),
|
||||
$this->getParameter('app.kevacoin.password')
|
||||
);
|
||||
|
||||
// Get room list
|
||||
$list = [];
|
||||
|
||||
foreach ((array) $client->kevaListNamespaces() as $value)
|
||||
{
|
||||
// Calculate room totals
|
||||
$total = 0;
|
||||
|
||||
foreach ((array) $client->kevaFilter($value['namespaceId']) as $post)
|
||||
{
|
||||
// Skip values with meta keys
|
||||
if (false !== stripos($post['key'], '_KEVA_'))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Require valid kevachat meta
|
||||
if ($this->_post($post))
|
||||
{
|
||||
$total++;
|
||||
}
|
||||
}
|
||||
|
||||
// Add to room list
|
||||
$list[] =
|
||||
[
|
||||
'namespace' => $value['namespaceId'],
|
||||
'name' => $value['displayName'],
|
||||
'total' => $total,
|
||||
'pinned' => in_array(
|
||||
$value['namespaceId'],
|
||||
(array) explode(
|
||||
'|',
|
||||
$this->getParameter('app.kevacoin.room.namespaces.pinned')
|
||||
)
|
||||
)
|
||||
];
|
||||
}
|
||||
|
||||
// Sort by name
|
||||
array_multisort(
|
||||
array_column(
|
||||
$list,
|
||||
'name'
|
||||
),
|
||||
SORT_ASC,
|
||||
$list
|
||||
);
|
||||
|
||||
// RSS
|
||||
if ('rss' === $request->get('feed'))
|
||||
{
|
||||
$response = new Response();
|
||||
|
||||
$response->headers->set(
|
||||
'Content-Type',
|
||||
'text/xml'
|
||||
);
|
||||
|
||||
return $this->render(
|
||||
'default/room/list.rss.twig',
|
||||
[
|
||||
'list' => $list,
|
||||
'request' => $request
|
||||
],
|
||||
$response
|
||||
);
|
||||
}
|
||||
|
||||
// HTML
|
||||
return $this->render(
|
||||
'default/room/list.html.twig',
|
||||
[
|
||||
'list' => $list,
|
||||
'request' => $request
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
#[Route(
|
||||
'/room/{namespace}/{txid}',
|
||||
name: 'room_namespace',
|
||||
@ -61,21 +161,6 @@ class RoomController extends AbstractController
|
||||
$this->getParameter('app.kevacoin.password')
|
||||
);
|
||||
|
||||
// Check for external rooms reading allowed in config
|
||||
if (
|
||||
!in_array(
|
||||
$request->get('namespace'),
|
||||
(array) explode('|', $this->getParameter('app.kevacoin.room.namespaces'))
|
||||
)
|
||||
&&
|
||||
$this->getParameter('app.kevacoin.room.namespaces.external')
|
||||
) {
|
||||
// @TODO process to error page instead of redirect to default room
|
||||
return $this->redirectToRoute(
|
||||
'room_index'
|
||||
);
|
||||
}
|
||||
|
||||
// Get room feed
|
||||
$feed = [];
|
||||
|
||||
@ -263,14 +348,21 @@ class RoomController extends AbstractController
|
||||
);
|
||||
|
||||
// Check namespace defined in config
|
||||
if (!in_array($request->get('namespace'), (array) explode('|', $this->getParameter('app.kevacoin.room.namespaces'))))
|
||||
$rooms = [];
|
||||
|
||||
foreach ((array) $client->kevaListNamespaces() as $value)
|
||||
{
|
||||
$rooms[] = $value['namespaceId'];
|
||||
}
|
||||
|
||||
if (!in_array($request->get('namespace'), $rooms))
|
||||
{
|
||||
return $this->redirectToRoute(
|
||||
'room_namespace',
|
||||
[
|
||||
'namespace' => $request->get('namespace'),
|
||||
'message' => $request->get('message'),
|
||||
'error' => $translator->trans('Namespace not listed in settings!')
|
||||
'error' => $translator->trans('Namespace not not found on this node!')
|
||||
]
|
||||
);
|
||||
}
|
||||
|
@ -17,4 +17,19 @@
|
||||
</svg></a>
|
||||
</sup>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
{% if list %}
|
||||
•
|
||||
<h2>
|
||||
{% if form.namespace.value %}
|
||||
<a href="{{ path('room_list') }}">{{ 'all' | trans }}</a>
|
||||
{% else %}
|
||||
{{ 'all' | trans }}
|
||||
{% endif %}
|
||||
</h2>
|
||||
<sup>
|
||||
<a href="{{ path('room_list', { feed : 'rss' }) }}" title="{{ 'RSS' | trans }}" target="_blank"><svg xmlns="http://www.w3.org/2000/svg" width="10" height="10" viewBox="0 0 16 16">
|
||||
<path d="M2 0a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V2a2 2 0 0 0-2-2zm1.5 2.5c5.523 0 10 4.477 10 10a1 1 0 1 1-2 0 8 8 0 0 0-8-8 1 1 0 0 1 0-2m0 4a6 6 0 0 1 6 6 1 1 0 1 1-2 0 4 4 0 0 0-4-4 1 1 0 0 1 0-2m.5 7a1.5 1.5 0 1 1 0-3 1.5 1.5 0 0 1 0 3"/>
|
||||
</svg></a>
|
||||
</sup>
|
||||
{% endif %}
|
@ -50,7 +50,7 @@
|
||||
{{
|
||||
render(
|
||||
controller(
|
||||
'App\\Controller\\ModuleController::room',
|
||||
'App\\Controller\\ModuleController::rooms',
|
||||
{
|
||||
request: request
|
||||
}
|
||||
|
46
templates/default/room/list.html.twig
Normal file
46
templates/default/room/list.html.twig
Normal file
@ -0,0 +1,46 @@
|
||||
{% extends 'default/layout.html.twig' %}
|
||||
{% block head_title_content %}{{ 'Rooms' | trans }} - {{ 'KevaChat' | trans }}{% endblock %}
|
||||
{% block main_content %}
|
||||
{{
|
||||
render(
|
||||
controller(
|
||||
'App\\Controller\\ModuleController::rooms',
|
||||
{
|
||||
request: request
|
||||
}
|
||||
)
|
||||
)
|
||||
}}
|
||||
{% if list | length %}
|
||||
<ul>
|
||||
{% for room in list %}
|
||||
<li>
|
||||
<div>
|
||||
<strong>
|
||||
<a href="{{ path('room_namespace', { namespace : room.namespace }) }}">{{ room.namespace | keva_namespace_value }}</a>
|
||||
</strong>
|
||||
{{ room.total }}
|
||||
<a href="{{ path('room_namespace', { namespace : room.namespace, feed : 'rss' }) }}" title="{{ 'RSS' | trans }}" target="_blank"><svg xmlns="http://www.w3.org/2000/svg" width="10" height="10" viewBox="0 0 16 16">
|
||||
<path d="M2 0a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V2a2 2 0 0 0-2-2zm1.5 2.5c5.523 0 10 4.477 10 10a1 1 0 1 1-2 0 8 8 0 0 0-8-8 1 1 0 0 1 0-2m0 4a6 6 0 0 1 6 6 1 1 0 1 1-2 0 4 4 0 0 0-4-4 1 1 0 0 1 0-2m.5 7a1.5 1.5 0 1 1 0-3 1.5 1.5 0 0 1 0 3"/>
|
||||
</svg></a>
|
||||
{% if room.pinned %}
|
||||
<i title="{{ 'pinned' | trans }}">
|
||||
<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" fill="currentColor" viewBox="0 0 16 16" title="{{ 'pinned' | trans }}" style="float:right">
|
||||
<path d="M9.828.722a.5.5 0 0 1 .354.146l4.95 4.95a.5.5 0 0 1 0 .707c-.48.48-1.072.588-1.503.588-.177 0-.335-.018-.46-.039l-3.134 3.134a5.927 5.927 0 0 1 .16 1.013c.046.702-.032 1.687-.72 2.375a.5.5 0 0 1-.707 0l-2.829-2.828-3.182 3.182c-.195.195-1.219.902-1.414.707-.195-.195.512-1.22.707-1.414l3.182-3.182-2.828-2.829a.5.5 0 0 1 0-.707c.688-.688 1.673-.767 2.375-.72a5.922 5.922 0 0 1 1.013.16l3.134-3.133a2.772 2.772 0 0 1-.04-.461c0-.43.108-1.022.589-1.503a.5.5 0 0 1 .353-.146z"/>
|
||||
</svg>
|
||||
</i>
|
||||
{% endif %}
|
||||
</div>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
{% else %}
|
||||
<ul>
|
||||
<li>
|
||||
<div>
|
||||
{{ 'rooms not found' | trans }}
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
{% endif %}
|
||||
{% endblock %}
|
16
templates/default/room/list.rss.twig
Normal file
16
templates/default/room/list.rss.twig
Normal file
@ -0,0 +1,16 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
|
||||
<channel>
|
||||
<atom:link href="{{ url('room_list') }}" rel="self" type="application/rss+xml"></atom:link>
|
||||
<title>{{ 'Rooms' | trans }} - {{ 'KevaChat' | trans }}</title>
|
||||
<link>{{ url('room_list') }}</link>
|
||||
{% for room in list %}
|
||||
<item>
|
||||
<title>{{ room.namespace | keva_namespace_value }}</title>
|
||||
<guid>{{ url('room_namespace', { namespace : room.namespace }) }}</guid>
|
||||
<link>{{ url('room_namespace', { namespace : room.namespace }) }}</link>
|
||||
<description>{{ 'join' | trans }} {{ room.namespace | keva_namespace_value }} {{ 'room' | trans }}!</description>
|
||||
</item>
|
||||
{% endfor %}
|
||||
</channel>
|
||||
</rss>
|
Loading…
Reference in New Issue
Block a user