Coder Social home page Coder Social logo

lionheart / pinboard.py Goto Github PK

View Code? Open in Web Editor NEW
342.0 18.0 29.0 244 KB

A full-featured Python wrapper (and command-line utility) for the Pinboard API. Built by the makers of Pushpin for Pinboard.

License: Apache License 2.0

Python 95.00% Makefile 4.47% Dockerfile 0.53%
python pinboard

pinboard.py's Introduction

Version Versions

Pinboard.py is an easy-to-use and fully-functional Python wrapper and command-line utility for the Pinboard.in API.

Installation

Pinboard.py is available for download through the Python Package Index (PyPi). You can install it right away using pip or easy_install.

If you're using Python 3 or above:

pip install "pinboard>=2.0"

For Python 2.7:

pip install "pinboard>=1.0,<2.0"

Usage

To get started, you're going to need to get your Pinboard API token from the password page on the Pinboard website. Once you've got that, you're ready to go.

>>> import pinboard
>>> pb = pinboard.Pinboard('API_TOKEN')

Once you've done this, you can now use the pb object to make calls to the Pinboard API. Here are some examples:

Update

Returns the most recent time a bookmark was added, updated or deleted.

>>> pb.posts.update()
datetime.datetime(2014, 7, 27, 18, 11, 29)

Posts

Add a bookmark:

>>> pb.posts.add(url="http://google.com/", description="A Great Search Engine", \
        extended="This is a description!", tags=["search", "tools"], shared=True, \
        toread=False)
True

Update a bookmark:

# First, retrieve the bookmark you'd like to edit
>>> bookmark = pb.posts.get(url='http://google.com/')['posts'][0]
>>> bookmark
<Bookmark description="A Great Search Engine" url="google.com">

# You can now change description, extended, shared, toread, tags, or time directly with the bookmark object.
>>> bookmark.description = "Google is pretty awesome"
>>> bookmark.tags = ["search", "searching"]
>>> bookmark.save()
True

# If you want to update the bookmark creation date as well, you'll need to pass in `update_time=True` to the save method
>>> import datetime
>>> bookmark.time = datetime.datetime.now() - datetime.timedelta(days=5)
>>> bookmark.save(update_time=True)

Delete a bookmark:

>>> pb.posts.delete(url="http://google.com/")
True

Get one or more posts on a single day matching the parameters:

>>> pb.posts.get(url="http://google.com/")
{u'date': datetime.datetime(2014, 7, 25, 16, 35, 25),
 u'posts': [<Bookmark description="A Great Search Engine" url="google.com">],
 u'user': u'dlo'}

>>> import datetime
>>> pb.posts.get(dt=datetime.date.today())
{u'date': datetime.datetime(2014, 7, 25, 16, 35, 25),
 u'posts': [<Bookmark description="A Great Search Engine" url="google.com">,
  <Bookmark description="Smooth Scrolling | CSS-Tricks" url="css-tricks.com">,
  <Bookmark description="Apple "Frustrated" that "People Don't Want to Pay Anything" on Mobile, Says 'The Banner Saga' Developer | Touch Arcade" url="toucharcade.com">],
 u'user': u'dlo'}

Return all recent bookmarks (optionally filtering by tag):

>>> pb.posts.recent(tag=["programming", "python"])
{u'date': datetime.datetime(2014, 4, 28, 2, 7, 58),
 u'posts': [<Bookmark description="itunesfs 1.0.0.7 : Python Package Index" url="pypi.python.org">,
  <Bookmark description="mincss "Clears the junk out of your CSS" - Peterbe.com" url="www.peterbe.com">,
  <Bookmark description="Braintree Test Credit Card Account Numbers" url="www.braintreepayments.com">,
  <Bookmark description="Valued Lessons: Monads in Python (with nice syntax!)" url="www.valuedlessons.com">,
  <Bookmark description="Paste #EGY1XPQxQ2UPuT91SH83 at spacepaste" url="bpaste.net">,
  <Bookmark description="40 Random Letters and Numbers" url="gist.github.com">,
  <Bookmark description="PEP 3156 -- Asynchronous IO Support Rebooted" url="www.python.org">,
  <Bookmark description="Brython" url="www.brython.info">,
  <Bookmark description="Django REST framework" url="django-rest-framework.org">,
  <Bookmark description="mypy - A New Python Variant with Dynamic and Static Typing" url="www.mypy-lang.org">,
  <Bookmark description="Julython 2012" url="www.julython.org">,
  <Bookmark description="Stripe Blog: Exploring Python Using GDB" url="stripe.com">,
  <Bookmark description="Python FAQ: Descriptors - fuzzy notepad" url="me.veekun.com">,
  <Bookmark description="A Guide to Python's Magic Methods « rafekettler.com" url="www.rafekettler.com">,
  <Bookmark description="Melopy" url="prezjordan.github.com">,
  <Bookmark description="litl/rauth" url="github.com">],
 u'user': u'dlo'}

Return a list of dates with the number of posts at each date:

>>> pb.posts.dates(tag=["programming", "python"])
{u'dates': {datetime.date(2008, 12, 5): 1,
  datetime.date(2008, 12, 6): 1,
  ...
  datetime.date(2014, 7, 24): 6,
  datetime.date(2014, 7, 25): 4},
 u'tag': u'programming+python',
 u'user': u'dlo'}

Get all bookmarks in your account:

>>> pb.posts.all()
[<Bookmark description="Of Princesses and Dragons" url="medium.com">
 <Bookmark description="A Great Search Engine" url="google.com">,
 ...
 <Bookmark description="Runner Econ 101 - StimHa" url="stimhack.com">,
 <Bookmark description="서인국, 탄탄 근육+ 태평양 어깨…어부바 부른다 : 네이" url="news.naver.com">]

You can also filter by tag, start, results, fromdt, or todt.

>>> import datetime
>>> five_days_ago = datetime.datetime.now() - datetime.timedelta(days=5)
>>> pb.posts.all(tag=["programming"], start=10, results=100, fromdt=five_days_ago)
[<Bookmark description="Of Princesses and Dragons" url="medium.com">
 <Bookmark description="A Great Search Engine" url="google.com">,
 ...
 <Bookmark description="Runner Econ 101 - StimHa" url="stimhack.com">,
 <Bookmark description="서인국, 탄탄 근육+ 태평양 어깨…어부바 부른다 : 네이" url="news.naver.com">]

Tags

Suggest tags for a given URL:

>>> pb.posts.suggest(url="https://pinboard.in")
[{u'popular': [u'pinboard']},
 {u'recommended': [u'bookmark',
   u'bookmarks',
   u'\uc815\ubcf4\ud1b5\uc2e0',
   u'pinboard',
   u'Unread',
   u'webservice']}]

Return all tags in your account along with the number of times they were used:

>>> pb.tags.get()
[<Tag name="absurd" count=1>,
<Tag name="accessibility" count=2>,
<Tag name="accounting" count=3>,
<Tag name="zen" count=1>,
<Tag name="zsh" count=1>,
<Tag name="zynga" count=1>]

Delete a tag:

>>> pb.tags.delete(tag="zynga")
True

Rename a tag:

>>> pb.tags.rename(old='ppython', new='python')
True

Miscellaneous

By default, pinboard.py will return parsed JSON objects. If you'd like the raw response object for a request, just pass in parse_response=False.

>>> response = pb.tags.get(parse_response=False)
>>> response
<addinfourl at 4396047680 whose fp = <socket._fileobject object at 0x105f79850>>
>>> response.read()
... your tags ...

Pinboard.py maps one-to-one with the Pinboard API (e.g., pb.one.two.three() will send a request to "https://api.pinboard.in/v1/one/two/three"). For more information on other methods and usage, please refer to the Pinboard API documentation.

One more note--you might have noticed that there is no "title" attribute for bookmarks. I promise you, there's a good reason for this! This has been done since the Pinboard API calls titles "descriptions" and descriptions "extended" (which, interestingly, was done to stay consistent with the Delicious API, which the Pinboard API was modeled after). In order to keep things minimally confusing, this library sticks to how the Pinboard API names these fields. Just remember--"description" means "title" and "extended" means "description".

Command Line

In addition to providing full Python-level support for the Pinboard API, pinboard.py also comes bundled with a handy command-line utility called "pinboard". Just type "pinboard -h" for a full list of supported commands. Your API token needs to be available to pinboard.py, and can be entered in several ways. Firstly pinboard.py will try to read the ~/.pinboardrc configuration file. If not present then it will try to read an environment variable called PINBOARD_TOKEN. Lastly it will show a shell prompt for the user to enter their token (you can immediately force the latter behavior by typing pinboard login).

All of the commands pre-process and indent the JSON output. If you would like to shoot the raw response data to stdout, just pass "--raw" before the subcommand (e.g., "pinboard --raw bookmarks").

Examples:

$ pinboard login
Enter your Pinboard API token: username:XXXXX
Saved Pinboard credentials to ~/.pinboardrc
$ pinboard suggest-tags --url http://pymotw.com/2/argparse/
[
    {
        "popular": [
            "python"
        ]
    },
    {
        "recommended": [
            "python",
            "argument",
            "parsing"
        ]
    }
]
$ pinboard get --date 7-13-2014
{
    "date": "2014-07-13T03:03:58Z",
    "posts": [
        {
            "extended": "",
            "hash": "e2311835eb0de6bff2595a9b1525bb98",
            "description": "Python 2.7.x and Python 3.x key differences",
            "tags": "python",
            "href": "http://sebastianraschka.com/Articles/2014_python_2_3_key_diff.html",
            "meta": "561d1f53791a8c50109393411f0301fc",
            "time": "2014-07-13T03:03:58Z",
            "shared": "yes",
            "toread": "no"
        },
        {
            "extended": "",
            "hash": "4abe28f70154bd35f84be73cec0c53ef",
            "description": "Miami, the great world city, is drowning while the powers that be look away | World news | The Observer",
            "tags": "",
            "href": "http://www.theguardian.com/world/2014/jul/11/miami-drowning-climate-change-deniers-sea-levels-rising",
            "meta": "2ca547789553ba9d3202a5cd3d367685",
            "time": "2014-07-13T02:53:54Z",
            "shared": "yes",
            "toread": "yes"
        }
    ],
    "user": "dlo"
}
$ pinboard --raw get --date 7/13/2014
{"date":"2014-07-13T03:03:58Z","user":"dlo","posts":[{"href":"http:\/\/sebastianraschka.com\/Articles\/2014_python_2_3_key_diff.html","description":"Python 2.7.x and Python 3.x key differences","extended":"","meta":"561d1f53791a8c50109393411f0301fc","hash":"e2311835eb0de6bff2595a9b1525bb98","time":"2014-07-13T03:03:58Z","shared":"yes","toread":"no","tags":"python"},{"href":"http:\/\/www.theguardian.com\/world\/2014\/jul\/11\/miami-drowning-climate-change-deniers-sea-levels-rising","description":"Miami, the great world city, is drowning while the powers that be look away | World news | The Observer","extended":"","meta":"2ca547789553ba9d3202a5cd3d367685","hash":"4abe28f70154bd35f84be73cec0c53ef","time":"2014-07-13T02:53:54Z","shared":"yes","toread":"yes","tags":""}]}

You can print a full list of pinboard commands by passing the "-h" flag.

$ pinboard -h
usage: pinboard [-h] [--raw]

                {login,last-update,add,delete,get,recent,dates,bookmarks,suggest-tags,tags,delete-tag,rename-tag,notes,note,rss-key,api-token}
                ...

positional arguments:
  {login,last-update,add,delete,get,recent,dates,bookmarks,suggest-tags,tags,delete-tag,rename-tag,notes,note,rss-key,api-token}
    add                 posts/add
    delete              posts/delete
    get                 posts/get
    recent              posts/recent
    dates               posts/dates
    bookmarks           posts/all
    suggest-tags        posts/suggest
    tags                tags/get
    delete-tag          tags/delete
    rename-tag          tags/rename
    notes               notes/list
    note                notes/ID
    rss-key             user/secret
    api-token           user/api_token

optional arguments:
  -h, --help            show this help message and exit
  --raw                 Print the raw data from the Pinboard API without any
                        formatting.

...or help for a specific subcommand by passing the subcommand and then the "-h" flag.

$ pinboard bookmarks -h
usage: pinboard bookmarks [-h] [--from_date FROM_DATE] [--to_date TO_DATE]
                          [--tags TAGS [TAGS ...]] [--count COUNT]
                          [--offset OFFSET]

optional arguments:
  -h, --help            show this help message and exit
  --from_date FROM_DATE
  --to_date TO_DATE
  --tags TAGS [TAGS ...]
  --count COUNT
  --offset OFFSET

Using the CLI in Docker

To build the CLI in Docker:

$ cd <path_to_pinboard>/bin
$ docker build -t pinboard .

To run the CLI in Docker after building:

$ export PINBOARD_TOKEN=<your_pinboard_token>
$ docker run -ti -e PINBOARD_TOKEN pinboard bookmarks --count 10

Support

If you like this library, you might want to check out Pushpin for Pinboard.

License License

Apache License, Version 2.0. See LICENSE for details.

pinboard.py's People

Contributors

dhellmann avatar dlo avatar forestofthings avatar haron avatar johnharris85 avatar mpslanker avatar polm avatar ssssam avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

pinboard.py's Issues

AttributeError: 'dict' object has no attribute 'iteritems'

$ pinboard tags
Tag               Count 
Traceback (most recent call last):
  File "/usr/bin/pinboard", line 358, in <module>
    handler.run()
  File "/usr/bin/pinboard", line 280, in run
    command_map[self.namespace.subparser]()
  File "/usr/bin/pinboard", line 189, in _tags_action
    self._call_api_and_catch_exceptions(self.pinboard.tags.get, handler)
  File "/usr/bin/pinboard", line 88, in _call_api_and_catch_exceptions
    value = handler(json_response)
  File "/usr/bin/pinboard", line 186, in handler
    for tag, count in response.iteritems():
AttributeError: 'dict' object has no attribute 'iteritems'

Arch Linux, Python 3.6.4, pinboard.py 2.1.2

Time zones on datetime objects

I noticed that the datetime object on posts from posts.recent are naive, unaware of the timezone. I believe all Pinboard API responses are in UTC. It'd be nice to label them as such in the API so that simple code post post.time.timestamp() works. For now my workaround is to just add timezone info myself like this: dt.replace(tzinfo=datetime.timezone.utc).timestamp()

I believe the relevant code is around pinboard.py:115.

More info on how to add a timezone here. Better to add it when creating the object though, not using .replace() to add it later. Note that the timezone.utc object was added in Python 3.2; IIRC there were some simple hacks for Python 2.7 that would work for UTC dates.

Thanks for continuing to maintain this API!

DeprecationWarning

On line 45:

/usr/local/bin/pinboard:45: DeprecationWarning: This method will be removed in future versions.  Use 'parser.read_file()' instead.

TypeError: the JSON object must be str, not 'HTTPResponse' in pinboard.py

I am having an error when using any pinboard.posts functions. This issue happens with pinboard>=2 (tested with 2.0.3 and 2.1.4). This issue does not happen with pinboard<2 and python2.

The traceback is always the following:

[2018-06-11 15:07:47,131] ERROR in app: Exception on / [GET]
Traceback (most recent call last):
  File "venv/lib/python3.5/site-packages/flask/app.py", line 2292, in wsgi_app
    response = self.full_dispatch_request()
  File "venv/lib/python3.5/site-packages/flask/app.py", line 1815, in full_dispatch_request
    rv = self.handle_user_exception(e)
  File "venv/lib/python3.5/site-packages/flask/app.py", line 1718, in handle_user_exception
    reraise(exc_type, exc_value, tb)
  File "venv/lib/python3.5/site-packages/flask/_compat.py", line 35, in reraise
    raise value
  File "venv/lib/python3.5/site-packages/flask/app.py", line 1813, in full_dispatch_request
    rv = self.dispatch_request()
  File "venv/lib/python3.5/site-packages/flask/app.py", line 1799, in dispatch_request
    return self.view_functions[rule.endpoint](**req.view_args)
  File "app.py", line 13, in hello_world
    print(pb.posts.get(tag="wishlist"))
  File "venv/lib/python3.5/site-packages/pinboard/pinboard.py", line 198, in __call__
    json_response = json.load(response)
  File "/usr/lib/python3.5/json/__init__.py", line 268, in load
    parse_constant=parse_constant, object_pairs_hook=object_pairs_hook, **kw)
  File "/usr/lib/python3.5/json/__init__.py", line 312, in loads
    s.__class__.__name__))
TypeError: the JSON object must be str, not 'bytes'

From what I could read at StackOverflow, the issue may involve urllib and bytes encoding.

I've solved this problem in a venv by replacing:

json_response = json.load(response)

with:

decoded_reponse = response.read().decode('utf-8')
json_response = json.loads(decoded_reponse)

Another solution could be to use a more recent HTTP module.

Issue with pinboard?

Hello,
I am working with old code written by a hard to reach author. It appears to use pinboard and I am running into an error.

#Main.py
import miepy
from pinboard import pinboard
import numpy as np
import matplotlib.pyplot as plt
from tqdm import tqdm

#pb = pinboard.Pinboard('1ECA92EB875F599D22B5')

job = pinboard()
nm = 1e-9

diameter = 160*nm
material = miepy.constant_material(index=4.1)

theta = np.linspace(0, np.pi,30)
phi = np.linspace(0, 2*np.pi,30)

wavelengths = np.linspace(300*nm, 900*nm, 300)

sources = dict(linear=miepy.sources.plane_wave([1,0]),
               radial=miepy.sources.radial_beam(power=1, width=600*nm))
        

@job.cache
def sim(source, index): `


Originally the code had this without the comment, I added that when I tried to make a pinboard account to get an api token. when I run the code it errors on the job=pinboard() step with the error: "'module' object is not callable".  Later in the code it uses this job variable before a few functions like this:
`@job.cache
def integrate(source, index):
    label = f'{source}_n{index}'
    var = job.load(sim, label)

    P = np.zeros([3, len(wavelengths)], dtype=complex)
    T = np.zeros([3, len(wavelengths)], dtype=complex)
    for i, wavelength in enumerate(tqdm(wavelengths)):
        J = -1j*(4**2 - index**2)*var.E[i]
        r = np.array(miepy.coordinates.sph_to_cart(var.RAD[i], var.THETA[i], var.PHI[i]))
        k_med = 2*np.pi*index/wavelength

        P_shell = np.zeros([3, len(theta)], dtype=complex)
        T_shell = np.zeros([3, len(theta)], dtype=complex)
        for k in range(len(theta)):`

As well as the job.load(sim,label). 
It also does @job.at_end right before the final function where it graphs the final product. 
At the very end of the code it runs this loop which also uses the job variable:
`for source in ['linear', 'radial']:
    for index in [1, 1.5]:
        label = f'{source}_n{index}'
        job.add_instance(sim, label, source=source, index=index)
        job.add_instance(integrate, label, source=source, index=index)

job.execute()

Do you have any insight into this error and how pinboard is used in this way?

Python3: TypeError: the JSON object must be str, not 'bytes'

Anybody run into this one? Must be environmental but dependencies appear to be up to date. I am running 2.1.8:

$ python3
Python 3.5.2 (default, Sep 14 2017, 22:51:06)
[GCC 5.4.0 20160609] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> api_token = 'XXXX:YYYYYYYYYYYYYYYYYYYY'
>>> import pinboard
>>> pb = pinboard.Pinboard(api_token)
>>> print (pb)
<pinboard.pinboard.Pinboard object at 0x7f8a2330d198>
>>> pb.posts.update()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.5/dist-packages/pinboard/pinboard.py", line 196, in __call__
    json_response = json.load(response)
  File "/usr/lib/python3.5/json/__init__.py", line 268, in load
    parse_constant=parse_constant, object_pairs_hook=object_pairs_hook, **kw)
  File "/usr/lib/python3.5/json/__init__.py", line 312, in loads
    s.__class__.__name__))
TypeError: the JSON object must be str, not 'bytes'
>>>

Thanks!

bin/pinboard broken for python3

There seems to be some problems when using the command line interface when installed in python3.
The first encountered was using raw_input instead of input when doing pinboard login.

Just wanted to see if you were aware of this, and if you're open to a pull request, before getting too deep into it.

Unicode encode error

There appear to be some issues dealing with non-ASCII characters coming back from the Pinboard API. When I do a pinboard tags on the command line using my account I get the following error:

Traceback (most recent call last):
  File "/usr/local/bin/pinboard", line 358, in <module>
    handler.run()
  File "/usr/local/bin/pinboard", line 280, in run
    command_map[self.namespace.subparser]()
  File "/usr/local/bin/pinboard", line 189, in _tags_action
    self._call_api_and_catch_exceptions(self.pinboard.tags.get, handler)
  File "/usr/local/bin/pinboard", line 88, in _call_api_and_catch_exceptions
    value = handler(json_response)
  File "/usr/local/bin/pinboard", line 187, in handler
    print row_format.format(tag, count)
UnicodeEncodeError: 'ascii' codec can't encode character u'\xe1' in position 3: ordinal not in range(128)

I believe it is failing on this tag name:

<tag count="3" tag="Bahá'í" />

OR in tag search

Hi,

Is there a way to create a retrieve a set of bookmarks matching TAG1 or TAG2?

It'd be great to have this feature.

Thanks.

Bug - Destructively silently overwrites bookmarks data

Using the simple pb.posts.add(...) method listed in the readme to add a bookmark silently overwrites (loses) existing bookmark data already in Pinboard.

This is highly unintuitive behavior vs raising an exception or including something like an explicit allow_overwrite=True flag.

This client's silently overwriting data caused me to lose data on a bunch of existing bookmarks :(.

Release?

Would it be possible to have a new release of this on PyPI? It looks like the last release was in 2018, and there have been several improvements since then.

Still maintained?

Hi,

I'd like to know if this project is already maintained.

Thanks 👍

Pinboard.tags.get() breaks if tag key is "date" as it matches DATE_FIELDS

This is probably very similar to issue #19.

However, just as it says in the title. If you have tag keys that match on any of the field lists, it breaks.
For example, if you have a tag of "date" then at line 199 the tag count is passed to Pinboard.datetime_from_string().
This results in an error as a string, in the form of a date, was expect and not an int.

Utf-8

Excellent module -- thanks!

I ran into an exception in Python 3. File pinboard.py line 166

value = map(lambda k: k.decode("utf8"), kwargs[field])

Had to remove


.decode("utf8")

for it to run.

URLs returned by this library aren't the URLs of the bookmarks

Hey folks,

I feel like I might be missing something here, but it seems like all of the URL attributes returned by this library only consist of the domain name, not the actual URL of the bookmark.

This is shown in the examples in the readme, too; like this snippet:

<Bookmark description="40 Random Letters and Numbers" url="gist.github.com">,

Using parse_response=false shows the full URL as I'd expect.

installation fails on Windows

Output when trying to install on Windows (Python 3.6):

(venv) C:\Dev\scrapetube>pip install "pinboard>=2.0"
Collecting pinboard>=2.0
  Using cached pinboard-2.1.0.tar.gz
    Complete output from command python setup.py egg_info:
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "C:\Users\GIACOM~1.LAC\AppData\Local\Temp\pip-build-kq3vnhn0\pinboard\setup.py", line 30, in <module>
        long_description = file.read()
      File "c:\dev\scrapetube\venv\lib\encodings\cp1252.py", line 23, in decode
        return codecs.charmap_decode(input,self.errors,decoding_table)[0]
    UnicodeDecodeError: 'charmap' codec can't decode byte 0x9d in position 5829: character maps to <undefined>

    ----------------------------------------
Command "python setup.py egg_info" failed with error code 1 in C:\Users\GIACOM~1.LAC\AppData\Local\Temp\pip-build-kq3vnhn0\pinboard\

Python version: 3.6.4 (v3.6.4:d48eceb, Dec 19 2017, 06:54:40) [MSC v.1900 64 bit (AMD64)] on win32

"bad interpreter" when running CLI

Looks like the shebang line on the script is hard-coded to somebody's local environment:

$ python3 -m pip install pinboard==2.1.6

$ pinboard -h
bash: /usr/local/bin/pinboard: /Users/dan/Projects/pinboard.py/venv/bin/python3: bad interpreter: No such file or directory

$ head -n1 /usr/local/bin/pinboard
#!/Users/dan/Projects/pinboard.py/venv/bin/python3

It works in 2.1.4:

$ python3 -m pip install pinboard==2.1.4

$ pinboard -h
usage: pinboard [-h] [--raw]
...

$ head -n1 /usr/local/bin/pinboard
#!/usr/local/opt/python/bin/python3.6

It's broken in 2.1.5, but nothing jumps out to me when I compare that tag with 2.1.4.

I don't know enough (yet) about how package distributions are built to offer a fix.

tags.get() fails with ValueError: time data '3' does not match format '%Y-%m-%d %H:%M:%S'

import pinboard
pb=pinboard.Pinboard(APIKEY)
pb.tags.get() 
/usr/lib/python3.7/_strptime.py in _strptime(data_string, format)
    357     if not found:
    358         raise ValueError("time data %r does not match format %r" %
--> 359                          (data_string, format))
    360     if len(data_string) != found.end():
    361         raise ValueError("unconverted data remains: %s" %
ValueError: time data '3' does not match format '%Y-%m-%d %H:%M:%S'

Add ONLY from URL

I need a workflow where I can quickly add URLs just from their HREFs.

However, pinboard.py fails if no title is given.

Can there be another script or option or whatever that will retrieve the URL and get the title and pass it in, so that only one command will add the URL? I understand this will take retrieval time, but it saves a lot of human effort.

DeprecationWarning

Running the CLI command from pinboard-2.1.8 results in the following warning:

/usr/local/bin/pinboard:45: DeprecationWarning: This method will be removed in future versions.  Use 'parser.read_file()' instead.
  config.readfp(f)

update_time does not seem to update time

I am trying to update the time of posts following the documentation, but the interface shows no change in time.
For example, iterating over some rows row:

dt_obj = datetime.datetime.strptime(row['dt'], "%Y-%m-%d %H:%M:%S %Z")

bookmark = pb.posts.get(url = row['url'])['posts'][0]
print(bookmark, bookmark.time) # -> shows 2020-07-15 19:00:50

bookmark.time = dt_obj
print(bookmark.time) # -> shows 2016-09-19 03:44:42

bookmark.save(update_time=True)

But the website still says created 15min ago. Thank you for any pointers and for making the wrapper.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.