|
@@ -1,3 +1,6 @@
|
|
|
|
+from dataclasses import dataclass
|
|
|
|
+from typing import List, Dict, Optional
|
|
|
|
+
|
|
from hashlib import sha256
|
|
from hashlib import sha256
|
|
import os
|
|
import os
|
|
from pathlib import Path
|
|
from pathlib import Path
|
|
@@ -49,7 +52,7 @@ def index ():
|
|
|
|
|
|
@api.get('/img')
|
|
@api.get('/img')
|
|
def get_image ():
|
|
def get_image ():
|
|
- print('GET IMG')
|
|
+ print('GET IMG: FIXME this should be done with caching proxy')
|
|
url = request.args['url']
|
|
url = request.args['url']
|
|
url_hash = sha256(url.encode('utf-8')).hexdigest()
|
|
url_hash = sha256(url.encode('utf-8')).hexdigest()
|
|
path = f'.data/cache/media/{url_hash}'
|
|
path = f'.data/cache/media/{url_hash}'
|
|
@@ -180,6 +183,107 @@ def get_schedule_create_job_html ():
|
|
|
|
|
|
return render_template_string(template, **view_model)
|
|
return render_template_string(template, **view_model)
|
|
|
|
|
|
|
|
+@dataclass
|
|
|
|
+class FeedItemMedia:
|
|
|
|
+ url: str
|
|
|
|
+ mimetype: str
|
|
|
|
+
|
|
|
|
+@dataclass
|
|
|
|
+class FeedItem:
|
|
|
|
+ id: str
|
|
|
|
+ text: str
|
|
|
|
+ media: Optional[List[FeedItemMedia]] = None
|
|
|
|
+
|
|
|
|
+def ingest_feed_item (feed_item: FeedItem) -> FeedItem:
|
|
|
|
+ with sqlite3.connect('.data/ingest.db') as db:
|
|
|
|
+ with db.cursor() as cur:
|
|
|
|
+ #cur.row_factory = sqlite3.Row
|
|
|
|
+
|
|
|
|
+ feed_item_table_exists = False # example in Hogumathi, twitter archive plugin I think
|
|
|
|
+ if not feed_item_table_exists:
|
|
|
|
+ cur.execute("""
|
|
|
|
+ create table feed_item (
|
|
|
|
+ id text,
|
|
|
|
+ text text
|
|
|
|
+ )
|
|
|
|
+
|
|
|
|
+ """)
|
|
|
|
+ cur.execute("""
|
|
|
|
+ create table feed_item_media (
|
|
|
|
+ feed_item_id integer,
|
|
|
|
+ url text,
|
|
|
|
+ mimetype text
|
|
|
|
+ )
|
|
|
|
+
|
|
|
|
+ """)
|
|
|
|
+ sql = 'insert into feed_item (id, text) values (?, ?)'
|
|
|
|
+ params = [
|
|
|
|
+ feed_item.id,
|
|
|
|
+ feed_item.text
|
|
|
|
+ ]
|
|
|
|
+
|
|
|
|
+ res = cur.execute(sql, params)
|
|
|
|
+
|
|
|
|
+ if not res:
|
|
|
|
+ print('could not ingest feed_item')
|
|
|
|
+ return False
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+ return feed_item
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+def ingest_feed_item_media (feed_item: FeedItem) -> FeedItem:
|
|
|
|
+ print('ingest_feed_item_media')
|
|
|
|
+
|
|
|
|
+ if not feed_item.media:
|
|
|
|
+ return feed_item
|
|
|
|
+
|
|
|
|
+ with sqlite3.connect('.data/ingest.db') as db:
|
|
|
|
+ with db.cursor() as cur:
|
|
|
|
+ #cur.row_factory = sqlite3.Row
|
|
|
|
+
|
|
|
|
+ for media_item in feed_item.media:
|
|
|
|
+
|
|
|
|
+ # TODO import URL to files app and store that URL.
|
|
|
|
+ # may want to support several URLs, so that offline LANs work.
|
|
|
|
+
|
|
|
|
+ sql = 'insert into feed_item_media (feed_item_id, url, mimetype) values (?, ?, ?)'
|
|
|
|
+ params = [
|
|
|
|
+ feed_item.id,
|
|
|
|
+ media_item.url,
|
|
|
|
+ media_item.mimetype
|
|
|
|
+ ]
|
|
|
|
+ res = cur.execute(sql, params)
|
|
|
|
+
|
|
|
|
+ if not res:
|
|
|
|
+ print('could not ingest feed_item_media')
|
|
|
|
+
|
|
|
|
+ return feed_item
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+@api.post('/api/ingest/feed-item')
|
|
|
|
+def api_ingest_feed_item ():
|
|
|
|
+ """
|
|
|
|
+ Eventually other content sources with ingest here, and this will be the main DB.
|
|
|
|
+ Via inigest_feed_Item and ingest_feed_item_media.
|
|
|
|
+
|
|
|
|
+ They could be worker tasks. Work when submitted directly from browser extension.
|
|
|
|
+ """
|
|
|
|
+ print('api_ingest_feed_item')
|
|
|
|
+ ingest_media = int(request.args.get('ingest_media', 1))
|
|
|
|
+ feed_item = request.args.get('feed_item') # FIXME might want to use post body/form
|
|
|
|
+ feed_item = from_dict(data_class=FeedItem, data=feed_item)
|
|
|
|
+
|
|
|
|
+ fi_i_res = ingest_feed_item(feed_item)
|
|
|
|
+
|
|
|
|
+ if ingest_media: # and fi_i_res(blocking=True, timeout=5):
|
|
|
|
+ fi_i_media_res = ingest_feed_item_media(feed_item)
|
|
|
|
+
|
|
|
|
+ #fi_i_media_res(blocking=True)
|
|
|
|
+
|
|
|
|
+ return 'ok'
|
|
|
|
+
|
|
@api.get('/health')
|
|
@api.get('/health')
|
|
def get_health ():
|
|
def get_health ():
|
|
return 'ok'
|
|
return 'ok'
|