فهرست منبع

fix(docs): update confirmation code security considerations

Peter Thomassen 5 سال پیش
والد
کامیت
49e3a65ae7
1فایلهای تغییر یافته به همراه31 افزوده شده و 27 حذف شده
  1. 31 27
      docs/authentication.rst

+ 31 - 27
docs/authentication.rst

@@ -9,7 +9,7 @@ users only. Users can register an account free of charge through the API as
 described below.
 described below.
 
 
 Obtain a Captcha
 Obtain a Captcha
-```````````````````
+````````````````
 
 
 Before registering a user account, you need to solve a captcha. You will have
 Before registering a user account, you need to solve a captcha. You will have
 to send the captcha ID and solution along with your registration request. To
 to send the captcha ID and solution along with your registration request. To
@@ -303,35 +303,39 @@ Confirmation Codes
     user's email address. Although clients generally should consider these
     user's email address. Although clients generally should consider these
     codes opaque, we would like to give some insights into how they work.
     codes opaque, we would like to give some insights into how they work.
 
 
-    The code is a base64-encoded JSON representation of the user's intent.
-    The representation carries a timestamp of when the intent was expressed,
-    the user ID, and also any extra parameters that were submitted along with
-    the intent. An example of such a parameter is the new email address in the
-    context of a `change email address`_ operation. Parameters that are
-    unknown at the time when the code is generated are not included in the
-    code and must be provided via ``POST`` request payload when using the
-    code. A typical example of this is the new password in a `password reset`_
+    The code is a base64-encoded encrypted-then-signed JSON representation of
+    the user's intent. Encryption/decryption and authentication (sign/verify)
+    is handled by `pyca/cryptography's Fernet implementation
+    <https://cryptography.io/en/latest/fernet/>`_ which is uses AES-CBC and
+    HMAC-SHA256 with specifically derived key material. The HMAC also signs the
+    current time (i.e. when the intent was expressed). During verification,
+    codes are checked for freshness and rejected when older than allowed.
+
+    The encoded intent is composed of the user ID and any extra parameters that
+    were submitted along with the intent. An example of such a parameter is the
+    new email address in the context of a `change email address`_ operation.
+    Parameters that are unknown at code generation time are not included in the
+    code and must be provided via ``POST`` request payload when using the code.
+    A typical example of this is the new password in a `password reset`_
     operation, as it is only provided when the code is being used (and not at
     operation, as it is only provided when the code is being used (and not at
     the time when the code is requested).
     the time when the code is requested).
 
 
-    To ensure integrity, we also include a message authentication code (MAC)
-    using `Django's signature implementation
-    <https://docs.djangoproject.com/en/2.2/_modules/django/core/signing/#Signer>`_.
-    When a confirmation code is used, we recompute the MAC based on the data
-    incorporated in the code, and only perform the requested action if the MAC
-    is reproduced identically. Codes are also checked for freshness using the
-    timestamp, and rejected if older than allowed.
-
-    In order to prevent race conditions, we add additional data to the MAC
-    input such that codes are only valid as long as the user state is not
-    modified (e.g. by performing another sensitive account operation). This is
-    achieved by mixing a) the account operation type (e.g. password reset), b)
-    the account's activation status, c) the account's current email address,
-    and d) the user's password hash into the MAC input. If any of these
-    parameters happens to change before a code is applied, the MAC will be
+    In order to prevent race conditions, we augment the code with additional
+    data which we use to invalidate codes when the user state is modified (e.g.
+    by performing another sensitive account operation). This is achieved by
+    including the combined hash of a) the account operation type (e.g. password
+    reset), b) the account's activation status, c) the account's current email
+    address, and d) the user's password hash. When a confirmation code is used,
+    we recompute this hash based on the user's current state, and only perform
+    the requested action if the hash is reproduced identically. If any of these
+    parameters happens to change before a code is applied, the code will be
     rendered invalid, and the operation will fail. This measure blocks
     rendered invalid, and the operation will fail. This measure blocks
     scenarios such as using an old email address change code after a more
     scenarios such as using an old email address change code after a more
-    recent password change.
+    recent password change. (Note that it is sometimes possible to revert the
+    state so that an old code becomes valid again, such as when you change the
+    email address twice, with the second change undoing the first one. This
+    issue does not occur for password changes; those do permanently invalidate
+    other codes.)
 
 
     This approach allows us to securely authenticate sensitive user operations
     This approach allows us to securely authenticate sensitive user operations
     without keeping a list of requested operations on the server. This is both
     without keeping a list of requested operations on the server. This is both
@@ -450,8 +454,8 @@ Note that, for now, all tokens have equal power -- every token can authorize
 any action. We are planning to implement scoped tokens in the future.
 any action. We are planning to implement scoped tokens in the future.
 
 
 
 
-Token Security Considerations
-`````````````````````````````
+Security Considerations
+```````````````````````
 
 
 This section is for information only. Token length and encoding may change in
 This section is for information only. Token length and encoding may change in
 the future.
 the future.