update documentation on using Polar
This commit is contained in:
parent
968c448013
commit
9e9fa9620c
4 changed files with 25 additions and 39 deletions
|
@ -117,6 +117,13 @@ Generally you can just try using the module and then install missing packages vi
|
||||||
* Usage examples
|
* Usage examples
|
||||||
If you run your script with ~with_my~ wrapper, you'd have ~my~ in ~PYTHONPATH~ which gives you access to your data from within the script.
|
If you run your script with ~with_my~ wrapper, you'd have ~my~ in ~PYTHONPATH~ which gives you access to your data from within the script.
|
||||||
|
|
||||||
|
** Polar
|
||||||
|
Polar doesn't require any setup as it accesses the highlights on your filesystem (should be in =~/.polar=).
|
||||||
|
|
||||||
|
You can try if it works with:
|
||||||
|
|
||||||
|
: with_my python3 -c 'import my.reading.polar as polar; print(polar.get_entries())'
|
||||||
|
|
||||||
** Kobo reader
|
** Kobo reader
|
||||||
Kobo provider allows you access the books you've read along with the highlights and notes.
|
Kobo provider allows you access the books you've read along with the highlights and notes.
|
||||||
It uses exports provided by [[https://github.com/karlicoss/kobuddy][kobuddy]] package.
|
It uses exports provided by [[https://github.com/karlicoss/kobuddy][kobuddy]] package.
|
||||||
|
@ -137,11 +144,13 @@ After that you should be able to use it:
|
||||||
#+end_src
|
#+end_src
|
||||||
|
|
||||||
** Orger
|
** Orger
|
||||||
|
# TODO include this from orger docs??
|
||||||
|
|
||||||
You can use [[https://github.com/karlicoss/orger][orger]] to get Org-mode representations of your data.
|
You can use [[https://github.com/karlicoss/orger][orger]] to get Org-mode representations of your data.
|
||||||
|
|
||||||
Some examples:
|
Some examples (assuming you've [[https://github.com/karlicoss/orger#installing][installed]] Orger):
|
||||||
|
|
||||||
*** [[https://github.com/burtonator/polar-bookshelf][Polar]]
|
*** Orger + [[https://github.com/burtonator/polar-bookshelf][Polar]]
|
||||||
|
|
||||||
This will convert Polar highlights into org-mode:
|
This will convert Polar highlights into org-mode:
|
||||||
|
|
||||||
|
|
19
lint
19
lint
|
@ -18,25 +18,22 @@ DIR = Path(__file__).absolute().parent
|
||||||
|
|
||||||
# TODO could reuse in readme??
|
# TODO could reuse in readme??
|
||||||
# returns None if not a package
|
# returns None if not a package
|
||||||
def package_name(p: Path) -> Optional[str]:
|
def package_name(p: Path) -> str:
|
||||||
def mname(p: Path):
|
def mname(p: Path):
|
||||||
nosuf = p.with_suffix('')
|
nosuf = p.with_suffix('')
|
||||||
return str(nosuf).replace('/', '.')
|
return str(nosuf).replace('/', '.')
|
||||||
|
|
||||||
if p.suffix == '.py':
|
has_init = (p.parent / '__init__.py').exists()
|
||||||
|
if has_init:
|
||||||
|
return mname(p.parent)
|
||||||
|
else:
|
||||||
return mname(p)
|
return mname(p)
|
||||||
|
|
||||||
if p.is_dir() and (p / '__init__.py').exists():
|
|
||||||
return mname(p)
|
|
||||||
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
def packages() -> Iterable[str]:
|
def packages() -> Iterable[str]:
|
||||||
for p in sorted(p.relative_to(DIR) for p in (DIR / 'my').iterdir()):
|
yield from sorted(set(
|
||||||
res = package_name(p)
|
package_name(p.relative_to(DIR)) for p in (DIR / 'my').rglob('*.py')
|
||||||
if res is not None:
|
))
|
||||||
yield res
|
|
||||||
|
|
||||||
|
|
||||||
def pylint():
|
def pylint():
|
||||||
|
|
|
@ -1,36 +1,25 @@
|
||||||
#!/usr/bin/python3
|
|
||||||
"""
|
"""
|
||||||
Module for Polar articles and highlights
|
[[https://github.com/burtonator/polar-books][Polar]] articles and highlights
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
import logging
|
|
||||||
from typing import List, Dict, Iterator, NamedTuple, Sequence, Optional
|
from typing import List, Dict, Iterator, NamedTuple, Sequence, Optional
|
||||||
import json
|
import json
|
||||||
|
|
||||||
import pytz
|
import pytz
|
||||||
# TODO declare DEPENDS = [pytz??]
|
# TODO declare DEPENDS = [pytz??]
|
||||||
|
|
||||||
from ..common import setup_logger
|
from ..common import LazyLogger, get_files
|
||||||
|
|
||||||
from ..error import ResT, echain, unwrap, sort_res_by
|
from ..error import ResT, echain, unwrap, sort_res_by
|
||||||
from ..kython.konsume import wrap, zoom, ignore
|
from ..kython.konsume import wrap, zoom, ignore
|
||||||
|
|
||||||
|
|
||||||
# TOFO FIXME appdirs??
|
_POLAR_DIR = Path('~').expanduser() / '.polar'
|
||||||
_POLAR_DIR = Path('~/.polar')
|
|
||||||
|
|
||||||
|
|
||||||
# TODO FIXME lazylogger??
|
logger = LazyLogger(__name__)
|
||||||
def get_logger():
|
|
||||||
# TODO __package__?
|
|
||||||
return logging.getLogger('my.reading.polar')
|
|
||||||
|
|
||||||
|
|
||||||
def _get_datas() -> List[Path]:
|
|
||||||
return list(sorted(_POLAR_DIR.expanduser().glob('*/state.json')))
|
|
||||||
|
|
||||||
|
|
||||||
def parse_dt(s: str) -> datetime:
|
def parse_dt(s: str) -> datetime:
|
||||||
|
@ -74,7 +63,7 @@ class Loader:
|
||||||
self.path = p
|
self.path = p
|
||||||
self.uid = self.path.parent.name
|
self.uid = self.path.parent.name
|
||||||
self.err = Error(p)
|
self.err = Error(p)
|
||||||
self.logger = get_logger()
|
self.logger = logger
|
||||||
|
|
||||||
def error(self, cause, extra=''):
|
def error(self, cause, extra=''):
|
||||||
return echain(Error(self.path, extra), cause)
|
return echain(Error(self.path, extra), cause)
|
||||||
|
@ -185,8 +174,7 @@ class Loader:
|
||||||
|
|
||||||
|
|
||||||
def iter_entries() -> Iterator[Result]:
|
def iter_entries() -> Iterator[Result]:
|
||||||
logger = get_logger()
|
for d in get_files(_POLAR_DIR, glob='*/state.json'):
|
||||||
for d in _get_datas():
|
|
||||||
loader = Loader(d)
|
loader = Loader(d)
|
||||||
try:
|
try:
|
||||||
yield from loader.load()
|
yield from loader.load()
|
||||||
|
@ -198,14 +186,10 @@ def iter_entries() -> Iterator[Result]:
|
||||||
|
|
||||||
def get_entries() -> List[Result]:
|
def get_entries() -> List[Result]:
|
||||||
# sorting by first annotation is reasonable I guess???
|
# sorting by first annotation is reasonable I guess???
|
||||||
# TODO
|
|
||||||
return list(sort_res_by(iter_entries(), key=lambda e: e.created))
|
return list(sort_res_by(iter_entries(), key=lambda e: e.created))
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
logger = get_logger()
|
|
||||||
setup_logger(logger, level=logging.DEBUG)
|
|
||||||
|
|
||||||
for entry in iter_entries():
|
for entry in iter_entries():
|
||||||
logger.info('processed %s', entry.uid)
|
logger.info('processed %s', entry.uid)
|
||||||
try:
|
try:
|
||||||
|
@ -215,7 +199,3 @@ def main():
|
||||||
else:
|
else:
|
||||||
for i in ee.items:
|
for i in ee.items:
|
||||||
logger.info(i)
|
logger.info(i)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
|
||||||
main()
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue