mirror of https://github.com/tildeclub/ttbp.git
commit
37cd29090c
|
@ -236,6 +236,9 @@ instance of this yourself)
|
||||||
* [mistune](https://pypi.python.org/pypi/mistune)
|
* [mistune](https://pypi.python.org/pypi/mistune)
|
||||||
* [inflect](https://pypi.python.org/pypi/inflect)
|
* [inflect](https://pypi.python.org/pypi/inflect)
|
||||||
* [six](https://pypi.python.org/pypi/six)
|
* [six](https://pypi.python.org/pypi/six)
|
||||||
|
* [colorama](https://pypi.python.org/pypi/colorama)
|
||||||
|
* [feedgen](https://pypi.python.org/pypi/feedgen)
|
||||||
|
* [dateutil](https://pypi.python.org/pypi/python-dateutil)
|
||||||
|
|
||||||
### contributing
|
### contributing
|
||||||
|
|
||||||
|
|
4
setup.py
4
setup.py
|
@ -20,7 +20,9 @@ setup(
|
||||||
'inflect',
|
'inflect',
|
||||||
'mistune',
|
'mistune',
|
||||||
'colorama',
|
'colorama',
|
||||||
'six'
|
'six',
|
||||||
|
'feedgen',
|
||||||
|
'python-dateutil',
|
||||||
],
|
],
|
||||||
include_package_data = True,
|
include_package_data = True,
|
||||||
entry_points = {
|
entry_points = {
|
||||||
|
|
|
@ -0,0 +1,96 @@
|
||||||
|
#!/usr/bin/python
|
||||||
|
|
||||||
|
'''
|
||||||
|
ttbp: tilde town blogging platform
|
||||||
|
(also known as the feels engine)
|
||||||
|
a console-based blogging program developed for tilde.town
|
||||||
|
copyright (c) 2016 ~endorphant (endorphant@tilde.town)
|
||||||
|
|
||||||
|
atom.py:
|
||||||
|
Atom feed generation
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining
|
||||||
|
a copy of this software and associated documentation files (the
|
||||||
|
"Software"), to deal in the Software without restriction, including
|
||||||
|
without limitation the rights to use, copy, modify, merge, publish,
|
||||||
|
distribute, sublicense, and/or sell copies of the Software, and to
|
||||||
|
permit persons to whom the Software is furnished to do so, subject to
|
||||||
|
the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be
|
||||||
|
included in all copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
|
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||||
|
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||||
|
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||||
|
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
|
||||||
|
the complete codebase is available at:
|
||||||
|
https://github.com/modgethanc/ttbp
|
||||||
|
'''
|
||||||
|
from . import config
|
||||||
|
from . import util
|
||||||
|
from feedgen.feed import FeedGenerator
|
||||||
|
import os
|
||||||
|
import mistune
|
||||||
|
import datetime
|
||||||
|
import stat
|
||||||
|
from dateutil import tz
|
||||||
|
|
||||||
|
def publish_atom(entry_filenames, settings):
|
||||||
|
fg = FeedGenerator()
|
||||||
|
url = (config.LIVE + config.USER + '/' +
|
||||||
|
str(settings.get("publish dir"))).rstrip('/')
|
||||||
|
fg.id(url)
|
||||||
|
fg.title("{}'s feels".format(config.USER))
|
||||||
|
fg.author(name=config.USER)
|
||||||
|
fg.link(href=url+'/', rel='alternate')
|
||||||
|
fg.link(href=url+'/atom.xml', rel='self')
|
||||||
|
fg.language('en') # TODO: feels language should be configurable
|
||||||
|
fg.updated(datetime.datetime.now(tz.tzlocal()))
|
||||||
|
|
||||||
|
for filename in sorted(entry_filenames):
|
||||||
|
date = util.parse_date(filename)
|
||||||
|
title = "-".join(date)
|
||||||
|
name = "".join(date)
|
||||||
|
|
||||||
|
path = os.path.join(config.MAIN_FEELS, filename)
|
||||||
|
with open(path) as f:
|
||||||
|
raw = f.read()
|
||||||
|
html = mistune.markdown(raw)
|
||||||
|
|
||||||
|
fe = fg.add_entry(order='prepend')
|
||||||
|
fe.id(url+'/'+name)
|
||||||
|
fe.link(href=url+'/'+name+'.html', rel="alternate")
|
||||||
|
fe.title(title)
|
||||||
|
fe.author(name=config.USER)
|
||||||
|
fe.content(html, type="html")
|
||||||
|
try: # crashing because of an invalid date would be sad
|
||||||
|
year, month, day = [int(x) for x in date]
|
||||||
|
fe.published(datetime.datetime(year, month, day,
|
||||||
|
tzinfo=tz.tzlocal()))
|
||||||
|
stats = os.stat(path)
|
||||||
|
updated = datetime.datetime.fromtimestamp(stats[stat.ST_MTIME],
|
||||||
|
tz.tzlocal())
|
||||||
|
fe.updated(updated)
|
||||||
|
except ValueError:
|
||||||
|
pass
|
||||||
|
outfile = os.path.join(config.WWW, 'atom.xml')
|
||||||
|
fg.atom_file(outfile)
|
||||||
|
|
||||||
|
def select_atom():
|
||||||
|
publish = util.input_yn("""
|
||||||
|
SETTING UP ATOM
|
||||||
|
|
||||||
|
Atom is a syndication format similar to RSS.
|
||||||
|
it is used so that people can subscribe to blogs and other news sources.
|
||||||
|
|
||||||
|
do you want to generate an atom feed for your feels along the HTML?
|
||||||
|
this setting only has effect if publishing is enabled.
|
||||||
|
|
||||||
|
you can change this option any time.
|
||||||
|
""")
|
||||||
|
return publish
|
24
ttbp/core.py
24
ttbp/core.py
|
@ -43,6 +43,7 @@ from . import chatter
|
||||||
from . import config
|
from . import config
|
||||||
from . import gopher
|
from . import gopher
|
||||||
from . import util
|
from . import util
|
||||||
|
from . import atom
|
||||||
|
|
||||||
FEED = os.path.join("/home", "endorphant", "public_html", "ttbp", "index.html")
|
FEED = os.path.join("/home", "endorphant", "public_html", "ttbp", "index.html")
|
||||||
SETTINGS = {}
|
SETTINGS = {}
|
||||||
|
@ -95,6 +96,23 @@ def get_files(feelsdir=config.MAIN_FEELS):
|
||||||
|
|
||||||
return files
|
return files
|
||||||
|
|
||||||
|
def render(files):
|
||||||
|
out = ""
|
||||||
|
if publishing():
|
||||||
|
write_html("index.html")
|
||||||
|
out += "posted to {url}/index.html\n\n> ".format(
|
||||||
|
url="/".join(
|
||||||
|
[config.LIVE+config.USER,
|
||||||
|
str(SETTINGS.get("publish dir"))]))
|
||||||
|
if SETTINGS.get('gopher'):
|
||||||
|
gopher.publish_gopher('feels', files)
|
||||||
|
out += "also posted to your ~/public_gopher!\n\n> "
|
||||||
|
if SETTINGS.get('atom'):
|
||||||
|
atom.publish_atom(files, SETTINGS)
|
||||||
|
out += "also posted to your atom feed {url}/atom.xml!\n\n> "
|
||||||
|
return out
|
||||||
|
|
||||||
|
|
||||||
def load_files(feelsdir=config.MAIN_FEELS):
|
def load_files(feelsdir=config.MAIN_FEELS):
|
||||||
'''
|
'''
|
||||||
file loader
|
file loader
|
||||||
|
@ -108,11 +126,7 @@ def load_files(feelsdir=config.MAIN_FEELS):
|
||||||
|
|
||||||
load_nopubs()
|
load_nopubs()
|
||||||
FILES = get_files(feelsdir)
|
FILES = get_files(feelsdir)
|
||||||
|
render(FILES)
|
||||||
if publishing():
|
|
||||||
write_html("index.html")
|
|
||||||
if SETTINGS.get('gopher'):
|
|
||||||
gopher.publish_gopher('feels', FILES)
|
|
||||||
|
|
||||||
def load_nopubs():
|
def load_nopubs():
|
||||||
"""Load a list of the user's nopub entries.
|
"""Load a list of the user's nopub entries.
|
||||||
|
|
26
ttbp/ttbp.py
26
ttbp/ttbp.py
|
@ -50,6 +50,7 @@ from . import core
|
||||||
from . import chatter
|
from . import chatter
|
||||||
from . import gopher
|
from . import gopher
|
||||||
from . import util
|
from . import util
|
||||||
|
from . import atom
|
||||||
|
|
||||||
__version__ = "0.12.2"
|
__version__ = "0.12.2"
|
||||||
__author__ = "endorphant <endorphant@tilde.town)"
|
__author__ = "endorphant <endorphant@tilde.town)"
|
||||||
|
@ -75,6 +76,7 @@ DEFAULT_SETTINGS = {
|
||||||
"publishing": False,
|
"publishing": False,
|
||||||
"rainbows": False,
|
"rainbows": False,
|
||||||
"post as nopub": False,
|
"post as nopub": False,
|
||||||
|
"atom": False,
|
||||||
}
|
}
|
||||||
|
|
||||||
## user globals
|
## user globals
|
||||||
|
@ -85,7 +87,8 @@ SETTINGS = {
|
||||||
"publishing": False,
|
"publishing": False,
|
||||||
"rainbows": False,
|
"rainbows": False,
|
||||||
"post as nopub": False,
|
"post as nopub": False,
|
||||||
}
|
"atom": False,
|
||||||
|
}
|
||||||
|
|
||||||
## ttbp specific utilities
|
## ttbp specific utilities
|
||||||
|
|
||||||
|
@ -402,7 +405,8 @@ def setup_repair():
|
||||||
"publish dir": select_publish_dir,
|
"publish dir": select_publish_dir,
|
||||||
"gopher": gopher.select_gopher,
|
"gopher": gopher.select_gopher,
|
||||||
"rainbows": toggle_rainbows,
|
"rainbows": toggle_rainbows,
|
||||||
"post as nopub": toggle_pub_default
|
"post as nopub": toggle_pub_default,
|
||||||
|
"atom": atom.select_atom,
|
||||||
}
|
}
|
||||||
|
|
||||||
for option in iter(settings_map):
|
for option in iter(settings_map):
|
||||||
|
@ -504,6 +508,13 @@ def setup():
|
||||||
save_settings()
|
save_settings()
|
||||||
return setup()
|
return setup()
|
||||||
|
|
||||||
|
#atom opt-in
|
||||||
|
elif settingList[int(choice)] == "atom":
|
||||||
|
SETTINGS.update({"atom": atom.select_atom()})
|
||||||
|
redraw("atom set to {}".format(SETTINGS.get("atom")))
|
||||||
|
save_settings()
|
||||||
|
return setup()
|
||||||
|
|
||||||
input("\nyou're all good to go, {friend}! hit <enter> to continue.\n\n".format(friend=chatter.say("friend")))
|
input("\nyou're all good to go, {friend}! hit <enter> to continue.\n\n".format(friend=chatter.say("friend")))
|
||||||
redraw()
|
redraw()
|
||||||
|
|
||||||
|
@ -1202,16 +1213,7 @@ def write_entry(entry=os.path.join(config.MAIN_FEELS, "test.txt")):
|
||||||
if SETTINGS.get("post as nopub"):
|
if SETTINGS.get("post as nopub"):
|
||||||
core.toggle_nopub(os.path.basename(entry))
|
core.toggle_nopub(os.path.basename(entry))
|
||||||
else:
|
else:
|
||||||
if core.publishing():
|
left = core.render(core.FILES)
|
||||||
core.write_html("index.html")
|
|
||||||
left = "posted to {url}/index.html\n\n> ".format(
|
|
||||||
url="/".join(
|
|
||||||
[config.LIVE+config.USER,
|
|
||||||
str(SETTINGS.get("publish dir"))]))
|
|
||||||
|
|
||||||
if SETTINGS.get('gopher'):
|
|
||||||
gopher.publish_gopher('feels', core.FILES)
|
|
||||||
left += "also posted to your ~/public_gopher!\n\n> "
|
|
||||||
|
|
||||||
#core.load_files()
|
#core.load_files()
|
||||||
redraw(left + "thanks for sharing your feels!")
|
redraw(left + "thanks for sharing your feels!")
|
||||||
|
|
Loading…
Reference in New Issue