*: add pyright type checking
This commit is contained in:
parent
80d90b91e8
commit
813dd2894f
|
@ -52,6 +52,13 @@ jobs:
|
|||
run: sudo pip install -U wheel pipenv && pipenv install --dev
|
||||
- name: Lint with bandit
|
||||
run: pipenv run bandit -r passbook
|
||||
pyright:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v1
|
||||
- uses: actions/setup-node@v1
|
||||
- name: Run pyright
|
||||
run: pyright
|
||||
# Actual CI tests
|
||||
migrations:
|
||||
needs:
|
||||
|
|
|
@ -66,7 +66,9 @@ class EventAction(Enum):
|
|||
@staticmethod
|
||||
def as_choices():
|
||||
"""Generate choices of actions used for database"""
|
||||
return tuple((x, y.value) for x, y in EventAction.__members__.items())
|
||||
return tuple(
|
||||
(x, y.value) for x, y in getattr(EventAction, "__members__").items()
|
||||
)
|
||||
|
||||
|
||||
class Event(UUIDModel):
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
"""passbook expression policy evaluator"""
|
||||
import re
|
||||
from typing import TYPE_CHECKING, Any, Dict
|
||||
from typing import TYPE_CHECKING, Any, Dict, Optional
|
||||
|
||||
from django.core.exceptions import ValidationError
|
||||
from jinja2 import Undefined
|
||||
|
@ -72,7 +72,7 @@ class Evaluator:
|
|||
except TemplateSyntaxError as exc:
|
||||
return PolicyResult(False, str(exc))
|
||||
try:
|
||||
result = expression.render(
|
||||
result: Optional[Any] = expression.render(
|
||||
request=request, **self._get_expression_context(request)
|
||||
)
|
||||
if isinstance(result, Undefined):
|
||||
|
|
|
@ -1,8 +1,11 @@
|
|||
"""passbook OAuth2 Views"""
|
||||
from typing import Optional
|
||||
from urllib.parse import urlencode
|
||||
|
||||
from django.contrib import messages
|
||||
from django.contrib.auth.mixins import LoginRequiredMixin
|
||||
from django.forms import Form
|
||||
from django.http import HttpRequest, HttpResponse
|
||||
from django.shortcuts import get_object_or_404, redirect, reverse
|
||||
from django.utils.translation import ugettext as _
|
||||
from oauth2_provider.views.base import AuthorizationView
|
||||
|
@ -36,7 +39,7 @@ class OAuthPermissionDenied(PermissionDeniedView):
|
|||
class PassbookAuthorizationView(AccessMixin, AuthorizationView):
|
||||
"""Custom OAuth2 Authorization View which checks policies, etc"""
|
||||
|
||||
_application = None
|
||||
_application: Optional[Application] = None
|
||||
|
||||
def _inject_response_type(self):
|
||||
"""Inject response_type into querystring if not set"""
|
||||
|
@ -47,7 +50,7 @@ class PassbookAuthorizationView(AccessMixin, AuthorizationView):
|
|||
reverse("passbook_providers_oauth:oauth2-ok-authorize") + "?" + querystring
|
||||
)
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
def dispatch(self, request: HttpRequest, *args, **kwargs) -> HttpResponse:
|
||||
"""Update OAuth2Provider's skip_authorization state"""
|
||||
# Get client_id to get provider, so we can update skip_authorization field
|
||||
client_id = request.GET.get("client_id")
|
||||
|
@ -69,12 +72,12 @@ class PassbookAuthorizationView(AccessMixin, AuthorizationView):
|
|||
# Some clients don't pass response_type, so we default to code
|
||||
if "response_type" not in request.GET:
|
||||
return self._inject_response_type()
|
||||
actual_response = super().dispatch(request, *args, **kwargs)
|
||||
actual_response = AuthorizationView.dispatch(self, request, *args, **kwargs)
|
||||
if actual_response.status_code == 400:
|
||||
LOGGER.debug(request.GET.get("redirect_uri"))
|
||||
LOGGER.debug("Bad request", redirect_uri=request.GET.get("redirect_uri"))
|
||||
return actual_response
|
||||
|
||||
def form_valid(self, form):
|
||||
def form_valid(self, form: Form):
|
||||
# User has clicked on "Authorize"
|
||||
Event.new(
|
||||
EventAction.AUTHORIZE_APPLICATION, authorized_application=self._application,
|
||||
|
@ -84,4 +87,4 @@ class PassbookAuthorizationView(AccessMixin, AuthorizationView):
|
|||
user=self.request.user,
|
||||
application=self._application,
|
||||
)
|
||||
return super().form_valid(form)
|
||||
return AuthorizationView.form_valid(self, form)
|
||||
|
|
|
@ -100,7 +100,7 @@ class SAMLProvider(Provider):
|
|||
self._meta.get_field("processor_path").choices = get_provider_choices()
|
||||
|
||||
@property
|
||||
def processor(self) -> Processor:
|
||||
def processor(self) -> Optional[Processor]:
|
||||
"""Return selected processor as instance"""
|
||||
if not self._processor:
|
||||
try:
|
||||
|
@ -163,4 +163,6 @@ class SAMLPropertyMapping(PropertyMapping):
|
|||
|
||||
def get_provider_choices():
|
||||
"""Return tuple of class_path, class name of all providers."""
|
||||
return [(class_to_path(x), x.__name__) for x in Processor.__subclasses__()]
|
||||
return [
|
||||
(class_to_path(x), x.__name__) for x in Processor.__dict__["__subclasses__"]()
|
||||
]
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
#!/bin/bash -xe
|
||||
isort -rc passbook
|
||||
pyright
|
||||
black passbook
|
||||
scripts/coverage.sh
|
||||
bandit -r passbook
|
||||
|
|
Reference in New Issue