sfeed

Simple RSS and Atom feed parser
git clone https://git.sinitax.com/codemadness/sfeed
Log | Files | Refs | README | LICENSE | Upstream | sfeed.txt

sfeed_html.c (3765B)


      1#include <stdio.h>
      2#include <stdlib.h>
      3#include <string.h>
      4#include <time.h>
      5
      6#include "util.h"
      7
      8static struct feed *feeds;
      9static int showsidebar;
     10static char *line;
     11static size_t linesize;
     12static unsigned long totalnew, total;
     13static time_t comparetime;
     14
     15static void
     16printfeed(FILE *fp, struct feed *f)
     17{
     18	char *fields[FieldLast];
     19	struct tm rtm, *tm;
     20	time_t parsedtime;
     21	unsigned int isnew;
     22	ssize_t linelen;
     23
     24	if (f->name[0]) {
     25		fputs("<h2 id=\"", stdout);
     26		xmlencode(f->name, stdout);
     27		fputs("\"><a href=\"#", stdout);
     28		xmlencode(f->name, stdout);
     29		fputs("\">", stdout);
     30		xmlencode(f->name, stdout);
     31		fputs("</a></h2>\n", stdout);
     32	}
     33	fputs("<pre>\n", stdout);
     34
     35	while ((linelen = getline(&line, &linesize, fp)) > 0 &&
     36	       !ferror(stdout)) {
     37		if (line[linelen - 1] == '\n')
     38			line[--linelen] = '\0';
     39		parseline(line, fields);
     40
     41		parsedtime = 0;
     42		if (!strtotime(fields[FieldUnixTimestamp], &parsedtime) &&
     43		    (tm = localtime_r(&parsedtime, &rtm))) {
     44			isnew = (parsedtime >= comparetime) ? 1 : 0;
     45			totalnew += isnew;
     46			f->totalnew += isnew;
     47
     48			fprintf(stdout, "%04d-%02d-%02d&nbsp;%02d:%02d ",
     49			        tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday,
     50			        tm->tm_hour, tm->tm_min);
     51		} else {
     52			isnew = 0;
     53			fputs("                 ", stdout);
     54		}
     55		f->total++;
     56		total++;
     57
     58		if (fields[FieldLink][0]) {
     59			fputs("<a href=\"", stdout);
     60			xmlencode(fields[FieldLink], stdout);
     61			fputs("\">", stdout);
     62		}
     63		if (isnew)
     64			fputs("<b><u>", stdout);
     65		xmlencode(fields[FieldTitle], stdout);
     66		if (isnew)
     67			fputs("</u></b>", stdout);
     68		if (fields[FieldLink][0])
     69			fputs("</a>", stdout);
     70		fputs("\n", stdout);
     71	}
     72	fputs("</pre>\n", stdout);
     73}
     74
     75int
     76main(int argc, char *argv[])
     77{
     78	struct feed *f;
     79	char *name;
     80	FILE *fp;
     81	int i;
     82
     83	if (pledge(argc == 1 ? "stdio" : "stdio rpath", NULL) == -1)
     84		err(1, "pledge");
     85
     86	if (!(feeds = calloc(argc, sizeof(struct feed))))
     87		err(1, "calloc");
     88	if ((comparetime = getcomparetime()) == (time_t)-1)
     89		errx(1, "getcomparetime");
     90
     91	fputs("<!DOCTYPE HTML>\n"
     92	      "<html>\n"
     93	      "\t<head>\n"
     94	      "\t<meta name=\"referrer\" content=\"no-referrer\" />\n"
     95	      "\t\t<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\" />\n"
     96	      "\t\t<link rel=\"stylesheet\" type=\"text/css\" href=\"style.css\" />\n"
     97	      "\t</head>\n"
     98	      "\t<body class=\"noframe\">\n", stdout);
     99
    100	showsidebar = (argc > 1);
    101	if (showsidebar)
    102		fputs("\t\t<div id=\"items\">\n", stdout);
    103	else
    104		fputs("\t\t<div id=\"items\" class=\"nosidebar\">\n", stdout);
    105
    106	if (argc == 1) {
    107		feeds[0].name = "";
    108		printfeed(stdin, &feeds[0]);
    109		checkfileerror(stdin, "<stdin>", 'r');
    110	} else {
    111		for (i = 1; i < argc; i++) {
    112			name = ((name = strrchr(argv[i], '/'))) ? name + 1 : argv[i];
    113			feeds[i - 1].name = name;
    114			if (!(fp = fopen(argv[i], "r")))
    115				err(1, "fopen: %s", argv[i]);
    116			printfeed(fp, &feeds[i - 1]);
    117			checkfileerror(fp, argv[i], 'r');
    118			checkfileerror(stdout, "<stdout>", 'w');
    119			fclose(fp);
    120		}
    121	}
    122	fputs("</div>\n", stdout); /* div items */
    123
    124	if (showsidebar) {
    125		fputs("\t<div id=\"sidebar\">\n\t\t<ul>\n", stdout);
    126
    127		for (i = 1; i < argc; i++) {
    128			f = &feeds[i - 1];
    129			if (f->totalnew > 0)
    130				fputs("<li class=\"n\"><a href=\"#", stdout);
    131			else
    132				fputs("<li><a href=\"#", stdout);
    133			xmlencode(f->name, stdout);
    134			fputs("\">", stdout);
    135			if (f->totalnew > 0)
    136				fputs("<b><u>", stdout);
    137			xmlencode(f->name, stdout);
    138			fprintf(stdout, " (%lu)", f->totalnew);
    139			if (f->totalnew > 0)
    140				fputs("</u></b>", stdout);
    141			fputs("</a></li>\n", stdout);
    142		}
    143		fputs("\t\t</ul>\n\t</div>\n", stdout);
    144	}
    145
    146	fprintf(stdout, "\t</body>\n\t<title>(%lu/%lu) - Newsfeed</title>\n</html>\n",
    147	        totalnew, total);
    148
    149	checkfileerror(stdout, "<stdout>", 'w');
    150
    151	return 0;
    152}