CSS: Ad support for element category;

XSLT: Add a reference to script postprocess.js to file opml_as_xhtml.xsl;
XSLT: Add support for element category;
Python: Add support for element category.
This commit is contained in:
Schimon Jehudah, Adv. 2024-07-14 12:35:59 +03:00
parent cb4507bb78
commit 8ab7396a36
6 changed files with 46 additions and 21 deletions

View file

@ -124,6 +124,7 @@ http://127.0.0.1:8000/atom?pubsub=pubsub.movim.eu&node=jesus-christ-son-of-god&i
## Supported XEPs ## Supported XEPs
- [XEP-0060: Publish-Subscribe](https://xmpp.org/extensions/xep-0060.html) - [XEP-0060: Publish-Subscribe](https://xmpp.org/extensions/xep-0060.html)
- [XEP-0277: Microblogging over XMPP](https://xmpp.org/extensions/xep-0277.html)
- [XEP-0472: Pubsub Social Feed](https://xmpp.org/extensions/xep-0472.html) - [XEP-0472: Pubsub Social Feed](https://xmpp.org/extensions/xep-0472.html)
## Author ## Author

View file

@ -188,6 +188,15 @@ h3.title > a {
text-decoration: underline; text-decoration: underline;
} }
#articles div.entry span.tags {
display: inline-flex;
/* display: ruby; */
}
#articles div.entry span.tags > div {
margin: 5px;
}
.enclosures { .enclosures {
cursor: help; cursor: help;
direction: ltr; direction: ltr;

View file

@ -8,7 +8,6 @@ from fastapi.staticfiles import StaticFiles
import json import json
from slixmpp import ClientXMPP from slixmpp import ClientXMPP
from slixmpp.exceptions import IqError, IqTimeout from slixmpp.exceptions import IqError, IqTimeout
import xml
import xml.etree.ElementTree as ET import xml.etree.ElementTree as ET
#import importlib.resources #import importlib.resources
@ -59,7 +58,7 @@ async def view_pubsub_nodes(request: Request):
xml_opml = generate_opml(iq) xml_opml = generate_opml(iq)
result = append_stylesheet(xml_opml, 'opml') result = append_stylesheet(xml_opml, 'opml')
else: else:
text = 'Please check that PubSub Jabber ID is valid and accessible.' text = 'Please ensure that the PubSub Jabber ID is valid and accessible.'
xml_atom = error_message(text) xml_atom = error_message(text)
result = append_stylesheet(xml_atom, 'atom') result = append_stylesheet(xml_atom, 'atom')
else: else:
@ -112,7 +111,7 @@ async def view_node_items(request: Request):
generate_json(iq) generate_json(iq)
else: else:
operator = get_configuration('settings')['operator'] operator = get_configuration('settings')['operator']
json_data = [{'title' : 'Error retrieving items list.', json_data = [{'title' : 'Error retrieving node items.',
'link' : ('javascript:alert("Rivista has experienced an error ' 'link' : ('javascript:alert("Rivista has experienced an error '
'while attempting to retrieve the list of items for ' 'while attempting to retrieve the list of items for '
'Node {} of PubSub {}.")') 'Node {} of PubSub {}.")')
@ -125,7 +124,7 @@ async def view_node_items(request: Request):
with open(filename, 'w', encoding='utf-8') as f: with open(filename, 'w', encoding='utf-8') as f:
json.dump(json_data, f, ensure_ascii=False, indent=4) json.dump(json_data, f, ensure_ascii=False, indent=4)
else: else:
text = 'Please check that PubSub node and item are valid and accessible.' text = 'Please ensure that the PubSub node and item are valid and accessible.'
xml_atom = error_message(text) xml_atom = error_message(text)
result = append_stylesheet(xml_atom, 'atom') result = append_stylesheet(xml_atom, 'atom')
@ -145,7 +144,7 @@ async def view_node_items(request: Request):
link = form_a_node_link(pubsub, node) link = form_a_node_link(pubsub, node)
xml_atom = generate_atom(iq, link) xml_atom = generate_atom(iq, link)
else: else:
text = 'Please check that PubSub node is valid and accessible.' text = 'Please ensure that the PubSub node is valid and accessible.'
xml_atom = error_message(text) xml_atom = error_message(text)
result = append_stylesheet(xml_atom, 'atom') result = append_stylesheet(xml_atom, 'atom')
elif pubsub: elif pubsub:
@ -281,12 +280,12 @@ def generate_atom(iq, link):
namespace = '{http://www.w3.org/2005/Atom}' namespace = '{http://www.w3.org/2005/Atom}'
title = item_payload.find(namespace + 'title') title = item_payload.find(namespace + 'title')
links = item_payload.find(namespace + 'link') links = item_payload.find(namespace + 'link')
if (not isinstance(title, xml.etree.ElementTree.Element) and if (not isinstance(title, ET.Element) and
not isinstance(links, xml.etree.ElementTree.Element)): continue not isinstance(links, ET.Element)): continue
title_text = None if title == None else title.text title_text = None if title == None else title.text
e_entry = ET.SubElement(e_feed, 'entry') e_entry = ET.SubElement(e_feed, 'entry')
ET.SubElement(e_entry, 'title').text = title_text ET.SubElement(e_entry, 'title').text = title_text
if isinstance(links, xml.etree.ElementTree.Element): if isinstance(links, ET.Element):
for link in item_payload.findall(namespace + 'link'): for link in item_payload.findall(namespace + 'link'):
link_href = link.attrib['href'] if 'href' in link.attrib else '' link_href = link.attrib['href'] if 'href' in link.attrib else ''
link_type = link.attrib['type'] if 'type' in link.attrib else '' link_type = link.attrib['type'] if 'type' in link.attrib else ''
@ -297,11 +296,12 @@ def generate_atom(iq, link):
link_xmpp = form_an_item_link(pubsub, node, item_id) link_xmpp = form_an_item_link(pubsub, node, item_id)
ET.SubElement(e_entry, 'link', {'href': link_xmpp, 'rel': 'alternate', 'type': 'x-scheme-handler/xmpp'}) ET.SubElement(e_entry, 'link', {'href': link_xmpp, 'rel': 'alternate', 'type': 'x-scheme-handler/xmpp'})
contents = item_payload.find(namespace + 'content') contents = item_payload.find(namespace + 'content')
if isinstance(contents, xml.etree.ElementTree.Element): if isinstance(contents, ET.Element):
for content in item_payload.findall(namespace + 'content'): for content in item_payload.findall(namespace + 'content'):
content_text = content.text if content.text else 'No content.' if not content.text: continue
content_text = content.text
content_type = content.attrib['type'] if 'type' in content.attrib else 'html' content_type = content.attrib['type'] if 'type' in content.attrib else 'html'
content_type_text = 'html' if 'html' in content_type else 'html' content_type_text = 'html' if 'html' in content_type else 'text'
ET.SubElement(e_entry, 'content', {'type': content_type_text}).text = content_text ET.SubElement(e_entry, 'content', {'type': content_type_text}).text = content_text
else: else:
ET.SubElement(e_entry, 'content').text = 'No content.' ET.SubElement(e_entry, 'content').text = 'No content.'
@ -313,7 +313,7 @@ def generate_atom(iq, link):
ET.SubElement(e_entry, 'updated').text = updated_text ET.SubElement(e_entry, 'updated').text = updated_text
e_author = ET.SubElement(e_entry, 'author') e_author = ET.SubElement(e_entry, 'author')
authors = item_payload.find(namespace + 'author') authors = item_payload.find(namespace + 'author')
if isinstance(authors, xml.etree.ElementTree.Element): if isinstance(authors, ET.Element):
for author in item_payload.findall(namespace + 'author'): for author in item_payload.findall(namespace + 'author'):
if not author.text: continue if not author.text: continue
author_text = author.text author_text = author.text
@ -322,6 +322,12 @@ def generate_atom(iq, link):
author_summary = link.attrib['rel'] if 'rel' in link.attrib else '' author_summary = link.attrib['rel'] if 'rel' in link.attrib else ''
ET.SubElement(e_author, 'name').text = author_text ET.SubElement(e_author, 'name').text = author_text
if author and author.attrib: print(author.attrib) if author and author.attrib: print(author.attrib)
categories = item_payload.find(namespace + 'category')
if isinstance(categories, ET.Element):
for category in item_payload.findall(namespace + 'category'):
if not 'term' in category.attrib and not category.attrib['term']: continue
category_term = category.attrib['term']
ET.SubElement(e_entry, 'category', {'term': category_term})
identifier = item_payload.find(namespace + 'id') identifier = item_payload.find(namespace + 'id')

View file

@ -81,7 +81,7 @@ window.onload = async function(){
} }
// Build a journal list // Build a journal list
if (node) { if (locationHref.pathname.startsWith('/atom') && node) {
itemsList = await openJson(node) itemsList = await openJson(node)
if (itemsList && locationHref.searchParams.get('item')) { if (itemsList && locationHref.searchParams.get('item')) {
node = locationHref.searchParams.get('node') node = locationHref.searchParams.get('node')
@ -135,7 +135,7 @@ window.onload = async function(){
// Convert URI xmpp: to URI http: links. // Convert URI xmpp: to URI http: links.
for (let xmppLink of document.querySelectorAll( for (let xmppLink of document.querySelectorAll(
'#articles > ul > li > div > h3 > a[href^="xmpp:"],' + '#articles h3 > a[href^="xmpp:"][id^="rivista-"],' +
'#journal > ol > li > a[href^="xmpp:"]')) { '#journal > ol > li > a[href^="xmpp:"]')) {
xmppUri = new URL(xmppLink); xmppUri = new URL(xmppLink);
let parameters = xmppUri.search.split(';'); let parameters = xmppUri.search.split(';');

View file

@ -53,7 +53,7 @@ xmlns:atom='http://www.w3.org/2005/Atom'>
</xsl:choose> </xsl:choose>
</title> </title>
<!-- TODO media='print' --> <!-- TODO media='print' -->
<link href='/css/stylesheet.css' rel='stylesheet' type='text/css' media='screen'/> <link rel='stylesheet' type='text/css' media='screen' href='/css/stylesheet.css'/>
<link rel='icon' type='image/svg+xml' href='/graphic/xmpp.svg'/> <link rel='icon' type='image/svg+xml' href='/graphic/xmpp.svg'/>
<!-- whether language code is of direction right-to-left --> <!-- whether language code is of direction right-to-left -->
<xsl:if test='$rtl'> <xsl:if test='$rtl'>
@ -359,10 +359,21 @@ xmlns:atom='http://www.w3.org/2005/Atom'>
</xsl:choose> </xsl:choose>
</div> </div>
</xsl:if> </xsl:if>
<!-- entry tags -->
<xsl:if test='atom:category/@term'>
<h4>Tags</h4>
<span class='tags'>
<xsl:for-each select='atom:category'>
<xsl:element name='div'>
<xsl:value-of select='@term'/>
</xsl:element>
</xsl:for-each>
</span>
</xsl:if>
<!-- entry enclosure --> <!-- entry enclosure -->
<xsl:if test='atom:link[@rel="enclosure"]'> <xsl:if test='atom:link[@rel="enclosure"]'>
<h4>Enclosures</h4> <h4>Enclosures</h4>
<div class='enclosures' title='Right-click and Save link as…'> <span class='enclosures' title='Right-click and Save link as…'>
<xsl:for-each select='atom:link[@rel="enclosure"]'> <xsl:for-each select='atom:link[@rel="enclosure"]'>
<div class='enclosure' title='Right-click and Save link as…'> <div class='enclosure' title='Right-click and Save link as…'>
<xsl:element name='span'> <xsl:element name='span'>
@ -392,7 +403,7 @@ xmlns:atom='http://www.w3.org/2005/Atom'>
<br/> <br/>
</div> </div>
</xsl:for-each> </xsl:for-each>
</div> </span>
</xsl:if> </xsl:if>
</div> </div>
<!-- entry id --> <!-- entry id -->

View file

@ -45,12 +45,13 @@ xmlns:xml='http://www.w3.org/XML/1998/namespace'>
</xsl:choose> </xsl:choose>
</title> </title>
<!-- TODO media='print' --> <!-- TODO media='print' -->
<link href='/css/stylesheet.css' rel='stylesheet' type='text/css' media='screen'/> <link rel='stylesheet' type='text/css' media='screen' href='/css/stylesheet.css'/>
<link rel='icon' type='image/svg+xml' href='/graphic/xmpp.svg'/> <link rel='icon' type='image/svg+xml' href='/graphic/xmpp.svg'/>
<!-- whether language code is of direction right-to-left --> <!-- whether language code is of direction right-to-left -->
<xsl:if test='$rtl'> <xsl:if test='$rtl'>
<link id='semitic' href='/css/stylesheet-rtl.css' rel='stylesheet' type='text/css' /> <link id='semitic' href='/css/stylesheet-rtl.css' rel='stylesheet' type='text/css' />
</xsl:if> </xsl:if>
<script type='text/javascript' src='/script/postprocess.js'/>
</head> </head>
<body> <body>
<div id='actions'> <div id='actions'>
@ -133,9 +134,6 @@ xmlns:xml='http://www.w3.org/XML/1998/namespace'>
<xsl:attribute name='href'> <xsl:attribute name='href'>
<xsl:value-of select='@xmlUrl'/> <xsl:value-of select='@xmlUrl'/>
</xsl:attribute> </xsl:attribute>
<xsl:attribute name='title'>
<xsl:value-of select='@text'/>
</xsl:attribute>
<xsl:attribute name='id'> <xsl:attribute name='id'>
<xsl:text>rivista-</xsl:text> <xsl:text>rivista-</xsl:text>
<xsl:value-of select='position()'/> <xsl:value-of select='position()'/>