list-books.json with Booktype 2.x
  • Hi,

    I'm testing Booktype master branch, and particularly how books can be imported from another frontpage application. FMfr and FMen currently use Booktype 1.6.1, and the books list can be retrieved with the list-books.json file (see https://fr.flossmanuals.net/list-books.json). We used it in the past with the old Publisher frontend, and we still use it now with our custom fm-site application to import the generated ePub, PDF and HTML files.
    Unfortunately, it seems that the feature no longer works with Booktype 2.x (and I find no clue in the code). Is there another way to get the list from an URL, or is it completely removed.

    Regards,
    --
    Nicolas
  • 14 Comments sorted by
  • Vote Up0Vote Down Daniel JamesDaniel James
    Posts: 844Member, Sourcefabric Team
    Hi Nicolas,

    In Booktype 2.x the API is far more advanced and is self-documenting.

    First, you need to authenticate, for a quick test you can log into https://demo.booktype.pro

    Once logged into the demo site:


    So after the upgrade you can do the same at https://fr.flossmanuals.net/_api

    Cheers!

    Daniel
  • Vote Up0Vote Down Daniel JamesDaniel James
    Posts: 844Member, Sourcefabric Team
  • I'm experimenting the new API with curl. Thanks to the API documentation I managed to retrieve an authentification token, but I can't find a way to pass that token to the following request (e.g. _api/v1/books/). I tried to use it in the header and in the GET parameters, but nothing seems to work and I constantly get {"detail":"Authentication credentials were not provided."}.

    Could you give a simple example? It's probably very easy, but I'm quite new to that kind of API and a bit lost.

    Thanks!
  • I just found out the Booktype API is based on Django Rest Framework, so it should be relatively easy to access it using API clients such as coreapi (see http://www.django-rest-framework.org/topics/api-clients/).
  • I tested all the options provided in the Django Rest Framework documentation, and unfortunately it still doesn't work with coreapi (and the coreapi CLI). Not being able to access the API from a python script is a blocker for us, so some help would be more than welcome.

    Thanks!
  • Hi Nicolas, 
    I will provide you step by step manual how to make a proper request later today.

    Best!
  • Hi Nicolas,

    To retrieve a token you should send a next request:
    curl -X POST \
      -H 'Cache-Control: no-cache' \
      -H 'content-type: multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW' \
      -F username=admin \
      -F password=admin

    To access a books data:
    curl -X GET \
      -H 'Authorization: Token 7b714b8af74c2191c1c5e898ca8267bc4af45fe9' \
      -H 'Cache-Control: no-cache'

    To use a token auth you need to set the booktype.api.middleware.AuthMiddleware 
    into your MIDDLEWARE_CLASSES and also set the booktype.api.auth.Backend in the AUTHENTICATION_BACKENDS setting.

    Best!





      
  • Thanks for your help. I didn't change the content of the server's settings, and thus didn't use the booktype api backend to authenticate. But unfortunately, it still doesn't work.

    In my settings/base.py, I now have:

    MIDDLEWARE_CLASSES = (
        'django.contrib.sessions.middleware.SessionMiddleware',
        'django.middleware.locale.LocaleMiddleware',
        'django.middleware.common.CommonMiddleware',
        'django.middleware.csrf.CsrfViewMiddleware',
        'django.contrib.auth.middleware.AuthenticationMiddleware',
        'django.contrib.messages.middleware.MessageMiddleware',
        'booktype.api.middleware.APILoggingMiddleware',
        'booktype.api.middleware.AuthMiddleware',
        'booktype.apps.core.middleware.StrictAuthentication',
        'booktype.apps.core.middleware.SecurityMiddleware',
    )

    AUTHENTICATION_BACKENDS = (
        'django.contrib.auth.backends.ModelBackend',
        'booktype.api.auth.Backend',
    )


    I can retrieve the token with:

    curl -X POST \
      https://test.flossmanualsfr.net/_api/v1/auth-token/ \
      -H 'Cache-Control: no-cache' \
      -H 'content-type: multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW' \
      -F username=<login> \
      -F password=<passwd>


    But the following command:

    curl -X GET \
      https://test.flossmanualsfr.net/_api/v1/books/ \
      -H 'Authorization: Token <token from the previous command>' \
      -H 'Cache-Control: no-cache'


    still returns {"detail":"Authentication credentials were not provided."}.
  • Also note that if I remove 'django.contrib.auth.backends.ModelBackend' I can't login a all (or retrieve a token) even from the web application.
  • and relying on the api backend fails with the following message: {"non_field_errors":["Unable to log in with provided credentials."]}.
  • No progress so far. I'm going to switch to a production profile in case there's something blocking in the dev one.
  • Not better with the production profile. Since there's no big difference with the dev profile, it's not a surprise.
    I've also tried to create a different user with specific rights, but it's still failing. I can get the token, but can't use it.
  • It's fixed!

    In case someone else has the same problem, the Apache WSGI module had to be properly configured to accept authentication (see http://www.django-rest-framework.org/api-guide/authentication/#apache-mod_wsgi-specific-configuration). For the record, I detected it was a configuration issue after testing (successfully) with the Django internal web server.

    Daniel, Oleg, thanks again for your help!
  • Vote Up0Vote Down Daniel JamesDaniel James
    Posts: 844Member, Sourcefabric Team
    Hi Nicolas,

    Thanks for the tip, I will add this to the user manual. We use Nginx for managed Booktype hosting so we had not run into this issue with Apache before.

    Cheers!

    Daniel