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
|
APP_KEVACOIN_BOOST_ADDRESS=EDIT_ME
|
||||||
|
|
||||||
# Allowed room namespaces, separated with | (must be owned to accept posts)
|
# 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 |
|
# 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
|
# Redirect from index page to default room
|
||||||
APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT=EDIT_ME
|
APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT=EDIT_ME
|
||||||
|
|
||||||
# Allow users to read external node rooms
|
|
||||||
APP_KEVACOIN_ROOM_NAMESPACES_EXTERNAL=
|
|
||||||
|
|
||||||
# Online session expiration timeout
|
# Online session expiration timeout
|
||||||
APP_SESSION_ONLINE_TIMEOUT=900
|
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`
|
* 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`
|
* 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
|
* 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`
|
* Create at least one room namespace with Web UI or CLI `kevacoin-cli keva_namespace "sandbox"`
|
||||||
* Also Provide at least one namespace for default chat room to `env`.`APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT` (for homepage redirects)
|
* Provide at least one namespace for default chat room to `env`.`APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT` (for homepage redirects)
|
||||||
|
|
||||||
## Contribution
|
## Contribution
|
||||||
|
|
||||||
|
@ -15,9 +15,8 @@ parameters:
|
|||||||
app.kevacoin.port: '%env(APP_KEVACOIN_PORT)%'
|
app.kevacoin.port: '%env(APP_KEVACOIN_PORT)%'
|
||||||
app.kevacoin.username: '%env(APP_KEVACOIN_USERNAME)%'
|
app.kevacoin.username: '%env(APP_KEVACOIN_USERNAME)%'
|
||||||
app.kevacoin.password: '%env(APP_KEVACOIN_PASSWORD)%'
|
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.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.room.namespace.default: '%env(APP_KEVACOIN_ROOM_NAMESPACE_DEFAULT)%'
|
||||||
app.kevacoin.boost.address: '%env(APP_KEVACOIN_BOOST_ADDRESS)%'
|
app.kevacoin.boost.address: '%env(APP_KEVACOIN_BOOST_ADDRESS)%'
|
||||||
app.kevacoin.explorer.url: '%env(APP_KEVACOIN_EXPLORER_URL)%'
|
app.kevacoin.explorer.url: '%env(APP_KEVACOIN_EXPLORER_URL)%'
|
||||||
|
@ -127,7 +127,7 @@ main ul li span > svg
|
|||||||
float: right;
|
float: right;
|
||||||
}
|
}
|
||||||
|
|
||||||
main > sup > a > svg
|
main a > svg
|
||||||
{
|
{
|
||||||
fill: var(--color-warning);
|
fill: var(--color-warning);
|
||||||
}
|
}
|
||||||
|
@ -95,7 +95,7 @@ class ModuleController extends AbstractController
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function room(
|
public function rooms(
|
||||||
Request $request
|
Request $request
|
||||||
): Response
|
): Response
|
||||||
{
|
{
|
||||||
@ -108,9 +108,9 @@ class ModuleController extends AbstractController
|
|||||||
);
|
);
|
||||||
|
|
||||||
return $this->render(
|
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' =>
|
'form' =>
|
||||||
[
|
[
|
||||||
'namespace' =>
|
'namespace' =>
|
||||||
@ -168,11 +168,6 @@ class ModuleController extends AbstractController
|
|||||||
|
|
||||||
'enabled' =>
|
'enabled' =>
|
||||||
(
|
(
|
||||||
in_array(
|
|
||||||
$request->get('namespace'),
|
|
||||||
explode('|', $this->getParameter('app.kevacoin.room.namespaces'))
|
|
||||||
)
|
|
||||||
&&
|
|
||||||
!in_array(
|
!in_array(
|
||||||
$request->get('namespace'),
|
$request->get('namespace'),
|
||||||
explode('|', $this->getParameter('app.kevacoin.room.namespaces.readonly'))
|
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(
|
#[Route(
|
||||||
'/room/{namespace}/{txid}',
|
'/room/{namespace}/{txid}',
|
||||||
name: 'room_namespace',
|
name: 'room_namespace',
|
||||||
@ -61,21 +161,6 @@ class RoomController extends AbstractController
|
|||||||
$this->getParameter('app.kevacoin.password')
|
$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
|
// Get room feed
|
||||||
$feed = [];
|
$feed = [];
|
||||||
|
|
||||||
@ -263,14 +348,21 @@ class RoomController extends AbstractController
|
|||||||
);
|
);
|
||||||
|
|
||||||
// Check namespace defined in config
|
// 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(
|
return $this->redirectToRoute(
|
||||||
'room_namespace',
|
'room_namespace',
|
||||||
[
|
[
|
||||||
'namespace' => $request->get('namespace'),
|
'namespace' => $request->get('namespace'),
|
||||||
'message' => $request->get('message'),
|
'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>
|
</svg></a>
|
||||||
</sup>
|
</sup>
|
||||||
{% endfor %}
|
{% 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 %}
|
{% endif %}
|
@ -50,7 +50,7 @@
|
|||||||
{{
|
{{
|
||||||
render(
|
render(
|
||||||
controller(
|
controller(
|
||||||
'App\\Controller\\ModuleController::room',
|
'App\\Controller\\ModuleController::rooms',
|
||||||
{
|
{
|
||||||
request: request
|
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