Skip to content
This repository has been archived by the owner on Apr 26, 2024. It is now read-only.

Commit

Permalink
Merge branch 'dinsic' into babolivier/dinsic-message-retention
Browse files Browse the repository at this point in the history
  • Loading branch information
babolivier committed Aug 28, 2019
2 parents 7071459 + 62f5e3b commit e5df12a
Show file tree
Hide file tree
Showing 14 changed files with 344 additions and 44 deletions.
1 change: 1 addition & 0 deletions changelog.d/5760.feature
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Force the access rule to be "restricted" if the join rule is "public".
1 change: 1 addition & 0 deletions changelog.d/5780.misc
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Allow looping calls to be given arguments.
1 change: 1 addition & 0 deletions changelog.d/5807.feature
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Allow defining HTML templates to serve the user on account renewal attempt when using the account validity feature.
10 changes: 10 additions & 0 deletions docs/sample_config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -860,6 +860,16 @@ uploads_path: "DATADIR/uploads"
# period: 6w
# renew_at: 1w
# renew_email_subject: "Renew your %(app)s account"
# # Directory in which Synapse will try to find the HTML files to serve to the
# # user when trying to renew an account. Optional, defaults to
# # synapse/res/templates.
# template_dir: "res/templates"
# # HTML to be displayed to the user after they successfully renewed their
# # account. Optional.
# account_renewed_html_path: "account_renewed.html"
# # HTML to be displayed when the user tries to renew an account with an invalid
# # renewal token. Optional.
# invalid_token_html_path: "invalid_token.html"

# The user must provide all of the below types of 3PID when registering.
#
Expand Down
45 changes: 43 additions & 2 deletions synapse/config/registration.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,11 @@
# See the License for the specific language governing permissions and
# limitations under the License.

import os
from distutils.util import strtobool

import pkg_resources

from synapse.config._base import Config, ConfigError
from synapse.types import RoomAlias
from synapse.util.stringutils import random_string_with_symbols
Expand All @@ -41,8 +44,36 @@ def __init__(self, config, synapse_config):

self.startup_job_max_delta = self.period * 10. / 100.

if self.renew_by_email_enabled and "public_baseurl" not in synapse_config:
raise ConfigError("Can't send renewal emails without 'public_baseurl'")
if self.renew_by_email_enabled:
if "public_baseurl" not in synapse_config:
raise ConfigError("Can't send renewal emails without 'public_baseurl'")

template_dir = config.get("template_dir")

if not template_dir:
template_dir = pkg_resources.resource_filename("synapse", "res/templates")

if "account_renewed_html_path" in config:
file_path = os.path.join(template_dir, config["account_renewed_html_path"])

self.account_renewed_html_content = self.read_file(
file_path, "account_validity.account_renewed_html_path"
)
else:
self.account_renewed_html_content = (
"<html><body>Your account has been successfully renewed.</body><html>"
)

if "invalid_token_html_path" in config:
file_path = os.path.join(template_dir, config["invalid_token_html_path"])

self.invalid_token_html_content = self.read_file(
file_path, "account_validity.invalid_token_html_path"
)
else:
self.invalid_token_html_content = (
"<html><body>Invalid renewal token.</body><html>"
)


class RegistrationConfig(Config):
Expand Down Expand Up @@ -161,6 +192,16 @@ def default_config(self, generate_secrets=False, **kwargs):
# period: 6w
# renew_at: 1w
# renew_email_subject: "Renew your %%(app)s account"
# # Directory in which Synapse will try to find the HTML files to serve to the
# # user when trying to renew an account. Optional, defaults to
# # synapse/res/templates.
# template_dir: "res/templates"
# # HTML to be displayed to the user after they successfully renewed their
# # account. Optional.
# account_renewed_html_path: "account_renewed.html"
# # HTML to be displayed when the user tries to renew an account with an invalid
# # renewal token. Optional.
# invalid_token_html_path: "invalid_token.html"
# The user must provide all of the below types of 3PID when registering.
#
Expand Down
10 changes: 9 additions & 1 deletion synapse/handlers/account_validity.py
Original file line number Diff line number Diff line change
Expand Up @@ -223,11 +223,19 @@ def renew_account(self, renewal_token):
Args:
renewal_token (str): Token sent with the renewal request.
Returns:
bool: Whether the provided token is valid.
"""
user_id = yield self.store.get_user_from_renewal_token(renewal_token)
try:
user_id = yield self.store.get_user_from_renewal_token(renewal_token)
except StoreError:
defer.returnValue(False)

logger.debug("Renewing an account for user %s", user_id)
yield self.renew_account_for_user(user_id)

defer.returnValue(True)

@defer.inlineCallbacks
def renew_account_for_user(self, user_id, expiration_ts=None, email_sent=False):
"""Renews the account attached to a given user by pushing back the
Expand Down
1 change: 1 addition & 0 deletions synapse/res/templates/account_renewed.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<html><body>Your account has been successfully renewed.</body><html>
1 change: 1 addition & 0 deletions synapse/res/templates/invalid_token.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<html><body>Invalid renewal token.</body><html>
21 changes: 15 additions & 6 deletions synapse/rest/client/v2_alpha/account_validity.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,21 +40,30 @@ def __init__(self, hs):
self.hs = hs
self.account_activity_handler = hs.get_account_validity_handler()
self.auth = hs.get_auth()
self.success_html = hs.config.account_validity.account_renewed_html_content
self.failure_html = hs.config.account_validity.invalid_token_html_content

@defer.inlineCallbacks
def on_GET(self, request):
if b"token" not in request.args:
raise SynapseError(400, "Missing renewal token")
renewal_token = request.args[b"token"][0]

yield self.account_activity_handler.renew_account(renewal_token.decode('utf8'))
token_valid = yield self.account_activity_handler.renew_account(
renewal_token.decode("utf8")
)

request.setResponseCode(200)
if token_valid:
status_code = 200
response = self.success_html
else:
status_code = 404
response = self.failure_html

request.setResponseCode(status_code)
request.setHeader(b"Content-Type", b"text/html; charset=utf-8")
request.setHeader(b"Content-Length", b"%d" % (
len(AccountValidityRenewServlet.SUCCESS_HTML),
))
request.write(AccountValidityRenewServlet.SUCCESS_HTML)
request.setHeader(b"Content-Length", b"%d" % (len(response),))
request.write(response.encode("utf8"))
finish_request(request)
defer.returnValue(None)

Expand Down
49 changes: 32 additions & 17 deletions synapse/storage/events_worker.py
Original file line number Diff line number Diff line change
Expand Up @@ -255,6 +255,26 @@ def get_events_as_list(
# didn't have the redacted event at the time, so we recheck on read
# instead.
if not allow_rejected and entry.event.type == EventTypes.Redaction:
orig_event_info = yield self._simple_select_one(
table="events",
keyvalues={"event_id": entry.event.redacts},
retcols=["sender", "room_id", "type"],
allow_none=True,
)

if not orig_event_info:
# We don't have the event that is being redacted, so we
# assume that the event isn't authorized for now. (If we
# later receive the event, then we will always redact
# it anyway, since we have this redaction)
continue

if orig_event_info["room_id"] != entry.event.room_id:
# Don't process redactions if the redacted event doesn't belong to the
# redaction's room.
logger.info("Ignoring redation in another room.")
continue

if entry.event.internal_metadata.need_to_check_redaction():
# XXX: we need to avoid calling get_event here.
#
Expand All @@ -277,27 +297,13 @@ def get_events_as_list(
# 2. have _get_event_from_row just call the first half of
# that

orig_sender = yield self._simple_select_one_onecol(
table="events",
keyvalues={"event_id": entry.event.redacts},
retcol="sender",
allow_none=True,
)

expected_domain = get_domain_from_id(entry.event.sender)
if (
orig_sender
and get_domain_from_id(orig_sender) == expected_domain
get_domain_from_id(orig_event_info["sender"]) == expected_domain
):
# This redaction event is allowed. Mark as not needing a
# recheck.
entry.event.internal_metadata.recheck_redaction = False
else:
# We don't have the event that is being redacted, so we
# assume that the event isn't authorized for now. (If we
# later receive the event, then we will always redact
# it anyway, since we have this redaction)
continue

if allow_rejected or not entry.event.rejected_reason:
if check_redacted and entry.redacted_event:
Expand Down Expand Up @@ -532,7 +538,7 @@ def _get_event_from_row(
)

redacted_event = None
if redacted:
if redacted and original_ev.type != EventTypes.Redaction:
redacted_event = prune_event(original_ev)

redaction_id = yield self._simple_select_one_onecol(
Expand Down Expand Up @@ -564,9 +570,18 @@ def _get_event_from_row(
# recheck.
because.internal_metadata.recheck_redaction = False
else:
# Senders don't match, so the event isn't actually redacted
# Senders don't match, so the event isn't actually
# redacted
redacted_event = None

if because.room_id != original_ev.room_id:
redacted_event = None
else:
# The lack of a redaction likely means that the redaction is invalid
# and therefore not returned by get_event, so it should be safe to
# just ignore it here.
redacted_event = None

cache_entry = _EventCacheEntry(
event=original_ev, redacted_event=redacted_event
)
Expand Down
Loading

0 comments on commit e5df12a

Please sign in to comment.