django-pfx 1.2.dev105__tar.gz → 1.2.dev110__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (122) hide show
  1. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/.gitlab-ci.yml +37 -1
  2. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/PKG-INFO +6 -8
  3. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/README.md +1 -4
  4. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/django_pfx.egg-info/PKG-INFO +6 -8
  5. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/django_pfx.egg-info/requires.txt +1 -1
  6. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/index.rst +1 -7
  7. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/decorator.md +18 -6
  8. django-pfx-1.2.dev110/doc/source/getting_started.md +179 -0
  9. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/internationalisation.md +1 -1
  10. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/model.md +21 -13
  11. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/pfx_views.md +49 -21
  12. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/testing.md +40 -13
  13. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/authentication_views.py +3 -1
  14. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/setup.cfg +5 -4
  15. django-pfx-1.2.dev105/doc/source/getting_started.md +0 -81
  16. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/.gitignore +0 -0
  17. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/.pre-commit-config.yaml +0 -0
  18. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/LICENSE +0 -0
  19. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/MANIFEST.in +0 -0
  20. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/django_pfx.egg-info/SOURCES.txt +0 -0
  21. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/django_pfx.egg-info/dependency_links.txt +0 -0
  22. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/django_pfx.egg-info/top_level.txt +0 -0
  23. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/Makefile +0 -0
  24. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/conf.py +0 -0
  25. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/api.views.rst +0 -0
  26. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/authentication.md +0 -0
  27. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/doc/source/cookbook.md +0 -0
  28. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/img/pfx.png +0 -0
  29. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/img/pfx.svg +0 -0
  30. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/__init__.py +0 -0
  31. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/__init__.py +0 -0
  32. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/apidoc/__init__.py +0 -0
  33. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/apidoc/parameters.py +0 -0
  34. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/apidoc/schema.py +0 -0
  35. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/apidoc/tags.py +0 -0
  36. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/apps.py +0 -0
  37. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/decorator/__init__.py +0 -0
  38. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/decorator/rest.py +0 -0
  39. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/default_settings.py +0 -0
  40. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/exceptions.py +0 -0
  41. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/fields.py +0 -0
  42. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/http/__init__.py +0 -0
  43. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/http/json_response.py +0 -0
  44. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/locale/fr/LC_MESSAGES/django.mo +0 -0
  45. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/locale/fr/LC_MESSAGES/django.po +0 -0
  46. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/management/__init__.py +0 -0
  47. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/management/commands/__init__.py +0 -0
  48. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/management/commands/makeapidoc.py +0 -0
  49. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/middleware/__init__.py +0 -0
  50. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/middleware/authentication.py +0 -0
  51. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/middleware/locale.py +0 -0
  52. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/models/__init__.py +0 -0
  53. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/models/cache_mixins.py +0 -0
  54. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/models/not_null_fields.py +0 -0
  55. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/models/pfx_models.py +0 -0
  56. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/models/user_filtered_queryset_mixin.py +0 -0
  57. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/serializers/__init__.py +0 -0
  58. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/serializers/json.py +0 -0
  59. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/settings.py +0 -0
  60. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/shortcuts.py +0 -0
  61. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/storage/__init__.py +0 -0
  62. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/storage/s3_storage.py +0 -0
  63. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/templates/registration/password_reset_email.txt +0 -0
  64. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/templates/registration/password_reset_subject.txt +0 -0
  65. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/templates/registration/welcome_email.txt +0 -0
  66. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/templates/registration/welcome_subject.txt +0 -0
  67. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/test.py +0 -0
  68. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/urls.py +0 -0
  69. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/__init__.py +0 -0
  70. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/fields.py +0 -0
  71. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/filters_views.py +0 -0
  72. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/locale_views.py +0 -0
  73. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/__init__.py +0 -0
  74. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/date_format.py +0 -0
  75. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/groups.py +0 -0
  76. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/list_count.py +0 -0
  77. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/list_items.py +0 -0
  78. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/list_mode.py +0 -0
  79. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/list_order.py +0 -0
  80. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/list_search.py +0 -0
  81. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/media_redirect.py +0 -0
  82. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/meta_fields.py +0 -0
  83. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/meta_filters.py +0 -0
  84. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/meta_orders.py +0 -0
  85. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset.py +0 -0
  86. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset_limit.py +0 -0
  87. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset_offset.py +0 -0
  88. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset_page.py +0 -0
  89. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset_page_size.py +0 -0
  90. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/parameters/subset_page_subset.py +0 -0
  91. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pfx/pfxcore/views/rest_views.py +0 -0
  92. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/pyproject.toml +0 -0
  93. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/requirements.txt +0 -0
  94. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/runtest.py +0 -0
  95. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/setup.py +0 -0
  96. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/__init__.py +0 -0
  97. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/models.py +0 -0
  98. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/__init__.py +0 -0
  99. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/ci.py +0 -0
  100. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/common.py +0 -0
  101. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/dev.py +0 -0
  102. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/dev_custom_example.py +0 -0
  103. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/settings/dev_default.py +0 -0
  104. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/__init__.py +0 -0
  105. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/basic_api_errors.py +0 -0
  106. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/basic_api_test.py +0 -0
  107. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_api_doc.py +0 -0
  108. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_auth_api.py +0 -0
  109. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_cache.py +0 -0
  110. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_fields.py +0 -0
  111. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_filters.py +0 -0
  112. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_locale_api.py +0 -0
  113. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_perm_tests.py +0 -0
  114. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_perms_api.py +0 -0
  115. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_shortcuts.py +0 -0
  116. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_timezone_middleware.py +0 -0
  117. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_tools.py +0 -0
  118. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_user_queryset.py +0 -0
  119. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_view_decorators.py +0 -0
  120. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/tests/test_view_fields.py +0 -0
  121. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/urls.py +0 -0
  122. {django-pfx-1.2.dev105 → django-pfx-1.2.dev110}/tests/views.py +0 -0
@@ -8,7 +8,7 @@ variables:
8
8
 
9
9
  cache:
10
10
  paths:
11
- - ~/.cache/pip/
11
+ - .cache/pip/
12
12
 
13
13
  before_script:
14
14
  - python -V # Print out python version for debugging
@@ -20,6 +20,7 @@ before_script:
20
20
 
21
21
  stages:
22
22
  - test
23
+ - build
23
24
  - package
24
25
 
25
26
  test:
@@ -34,9 +35,13 @@ test:
34
35
  - coverage run --source='.' runtest.py
35
36
  - coverage report
36
37
  - coverage xml
38
+ - coverage html
37
39
  coverage: '/TOTAL.*\s([.\d]+)%/'
38
40
  artifacts:
39
41
  when: always
42
+ paths:
43
+ - htmlcov/**
44
+ expire_in: 7 day
40
45
  reports:
41
46
  junit: testreport.xml
42
47
  coverage_report:
@@ -48,6 +53,37 @@ test:
48
53
  - DJANGO_VERSION: 'Django>=3.2,<4.0'
49
54
  - DJANGO_VERSION: 'Django>=4.0,<5.0'
50
55
  - DJANGO_VERSION: 'Django>=4.2.*' # LTS
56
+
57
+ build doc:
58
+ stage: build
59
+ needs: []
60
+ interruptible: true
61
+ script:
62
+ - cd doc
63
+ - make html
64
+ artifacts:
65
+ when: always
66
+ paths:
67
+ - doc/_build/**
68
+ expire_in: 7 day
69
+
70
+ pages:
71
+ stage: package
72
+ needs:
73
+ - job: build doc
74
+ artifacts: true
75
+ - job: test
76
+ artifacts: true
77
+ script:
78
+ - mkdir public
79
+ - mv doc/_build/html public/doc
80
+ - mv htmlcov public/coverage
81
+ artifacts:
82
+ paths:
83
+ - public
84
+ only:
85
+ - master
86
+
51
87
  package:
52
88
  only:
53
89
  refs:
@@ -1,12 +1,13 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: django-pfx
3
- Version: 1.2.dev105
4
- Summary: Django PFX is a toolkit to build web APIs dedicated to be used by React progressive web app.
3
+ Version: 1.2.dev110
4
+ Summary: Django PFX is a toolkit to build rest APIs with the Django framework.
5
5
  Author: Hervé Martinet
6
6
  Author-email: herve.martinet@gmail.com
7
7
  License: BSD-3-Clause
8
- Project-URL: Source, https://gitlab.com/hmartinet/django-pfx
9
- Project-URL: Tracker, https://gitlab.com/hmartinet/django-pfx/-/issues
8
+ Project-URL: Source, https://gitlab.com/pfx4/django-pfx
9
+ Project-URL: Tracker, https://gitlab.com/pfx4/django-pfx/-/issues
10
+ Project-URL: Documentation, https://pfx4.gitlab.io/django-pfx/doc/
10
11
  Classifier: Environment :: Web Environment
11
12
  Classifier: Framework :: Django
12
13
  Classifier: Framework :: Django :: 3.2
@@ -31,11 +32,8 @@ License-File: LICENSE
31
32
 
32
33
  ![logo]
33
34
 
34
- Django PFX is a toolkit to build web APIs dedicated to be used by React progressive web app.
35
+ Django PFX is a toolkit to build rest APIs with the Django framework.
35
36
 
36
- > **WARNING**
37
- >
38
- > This is an experimental projet. It should not be used in real project because it is incomplete and there is no warranty of keeping compatibility in future version.
39
37
 
40
38
  [logo]: https://gitlab.com/hmartinet/django-pfx/-/raw/master/img/pfx.png "PFX"
41
39
  [pipeline]: https://gitlab.com/hmartinet/django-pfx/badges/master/pipeline.svg "Pipeline Status"
@@ -5,11 +5,8 @@
5
5
 
6
6
  ![logo]
7
7
 
8
- Django PFX is a toolkit to build web APIs dedicated to be used by React progressive web app.
8
+ Django PFX is a toolkit to build rest APIs with the Django framework.
9
9
 
10
- > **WARNING**
11
- >
12
- > This is an experimental projet. It should not be used in real project because it is incomplete and there is no warranty of keeping compatibility in future version.
13
10
 
14
11
  [logo]: https://gitlab.com/hmartinet/django-pfx/-/raw/master/img/pfx.png "PFX"
15
12
  [pipeline]: https://gitlab.com/hmartinet/django-pfx/badges/master/pipeline.svg "Pipeline Status"
@@ -1,12 +1,13 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: django-pfx
3
- Version: 1.2.dev105
4
- Summary: Django PFX is a toolkit to build web APIs dedicated to be used by React progressive web app.
3
+ Version: 1.2.dev110
4
+ Summary: Django PFX is a toolkit to build rest APIs with the Django framework.
5
5
  Author: Hervé Martinet
6
6
  Author-email: herve.martinet@gmail.com
7
7
  License: BSD-3-Clause
8
- Project-URL: Source, https://gitlab.com/hmartinet/django-pfx
9
- Project-URL: Tracker, https://gitlab.com/hmartinet/django-pfx/-/issues
8
+ Project-URL: Source, https://gitlab.com/pfx4/django-pfx
9
+ Project-URL: Tracker, https://gitlab.com/pfx4/django-pfx/-/issues
10
+ Project-URL: Documentation, https://pfx4.gitlab.io/django-pfx/doc/
10
11
  Classifier: Environment :: Web Environment
11
12
  Classifier: Framework :: Django
12
13
  Classifier: Framework :: Django :: 3.2
@@ -31,11 +32,8 @@ License-File: LICENSE
31
32
 
32
33
  ![logo]
33
34
 
34
- Django PFX is a toolkit to build web APIs dedicated to be used by React progressive web app.
35
+ Django PFX is a toolkit to build rest APIs with the Django framework.
35
36
 
36
- > **WARNING**
37
- >
38
- > This is an experimental projet. It should not be used in real project because it is incomplete and there is no warranty of keeping compatibility in future version.
39
37
 
40
38
  [logo]: https://gitlab.com/hmartinet/django-pfx/-/raw/master/img/pfx.png "PFX"
41
39
  [pipeline]: https://gitlab.com/hmartinet/django-pfx/badges/master/pipeline.svg "Pipeline Status"
@@ -1,4 +1,4 @@
1
- django<4.0,>=3.2
1
+ django<5.0,>=3.2
2
2
  django-cors-headers
3
3
  django_json_widget
4
4
  pyjwt>=2.1
@@ -6,13 +6,7 @@
6
6
  Welcome to Django PFX's documentation!
7
7
  ======================================
8
8
 
9
- Django PFX is a toolkit to build web APIs dedicated
10
- to be used by React progressive web app.
11
-
12
- .. warning::
13
- This is a project in development.
14
- It should not be used in real project because it is incomplete
15
- and changes may break the compatibility in future version.
9
+ Django PFX is a toolkit to build rest APIs with the Django framework.
16
10
 
17
11
 
18
12
  Topics
@@ -1,7 +1,9 @@
1
1
  # View decorator and URL
2
2
  ## @rest_view
3
3
  Used to provide the base path of a view class
4
- ```
4
+ ```python
5
+ from pfx.pfxcore.decorator import rest_view
6
+
5
7
  @rest_view("/base-path")
6
8
  class ViewClass():
7
9
  ```
@@ -9,13 +11,18 @@ class ViewClass():
9
11
  ## @rest_api
10
12
  Used to annotate the rest services method.
11
13
  Parameters are the path and the HTTP method.
12
- ```
14
+ ```python
15
+ from pfx.pfxcore.decorator import rest_api
16
+
13
17
  @rest_api("/path", method="get")
14
18
  def class_method(self):
15
19
  ```
16
20
 
17
21
  A short example
18
- ```
22
+ ```python
23
+ from pfx.pfxcore.decorator import rest_view, rest_api
24
+ from pfx.pfxcore.http import JsonResponse
25
+
19
26
  @rest_view("/books")
20
27
  class BookRestView():
21
28
 
@@ -27,7 +34,9 @@ class BookRestView():
27
34
 
28
35
  ### path parameters
29
36
  Path can contain parameters that are passed to the method.
30
- ```
37
+ ```python
38
+ from pfx.pfxcore.decorator import rest_api
39
+
31
40
  @rest_api("/path/<int:pk>/test/<slug:slug>", method="get")
32
41
  def class_method(self, pk, slug):
33
42
  ```
@@ -35,7 +44,8 @@ def class_method(self, pk, slug):
35
44
  ## Registering urls
36
45
  To be available, annotated view class must be registered
37
46
  in your urls.py file as follows.
38
- ```
47
+
48
+ ```python
39
49
  from pfx.pfxcore import register_views
40
50
 
41
51
  from . import views
@@ -44,9 +54,11 @@ urlpatterns = register_views(
44
54
  views.AuthorRestView,
45
55
  views.BookRestView)
46
56
  ```
57
+
47
58
  You can include multiple views under one path, or add a path
48
59
  wih a specific class method for each HTTP methods:
49
- ```
60
+ ```python
61
+ from django.urls import include, path
50
62
  from pfx.pfxcore import register_views
51
63
 
52
64
  from . import views
@@ -0,0 +1,179 @@
1
+ # Getting Started with PFX
2
+
3
+ ## Install django pfx
4
+
5
+ Using pip
6
+ ```bash
7
+ pip install django-pfx
8
+ ```
9
+
10
+ ## Configuration
11
+
12
+ Add pfxcore to the installed app
13
+
14
+ ```python
15
+ INSTALLED_APPS = [
16
+ 'pfx.pfxcore',
17
+ ]
18
+ ```
19
+
20
+ ## Create your services
21
+
22
+ ### Model class
23
+ Create a simple model class.
24
+ ```python
25
+ from django.db import models
26
+
27
+
28
+ class Book(models.Model):
29
+ BOOK_TYPES = [
30
+ ('science_fiction', 'Science Fiction'),
31
+ ('heroic_fantasy', 'Heroic Fantasy'),
32
+ ('detective', 'Detective')]
33
+
34
+ title = models.CharField("Title", max_length=30)
35
+ author = models.CharField("Author", max_length=150)
36
+ type = models.CharField("Type", max_length=20, choices=BOOK_TYPES)
37
+ pub_date = models.DateField("Pub Date")
38
+ created_at = models.DateField("Created at", auto_now_add=True)
39
+
40
+ class Meta:
41
+ verbose_name = "Book"
42
+ verbose_name_plural = "Books"
43
+
44
+ def __str__(self):
45
+ return f"{self.name}"
46
+
47
+ ```
48
+
49
+ ### Views
50
+ Create a new view
51
+ ```python
52
+ from pfx.pfxcore.decorator import rest_view
53
+ from pfx.pfxcore.views import RestView
54
+
55
+ from book.models import Book
56
+
57
+
58
+ @rest_view("/books")
59
+ class BookRestView(RestView):
60
+ default_public = True
61
+ queryset = Book.objects
62
+ fields = ['title', 'author', 'type', 'pub_date', 'created_at']
63
+ ```
64
+
65
+ ### URLs
66
+ Register the url in urls.py.
67
+ ```python
68
+ from django.urls import path, include
69
+ from pfx.pfxcore import register_views
70
+
71
+
72
+ from book import views
73
+
74
+ apipatterns = register_views(views.BookRestView)
75
+
76
+ urlpatterns = [
77
+ path('api/', include(apipatterns)),
78
+ ]
79
+ ```
80
+
81
+ You now have a fully functional public API for the book objet.
82
+
83
+ ### Test the API
84
+ The next step is to create a test class to test your new API.
85
+ PFX provides [some tools](testing.md) to ease the testing.
86
+
87
+ ```python
88
+ from datetime import date
89
+ from django.test import TransactionTestCase
90
+ from pfx.pfxcore.test import TestAssertMixin, APIClient
91
+
92
+ from book.models import Book, Author
93
+
94
+ class BookTestClass(TestAssertMixin, TransactionTestCase):
95
+
96
+ @classmethod
97
+ def setUpTestData(cls):
98
+ # create some test data
99
+ cls.author = Author.objects.create(
100
+ first_name='Isaac',
101
+ last_name='Asimov')
102
+ cls.book1 = Book.objects.create(
103
+ author=cls.author,
104
+ title="The Caves of Steel",
105
+ type='science_fiction',
106
+ pub_date=date(1954, 1, 1))
107
+ cls.book2 = Book.objects.create(
108
+ author=cls.author,
109
+ title="The Naked Sun",
110
+ type='science_fiction',
111
+ pub_date=date(1957, 1, 1))
112
+
113
+ def test_get_book_list(self):
114
+ client = APIClient()
115
+ response = client.get('/api/books')
116
+
117
+ # assert response status is 200 OK
118
+ self.assertRC(response, 200)
119
+ # assert number of item returned
120
+ self.assertSize(response, 'items', 2)
121
+ # test the author of the second item is Asimov
122
+ self.assertJE(response, 'items.@1.author.pk', self.author.pk)
123
+
124
+ def test_get_book(self):
125
+ client = APIClient()
126
+ response = client.get(f'/api/books/{self.book2.pk}')
127
+
128
+ # assert response status is 200 OK
129
+ self.assertRC(response, 200)
130
+ # assert json content of the response
131
+ self.assertJE(response, 'title', "The Naked Sun")
132
+ self.assertJE(response, 'pub_date', "1957-01-01")
133
+
134
+ def test_create_book(self):
135
+ client = APIClient()
136
+ response = client.post(
137
+ '/api/books/',dict(
138
+ title="The Robots of Dawn",
139
+ author=self.author,
140
+ type='science_fiction',
141
+ pub_date=date(1983, 1, 1)
142
+ ))
143
+ self.assertRC(response, 200)
144
+ self.assertJE(response, 'title', "The Robots of Dawn")
145
+
146
+ def test_create_book_validation(self):
147
+ client = APIClient()
148
+ # make a post request
149
+ response = client.post(
150
+ '/api/books/',dict(
151
+ title=None,
152
+ author=self.author,
153
+ type='science_fiction',
154
+ pub_date=date(1983, 1, 1)
155
+ ))
156
+ self.assertRC(response, 422)
157
+ self.assertJE(
158
+ response, 'title.@0', "This field cannot be null.")
159
+
160
+ def test_update_book(self):
161
+ client = APIClient()
162
+ response = client.put(
163
+ f'/api/books/{self.book2.pk}',dict(
164
+ title="The Robots of Dawn",
165
+ pub_date=date(1983, 1, 1),
166
+ ))
167
+ self.assertRC(response, 200)
168
+ self.assertJE(response, 'title', "The Robots of Dawn")
169
+
170
+ def test_delete_book(self):
171
+ client = APIClient()
172
+ response = client.delete(
173
+ f'/api/books/{self.book2.pk}')
174
+ self.assertRC(response, 200)
175
+
176
+ books = Book.objects.filter(pk=self.book2.pk)
177
+ self.assertEqual(books.count(), 0)
178
+
179
+ ```
@@ -12,7 +12,7 @@ In Django, `USE_I18N` must be `True` to use internationalization. Use `LANGUAGE_
12
12
  You can optionally set `USE_L10N` to `True` (see Django documentation).
13
13
 
14
14
  In Addition, you can set the list of available languages for web services with `LANGUAGES`:
15
- ```
15
+ ```python
16
16
  LANGUAGES = [
17
17
  ('fr', "French"),
18
18
  ('en', "English"),
@@ -5,15 +5,19 @@ Django PFX use plain Django Models classes.
5
5
  This library only provides some helpers for properties
6
6
  and foreign keys representations.
7
7
 
8
- ## `@rest_property`
8
+ ## @rest_property
9
9
  If you want to use properties in your model,
10
- you have to annotate them with @rest_property.
10
+ you have to annotate them with `@rest_property`.
11
11
 
12
12
  Rest property takes 2 parameters, a name and
13
13
  the type of the Field (CharField, IntegerField, etc.)
14
14
 
15
15
  Rest properties can be listed as fields to be returned in list and detail views.
16
- ```
16
+
17
+ ```python
18
+ from django.db import models
19
+ from pfx.pfxcore.decorator import rest_property
20
+
17
21
  class Book(models.Model):
18
22
  name = models.CharField("Name", max_length=30)
19
23
  author = models.ForeignKey(
@@ -35,12 +39,11 @@ class Book(models.Model):
35
39
  ```
36
40
 
37
41
  ## JSONReprMixin
38
-
39
- Foreign keys are returned by {doc}`Django PFX views <pfx_views>` as a JSON
42
+ Foreign keys are returned by [Django PFX views <pfx_views>](./pfx_views.md) as a JSON
40
43
  structure with two fields : pk, resource_name
41
44
 
42
45
  For instance for the book class, with the author foreign key :
43
- ```
46
+ ```python
44
47
  {
45
48
  "author": {
46
49
  "pk": 1,
@@ -60,8 +63,11 @@ by inheriting JSONReprMixin on the Model class and
60
63
  by overriding the json_repr method.
61
64
 
62
65
  For instance for the Author class :
63
- ```
64
- class Author(models.Model):
66
+ ```python
67
+ from django.db import models
68
+ from pfx.pfxcore.models import JSONReprMixin
69
+
70
+ class Author(JSONReprMixin, models.Model):
65
71
  first_name = models.CharField("First Name", max_length=30)
66
72
  last_name = models.CharField("Last Name", max_length=30)
67
73
  slug = models.SlugField("Slug", unique=True)
@@ -80,11 +86,11 @@ class Author(models.Model):
80
86
  ```
81
87
 
82
88
  Which give the following result on the book service :
83
- ```
89
+ ```python
84
90
  {
85
91
  "author": {
86
92
  "pk": 1,
87
- "resource_name": "John Ronald Reuel Tolkien"
93
+ "resource_name": "John Ronald Reuel Tolkien",
88
94
  "resource_slug": "john-ronald-reuel-tolkien"
89
95
  },
90
96
  "created_at": "2022-01-14",
@@ -104,9 +110,11 @@ converting `null` values to empty strings, you can use the following model field
104
110
  * `NotNullCharField`
105
111
  * `NotNullTextField`
106
112
  * `NotNullURLField`
107
- ```
108
- a_string_field = NotNullCharField(
109
- _("A string"), max_length=255, blank=True, default="")
113
+ ```python
114
+ from pfx.pfxcore.models import NotNullCharField
115
+
116
+ a_string_field = NotNullCharField(
117
+ "A string", max_length=255, blank=True, default="")
110
118
  ```
111
119
 
112
120
  The `null` parameter of these fields is automatically set to `False`.