Reputation: 25
I have a page with bookmarks and I want to implement several types of sorting for them. The user chooses the type of sorting and it's stored in the database. He/she sees the chosen type of sorting as the default value for the select-menu.
I wrote this:
class BookmarksSortingForm(forms.Form):
SORTING_CHOICES = [(1, "новым"),
(2, "имени"),
(3, "звёздам -"),
(4, "звёздам +")]
bm_sorting = forms.ChoiceField(SORTING_CHOICES)
# https://stackoverflow.com/questions/6325681/passing-a-user-request-to-forms
# In your view: form = MyForm(..., request=request)
def __init__(self, *args, **kwargs):
self.request = kwargs.pop("request", None)
super().__init__(*args, **kwargs)
self.fields['bm_sorting'].initial = BookmarksSortingForm.SORTING_CHOICES[self.get_current_sorting() - 1][1]
def get_current_sorting(self):
user = User.objects.get(username=self.request.user)
return user.profile.bookmarks_sorting # small integer, default = 1
But I get "TypeError: init() takes 1 positional argument but 2 were given" at the line with bm_sorting. How could I fix this? Django version is 3.2.4.
Upd: Traceback
Traceback (most recent call last):
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/core/handlers/exception.py", line 47, in inner
response = get_response(request)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/utils/deprecation.py", line 116, in __call__
response = self.process_request(request)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/middleware/common.py", line 53, in process_request
if self.should_redirect_with_slash(request):
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/middleware/common.py", line 70, in should_redirect_with_slash
if not is_valid_path(request.path_info, urlconf):
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/base.py", line 153, in is_valid_path
return resolve(path, urlconf)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/base.py", line 24, in resolve
return get_resolver(urlconf).resolve(path)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/resolvers.py", line 556, in resolve
for pattern in self.url_patterns:
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/utils/functional.py", line 48, in __get__
res = instance.__dict__[self.name] = self.func(instance)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/resolvers.py", line 598, in url_patterns
patterns = getattr(self.urlconf_module, "urlpatterns", self.urlconf_module)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/utils/functional.py", line 48, in __get__
res = instance.__dict__[self.name] = self.func(instance)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/resolvers.py", line 591, in urlconf_module
return import_module(self.urlconf_name)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/importlib/__init__.py", line 127, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
File "<frozen importlib._bootstrap>", line 1014, in _gcd_import
<source code not available>
File "<frozen importlib._bootstrap>", line 991, in _find_and_load
<source code not available>
File "<frozen importlib._bootstrap>", line 975, in _find_and_load_unlocked
<source code not available>
File "<frozen importlib._bootstrap>", line 671, in _load_unlocked
<source code not available>
File "<frozen importlib._bootstrap_external>", line 783, in exec_module
<source code not available>
File "<frozen importlib._bootstrap>", line 219, in _call_with_frames_removed
<source code not available>
File "/home/gamecoach/Seearo/Seearo/urls.py", line 23, in <module>
re_path('account/?', include('account.urls')),
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/site-packages/django/urls/conf.py", line 34, in include
urlconf_module = import_module(urlconf_module)
File "/home/gamecoach/.virtualenvs/django3/lib/python3.8/importlib/__init__.py", line 127, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
File "<frozen importlib._bootstrap>", line 1014, in _gcd_import
<source code not available>
File "<frozen importlib._bootstrap>", line 991, in _find_and_load
<source code not available>
File "<frozen importlib._bootstrap>", line 975, in _find_and_load_unlocked
<source code not available>
File "<frozen importlib._bootstrap>", line 671, in _load_unlocked
<source code not available>
File "<frozen importlib._bootstrap_external>", line 783, in exec_module
<source code not available>
File "<frozen importlib._bootstrap>", line 219, in _call_with_frames_removed
<source code not available>
File "/home/gamecoach/Seearo/account/urls.py", line 2, in <module>
from account.views import AccountView, AchievementsView, AddToBookmarksView, \
File "/home/gamecoach/Seearo/account/views.py", line 8, in <module>
from account.forms import SettingsForm, UploadPhotoForm
File "/home/gamecoach/Seearo/account/forms.py", line 6, in <module>
class BookmarksSortingForm(forms.Form):
File "/home/gamecoach/Seearo/account/forms.py", line 13, in BookmarksSortingForm
bm_sorting = forms.ChoiceField(SORTING_CHOICES)
Exception Type: TypeError at /account/bookmarks.html
Exception Value: __init__() takes 1 positional argument but 2 were given
Upd2: The answer below helped:
bm_sorting = forms.ChoiceField(choices=SORTING_CHOICES)
and I also had to change a bit this line:
self.fields['bm_sorting'].initial = BookmarksSortingForm.SORTING_CHOICES[self.get_current_sorting() - 1]
and it started to show my form.
Upvotes: 0
Views: 39
Reputation: 4034
You must pass a keyword argument instead of positional to the forms.ChoiceField
.
bm_sorting = forms.ChoiceField(choices=SORTING_CHOICES)
Here is how the ChoiceField
is defined in Django. Notice the *
after self
- this denotes that only keyword arguments will be accepted.
class ChoiceField(Field):
def __init__(self, *, choices=(), **kwargs):
super().__init__(**kwargs)
self.choices = choices
Upvotes: 1