Best Python code snippet using lemoncheesecake
loader.py
Source:loader.py
1from __future__ import annotations2import importlib.resources3from dataclasses import asdict4from pathlib import Path5from typing import Any, Dict6import jsonschema7import yaml8from .paramfield import ParamField9from .paramschema import ParamSchema10from .paramschemaparser import parse as parse_param_schema11from .types import ModuleSpec12__all__ = [13 "load_spec",14 "load_spec_file",15]16MODULE_ALLOWED_SECRETS = {17 "googlesheets": ["google"], # OAuth2: generate temporary access token18 "intercom": ["intercom"], # OAuth2: pass user's long-lasting access token19 "twitter": ["twitter"], # OAuth1: give module consumer_key+consumer_secret20}21"""Mapping from module slug to OAUTH_SERVICES key mangling `fetch(secrets=...)`."""22_spec_yaml = importlib.resources.read_text(__package__, "schema.yaml")23_spec_validator = jsonschema.Draft7Validator(24 yaml.safe_load(_spec_yaml), format_checker=jsonschema.FormatChecker()25)26def _validate_secret_param(module_id_name, param) -> None:27 """Raise ValueError rather than leak global secrets to an untrusted module.28 SECURITY: this is ... a hack. First, let's describe The Vision; then Reality.29 The Vision: each module ought to have its own security tokens. There should30 not be an OAUTH_SERVICES global variable. A sysadmin should register an app31 with Twitter/Google/whatever at module-installation time. When we have that,32 we can delete MODULE_ALLOWED_SECRETS.33 Reality: [2019-10-16] today isn't the revamp day. Consumer secrets are34 global; and in the case of OAuth1.0a (Twitter), the module can read those35 secrets. If a new module, "eviltwitter," comes along with a36 "twitter_credentials" parameter, the module author will gain Workbench's37 Twitter credentials -- and the user's credentials, too.38 From the user's perspective:39 1. Add "twitter" step40 2. Sign in; grant (global-variable) Workbench access to Twitter stuff41 3. Add "eviltwitter" module42 4. Sign in again?43 Results (The Vision): step 4 prompts the user to trust "eviltwitter".44 Results (SECURITY disaster): step 4 re-uses the grant from step 2.45 Results (alternate SECURITY disaster): step 4 prompts the user, NOT46 mentioning "eviltwitter != twitter".47 Results (Reality, 2019-10-16): "eviltwitter" does not validate because it48 isn't in MODULE_ALLOWED_SECRETS. Not fun,49 but not a security disaster.50 """51 allowed_secrets = MODULE_ALLOWED_SECRETS.get(module_id_name, [])52 if param["secret_logic"]["provider"] == "string":53 return54 if param["secret_logic"]["service"] in allowed_secrets:55 return56 else:57 raise ValueError(58 "Denied access to global %r secrets" % param["secret_logic"]["service"]59 )60def _validate_spec_dict(spec: Dict[str, Any]) -> None:61 """Raise ValueError if the spec is invalid.62 "Valid" means:63 * `spec` adheres to jsonschema `schema.yaml`64 * `spec.parameters[*].id_name` are unique65 * Only whitelisted secrets are allowed (ref: cjworkbench/settings.py)66 * `spec.parameters[*].visible_if[*].id_name` are valid67 * If `spec.parameters[*].options` and `default` exist, `default` is valid68 * `spec.parameters[*].visible_if[*].value` is/are valid if it's a menu69 * `spec.parameters[*].tab_parameter` point to valid params70 * `spec.parameters[*].secret` is correct71 """72 # No need to do i18n on these errors: they're only for admins. Good thing,73 # too -- most of the error messages come from jsonschema, and there are74 # _plenty_ of potential messages there.75 messages = []76 for err in _spec_validator.iter_errors(spec):77 messages.append(err.message)78 if messages:79 # Don't bother validating the rest. The rest of this method assumes80 # the schema is valid.81 raise ValueError("; ".join(messages))82 param_lookup = {}83 for param in spec["parameters"]:84 id_name = param["id_name"]85 if id_name in param_lookup:86 messages.append(f"Param '{id_name}' appears twice")87 else:88 param_lookup[id_name] = param89 # check 'default' is valid in menu/radio90 for param in spec["parameters"]:91 if "default" in param and "options" in param:92 options = [93 o["value"] for o in param["options"] if isinstance(o, dict)94 ] # skip 'separator'95 if param["default"] not in options:96 messages.append(97 f"Param '{param['id_name']}' has a 'default' that is not "98 "in its 'options'"99 )100 # Check that secrets are in global whitelist.101 #102 # This is to prevent malicious modules from stealing our global secrets.103 # A better approach would be to nix global secrets altogether and configure104 # OAuth per-module. So far we've been too lazy to do this.105 for param in spec["parameters"]:106 if param["type"] == "secret":107 _validate_secret_param(spec["id_name"], param)108 # Now that check visible_if refs109 for param in spec["parameters"]:110 try:111 visible_if = param["visible_if"]112 except KeyError:113 continue114 try:115 ref_param = param_lookup[visible_if["id_name"]]116 except KeyError:117 messages.append(118 f"Param '{param['id_name']}' has visible_if "119 f"id_name '{visible_if['id_name']}', which does not exist"120 )121 continue122 if "options" in ref_param and not isinstance(visible_if["value"], list):123 messages.append(124 f"Param '{param['id_name']}' needs its visible_if.value "125 f"to be an Array of Strings, since '{visible_if['id_name']}' "126 "has options."127 )128 if "options" in ref_param:129 if_values = visible_if["value"]130 if isinstance(if_values, list):131 if_values = set(if_values)132 else:133 if_values = set(if_values.split("|"))134 options = set(135 o["value"] for o in ref_param["options"] if isinstance(o, dict)136 ) # skip 'separator'137 missing = if_values - options138 if missing:139 messages.append(140 f"Param '{param['id_name']}' has visible_if values "141 f"{repr(missing)} not in '{ref_param['id_name']}' options"142 )143 # Check tab_parameter refs144 for param in spec["parameters"]:145 try:146 tab_parameter = param["tab_parameter"]147 except KeyError:148 continue # we aren't referencing a "tab" parameter149 if tab_parameter not in param_lookup:150 messages.append(151 f"Param '{param['id_name']}' has a 'tab_parameter' "152 "that is not in 'parameters'"153 )154 elif param_lookup[tab_parameter]["type"] != "tab":155 messages.append(156 f"Param '{param['id_name']}' has a 'tab_parameter' "157 "that is not a 'tab'"158 )159 # Check secret refs160 for param in spec["parameters"]:161 try:162 secret_parameter = param["secret_parameter"]163 except KeyError:164 continue # we aren't referencing a "secret" parameter165 if secret_parameter not in param_lookup:166 messages.append(167 f"Param '{param['id_name']}' has a 'secret_parameter' "168 "that is not a 'secret'"169 )170 else:171 secret = param_lookup[secret_parameter]172 if secret["type"] != "secret":173 messages.append(174 f"Param '{param['id_name']}' has a 'secret_parameter' "175 "that is not a 'secret'"176 )177 elif param["type"] == "gdrivefile" and (178 secret["secret_logic"]["provider"] != "oauth2"179 or secret["secret_logic"]["service"] != "google"180 ):181 messages.append(182 f"Param '{param['id_name']}' 'secret_parameter' "183 "does not refer to a 'google', 'oauth2' secret"184 )185 if messages:186 raise ValueError("; ".join(messages))187def load_spec(jsonish: Dict[str, Any]) -> ModuleSpec:188 """Convert a JSON-ish data structure to a ModuleSpec.189 Raise ValueError if the JSON-ish data structure has an error.190 """191 _validate_spec_dict(jsonish)192 loads_data = jsonish.get("loads_data", False)193 uses_data = jsonish.get("uses_data", not loads_data)194 param_fields = [ParamField.from_dict(d) for d in jsonish["parameters"]]195 if "param_schema" in jsonish:196 # Deprecated behavior: Module author wrote a schema in the YAML,197 # to define storage of 'custom' parameters198 param_schema = parse_param_schema(199 dict(type="dict", properties=jsonish["param_schema"])200 )201 else:202 # Usual case: infer schema from module parameter types203 param_schema = ParamSchema.Dict(204 {205 f.id_name: f.to_schema()206 for f in param_fields207 if f.to_schema() is not None208 }209 )210 return ModuleSpec(211 id_name=jsonish["id_name"],212 name=jsonish["name"],213 category=jsonish["category"],214 deprecated=jsonish.get("deprecated"),215 icon=jsonish.get("icon", ""),216 link=jsonish.get("link", ""),217 description=jsonish.get("description", ""),218 loads_data=loads_data,219 uses_data=uses_data,220 html_output=jsonish.get("html_output", False),221 has_zen_mode=jsonish.get("has_zen_mode", False),222 row_action_menu_entry_title=jsonish.get("row_action_menu_entry_title", ""),223 help_url=jsonish.get("help_url", ""),224 param_fields=param_fields,225 param_schema=param_schema,226 )227def load_spec_file(path: Path) -> ModuleSpec:228 """Load a ModuleSpec from a .yaml or .json file.229 Raise ValueError on validation error.230 Raise OSError on read error.231 """232 # raise OSError, ValueError233 with path.open("rb") as f:234 jsonish = yaml.safe_load(f)235 # raise ValueError236 return load_spec(jsonish)237if __name__ == "__main__":238 import sys239 filename = sys.argv[1]240 path = Path(filename)241 spec = load_spec_file(path)242 def repr_ParamField(dumper, data):243 return dumper.represent_mapping(type(data).__name__, asdict(data))244 def repr_NamedTuple(dumper, data):245 return dumper.represent_mapping(type(data).__name__, data._asdict())246 yaml.add_multi_representer(ParamField, repr_ParamField)247 yaml.add_multi_representer(tuple, repr_NamedTuple)...
apps.py
Source:apps.py
1from django.apps import AppConfig2from django.utils.translation import gettext_lazy as _3from ..conf import settings4from .pages import user_profile, usercp, users_list5class MisagoUsersConfig(AppConfig):6 name = "misago.users"7 label = "misago_users"8 verbose_name = "Misago Auth"9 def ready(self):10 from . import signals as _11 from .admin import tasks # pylint: disable=unused-import12 self.register_default_usercp_pages()13 self.register_default_users_list_pages()14 self.register_default_user_profile_pages()15 def register_default_usercp_pages(self):16 def sso_is_disabled(request):17 return not request.settings.enable_sso18 usercp.add_section(19 link="misago:usercp-change-forum-options",20 name=_("Forum options"),21 component="forum-options",22 icon="settings",23 )24 usercp.add_section(25 link="misago:usercp-edit-details",26 name=_("Edit details"),27 component="edit-details",28 icon="person_outline",29 )30 usercp.add_section(31 link="misago:usercp-change-username",32 name=_("Change username"),33 component="change-username",34 icon="card_membership",35 visible_if=sso_is_disabled,36 )37 usercp.add_section(38 link="misago:usercp-change-email-password",39 name=_("Change email or password"),40 component="sign-in-credentials",41 icon="vpn_key",42 visible_if=sso_is_disabled,43 )44 def can_download_own_data(request):45 return request.settings.allow_data_downloads46 usercp.add_section(47 link="misago:usercp-download-data",48 name=_("Download data"),49 component="download-data",50 icon="save_alt",51 visible_if=can_download_own_data,52 )53 def can_delete_own_account(request):54 if request.settings.enable_sso:55 return False56 return request.settings.allow_delete_own_account57 usercp.add_section(58 link="misago:usercp-delete-account",59 name=_("Delete account"),60 component="delete-account",61 icon="cancel",62 visible_if=can_delete_own_account,63 )64 def register_default_users_list_pages(self):65 users_list.add_section(66 link="misago:users-active-posters",67 component="active-posters",68 name=_("Top posters"),69 )70 def register_default_user_profile_pages(self):71 def can_see_names_history(request, profile):72 if request.user.is_authenticated:73 is_account_owner = profile.pk == request.user.pk74 has_permission = request.user_acl["can_see_users_name_history"]75 return is_account_owner or has_permission76 return False77 def can_see_ban_details(request, profile):78 if request.user.is_authenticated:79 if request.user_acl["can_see_ban_details"]:80 from .bans import get_user_ban81 return bool(get_user_ban(profile, request.cache_versions))82 return False83 return False84 user_profile.add_section(85 link="misago:user-posts", name=_("Posts"), icon="message", component="posts"86 )87 user_profile.add_section(88 link="misago:user-threads",89 name=_("Threads"),90 icon="forum",91 component="threads",92 )93 user_profile.add_section(94 link="misago:user-followers",95 name=_("Followers"),96 icon="favorite",97 component="followers",98 )99 user_profile.add_section(100 link="misago:user-follows",101 name=_("Follows"),102 icon="favorite_border",103 component="follows",104 )105 user_profile.add_section(106 link="misago:user-details",107 name=_("Details"),108 icon="person_outline",109 component="details",110 )111 user_profile.add_section(112 link="misago:username-history",113 name=_("Username history"),114 icon="card_membership",115 component="username-history",116 visible_if=can_see_names_history,117 )118 user_profile.add_section(119 link="misago:user-ban",120 name=_("Ban details"),121 icon="remove_circle_outline",122 component="ban-details",123 visible_if=can_see_ban_details,...
menu.py
Source:menu.py
1from app.models import User2class MenuItem:3 def __init__(self, item_type, **kwargs):4 self.type = item_type5 self.url = kwargs.get('url', None)6 self.title = kwargs.get('title', None)7 self.icon = kwargs.get('icon', None)8 self.selected = False9 self.visible = False10 self.visible_if = kwargs.get('visible_if', lambda u: True)11SIDE_MENU = [12 MenuItem(item_type='item', url='chat', title='Chat', icon='chat_bubble'),13 MenuItem(item_type='item', url='favorites', title='Favorites', icon='favorite'),14 MenuItem(item_type='item', url='watched', title='Watched', icon='movie'),15 MenuItem(item_type='item', url='expert_picks', title='Expert picks', icon='stars'),16 MenuItem(item_type='divider', visible_if=lambda u: User.is_auth_user_expert(u) or User.is_auth_user_admin(u)),17 MenuItem(item_type='item', url='add_expert_picks', title='Add expert picks', icon='library_add',18 visible_if=User.is_auth_user_expert),19 MenuItem(item_type='item', url='statistics', title='Statistics', icon='bar_chart',20 visible_if=lambda u: User.is_auth_user_expert(u) or User.is_auth_user_admin(u)),21 MenuItem(item_type='item', url='admin_dashboard', title='Admin dashboard', icon='supervised_user_circle',22 visible_if=User.is_auth_user_admin)...
Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.
You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.
Get 100 minutes of automation test minutes FREE!!