From 0cc319a702d2d844cd97ff5a50d767ebf246b4ca Mon Sep 17 00:00:00 2001 From: DeaDvey Date: Wed, 30 Jul 2025 01:28:23 +0100 Subject: [PATCH] Added user specific RSS and ATOM feeds and updated the EJS templates to add them by default to the user's header section --- README.md | 3 +- src/functions.js | 2 +- src/server.js | 48 ++++++++++++++++++++- views/headers/timeline.ejs | 3 +- views/headers/user.ejs | 4 +- views/syndication/global_atom.ejs | 2 +- views/syndication/user_atom.ejs | 24 +++++++++++ views/syndication/{rss.ejs => user_rss.ejs} | 6 ++- 8 files changed, 83 insertions(+), 9 deletions(-) create mode 100644 views/syndication/user_atom.ejs rename views/syndication/{rss.ejs => user_rss.ejs} (82%) diff --git a/README.md b/README.md index 13177dd..17e9ae3 100644 --- a/README.md +++ b/README.md @@ -18,7 +18,7 @@ Read the [configuation guide](docs/CONFIG.md) for configuration help (in config. * user creation, modification and deletion via frontend * multi user * powerful customisation via EJS -* site wide rss, atom +* site wide and user specific rss, atom * hitcount * Markdown syntax in posts * Commenting on posts @@ -29,7 +29,6 @@ Read the [configuation guide](docs/CONFIG.md) for configuration help (in config. * probably insecure as hell # Planned features/todo list -* user specific RSS/atom feeds * federation (looks tricky) * All strings (including in edit and post page) customisable * formatable custom strings diff --git a/src/functions.js b/src/functions.js index d5db46c..51843f3 100644 --- a/src/functions.js +++ b/src/functions.js @@ -29,7 +29,7 @@ export function unix_time_to_rss_date(unix_time) { export function unix_time_to_atom_date(unix_time) { const { fromUnixTime, format, getUnixTime } = require("date-fns") // A date utility library let date = fromUnixTime(unix_time) - let formatted_date = format(date, "yyyy-MM-dd\\THH:mm:ss\\Z") + let formatted_date = format(date, "yyyy-MM-dd'T'HH:mm:ss'Z'") return `${formatted_date}` } // This function accepts a list of strings eg ["string1","string2,"string3"] (any length) diff --git a/src/server.js b/src/server.js index 5b6649f..b0a9dee 100644 --- a/src/server.js +++ b/src/server.js @@ -60,7 +60,7 @@ app.set('view engine', 'ejs'); app.set('views', '../views') ////////////////////// SYNDICATION //////////////////////// -// RSS protocol gets +// global RSS protocol gets app.get("/rss", (req,res) => { if (config.rss == false) { res.render("partials/message", { @@ -78,7 +78,28 @@ app.get("/rss", (req,res) => { }) }; }); -// ATOM protocol gets +// user RSS protocol gets +app.get("/user/:username/rss", (req,res) => { + const username = req.params.username; + const userID = func.get_userID(username); + if (config.rss == false) { + res.render("partials/message", { + message: config.string.rss_disabled, + config: config, + }) + } + else { + res.setHeader('content-type', 'application/rss+xml'); + res.render("syndication/user_rss", { + config, + posts, + converter, + func, + userID, + }) + }; +}); +// global ATOM protocol gets app.get("/atom", (req,res) => { if (config.rss == false) { res.render("partials/message", { @@ -93,6 +114,29 @@ app.get("/atom", (req,res) => { posts, converter, func, + getUnixTime, + }) + }; +}); +// user ATOM protocol gets +app.get("/user/:username/atom", (req,res) => { + const username = req.params.username; + const userID = func.get_userID(username); + if (config.rss == false) { + res.render("partials/message", { + message: config.string.rss_disabled, + config: config, + }) + } + else { + res.setHeader('content-type', 'application/rss+xml'); + res.render("syndication/user_atom", { + config, + posts, + converter, + func, + userID, + getUnixTime, }) }; }); diff --git a/views/headers/timeline.ejs b/views/headers/timeline.ejs index d289f0b..a4ce164 100644 --- a/views/headers/timeline.ejs +++ b/views/headers/timeline.ejs @@ -4,7 +4,8 @@

<%- config.site_description %>

-RSS Feed
+RSS Feed
+ATOM Feed
New post
Sign Up
<% if (config.enable_hitcount == true) { %> diff --git a/views/headers/user.ejs b/views/headers/user.ejs index 23c8636..dfbff1c 100644 --- a/views/headers/user.ejs +++ b/views/headers/user.ejs @@ -2,5 +2,7 @@ <%= user.prettyname %>'s posts

<%- converter.makeHtml(user.description) %>

-edit account +edit account
+RSS
+ATOM <%- config.seperator %> diff --git a/views/syndication/global_atom.ejs b/views/syndication/global_atom.ejs index 9c72cd0..3e27a0c 100644 --- a/views/syndication/global_atom.ejs +++ b/views/syndication/global_atom.ejs @@ -3,7 +3,7 @@ <%= config.site_name %> <%= config.site_url %> <%= config.site_description %> - <%= new Date() %> + <%= func.unix_time_to_atom_date(getUnixTime(new Date())) %> <%= config.site_url %> <% for (let postID = posts.length-1; postID >= 0; postID--) { %> <% if (posts[postID]["deleted"] != true) { %> diff --git a/views/syndication/user_atom.ejs b/views/syndication/user_atom.ejs new file mode 100644 index 0000000..4b429d9 --- /dev/null +++ b/views/syndication/user_atom.ejs @@ -0,0 +1,24 @@ +" ?> + + <%= config.site_name %> + <%= config.site_url %> + <%= config.site_description %> + <%= func.unix_time_to_atom_date(getUnixTime(new Date())) %> + <%= config.site_url %> + <% for (let postID = posts.length-1; postID >= 0; postID--) { %> + <% if (posts[postID]["userID"] == userID) { %> + <% if (posts[postID]["deleted"] != true) { %> + + <%= posts[postID]["title"] %> + <%= config.site_url %>/post/<%= postID %> + ]]> + <%= config.site_url %>/post/<%= postID %> + <%# func.unix_time_to_atom_date(posts[postID]['pubdate']) %> + <% for (let tag_index = 0; tag_index < posts[postID]['tags'].length; tag_index++) { %> + ]]> + <% } %> + + <% } %> + <% } %> + <% } %> + diff --git a/views/syndication/rss.ejs b/views/syndication/user_rss.ejs similarity index 82% rename from views/syndication/rss.ejs rename to views/syndication/user_rss.ejs index 73e43e6..d5ae971 100644 --- a/views/syndication/rss.ejs +++ b/views/syndication/user_rss.ejs @@ -5,10 +5,12 @@ <%= config.site_url %> <%= config.site_description %> <% for (let postID = posts.length-1; postID >= 0; postID--) { %> + <% if (posts[postID]["userID"] == userID) { %> + <% if (posts[postID]["deleted"] != true) { %> <%= posts[postID]["title"] %> <%= config.site_url %>/post/<%= postID %> - ]]> + ]]> <%= config.site_url %>/post/<%= postID %> <%= func.unix_time_to_rss_date(posts[postID]['pubdate']) %> <% for (let tag_index = 0; tag_index < posts[postID]['tags'].length; tag_index++) { %> @@ -16,5 +18,7 @@ <% } %> <% } %> + <% } %> + <% } %>