commit d2031cdff9527a5e8562b80dad0a92a6e3ce4931
parent df1dcf5ff0f501cbef195231d10afadcc2386d9a
Author: Hiltjo Posthuma <hiltjo@codemadness.org>
Date: Sat, 22 Aug 2015 15:01:18 +0200
sfeed_opml_import: improve import
- support attribute entities better.
- escape some characters (it's still recommended to check the output ofcourse).
Diffstat:
M | sfeed_opml_import.c | | | 81 | +++++++++++++++++++++++++++++++++++++++++++++---------------------------------- |
1 file changed, 46 insertions(+), 35 deletions(-)
diff --git a/sfeed_opml_import.c b/sfeed_opml_import.c
@@ -1,4 +1,4 @@
-/* convert an opml file to sfeedrc file */
+#include <ctype.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
@@ -9,30 +9,14 @@
#include "xml.h"
static XMLParser parser; /* XML parser state */
-static char feedurl[2048], feedname[2048], basesiteurl[2048];
-
-static int
-istag(const char *s1, const char *s2)
-{
- return !strcasecmp(s1, s2);
-}
-
-static int
-isattr(const char *s1, const char *s2)
-{
- return !strcasecmp(s1, s2);
-}
+static char url[2048], text[256], title[256];
static void
-xml_handler_start_element(XMLParser *p, const char *tag, size_t taglen)
+printsafe(const char *s)
{
- (void)p;
- (void)taglen;
-
- if (istag(tag, "outline")) {
- feedurl[0] = '\0';
- feedname[0] = '\0';
- basesiteurl[0] = '\0';
+ for (; *s; s++) {
+ if (!iscntrl((int)*s) && *s != '\'' && *s != '\\')
+ putchar((int)*s);
}
}
@@ -44,11 +28,22 @@ xml_handler_end_element(XMLParser *p, const char *tag, size_t taglen,
(void)taglen;
(void)isshort;
- if (istag(tag, "outline")) {
- printf("\tfeed \"%s\" \"%s\" \"%s\"\n",
- feedname[0] ? feedname : "unnamed",
- feedurl, basesiteurl);
+ if (strcasecmp(tag, "outline"))
+ return;
+
+ if (url[0]) {
+ fputs("\tfeed '", stdout);
+ if (title[0])
+ printsafe(title);
+ else if (text[0])
+ printsafe(text);
+ else
+ fputs("unnamed", stdout);
+ fputs("' '", stdout);
+ printsafe(url);
+ fputs("'\n", stdout);
}
+ url[0] = text[0] = title[0] = '\0';
}
static void
@@ -60,22 +55,38 @@ xml_handler_attr(XMLParser *p, const char *tag, size_t taglen,
(void)namelen;
(void)valuelen;
- if (istag(tag, "outline")) {
- if (isattr(name, "text") || isattr(name, "title"))
- strlcpy(feedname, value, sizeof(feedname));
- else if (isattr(name, "htmlurl"))
- strlcpy(basesiteurl, value, sizeof(basesiteurl));
- else if (isattr(name, "xmlurl"))
- strlcpy(feedurl, value, sizeof(feedurl));
- }
+ if (strcasecmp(tag, "outline"))
+ return;
+
+ if (!strcasecmp(name, "title"))
+ strlcat(title, value, sizeof(title));
+ else if (!strcasecmp(name, "text"))
+ strlcat(text, value, sizeof(text));
+ else if (!strcasecmp(name, "xmlurl"))
+ strlcat(url, value, sizeof(url));
+}
+
+static void
+xml_handler_attrentity(XMLParser *p, const char *tag, size_t taglen,
+ const char *name, size_t namelen, const char *value, size_t valuelen)
+{
+ char buf[16];
+ ssize_t len;
+
+ if ((len = xml_entitytostr(value, buf, sizeof(buf))) < 0)
+ return;
+ if (len > 0)
+ xml_handler_attr(p, tag, taglen, name, namelen, buf, len);
+ else
+ xml_handler_attr(p, tag, taglen, name, namelen, value, valuelen);
}
int
main(void)
{
parser.xmlattr = xml_handler_attr;
+ parser.xmlattrentity = xml_handler_attrentity;
parser.xmltagend = xml_handler_end_element;
- parser.xmltagstart = xml_handler_start_element;
fputs(
"# paths\n"