Begin rewriting rss.cgi in perl using Blerg::Database
authorChip Black <bytex64@bytex64.net>
Sun, 16 Jun 2013 08:36:50 +0000 (03:36 -0500)
committerChip Black <bytex64@bytex64.net>
Sat, 29 Mar 2014 03:56:22 +0000 (22:56 -0500)
.gitignore
Makefile
cgi/rss.c [deleted file]
rss.cgi [new file with mode: 0755]

index 988f75d..c47b365 100644 (file)
@@ -7,5 +7,4 @@ blerglatest
 blerg.httpd
 blerg.cgi
 blerg.fcgi
-rss.cgi
 www/build
index 60bf441..850da29 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -8,18 +8,17 @@ LDFLAGS ?=
 HTTP_LIBDIRS = $(MHD_LIBDIR) $(YAJL_LIBDIR)
 CGI_LIBDIRS = $(CGI_UTIL_LIBDIR) $(YAJL_LIBDIR)
 
-targets = blerg.a blergtool blerglatest blerg.cgi rss.cgi www/build/enyo-blerg.js
+targets = blerg.a blergtool blerglatest blerg.cgi www/build/enyo-blerg.js
 blerg_a_objects = database/database.o database/tags.o database/util.o database/subscription.o common/stringbucket.o
 blergtool_objects = tools/blergtool.o blerg.a
 blerglatest_objects = tools/blerglatest.o blerg.a common/json.o
-rss_objects = cgi/rss.o cgi/canned_responses.o common/app.o common/escapery.o blerg.a
 http_blerg_objects = http/http_blerg.o http/canned_responses.o common/app.o common/json.o common/auth.o common/md5.o blerg.a
 cgi_blerg_objects = cgi/cgi_blerg.o cgi/canned_responses.o common/app.o common/json.o common/auth.o common/md5.o builddeps/scrypt.a blerg.a
 
 all: $(targets)
 
 clean:
-       rm -f $(targets) $(blerg_a_objects) $(blergtool_objects) $(blerglatest_objects) $(http_blerg_objects) $(cgi_blerg_objects) $(rss_objects) builddeps/*.a
+       rm -f $(targets) $(blerg_a_objects) $(blergtool_objects) $(blerglatest_objects) $(http_blerg_objects) $(cgi_blerg_objects) builddeps/*.a
        @make -C builddeps/scrypt-1.1.6 distclean
        @make -C builddeps/scrypt-1.1.6/lib/crypto clean
 
@@ -38,9 +37,6 @@ blerg.httpd: $(http_blerg_objects)
 blerg.cgi: $(cgi_blerg_objects)
        gcc $(CGI_LIBDIRS) $(LDFLAGS) $(cgi_blerg_objects) -lcgi-util -lyajl_s -o $@
 
-rss.cgi: $(rss_objects)
-       gcc $(CGI_LIBDIRS) $(LDFLAGS) $(rss_objects) -lcgi-util -o $@
-
 http/%.o: http/%.c
        gcc $(INCLUDES) $(HTTP_INCLUDES) $(CFLAGS) -c $< -o $@
 
diff --git a/cgi/rss.c b/cgi/rss.c
deleted file mode 100644 (file)
index f143e55..0000000
--- a/cgi/rss.c
+++ /dev/null
@@ -1,107 +0,0 @@
-/* Blerg is (C) 2011 The Dominion of Awesome, and is distributed under a
- * BSD-style license.  Please see the COPYING file for details.
- */
-#include <stdio.h>
-#include <stdlib.h>
-#include <time.h>
-#include <cgi-util.h>
-#include "database.h"
-#include "escapery.h"
-#include "canned_responses.h"
-#include "app.h"
-#include "config.h"
-
-int fprint_rss(FILE *f, const char *username) {
-       struct blerg *b = blerg_open(username);
-       uint64_t record_count = blerg_get_record_count(b);
-       uint64_t i = (record_count > 50 ? record_count - 50 : 0);
-       char *data;
-       char *tmp;
-       time_t post_time;
-       char date[40];
-       int len;
-
-       fprintf(f,
-               "<?xml version=\"1.0\" encoding=\"utf-8\" ?>\n"
-               "<rss version=\"2.0\">\n"
-               "<channel>\n"
-               "<title>%s's blërg</title>\n"
-               "<link>%s#%s</link>\n"
-               "<description>%s</description>\n",
-               username,
-               BASEURL,
-               username,
-               "Textual vomit"
-       );
-
-       while (i < record_count) {
-               blerg_fetch(b, i, &data, &len);
-               tmp = xml_escape_data(data, len);
-               post_time = blerg_get_timestamp(b, i);
-               strftime(date, 39, "%a, %d %b %Y %H:%M:%S %Z", gmtime(&post_time));
-               fprintf(f,
-                       "<item>\n"
-                       "<pubDate>%s</pubDate>\n"
-                       "<guid>%sget/%s/%llu</guid>\n"
-                       "<description>%s</description>\n"
-                       "</item>\n",
-                       date,
-                       BASEURL, username, i,
-                       tmp
-               );
-               free(tmp);
-               free(data);
-               i++;
-       }
-       blerg_close(b);
-
-       fprintf(f,
-               "</channel>\n"
-               "</rss>\n"
-       );
-}
-
-int main (int argc, char *argv) {
-       char *path;
-       char *request_method;
-       int ret;
-       struct url_info info;
-
-       request_method = getenv("REQUEST_METHOD");
-       if (request_method == NULL) {
-               fprintf(stderr, "Request method is null!?\n");
-               exit(0);
-       }
-
-       if (strncmp(request_method, "GET", 4) != 0) {
-               respond_405();
-               exit(0);
-       }
-
-       path = getenv("PATH_INFO");
-       if (path == NULL) {
-               respond_404();
-               exit(0);
-       }
-
-       if (path[0] != '/') {
-               respond_404();
-               exit(0);
-       }
-
-       ret = parse_url_info(path + 1, &info);
-       if ((ret & URL_INFO_NAME) == 0) {
-               respond_404();
-               exit(0);
-       }
-
-       if (!blerg_exists(info.name)) {
-               respond_404();
-               exit(0);
-       }
-
-       printf("Content-type: application/rss+xml\r\n\r\n");
-
-       fprint_rss(stdout, info.name);
-
-}
diff --git a/rss.cgi b/rss.cgi
new file mode 100755 (executable)
index 0000000..b207874
--- /dev/null
+++ b/rss.cgi
@@ -0,0 +1,108 @@
+#!/usr/bin/perl
+use CGI::Fast qw/:cgi/;
+use Blerg::Database;
+use URI::Escape;
+use POSIX qw/strftime/;
+use strict;
+
+my $baseurl = Blerg::Database::constant('BASEURL');
+
+sub xml_escape {
+    local $_ = shift;
+    s/&/&amp;/g;
+    s/</&lt;/g;
+    s/>/&gt;/g;
+    return $_;
+}
+
+sub print_404 {
+    print header(-type => 'text/html',
+                 -status => '404 Not Found');
+    print <<DOC;
+<!DOCTYPE html>
+<h1>404 Not Found</h1>
+Not Found
+DOC
+}
+
+sub print_rss {
+    my ($name, @items) = @_;
+
+    print <<HEADER;
+<?xml version="1.0" encoding="utf-8" ?>
+<rss version="2.0">
+  <channel>
+    <title>${name}'s blërg</title>
+    <link>${baseurl}#$name</link>
+    <description>Textual vomit</description>
+HEADER
+
+    for my $i (@items) {
+        my $data = xml_escape($i->{data});
+        my $post_time = strftime("%a, %d %b %Y %H:%M:%S %Z", gmtime($i->{timestamp}));
+        print <<ITEM;
+    <item>
+      <pubDate>$post_time</pubDate>
+      <guid>${baseurl}get/$name/$i->{record}</guid>
+      <description>$data</description>
+    </item>
+ITEM
+    }
+
+    print <<'FOOTER'
+  </channel>
+</rss>
+FOOTER
+}
+
+REQUEST:
+while (my $q = new CGI::Fast) {
+    my @path = split('/', $ENV{PATH_INFO});
+    shift @path;
+
+    if (@path == 1) {
+        # Assume this is a username; redirect to /user/<username>
+        my $username = $path[0];
+        my $b = Blerg::Database->open_existing($username);
+        if (!defined $b) {
+            print_404;
+            next REQUEST;
+        }
+        print header(-type => 'application/rss+xml',
+                     -charset => 'utf8',
+                     -status => '301 Moved Permanently',
+                     -location => "${baseurl}rss/user/$username");
+        # And present the content in case their client is broken
+        my $n = $b->record_count - 1;
+        my @list = reverse map {
+            {
+                record    => $_,
+                data      => $b->fetch($_),
+                timestamp => $b->timestamp($_),
+            }
+        } ($n > 50 ? $n - 50 : 0)..$n;
+        $b->close;
+        print_rss($username, @list);
+    } elsif ($path[0] eq 'user') {
+        my $username = $path[1];
+        my $b = Blerg::Database->open_existing($username);
+        if (!defined $b) {
+            print_404;
+            next REQUEST;
+        }
+        print header(-type => 'application/rss+xml');
+        my $n = $b->record_count - 1;
+        my @list = reverse map {
+            {
+                record    => $_,
+                data      => $b->fetch($_),
+                timestamp => $b->timestamp($_),
+            }
+        } ($n > 50 ? $n - 50 : 0)..$n;
+        $b->close;
+        print_rss($username, @list);
+    } elsif ($path[0] eq 'tag') {
+    } elsif ($path[0] eq 'ref') {
+    } elsif ($path[0] eq 'feed') {
+    }
+}