Compare commits

...
Author SHA1 Message Date
Jim Miller f7429140f8 Bump versions. 2013-12-23 17:45:19 -05:00
Jim Miller 7872b25034 Minor tweak to ffnet fix in case they change it back, sleep on ffnet meta lookup. 2013-12-23 17:45:08 -05:00
Jim Miller 3d468a4dc5 New site: literotica.com, tweaks to htmlheuristics for it. 2013-12-23 17:43:32 -05:00
asbjorn grandt 413525a881 url for fictionratings changed to https, breaking the soup find. 2013-12-23 08:14:10 +01:00
Jim Miller c066a809c7 Added tag FanFictionDownLoader-4.4.88 for changeset 7ed8deaec5d2 2013-12-12 18:10:51 -06:00
Jim Miller 443b2b5ef8 Save CLI download version *4.4.88* 2013-12-12 18:10:35 -06:00
Jim Miller 3e7f05ba44 Save CLI download version 4.4.87 2013-12-12 18:09:22 -06:00
Jim Miller 25e65da239 Added tag calibre-plugin-1.8.05 for changeset 8254e19f1ab2 2013-12-12 18:03:35 -06:00
Jim Miller c5f211f49f Moved tag calibre-plugin-1.8.04 to changeset 6e301aeb7f4b (from changeset e45187f4215e) 2013-12-12 18:03:26 -06:00
Jim Miller 20fff58813 Moved tag calibre-plugin-1.8.03 to changeset ea92e962bcaa (from changeset 6e301aeb7f4b) 2013-12-12 18:03:00 -06:00
Jim Miller 8fe250747c Added tag calibre-plugin-1.8.04 for changeset e45187f4215e 2013-12-12 17:59:56 -06:00
Jim Miller 4d41c28f3c Fix a bug with AO3 single chapter stories introduced with do_update_hook. 2013-12-12 17:59:41 -06:00
Jim Miller f8d1b21007 Moved tag FanFictionDownLoader-4.4.87 to changeset 8d78c6f57151 (from changeset 6e301aeb7f4b) 2013-12-12 13:35:55 -06:00
Jim Miller 72861e6cd5 Save CLI Zip file. 2013-12-12 13:35:30 -06:00
Jim Miller bd9dba5813 Added tag FanFictionDownLoader-4.4.87 for changeset 6e301aeb7f4b 2013-12-12 13:33:46 -06:00
Jim Miller 1478df572e Added tag calibre-plugin-1.8.03 for changeset 6e301aeb7f4b 2013-12-12 13:33:30 -06:00
Jim Miller 68466af944 Bump versions. 2013-12-12 13:33:13 -06:00
Jim Miller 7c9c84256c Graceful fail for 'k'HTML when no 'k'Url, bump min calibre version. 2013-12-11 12:14:55 -06:00
Jim Miller fcbfe96c64 Add do_update_hook to AO3 for updated chapters in the middle, trekiverse alt URL,
reorder defaults.ini files to put user/pass is_adult first in all sections.
2013-12-11 12:13:22 -06:00
Jim Miller e47748dbbc Added tag calibre-plugin-1.8.02 for changeset a277cb866377 2013-12-05 13:16:45 -06:00
Jim Miller 91a6c668d1 Added tag FanFictionDownLoader-4.4.86 for changeset a277cb866377 2013-12-05 13:16:22 -06:00
Jim Miller 4875265fd3 Bump versions. 2013-12-05 13:15:59 -06:00
Jim Miller bf651df38f Add prequels/sequels & fix groups site specific metadata for fimfiction.net. 2013-12-05 13:15:46 -06:00
Jim Miller 77e2d7beff New site: trekiverse.org/efiction/ 2013-12-03 21:56:46 -06:00
Jim Miller 9c85563ffd Fix: identifier searchs, overwrite newer with ffnet timestamps. 2013-12-02 12:49:16 -06:00
Jim Miller e217c6fe23 Fix: Reject lines shouldn't be translated 2013-12-02 12:48:44 -06:00
Jim Miller 17b6d090db Fix for higher rated stories with not logged in on TtH. 2013-11-30 16:55:00 -06:00
Jim Miller 4e1e04ef06 Update translations, add German. 2013-11-30 16:54:36 -06:00
Jim Miller c81ee20151 Added tag FanFictionDownLoader-4.4.85 for changeset dbc1c8e89543 2013-11-25 12:54:07 -06:00
Jim Miller eb5b447b09 Added tag calibre-plugin-1.8.01 for changeset dbc1c8e89543 2013-11-25 12:53:46 -06:00
Jim Miller 857ae5b7fa Fix dc:language issue with defaulting to English. Bump versions. 2013-11-25 12:48:17 -06:00
Jim Miller 1037fff11f Disable nook_img_fix if replace_br_with_p. 2013-11-25 12:25:11 -06:00
Jim Miller f611a1e26f Correction for 'Default' GC setting. 2013-11-25 11:06:42 -06:00
asbjorn grandt f3cfa72051 New code to correct the HTML when changing breaks to paragraphs. Example. <em> tags would not be properly terminated. 2013-11-25 09:31:39 +01:00
Jim Miller f13a698808 Fix for 1000+ chapters(commas) and 'Default' GC with translations. 2013-11-24 22:51:15 -06:00
Jim Miller 18064c269b Update index.html. 2013-11-18 07:49:57 -06:00
Jim Miller ccb4af4f63 Added tag FanFictionDownLoader-4.4.84 for changeset 9039b37d99c7 2013-11-18 07:47:53 -06:00
Jim Miller 0ee30ddeac Added tag calibre-plugin-1.8.00 for changeset 9039b37d99c7 2013-11-18 07:47:39 -06:00
26 changed files with 3609 additions and 879 deletions
+1 -1
View File
@@ -1,6 +1,6 @@
# ffd-retief-hrd fanfictiondownloader
application: fanfictiondownloader
version: 4-4-84
version: 4-4-89
runtime: python27
api_version: 1
threadsafe: true
+2 -2
View File
@@ -42,8 +42,8 @@ class FanFictionDownLoaderBase(InterfaceActionBase):
description = _('UI plugin to download FanFiction stories from various sites.')
supported_platforms = ['windows', 'osx', 'linux']
author = 'Jim Miller'
version = (1, 8, 00)
minimum_calibre_version = (0, 8, 57)
version = (1, 8, 06)
minimum_calibre_version = (1, 13, 0)
#: This field defines the GUI plugin class that contains all the code
#: that actually does something. Its format is module_path:class_name
+6 -1
View File
@@ -723,7 +723,12 @@ class GenerateCoverTab(QWidget):
dropdown.addItem('',QVariant('none'))
for setting in gc_settings:
dropdown.addItem(setting,QVariant(setting))
self.gc_dropdowns[site] = dropdown
if site == _("Default"):
self.gc_dropdowns["Default"] = dropdown
if 'Default' in prefs['gc_site_settings']:
dropdown.setCurrentIndex(dropdown.findData(QVariant(prefs['gc_site_settings']['Default'])))
else:
self.gc_dropdowns[site] = dropdown
if site in prefs['gc_site_settings']:
dropdown.setCurrentIndex(dropdown.findData(QVariant(prefs['gc_site_settings'][site])))
+2 -1
View File
@@ -136,7 +136,8 @@ class RejectUrlEntry:
def fullnote(self):
retval = ""
if self.title and self.auth:
retval = retval + _("%s by %s")%(self.title,self.auth)
# don't translate--ends up being saved and confuses regex above.
retval = retval + "%s by %s"%(self.title,self.auth)
if self.note:
retval = retval + " - "
+20 -8
View File
@@ -13,7 +13,7 @@ logger = logging.getLogger(__name__)
import time, os, copy, threading, re, platform, sys
from StringIO import StringIO
from functools import partial
from datetime import datetime
from datetime import datetime, time
from string import Template
import urllib
import email
@@ -841,7 +841,7 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
series = story.getMetadata('series')
if not merge and series and prefs['checkforseriesurlid']:
# try to find *series anthology* by *seriesUrl* identifier url or uri first.
searchstr = 'identifiers:"~ur(i|l):=%s"'%story.getMetadata('seriesUrl').replace(":","|")
searchstr = 'identifiers:"~ur(i|l):~^%s$"'%re.sub(r'https?\:','https?(\:|\|)',re.escape(story.getMetadata('seriesUrl')))
identicalbooks = db.search_getting_ids(searchstr, None)
# print("searchstr:%s"%searchstr)
# print("identicalbooks:%s"%identicalbooks)
@@ -918,8 +918,10 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
logger.debug("from URL(%s)"%url)
# try to find by identifier url or uri first.
searchstr = 'identifiers:"~ur(i|l):=%s"'%url.replace(":","|")
searchstr = 'identifiers:"~ur(i|l):~^%s$"'%re.sub(r'https?\:','https?(\:|\|)',url)
identicalbooks = db.search_getting_ids(searchstr, None)
# print("searchstr:%s"%searchstr)
# print("identicalbooks:%s"%identicalbooks)
if len(identicalbooks) < 1:
# find dups
authlist = story.getList("author", removeallentities=True)
@@ -943,7 +945,7 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
raise NotGoingToDownload(_("Skipping duplicate story."),"list_remove.png")
if len(identicalbooks) > 1:
raise NotGoingToDownload("More than one identical book by Identifer URL or title/author(s)--can't tell which book to update/overwrite.","minusminus.png")
raise NotGoingToDownload(_("More than one identical book by Identifer URL or title/author(s)--can't tell which book to update/overwrite."),"minusminus.png")
## changed: add new book when CALIBREONLY if none found.
if collision == CALIBREONLY and not identicalbooks:
@@ -1014,7 +1016,7 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
(epuburl,chaptercount) = \
get_dcsource_chaptercount(StringIO(db.format(book_id,'EPUB',
index_is_id=True)))
urlchaptercount = int(story.getMetadata('numChapters'))
urlchaptercount = int(story.getMetadata('numChapters').replace(',',''))
if chaptercount == urlchaptercount:
if collision == UPDATE:
raise NotGoingToDownload(_("Already contains %d chapters.")%chaptercount,'edit-undo.png')
@@ -1029,10 +1031,16 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
if collision == OVERWRITE and \
db.has_format(book_id,formmapping[fileform],index_is_id=True):
# check make sure incoming is newer.
lastupdated=story.getMetadataRaw('dateUpdated').date()
fileupdated=datetime.fromtimestamp(os.stat(db.format_abspath(book_id, formmapping[fileform], index_is_id=True))[8]).date()
if fileupdated > lastupdated:
lastupdated=story.getMetadataRaw('dateUpdated')
fileupdated=datetime.fromtimestamp(os.stat(db.format_abspath(book_id, formmapping[fileform], index_is_id=True))[8])
# updated doesn't have time (or is midnight), use dates only.
# updated does have time, use full timestamps.
if (lastupdated.time() == time.min and fileupdated.date() > lastupdated.date()) or \
(lastupdated.time() != time.min and fileupdated > lastupdated):
raise NotGoingToDownload(_("Not Overwriting, web site is not newer."),'edit-undo.png')
# For update, provide a tmp file copy of the existing epub so
# it can't change underneath us. Now also overwrite for logpage preserve.
@@ -1601,6 +1609,8 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
db.commit()
if 'Generate Cover' in self.gui.iactions and (book['added'] or not prefs['gcnewonly']):
logger.debug("Do Generate Cover added:%s gcnewonly:%s"%(book['added'],prefs['gcnewonly']))
# force a refresh if generating cover so complex composite
# custom columns are current and correct
@@ -1632,9 +1642,11 @@ class FanFictionDownLoaderPlugin(InterfaceAction):
if not setting_name and book['all_metadata']['site'] in prefs['gc_site_settings']:
setting_name = prefs['gc_site_settings'][book['all_metadata']['site']]
logger.debug("Generate Cover Setting from site(%s)"%setting_name)
if not setting_name and 'Default' in prefs['gc_site_settings']:
setting_name = prefs['gc_site_settings']['Default']
logger.debug("Generate Cover Setting from Default(%s)"%setting_name)
if setting_name:
logger.debug("Running Generate Cover with settings %s."%setting_name)
+1 -1
View File
@@ -182,7 +182,7 @@ def do_download_for_worker(book,options,notification=lambda x,y:x):
# update now handled by pre-populating the old images and
# chapters in the adapter rather than merging epubs.
urlchaptercount = int(story.getMetadata('numChapters'))
urlchaptercount = int(story.getMetadata('numChapters').replace(',',''))
(url,
chaptercount,
adapter.oldchapters,
File diff suppressed because it is too large Load Diff
+143 -137
View File
@@ -5,8 +5,8 @@
msgid ""
msgstr ""
"Project-Id-Version: FanFictionDownLoader 1.8\n"
"POT-Creation-Date: 2013-11-16 09:49+Central Standard Time\n"
"PO-Revision-Date: 2013-11-16 09:51-0600\n"
"POT-Creation-Date: 2013-11-29 10:53+Central Standard Time\n"
"PO-Revision-Date: 2013-11-29 10:54-0600\n"
"Last-Translator: Jim Miller <RetiefJimm@gmail.com>\n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
@@ -445,7 +445,7 @@ msgid ""
"downloads and metadata updates. Pick a GC setting by site or Default."
msgstr ""
#: config.py:709 config.py:713
#: config.py:709 config.py:713 config.py:726
msgid "Default"
msgstr ""
@@ -462,299 +462,299 @@ msgid "On Metadata update, run %(gc)s with this setting for %(site)s stories."
msgstr ""
# %(gc)s = Generate Cover. Keep as is.
#: config.py:735
#: config.py:740
msgid "Run %(gc)s Only on New Books"
msgstr ""
#: config.py:736
#: config.py:741
msgid "Default is to run GC any time the calibre metadata is updated."
msgstr ""
#: config.py:740
#: config.py:745
msgid "Allow %(gcset)s from %(pini)s to override"
msgstr ""
#: config.py:741
#: config.py:746
msgid ""
"The %(pini)s parameter %(gcset)s allows you to choose a GC setting based on "
"metadata rather than site, but it's much more complex.<br \\>%(gcset)s is "
"ignored when this is off."
msgstr ""
#: config.py:755
#: config.py:760
msgid ""
"These settings provide integration with the %(cp)s Plugin. %(cp)s can "
"automatically update custom columns with page, word and reading level "
"statistics. You have to create and configure the columns in %(cp)s first."
msgstr ""
#: config.py:760
#: config.py:765
msgid ""
"If any of the settings below are checked, when stories are added or updated, "
"the %(cp)s Plugin will be called to update the checked statistics."
msgstr ""
#: config.py:766
#: config.py:771
msgid "Which column and algorithm to use are configured in %(cp)s."
msgstr ""
#: config.py:774
#: config.py:779
msgid ""
"Will overwrite word count from FFDL metadata if set to update the same "
"custom column."
msgstr ""
#: config.py:805
#: config.py:810
msgid ""
"These controls aren't plugin settings as such, but convenience buttons for "
"setting Keyboard shortcuts and getting all the FanFictionDownLoader "
"confirmation dialogs back again."
msgstr ""
#: config.py:810
#: config.py:815
msgid "Keyboard shortcuts..."
msgstr ""
#: config.py:811
#: config.py:816
msgid "Edit the keyboard shortcuts associated with this plugin"
msgstr ""
#: config.py:815
#: config.py:820
msgid "Reset disabled &confirmation dialogs"
msgstr ""
#: config.py:816
#: config.py:821
msgid "Reset all show me again dialogs for the FanFictionDownLoader plugin"
msgstr ""
#: config.py:820
#: config.py:825
msgid "&View library preferences..."
msgstr ""
#: config.py:821
#: config.py:826
msgid "View data stored in the library database for this plugin"
msgstr ""
#: config.py:832
#: config.py:837
msgid "Done"
msgstr ""
#: config.py:833
#: config.py:838
msgid "Confirmation dialogs have all been reset"
msgstr ""
#: config.py:881
#: config.py:886
msgid "Category"
msgstr ""
#: config.py:882
#: config.py:887
msgid "Genre"
msgstr ""
#: config.py:883
#: config.py:888
msgid "Language"
msgstr ""
#: config.py:884 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:889 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Status"
msgstr ""
#: config.py:885
#: config.py:890
msgid "Status:%(cmplt)s"
msgstr ""
#: config.py:886
#: config.py:891
msgid "Status:%(inprog)s"
msgstr ""
#: config.py:887 config.py:1021
#: config.py:892 config.py:1026
msgid "Series"
msgstr ""
#: config.py:888
#: config.py:893
msgid "Characters"
msgstr ""
#: config.py:889
#: config.py:894
msgid "Relationships"
msgstr ""
#: config.py:890
#: config.py:895
msgid "Published"
msgstr ""
#: config.py:891 ffdl_plugin.py:1379 ffdl_plugin.py:1395
#: config.py:896 ffdl_plugin.py:1384 ffdl_plugin.py:1400
msgid "Updated"
msgstr ""
#: config.py:892
#: config.py:897
msgid "Created"
msgstr ""
#: config.py:893
#: config.py:898
msgid "Rating"
msgstr ""
#: config.py:894
#: config.py:899
msgid "Warnings"
msgstr ""
#: config.py:895
#: config.py:900
msgid "Chapters"
msgstr ""
#: config.py:896
#: config.py:901
msgid "Words"
msgstr ""
#: config.py:897
#: config.py:902
msgid "Site"
msgstr ""
#: config.py:898
#: config.py:903
msgid "Story ID"
msgstr ""
#: config.py:899
#: config.py:904
msgid "Author ID"
msgstr ""
#: config.py:900
#: config.py:905
msgid "Extra Tags"
msgstr ""
#: config.py:901 config.py:1013 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:906 config.py:1018 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Title"
msgstr ""
#: config.py:902
#: config.py:907
msgid "Story URL"
msgstr ""
#: config.py:903
#: config.py:908
msgid "Description"
msgstr ""
#: config.py:904 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1106
#: ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:909 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1111
#: ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Author"
msgstr ""
#: config.py:905
#: config.py:910
msgid "Author URL"
msgstr ""
#: config.py:906
#: config.py:911
msgid "File Format"
msgstr ""
#: config.py:907
#: config.py:912
msgid "File Extension"
msgstr ""
#: config.py:908
#: config.py:913
msgid "Site Abbrev"
msgstr ""
#: config.py:909
#: config.py:914
msgid "FFDL Version"
msgstr ""
#: config.py:924
#: config.py:929
msgid ""
"If you have custom columns defined, they will be listed below. Choose a "
"metadata value type to fill your columns automatically."
msgstr ""
#: config.py:949
#: config.py:954
msgid "Update this %s column(%s) with..."
msgstr ""
#: config.py:959
#: config.py:964
msgid "Values that aren't valid for this enumeration column will be ignored."
msgstr ""
#: config.py:959 config.py:961
#: config.py:964 config.py:966
msgid "Metadata values valid for this type of column."
msgstr ""
#: config.py:964 config.py:1040
#: config.py:969 config.py:1045
msgid "New Only"
msgstr ""
#: config.py:965
#: config.py:970
msgid ""
"Write to %s(%s) only for new\n"
"books, not updates to existing books."
msgstr ""
#: config.py:976
#: config.py:981
msgid "Allow %(ccset)s from %(pini)s to override"
msgstr ""
#: config.py:977
#: config.py:982
msgid ""
"The %(pini)s parameter %(ccset)s allows you to set custom columns to site "
"specific values that aren't common to all sites.<br />%(ccset)s is ignored "
"when this is off."
msgstr ""
#: config.py:982
#: config.py:987
msgid "Special column:"
msgstr ""
#: config.py:987
#: config.py:992
msgid "Update/Overwrite Error Column:"
msgstr ""
#: config.py:988
#: config.py:993
msgid ""
"When an update or overwrite of an existing story fails, record the reason in "
"this column.\n"
"(Text and Long Text columns only.)"
msgstr ""
#: config.py:1014
#: config.py:1019
msgid "Author(s)"
msgstr ""
#: config.py:1015
#: config.py:1020
msgid "Publisher"
msgstr ""
#: config.py:1016
#: config.py:1021
msgid "Tags"
msgstr ""
#: config.py:1017
#: config.py:1022
msgid "Languages"
msgstr ""
#: config.py:1018
#: config.py:1023
msgid "Published Date"
msgstr ""
#: config.py:1019
#: config.py:1024
msgid "Date"
msgstr ""
#: config.py:1020
#: config.py:1025
msgid "Comments"
msgstr ""
#: config.py:1022
#: config.py:1027
msgid "Ids(url id only)"
msgstr ""
#: config.py:1027
#: config.py:1032
msgid ""
"The standard calibre metadata columns are listed below. You may choose "
"whether FFDL will fill each column automatically on updates or only for new "
"books."
msgstr ""
#: config.py:1041
#: config.py:1046
msgid ""
"Write to %s only for new\n"
"books, not updates to existing books."
@@ -789,7 +789,7 @@ msgid "Update Calibre Metadata Only"
msgstr ""
# title by author
#: dialogs.py:139 ffdl_plugin.py:1945
#: dialogs.py:139 ffdl_plugin.py:1954
msgid "%s by %s"
msgstr ""
@@ -947,7 +947,7 @@ msgid ""
"What sort of update to perform. May set default from plugin configuration."
msgstr ""
#: dialogs.py:792 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: dialogs.py:792 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Comment"
msgstr ""
@@ -1302,276 +1302,282 @@ msgstr ""
msgid "Meta"
msgstr ""
#: ffdl_plugin.py:943
#: ffdl_plugin.py:948
msgid "Skipping duplicate story."
msgstr ""
#: ffdl_plugin.py:957
#: ffdl_plugin.py:951
msgid ""
"More than one identical book by Identifer URL or title/author(s)--can't tell "
"which book to update/overwrite."
msgstr ""
#: ffdl_plugin.py:962
msgid "Update"
msgstr ""
#: ffdl_plugin.py:964 ffdl_plugin.py:971
#: ffdl_plugin.py:969 ffdl_plugin.py:976
msgid "Change Story URL?"
msgstr ""
#: ffdl_plugin.py:972
#: ffdl_plugin.py:977
msgid ""
"<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL:"
msgstr ""
#: ffdl_plugin.py:973
#: ffdl_plugin.py:978
msgid "In library: <a href=\"%(liburl)s\">%(liburl)s</a>"
msgstr ""
#: ffdl_plugin.py:974 ffdl_plugin.py:988
#: ffdl_plugin.py:979 ffdl_plugin.py:993
msgid "New URL: <a href=\"%(newurl)s\">%(newurl)s</a>"
msgstr ""
#: ffdl_plugin.py:975
#: ffdl_plugin.py:980
msgid "Click '<b>Yes</b>' to update/overwrite book with new URL."
msgstr ""
#: ffdl_plugin.py:976
#: ffdl_plugin.py:981
msgid "Click '<b>No</b>' to skip updating/overwriting this book."
msgstr ""
#: ffdl_plugin.py:978 ffdl_plugin.py:985
#: ffdl_plugin.py:983 ffdl_plugin.py:990
msgid "Download as New Book?"
msgstr ""
#: ffdl_plugin.py:986
#: ffdl_plugin.py:991
msgid ""
"<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL."
msgstr ""
#: ffdl_plugin.py:987
#: ffdl_plugin.py:992
msgid ""
"You chose not to update the existing book. Do you want to add a new book "
"for this URL?"
msgstr ""
#: ffdl_plugin.py:989
#: ffdl_plugin.py:994
msgid "Click '<b>Yes</b>' to a new book with new URL."
msgstr ""
#: ffdl_plugin.py:990
#: ffdl_plugin.py:995
msgid "Click '<b>No</b>' to skip URL."
msgstr ""
#: ffdl_plugin.py:996
#: ffdl_plugin.py:1001
msgid "Update declined by user due to differing story URL(%s)"
msgstr ""
#: ffdl_plugin.py:999
#: ffdl_plugin.py:1004
msgid "Different URL"
msgstr ""
#: ffdl_plugin.py:1004
#: ffdl_plugin.py:1009
msgid "Metadata collected."
msgstr ""
#: ffdl_plugin.py:1020
#: ffdl_plugin.py:1025
msgid "Already contains %d chapters."
msgstr ""
#: ffdl_plugin.py:1025
#: ffdl_plugin.py:1030
msgid ""
"Existing epub contains %d chapters, web site only has %d. Use Overwrite to "
"force update."
msgstr ""
#: ffdl_plugin.py:1027
#: ffdl_plugin.py:1032
msgid ""
"FFDL doesn't recognize chapters in existing epub, epub is probably from a "
"different source. Use Overwrite to force update."
msgstr ""
#: ffdl_plugin.py:1035
#: ffdl_plugin.py:1040
msgid "Not Overwriting, web site is not newer."
msgstr ""
#: ffdl_plugin.py:1102
#: ffdl_plugin.py:1107
msgid "None of the <b>%d</b> URLs/stories given can be/need to be downloaded."
msgstr ""
#: ffdl_plugin.py:1103 ffdl_plugin.py:1261 ffdl_plugin.py:1291
#: ffdl_plugin.py:1108 ffdl_plugin.py:1266 ffdl_plugin.py:1296
msgid "See log for details."
msgstr ""
#: ffdl_plugin.py:1104
#: ffdl_plugin.py:1109
msgid "Proceed with updating your library(Error Column, if configured)?"
msgstr ""
#: ffdl_plugin.py:1111 ffdl_plugin.py:1273
#: ffdl_plugin.py:1116 ffdl_plugin.py:1278
msgid "Bad"
msgstr ""
#: ffdl_plugin.py:1119
#: ffdl_plugin.py:1124
msgid "FFDL download ended"
msgstr ""
#: ffdl_plugin.py:1119 ffdl_plugin.py:1316
#: ffdl_plugin.py:1124 ffdl_plugin.py:1321
msgid "FFDL log"
msgstr ""
#: ffdl_plugin.py:1127
#: ffdl_plugin.py:1132
msgid "Download FanFiction Book"
msgstr ""
#: ffdl_plugin.py:1133
#: ffdl_plugin.py:1138
msgid "Starting %d FanFictionDownLoads"
msgstr ""
#: ffdl_plugin.py:1163
#: ffdl_plugin.py:1168
msgid "Story Details:"
msgstr ""
#: ffdl_plugin.py:1166
#: ffdl_plugin.py:1171
msgid "Error Updating Metadata"
msgstr ""
#: ffdl_plugin.py:1167
#: ffdl_plugin.py:1172
msgid ""
"An error has occurred while FFDL was updating calibre's metadata for <a "
"href='%s'>%s</a>."
msgstr ""
#: ffdl_plugin.py:1168
#: ffdl_plugin.py:1173
msgid "The ebook has been updated, but the metadata has not."
msgstr ""
#: ffdl_plugin.py:1220
#: ffdl_plugin.py:1225
msgid "Finished Adding/Updating %d books."
msgstr ""
#: ffdl_plugin.py:1245
#: ffdl_plugin.py:1250
msgid "No Good Stories for Anthology"
msgstr ""
#: ffdl_plugin.py:1246
#: ffdl_plugin.py:1251
msgid ""
"No good stories/updates where downloaded, Anthology creation/update aborted."
msgstr ""
#: ffdl_plugin.py:1251 ffdl_plugin.py:1290
#: ffdl_plugin.py:1256 ffdl_plugin.py:1295
msgid "FFDL found <b>%s</b> good and <b>%s</b> bad updates."
msgstr ""
#: ffdl_plugin.py:1258
#: ffdl_plugin.py:1263
msgid ""
"Are you sure you want to continue with creating/updating this Anthology?"
msgstr ""
#: ffdl_plugin.py:1259
#: ffdl_plugin.py:1264
msgid "Any updates that failed will <b>not</b> be included in the Anthology."
msgstr ""
#: ffdl_plugin.py:1260
#: ffdl_plugin.py:1265
msgid "However, if there's an older version, it will still be included."
msgstr ""
#: ffdl_plugin.py:1263
#: ffdl_plugin.py:1268
msgid "Proceed with updating this anthology and your library?"
msgstr ""
#: ffdl_plugin.py:1271
#: ffdl_plugin.py:1276
msgid "Good"
msgstr ""
#: ffdl_plugin.py:1292
#: ffdl_plugin.py:1297
msgid "Proceed with updating your library?"
msgstr ""
#: ffdl_plugin.py:1316
#: ffdl_plugin.py:1321
msgid "FFDL download complete"
msgstr ""
#: ffdl_plugin.py:1329
#: ffdl_plugin.py:1334
msgid "Merging %s books."
msgstr ""
#: ffdl_plugin.py:1370
#: ffdl_plugin.py:1375
msgid "FFDL Adding/Updating books."
msgstr ""
#: ffdl_plugin.py:1377
#: ffdl_plugin.py:1382
msgid "Updating calibre for FanFiction stories..."
msgstr ""
#: ffdl_plugin.py:1378
#: ffdl_plugin.py:1383
msgid "Update calibre for FanFiction stories"
msgstr ""
#: ffdl_plugin.py:1387
#: ffdl_plugin.py:1392
msgid "Adding/Updating %s BAD books."
msgstr ""
#: ffdl_plugin.py:1393
#: ffdl_plugin.py:1398
msgid "Updating calibre for BAD FanFiction stories..."
msgstr ""
#: ffdl_plugin.py:1394
#: ffdl_plugin.py:1399
msgid "Update calibre for BAD FanFiction stories"
msgstr ""
#: ffdl_plugin.py:1422
#: ffdl_plugin.py:1427
msgid "Adding format to book failed for some reason..."
msgstr ""
#: ffdl_plugin.py:1425
#: ffdl_plugin.py:1430
msgid "Error"
msgstr ""
#: ffdl_plugin.py:1655
#: ffdl_plugin.py:1664
msgid ""
"You configured FanFictionDownLoader to automatically update Reading Lists, "
"but you don't have the %s plugin installed anymore?"
msgstr ""
#: ffdl_plugin.py:1667
#: ffdl_plugin.py:1676
msgid ""
"You configured FanFictionDownLoader to automatically update \"To Read\" "
"Reading Lists, but you don't have any lists set?"
msgstr ""
#: ffdl_plugin.py:1677 ffdl_plugin.py:1695
#: ffdl_plugin.py:1686 ffdl_plugin.py:1704
msgid ""
"You configured FanFictionDownLoader to automatically update Reading List "
"'%s', but you don't have a list of that name?"
msgstr ""
#: ffdl_plugin.py:1683
#: ffdl_plugin.py:1692
msgid ""
"You configured FanFictionDownLoader to automatically update \"Send to Device"
"\" Reading Lists, but you don't have any lists set?"
msgstr ""
#: ffdl_plugin.py:1802
#: ffdl_plugin.py:1811
msgid "No story URL found."
msgstr ""
#: ffdl_plugin.py:1805
#: ffdl_plugin.py:1814
msgid "Not Found"
msgstr ""
#: ffdl_plugin.py:1811
#: ffdl_plugin.py:1820
msgid "URL is not a valid story URL."
msgstr ""
#: ffdl_plugin.py:1814
#: ffdl_plugin.py:1823
msgid "Bad URL"
msgstr ""
#: ffdl_plugin.py:1944
#: ffdl_plugin.py:1953
msgid "Anthology containing:"
msgstr ""
#: ffdl_plugin.py:1965
#: ffdl_plugin.py:1974
msgid " Anthology"
msgstr ""
#: ffdl_plugin.py:2002
#: ffdl_plugin.py:2011
msgid "(was set, removed for security)"
msgstr ""
+140 -136
View File
@@ -5,7 +5,7 @@
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"POT-Creation-Date: 2013-11-16 09:49+Central Standard Time\n"
"POT-Creation-Date: 2013-11-29 10:53+Central Standard Time\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -397,7 +397,7 @@ msgstr ""
msgid "The %(gc)s plugin can create cover images for books using various metadata and configurations. If you have GC installed, FFDL can run GC on new downloads and metadata updates. Pick a GC setting by site or Default."
msgstr ""
#: config.py:709 config.py:713
#: config.py:709 config.py:713 config.py:726
msgid "Default"
msgstr ""
@@ -409,277 +409,277 @@ msgstr ""
msgid "On Metadata update, run %(gc)s with this setting for %(site)s stories."
msgstr ""
#: config.py:735
#: config.py:740
msgid "Run %(gc)s Only on New Books"
msgstr ""
#: config.py:736
#: config.py:741
msgid "Default is to run GC any time the calibre metadata is updated."
msgstr ""
#: config.py:740
#: config.py:745
msgid "Allow %(gcset)s from %(pini)s to override"
msgstr ""
#: config.py:741
#: config.py:746
msgid "The %(pini)s parameter %(gcset)s allows you to choose a GC setting based on metadata rather than site, but it's much more complex.<br \\>%(gcset)s is ignored when this is off."
msgstr ""
#: config.py:755
#: config.py:760
msgid "These settings provide integration with the %(cp)s Plugin. %(cp)s can automatically update custom columns with page, word and reading level statistics. You have to create and configure the columns in %(cp)s first."
msgstr ""
#: config.py:760
#: config.py:765
msgid "If any of the settings below are checked, when stories are added or updated, the %(cp)s Plugin will be called to update the checked statistics."
msgstr ""
#: config.py:766
#: config.py:771
msgid "Which column and algorithm to use are configured in %(cp)s."
msgstr ""
#: config.py:774
#: config.py:779
msgid "Will overwrite word count from FFDL metadata if set to update the same custom column."
msgstr ""
#: config.py:805
#: config.py:810
msgid "These controls aren't plugin settings as such, but convenience buttons for setting Keyboard shortcuts and getting all the FanFictionDownLoader confirmation dialogs back again."
msgstr ""
#: config.py:810
#: config.py:815
msgid "Keyboard shortcuts..."
msgstr ""
#: config.py:811
#: config.py:816
msgid "Edit the keyboard shortcuts associated with this plugin"
msgstr ""
#: config.py:815
#: config.py:820
msgid "Reset disabled &confirmation dialogs"
msgstr ""
#: config.py:816
#: config.py:821
msgid "Reset all show me again dialogs for the FanFictionDownLoader plugin"
msgstr ""
#: config.py:820
#: config.py:825
msgid "&View library preferences..."
msgstr ""
#: config.py:821
#: config.py:826
msgid "View data stored in the library database for this plugin"
msgstr ""
#: config.py:832
#: config.py:837
msgid "Done"
msgstr ""
#: config.py:833
#: config.py:838
msgid "Confirmation dialogs have all been reset"
msgstr ""
#: config.py:881
#: config.py:886
msgid "Category"
msgstr ""
#: config.py:882
#: config.py:887
msgid "Genre"
msgstr ""
#: config.py:883
#: config.py:888
msgid "Language"
msgstr ""
#: config.py:884 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:889 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Status"
msgstr ""
#: config.py:885
#: config.py:890
msgid "Status:%(cmplt)s"
msgstr ""
#: config.py:886
#: config.py:891
msgid "Status:%(inprog)s"
msgstr ""
#: config.py:887 config.py:1021
#: config.py:892 config.py:1026
msgid "Series"
msgstr ""
#: config.py:888
#: config.py:893
msgid "Characters"
msgstr ""
#: config.py:889
#: config.py:894
msgid "Relationships"
msgstr ""
#: config.py:890
#: config.py:895
msgid "Published"
msgstr ""
#: config.py:891 ffdl_plugin.py:1379 ffdl_plugin.py:1395
#: config.py:896 ffdl_plugin.py:1384 ffdl_plugin.py:1400
msgid "Updated"
msgstr ""
#: config.py:892
#: config.py:897
msgid "Created"
msgstr ""
#: config.py:893
#: config.py:898
msgid "Rating"
msgstr ""
#: config.py:894
#: config.py:899
msgid "Warnings"
msgstr ""
#: config.py:895
#: config.py:900
msgid "Chapters"
msgstr ""
#: config.py:896
#: config.py:901
msgid "Words"
msgstr ""
#: config.py:897
#: config.py:902
msgid "Site"
msgstr ""
#: config.py:898
#: config.py:903
msgid "Story ID"
msgstr ""
#: config.py:899
#: config.py:904
msgid "Author ID"
msgstr ""
#: config.py:900
#: config.py:905
msgid "Extra Tags"
msgstr ""
#: config.py:901 config.py:1013 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:906 config.py:1018 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Title"
msgstr ""
#: config.py:902
#: config.py:907
msgid "Story URL"
msgstr ""
#: config.py:903
#: config.py:908
msgid "Description"
msgstr ""
#: config.py:904 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1106
#: ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:909 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1111
#: ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Author"
msgstr ""
#: config.py:905
#: config.py:910
msgid "Author URL"
msgstr ""
#: config.py:906
#: config.py:911
msgid "File Format"
msgstr ""
#: config.py:907
#: config.py:912
msgid "File Extension"
msgstr ""
#: config.py:908
#: config.py:913
msgid "Site Abbrev"
msgstr ""
#: config.py:909
#: config.py:914
msgid "FFDL Version"
msgstr ""
#: config.py:924
#: config.py:929
msgid "If you have custom columns defined, they will be listed below. Choose a metadata value type to fill your columns automatically."
msgstr ""
#: config.py:949
#: config.py:954
msgid "Update this %s column(%s) with..."
msgstr ""
#: config.py:959
#: config.py:964
msgid "Values that aren't valid for this enumeration column will be ignored."
msgstr ""
#: config.py:959 config.py:961
#: config.py:964 config.py:966
msgid "Metadata values valid for this type of column."
msgstr ""
#: config.py:964 config.py:1040
#: config.py:969 config.py:1045
msgid "New Only"
msgstr ""
#: config.py:965
#: config.py:970
msgid ""
"Write to %s(%s) only for new\n"
"books, not updates to existing books."
msgstr ""
#: config.py:976
#: config.py:981
msgid "Allow %(ccset)s from %(pini)s to override"
msgstr ""
#: config.py:977
#: config.py:982
msgid "The %(pini)s parameter %(ccset)s allows you to set custom columns to site specific values that aren't common to all sites.<br />%(ccset)s is ignored when this is off."
msgstr ""
#: config.py:982
#: config.py:987
msgid "Special column:"
msgstr ""
#: config.py:987
#: config.py:992
msgid "Update/Overwrite Error Column:"
msgstr ""
#: config.py:988
#: config.py:993
msgid ""
"When an update or overwrite of an existing story fails, record the reason in this column.\n"
"(Text and Long Text columns only.)"
msgstr ""
#: config.py:1014
#: config.py:1019
msgid "Author(s)"
msgstr ""
#: config.py:1015
#: config.py:1020
msgid "Publisher"
msgstr ""
#: config.py:1016
#: config.py:1021
msgid "Tags"
msgstr ""
#: config.py:1017
#: config.py:1022
msgid "Languages"
msgstr ""
#: config.py:1018
#: config.py:1023
msgid "Published Date"
msgstr ""
#: config.py:1019
#: config.py:1024
msgid "Date"
msgstr ""
#: config.py:1020
#: config.py:1025
msgid "Comments"
msgstr ""
#: config.py:1022
#: config.py:1027
msgid "Ids(url id only)"
msgstr ""
#: config.py:1027
#: config.py:1032
msgid "The standard calibre metadata columns are listed below. You may choose whether FFDL will fill each column automatically on updates or only for new books."
msgstr ""
#: config.py:1041
#: config.py:1046
msgid ""
"Write to %s only for new\n"
"books, not updates to existing books."
@@ -713,7 +713,7 @@ msgstr ""
msgid "Update Calibre Metadata Only"
msgstr ""
#: dialogs.py:139 ffdl_plugin.py:1945
#: dialogs.py:139 ffdl_plugin.py:1954
msgid "%s by %s"
msgstr ""
@@ -862,7 +862,7 @@ msgstr ""
msgid "What sort of update to perform. May set default from plugin configuration."
msgstr ""
#: dialogs.py:792 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: dialogs.py:792 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Comment"
msgstr ""
@@ -1206,255 +1206,259 @@ msgstr ""
msgid "Meta"
msgstr ""
#: ffdl_plugin.py:943
#: ffdl_plugin.py:948
msgid "Skipping duplicate story."
msgstr ""
#: ffdl_plugin.py:957
#: ffdl_plugin.py:951
msgid "More than one identical book by Identifer URL or title/author(s)--can't tell which book to update/overwrite."
msgstr ""
#: ffdl_plugin.py:962
msgid "Update"
msgstr ""
#: ffdl_plugin.py:964 ffdl_plugin.py:971
#: ffdl_plugin.py:969 ffdl_plugin.py:976
msgid "Change Story URL?"
msgstr ""
#: ffdl_plugin.py:972
#: ffdl_plugin.py:977
msgid "<b>%s</b> by <b>%s</b> is already in your library with a different source URL:"
msgstr ""
#: ffdl_plugin.py:973
#: ffdl_plugin.py:978
msgid "In library: <a href=\"%(liburl)s\">%(liburl)s</a>"
msgstr ""
#: ffdl_plugin.py:974 ffdl_plugin.py:988
#: ffdl_plugin.py:979 ffdl_plugin.py:993
msgid "New URL: <a href=\"%(newurl)s\">%(newurl)s</a>"
msgstr ""
#: ffdl_plugin.py:975
#: ffdl_plugin.py:980
msgid "Click '<b>Yes</b>' to update/overwrite book with new URL."
msgstr ""
#: ffdl_plugin.py:976
#: ffdl_plugin.py:981
msgid "Click '<b>No</b>' to skip updating/overwriting this book."
msgstr ""
#: ffdl_plugin.py:978 ffdl_plugin.py:985
#: ffdl_plugin.py:983 ffdl_plugin.py:990
msgid "Download as New Book?"
msgstr ""
#: ffdl_plugin.py:986
#: ffdl_plugin.py:991
msgid "<b>%s</b> by <b>%s</b> is already in your library with a different source URL."
msgstr ""
#: ffdl_plugin.py:987
#: ffdl_plugin.py:992
msgid "You chose not to update the existing book. Do you want to add a new book for this URL?"
msgstr ""
#: ffdl_plugin.py:989
#: ffdl_plugin.py:994
msgid "Click '<b>Yes</b>' to a new book with new URL."
msgstr ""
#: ffdl_plugin.py:990
#: ffdl_plugin.py:995
msgid "Click '<b>No</b>' to skip URL."
msgstr ""
#: ffdl_plugin.py:996
#: ffdl_plugin.py:1001
msgid "Update declined by user due to differing story URL(%s)"
msgstr ""
#: ffdl_plugin.py:999
#: ffdl_plugin.py:1004
msgid "Different URL"
msgstr ""
#: ffdl_plugin.py:1004
#: ffdl_plugin.py:1009
msgid "Metadata collected."
msgstr ""
#: ffdl_plugin.py:1020
#: ffdl_plugin.py:1025
msgid "Already contains %d chapters."
msgstr ""
#: ffdl_plugin.py:1025
#: ffdl_plugin.py:1030
msgid "Existing epub contains %d chapters, web site only has %d. Use Overwrite to force update."
msgstr ""
#: ffdl_plugin.py:1027
#: ffdl_plugin.py:1032
msgid "FFDL doesn't recognize chapters in existing epub, epub is probably from a different source. Use Overwrite to force update."
msgstr ""
#: ffdl_plugin.py:1035
#: ffdl_plugin.py:1040
msgid "Not Overwriting, web site is not newer."
msgstr ""
#: ffdl_plugin.py:1102
#: ffdl_plugin.py:1107
msgid "None of the <b>%d</b> URLs/stories given can be/need to be downloaded."
msgstr ""
#: ffdl_plugin.py:1103 ffdl_plugin.py:1261 ffdl_plugin.py:1291
#: ffdl_plugin.py:1108 ffdl_plugin.py:1266 ffdl_plugin.py:1296
msgid "See log for details."
msgstr ""
#: ffdl_plugin.py:1104
#: ffdl_plugin.py:1109
msgid "Proceed with updating your library(Error Column, if configured)?"
msgstr ""
#: ffdl_plugin.py:1111 ffdl_plugin.py:1273
#: ffdl_plugin.py:1116 ffdl_plugin.py:1278
msgid "Bad"
msgstr ""
#: ffdl_plugin.py:1119
#: ffdl_plugin.py:1124
msgid "FFDL download ended"
msgstr ""
#: ffdl_plugin.py:1119 ffdl_plugin.py:1316
#: ffdl_plugin.py:1124 ffdl_plugin.py:1321
msgid "FFDL log"
msgstr ""
#: ffdl_plugin.py:1127
#: ffdl_plugin.py:1132
msgid "Download FanFiction Book"
msgstr ""
#: ffdl_plugin.py:1133
#: ffdl_plugin.py:1138
msgid "Starting %d FanFictionDownLoads"
msgstr ""
#: ffdl_plugin.py:1163
#: ffdl_plugin.py:1168
msgid "Story Details:"
msgstr ""
#: ffdl_plugin.py:1166
#: ffdl_plugin.py:1171
msgid "Error Updating Metadata"
msgstr ""
#: ffdl_plugin.py:1167
#: ffdl_plugin.py:1172
msgid "An error has occurred while FFDL was updating calibre's metadata for <a href='%s'>%s</a>."
msgstr ""
#: ffdl_plugin.py:1168
#: ffdl_plugin.py:1173
msgid "The ebook has been updated, but the metadata has not."
msgstr ""
#: ffdl_plugin.py:1220
#: ffdl_plugin.py:1225
msgid "Finished Adding/Updating %d books."
msgstr ""
#: ffdl_plugin.py:1245
#: ffdl_plugin.py:1250
msgid "No Good Stories for Anthology"
msgstr ""
#: ffdl_plugin.py:1246
#: ffdl_plugin.py:1251
msgid "No good stories/updates where downloaded, Anthology creation/update aborted."
msgstr ""
#: ffdl_plugin.py:1251 ffdl_plugin.py:1290
#: ffdl_plugin.py:1256 ffdl_plugin.py:1295
msgid "FFDL found <b>%s</b> good and <b>%s</b> bad updates."
msgstr ""
#: ffdl_plugin.py:1258
#: ffdl_plugin.py:1263
msgid "Are you sure you want to continue with creating/updating this Anthology?"
msgstr ""
#: ffdl_plugin.py:1259
#: ffdl_plugin.py:1264
msgid "Any updates that failed will <b>not</b> be included in the Anthology."
msgstr ""
#: ffdl_plugin.py:1260
#: ffdl_plugin.py:1265
msgid "However, if there's an older version, it will still be included."
msgstr ""
#: ffdl_plugin.py:1263
#: ffdl_plugin.py:1268
msgid "Proceed with updating this anthology and your library?"
msgstr ""
#: ffdl_plugin.py:1271
#: ffdl_plugin.py:1276
msgid "Good"
msgstr ""
#: ffdl_plugin.py:1292
#: ffdl_plugin.py:1297
msgid "Proceed with updating your library?"
msgstr ""
#: ffdl_plugin.py:1316
#: ffdl_plugin.py:1321
msgid "FFDL download complete"
msgstr ""
#: ffdl_plugin.py:1329
#: ffdl_plugin.py:1334
msgid "Merging %s books."
msgstr ""
#: ffdl_plugin.py:1370
#: ffdl_plugin.py:1375
msgid "FFDL Adding/Updating books."
msgstr ""
#: ffdl_plugin.py:1377
#: ffdl_plugin.py:1382
msgid "Updating calibre for FanFiction stories..."
msgstr ""
#: ffdl_plugin.py:1378
#: ffdl_plugin.py:1383
msgid "Update calibre for FanFiction stories"
msgstr ""
#: ffdl_plugin.py:1387
#: ffdl_plugin.py:1392
msgid "Adding/Updating %s BAD books."
msgstr ""
#: ffdl_plugin.py:1393
#: ffdl_plugin.py:1398
msgid "Updating calibre for BAD FanFiction stories..."
msgstr ""
#: ffdl_plugin.py:1394
#: ffdl_plugin.py:1399
msgid "Update calibre for BAD FanFiction stories"
msgstr ""
#: ffdl_plugin.py:1422
#: ffdl_plugin.py:1427
msgid "Adding format to book failed for some reason..."
msgstr ""
#: ffdl_plugin.py:1425
#: ffdl_plugin.py:1430
msgid "Error"
msgstr ""
#: ffdl_plugin.py:1655
#: ffdl_plugin.py:1664
msgid "You configured FanFictionDownLoader to automatically update Reading Lists, but you don't have the %s plugin installed anymore?"
msgstr ""
#: ffdl_plugin.py:1667
#: ffdl_plugin.py:1676
msgid "You configured FanFictionDownLoader to automatically update \"To Read\" Reading Lists, but you don't have any lists set?"
msgstr ""
#: ffdl_plugin.py:1677 ffdl_plugin.py:1695
#: ffdl_plugin.py:1686 ffdl_plugin.py:1704
msgid "You configured FanFictionDownLoader to automatically update Reading List '%s', but you don't have a list of that name?"
msgstr ""
#: ffdl_plugin.py:1683
#: ffdl_plugin.py:1692
msgid "You configured FanFictionDownLoader to automatically update \"Send to Device\" Reading Lists, but you don't have any lists set?"
msgstr ""
#: ffdl_plugin.py:1802
#: ffdl_plugin.py:1811
msgid "No story URL found."
msgstr ""
#: ffdl_plugin.py:1805
#: ffdl_plugin.py:1814
msgid "Not Found"
msgstr ""
#: ffdl_plugin.py:1811
#: ffdl_plugin.py:1820
msgid "URL is not a valid story URL."
msgstr ""
#: ffdl_plugin.py:1814
#: ffdl_plugin.py:1823
msgid "Bad URL"
msgstr ""
#: ffdl_plugin.py:1944
#: ffdl_plugin.py:1953
msgid "Anthology containing:"
msgstr ""
#: ffdl_plugin.py:1965
#: ffdl_plugin.py:1974
msgid " Anthology"
msgstr ""
#: ffdl_plugin.py:2002
#: ffdl_plugin.py:2011
msgid "(was set, removed for security)"
msgstr ""
+145 -137
View File
@@ -5,8 +5,8 @@
msgid ""
msgstr ""
"Project-Id-Version: FanFictionDownLoader 1.8\n"
"POT-Creation-Date: 2013-11-16 09:49+Central Standard Time\n"
"PO-Revision-Date: 2013-11-16 09:51-0600\n"
"POT-Creation-Date: 2013-11-29 10:53+Central Standard Time\n"
"PO-Revision-Date: 2013-11-30 16:54-0600\n"
"Last-Translator: Jim Miller <RetiefJimm@gmail.com>\n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
@@ -530,7 +530,7 @@ msgstr ""
"and configurations. If you have GC installed, FFDL can run GC on new "
"downloads and metadata updates. Pick a GC setting by site or Default."
#: config.py:709 config.py:713
#: config.py:709 config.py:713 config.py:726
msgid "Default"
msgstr "zzDefault"
@@ -550,19 +550,19 @@ msgstr ""
"zzOn Metadata update, run %(gc)s with this setting for %(site)s stories."
# %(gc)s = Generate Cover. Keep as is.
#: config.py:735
#: config.py:740
msgid "Run %(gc)s Only on New Books"
msgstr "zzRun %(gc)s Only on New Books"
#: config.py:736
#: config.py:741
msgid "Default is to run GC any time the calibre metadata is updated."
msgstr "zzDefault is to run GC any time the calibre metadata is updated."
#: config.py:740
#: config.py:745
msgid "Allow %(gcset)s from %(pini)s to override"
msgstr "zzAllow %(gcset)s from %(pini)s to override"
#: config.py:741
#: config.py:746
msgid ""
"The %(pini)s parameter %(gcset)s allows you to choose a GC setting based on "
"metadata rather than site, but it's much more complex.<br \\>%(gcset)s is "
@@ -572,7 +572,7 @@ msgstr ""
"on metadata rather than site, but it's much more complex.<br \\>%(gcset)s is "
"ignored when this is off."
#: config.py:755
#: config.py:760
msgid ""
"These settings provide integration with the %(cp)s Plugin. %(cp)s can "
"automatically update custom columns with page, word and reading level "
@@ -582,7 +582,7 @@ msgstr ""
"automatically update custom columns with page, word and reading level "
"statistics. You have to create and configure the columns in %(cp)s first."
#: config.py:760
#: config.py:765
msgid ""
"If any of the settings below are checked, when stories are added or updated, "
"the %(cp)s Plugin will be called to update the checked statistics."
@@ -590,11 +590,11 @@ msgstr ""
"zzIf any of the settings below are checked, when stories are added or "
"updated, the %(cp)s Plugin will be called to update the checked statistics."
#: config.py:766
#: config.py:771
msgid "Which column and algorithm to use are configured in %(cp)s."
msgstr "zzWhich column and algorithm to use are configured in %(cp)s."
#: config.py:774
#: config.py:779
msgid ""
"Will overwrite word count from FFDL metadata if set to update the same "
"custom column."
@@ -602,7 +602,7 @@ msgstr ""
"zzWill overwrite word count from FFDL metadata if set to update the same "
"custom column."
#: config.py:805
#: config.py:810
msgid ""
"These controls aren't plugin settings as such, but convenience buttons for "
"setting Keyboard shortcuts and getting all the FanFictionDownLoader "
@@ -612,157 +612,157 @@ msgstr ""
"setting Keyboard shortcuts and getting all the FanFictionDownLoader "
"confirmation dialogs back again."
#: config.py:810
#: config.py:815
msgid "Keyboard shortcuts..."
msgstr "zzKeyboard shortcuts..."
#: config.py:811
#: config.py:816
msgid "Edit the keyboard shortcuts associated with this plugin"
msgstr "zzEdit the keyboard shortcuts associated with this plugin"
#: config.py:815
#: config.py:820
msgid "Reset disabled &confirmation dialogs"
msgstr "zzReset disabled &confirmation dialogs"
#: config.py:816
#: config.py:821
msgid "Reset all show me again dialogs for the FanFictionDownLoader plugin"
msgstr "zzReset all show me again dialogs for the FanFictionDownLoader plugin"
#: config.py:820
#: config.py:825
msgid "&View library preferences..."
msgstr "zz&View library preferences..."
#: config.py:821
#: config.py:826
msgid "View data stored in the library database for this plugin"
msgstr "zzView data stored in the library database for this plugin"
#: config.py:832
#: config.py:837
msgid "Done"
msgstr "zzDone"
#: config.py:833
#: config.py:838
msgid "Confirmation dialogs have all been reset"
msgstr "zzConfirmation dialogs have all been reset"
#: config.py:881
#: config.py:886
msgid "Category"
msgstr "zzCategory"
#: config.py:882
#: config.py:887
msgid "Genre"
msgstr "zzGenre"
#: config.py:883
#: config.py:888
msgid "Language"
msgstr "zzLanguage"
#: config.py:884 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:889 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Status"
msgstr "zzStatus"
#: config.py:885
#: config.py:890
msgid "Status:%(cmplt)s"
msgstr "zzStatus:%(cmplt)s"
#: config.py:886
#: config.py:891
msgid "Status:%(inprog)s"
msgstr "zzStatus:%(inprog)s"
#: config.py:887 config.py:1021
#: config.py:892 config.py:1026
msgid "Series"
msgstr "zzSeries"
#: config.py:888
#: config.py:893
msgid "Characters"
msgstr "zzCharacters"
#: config.py:889
#: config.py:894
msgid "Relationships"
msgstr "zzRelationships"
#: config.py:890
#: config.py:895
msgid "Published"
msgstr "zzPublished"
#: config.py:891 ffdl_plugin.py:1379 ffdl_plugin.py:1395
#: config.py:896 ffdl_plugin.py:1384 ffdl_plugin.py:1400
msgid "Updated"
msgstr "zzUpdated"
#: config.py:892
#: config.py:897
msgid "Created"
msgstr "zzCreated"
#: config.py:893
#: config.py:898
msgid "Rating"
msgstr "zzRating"
#: config.py:894
#: config.py:899
msgid "Warnings"
msgstr "zzWarnings"
#: config.py:895
#: config.py:900
msgid "Chapters"
msgstr "zzChapters"
#: config.py:896
#: config.py:901
msgid "Words"
msgstr "zzWords"
#: config.py:897
#: config.py:902
msgid "Site"
msgstr "zzSite"
#: config.py:898
#: config.py:903
msgid "Story ID"
msgstr "zzStory ID"
#: config.py:899
#: config.py:904
msgid "Author ID"
msgstr "zzAuthor ID"
#: config.py:900
#: config.py:905
msgid "Extra Tags"
msgstr "zzExtra Tags"
#: config.py:901 config.py:1013 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:906 config.py:1018 dialogs.py:792 dialogs.py:888
#: ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Title"
msgstr "zzTitle"
#: config.py:902
#: config.py:907
msgid "Story URL"
msgstr "zzStory URL"
#: config.py:903
#: config.py:908
msgid "Description"
msgstr "zzDescription"
#: config.py:904 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1106
#: ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: config.py:909 dialogs.py:792 dialogs.py:888 ffdl_plugin.py:1111
#: ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Author"
msgstr "zzAuthor"
#: config.py:905
#: config.py:910
msgid "Author URL"
msgstr "zzAuthor URL"
#: config.py:906
#: config.py:911
msgid "File Format"
msgstr "zzFile Format"
#: config.py:907
#: config.py:912
msgid "File Extension"
msgstr "zzFile Extension"
#: config.py:908
#: config.py:913
msgid "Site Abbrev"
msgstr "zzSite Abbrev"
#: config.py:909
#: config.py:914
msgid "FFDL Version"
msgstr "zzFFDL Version"
#: config.py:924
#: config.py:929
msgid ""
"If you have custom columns defined, they will be listed below. Choose a "
"metadata value type to fill your columns automatically."
@@ -770,24 +770,24 @@ msgstr ""
"zzIf you have custom columns defined, they will be listed below. Choose a "
"metadata value type to fill your columns automatically."
#: config.py:949
#: config.py:954
msgid "Update this %s column(%s) with..."
msgstr "zzUpdate this %s column(%s) with..."
#: config.py:959
#: config.py:964
msgid "Values that aren't valid for this enumeration column will be ignored."
msgstr ""
"zzValues that aren't valid for this enumeration column will be ignored."
#: config.py:959 config.py:961
#: config.py:964 config.py:966
msgid "Metadata values valid for this type of column."
msgstr "zzMetadata values valid for this type of column."
#: config.py:964 config.py:1040
#: config.py:969 config.py:1045
msgid "New Only"
msgstr "zzNew Only"
#: config.py:965
#: config.py:970
msgid ""
"Write to %s(%s) only for new\n"
"books, not updates to existing books."
@@ -795,11 +795,11 @@ msgstr ""
"zzWrite to %s(%s) only for new\n"
"books, not updates to existing books."
#: config.py:976
#: config.py:981
msgid "Allow %(ccset)s from %(pini)s to override"
msgstr "zzAllow %(ccset)s from %(pini)s to override"
#: config.py:977
#: config.py:982
msgid ""
"The %(pini)s parameter %(ccset)s allows you to set custom columns to site "
"specific values that aren't common to all sites.<br />%(ccset)s is ignored "
@@ -809,15 +809,15 @@ msgstr ""
"specific values that aren't common to all sites.<br />%(ccset)s is ignored "
"when this is off."
#: config.py:982
#: config.py:987
msgid "Special column:"
msgstr "zzSpecial column:"
#: config.py:987
#: config.py:992
msgid "Update/Overwrite Error Column:"
msgstr "zzUpdate/Overwrite Error Column:"
#: config.py:988
#: config.py:993
msgid ""
"When an update or overwrite of an existing story fails, record the reason in "
"this column.\n"
@@ -827,39 +827,39 @@ msgstr ""
"in this column.\n"
"(Text and Long Text columns only.)"
#: config.py:1014
#: config.py:1019
msgid "Author(s)"
msgstr "zzAuthor(s)"
#: config.py:1015
#: config.py:1020
msgid "Publisher"
msgstr "zzPublisher"
#: config.py:1016
#: config.py:1021
msgid "Tags"
msgstr "zzTags"
#: config.py:1017
#: config.py:1022
msgid "Languages"
msgstr "zzLanguages"
#: config.py:1018
#: config.py:1023
msgid "Published Date"
msgstr "zzPublished Date"
#: config.py:1019
#: config.py:1024
msgid "Date"
msgstr "zzDate"
#: config.py:1020
#: config.py:1025
msgid "Comments"
msgstr "zzComments"
#: config.py:1022
#: config.py:1027
msgid "Ids(url id only)"
msgstr "zzIds(url id only)"
#: config.py:1027
#: config.py:1032
msgid ""
"The standard calibre metadata columns are listed below. You may choose "
"whether FFDL will fill each column automatically on updates or only for new "
@@ -869,7 +869,7 @@ msgstr ""
"whether FFDL will fill each column automatically on updates or only for new "
"books."
#: config.py:1041
#: config.py:1046
msgid ""
"Write to %s only for new\n"
"books, not updates to existing books."
@@ -906,7 +906,7 @@ msgid "Update Calibre Metadata Only"
msgstr "zzUpdate Calibre Metadata Only"
# title by author
#: dialogs.py:139 ffdl_plugin.py:1945
#: dialogs.py:139 ffdl_plugin.py:1954
msgid "%s by %s"
msgstr "zz%s by %s"
@@ -1082,7 +1082,7 @@ msgid ""
msgstr ""
"zzWhat sort of update to perform. May set default from plugin configuration."
#: dialogs.py:792 ffdl_plugin.py:1106 ffdl_plugin.py:1265 ffdl_plugin.py:1295
#: dialogs.py:792 ffdl_plugin.py:1111 ffdl_plugin.py:1270 ffdl_plugin.py:1300
msgid "Comment"
msgstr "zzComment"
@@ -1448,19 +1448,27 @@ msgstr "zzAdd"
msgid "Meta"
msgstr "zzMeta"
#: ffdl_plugin.py:943
#: ffdl_plugin.py:948
msgid "Skipping duplicate story."
msgstr "zzSkipping duplicate story."
#: ffdl_plugin.py:957
#: ffdl_plugin.py:951
msgid ""
"More than one identical book by Identifer URL or title/author(s)--can't tell "
"which book to update/overwrite."
msgstr ""
"zzMore than one identical book by Identifer URL or title/author(s)--can't "
"tell which book to update/overwrite."
#: ffdl_plugin.py:962
msgid "Update"
msgstr "zzUpdate"
#: ffdl_plugin.py:964 ffdl_plugin.py:971
#: ffdl_plugin.py:969 ffdl_plugin.py:976
msgid "Change Story URL?"
msgstr "zzChange Story URL?"
#: ffdl_plugin.py:972
#: ffdl_plugin.py:977
msgid ""
"<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL:"
@@ -1468,27 +1476,27 @@ msgstr ""
"zz<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL:"
#: ffdl_plugin.py:973
#: ffdl_plugin.py:978
msgid "In library: <a href=\"%(liburl)s\">%(liburl)s</a>"
msgstr "zzIn library: <a href=\"%(liburl)s\">%(liburl)s</a>"
#: ffdl_plugin.py:974 ffdl_plugin.py:988
#: ffdl_plugin.py:979 ffdl_plugin.py:993
msgid "New URL: <a href=\"%(newurl)s\">%(newurl)s</a>"
msgstr "zzNew URL: <a href=\"%(newurl)s\">%(newurl)s</a>"
#: ffdl_plugin.py:975
#: ffdl_plugin.py:980
msgid "Click '<b>Yes</b>' to update/overwrite book with new URL."
msgstr "zzClick '<b>Yes</b>' to update/overwrite book with new URL."
#: ffdl_plugin.py:976
#: ffdl_plugin.py:981
msgid "Click '<b>No</b>' to skip updating/overwriting this book."
msgstr "zzClick '<b>No</b>' to skip updating/overwriting this book."
#: ffdl_plugin.py:978 ffdl_plugin.py:985
#: ffdl_plugin.py:983 ffdl_plugin.py:990
msgid "Download as New Book?"
msgstr "zzDownload as New Book?"
#: ffdl_plugin.py:986
#: ffdl_plugin.py:991
msgid ""
"<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL."
@@ -1496,7 +1504,7 @@ msgstr ""
"zz<b>%s</b> by <b>%s</b> is already in your library with a different source "
"URL."
#: ffdl_plugin.py:987
#: ffdl_plugin.py:992
msgid ""
"You chose not to update the existing book. Do you want to add a new book "
"for this URL?"
@@ -1504,31 +1512,31 @@ msgstr ""
"zzYou chose not to update the existing book. Do you want to add a new book "
"for this URL?"
#: ffdl_plugin.py:989
#: ffdl_plugin.py:994
msgid "Click '<b>Yes</b>' to a new book with new URL."
msgstr "zzClick '<b>Yes</b>' to a new book with new URL."
#: ffdl_plugin.py:990
#: ffdl_plugin.py:995
msgid "Click '<b>No</b>' to skip URL."
msgstr "zzClick '<b>No</b>' to skip URL."
#: ffdl_plugin.py:996
#: ffdl_plugin.py:1001
msgid "Update declined by user due to differing story URL(%s)"
msgstr "zzUpdate declined by user due to differing story URL(%s)"
#: ffdl_plugin.py:999
#: ffdl_plugin.py:1004
msgid "Different URL"
msgstr "zzDifferent URL"
#: ffdl_plugin.py:1004
#: ffdl_plugin.py:1009
msgid "Metadata collected."
msgstr "zzMetadata collected."
#: ffdl_plugin.py:1020
#: ffdl_plugin.py:1025
msgid "Already contains %d chapters."
msgstr "zzAlready contains %d chapters."
#: ffdl_plugin.py:1025
#: ffdl_plugin.py:1030
msgid ""
"Existing epub contains %d chapters, web site only has %d. Use Overwrite to "
"force update."
@@ -1536,7 +1544,7 @@ msgstr ""
"zzExisting epub contains %d chapters, web site only has %d. Use Overwrite to "
"force update."
#: ffdl_plugin.py:1027
#: ffdl_plugin.py:1032
msgid ""
"FFDL doesn't recognize chapters in existing epub, epub is probably from a "
"different source. Use Overwrite to force update."
@@ -1544,52 +1552,52 @@ msgstr ""
"zzFFDL doesn't recognize chapters in existing epub, epub is probably from a "
"different source. Use Overwrite to force update."
#: ffdl_plugin.py:1035
#: ffdl_plugin.py:1040
msgid "Not Overwriting, web site is not newer."
msgstr "zzNot Overwriting, web site is not newer."
#: ffdl_plugin.py:1102
#: ffdl_plugin.py:1107
msgid "None of the <b>%d</b> URLs/stories given can be/need to be downloaded."
msgstr ""
"zzNone of the <b>%d</b> URLs/stories given can be/need to be downloaded."
#: ffdl_plugin.py:1103 ffdl_plugin.py:1261 ffdl_plugin.py:1291
#: ffdl_plugin.py:1108 ffdl_plugin.py:1266 ffdl_plugin.py:1296
msgid "See log for details."
msgstr "zzSee log for details."
#: ffdl_plugin.py:1104
#: ffdl_plugin.py:1109
msgid "Proceed with updating your library(Error Column, if configured)?"
msgstr "zzProceed with updating your library(Error Column, if configured)?"
#: ffdl_plugin.py:1111 ffdl_plugin.py:1273
#: ffdl_plugin.py:1116 ffdl_plugin.py:1278
msgid "Bad"
msgstr "zzBad"
#: ffdl_plugin.py:1119
#: ffdl_plugin.py:1124
msgid "FFDL download ended"
msgstr "zzFFDL download ended"
#: ffdl_plugin.py:1119 ffdl_plugin.py:1316
#: ffdl_plugin.py:1124 ffdl_plugin.py:1321
msgid "FFDL log"
msgstr "zzFFDL log"
#: ffdl_plugin.py:1127
#: ffdl_plugin.py:1132
msgid "Download FanFiction Book"
msgstr "zzDownload FanFiction Book"
#: ffdl_plugin.py:1133
#: ffdl_plugin.py:1138
msgid "Starting %d FanFictionDownLoads"
msgstr "zzStarting %d FanFictionDownLoads"
#: ffdl_plugin.py:1163
#: ffdl_plugin.py:1168
msgid "Story Details:"
msgstr "zzStory Details:"
#: ffdl_plugin.py:1166
#: ffdl_plugin.py:1171
msgid "Error Updating Metadata"
msgstr "zzError Updating Metadata"
#: ffdl_plugin.py:1167
#: ffdl_plugin.py:1172
msgid ""
"An error has occurred while FFDL was updating calibre's metadata for <a "
"href='%s'>%s</a>."
@@ -1597,97 +1605,97 @@ msgstr ""
"zzAn error has occurred while FFDL was updating calibre's metadata for <a "
"href='%s'>%s</a>."
#: ffdl_plugin.py:1168
#: ffdl_plugin.py:1173
msgid "The ebook has been updated, but the metadata has not."
msgstr "zzThe ebook has been updated, but the metadata has not."
#: ffdl_plugin.py:1220
#: ffdl_plugin.py:1225
msgid "Finished Adding/Updating %d books."
msgstr "zzFinished Adding/Updating %d books."
#: ffdl_plugin.py:1245
#: ffdl_plugin.py:1250
msgid "No Good Stories for Anthology"
msgstr "zzNo Good Stories for Anthology"
#: ffdl_plugin.py:1246
#: ffdl_plugin.py:1251
msgid ""
"No good stories/updates where downloaded, Anthology creation/update aborted."
msgstr ""
"zzNo good stories/updates where downloaded, Anthology creation/update "
"aborted."
#: ffdl_plugin.py:1251 ffdl_plugin.py:1290
#: ffdl_plugin.py:1256 ffdl_plugin.py:1295
msgid "FFDL found <b>%s</b> good and <b>%s</b> bad updates."
msgstr "zzFFDL found <b>%s</b> good and <b>%s</b> bad updates."
#: ffdl_plugin.py:1258
#: ffdl_plugin.py:1263
msgid ""
"Are you sure you want to continue with creating/updating this Anthology?"
msgstr ""
"zzAre you sure you want to continue with creating/updating this Anthology?"
#: ffdl_plugin.py:1259
#: ffdl_plugin.py:1264
msgid "Any updates that failed will <b>not</b> be included in the Anthology."
msgstr ""
"zzAny updates that failed will <b>not</b> be included in the Anthology."
#: ffdl_plugin.py:1260
#: ffdl_plugin.py:1265
msgid "However, if there's an older version, it will still be included."
msgstr "zzHowever, if there's an older version, it will still be included."
#: ffdl_plugin.py:1263
#: ffdl_plugin.py:1268
msgid "Proceed with updating this anthology and your library?"
msgstr "zzProceed with updating this anthology and your library?"
#: ffdl_plugin.py:1271
#: ffdl_plugin.py:1276
msgid "Good"
msgstr "zzGood"
#: ffdl_plugin.py:1292
#: ffdl_plugin.py:1297
msgid "Proceed with updating your library?"
msgstr "zzProceed with updating your library?"
#: ffdl_plugin.py:1316
#: ffdl_plugin.py:1321
msgid "FFDL download complete"
msgstr "zzFFDL download complete"
#: ffdl_plugin.py:1329
#: ffdl_plugin.py:1334
msgid "Merging %s books."
msgstr "zzMerging %s books."
#: ffdl_plugin.py:1370
#: ffdl_plugin.py:1375
msgid "FFDL Adding/Updating books."
msgstr "zzFFDL Adding/Updating books."
#: ffdl_plugin.py:1377
#: ffdl_plugin.py:1382
msgid "Updating calibre for FanFiction stories..."
msgstr "zzUpdating calibre for FanFiction stories..."
#: ffdl_plugin.py:1378
#: ffdl_plugin.py:1383
msgid "Update calibre for FanFiction stories"
msgstr "zzUpdate calibre for FanFiction stories"
#: ffdl_plugin.py:1387
#: ffdl_plugin.py:1392
msgid "Adding/Updating %s BAD books."
msgstr "zzAdding/Updating %s BAD books."
#: ffdl_plugin.py:1393
#: ffdl_plugin.py:1398
msgid "Updating calibre for BAD FanFiction stories..."
msgstr "zzUpdating calibre for BAD FanFiction stories..."
#: ffdl_plugin.py:1394
#: ffdl_plugin.py:1399
msgid "Update calibre for BAD FanFiction stories"
msgstr "zzUpdate calibre for BAD FanFiction stories"
#: ffdl_plugin.py:1422
#: ffdl_plugin.py:1427
msgid "Adding format to book failed for some reason..."
msgstr "zzAdding format to book failed for some reason..."
#: ffdl_plugin.py:1425
#: ffdl_plugin.py:1430
msgid "Error"
msgstr "zzError"
#: ffdl_plugin.py:1655
#: ffdl_plugin.py:1664
msgid ""
"You configured FanFictionDownLoader to automatically update Reading Lists, "
"but you don't have the %s plugin installed anymore?"
@@ -1695,7 +1703,7 @@ msgstr ""
"zzYou configured FanFictionDownLoader to automatically update Reading Lists, "
"but you don't have the %s plugin installed anymore?"
#: ffdl_plugin.py:1667
#: ffdl_plugin.py:1676
msgid ""
"You configured FanFictionDownLoader to automatically update \"To Read\" "
"Reading Lists, but you don't have any lists set?"
@@ -1703,7 +1711,7 @@ msgstr ""
"zzYou configured FanFictionDownLoader to automatically update \"To Read\" "
"Reading Lists, but you don't have any lists set?"
#: ffdl_plugin.py:1677 ffdl_plugin.py:1695
#: ffdl_plugin.py:1686 ffdl_plugin.py:1704
msgid ""
"You configured FanFictionDownLoader to automatically update Reading List "
"'%s', but you don't have a list of that name?"
@@ -1711,7 +1719,7 @@ msgstr ""
"zzYou configured FanFictionDownLoader to automatically update Reading List "
"'%s', but you don't have a list of that name?"
#: ffdl_plugin.py:1683
#: ffdl_plugin.py:1692
msgid ""
"You configured FanFictionDownLoader to automatically update \"Send to Device"
"\" Reading Lists, but you don't have any lists set?"
@@ -1719,30 +1727,30 @@ msgstr ""
"zzYou configured FanFictionDownLoader to automatically update \"Send to "
"Device\" Reading Lists, but you don't have any lists set?"
#: ffdl_plugin.py:1802
#: ffdl_plugin.py:1811
msgid "No story URL found."
msgstr "zzNo story URL found."
#: ffdl_plugin.py:1805
#: ffdl_plugin.py:1814
msgid "Not Found"
msgstr "zzNot Found"
#: ffdl_plugin.py:1811
#: ffdl_plugin.py:1820
msgid "URL is not a valid story URL."
msgstr "zzURL is not a valid story URL."
#: ffdl_plugin.py:1814
#: ffdl_plugin.py:1823
msgid "Bad URL"
msgstr "zzBad URL"
#: ffdl_plugin.py:1944
#: ffdl_plugin.py:1953
msgid "Anthology containing:"
msgstr "zzAnthology containing:"
#: ffdl_plugin.py:1965
#: ffdl_plugin.py:1974
msgid " Anthology"
msgstr "zz Anthology"
#: ffdl_plugin.py:2002
#: ffdl_plugin.py:2011
msgid "(was set, removed for security)"
msgstr "zz(was set, removed for security)"
+225 -176
View File
@@ -473,7 +473,8 @@ remove_transparency: true
## confused and displays it on every page after that under the text
## for the rest of the chapter. I doubt adding a div around the img
## will break any other readers, but in case it does, the fix can be
## turned off.
## turned off. This setting is not used if replace_br_with_p is
## true--replace_br_with_p also fixes the problem.
nook_img_fix:true
[mobi]
@@ -537,6 +538,13 @@ extratags: FanFiction,Testing,HTML
## personal.ini, not defaults.ini.
#is_adult:true
## archiveofourown.org stories allow chapters to be added out of
## order. So the newest chapter may not be the last one. FFDL update
## doesn't like that. If do_update_hook is uncommented and set true,
## the adapter will discard all existing chapters from the newest one
## on when updating to enforce accurate chapters.
#do_update_hook:false
## AO3 adapter defines a few extra metadata entries.
## If there's ever more than 4 series, add series04,series04Url etc.
extra_valid_entries:fandoms,freeformtags,freefromtags,ao3categories,comments,kudos,hits,bookmarks,collections,series00,series01,series02,series03,series00Url,series01Url,series02Url,series03Url
@@ -561,11 +569,6 @@ include_in_freefromtags:freeformtags
#extra_subject_tags:fandoms,freeformtags,ao3categories
[ashwinder.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Hermione Granger
extraships:Severus Snape/Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -573,6 +576,11 @@ extraships:Severus Snape/Hermione Granger
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Hermione Granger
extraships:Severus Snape/Hermione Granger
[asr3.slashzone.org]
## Site dedicated to these categories/characters/ships
extracategories:The Sentinel
@@ -583,9 +591,6 @@ extracategories:The Sentinel
#is_adult:true
[bloodties-fans.com]
## Site dedicated to these categories/characters/ships
extracategories:Blood Ties
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -598,6 +603,9 @@ extracategories:Blood Ties
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Blood Ties
[buffynfaith.net]
## Site dedicated to these categories/characters/ships
extracategories:Buffy: The Vampire Slayer
@@ -608,9 +616,6 @@ extracategories:Buffy: The Vampire Slayer
#is_adult:true
[castlefans.org]
## Site dedicated to these categories/characters/ships
extracategories:Castle
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -623,6 +628,9 @@ extracategories:Castle
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Castle
[chaos.sycophanthex.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -635,10 +643,23 @@ cover_exclusion_regexp:/images/.*?ribbon.gif
[dark-solace.org]
## Site dedicated to these categories/characters/ships
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
extracategories:Buffy: The Vampire Slayer
extracharacters:Buffy, Spike
extraships:Spike/Buffy
[dramione.org]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -651,24 +672,11 @@ extraships:Spike/Buffy
## personal.ini, not defaults.ini.
#is_adult:true
[dramione.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Draco Malfoy,Hermione Granger
extraships:Draco Malfoy/Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/images/.*?ribbon.gif
@@ -711,22 +719,19 @@ cliches_label:Character Cliches
extracategories:Lord of the Rings
[erosnsappho.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/images/.*?ribbon.gif
[fanfiction.mugglenet.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -739,10 +744,10 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[fanfic.potterheadsanonymous.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -755,16 +760,19 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[fanfiction.portkey.org]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Hermione Granger
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[fanfiction.tenhawkpresents.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -817,10 +825,6 @@ universe_label:Universe
codes_label:Codes
[grangerenchanted.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -833,6 +837,10 @@ extracharacters:Hermione Granger
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Hermione Granger
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:read,reviews
@@ -869,18 +877,15 @@ extracharacters:Kirk,Spock
extraships:Kirk/Spock
[lumos.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[merlinfic.dtwins.co.uk]
## Site dedicated to these categories/characters/ships
extracategories:Merlin
extracategories:Harry Potter
[merlinfic.dtwins.co.uk]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -893,6 +898,9 @@ extracategories:Merlin
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Merlin
[national-library.net]
## Site dedicated to these categories/characters/ships
extracategories:West Wing
@@ -904,24 +912,32 @@ extracategories:NCIS
[netraptor.org]
[nfacommunity.com]
## Site dedicated to these categories/characters/ships
extracategories:NCIS
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:NCIS
[nha.magical-worlds.us]
## Site dedicated to these categories/characters/ships
extracategories:Buffy: The Vampire Slayer
extracharacters:Willow
[occlumency.sycophanthex.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape
[onedirectionfanfiction.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -929,10 +945,15 @@ extracharacters:Severus Snape
#username:YourName
#password:yourpassword
[onedirectionfanfiction.com]
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:One Direction
[pommedesang.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -945,40 +966,27 @@ extracategories:One Direction
## personal.ini, not defaults.ini.
#is_adult:true
[pommedesang.com]
## Site dedicated to these categories/characters/ships
extracategories:Anita Blake Vampire Hunter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
[ponyfictionarchive.net]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[ponyfictionarchive.net]
## Site dedicated to these categories/characters/ships
extracategories:My Little Pony: Friendship is Magic
[pretendercentre.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[pretendercentre.com]
## Site dedicated to these categories/characters/ships
extracategories:The Pretender
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[samdean.archive.nu]
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
@@ -986,9 +994,6 @@ extracharacters:Sam,Dean
extraships:Sam/Dean
[scarhead.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1001,6 +1006,9 @@ extracategories:Harry Potter
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[sg1-heliopolis.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -1031,9 +1039,6 @@ extracharacters:Draco Malfoy,Harry Potter
extraships:Harry Potter/Draco Malfoy
[thehookupzone.net]
## Site dedicated to these categories/characters/ships
extracategories:Criminal Minds
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1046,6 +1051,9 @@ extracategories:Criminal Minds
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Criminal Minds
[themasque.net]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1060,9 +1068,6 @@ extracategories:Criminal Minds
#is_adult:true
[thequidditchpitch.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1075,50 +1080,71 @@ extracategories:Harry Potter
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[tokra.fandomnet.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Stargate: SG-1
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
[trekiverse.org]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
[www.adastrafanfic.com]
## Site dedicated to these categories/characters/ships
extracategories:Star Trek
extra_valid_entries:awards
awards_label:Awards
cover_exclusion_regexp:art/.*Awards.jpg
[www.adastrafanfic.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Star Trek
[www.dracoandginny.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Draco Malfoy,Ginny Weasley
extraships:Draco Malfoy/Ginny Weasley
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
[www.thealphagate.com]
## Site dedicated to these categories/characters/ships
extracategories:Stargate: SG-1
[www.checkmated.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1126,6 +1152,9 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.destinysgateway.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -1133,11 +1162,6 @@ extracategories:Harry Potter
#is_adult:true
[www.dokuga.com]
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:Sesshoumaru,Kagome
extraships:Sesshoumaru/Kagome
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1145,6 +1169,11 @@ extraships:Sesshoumaru/Kagome
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:Sesshoumaru,Kagome
extraships:Sesshoumaru/Kagome
[www.dotmoon.net]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1200,14 +1229,14 @@ dateUpdated_format:%%Y-%%m-%%d %%H:%%M:%%S
[www.ficbook.net]
[www.fictionalley.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## fictionally.org storyIds are not unique. Combine with authorId.
output_filename: ${title}-${siteabbrev}_${authorId}_${storyId}${formatext}
@@ -1233,19 +1262,6 @@ extra_valid_entries:reviews,favs,follows
#password:yourpassword
[www.fimfiction.net]
## Site dedicated to these categories/characters/ships
extracategories:My Little Pony: Friendship is Magic
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:likes,dislikes,views,total_views,short_description,groups
likes_label:Likes
dislikes_label:Dislikes
views_label:Highest Single Chapter Views
total_views_label:Total Views
short_description_label:Short Summary
groups_label:Groups
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -1263,38 +1279,63 @@ groups_label:Groups
## when updating to enforce accurate chapters.
#do_update_hook:false
[www.harrypotterfanfiction.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracategories:My Little Pony: Friendship is Magic
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:likes,dislikes,views,total_views,short_description,groups,groupsUrl,groupsHTML,prequel,prequelUrl,prequelHTML,sequels,sequelsUrl,sequelsHTML
likes_label:Likes
dislikes_label:Dislikes
views_label:Highest Single Chapter Views
total_views_label:Total Views
short_description_label:Short Summary
groups_label:Groups
groupsUrl_label:Groups URLs
groupsHTML_label:Groups
prequel_label:Prequel
prequelUrl_label:Prequel URL
prequelHTML_label:Prequel
sequels_label:Sequels
sequelsUrl_label:Sequel URLs
sequelsHTML_label:Sequels
keep_in_order_sequels:true
keep_in_order_sequelsUrl:true
keep_in_order_groups:true
keep_in_order_groupsUrl:true
## Assume entryUrl, apply to "<a class='%slink' href='%s'>%s</a>" to
## make entryHTML.
make_linkhtml_entries:prequel,sequels,groups
[www.harrypotterfanfiction.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.henneth-annun.net]
## Site dedicated to these categories/characters/ships
extracategories:The Hobbit
[www.hpfandom.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.hpfanficarchive.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.ik-eternal.net]
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:InuYasha,Kagome
extraships:InuYasha/Kagome
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1307,30 +1348,35 @@ extraships:InuYasha/Kagome
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:InuYasha,Kagome
extraships:InuYasha/Kagome
[www.jlaunlimited.com]
## Site dedicated to these categories/characters/ships
extracategories:JLA
[www.libraryofmoria.com]
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
[www.mediaminer.org]
[www.midnightwhispers.ca]
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/stories/999/images/.*?_trophy.png
@@ -1345,10 +1391,6 @@ extracategories:CSI
extraships:Nick Stokes/Greg Sanders
[www.phoenixsong.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Ginny Weasley
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1359,9 +1401,13 @@ extraships:Harry Potter/Ginny Weasley
## phoenixsong.net, oddly, can have high rated chapters (login
## required) in the middle of a lower rated story. Use this to force
## FFDL to always login to phoenixsong.net so those stories download
## correctly.
## correctly. If you have a login, this is recommended.
#force_login:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Ginny Weasley
[www.potionsandsnitches.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
@@ -1384,17 +1430,15 @@ extracategories:Psych
#is_adult:true
[www.qaf-fic.com]
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
[www.restrictedsection.org]
extracategories:Harry Potter
extragenres:Erotica
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1402,20 +1446,21 @@ extragenres:Erotica
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extragenres:Erotica
[www.scarvesandcoffee.net]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Glee
extracharacters:Kurt Hummel,Blaine Anderson
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[www.simplyundeniable.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1423,15 +1468,18 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
[www.sinful-desire.org]
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
extracategories:Harry Potter
[www.sinful-desire.org]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
[www.siye.co.uk]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
@@ -1439,25 +1487,26 @@ extracharacters:Harry Potter,Ginny Weasley
extraships:Harry Potter/Ginny Weasley
[www.squidge.org/peja]
# www.squidge.org/peja calls it Fandom <shrug>
## www.squidge.org/peja calls it Fandom <shrug>
category_label:Fandom
# Remove numWords -- www.squidge.org/peja word counts are inaccurate
## Remove numWords -- www.squidge.org/peja word counts are inaccurate
titlepage_entries: seriesHTML,category,genre,language,characters,ships,status,datePublished,dateUpdated,dateCreated,rating,warnings,numChapters,site,description
[www.squidge.org/peja:txt]
## Add URLs since there aren't links.
# Remove numWords -- www.squidge.org/peja word counts are inaccurate
## Add URLs since there aren't links and remove numWords --
## www.squidge.org/peja word counts are inaccurate
titlepage_entries: series,seriesUrl,category,genre,language,status,datePublished,dateUpdated,dateCreated,rating,warnings,numChapters,site,storyUrl, authorUrl, description
[www.storiesofarda.com]
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
[www.thepetulantpoetess.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1500,9 +1549,6 @@ collect_series: false
extracategories:Twilight
[www.twilighted.net]
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1510,13 +1556,13 @@ extracategories:Twilight
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## twilighted.net (ab)uses series as personal reading lists.
collect_series: false
[www.twiwrite.net]
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1524,20 +1570,23 @@ extracategories:Twilight
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## twiwrite.net (ab)uses series as personal reading lists.
collect_series: false
[www.walkingtheplank.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Harry Potter
extraships:Severus Snape/Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Harry Potter
extraships:Severus Snape/Harry Potter
[www.whofic.com]
[www.wizardtales.net]
@@ -1559,14 +1608,14 @@ extracategories:X-Men Movie
extracharacters:Wolverine,Rogue
[www.wraithbait.com]
## Site dedicated to these categories/characters/ships
extracategories:Stargate: Atlantis
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Stargate: Atlantis
[overrides]
## It may sometimes be useful to override all of the specific format,
## site and site:format sections in your private configuration. For
Binary file not shown.
+57
View File
@@ -0,0 +1,57 @@
# coding: utf-8
import re
import codecs
stack = []
def get_end_tag(tag):
if len(tag) > 0 and tag.find(u'<') > -1 and tag.rfind(u'>') > -1:
return re.sub(r'.*<([^\ >]+).*', r'</\1>', tag)
return u''
def get_tag_name(tag):
if len(tag) > 0 and tag.find(u'<') > -1 and tag.rfind(u'>') > -1:
return re.sub(r'</*([^\ >]+).*', r'\1', tag)
return u''
def push(tag):
if len(tag) > 0 and tag.find(u'<') > -1 and tag.rfind(u'>') > -1:
stack.append(tag)
def pop():
if len(stack) > 0:
return stack.pop()
return u''
def pop_end_tag():
return unicode(get_end_tag(pop()))
def spool_end():
html = u''
for tag in reversed(stack):
html += get_end_tag(tag)
return html
def spool_start():
html = u''
for item in stack:
html += item
return html
def has_elements():
return len(stack) > 0
def get_last():
# t = pop()
# push(t)
# return t
if len(stack) > 0:
return stack[len(stack)-1]
return u''
def flush():
del stack[:]
def get_stack():
return stack
+2
View File
@@ -121,6 +121,8 @@ import adapter_simplyundeniablecom
import adapter_scarheadnet
import adapter_fictionpadcom
import adapter_storiesonlinenet
import adapter_trekiverseorg
import adapter_literotica
## This bit of complexity allows adapters to be added by just adding
## importing. It eliminates the long if/else clauses we used to need
@@ -77,7 +77,7 @@ class ArchiveOfOurOwnOrgAdapter(BaseSiteAdapter):
# The site domain. Does have www here, if it uses it.
return 'archiveofourown.org'
@classmethod
@classmethod
def getSiteExampleURLs(self):
return "http://"+self.getSiteDomain()+"/works/123456 http://"+self.getSiteDomain()+"/collections/Some_Archive/works/123456 http://"+self.getSiteDomain()+"/works/123456/chapters/78901"
@@ -177,19 +177,28 @@ class ArchiveOfOurOwnOrgAdapter(BaseSiteAdapter):
self.story.addToList('authorUrl','http://'+self.host+a['href'])
self.story.addToList('author',a.text)
newestChapter = None
self.newestChapterNum = None # save for comparing during update.
# Scan all chapters to find the oldest and newest, on AO3 it's
# possible for authors to insert new chapters out-of-order or
# change the dates of earlier ones by editing them--That WILL
# break epub update.
# Find the chapters:
chapters=soup.findAll('a', href=re.compile(r'/works/'+self.story.getMetadata('storyId')+"/chapters/\d+$"))
self.story.setMetadata('numChapters',len(chapters))
logger.debug("numChapters: (%s)"%self.story.getMetadata('numChapters'))
for x in range(0,len(chapters)):
# just in case there's tags, like <i> in chapter titles.
chapter=chapters[x]
if len(chapters)==1:
self.chapterUrls.append((self.story.getMetadata('title'),'http://'+self.host+chapter['href']+addurl))
else:
if len(chapters)==1:
self.chapterUrls.append((self.story.getMetadata('title'),'http://'+self.host+chapters[0]['href']+addurl))
else:
for index, chapter in enumerate(chapters):
# strip just in case there's tags, like <i> in chapter titles.
self.chapterUrls.append((stripHTML(chapter),'http://'+self.host+chapter['href']+addurl))
# (2013-09-21)
date = stripHTML(chapter.findNext('span'))[1:-1]
chapterDate = makeDate(date,self.dateformat)
if newestChapter == None or chapterDate > newestChapter:
newestChapter = chapterDate
self.newestChapterNum = index
a = metasoup.find('blockquote',{'class':'userstuff'})
if a != None:
@@ -299,6 +308,12 @@ class ArchiveOfOurOwnOrgAdapter(BaseSiteAdapter):
self.setSeries(series_name, series_index)
self.story.setMetadata('seriesUrl',series_url)
def hookForUpdates(self,chaptercount):
if self.oldchapters and len(self.oldchapters) > self.newestChapterNum:
print("Existing epub has %s chapters\nNewest chapter is %s. Discarding old chapters from there on."%(len(self.oldchapters), self.newestChapterNum+1))
self.oldchapters = self.oldchapters[:self.newestChapterNum]
return len(self.oldchapters)
# grab the text for an individual chapter.
def getChapterText(self, url):
logger.debug('Getting chapter text from: %s' % url)
@@ -72,6 +72,13 @@ class FanFictionNetSiteAdapter(BaseSiteAdapter):
def getSiteURLPattern(self):
return r"https?://(www|m)?\.fanfiction\.net/s/\d+(/\d+)?(/|/[^/]+)?/?$"
def _fetchUrl(self,url):
time.sleep(1.0) ## ffnet(and, I assume, fpcom) tends to fail
## more if hit too fast. This is in
## additional to what ever the
## slow_down_sleep_time setting is.
return BaseSiteAdapter._fetchUrl(self,url)
def extractChapterUrlsAndMetadata(self):
# fetch the chapter. From that we will get almost all the
@@ -157,7 +164,7 @@ class FanFictionNetSiteAdapter(BaseSiteAdapter):
a = soup.find('a', href='http://www.fictionratings.com/')
a = soup.find('a', href=re.compile(r'https?://www\.fictionratings\.com/'))
rating = a.string
if 'Fiction' in rating: # if rating has 'Fiction ', strip that out for consistency with past.
rating = rating[8:]
@@ -275,7 +282,7 @@ class FanFictionNetSiteAdapter(BaseSiteAdapter):
return
def getChapterText(self, url):
time.sleep(5.0) ## ffnet(and, I assume, fpcom) tends to fail
time.sleep(4.0) ## ffnet(and, I assume, fpcom) tends to fail
## more if hit too fast. This is in
## additional to what ever the
## slow_down_sleep_time setting is.
@@ -249,11 +249,33 @@ class FimFictionNetSiteAdapter(BaseSiteAdapter):
value = unicode(value)
self.story.setMetadata(metakey, value)
rawGroupList = soup.find('ul', {'id':'story_group_list'})
if rawGroupList is not None:
for groupName in rawGroupList.findAll('a', {'href':re.compile('^/group/')}):
#Sequel links and group links are each bundled into story_group_list containers.
#Rather than mess around examining the header text, which is outside the containers,
#one can tell the two link types apart by examining them directly.
allGroupLists = soup.findAll('ul', {'id':'story_group_list'})
for groupList in allGroupLists:
for groupName in groupList.findAll('a', {'href':re.compile('^/group/')}):
self.story.addToList("groupsUrl", 'http://'+self.host+groupName["href"])
self.story.addToList("groups",stripHTML(groupName).replace(',', ';'))
for sequel in groupList.findAll('a', {'class':'story_link'}):
self.story.addToList("sequelsUrl", 'http://'+self.host+sequel["href"])
self.story.addToList("sequels", stripHTML(sequel).replace(',', ';'))
#The link to the prequel is embedded in the description text, so erring
#on the side of caution and wrapping this whole thing in a try block.
#If anything goes wrong this probably wasn't a valid prequel link.
try:
description = soup.find('div', {'class':'description'})
firstHR = description.find("hr")
nextSib = firstHR.nextSibling
if "This story is a sequel to" in nextSib.string:
link = nextSib.nextSibling
if link.name == "a":
self.story.setMetadata("prequelUrl", 'http://'+self.host+link["href"])
self.story.setMetadata("prequel", stripHTML(link))
except:
pass
def hookForUpdates(self,chaptercount):
if self.oldchapters and len(self.oldchapters) > self.newestChapterNum:
print("Existing epub has %s chapters\nNewest chapter is %s. Discarding old chapters from there on."%(len(self.oldchapters), self.newestChapterNum+1))
@@ -0,0 +1,237 @@
# -*- coding: utf-8 -*-
# Copyright 2013 Fanficdownloader team
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
import time
import logging
logger = logging.getLogger(__name__)
import re
import urllib2
import urlparse
import time
from .. import BeautifulSoup as bs
from ..htmlcleanup import stripHTML
from .. import exceptions as exceptions
from base_adapter import BaseSiteAdapter, makeDate
class LiteroticaSiteAdapter(BaseSiteAdapter):
def __init__(self, config, url):
BaseSiteAdapter.__init__(self, config, url)
self.decode = ["utf8",
"Windows-1252"] # 1252 is a superset of iso-8859-1.
# Most sites that claim to be
# iso-8859-1 (and some that claim to be
# utf8) are really windows-1252.
self.story.setMetadata('siteabbrev','litero')
# get storyId from url--url validation guarantees query is only sid=1234
self.story.setMetadata('storyId',self.parsedUrl.path.split('/',)[2])
self.origurl = url
if "http://www.i." in self.origurl:
## accept m(mobile)url, but use www.
self.origurl = self.origurl.replace("http://www.i.","http://www.")
# normalized story URL.
self._setURL("http://"+self.getSiteDomain()\
+"/s/"+self.story.getMetadata('storyId'))
# The date format will vary from site to site.
# http://docs.python.org/library/datetime.html#strftime-strptime-behavior
self.dateformat = '%m/%d/%y'
@staticmethod
def getSiteDomain():
return 'www.literotica.com'
@classmethod
def getAcceptDomains(cls):
return ['www.literotica.com', 'www.i.literotica.com']
@classmethod
def getSiteExampleURLs(self):
#return "http://www.literotica.com/s/story-title http://www.literotica.com/stories/showstory.php?id=1234 http://www.i.literotica.com/stories/showstory.php?id=1234"
return "http://www.literotica.com/s/story-title"
def getSiteURLPattern(self):
return r"http://www(\.i)?\.literotica\.com/s/([a-zA-Z0-9_-]+)"
def extractChapterUrlsAndMetadata(self):
if not (self.is_adult or self.getConfig("is_adult")):
raise exceptions.AdultCheckRequired(self.url)
url1 = self.origurl
logger.debug("first page URL: "+url1)
try:
data1 = self._fetchUrl(url1)
soup1 = bs.BeautifulSoup(data1)
except urllib2.HTTPError, e:
if e.code == 404:
raise exceptions.StoryDoesNotExist(url1)
else:
raise e
#strip comments from soup
[comment.extract() for comment in soup1.findAll(text=lambda text:isinstance(text, bs.Comment))]
# author
a = soup1.find("span", "b-story-user-y")
self.story.setMetadata('authorId', urlparse.parse_qs(a.a['href'].split('?')[1])['uid'])
self.story.setMetadata('authorUrl', a.a['href'])
self.story.setMetadata('author', a.text)
# get the author page
try:
dataAuth = self._fetchUrl(a.a['href'])
soupAuth = bs.BeautifulSoup(dataAuth)
except urllib2.HTTPError, e:
if e.code == 404:
raise exceptions.StoryDoesNotExist(a.a['href'])
else:
raise e
storyLink = soupAuth.find('a', href=url1)
if storyLink is not None:
# pull the published date from the author page
# default values from single link. Updated below if multiple chapter.
date = storyLink.parent.parent.findAll('td')[-1].text
self.story.setMetadata('datePublished', makeDate(date, self.dateformat))
self.story.setMetadata('dateUpdated',makeDate(date, self.dateformat))
# find num of pages
# find a "3 Pages:" string on the page and parse it
pgs = soup1.find("span", "b-pager-caption-t r-d45").string.split(' ')[0]
# If there are multiple pages, find and request the last page
if "1" != pgs:
logger.debug("last page number: "+pgs)
try:
data2 = self._fetchUrl(url1, {'page': pgs})
soup2 = bs.BeautifulSoup(data2)
[comment.extract() for comment in soup2.findAll(text=lambda text:isinstance(text, bs.Comment))]
except urllib2.HTTPError, e:
if e.code == 404:
# TODO: Probably should reformat this
raise exceptions.StoryDoesNotExist(url1, {'page': pgs})
else:
raise e
else:
#If we're already on the last page, copy the soup
soup2 = soup1
# parse out the list of chapters
chaps = soup2.find('div', id='b-series')
if chaps: # may be one post only
#self.chapterUrls = [(ch.a.text, ch.a['href']) for ch in chaps.findAll('li')]
# if there are chapters, lets pull them and title from the
# author page because *this* chapter is omitted from the
# list on the last page.
row = storyLink.parent.parent.previousSibling
while row['class'] != 'ser-ttl':
row = row.previousSibling
seriesTitle = stripHTML(row)
if seriesTitle:
# this regex is deliberately greedy. We want to get the biggest match before a ':'
self.story.setMetadata('title', re.match('(.*):[^:]*$', seriesTitle).group(1))
else:
self.story.setMetadata('title', soup1.h1.string)
# now chapter list. Assumed oldest to newest.
self.chapterUrls = []
row = row.nextSibling
self.story.setMetadata('datePublished',makeDate(stripHTML(row.find('td',{'class':'dt'})), self.dateformat))
while row['class'] == 'sl':
# pages include full URLs.
self.chapterUrls.append((row.a.string,row.a['href']))
if not row.nextSibling:
break
row = row.nextSibling
row = row.previousSibling
self.story.setMetadata('dateUpdated',makeDate(stripHTML(row.find('td',{'class':'dt'})), self.dateformat))
else: # if one post only
self.chapterUrls = [(soup1.h1.string, url1)]
self.story.setMetadata('title', soup1.h1.string)
# normalize on first chapter URL.
self._setURL(self.chapterUrls[0][1])
# reset storyId to first chapter.
self.story.setMetadata('storyId',self.parsedUrl.path.split('/',)[2])
self.story.setMetadata('numChapters', len(self.chapterUrls))
self.story.setMetadata('category', soup1.find('div', 'b-breadcrumbs').findAll('a')[1].string)
self.story.setMetadata('description', soup1.find('meta', {'name': 'description'})['content'])
return
def getChapterText(self, url):
logger.debug('Getting chapter text from: %s' % url)
time.sleep(0.5)
data1 = self._fetchUrl(url)
soup1 = bs.BeautifulSoup(data1)
#strip comments from soup
[comment.extract() for comment in soup1.findAll(text=lambda text:isinstance(text, bs.Comment))]
# get story text
story1 = soup1.find('div', 'b-story-body-x').p
story1.name='div'
story1.append('<br>')
storytext = self.utf8FromSoup(url,story1)
# find num pages
pgs = int(soup1.find("span", "b-pager-caption-t r-d45").string.split(' ')[0])
logger.debug("pages: "+str(pgs))
# get all the pages
for i in xrange(2, pgs+1):
try:
logger.debug("fetching page "+str(i))
time.sleep(0.5)
data2 = self._fetchUrl(url, {'page': i})
soup2 = bs.BeautifulSoup(data2)
[comment.extract() for comment in soup2.findAll(text=lambda text:isinstance(text, bs.Comment))]
story2 = soup2.find('div', 'b-story-body-x').p
story2.name='div'
story2.append('<br>')
storytext += self.utf8FromSoup(url,story2)
except urllib2.HTTPError, e:
if e.code == 404:
raise exceptions.StoryDoesNotExist(url)
else:
raise e
return storytext
def getClass():
return LiteroticaSiteAdapter
@@ -0,0 +1,325 @@
# -*- coding: utf-8 -*-
# Copyright 2013 Fanficdownloader team
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
import time
import logging
logger = logging.getLogger(__name__)
import re
import urllib2
from .. import BeautifulSoup as bs
from ..htmlcleanup import stripHTML
from .. import exceptions as exceptions
from base_adapter import BaseSiteAdapter, makeDate
def getClass():
return TrekiverseOrgAdapter
# Class name has to be unique. Our convention is camel case the
# sitename with Adapter at the end. www is skipped.
class TrekiverseOrgAdapter(BaseSiteAdapter):
def __init__(self, config, url):
BaseSiteAdapter.__init__(self, config, url)
self.decode = ["iso-8859-1",
"Windows-1252"] # 1252 is a superset of iso-8859-1.
# Most sites that claim to be
# iso-8859-1 (and some that claim to be
# utf8) are really windows-1252.
self.username = "NoneGiven" # if left empty, site doesn't return any message at all.
self.password = ""
self.is_adult=False
# get storyId from url--url validation guarantees query is only sid=1234
self.story.setMetadata('storyId',self.parsedUrl.query.split('=',)[1])
# normalized story URL.
self._setURL("http://"+self.getSiteDomain()\
+"/efiction/viewstory.php?sid="+self.story.getMetadata('storyId'))
# Each adapter needs to have a unique site abbreviation.
self.story.setMetadata('siteabbrev','trkvs')
# The date format will vary from site to site.
# http://docs.python.org/library/datetime.html#strftime-strptime-behavior
self.dateformat = "%d/%m/%Y"
@staticmethod # must be @staticmethod, don't remove it.
def getSiteDomain():
# The site domain.
return 'trekiverse.org'
@classmethod
def getAcceptDomains(cls):
return ['trekiverse.org','efiction.trekiverse.org']
@classmethod
def getSiteExampleURLs(self):
return "http://"+self.getSiteDomain()+"/efiction/viewstory.php?sid=1234 http://efiction."+self.getSiteDomain()+"/viewstory.php?sid=1234"
def getSiteURLPattern(self):
return r'(http://trekiverse\.org/efiction/viewstory\.php\?sid=\d+|http://efiction\.trekiverse\.org/viewstory\.php\?sid=\d+)'
## Login seems to be reasonably standard across eFiction sites.
def needToLoginCheck(self, data):
if 'Registered Users Only' in data \
or 'There is no such account on our website' in data \
or "That password doesn't match the one in our database" in data:
return True
else:
return False
def performLogin(self, url):
params = {}
if self.password:
params['penname'] = self.username
params['password'] = self.password
else:
params['penname'] = self.getConfig("username")
params['password'] = self.getConfig("password")
params['cookiecheck'] = '1'
params['submit'] = 'Submit'
loginUrl = 'http://' + self.getSiteDomain() + '/efiction/user.php?action=login'
logger.debug("Will now login to URL (%s) as (%s)" % (loginUrl,
params['penname']))
d = self._fetchUrl(loginUrl, params)
if "Member Account" not in d : #Member Account
logger.info("Failed to login to URL %s as %s" % (loginUrl,
params['penname']))
raise exceptions.FailedToLogin(url,params['penname'])
return False
else:
return True
## Getting the chapter list and the meta data, plus 'is adult' checking.
def extractChapterUrlsAndMetadata(self):
if self.is_adult or self.getConfig("is_adult"):
# Weirdly, different sites use different warning numbers.
# If the title search below fails, there's a good chance
# you need a different number. print data at that point
# and see what the 'click here to continue' url says.
addurl = "&index=1&ageconsent=ok&warning=5"
else:
addurl="&index=1"
# index=1 makes sure we see the story chapter index. Some
# sites skip that for one-chapter stories.
url = self.url+addurl
logger.debug("URL: "+url)
try:
data = self._fetchUrl(url)
except urllib2.HTTPError, e:
if e.code == 404:
raise exceptions.StoryDoesNotExist(self.url)
else:
raise e
if self.needToLoginCheck(data):
# need to log in for this one.
self.performLogin(url)
data = self._fetchUrl(url)
m = re.search(r"'viewstory.php\?sid=\d+((?:&amp;ageconsent=ok)?&amp;warning=\d+)'",data)
if m != None:
if self.is_adult or self.getConfig("is_adult"):
# We tried the default and still got a warning, so
# let's pull the warning number from the 'continue'
# link and reload data.
addurl = m.group(1)
# correct stupid &amp; error in url.
addurl = addurl.replace("&amp;","&")
url = self.url+'&index=1'+addurl
logger.debug("URL 2nd try: "+url)
try:
data = self._fetchUrl(url)
except urllib2.HTTPError, e:
if e.code == 404:
raise exceptions.StoryDoesNotExist(self.url)
else:
raise e
else:
raise exceptions.AdultCheckRequired(self.url)
if "Access denied. This story has not been validated by the adminstrators of this site." in data:
raise exceptions.FailedToDownload(self.getSiteDomain() +" says: Access denied. This story has not been validated by the adminstrators of this site.")
# use BeautifulSoup HTML parser to make everything easier to find.
soup = bs.BeautifulSoup(data)
# Now go hunting for all the meta data and the chapter list.
## Title and author
a = soup.find('div', {'id' : 'pagetitle'})
aut = a.find('a', href=re.compile(r"^viewuser\.php\?uid="))
self.story.setMetadata('authorId',aut['href'].split('=')[1])
self.story.setMetadata('authorUrl','http://'+self.host+'/efiction/'+aut['href'])
self.story.setMetadata('author',aut.string)
ttl = a.find('a', href=re.compile(r'^viewstory.php\?sid=%s$'%self.story.getMetadata('storyId')))
self.story.setMetadata('title',ttl.string)
# Find the chapters:
outputdiv = soup.find('div', {'id':'output'})
# (amp;)? because it should be &, but is escaped to &amp; in URL.
# viewstory.php?sid=35&amp;chapter=3
chapters=outputdiv.findAll('a', href=re.compile(r'^viewstory.php\?sid=%s&(amp;)?chapter=\d+$'%self.story.getMetadata('storyId')))
if len(chapters)==0:
raise exceptions.FailedToDownload(self.getSiteDomain() +" says: No php/html chapters found.")
if len(chapters)==1:
self.chapterUrls.append((self.story.getMetadata('title'),'http://'+self.host+'/efiction/'+chapters[0]['href']))
else:
for chapter in chapters:
# just in case there's tags, like <i> in chapter titles.
self.chapterUrls.append((stripHTML(chapter),'http://'+self.host+'/efiction/'+chapter['href']))
self.story.setMetadata('numChapters',len(self.chapterUrls))
# eFiction sites don't help us out a lot with their meta data
# formating, so it's a little ugly.
def defaultGetattr(d,k):
try:
return d[k]
except:
return ""
# <span class="label">Rated:</span> NC-17<br /> etc
labels = soup.findAll('span',{'class':'label'})
for labelspan in labels:
value = labelspan.nextSibling
label = labelspan.string
if 'Summary' in label:
## Everything until the next span class='label'
svalue = ''
while value and not defaultGetattr(value,'class') == 'label':
svalue += str(value)
value = value.nextSibling
# sometimes poorly formated desc (<p> w/o </p>) leads
# to all labels being included.
svalue=svalue[:svalue.find('<span class="label">')]
self.setDescription(url,svalue)
#self.story.setMetadata('description',stripHTML(svalue))
if 'Rated' in label:
self.story.setMetadata('rating', value)
if 'Word count' in label:
self.story.setMetadata('numWords', value)
if 'Categories' in label:
cats = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=categories'))
catstext = [cat.string for cat in cats]
for cat in catstext:
self.story.addToList('category',cat.string)
if 'Characters' in label:
chars = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=characters'))
charstext = [char.string for char in chars]
for char in charstext:
self.story.addToList('characters',char.string)
if 'Genre' in label:
genres = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=class&type_id=9'))
genrestext = [genre.string for genre in genres]
self.genre = ', '.join(genrestext)
for genre in genrestext:
self.story.addToList('genre',genre.string)
if 'Awards' in label:
awards = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=class&type_id=12'))
awardstext = [award.string for award in awards]
self.award = ', '.join(awardstext)
for award in awardstext:
self.story.addToList('awards',award.string)
if 'Pairing' in label:
ships = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=class&type_id=10'))
shipstext = [ship.string for ship in ships]
self.ship = ', '.join(shipstext)
for ship in shipstext:
self.story.addToList('ships',ship.string)
if 'Warnings' in label:
warnings = labelspan.parent.findAll('a',href=re.compile(r'browse.php\?type=class&type_id=11'))
warningstext = [warning.string for warning in warnings]
self.warning = ', '.join(warningstext)
for warning in warningstext:
self.story.addToList('warnings',warning.string)
if 'Completed' in label:
if 'Yes' in value:
self.story.setMetadata('status', 'Completed')
else:
self.story.setMetadata('status', 'In-Progress')
if 'Published' in label:
self.story.setMetadata('datePublished', makeDate(value.strip(), "%d %b %Y"))
if 'Updated' in label:
self.story.setMetadata('dateUpdated', makeDate(value.strip(), "%d %b %Y"))
try:
# Find Series name from series URL.
a = soup.find('a', href=re.compile(r"viewseries.php\?seriesid=\d+"))
series_name = a.string
series_url = 'http://'+self.host+'/efiction/'+a['href']
# use BeautifulSoup HTML parser to make everything easier to find.
seriessoup = bs.BeautifulSoup(self._fetchUrl(series_url))
storyas = seriessoup.findAll('a', href=re.compile(r'^viewstory.php\?sid=\d+$'))
i=1
for a in storyas:
if a['href'] == ('viewstory.php?sid='+self.story.getMetadata('storyId')):
self.setSeries(series_name, i)
self.story.setMetadata('seriesUrl',series_url)
break
i+=1
except:
# I find it hard to care if the series parsing fails
pass
# grab the text for an individual chapter.
def getChapterText(self, url):
logger.debug('Getting chapter text from: %s' % url)
soup = bs.BeautifulSoup(self._fetchUrl(url)) # otherwise soup eats the br/hr tags.
div = soup.find('div', {'id' : 'story'})
if None == div:
raise exceptions.FailedToDownload("Error downloading Chapter: %s! Missing required element!" % url)
notesdiv = soup.find('div', {'class':'noteinfo'})
if notesdiv != None:
div.insert(0,"<hr>")
div.insert(0,notesdiv)
div.insert(0,"<hr>")
return self.utf8FromSoup(url,div)
@@ -134,18 +134,18 @@ class TwistingTheHellmouthSiteAdapter(BaseSiteAdapter):
if "<h2>Story Not Found</h2>" in data:
raise exceptions.StoryDoesNotExist(url)
if self.is_adult or self.getConfig("is_adult"):
form = soup.find('form', {'id':'sitemaxratingform'})
params={'ctkn':form.find('input', {'name':'ctkn'})['value'],
'sitemaxrating':'5'}
logger.info("Attempting to get rating cookie for %s" % url)
data = self._postUrl("http://"+self.getSiteDomain()+'/setmaxrating.php',params)
# refetch story page.
data = self._fetchUrl(url)
soup = bs.BeautifulSoup(data)
if "NOTE: This story is rated FR21 which is above your chosen filter level." in data:
if self.is_adult or self.getConfig("is_adult"):
form = soup.find('form', {'id':'sitemaxratingform'})
params={'ctkn':form.find('input', {'name':'ctkn'})['value'],
'sitemaxrating':'5'}
logger.info("Attempting to get rating cookie for %s" % url)
data = self._postUrl("http://"+self.getSiteDomain()+'/setmaxrating.php',params)
# refetch story page.
data = self._fetchUrl(url)
soup = bs.BeautifulSoup(data)
else:
raise exceptions.AdultCheckRequired(self.url)
raise exceptions.AdultCheckRequired(self.url)
# http://www.tthfanfic.org/AuthorStories-3449/Greywizard.htm
# Find authorid and URL from... author url.
@@ -163,7 +163,14 @@ class TwistingTheHellmouthSiteAdapter(BaseSiteAdapter):
authorsoup = bs.BeautifulSoup(authordata)
# author can have several pages, scan until we find it.
while( not authorsoup.find('a', href=re.compile(r"^/Story-"+self.story.getMetadata('storyId'))) ):
nextpage = 'http://'+self.host+authorsoup.find('a', {'class':'arrowf'})['href']
nextarrow = authorsoup.find('a', {'class':'arrowf'})
if not nextarrow:
## if rating is set lower than story, it won't be
## visible on author lists unless. The *story* is
## visible via the url, just not the entry on
## author list.
raise exceptions.AdultCheckRequired(self.url)
nextpage = 'http://'+self.host+nextarrow['href']
logger.debug("**AUTHOR** nextpage URL: "+nextpage)
authordata = self._fetchUrl(nextpage)
descurl=nextpage
+1 -1
View File
@@ -358,7 +358,7 @@ class BaseSiteAdapter(Configurable):
retval = soup.__str__('utf8').decode('utf-8')
if self.getConfig('nook_img_fix'):
if self.getConfig('nook_img_fix') and not self.getConfig('replace_br_with_p'):
# if the <img> tag doesn't have a div or a p around it,
# nook gets confused and displays it on every page after
# that under the text for the rest of the chapter.
+87 -25
View File
@@ -18,7 +18,9 @@
import logging
logger = logging.getLogger(__name__)
import re
import codecs
import BeautifulSoup as bs
import HtmlTagStack as stack
from . import exceptions as exceptions
@@ -28,7 +30,7 @@ def replace_br_with_p(body):
# However, Python Regex does not recognize it as a whitespace, so we'll be changing it to a reagular space.
body = body.replace(u'\xa0', u' ')
if body.find('>') == -1 or body.rfind("<") == -1:
if body.find('>') == -1 or body.rfind('<') == -1:
return body
# logger.debug(u'BODY start.: ' + body[:250])
@@ -42,11 +44,11 @@ def replace_br_with_p(body):
# tag in all cases now should be div, to just strip the first and
# last tags.
if is_valid_block(body) and body.find('<div') == 0:
body = body[body.index('>')+1:body.rindex("<")]
body = body[body.index('>')+1:body.rindex('<')]
body = soup_up_div(u'<div>' + body + u'</div>')
body = body[body.index('>')+1:body.rindex("<")]
body = body[body.index('>')+1:body.rindex('<')]
# Find all bexisting blocks with p, pre and blockquote tags, we need to shields break tags inside those.
# This is for "lenient" mode, however it is also used to clear break tags before and after the block elements.
@@ -139,28 +141,28 @@ def replace_br_with_p(body):
averageLineLength = contentLinesSum/contentLines
logger.debug(u'---')
logger.debug(u'Lines.............: ' + str(len(lines)))
logger.debug(u'contentLines......: ' + str(contentLines))
logger.debug(u'contentLinesSum...: ' + str(contentLinesSum))
logger.debug(u'longestLineLength.: ' + str(longestLineLength))
logger.debug(u'averageLineLength.: ' + str(averageLineLength))
logger.debug(u'Lines.............: ' + unicode(len(lines)))
logger.debug(u'contentLines......: ' + unicode(contentLines))
logger.debug(u'contentLinesSum...: ' + unicode(contentLinesSum))
logger.debug(u'longestLineLength.: ' + unicode(longestLineLength))
logger.debug(u'averageLineLength.: ' + unicode(averageLineLength))
if breaksMaxIndex == len(breaksCount)-1 and breaksMax < 2:
breaksMaxIndex = 0
breaksMax = breaksCount[0]
logger.debug(u'---')
logger.debug(u'breaks 1: ' + str(breaksCount[0]))
logger.debug(u'breaks 2: ' + str(breaksCount[1]))
logger.debug(u'breaks 3: ' + str(breaksCount[2]))
logger.debug(u'breaks 4: ' + str(breaksCount[3]))
logger.debug(u'breaks 5: ' + str(breaksCount[4]))
logger.debug(u'breaks 6: ' + str(breaksCount[5]))
logger.debug(u'breaks 7: ' + str(breaksCount[6]))
logger.debug(u'breaks 8: ' + str(breaksCount[7]))
logger.debug(u'breaks 1: ' + unicode(breaksCount[0]))
logger.debug(u'breaks 2: ' + unicode(breaksCount[1]))
logger.debug(u'breaks 3: ' + unicode(breaksCount[2]))
logger.debug(u'breaks 4: ' + unicode(breaksCount[3]))
logger.debug(u'breaks 5: ' + unicode(breaksCount[4]))
logger.debug(u'breaks 6: ' + unicode(breaksCount[5]))
logger.debug(u'breaks 7: ' + unicode(breaksCount[6]))
logger.debug(u'breaks 8: ' + unicode(breaksCount[7]))
logger.debug(u'----')
logger.debug(u'max found: ' + str(breaksMax))
logger.debug(u'max Index: ' + str(breaksMaxIndex))
logger.debug(u'max found: ' + unicode(breaksMax))
logger.debug(u'max Index: ' + unicode(breaksMaxIndex))
logger.debug(u'----')
if breaksMaxIndex > 0 and breaksCount[0] > breaksMax and averageLineLength < 90:
@@ -169,14 +171,15 @@ def replace_br_with_p(body):
# Find all instances of consecutive breaks less than otr equal to the max count use most often
# replase those tags to inverted p tag pairs, those with more connsecutive breaks are replaced them with a horisontal line
for i in range(len(breaksCount)):
# if i > 0 or breaksMaxIndex == 0:
if i <= breaksMaxIndex:
logger.debug(str(i) + u' <= breaksMaxIndex (' + str(breaksMaxIndex) + u')')
logger.debug(unicode(i) + u' <= breaksMaxIndex (' + unicode(breaksMaxIndex) + u')')
body = breaksRegexp[i].sub(r'\1</p>\n<p>\3', body)
elif i == breaksMaxIndex+1:
logger.debug(str(i) + u' == breaksMaxIndex+1 (' + str(breaksMaxIndex+1) + u')')
logger.debug(unicode(i) + u' == breaksMaxIndex+1 (' + unicode(breaksMaxIndex+1) + u')')
body = breaksRegexp[i].sub(r'\1</p>\n<p><br/></p>\n<p>\3', body)
else:
logger.debug(str(i) + u' > breaksMaxIndex+1 (' + str(breaksMaxIndex+1) + u')')
logger.debug(unicode(i) + u' > breaksMaxIndex+1 (' + unicode(breaksMaxIndex+1) + u')')
body = breaksRegexp[i].sub(r'\1</p>\n<hr />\n<p>\3', body)
body = breaksRegexp[8].sub(r'</p>\n<hr />\n<p>', body)
@@ -223,10 +226,11 @@ def replace_br_with_p(body):
# re-wrap in div tag.
body = u'<div>\n' + body + u'</div>\n'
return body
# return body
return tag_sanitizer(body)
def is_valid_block(block):
return str(block).find('<') == 0 and str(block).find('<!') != 0
return unicode(block).find('<') == 0 and unicode(block).find('<!') != 0
def soup_up_div(body):
blockTags = ['address', 'blockquote', 'del', 'div', 'dl', 'fieldset', 'form', 'ins', 'noscript', 'ol', 'p', 'pre', 'table', 'ul']
@@ -243,8 +247,8 @@ def soup_up_div(body):
lastElement = 1 # 1 = block, 2 = nested, 3 = invalid
for i in soup.contents[0]:
if str(i).strip().__len__() > 0:
s = str(i)
if unicode(i).strip().__len__() > 0:
s = unicode(i)
if type(i) == bs.Tag:
if i.name in blockTags:
if lastElement > 1:
@@ -281,3 +285,61 @@ def soup_up_div(body):
body = body.replace(u'[br /]', u'<br />')
return tag + body + tagend
def is_end_tag(tag):
return re.match(r'</([^\ >]+)>', tag) != None
def is_comment_tag(tag):
return re.match(r'<\!\-\-([^>]+)>', tag) != None
def is_closed_tag(tag):
return re.match(r'<(.+?)/>', tag) != None
def tag_sanitizer(html):
blockTags = ['address', 'blockquote', 'del', 'div', 'dl', 'fieldset', 'form', 'ins', 'noscript', 'ol', 'pre', 'table', 'ul']
body = u''
tags = re.findall(r'(<[^>]+>)([^<]*)', html)
for rTag in tags:
name = stack.get_tag_name(rTag[0])
is_end = is_end_tag(rTag[0])
is_closed = is_closed_tag(rTag[0]) or is_comment_tag(rTag[0])
# is_comment = is_comment_tag(rTag[0])
# logger.debug(u'%s > isEnd: %s > isClosed: %s > isComment: %s'%(name, unicode(is_end), unicode(is_closed), unicode(is_comment)))
# logger.debug(u'> %s%s\n'%(rTag[0], rTag[1]))
if name in blockTags:
body += rTag[0]
body += rTag[1]
elif name == u'p':
if is_end:
body += stack.spool_end()
body += rTag[0]
body += rTag[1]
elif is_closed:
body += rTag[0]
body += rTag[1]
else:
body += rTag[0]
body += stack.spool_start()
body += rTag[1]
else:
if is_end:
t = stack.get_last()
tn = stack.get_tag_name(t)
rTn = stack.get_tag_name(rTag[0])
if tn == rTn:
body += rTag[0]
stack.pop()
elif not is_closed:
stack.push(rTag[0])
body += rTag[0]
else:
body += rTag[0]
body += rTag[1]
stack.flush()
return body
+70 -47
View File
@@ -30,7 +30,7 @@ from configurable import Configurable
# Create convert_image method depending on which graphics lib we can
# load. Preferred: calibre, PIL, none
imagetypes = {
'jpg':'image/jpeg',
'jpeg':'image/jpeg',
@@ -48,14 +48,14 @@ try:
export = False
img = Image()
img.load(data)
owidth, oheight = img.size
nwidth, nheight = sizes
scaled, nwidth, nheight = fit_image(owidth, oheight, nwidth, nheight)
if scaled:
img.size = (nwidth, nheight)
export = True
if normalize_format_name(img.format) != imgtype:
export = True
@@ -65,7 +65,7 @@ try:
canvas.compose(img)
img = canvas
export = True
if grayscale and img.type != "GrayscaleType":
img.type = "GrayscaleType"
export = True
@@ -75,7 +75,7 @@ try:
else:
logger.debug("image used unchanged")
return (data,imgtype,imagetypes[imgtype])
except:
# No calibre routines, try for PIL for CLI.
@@ -87,14 +87,14 @@ except:
removetrans,imgtype="jpg",background='#ffffff'):
export = False
img = Image.open(StringIO(data))
owidth, oheight = img.size
nwidth, nheight = sizes
scaled, nwidth, nheight = fit_image(owidth, oheight, nwidth, nheight)
if scaled:
img = img.resize((nwidth, nheight),Image.ANTIALIAS)
export = True
if normalize_format_name(img.format) != imgtype:
if img.mode == "P":
# convert pallete gifs to RGB so jpg save doesn't fail.
@@ -119,7 +119,7 @@ except:
else:
logger.debug("image used unchanged")
return (data,imgtype,imagetypes[imgtype])
except:
# No calibre or PIL, simple pass through with mimetype.
def convert_image(url,data,sizes,grayscale,
@@ -129,16 +129,16 @@ except:
## also used for explicit no image processing.
def no_convert_image(url,data):
parsedUrl = up.urlparse(url)
ext=parsedUrl.path[parsedUrl.path.rfind('.')+1:].lower()
if ext not in imagetypes:
logger.debug("no_convert_image url:%s - no known extension"%url)
# doesn't have extension? use jpg.
ext='jpg'
return (data,ext,imagetypes[ext])
def normalize_format_name(fmt):
if fmt:
fmt = fmt.lower()
@@ -222,7 +222,7 @@ langs = {
}
class Story(Configurable):
def __init__(self, configuration):
Configurable.__init__(self, configuration)
try:
@@ -234,7 +234,7 @@ class Story(Configurable):
self.chapters = [] # chapters will be tuples of (title,html)
self.imgurls = []
self.imgtuples = []
self.cover=None # *href* of new cover image--need to create html.
self.oldcover=None # (oldcoverhtmlhref,oldcoverhtmltype,oldcoverhtmldata,oldcoverimghref,oldcoverimgtype,oldcoverimgdata)
self.calibrebookmark=None # cheesy way to carry calibre bookmark file forward across update.
@@ -251,7 +251,7 @@ class Story(Configurable):
self.addToList(metadata,val)
self.setReplace(self.getConfig('replace_metadata'))
def setMetadata(self, key, value, condremoveentities=True):
## still keeps &lt; &lt; and &amp;
if condremoveentities:
@@ -297,9 +297,9 @@ class Story(Configurable):
# A way to explicitly include spaces in the
# replacement string. The .ini parser eats any
# trailing spaces.
replacement=replacement.replace('\s',' ')
replacement=replacement.replace('\s',' ')
self.replacements.append([metakeys,regexp,replacement,condkey,condregexp])
def doReplacements(self,value,key):
for (metakeys,regexp,replacement,condkey,condregexp) in self.replacements:
if (metakeys == None or key in metakeys) \
@@ -309,11 +309,11 @@ class Story(Configurable):
if condkey and condkey != key: # prevent infinite recursion.
condval = self.getMetadata(condkey)
doreplace = condval != None and condregexp.search(condval)
if doreplace:
value = regexp.sub(replacement,value)
return value
def getMetadataRaw(self,key):
if self.isValidMetaEntry(key) and self.metadata.has_key(key):
return self.metadata[key]
@@ -326,7 +326,7 @@ class Story(Configurable):
return value
if self.isList(key):
join_string = self.getConfig("join_string_"+key,u", ").replace('\s',' ')
join_string = self.getConfig("join_string_"+key,u", ").replace('\s',' ')
value = join_string.join(self.getList(key, removeallentities, doreplacements=True))
if doreplacements:
value = self.doReplacements(value,key+"_LIST")
@@ -351,7 +351,7 @@ class Story(Configurable):
return value
else: #if self.getConfig("default_value_"+key):
return self.getConfig("default_value_"+key)
def getAllMetadata(self,
removeallentities=False,
doreplacements=True,
@@ -360,13 +360,13 @@ class Story(Configurable):
All single value *and* list value metadata as strings (unless keeplists=True, then keep lists).
'''
allmetadata = {}
# special handling for authors/authorUrls
linkhtml="<a class='%slink' href='%s'>%s</a>"
if self.isList('author'): # more than one author, assume multiple authorUrl too.
htmllist=[]
for i, v in enumerate(self.getList('author')):
aurl = self.getList('authorUrl')[i]
aurl = self.getList('authorUrl')[i]
auth = v
# make sure doreplacements & removeallentities are honored.
if doreplacements:
@@ -375,9 +375,9 @@ class Story(Configurable):
if removeallentities:
aurl=removeAllEntities(aurl)
auth=removeAllEntities(auth)
htmllist.append(linkhtml%('author',aurl,auth))
join_string = self.getConfig("join_string_authorHTML",u", ").replace('\s',' ')
join_string = self.getConfig("join_string_authorHTML",u", ").replace('\s',' ')
self.setMetadata('authorHTML',join_string.join(htmllist))
else:
self.setMetadata('authorHTML',linkhtml%('author',self.getMetadata('authorUrl', removeallentities, doreplacements),
@@ -388,20 +388,43 @@ class Story(Configurable):
self.getMetadata('series', removeallentities, doreplacements)))
elif self.getMetadataRaw('series') != None:
self.setMetadata('seriesHTML',self.getMetadataRaw('series'))
# logger.debug("make_linkhtml_entries:%s"%self.getConfig('make_linkhtml_entries'))
for k in self.getConfigList('make_linkhtml_entries'):
# Assuming list, because it has to be site specific and
# they are all lists. Bail if kUrl list not the same
# length.
# logger.debug("\nk:%s\nlist:%s\nlistURL:%s"%(k,self.getList(k),self.getList(k+'Url')))
if len(self.getList(k+'Url')) != len(self.getList(k)):
continue
htmllist=[]
for i, v in enumerate(self.getList(k)):
url = self.getList(k+'Url')[i]
# make sure doreplacements & removeallentities are honored.
if doreplacements:
url=self.doReplacements(url,k+'Url')
v=self.doReplacements(v,k)
if removeallentities:
url=removeAllEntities(url)
v=removeAllEntities(v)
htmllist.append(linkhtml%(k,url,v))
join_string = self.getConfig("join_string_"+k+"HTML",u", ").replace('\s',' ')
self.setMetadata(k+'HTML',join_string.join(htmllist))
for k in self.getValidMetaList():
if self.isList(k) and keeplists:
allmetadata[k] = self.getList(k, removeallentities, doreplacements)
else:
allmetadata[k] = self.getMetadata(k, removeallentities, doreplacements)
return allmetadata
# just for less clutter in adapters.
def extendList(self,listname,l):
for v in l:
self.addToList(listname,v.strip())
def addToList(self,listname,value):
if value==None:
return
@@ -421,24 +444,24 @@ class Story(Configurable):
return self.hasConfig("include_in_"+listname) or \
( self.isValidMetaEntry(listname) and self.metadata.has_key(listname) \
and isinstance(self.metadata[listname],list) )
def getList(self,listname,
removeallentities=False,
doreplacements=True,
includelist=[]):
#print("getList(%s,%s)"%(listname,includelist))
retlist = []
if not self.isValidMetaEntry(listname):
return retlist
# includelist prevents infinite recursion of include_in_'s
if self.hasConfig("include_in_"+listname) and listname not in includelist:
for k in self.getConfigList("include_in_"+listname):
retlist.extend(self.getList(k,removeallentities=False,
doreplacements=doreplacements,includelist=includelist+[listname]))
else:
if not self.isList(listname):
retlist = [self.getMetadata(listname,removeallentities=False,
doreplacements=doreplacements)]
@@ -458,7 +481,7 @@ class Story(Configurable):
# ships=>[ ]*(/|&amp;|&)[ ]*=>/
if listname == 'ships' and self.getConfig('sort_ships'):
retlist = [ '/'.join(sorted(x.split('/'))) for x in retlist ]
if retlist:
if listname in ('author','authorUrl','authorId') or self.getConfig('keep_in_order_'+listname):
# need to retain order for author & authorUrl so the
@@ -473,9 +496,9 @@ class Story(Configurable):
def getSubjectTags(self, removeallentities=False):
# set to avoid duplicates subject tags.
subjectset = set()
tags_list = self.getConfigList("include_subject_tags") + self.getConfigList("extra_subject_tags")
# metadata all go into dc:subject tags, but only if they are configured.
for (name,value) in self.getAllMetadata(removeallentities=removeallentities,keeplists=True).iteritems():
if name in tags_list:
@@ -491,7 +514,7 @@ class Story(Configurable):
subjectset.remove('')
return list(subjectset | set(self.getConfigList("extratags")))
def addChapter(self, url, title, html):
if self.getConfig('strip_chapter_numbers') and \
self.getConfig('chapter_title_strip_pattern'):
@@ -512,7 +535,7 @@ class Story(Configurable):
html) )
else:
retval = self.chapters
return retval
def formatFileName(self,template,allowunsafefilename=True):
@@ -526,7 +549,7 @@ class Story(Configurable):
pattern = re.compile(self.getConfig("output_filename_safepattern",r"[^a-zA-Z0-9_\. \[\]\(\)&'-]+"))
for k in origvalues.keys():
values[k]=re.sub(pattern,'_', removeAllEntities(self.getMetadata(k)))
return string.Template(template).substitute(values).encode('utf8')
# pass fetch in from adapter in case we need the cookies collected
@@ -537,7 +560,7 @@ class Story(Configurable):
# isn't used anywhere.
if cover and self.getConfig('never_make_cover'):
return
url = url.strip() # ran across an image with a space in the
# src. Browser handled it, so we'd better, too.
@@ -545,7 +568,7 @@ class Story(Configurable):
# gets too big too fast and breaks things.
if is_appengine:
return
if url.startswith("http") or url.startswith("file") or parenturl == None:
imgurl = url
else:
@@ -598,7 +621,7 @@ class Story(Configurable):
except Exception, e:
logger.info("Failed to load or convert image, skipping:\n%s\nException: %s"%(imgurl,e))
return "failedtoload"
# explicit cover, make the first image.
if cover and not self.getConfig('never_make_cover'):
if len(self.imgtuples) > 0 and 'cover' in self.imgtuples[0]['newsrc']:
@@ -624,19 +647,19 @@ class Story(Configurable):
self.cover=newsrc
self.imgtuples.append({'newsrc':newsrc,'mime':mime,'data':data})
self.imgurls.append(imgurl)
newsrc = "images/%s-%s.%s"%(
prefix,
self.imgurls.index(imgurl),
ext)
self.imgtuples.append({'newsrc':newsrc,'mime':mime,'data':data})
#logger.debug("\nimgurl:%s\nnewsrc:%s\nimage size:%d\n"%(imgurl,newsrc,len(data)))
else:
newsrc = self.imgtuples[self.imgurls.index(imgurl)]['newsrc']
#print("===============\n%s\nimg url:%s\n============"%(newsrc,self.imgurls[-1]))
return newsrc
def getImgUrls(self):
@@ -645,9 +668,9 @@ class Story(Configurable):
#parsedUrl = urlparse.urlparse(url)
retlist.append(self.imgtuples[i])
return retlist
def __str__(self):
return "Metadata: " +str(self.metadata)
return "Metadata: " +str(self.metadata)
def commaGroups(s):
groups = []
+1 -1
View File
@@ -361,7 +361,7 @@ div { margin: 0pt; padding: 0pt; }
metadata.appendChild(newTag(contentdom,"dc:contributor",text="fanficdownloader [http://fanficdownloader.googlecode.com]",attrs={"opf:role":"bkp"}))
metadata.appendChild(newTag(contentdom,"dc:rights",text=""))
if self.story.getMetadata('langcode') != None:
if self.story.getMetadata('langcode'):
metadata.appendChild(newTag(contentdom,"dc:language",text=self.story.getMetadata('langcode')))
else:
metadata.appendChild(newTag(contentdom,"dc:language",text='en'))
+3 -2
View File
@@ -68,7 +68,8 @@
<h3>Changes:</h3>
<p>
<ul>
<li>Additional fixes/enhancements for replace_br_with_p heuristic processing feature. Turn on in personal User Config. Thanks, Asbjørn Grandt.</li>
<li>Alternate URL efiction.trekiverse.org for trekiverse.org/efiction/</li>
<li>Minor fixes</li>
</ul>
</p>
@@ -80,7 +81,7 @@
If you have any problems with this application, please
report them in
the <a href="http://groups.google.com/group/fanfic-downloader">FanFictionDownLoader Google Group</a>. The
<a href="http://4-4-81.fanfictiondownloader.appspot.com">Previous Version</a> is also available for you to use if necessary.
<a href="http://4-4-86.fanfictiondownloader.appspot.com">Previous Version</a> is also available for you to use if necessary.
</p>
<div id='error'>
{{ error_message }}
+225 -176
View File
@@ -442,7 +442,8 @@ image_max_size: 580, 725
## confused and displays it on every page after that under the text
## for the rest of the chapter. I doubt adding a div around the img
## will break any other readers, but in case it does, the fix can be
## turned off.
## turned off. This setting is not used if replace_br_with_p is
## true--replace_br_with_p also fixes the problem.
nook_img_fix:true
[mobi]
@@ -506,6 +507,13 @@ extratags: FanFiction,Testing,HTML
## personal.ini, not defaults.ini.
#is_adult:true
## archiveofourown.org stories allow chapters to be added out of
## order. So the newest chapter may not be the last one. FFDL update
## doesn't like that. If do_update_hook is uncommented and set true,
## the adapter will discard all existing chapters from the newest one
## on when updating to enforce accurate chapters.
#do_update_hook:false
## AO3 adapter defines a few extra metadata entries.
## If there's ever more than 4 series, add series04,series04Url etc.
extra_valid_entries:fandoms,freeformtags,freefromtags,ao3categories,comments,kudos,hits,bookmarks,collections,series00,series01,series02,series03,series00Url,series01Url,series02Url,series03Url
@@ -530,11 +538,6 @@ include_in_freefromtags:freeformtags
#extra_subject_tags:fandoms,freeformtags,ao3categories
[ashwinder.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Hermione Granger
extraships:Severus Snape/Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -542,6 +545,11 @@ extraships:Severus Snape/Hermione Granger
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Hermione Granger
extraships:Severus Snape/Hermione Granger
[asr3.slashzone.org]
## Site dedicated to these categories/characters/ships
extracategories:The Sentinel
@@ -552,9 +560,6 @@ extracategories:The Sentinel
#is_adult:true
[bloodties-fans.com]
## Site dedicated to these categories/characters/ships
extracategories:Blood Ties
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -567,6 +572,9 @@ extracategories:Blood Ties
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Blood Ties
[buffynfaith.net]
## Site dedicated to these categories/characters/ships
extracategories:Buffy: The Vampire Slayer
@@ -577,9 +585,6 @@ extracategories:Buffy: The Vampire Slayer
#is_adult:true
[castlefans.org]
## Site dedicated to these categories/characters/ships
extracategories:Castle
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -592,6 +597,9 @@ extracategories:Castle
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Castle
[chaos.sycophanthex.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -604,10 +612,23 @@ cover_exclusion_regexp:/images/.*?ribbon.gif
[dark-solace.org]
## Site dedicated to these categories/characters/ships
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
extracategories:Buffy: The Vampire Slayer
extracharacters:Buffy, Spike
extraships:Spike/Buffy
[dramione.org]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -620,24 +641,11 @@ extraships:Spike/Buffy
## personal.ini, not defaults.ini.
#is_adult:true
[dramione.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Draco Malfoy,Hermione Granger
extraships:Draco Malfoy/Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/images/.*?ribbon.gif
@@ -696,22 +704,19 @@ cliches_label:Character Cliches
extracategories:Lord of the Rings
[erosnsappho.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/images/.*?ribbon.gif
[fanfiction.mugglenet.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -724,10 +729,10 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[fanfic.potterheadsanonymous.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -740,16 +745,19 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[fanfiction.portkey.org]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Hermione Granger
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[fanfiction.tenhawkpresents.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -802,10 +810,6 @@ universe_label:Universe
codes_label:Codes
[grangerenchanted.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Hermione Granger
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -818,6 +822,10 @@ extracharacters:Hermione Granger
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Hermione Granger
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:read,reviews
@@ -854,18 +862,15 @@ extracharacters:Kirk,Spock
extraships:Kirk/Spock
[lumos.sycophanthex.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[merlinfic.dtwins.co.uk]
## Site dedicated to these categories/characters/ships
extracategories:Merlin
extracategories:Harry Potter
[merlinfic.dtwins.co.uk]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -878,6 +883,9 @@ extracategories:Merlin
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Merlin
[national-library.net]
## Site dedicated to these categories/characters/ships
extracategories:West Wing
@@ -889,24 +897,32 @@ extracategories:NCIS
[netraptor.org]
[nfacommunity.com]
## Site dedicated to these categories/characters/ships
extracategories:NCIS
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:NCIS
[nha.magical-worlds.us]
## Site dedicated to these categories/characters/ships
extracategories:Buffy: The Vampire Slayer
extracharacters:Willow
[occlumency.sycophanthex.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape
[onedirectionfanfiction.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -914,10 +930,15 @@ extracharacters:Severus Snape
#username:YourName
#password:yourpassword
[onedirectionfanfiction.com]
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:One Direction
[pommedesang.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -930,40 +951,27 @@ extracategories:One Direction
## personal.ini, not defaults.ini.
#is_adult:true
[pommedesang.com]
## Site dedicated to these categories/characters/ships
extracategories:Anita Blake Vampire Hunter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
[ponyfictionarchive.net]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[ponyfictionarchive.net]
## Site dedicated to these categories/characters/ships
extracategories:My Little Pony: Friendship is Magic
[pretendercentre.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[pretendercentre.com]
## Site dedicated to these categories/characters/ships
extracategories:The Pretender
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[samdean.archive.nu]
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
@@ -971,9 +979,6 @@ extracharacters:Sam,Dean
extraships:Sam/Dean
[scarhead.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -986,6 +991,9 @@ extracategories:Harry Potter
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[sg1-heliopolis.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -1016,9 +1024,6 @@ extracharacters:Draco Malfoy,Harry Potter
extraships:Harry Potter/Draco Malfoy
[thehookupzone.net]
## Site dedicated to these categories/characters/ships
extracategories:Criminal Minds
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1031,6 +1036,9 @@ extracategories:Criminal Minds
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Criminal Minds
[themasque.net]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1045,9 +1053,6 @@ extracategories:Criminal Minds
#is_adult:true
[thequidditchpitch.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1060,50 +1065,71 @@ extracategories:Harry Potter
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[tokra.fandomnet.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Stargate: SG-1
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
[trekiverse.org]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
[www.adastrafanfic.com]
## Site dedicated to these categories/characters/ships
extracategories:Star Trek
extra_valid_entries:awards
awards_label:Awards
cover_exclusion_regexp:art/.*Awards.jpg
[www.adastrafanfic.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Star Trek
[www.dracoandginny.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Draco Malfoy,Ginny Weasley
extraships:Draco Malfoy/Ginny Weasley
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
## defaults.ini.
#username:YourName
#password:yourpassword
## Some sites also require the user to confirm they are adult for
## adult content. In commandline version, this should go in your
## personal.ini, not defaults.ini.
#is_adult:true
[www.thealphagate.com]
## Site dedicated to these categories/characters/ships
extracategories:Stargate: SG-1
[www.checkmated.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1111,6 +1137,9 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.destinysgateway.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
@@ -1118,11 +1147,6 @@ extracategories:Harry Potter
#is_adult:true
[www.dokuga.com]
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:Sesshoumaru,Kagome
extraships:Sesshoumaru/Kagome
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1130,6 +1154,11 @@ extraships:Sesshoumaru/Kagome
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:Sesshoumaru,Kagome
extraships:Sesshoumaru/Kagome
[www.dotmoon.net]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1185,14 +1214,14 @@ dateUpdated_format:%%Y-%%m-%%d %%H:%%M:%%S
[www.ficbook.net]
[www.fictionalley.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## fictionalley.org doesn't have a status metadatum. If uncommented,
## this will be used for status.
#default_value_status:Unknown
@@ -1215,19 +1244,6 @@ extra_valid_entries:reviews,favs,follows
#password:yourpassword
[www.fimfiction.net]
## Site dedicated to these categories/characters/ships
extracategories:My Little Pony: Friendship is Magic
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:likes,dislikes,views,total_views,short_description,groups
likes_label:Likes
dislikes_label:Dislikes
views_label:Highest Single Chapter Views
total_views_label:Total Views
short_description_label:Short Summary
groups_label:Groups
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
@@ -1245,38 +1261,63 @@ groups_label:Groups
## when updating to enforce accurate chapters.
#do_update_hook:false
[www.harrypotterfanfiction.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracategories:My Little Pony: Friendship is Magic
## Extra metadata that this adapter knows about. See [dramione.org]
## for examples of how to use them.
extra_valid_entries:likes,dislikes,views,total_views,short_description,groups,groupsUrl,groupsHTML,prequel,prequelUrl,prequelHTML,sequels,sequelsUrl,sequelsHTML
likes_label:Likes
dislikes_label:Dislikes
views_label:Highest Single Chapter Views
total_views_label:Total Views
short_description_label:Short Summary
groups_label:Groups
groupsUrl_label:Groups URLs
groupsHTML_label:Groups
prequel_label:Prequel
prequelUrl_label:Prequel URL
prequelHTML_label:Prequel
sequels_label:Sequels
sequelsUrl_label:Sequel URLs
sequelsHTML_label:Sequels
keep_in_order_sequels:true
keep_in_order_sequelsUrl:true
keep_in_order_groups:true
keep_in_order_groupsUrl:true
## Assume entryUrl, apply to "<a class='%slink' href='%s'>%s</a>" to
## make entryHTML.
make_linkhtml_entries:prequel,sequels,groups
[www.harrypotterfanfiction.com]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.henneth-annun.net]
## Site dedicated to these categories/characters/ships
extracategories:The Hobbit
[www.hpfandom.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.hpfanficarchive.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
[www.ik-eternal.net]
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:InuYasha,Kagome
extraships:InuYasha/Kagome
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1289,30 +1330,35 @@ extraships:InuYasha/Kagome
## personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:InuYasha
extracharacters:InuYasha,Kagome
extraships:InuYasha/Kagome
[www.jlaunlimited.com]
## Site dedicated to these categories/characters/ships
extracategories:JLA
[www.libraryofmoria.com]
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
[www.mediaminer.org]
[www.midnightwhispers.ca]
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## some sites include images that we don't ever want becoming the
## cover image. This lets you exclude them.
cover_exclusion_regexp:/stories/999/images/.*?_trophy.png
@@ -1327,10 +1373,6 @@ extracategories:CSI
extraships:Nick Stokes/Greg Sanders
[www.phoenixsong.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Ginny Weasley
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1341,9 +1383,13 @@ extraships:Harry Potter/Ginny Weasley
## phoenixsong.net, oddly, can have high rated chapters (login
## required) in the middle of a lower rated story. Use this to force
## FFDL to always login to phoenixsong.net so those stories download
## correctly.
## correctly. If you have a login, this is recommended.
#force_login:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extraships:Harry Potter/Ginny Weasley
[www.potionsandsnitches.net]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
@@ -1366,17 +1412,15 @@ extracategories:Psych
#is_adult:true
[www.qaf-fic.com]
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Queer as Folk
[www.restrictedsection.org]
extracategories:Harry Potter
extragenres:Erotica
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1384,20 +1428,21 @@ extragenres:Erotica
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extragenres:Erotica
[www.scarvesandcoffee.net]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Glee
extracharacters:Kurt Hummel,Blaine Anderson
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
[www.simplyundeniable.com]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1405,15 +1450,18 @@ extracategories:Harry Potter
#username:YourName
#password:yourpassword
[www.sinful-desire.org]
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
extracategories:Harry Potter
[www.sinful-desire.org]
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Supernatural
[www.siye.co.uk]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
@@ -1421,25 +1469,26 @@ extracharacters:Harry Potter,Ginny Weasley
extraships:Harry Potter/Ginny Weasley
[www.squidge.org/peja]
# www.squidge.org/peja calls it Fandom <shrug>
## www.squidge.org/peja calls it Fandom <shrug>
category_label:Fandom
# Remove numWords -- www.squidge.org/peja word counts are inaccurate
## Remove numWords -- www.squidge.org/peja word counts are inaccurate
titlepage_entries: seriesHTML,category,genre,language,characters,ships,status,datePublished,dateUpdated,dateCreated,rating,warnings,numChapters,site,description
[www.squidge.org/peja:txt]
## Add URLs since there aren't links.
# Remove numWords -- www.squidge.org/peja word counts are inaccurate
## Add URLs since there aren't links and remove numWords --
## www.squidge.org/peja word counts are inaccurate
titlepage_entries: series,seriesUrl,category,genre,language,status,datePublished,dateUpdated,dateCreated,rating,warnings,numChapters,site,storyUrl, authorUrl, description
[www.storiesofarda.com]
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Lord of the Rings
[www.thepetulantpoetess.com]
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
@@ -1482,9 +1531,6 @@ collect_series: false
extracategories:Twilight
[www.twilighted.net]
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1492,13 +1538,13 @@ extracategories:Twilight
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## twilighted.net (ab)uses series as personal reading lists.
collect_series: false
[www.twiwrite.net]
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## Some sites require login (or login for some rated stories) The
## program can prompt you, or you can save it in config. In
## commandline version, this should go in your personal.ini, not
@@ -1506,20 +1552,23 @@ extracategories:Twilight
#username:YourName
#password:yourpassword
## Site dedicated to these categories/characters/ships
extracategories:Twilight
## twiwrite.net (ab)uses series as personal reading lists.
collect_series: false
[www.walkingtheplank.org]
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Harry Potter
extraships:Severus Snape/Harry Potter
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Harry Potter
extracharacters:Severus Snape,Harry Potter
extraships:Severus Snape/Harry Potter
[www.whofic.com]
[www.wizardtales.net]
@@ -1541,14 +1590,14 @@ extracategories:X-Men Movie
extracharacters:Wolverine,Rogue
[www.wraithbait.com]
## Site dedicated to these categories/characters/ships
extracategories:Stargate: Atlantis
## Some sites do not require a login, but do require the user to
## confirm they are adult for adult content. In commandline version,
## this should go in your personal.ini, not defaults.ini.
#is_adult:true
## Site dedicated to these categories/characters/ships
extracategories:Stargate: Atlantis
[overrides]
## It may sometimes be useful to override all of the specific format,
## site and site:format sections in your private configuration. For