diff --git a/README.md b/README.md index 15728ce9b..d9e8ff444 100644 --- a/README.md +++ b/README.md @@ -113,7 +113,7 @@ JumpServer是一款安全产品,请参考 [基本安全建议](https://docs.ju ## License & Copyright -Copyright (c) 2014-2023 飞致云 FIT2CLOUD, All rights reserved. +Copyright (c) 2014-2024 飞致云 FIT2CLOUD, All rights reserved. Licensed under The GNU General Public License version 3 (GPLv3) (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at diff --git a/apps/accounts/automations/backup_account/handlers.py b/apps/accounts/automations/backup_account/handlers.py index 763428308..c47454685 100644 --- a/apps/accounts/automations/backup_account/handlers.py +++ b/apps/accounts/automations/backup_account/handlers.py @@ -145,9 +145,9 @@ class AccountBackupHandler: wb = Workbook(filename) for sheet, data in data_map.items(): ws = wb.add_worksheet(str(sheet)) - for row in data: - for col, _data in enumerate(row): - ws.write_string(0, col, _data) + for row_index, row_data in enumerate(data): + for col_index, col_data in enumerate(row_data): + ws.write_string(row_index, col_index, col_data) wb.close() files.append(filename) timedelta = round((time.time() - time_start), 2) diff --git a/apps/accounts/automations/change_secret/manager.py b/apps/accounts/automations/change_secret/manager.py index 74dfc717e..8381419ad 100644 --- a/apps/accounts/automations/change_secret/manager.py +++ b/apps/accounts/automations/change_secret/manager.py @@ -161,7 +161,8 @@ class ChangeSecretManager(AccountBasePlaybookManager): print("Account not found, deleted ?") return account.secret = recorder.new_secret - account.save(update_fields=['secret']) + account.date_updated = timezone.now() + account.save(update_fields=['secret', 'date_updated']) def on_host_error(self, host, error, result): recorder = self.name_recorder_mapper.get(host) @@ -228,8 +229,8 @@ class ChangeSecretManager(AccountBasePlaybookManager): rows.insert(0, header) wb = Workbook(filename) ws = wb.add_worksheet('Sheet1') - for row in rows: - for col, data in enumerate(row): - ws.write_string(0, col, data) + for row_index, row_data in enumerate(rows): + for col_index, col_data in enumerate(row_data): + ws.write_string(row_index, col_index, col_data) wb.close() return True diff --git a/apps/accounts/signal_handlers.py b/apps/accounts/signal_handlers.py index d086a049c..4c87df5cf 100644 --- a/apps/accounts/signal_handlers.py +++ b/apps/accounts/signal_handlers.py @@ -21,7 +21,8 @@ def on_account_pre_save(sender, instance, **kwargs): if instance.version == 0: instance.version = 1 else: - instance.version = instance.history.count() + history_account = instance.history.first() + instance.version = history_account.version + 1 if history_account else 0 @merge_delay_run(ttl=5) diff --git a/apps/accounts/tasks/remove_account.py b/apps/accounts/tasks/remove_account.py index 269a7f349..44bb9a840 100644 --- a/apps/accounts/tasks/remove_account.py +++ b/apps/accounts/tasks/remove_account.py @@ -1,9 +1,19 @@ -from celery import shared_task +import uuid +from collections import defaultdict + +from celery import shared_task, current_task +from django.conf import settings +from django.db.models import Count from django.utils.translation import gettext_noop, gettext_lazy as _ from accounts.const import AutomationTypes +from accounts.models import Account from accounts.tasks.common import quickstart_automation_by_snapshot +from audits.const import ActivityChoices +from common.const.crontab import CRONTAB_AT_AM_TWO from common.utils import get_logger +from ops.celery.decorator import register_as_period_task +from orgs.utils import tmp_to_root_org logger = get_logger(__file__) @@ -29,3 +39,39 @@ def remove_accounts_task(gather_account_ids): tp = AutomationTypes.remove_account quickstart_automation_by_snapshot(task_name, tp, task_snapshot) + + +@shared_task(verbose_name=_('Clean historical accounts')) +@register_as_period_task(crontab=CRONTAB_AT_AM_TWO) +@tmp_to_root_org() +def clean_historical_accounts(): + from audits.signal_handlers import create_activities + print("Clean historical accounts start.") + if settings.HISTORY_ACCOUNT_CLEAN_LIMIT >= 999: + return + limit = settings.HISTORY_ACCOUNT_CLEAN_LIMIT + + history_ids_to_be_deleted = [] + history_model = Account.history.model + history_id_mapper = defaultdict(list) + + ids = history_model.objects.values('id').annotate(count=Count('id')) \ + .filter(count__gte=limit).values_list('id', flat=True) + + if not ids: + return + + for i in history_model.objects.filter(id__in=ids): + _id = str(i.id) + history_id_mapper[_id].append(i.history_id) + + for history_ids in history_id_mapper.values(): + history_ids_to_be_deleted.extend(history_ids[limit:]) + history_qs = history_model.objects.filter(history_id__in=history_ids_to_be_deleted) + + resource_ids = list(history_qs.values_list('history_id', flat=True)) + history_qs.delete() + + task_id = current_task.request.id if current_task else str(uuid.uuid4()) + detail = gettext_noop('Remove historical accounts that are out of range.') + create_activities(resource_ids, detail, task_id, action=ActivityChoices.task, org_id='') diff --git a/apps/assets/api/asset/asset.py b/apps/assets/api/asset/asset.py index eef18a773..b6e532b36 100644 --- a/apps/assets/api/asset/asset.py +++ b/apps/assets/api/asset/asset.py @@ -21,7 +21,6 @@ from common.drf.filters import BaseFilterSet, AttrRulesFilterBackend from common.utils import get_logger, is_uuid from orgs.mixins import generics from orgs.mixins.api import OrgBulkModelViewSet -from ..mixin import NodeFilterMixin from ...notifications import BulkUpdatePlatformSkipAssetUserMsg logger = get_logger(__file__) @@ -86,7 +85,7 @@ class AssetFilterSet(BaseFilterSet): return queryset.filter(protocols__name__in=value).distinct() -class AssetViewSet(SuggestionMixin, NodeFilterMixin, OrgBulkModelViewSet): +class AssetViewSet(SuggestionMixin, OrgBulkModelViewSet): """ API endpoint that allows Asset to be viewed or edited. """ @@ -114,9 +113,7 @@ class AssetViewSet(SuggestionMixin, NodeFilterMixin, OrgBulkModelViewSet): ] def get_queryset(self): - queryset = super().get_queryset() \ - .prefetch_related('nodes', 'protocols') \ - .select_related('platform', 'domain') + queryset = super().get_queryset() if queryset.model is not Asset: queryset = queryset.select_related('asset_ptr') return queryset diff --git a/apps/assets/api/domain.py b/apps/assets/api/domain.py index 86097247c..46b586458 100644 --- a/apps/assets/api/domain.py +++ b/apps/assets/api/domain.py @@ -20,14 +20,15 @@ class DomainViewSet(OrgBulkModelViewSet): filterset_fields = ("name",) search_fields = filterset_fields ordering = ('name',) + serializer_classes = { + 'default': serializers.DomainSerializer, + 'list': serializers.DomainListSerializer, + } def get_serializer_class(self): if self.request.query_params.get('gateway'): return serializers.DomainWithGatewaySerializer - return serializers.DomainSerializer - - def get_queryset(self): - return super().get_queryset().prefetch_related('assets') + return super().get_serializer_class() class GatewayViewSet(HostViewSet): diff --git a/apps/assets/api/mixin.py b/apps/assets/api/mixin.py index d3ea4761d..af5864e4e 100644 --- a/apps/assets/api/mixin.py +++ b/apps/assets/api/mixin.py @@ -2,7 +2,7 @@ from typing import List from rest_framework.request import Request -from assets.models import Node, Protocol +from assets.models import Node, Platform, Protocol from assets.utils import get_node_from_request, is_query_node_all_assets from common.utils import lazyproperty, timeit @@ -71,37 +71,49 @@ class SerializeToTreeNodeMixin: return 'file' @timeit - def serialize_assets(self, assets, node_key=None, pid=None): - if node_key is None: - get_pid = lambda asset: getattr(asset, 'parent_key', '') - else: - get_pid = lambda asset: node_key + def serialize_assets(self, assets, node_key=None, get_pid=None): + if not get_pid and not node_key: + get_pid = lambda asset, platform: getattr(asset, 'parent_key', '') + sftp_asset_ids = Protocol.objects.filter(name='sftp') \ .values_list('asset_id', flat=True) - sftp_asset_ids = list(sftp_asset_ids) - data = [ - { + sftp_asset_ids = set(sftp_asset_ids) + platform_map = {p.id: p for p in Platform.objects.all()} + + data = [] + root_assets_count = 0 + for asset in assets: + platform = platform_map.get(asset.platform_id) + if not platform: + continue + pid = node_key or get_pid(asset, platform) + if not pid: + continue + # 根节点最多显示 1000 个资产 + if pid.isdigit(): + if root_assets_count > 1000: + continue + root_assets_count += 1 + data.append({ 'id': str(asset.id), 'name': asset.name, - 'title': f'{asset.address}\n{asset.comment}', - 'pId': pid or get_pid(asset), + 'title': f'{asset.address}\n{asset.comment}'.strip(), + 'pId': pid, 'isParent': False, 'open': False, - 'iconSkin': self.get_icon(asset), + 'iconSkin': self.get_icon(platform), 'chkDisabled': not asset.is_active, 'meta': { 'type': 'asset', 'data': { - 'platform_type': asset.platform.type, + 'platform_type': platform.type, 'org_name': asset.org_name, 'sftp': asset.id in sftp_asset_ids, 'name': asset.name, 'address': asset.address }, } - } - for asset in assets - ] + }) return data diff --git a/apps/assets/api/platform.py b/apps/assets/api/platform.py index 449b7b8a3..6a31f9519 100644 --- a/apps/assets/api/platform.py +++ b/apps/assets/api/platform.py @@ -29,7 +29,10 @@ class AssetPlatformViewSet(JMSModelViewSet): } def get_queryset(self): - queryset = super().get_queryset() + # 因为没有走分页逻辑,所以需要这里 prefetch + queryset = super().get_queryset().prefetch_related( + 'protocols', 'automation', 'labels', 'labels__label', + ) queryset = queryset.filter(type__in=AllTypes.get_types_values()) return queryset diff --git a/apps/assets/api/tree.py b/apps/assets/api/tree.py index 762859ca1..277ab323e 100644 --- a/apps/assets/api/tree.py +++ b/apps/assets/api/tree.py @@ -126,6 +126,8 @@ class NodeChildrenAsTreeApi(SerializeToTreeNodeMixin, NodeChildrenApi): include_assets = self.request.query_params.get('assets', '0') == '1' if not self.instance or not include_assets: return Asset.objects.none() + if self.instance.is_org_root(): + return Asset.objects.none() if query_all: assets = self.instance.get_all_assets() else: diff --git a/apps/assets/const/types.py b/apps/assets/const/types.py index c33052c64..220d10731 100644 --- a/apps/assets/const/types.py +++ b/apps/assets/const/types.py @@ -268,7 +268,7 @@ class AllTypes(ChoicesMixin): meta = {'type': 'category', 'category': category.value, '_type': category.value} category_node = cls.choice_to_node(category, 'ROOT', meta=meta) category_count = category_type_mapper.get(category, 0) - category_node['name'] += f'({category_count})' + category_node['name'] += f' ({category_count})' nodes.append(category_node) # Type 格式化 @@ -277,7 +277,7 @@ class AllTypes(ChoicesMixin): meta = {'type': 'type', 'category': category.value, '_type': tp.value} tp_node = cls.choice_to_node(tp, category_node['id'], opened=False, meta=meta) tp_count = category_type_mapper.get(category + '_' + tp, 0) - tp_node['name'] += f'({tp_count})' + tp_node['name'] += f' ({tp_count})' platforms = tp_platforms.get(category + '_' + tp, []) if not platforms: tp_node['isParent'] = False @@ -286,7 +286,7 @@ class AllTypes(ChoicesMixin): # Platform 格式化 for p in platforms: platform_node = cls.platform_to_node(p, tp_node['id'], include_asset) - platform_node['name'] += f'({platform_count.get(p.id, 0)})' + platform_node['name'] += f' ({platform_count.get(p.id, 0)})' nodes.append(platform_node) return nodes diff --git a/apps/assets/filters.py b/apps/assets/filters.py index f1fe6d666..1475f9b2e 100644 --- a/apps/assets/filters.py +++ b/apps/assets/filters.py @@ -63,11 +63,10 @@ class NodeFilterBackend(filters.BaseFilterBackend): query_all = is_query_node_all_assets(request) if query_all: return queryset.filter( - Q(nodes__key__istartswith=f'{node.key}:') | + Q(nodes__key__startswith=f'{node.key}:') | Q(nodes__key=node.key) ).distinct() else: - print("Query query origin: ", queryset.count()) return queryset.filter(nodes__key=node.key).distinct() diff --git a/apps/assets/models/node.py b/apps/assets/models/node.py index d4fc8165d..7a15b9349 100644 --- a/apps/assets/models/node.py +++ b/apps/assets/models/node.py @@ -13,7 +13,7 @@ from django.db.transaction import atomic from django.utils.translation import gettext_lazy as _, gettext from common.db.models import output_as_string -from common.utils import get_logger +from common.utils import get_logger, timeit from common.utils.lock import DistributedLock from orgs.mixins.models import OrgManager, JMSOrgBaseModel from orgs.models import Organization @@ -195,11 +195,6 @@ class FamilyMixin: ancestor_keys = self.get_ancestor_keys(with_self=with_self) return self.__class__.objects.filter(key__in=ancestor_keys) - # @property - # def parent_key(self): - # parent_key = ":".join(self.key.split(":")[:-1]) - # return parent_key - def compute_parent_key(self): return compute_parent_key(self.key) @@ -349,29 +344,26 @@ class NodeAllAssetsMappingMixin: return 'ASSETS_ORG_NODE_ALL_ASSET_ids_MAPPING_{}'.format(org_id) @classmethod + @timeit def generate_node_all_asset_ids_mapping(cls, org_id): - from .asset import Asset - - logger.info(f'Generate node asset mapping: ' - f'thread={threading.get_ident()} ' - f'org_id={org_id}') + logger.info(f'Generate node asset mapping: org_id={org_id}') t1 = time.time() with tmp_to_org(org_id): node_ids_key = Node.objects.annotate( char_id=output_as_string('id') ).values_list('char_id', 'key') - # * 直接取出全部. filter(node__org_id=org_id)(大规模下会更慢) - nodes_asset_ids = Asset.nodes.through.objects.all() \ - .annotate(char_node_id=output_as_string('node_id')) \ - .annotate(char_asset_id=output_as_string('asset_id')) \ - .values_list('char_node_id', 'char_asset_id') - node_id_ancestor_keys_mapping = { node_id: cls.get_node_ancestor_keys(node_key, with_self=True) for node_id, node_key in node_ids_key } + # * 直接取出全部. filter(node__org_id=org_id)(大规模下会更慢) + nodes_asset_ids = cls.assets.through.objects.all() \ + .annotate(char_node_id=output_as_string('node_id')) \ + .annotate(char_asset_id=output_as_string('asset_id')) \ + .values_list('char_node_id', 'char_asset_id') + nodeid_assetsid_mapping = defaultdict(set) for node_id, asset_id in nodes_asset_ids: nodeid_assetsid_mapping[node_id].add(asset_id) @@ -386,7 +378,7 @@ class NodeAllAssetsMappingMixin: mapping[ancestor_key].update(asset_ids) t3 = time.time() - logger.info('t1-t2(DB Query): {} s, t3-t2(Generate mapping): {} s'.format(t2 - t1, t3 - t2)) + logger.info('Generate asset nodes mapping, DB query: {:.2f}s, mapping: {:.2f}s'.format(t2 - t1, t3 - t2)) return mapping @@ -436,6 +428,7 @@ class NodeAssetsMixin(NodeAllAssetsMappingMixin): return asset_ids @classmethod + @timeit def get_nodes_all_assets(cls, *nodes): from .asset import Asset node_ids = set() @@ -559,11 +552,6 @@ class Node(JMSOrgBaseModel, SomeNodesMixin, FamilyMixin, NodeAssetsMixin): def __str__(self): return self.full_value - # def __eq__(self, other): - # if not other: - # return False - # return self.id == other.id - # def __gt__(self, other): self_key = [int(k) for k in self.key.split(':')] other_key = [int(k) for k in other.key.split(':')] diff --git a/apps/assets/pagination.py b/apps/assets/pagination.py index 8ae42ef16..316029301 100644 --- a/apps/assets/pagination.py +++ b/apps/assets/pagination.py @@ -1,8 +1,8 @@ from rest_framework.pagination import LimitOffsetPagination from rest_framework.request import Request -from common.utils import get_logger from assets.models import Node +from common.utils import get_logger logger = get_logger(__name__) @@ -28,6 +28,7 @@ class AssetPaginationBase(LimitOffsetPagination): 'key', 'all', 'show_current_asset', 'cache_policy', 'display', 'draw', 'order', 'node', 'node_id', 'fields_size', + 'asset' } for k, v in self._request.query_params.items(): if k not in exclude_query_params and v is not None: diff --git a/apps/assets/serializers/asset/common.py b/apps/assets/serializers/asset/common.py index 6c45944de..96371bcd2 100644 --- a/apps/assets/serializers/asset/common.py +++ b/apps/assets/serializers/asset/common.py @@ -100,7 +100,10 @@ class AssetAccountSerializer(AccountSerializer): class Meta(AccountSerializer.Meta): fields = [ f for f in AccountSerializer.Meta.fields - if f not in ['spec_info'] + if f not in [ + 'spec_info', 'connectivity', 'labels', 'created_by', + 'date_update', 'date_created' + ] ] extra_kwargs = { **AccountSerializer.Meta.extra_kwargs, @@ -203,9 +206,12 @@ class AssetSerializer(BulkOrgResourceModelSerializer, ResourceLabelsMixin, Writa """ Perform necessary eager loading of data. """ queryset = queryset.prefetch_related('domain', 'nodes', 'protocols', ) \ .prefetch_related('platform', 'platform__automation') \ - .prefetch_related('labels', 'labels__label') \ .annotate(category=F("platform__category")) \ .annotate(type=F("platform__type")) + if queryset.model is Asset: + queryset = queryset.prefetch_related('labels__label', 'labels') + else: + queryset = queryset.prefetch_related('asset_ptr__labels__label', 'asset_ptr__labels') return queryset @staticmethod @@ -375,7 +381,6 @@ class AssetSerializer(BulkOrgResourceModelSerializer, ResourceLabelsMixin, Writa class DetailMixin(serializers.Serializer): - accounts = AssetAccountSerializer(many=True, required=False, label=_('Accounts')) spec_info = MethodSerializer(label=_('Spec info'), read_only=True) gathered_info = MethodSerializer(label=_('Gathered info'), read_only=True) auto_config = serializers.DictField(read_only=True, label=_('Auto info')) @@ -390,8 +395,7 @@ class DetailMixin(serializers.Serializer): def get_field_names(self, declared_fields, info): names = super().get_field_names(declared_fields, info) names.extend([ - 'accounts', 'gathered_info', 'spec_info', - 'auto_config', + 'gathered_info', 'spec_info', 'auto_config', ]) return names diff --git a/apps/assets/serializers/domain.py b/apps/assets/serializers/domain.py index d2b3e3550..9ea603ac3 100644 --- a/apps/assets/serializers/domain.py +++ b/apps/assets/serializers/domain.py @@ -1,5 +1,6 @@ # -*- coding: utf-8 -*- # +from django.db.models import Count from django.utils.translation import gettext_lazy as _ from rest_framework import serializers @@ -7,18 +8,15 @@ from common.serializers import ResourceLabelsMixin from common.serializers.fields import ObjectRelatedField from orgs.mixins.serializers import BulkOrgResourceModelSerializer from .gateway import GatewayWithAccountSecretSerializer -from ..models import Domain, Asset +from ..models import Domain -__all__ = ['DomainSerializer', 'DomainWithGatewaySerializer'] +__all__ = ['DomainSerializer', 'DomainWithGatewaySerializer', 'DomainListSerializer'] class DomainSerializer(ResourceLabelsMixin, BulkOrgResourceModelSerializer): gateways = ObjectRelatedField( many=True, required=False, label=_('Gateway'), read_only=True, ) - assets = ObjectRelatedField( - many=True, required=False, queryset=Asset.objects, label=_('Asset') - ) class Meta: model = Domain @@ -30,7 +28,9 @@ class DomainSerializer(ResourceLabelsMixin, BulkOrgResourceModelSerializer): def to_representation(self, instance): data = super().to_representation(instance) - assets = data['assets'] + assets = data.get('assets') + if assets is None: + return data gateway_ids = [str(i['id']) for i in data['gateways']] data['assets'] = [i for i in assets if str(i['id']) not in gateway_ids] return data @@ -49,6 +49,20 @@ class DomainSerializer(ResourceLabelsMixin, BulkOrgResourceModelSerializer): return queryset +class DomainListSerializer(DomainSerializer): + assets_amount = serializers.IntegerField(label=_('Assets amount'), read_only=True) + + class Meta(DomainSerializer.Meta): + fields = list(set(DomainSerializer.Meta.fields + ['assets_amount']) - {'assets'}) + + @classmethod + def setup_eager_loading(cls, queryset): + queryset = queryset.annotate( + assets_amount=Count('assets'), + ) + return queryset + + class DomainWithGatewaySerializer(serializers.ModelSerializer): gateways = GatewayWithAccountSecretSerializer(many=True, read_only=True) diff --git a/apps/assets/serializers/platform.py b/apps/assets/serializers/platform.py index f67df9906..4fb0418c6 100644 --- a/apps/assets/serializers/platform.py +++ b/apps/assets/serializers/platform.py @@ -191,7 +191,6 @@ class PlatformSerializer(ResourceLabelsMixin, WritableNestedModelSerializer): def add_type_choices(self, name, label): tp = self.fields['type'] tp.choices[name] = label - tp.choice_mapper[name] = label tp.choice_strings_to_values[name] = label @lazyproperty @@ -200,12 +199,6 @@ class PlatformSerializer(ResourceLabelsMixin, WritableNestedModelSerializer): constraints = AllTypes.get_constraints(category, tp) return constraints - @classmethod - def setup_eager_loading(cls, queryset): - queryset = queryset.prefetch_related('protocols', 'automation') \ - .prefetch_related('labels', 'labels__label') - return queryset - def validate_protocols(self, protocols): if not protocols: raise serializers.ValidationError(_("Protocols is required")) diff --git a/apps/assets/signal_handlers/asset.py b/apps/assets/signal_handlers/asset.py index 9598bec5d..5ab4a4117 100644 --- a/apps/assets/signal_handlers/asset.py +++ b/apps/assets/signal_handlers/asset.py @@ -80,10 +80,11 @@ RELATED_NODE_IDS = '_related_node_ids' @receiver(pre_delete, sender=Asset) def on_asset_delete(instance: Asset, using, **kwargs): - logger.debug("Asset pre delete signal recv: {}".format(instance)) node_ids = Node.objects.filter(assets=instance) \ .distinct().values_list('id', flat=True) - setattr(instance, RELATED_NODE_IDS, node_ids) + node_ids = list(node_ids) + logger.debug("Asset pre delete signal recv: {}, node_ids: {}".format(instance, node_ids)) + setattr(instance, RELATED_NODE_IDS, list(node_ids)) m2m_changed.send( sender=Asset.nodes.through, instance=instance, reverse=False, model=Node, pk_set=node_ids, @@ -93,8 +94,8 @@ def on_asset_delete(instance: Asset, using, **kwargs): @receiver(post_delete, sender=Asset) def on_asset_post_delete(instance: Asset, using, **kwargs): - logger.debug("Asset post delete signal recv: {}".format(instance)) node_ids = getattr(instance, RELATED_NODE_IDS, []) + logger.debug("Asset post delete signal recv: {}, node_ids: {}".format(instance, node_ids)) if node_ids: m2m_changed.send( sender=Asset.nodes.through, instance=instance, reverse=False, diff --git a/apps/assets/signal_handlers/node_assets_amount.py b/apps/assets/signal_handlers/node_assets_amount.py index 79e2ed568..ea2b3ba8a 100644 --- a/apps/assets/signal_handlers/node_assets_amount.py +++ b/apps/assets/signal_handlers/node_assets_amount.py @@ -15,8 +15,8 @@ from ..tasks import check_node_assets_amount_task logger = get_logger(__file__) -@on_transaction_commit @receiver(m2m_changed, sender=Asset.nodes.through) +@on_transaction_commit def on_node_asset_change(sender, action, instance, reverse, pk_set, **kwargs): # 不允许 `pre_clear` ,因为该信号没有 `pk_set` # [官网](https://docs.djangoproject.com/en/3.1/ref/signals/#m2m-changed) @@ -37,7 +37,7 @@ def on_node_asset_change(sender, action, instance, reverse, pk_set, **kwargs): update_nodes_assets_amount(node_ids=node_ids) -@merge_delay_run(ttl=5) +@merge_delay_run(ttl=30) def update_nodes_assets_amount(node_ids=()): nodes = Node.objects.filter(id__in=node_ids) nodes = Node.get_ancestor_queryset(nodes) diff --git a/apps/assets/signal_handlers/node_assets_mapping.py b/apps/assets/signal_handlers/node_assets_mapping.py index 34b707dab..a53e534b6 100644 --- a/apps/assets/signal_handlers/node_assets_mapping.py +++ b/apps/assets/signal_handlers/node_assets_mapping.py @@ -21,7 +21,7 @@ logger = get_logger(__name__) node_assets_mapping_pub_sub = lazy(lambda: RedisPubSub('fm.node_asset_mapping'), RedisPubSub)() -@merge_delay_run(ttl=5) +@merge_delay_run(ttl=30) def expire_node_assets_mapping(org_ids=()): logger.debug("Recv asset nodes changed signal, expire memery node asset mapping") # 所有进程清除(自己的 memory 数据) @@ -53,8 +53,9 @@ def on_node_post_delete(sender, instance, **kwargs): @receiver(m2m_changed, sender=Asset.nodes.through) -def on_node_asset_change(sender, instance, **kwargs): - expire_node_assets_mapping(org_ids=(instance.org_id,)) +def on_node_asset_change(sender, instance, action='pre_remove', **kwargs): + if action.startswith('post'): + expire_node_assets_mapping(org_ids=(instance.org_id,)) @receiver(django_ready) diff --git a/apps/assets/urls/api_urls.py b/apps/assets/urls/api_urls.py index 408550ece..b56458758 100644 --- a/apps/assets/urls/api_urls.py +++ b/apps/assets/urls/api_urls.py @@ -2,6 +2,7 @@ from django.urls import path from rest_framework_bulk.routes import BulkRouter +from labels.api import LabelViewSet from .. import api app_name = 'assets' @@ -22,6 +23,7 @@ router.register(r'domains', api.DomainViewSet, 'domain') router.register(r'gateways', api.GatewayViewSet, 'gateway') router.register(r'favorite-assets', api.FavoriteAssetViewSet, 'favorite-asset') router.register(r'protocol-settings', api.PlatformProtocolViewSet, 'protocol-setting') +router.register(r'labels', LabelViewSet, 'label') urlpatterns = [ # path('assets//gateways/', api.AssetGatewayListApi.as_view(), name='asset-gateway-list'), diff --git a/apps/assets/utils/k8s.py b/apps/assets/utils/k8s.py index 2b33ded89..dc3cd8bc6 100644 --- a/apps/assets/utils/k8s.py +++ b/apps/assets/utils/k8s.py @@ -4,7 +4,6 @@ from urllib.parse import urlencode, urlparse from kubernetes import client from kubernetes.client import api_client from kubernetes.client.api import core_v1_api -from kubernetes.client.exceptions import ApiException from sshtunnel import SSHTunnelForwarder, BaseSSHTunnelForwarderError from common.utils import get_logger @@ -88,8 +87,9 @@ class KubernetesClient: if hasattr(self, func_name): try: data = getattr(self, func_name)(*args) - except ApiException as e: - logger.error(e.reason) + except Exception as e: + logger.error(e) + raise e if self.server: self.server.stop() diff --git a/apps/audits/api.py b/apps/audits/api.py index c2cd84756..209bc30fd 100644 --- a/apps/audits/api.py +++ b/apps/audits/api.py @@ -5,6 +5,7 @@ from importlib import import_module from django.conf import settings from django.db.models import F, Value, CharField, Q +from django.db.models.functions import Cast from django.http import HttpResponse, FileResponse from django.utils.encoding import escape_uri_path from rest_framework import generics @@ -40,6 +41,7 @@ from .serializers import ( PasswordChangeLogSerializer, ActivityUnionLogSerializer, FileSerializer, UserSessionSerializer ) +from .utils import construct_userlogin_usernames logger = get_logger(__name__) @@ -125,15 +127,16 @@ class UserLoginCommonMixin: class UserLoginLogViewSet(UserLoginCommonMixin, OrgReadonlyModelViewSet): @staticmethod - def get_org_members(): - users = current_org.get_members().values_list('username', flat=True) + def get_org_member_usernames(): + user_queryset = current_org.get_members() + users = construct_userlogin_usernames(user_queryset) return users def get_queryset(self): queryset = super().get_queryset() if current_org.is_root(): return queryset - users = self.get_org_members() + users = self.get_org_member_usernames() queryset = queryset.filter(username__in=users) return queryset @@ -163,7 +166,7 @@ class ResourceActivityAPIView(generics.ListAPIView): q |= Q(user=str(user)) queryset = OperateLog.objects.filter(q, org_q).annotate( r_type=Value(ActivityChoices.operate_log, CharField()), - r_detail_id=F('id'), r_detail=Value(None, CharField()), + r_detail_id=Cast(F('id'), CharField()), r_detail=Value(None, CharField()), r_user=F('user'), r_action=F('action'), ).values(*fields)[:limit] return queryset diff --git a/apps/audits/utils.py b/apps/audits/utils.py index 4312962e6..d9728fbbd 100644 --- a/apps/audits/utils.py +++ b/apps/audits/utils.py @@ -4,6 +4,8 @@ from itertools import chain from django.contrib.contenttypes.fields import GenericForeignKey, GenericRelation from django.db import models +from django.db.models import F, Value, CharField +from django.db.models.functions import Concat from common.db.fields import RelatedManager from common.utils import validate_ip, get_ip_city, get_logger @@ -115,3 +117,12 @@ def model_to_dict_for_operate_log( get_related_values(f) return data + + +def construct_userlogin_usernames(user_queryset): + usernames_original = user_queryset.values_list('username', flat=True) + usernames_combined = user_queryset.annotate( + usernames_combined_field=Concat(F('name'), Value('('), F('username'), Value(')'), output_field=CharField()) + ).values_list("usernames_combined_field", flat=True) + usernames = list(chain(usernames_original, usernames_combined)) + return usernames diff --git a/apps/authentication/api/mfa.py b/apps/authentication/api/mfa.py index 049cd177a..2d3a9b072 100644 --- a/apps/authentication/api/mfa.py +++ b/apps/authentication/api/mfa.py @@ -90,6 +90,6 @@ class MFAChallengeVerifyApi(AuthMixin, CreateAPIView): return Response({'msg': 'ok'}) except errors.AuthFailedError as e: data = {"error": e.error, "msg": e.msg} - raise ValidationError(data) + return Response(data, status=401) except errors.NeedMoreInfoError as e: return Response(e.as_data(), status=200) diff --git a/apps/authentication/api/password.py b/apps/authentication/api/password.py index cc1e6aff7..f721ed2a8 100644 --- a/apps/authentication/api/password.py +++ b/apps/authentication/api/password.py @@ -15,12 +15,11 @@ from authentication.mixins import authenticate from authentication.serializers import ( PasswordVerifySerializer, ResetPasswordCodeSerializer ) +from authentication.utils import check_user_property_is_correct from common.permissions import IsValidUser -from common.utils import get_object_or_none from common.utils.random import random_string from common.utils.verify_code import SendAndVerifyCodeUtil from settings.utils import get_login_title -from users.models import User class UserResetPasswordSendCodeApi(CreateAPIView): @@ -28,8 +27,8 @@ class UserResetPasswordSendCodeApi(CreateAPIView): serializer_class = ResetPasswordCodeSerializer @staticmethod - def is_valid_user(**kwargs): - user = get_object_or_none(User, **kwargs) + def is_valid_user(username, **properties): + user = check_user_property_is_correct(username, **properties) if not user: err_msg = _('User does not exist: {}').format(_("No user matched")) return None, err_msg @@ -56,7 +55,6 @@ class UserResetPasswordSendCodeApi(CreateAPIView): target = serializer.validated_data[form_type] if form_type == 'sms': query_key = 'phone' - target = target.lstrip('+') else: query_key = form_type user, err = self.is_valid_user(username=username, **{query_key: target}) diff --git a/apps/authentication/utils.py b/apps/authentication/utils.py index 9cbc95bf2..4cb1e7368 100644 --- a/apps/authentication/utils.py +++ b/apps/authentication/utils.py @@ -7,8 +7,9 @@ from django.conf import settings from django.utils.translation import gettext_lazy as _ from audits.const import DEFAULT_CITY +from users.models import User from audits.models import UserLoginLog -from common.utils import get_logger +from common.utils import get_logger, get_object_or_none from common.utils import validate_ip, get_ip_city, get_request_ip from .notifications import DifferentCityLoginMessage @@ -24,9 +25,10 @@ def check_different_city_login_if_need(user, request): is_private = ipaddress.ip_address(ip).is_private if is_private: return + usernames = [user.username, f"{user.name}({user.username})"] last_user_login = UserLoginLog.objects.exclude( city__in=city_white - ).filter(username=user.username, status=True).first() + ).filter(username__in=usernames, status=True).first() if not last_user_login: return @@ -59,3 +61,12 @@ def build_absolute_uri_for_oidc(request, path=None): redirect_uri = urljoin(settings.BASE_SITE_URL, path) return redirect_uri return build_absolute_uri(request, path=path) + + +def check_user_property_is_correct(username, **properties): + user = get_object_or_none(User, username=username) + for attr, value in properties.items(): + if getattr(user, attr, None) != value: + user = None + break + return user diff --git a/apps/common/api/mixin.py b/apps/common/api/mixin.py index c87d5f22a..e8266d928 100644 --- a/apps/common/api/mixin.py +++ b/apps/common/api/mixin.py @@ -98,12 +98,19 @@ class QuerySetMixin: return queryset if self.action == 'metadata': queryset = queryset.none() - if self.action in ['list', 'metadata']: - serializer_class = self.get_serializer_class() - if serializer_class and hasattr(serializer_class, 'setup_eager_loading'): - queryset = serializer_class.setup_eager_loading(queryset) return queryset + def paginate_queryset(self, queryset): + page = super().paginate_queryset(queryset) + serializer_class = self.get_serializer_class() + if page and serializer_class and hasattr(serializer_class, 'setup_eager_loading'): + ids = [str(obj.id) for obj in page] + page = self.get_queryset().filter(id__in=ids) + page = serializer_class.setup_eager_loading(page) + page_mapper = {str(obj.id): obj for obj in page} + page = [page_mapper.get(_id) for _id in ids if _id in page_mapper] + return page + class ExtraFilterFieldsMixin: """ diff --git a/apps/common/decorators.py b/apps/common/decorators.py index 24b2695d3..7269c9e0d 100644 --- a/apps/common/decorators.py +++ b/apps/common/decorators.py @@ -65,7 +65,7 @@ class EventLoopThread(threading.Thread): _loop_thread = EventLoopThread() -_loop_thread.setDaemon(True) +_loop_thread.daemon = True _loop_thread.start() executor = ThreadPoolExecutor( max_workers=10, diff --git a/apps/common/drf/filters.py b/apps/common/drf/filters.py index 0fb8ca63a..d84692dfe 100644 --- a/apps/common/drf/filters.py +++ b/apps/common/drf/filters.py @@ -219,11 +219,11 @@ class LabelFilterBackend(filters.BaseFilterBackend): if not hasattr(queryset, 'model'): return queryset - if not hasattr(queryset.model, 'labels'): + if not hasattr(queryset.model, 'label_model'): return queryset - model = queryset.model - labeled_resource_cls = model._labels.field.related_model + model = queryset.model.label_model() + labeled_resource_cls = model.labels.field.related_model app_label = model._meta.app_label model_name = model._meta.model_name diff --git a/apps/common/management/commands/services/services/celery_base.py b/apps/common/management/commands/services/services/celery_base.py index 8d197d4f8..4e63f4cbb 100644 --- a/apps/common/management/commands/services/services/celery_base.py +++ b/apps/common/management/commands/services/services/celery_base.py @@ -14,6 +14,7 @@ class CeleryBaseService(BaseService): print('\n- Start Celery as Distributed Task Queue: {}'.format(self.queue.capitalize())) ansible_config_path = os.path.join(settings.APPS_DIR, 'ops', 'ansible', 'ansible.cfg') ansible_modules_path = os.path.join(settings.APPS_DIR, 'ops', 'ansible', 'modules') + os.environ.setdefault('LC_ALL', 'C.UTF-8') os.environ.setdefault('PYTHONOPTIMIZE', '1') os.environ.setdefault('ANSIBLE_FORCE_COLOR', 'True') os.environ.setdefault('ANSIBLE_CONFIG', ansible_config_path) diff --git a/apps/common/sdk/im/slack/__init__.py b/apps/common/sdk/im/slack/__init__.py index bea92e78e..2ff6e071d 100644 --- a/apps/common/sdk/im/slack/__init__.py +++ b/apps/common/sdk/im/slack/__init__.py @@ -1,16 +1,14 @@ -import requests import mistune - -from rest_framework.exceptions import APIException +import requests from django.utils.translation import gettext_lazy as _ +from rest_framework.exceptions import APIException -from users.utils import construct_user_email from common.utils.common import get_logger from jumpserver.utils import get_current_request +from users.utils import construct_user_email logger = get_logger(__name__) - SLACK_REDIRECT_URI_SESSION_KEY = '_slack_redirect_uri' @@ -22,15 +20,15 @@ class URL: AUTH_TEST = 'https://slack.com/api/auth.test' -class SlackRenderer(mistune.Renderer): - def header(self, text, level, raw=None): +class SlackRenderer(mistune.HTMLRenderer): + def heading(self, text, level): return '*' + text + '*\n' - def double_emphasis(self, text): + def strong(self, text): return '*' + text + '*' - def list(self, body, ordered=True): - lines = body.split('\n') + def list(self, text, **kwargs): + lines = text.split('\n') for i, line in enumerate(lines): if not line: continue @@ -41,9 +39,9 @@ class SlackRenderer(mistune.Renderer): def block_code(self, code, lang=None): return f'`{code}`' - def link(self, link, title, content): - if title or content: - label = str(title or content).strip() + def link(self, link, text=None, title=None): + if title or text: + label = str(title or text).strip() return f'<{link}|{label}>' return f'<{link}>' diff --git a/apps/common/serializers/mixin.py b/apps/common/serializers/mixin.py index d51849f07..81fac91d9 100644 --- a/apps/common/serializers/mixin.py +++ b/apps/common/serializers/mixin.py @@ -394,20 +394,20 @@ class CommonBulkModelSerializer(CommonBulkSerializerMixin, serializers.ModelSeri class ResourceLabelsMixin(serializers.Serializer): - labels = LabelRelatedField(many=True, label=_('Labels'), required=False, allow_null=True) + labels = LabelRelatedField(many=True, label=_('Labels'), required=False, allow_null=True, source='res_labels') def update(self, instance, validated_data): - labels = validated_data.pop('labels', None) + labels = validated_data.pop('res_labels', None) res = super().update(instance, validated_data) if labels is not None: - instance.labels.set(labels, bulk=False) + instance.res_labels.set(labels, bulk=False) return res def create(self, validated_data): - labels = validated_data.pop('labels', None) + labels = validated_data.pop('res_labels', None) instance = super().create(validated_data) if labels is not None: - instance.labels.set(labels, bulk=False) + instance.res_labels.set(labels, bulk=False) return instance @classmethod diff --git a/apps/common/signal_handlers.py b/apps/common/signal_handlers.py index 588a63632..ad765657e 100644 --- a/apps/common/signal_handlers.py +++ b/apps/common/signal_handlers.py @@ -62,14 +62,14 @@ def digest_sql_query(): method = current_request.method path = current_request.get_full_path() - print(">>> [{}] {}".format(method, path)) + print(">>>. [{}] {}".format(method, path)) for table_name, queries in table_queries.items(): if table_name.startswith('rbac_') or table_name.startswith('auth_permission'): continue for query in queries: sql = query['sql'] - print(" # {}: {}".format(query['time'], sql)) + print(" # {}: {}".format(query['time'], sql[:1000])) if len(queries) < 3: continue print("- Table: {}".format(table_name)) @@ -77,9 +77,9 @@ def digest_sql_query(): sql = query['sql'] if not sql or not sql.startswith('SELECT'): continue - print('\t{}. {}'.format(i, sql)) + print('\t{}.[{}s] {}'.format(i, round(float(query['time']), 2), sql[:1000])) - logger.debug(">>> [{}] {}".format(method, path)) + # logger.debug(">>> [{}] {}".format(method, path)) for name, counter in counters: logger.debug("Query {:3} times using {:.2f}s {}".format( counter.counter, counter.time, name) diff --git a/apps/common/tasks.py b/apps/common/tasks.py index d5c0cb609..5bffe07f4 100644 --- a/apps/common/tasks.py +++ b/apps/common/tasks.py @@ -2,7 +2,7 @@ import os from celery import shared_task from django.conf import settings -from django.core.mail import send_mail, EmailMultiAlternatives +from django.core.mail import send_mail, EmailMultiAlternatives, get_connection from django.utils.translation import gettext_lazy as _ import jms_storage @@ -11,6 +11,16 @@ from .utils import get_logger logger = get_logger(__file__) +def get_email_connection(**kwargs): + email_backend_map = { + 'smtp': 'django.core.mail.backends.smtp.EmailBackend', + 'exchange': 'jumpserver.rewriting.exchange.EmailBackend' + } + return get_connection( + backend=email_backend_map.get(settings.EMAIL_PROTOCOL), **kwargs + ) + + def task_activity_callback(self, subject, message, recipient_list, *args, **kwargs): from users.models import User email_list = recipient_list @@ -40,7 +50,7 @@ def send_mail_async(*args, **kwargs): args = tuple(args) try: - return send_mail(*args, **kwargs) + return send_mail(connection=get_email_connection(), *args, **kwargs) except Exception as e: logger.error("Sending mail error: {}".format(e)) @@ -55,7 +65,8 @@ def send_mail_attachment_async(subject, message, recipient_list, attachment_list subject=subject, body=message, from_email=from_email, - to=recipient_list + to=recipient_list, + connection=get_email_connection(), ) for attachment in attachment_list: email.attach_file(attachment) diff --git a/apps/common/utils/common.py b/apps/common/utils/common.py index 798b4a94c..86b68bef7 100644 --- a/apps/common/utils/common.py +++ b/apps/common/utils/common.py @@ -220,7 +220,7 @@ def timeit(func): now = time.time() result = func(*args, **kwargs) using = (time.time() - now) * 1000 - msg = "End call {}, using: {:.1f}ms".format(name, using) + msg = "Ends call: {}, using: {:.1f}ms".format(name, using) logger.debug(msg) return result diff --git a/apps/common/utils/lock.py b/apps/common/utils/lock.py index 773647725..949d13c6b 100644 --- a/apps/common/utils/lock.py +++ b/apps/common/utils/lock.py @@ -1,18 +1,16 @@ -from functools import wraps import threading +from functools import wraps +from django.db import transaction from redis_lock import ( Lock as RedisLock, NotAcquired, UNLOCK_SCRIPT, EXTEND_SCRIPT, RESET_SCRIPT, RESET_ALL_SCRIPT ) -from redis import Redis -from django.db import transaction -from common.utils import get_logger -from common.utils.inspect import copy_function_args -from common.utils.connection import get_redis_client -from jumpserver.const import CONFIG from common.local import thread_local +from common.utils import get_logger +from common.utils.connection import get_redis_client +from common.utils.inspect import copy_function_args logger = get_logger(__file__) @@ -76,6 +74,7 @@ class DistributedLock(RedisLock): # 要创建一个新的锁对象 with self.__class__(**self.kwargs_copy): return func(*args, **kwds) + return inner @classmethod @@ -95,7 +94,6 @@ class DistributedLock(RedisLock): if self.locked(): owner_id = self.get_owner_id() local_owner_id = getattr(thread_local, self.name, None) - if local_owner_id and owner_id == local_owner_id: return True return False @@ -140,14 +138,16 @@ class DistributedLock(RedisLock): logger.debug(f'Released reentrant-lock: lock_id={self.id} owner_id={self.get_owner_id()} lock={self.name}') return else: - self._raise_exc_with_log(f'Reentrant-lock is not acquired: lock_id={self.id} owner_id={self.get_owner_id()} lock={self.name}') + self._raise_exc_with_log( + f'Reentrant-lock is not acquired: lock_id={self.id} owner_id={self.get_owner_id()} lock={self.name}') def _release_on_reentrant_locked_by_me(self): logger.debug(f'Release reentrant-lock locked by me: lock_id={self.id} lock={self.name}') id = getattr(thread_local, self.name, None) if id != self.id: - raise PermissionError(f'Reentrant-lock is not locked by me: lock_id={self.id} owner_id={self.get_owner_id()} lock={self.name}') + raise PermissionError( + f'Reentrant-lock is not locked by me: lock_id={self.id} owner_id={self.get_owner_id()} lock={self.name}') try: # 这里要保证先删除 thread_local 的标记, delattr(thread_local, self.name) @@ -191,7 +191,7 @@ class DistributedLock(RedisLock): # 处理是否在事务提交时才释放锁 if self._release_on_transaction_commit: logger.debug( - f'Release lock on transaction commit ... :lock_id={self.id} lock={self.name}') + f'Release lock on transaction commit:lock_id={self.id} lock={self.name}') transaction.on_commit(_release) else: _release() diff --git a/apps/jumpserver/api.py b/apps/jumpserver/api.py index 63d13df55..cfa6b771d 100644 --- a/apps/jumpserver/api.py +++ b/apps/jumpserver/api.py @@ -17,6 +17,7 @@ from assets.models import Asset from audits.api import OperateLogViewSet from audits.const import LoginStatusChoices from audits.models import UserLoginLog, PasswordChangeLog, OperateLog, FTPLog, JobLog +from audits.utils import construct_userlogin_usernames from common.utils import lazyproperty from common.utils.timezone import local_now, local_zero_hour from ops.const import JobStatus @@ -79,7 +80,7 @@ class DateTimeMixin: if not self.org.is_root(): if query_params == 'username': query = { - f'{query_params}__in': users.values_list('username', flat=True) + f'{query_params}__in': construct_userlogin_usernames(users) } else: query = { diff --git a/apps/jumpserver/conf.py b/apps/jumpserver/conf.py index 80790eb2e..741a0e5db 100644 --- a/apps/jumpserver/conf.py +++ b/apps/jumpserver/conf.py @@ -17,7 +17,7 @@ import re import sys import types from importlib import import_module -from urllib.parse import urljoin, urlparse +from urllib.parse import urljoin, urlparse, quote import yaml from django.urls import reverse_lazy @@ -261,6 +261,8 @@ class Config(dict): 'VAULT_HCP_TOKEN': '', 'VAULT_HCP_MOUNT_POINT': 'jumpserver', + 'HISTORY_ACCOUNT_CLEAN_LIMIT': 999, + # Cache login password 'CACHE_LOGIN_PASSWORD_ENABLED': False, 'CACHE_LOGIN_PASSWORD_TTL': 60 * 60 * 24, @@ -280,6 +282,7 @@ class Config(dict): 'AUTH_LDAP_SYNC_INTERVAL': None, 'AUTH_LDAP_SYNC_CRONTAB': None, 'AUTH_LDAP_SYNC_ORG_IDS': ['00000000-0000-0000-0000-000000000002'], + 'AUTH_LDAP_SYNC_RECEIVERS': [], 'AUTH_LDAP_USER_LOGIN_ONLY_IN_USERS': False, 'AUTH_LDAP_OPTIONS_OPT_REFERRALS': -1, @@ -325,6 +328,7 @@ class Config(dict): 'RADIUS_SERVER': 'localhost', 'RADIUS_PORT': 1812, 'RADIUS_SECRET': '', + 'RADIUS_ATTRIBUTES': {}, 'RADIUS_ENCRYPT_PASSWORD': True, 'OTP_IN_RADIUS': False, @@ -451,6 +455,7 @@ class Config(dict): 'CUSTOM_SMS_REQUEST_METHOD': 'get', # Email + 'EMAIL_PROTOCOL': 'smtp', 'EMAIL_CUSTOM_USER_CREATED_SUBJECT': _('Create account successfully'), 'EMAIL_CUSTOM_USER_CREATED_HONORIFIC': _('Hello'), 'EMAIL_CUSTOM_USER_CREATED_BODY': _('Your account has been created successfully'), @@ -531,6 +536,7 @@ class Config(dict): 'SYSLOG_SOCKTYPE': 2, 'PERM_EXPIRED_CHECK_PERIODIC': 60 * 60, + 'PERM_TREE_REGEN_INTERVAL': 1, 'FLOWER_URL': "127.0.0.1:5555", 'LANGUAGE_CODE': 'zh', 'TIME_ZONE': 'Asia/Shanghai', @@ -693,6 +699,13 @@ class Config(dict): if openid_config: self.set_openid_config(openid_config) + def compatible_redis(self): + redis_config = { + 'REDIS_PASSWORD': quote(str(self.REDIS_PASSWORD)), + } + for key, value in redis_config.items(): + self[key] = value + def compatible(self): """ 对配置做兼容处理 @@ -704,6 +717,8 @@ class Config(dict): """ # 兼容 OpenID 配置 self.compatible_auth_openid() + # 兼容 Redis 配置 + self.compatible_redis() def convert_type(self, k, v): default_value = self.defaults.get(k) diff --git a/apps/jumpserver/rewriting/exchange.py b/apps/jumpserver/rewriting/exchange.py new file mode 100644 index 000000000..709e5558f --- /dev/null +++ b/apps/jumpserver/rewriting/exchange.py @@ -0,0 +1,104 @@ +import urllib3 + +from urllib3.exceptions import InsecureRequestWarning + +from django.core.mail.backends.base import BaseEmailBackend +from django.core.mail.message import sanitize_address +from django.conf import settings +from exchangelib import Account, Credentials, Configuration, DELEGATE +from exchangelib import Mailbox, Message, HTMLBody, FileAttachment +from exchangelib import BaseProtocol, NoVerifyHTTPAdapter +from exchangelib.errors import TransportError + + +urllib3.disable_warnings(InsecureRequestWarning) +BaseProtocol.HTTP_ADAPTER_CLS = NoVerifyHTTPAdapter + + +class EmailBackend(BaseEmailBackend): + def __init__( + self, + service_endpoint=None, + username=None, + password=None, + fail_silently=False, + **kwargs, + ): + super().__init__(fail_silently=fail_silently) + self.service_endpoint = service_endpoint or settings.EMAIL_HOST + self.username = settings.EMAIL_HOST_USER if username is None else username + self.password = settings.EMAIL_HOST_PASSWORD if password is None else password + self._connection = None + + def open(self): + if self._connection: + return False + + try: + config = Configuration( + service_endpoint=self.service_endpoint, credentials=Credentials( + username=self.username, password=self.password + ) + ) + self._connection = Account(self.username, config=config, access_type=DELEGATE) + return True + except TransportError: + if not self.fail_silently: + raise + + def close(self): + self._connection = None + + def send_messages(self, email_messages): + if not email_messages: + return 0 + + new_conn_created = self.open() + if not self._connection or new_conn_created is None: + return 0 + num_sent = 0 + for message in email_messages: + sent = self._send(message) + if sent: + num_sent += 1 + if new_conn_created: + self.close() + return num_sent + + def _send(self, email_message): + if not email_message.recipients(): + return False + + encoding = settings.DEFAULT_CHARSET + from_email = sanitize_address(email_message.from_email, encoding) + recipients = [ + Mailbox(email_address=sanitize_address(addr, encoding)) for addr in email_message.recipients() + ] + try: + message_body = email_message.body + alternatives = email_message.alternatives or [] + attachments = [] + for attachment in email_message.attachments or []: + name, content, mimetype = attachment + if isinstance(content, str): + content = content.encode(encoding) + attachments.append( + FileAttachment(name=name, content=content, content_type=mimetype) + ) + for alternative in alternatives: + if alternative[1] == 'text/html': + message_body = HTMLBody(alternative[0]) + break + + email_message = Message( + account=self._connection, subject=email_message.subject, + body=message_body, to_recipients=recipients, sender=from_email, + attachments=[] + ) + email_message.attach(attachments) + email_message.send_and_save() + except Exception as error: + if not self.fail_silently: + raise error + return False + return True diff --git a/apps/jumpserver/rewriting/storage/servers.py b/apps/jumpserver/rewriting/storage/servers.py new file mode 100644 index 000000000..5fc4b0514 --- /dev/null +++ b/apps/jumpserver/rewriting/storage/servers.py @@ -0,0 +1,14 @@ +from private_storage.servers import NginxXAccelRedirectServer, DjangoServer + + +class StaticFileServer(object): + + @staticmethod + def serve(private_file): + full_path = private_file.full_path + # todo: gzip 文件录像 nginx 处理后,浏览器无法正常解析内容 + # 造成在线播放失败,暂时仅使用 nginx 处理 mp4 录像文件 + if full_path.endswith('.mp4'): + return NginxXAccelRedirectServer.serve(private_file) + else: + return DjangoServer.serve(private_file) diff --git a/apps/jumpserver/settings/auth.py b/apps/jumpserver/settings/auth.py index 94c45b135..5e44a22a4 100644 --- a/apps/jumpserver/settings/auth.py +++ b/apps/jumpserver/settings/auth.py @@ -50,6 +50,7 @@ AUTH_LDAP_SYNC_IS_PERIODIC = CONFIG.AUTH_LDAP_SYNC_IS_PERIODIC AUTH_LDAP_SYNC_INTERVAL = CONFIG.AUTH_LDAP_SYNC_INTERVAL AUTH_LDAP_SYNC_CRONTAB = CONFIG.AUTH_LDAP_SYNC_CRONTAB AUTH_LDAP_SYNC_ORG_IDS = CONFIG.AUTH_LDAP_SYNC_ORG_IDS +AUTH_LDAP_SYNC_RECEIVERS = CONFIG.AUTH_LDAP_SYNC_RECEIVERS AUTH_LDAP_USER_LOGIN_ONLY_IN_USERS = CONFIG.AUTH_LDAP_USER_LOGIN_ONLY_IN_USERS # ============================================================================== @@ -99,6 +100,8 @@ AUTH_RADIUS_BACKEND = 'authentication.backends.radius.RadiusBackend' RADIUS_SERVER = CONFIG.RADIUS_SERVER RADIUS_PORT = CONFIG.RADIUS_PORT RADIUS_SECRET = CONFIG.RADIUS_SECRET +# https://github.com/robgolding/django-radius/blob/develop/radiusauth/backends/radius.py#L15-L52 +RADIUS_ATTRIBUTES = CONFIG.RADIUS_ATTRIBUTES # CAS Auth AUTH_CAS = CONFIG.AUTH_CAS @@ -190,6 +193,8 @@ VAULT_HCP_HOST = CONFIG.VAULT_HCP_HOST VAULT_HCP_TOKEN = CONFIG.VAULT_HCP_TOKEN VAULT_HCP_MOUNT_POINT = CONFIG.VAULT_HCP_MOUNT_POINT +HISTORY_ACCOUNT_CLEAN_LIMIT = CONFIG.HISTORY_ACCOUNT_CLEAN_LIMIT + # Other setting # 这个是 User Login Private Token TOKEN_EXPIRATION = CONFIG.TOKEN_EXPIRATION diff --git a/apps/jumpserver/settings/base.py b/apps/jumpserver/settings/base.py index e2bfbc5c1..10188a1a7 100644 --- a/apps/jumpserver/settings/base.py +++ b/apps/jumpserver/settings/base.py @@ -312,12 +312,15 @@ STATICFILES_DIRS = ( os.path.join(BASE_DIR, "static"), ) -# Media files (File, ImageField) will be save these +# Media files (File, ImageField) will be safe these MEDIA_URL = '/media/' MEDIA_ROOT = os.path.join(PROJECT_DIR, 'data', 'media').replace('\\', '/') + '/' PRIVATE_STORAGE_ROOT = MEDIA_ROOT PRIVATE_STORAGE_AUTH_FUNCTION = 'jumpserver.rewriting.storage.permissions.allow_access' +PRIVATE_STORAGE_INTERNAL_URL = '/private-media/' +PRIVATE_STORAGE_SERVER = 'jumpserver.rewriting.storage.servers.StaticFileServer' + # Use django-bootstrap-form to format template, input max width arg # BOOTSTRAP_COLUMN_COUNT = 11 @@ -326,6 +329,7 @@ PRIVATE_STORAGE_AUTH_FUNCTION = 'jumpserver.rewriting.storage.permissions.allow_ FIXTURE_DIRS = [os.path.join(BASE_DIR, 'fixtures'), ] # Email config +EMAIL_PROTOCOL = CONFIG.EMAIL_PROTOCOL EMAIL_HOST = CONFIG.EMAIL_HOST EMAIL_PORT = CONFIG.EMAIL_PORT EMAIL_HOST_USER = CONFIG.EMAIL_HOST_USER diff --git a/apps/jumpserver/settings/custom.py b/apps/jumpserver/settings/custom.py index fad5f0e9d..311e54aa8 100644 --- a/apps/jumpserver/settings/custom.py +++ b/apps/jumpserver/settings/custom.py @@ -208,6 +208,7 @@ OPERATE_LOG_ELASTICSEARCH_CONFIG = CONFIG.OPERATE_LOG_ELASTICSEARCH_CONFIG MAX_LIMIT_PER_PAGE = CONFIG.MAX_LIMIT_PER_PAGE DEFAULT_PAGE_SIZE = CONFIG.DEFAULT_PAGE_SIZE +PERM_TREE_REGEN_INTERVAL = CONFIG.PERM_TREE_REGEN_INTERVAL # Magnus DB Port MAGNUS_ORACLE_PORTS = CONFIG.MAGNUS_ORACLE_PORTS diff --git a/apps/jumpserver/settings/logging.py b/apps/jumpserver/settings/logging.py index c4cf90ebb..bd44e22dc 100644 --- a/apps/jumpserver/settings/logging.py +++ b/apps/jumpserver/settings/logging.py @@ -21,7 +21,7 @@ LOGGING = { }, 'main': { 'datefmt': '%Y-%m-%d %H:%M:%S', - 'format': '%(asctime)s [%(module)s %(levelname)s] %(message)s', + 'format': '%(asctime)s [%(levelname).4s] %(message)s', }, 'exception': { 'datefmt': '%Y-%m-%d %H:%M:%S', diff --git a/apps/labels/api.py b/apps/labels/api.py index 44a6702e7..1c6965a43 100644 --- a/apps/labels/api.py +++ b/apps/labels/api.py @@ -73,7 +73,7 @@ class LabelContentTypeResourceViewSet(JMSModelViewSet): queryset = model.objects.all() if bound == '1': queryset = queryset.filter(id__in=list(res_ids)) - elif bound == '0': + else: queryset = queryset.exclude(id__in=list(res_ids)) keyword = self.request.query_params.get('search') if keyword: @@ -90,9 +90,10 @@ class LabelContentTypeResourceViewSet(JMSModelViewSet): LabeledResource.objects \ .filter(res_type=content_type, label=label) \ .exclude(res_id__in=res_ids).delete() - resources = [] - for res_id in res_ids: - resources.append(LabeledResource(res_type=content_type, res_id=res_id, label=label, org_id=current_org.id)) + resources = [ + LabeledResource(res_type=content_type, res_id=res_id, label=label, org_id=current_org.id) + for res_id in res_ids + ] LabeledResource.objects.bulk_create(resources, ignore_conflicts=True) return Response({"total": len(res_ids)}) @@ -129,15 +130,22 @@ class LabeledResourceViewSet(OrgBulkModelViewSet): } ordering_fields = ('res_type', 'date_created') - # Todo: 这里需要优化,查询 sql 太多 def filter_search(self, queryset): keyword = self.request.query_params.get('search') if not keyword: return queryset + keyword = keyword.strip().lower() matched = [] - for instance in queryset: - if keyword.lower() in str(instance.resource).lower(): - matched.append(instance.id) + offset = 0 + limit = 10000 + while True: + page = queryset[offset:offset + limit] + if not page: + break + offset += limit + for instance in page: + if keyword in str(instance.resource).lower(): + matched.append(instance.id) return queryset.filter(id__in=matched) def get_queryset(self): diff --git a/apps/labels/mixins.py b/apps/labels/mixins.py index 90b76f3ed..4b775cde5 100644 --- a/apps/labels/mixins.py +++ b/apps/labels/mixins.py @@ -1,21 +1,38 @@ from django.contrib.contenttypes.fields import GenericRelation from django.db import models +from django.db.models import OneToOneField +from common.utils import lazyproperty from .models import LabeledResource __all__ = ['LabeledMixin'] class LabeledMixin(models.Model): - _labels = GenericRelation(LabeledResource, object_id_field='res_id', content_type_field='res_type') + labels = GenericRelation(LabeledResource, object_id_field='res_id', content_type_field='res_type') class Meta: abstract = True - @property - def labels(self): - return self._labels + @classmethod + def label_model(cls): + pk_field = cls._meta.pk + model = cls + if isinstance(pk_field, OneToOneField): + model = pk_field.related_model + return model - @labels.setter - def labels(self, value): - self._labels.set(value, bulk=False) + @lazyproperty + def real(self): + pk_field = self._meta.pk + if isinstance(pk_field, OneToOneField): + return getattr(self, pk_field.name) + return self + + @property + def res_labels(self): + return self.real.labels + + @res_labels.setter + def res_labels(self, value): + self.real.labels.set(value, bulk=False) diff --git a/apps/locale/ja/LC_MESSAGES/django.mo b/apps/locale/ja/LC_MESSAGES/django.mo index 50e4479af..0f74a7c63 100644 --- a/apps/locale/ja/LC_MESSAGES/django.mo +++ b/apps/locale/ja/LC_MESSAGES/django.mo @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:71d292647cf751c002b459449c7bebf4d2bf5a3933748387e7c2f80a7111302e -size 169602 +oid sha256:7879f4eeb499e920ad6c4bfdb0b1f334936ca344c275be056f12fcf7485f2bf6 +size 170948 diff --git a/apps/locale/ja/LC_MESSAGES/django.po b/apps/locale/ja/LC_MESSAGES/django.po index 92d6c4552..c6a6dfe37 100644 --- a/apps/locale/ja/LC_MESSAGES/django.po +++ b/apps/locale/ja/LC_MESSAGES/django.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2023-12-26 14:13+0800\n" +"POT-Creation-Date: 2024-01-17 19:11+0800\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -29,8 +29,9 @@ msgstr "パラメータ 'action' は [{}] でなければなりません。" #: authentication/confirm/password.py:26 authentication/forms.py:32 #: authentication/templates/authentication/login.html:330 #: settings/serializers/auth/ldap.py:25 settings/serializers/auth/ldap.py:47 -#: terminal/serializers/storage.py:123 terminal/serializers/storage.py:142 -#: users/forms/profile.py:22 users/serializers/user.py:104 +#: settings/serializers/msg.py:35 terminal/serializers/storage.py:123 +#: terminal/serializers/storage.py:142 users/forms/profile.py:22 +#: users/serializers/user.py:104 #: users/templates/users/_msg_user_created.html:13 #: users/templates/users/user_password_verify.html:18 #: xpack/plugins/cloud/serializers/account_attrs.py:28 @@ -115,8 +116,8 @@ msgstr "パスワードを変更する" msgid "Verify account" msgstr "アカウントを確認" -#: accounts/const/automation.py:27 accounts/tasks/remove_account.py:14 -#: accounts/tasks/remove_account.py:23 +#: accounts/const/automation.py:27 accounts/tasks/remove_account.py:24 +#: accounts/tasks/remove_account.py:33 msgid "Remove account" msgstr "アカウントの削除" @@ -200,10 +201,10 @@ msgstr "作成のみ" #: authentication/serializers/password_mfa.py:16 #: authentication/serializers/password_mfa.py:24 #: notifications/backends/__init__.py:10 settings/serializers/msg.py:22 -#: settings/serializers/msg.py:57 users/forms/profile.py:102 +#: settings/serializers/msg.py:64 users/forms/profile.py:102 #: users/forms/profile.py:109 users/models/user.py:802 #: users/templates/users/forgot_password.html:117 -#: users/views/profile/reset.py:92 +#: users/views/profile/reset.py:93 msgid "Email" msgstr "メール" @@ -248,8 +249,7 @@ msgstr "ユーザー %s がパスワードを閲覧/導き出しました" #: accounts/templates/accounts/asset_account_change_info.html:7 #: acls/serializers/base.py:123 assets/models/asset/common.py:95 #: assets/models/asset/common.py:350 assets/models/cmd_filter.py:36 -#: assets/serializers/domain.py:20 audits/models.py:58 -#: authentication/models/connection_token.py:36 +#: audits/models.py:58 authentication/models/connection_token.py:36 #: perms/models/asset_permission.py:69 perms/serializers/permission.py:36 #: terminal/backends/command/models.py:17 terminal/models/session/session.py:31 #: terminal/notifications.py:155 terminal/serializers/command.py:17 @@ -288,11 +288,11 @@ msgstr "ソース ID" #: accounts/serializers/automations/change_secret.py:107 #: accounts/serializers/automations/change_secret.py:127 #: acls/serializers/base.py:124 acls/templates/acls/asset_login_reminder.html:7 -#: assets/serializers/asset/common.py:125 assets/serializers/gateway.py:28 +#: assets/serializers/asset/common.py:128 assets/serializers/gateway.py:28 #: audits/models.py:59 authentication/api/connection_token.py:405 #: ops/models/base.py:18 perms/models/asset_permission.py:75 -#: perms/serializers/permission.py:41 terminal/backends/command/models.py:18 -#: terminal/models/session/session.py:33 +#: perms/serializers/permission.py:41 settings/serializers/msg.py:33 +#: terminal/backends/command/models.py:18 terminal/models/session/session.py:33 #: terminal/templates/terminal/_msg_command_warning.html:8 #: terminal/templates/terminal/_msg_session_sharing.html:8 #: tickets/models/ticket/command_confirm.py:13 xpack/plugins/cloud/models.py:89 @@ -362,8 +362,9 @@ msgstr "アカウントバックアップ計画" #: assets/models/automations/base.py:115 audits/models.py:65 #: ops/models/base.py:55 ops/models/celery.py:63 ops/models/job.py:235 #: ops/templates/ops/celery_task_log.html:75 -#: perms/models/asset_permission.py:78 terminal/models/applet/host.py:141 -#: terminal/models/session/session.py:44 +#: perms/models/asset_permission.py:78 +#: settings/templates/ldap/_msg_import_ldap_user.html:5 +#: terminal/models/applet/host.py:141 terminal/models/session/session.py:44 #: tickets/models/ticket/apply_application.py:30 #: tickets/models/ticket/apply_asset.py:19 msgid "Date start" @@ -372,6 +373,7 @@ msgstr "開始日" #: accounts/models/automations/backup_account.py:122 #: authentication/templates/authentication/_msg_oauth_bind.html:11 #: notifications/notifications.py:186 +#: settings/templates/ldap/_msg_import_ldap_user.html:3 msgid "Time" msgstr "時間" @@ -447,6 +449,7 @@ msgstr "SSHキープッシュ方式" #: accounts/models/automations/gather_account.py:58 #: accounts/serializers/account/backup.py:41 #: accounts/serializers/automations/change_secret.py:56 +#: settings/serializers/auth/ldap.py:81 msgid "Recipient" msgstr "受信者" @@ -492,6 +495,7 @@ msgstr "ステータス" #: authentication/templates/authentication/passkey.html:173 #: authentication/views/base.py:42 authentication/views/base.py:43 #: authentication/views/base.py:44 common/const/choices.py:20 +#: settings/templates/ldap/_msg_import_ldap_user.html:22 msgid "Error" msgstr "間違い" @@ -510,9 +514,8 @@ msgstr "最終ログイン日" #: accounts/models/automations/gather_account.py:17 #: accounts/models/automations/push_account.py:15 accounts/models/base.py:65 #: accounts/serializers/account/virtual.py:21 acls/serializers/base.py:19 -#: acls/serializers/base.py:50 acls/templates/acls/asset_login_reminder.html:5 -#: acls/templates/acls/user_login_reminder.html:5 assets/models/_user.py:23 -#: audits/models.py:188 authentication/forms.py:25 authentication/forms.py:27 +#: acls/serializers/base.py:50 assets/models/_user.py:23 audits/models.py:188 +#: authentication/forms.py:25 authentication/forms.py:27 #: authentication/models/temp_token.py:9 #: authentication/templates/authentication/_msg_different_city.html:9 #: authentication/templates/authentication/_msg_oauth_bind.html:9 @@ -595,8 +598,8 @@ msgstr "パスワードルール" #: assets/models/asset/common.py:159 assets/models/cmd_filter.py:21 #: assets/models/domain.py:19 assets/models/group.py:17 #: assets/models/label.py:18 assets/models/platform.py:16 -#: assets/models/platform.py:95 assets/serializers/asset/common.py:146 -#: assets/serializers/platform.py:118 assets/serializers/platform.py:235 +#: assets/models/platform.py:95 assets/serializers/asset/common.py:149 +#: assets/serializers/platform.py:118 assets/serializers/platform.py:228 #: authentication/backends/passkey/models.py:10 #: authentication/serializers/connect_token_secret.py:113 #: authentication/serializers/connect_token_secret.py:168 labels/models.py:11 @@ -604,7 +607,7 @@ msgstr "パスワードルール" #: ops/models/celery.py:57 ops/models/job.py:136 ops/models/playbook.py:28 #: ops/serializers/job.py:18 orgs/models.py:82 #: perms/models/asset_permission.py:61 rbac/models/role.py:29 -#: settings/models.py:33 settings/models.py:181 settings/serializers/msg.py:82 +#: settings/models.py:33 settings/models.py:181 settings/serializers/msg.py:89 #: terminal/models/applet/applet.py:33 terminal/models/component/endpoint.py:12 #: terminal/models/component/endpoint.py:95 #: terminal/models/component/storage.py:26 terminal/models/component/task.py:13 @@ -740,8 +743,8 @@ msgstr "アカウントの存在ポリシー" #: accounts/serializers/account/account.py:193 applications/models.py:11 #: assets/models/label.py:21 assets/models/platform.py:96 -#: assets/serializers/asset/common.py:122 assets/serializers/cagegory.py:12 -#: assets/serializers/platform.py:140 assets/serializers/platform.py:236 +#: assets/serializers/asset/common.py:125 assets/serializers/cagegory.py:12 +#: assets/serializers/platform.py:140 assets/serializers/platform.py:229 #: perms/serializers/user_permission.py:26 settings/models.py:35 #: tickets/models/ticket/apply_application.py:13 users/models/preference.py:12 msgid "Category" @@ -752,7 +755,7 @@ msgstr "カテゴリ" #: acls/serializers/command_acl.py:19 applications/models.py:14 #: assets/models/_user.py:50 assets/models/automations/base.py:20 #: assets/models/cmd_filter.py:74 assets/models/platform.py:97 -#: assets/serializers/asset/common.py:123 assets/serializers/platform.py:120 +#: assets/serializers/asset/common.py:126 assets/serializers/platform.py:120 #: assets/serializers/platform.py:139 audits/serializers.py:53 #: audits/serializers.py:170 #: authentication/serializers/connect_token_secret.py:126 ops/models/job.py:144 @@ -813,11 +816,13 @@ msgstr "アカウントはすでに存在しています" #: accounts/serializers/account/account.py:441 #: authentication/serializers/connect_token_secret.py:159 #: authentication/templates/authentication/_access_key_modal.html:30 -#: perms/models/perm_node.py:21 users/serializers/group.py:32 +#: perms/models/perm_node.py:21 users/serializers/group.py:33 msgid "ID" msgstr "ID" #: accounts/serializers/account/account.py:451 acls/serializers/base.py:116 +#: acls/templates/acls/asset_login_reminder.html:5 +#: acls/templates/acls/user_login_reminder.html:5 #: assets/models/cmd_filter.py:24 assets/models/label.py:16 audits/models.py:54 #: audits/models.py:90 audits/models.py:172 audits/models.py:269 #: audits/serializers.py:171 authentication/models/connection_token.py:32 @@ -831,8 +836,8 @@ msgstr "ID" #: terminal/notifications.py:205 terminal/serializers/command.py:16 #: terminal/templates/terminal/_msg_command_warning.html:6 #: terminal/templates/terminal/_msg_session_sharing.html:6 -#: tickets/models/comment.py:21 users/const.py:14 users/models/user.py:1003 -#: users/models/user.py:1040 users/serializers/group.py:19 +#: tickets/models/comment.py:21 users/const.py:14 users/models/user.py:1004 +#: users/models/user.py:1041 users/serializers/group.py:21 msgid "User" msgstr "ユーザー" @@ -868,7 +873,7 @@ msgid "Key password" msgstr "キーパスワード" #: accounts/serializers/account/base.py:78 -#: assets/serializers/asset/common.py:379 +#: assets/serializers/asset/common.py:384 msgid "Spec info" msgstr "特別情報" @@ -984,17 +989,17 @@ msgstr "自動タスク実行履歴" msgid "Success" msgstr "成功" -#: accounts/signal_handlers.py:46 +#: accounts/signal_handlers.py:47 #, python-format msgid "Push related accounts to assets: %s, by system" msgstr "関連するアカウントをアセットにプッシュ: %s, by system" -#: accounts/signal_handlers.py:55 +#: accounts/signal_handlers.py:56 #, python-format msgid "Add account: %s" msgstr "アカウントを追加: %s" -#: accounts/signal_handlers.py:57 +#: accounts/signal_handlers.py:58 #, python-format msgid "Delete account: %s" msgstr "アカウントを削除: %s" @@ -1019,6 +1024,14 @@ msgstr "資産の口座番号を収集する" msgid "Push accounts to assets" msgstr "アカウントをアセットにプッシュ:" +#: accounts/tasks/remove_account.py:44 +msgid "Clean historical accounts" +msgstr "過去のアカウントをクリアする" + +#: accounts/tasks/remove_account.py:76 +msgid "Remove historical accounts that are out of range." +msgstr "範囲外の履歴アカウントを削除する" + #: accounts/tasks/template.py:11 msgid "Template sync info to related accounts" msgstr "関連するアカウントへの情報の同期" @@ -1109,8 +1122,8 @@ msgid "Users" msgstr "ユーザー" #: acls/models/base.py:98 assets/models/automations/base.py:17 -#: assets/models/cmd_filter.py:38 assets/serializers/asset/common.py:378 -#: perms/serializers/user_permission.py:75 rbac/tree.py:35 +#: assets/models/cmd_filter.py:38 perms/serializers/user_permission.py:75 +#: rbac/tree.py:35 msgid "Accounts" msgstr "アカウント" @@ -1191,7 +1204,7 @@ msgstr "ログインasset acl" msgid "Login asset confirm" msgstr "ログイン資産の確認" -#: acls/notifications.py:11 +#: acls/notifications.py:12 msgid "User login reminder" msgstr "ユーザーログインのリマインダ" @@ -1312,13 +1325,13 @@ msgstr "アプリケーション" msgid "Can match application" msgstr "アプリケーションを一致させることができます" -#: assets/api/asset/asset.py:182 +#: assets/api/asset/asset.py:179 msgid "Cannot create asset directly, you should create a host or other" msgstr "" "資産を直接作成することはできません。ホストまたはその他を作成する必要がありま" "す" -#: assets/api/domain.py:63 +#: assets/api/domain.py:64 msgid "Number required" msgstr "必要な数" @@ -1415,8 +1428,8 @@ msgstr "脚本" #: assets/const/category.py:10 assets/models/asset/host.py:8 #: settings/serializers/auth/radius.py:16 settings/serializers/auth/sms.py:71 -#: settings/serializers/feature.py:49 terminal/models/component/endpoint.py:13 -#: terminal/serializers/applet.py:17 +#: settings/serializers/feature.py:49 settings/serializers/msg.py:31 +#: terminal/models/component/endpoint.py:13 terminal/serializers/applet.py:17 #: xpack/plugins/cloud/serializers/account_attrs.py:72 msgid "Host" msgstr "ホスト" @@ -1540,7 +1553,7 @@ msgid "We will consider login success when we see this prompt" msgstr "このプロンプトが表示されたらログイン成功とみなします" #: assets/const/protocol.py:119 assets/models/asset/database.py:10 -#: settings/serializers/msg.py:40 +#: settings/serializers/msg.py:47 msgid "Use SSL" msgstr "SSLの使用" @@ -1617,7 +1630,7 @@ msgstr "SSHパブリックキー" #: assets/models/_user.py:28 assets/models/automations/base.py:114 #: assets/models/cmd_filter.py:41 assets/models/group.py:19 #: audits/models.py:267 common/db/models.py:34 ops/models/base.py:54 -#: ops/models/job.py:234 users/models/user.py:1041 +#: ops/models/job.py:234 users/models/user.py:1042 msgid "Date created" msgstr "作成された日付" @@ -1629,7 +1642,7 @@ msgstr "更新日" #: assets/models/_user.py:30 assets/models/cmd_filter.py:44 #: assets/models/cmd_filter.py:91 assets/models/group.py:18 #: common/db/models.py:32 users/models/user.py:843 -#: users/serializers/group.py:30 +#: users/serializers/group.py:32 msgid "Created by" msgstr "によって作成された" @@ -1655,7 +1668,7 @@ msgstr "ユーザーと同じユーザー名" #: assets/models/_user.py:52 authentication/models/connection_token.py:41 #: authentication/serializers/connect_token_secret.py:114 -#: terminal/models/applet/applet.py:42 +#: settings/serializers/msg.py:29 terminal/models/applet/applet.py:42 #: terminal/models/virtualapp/virtualapp.py:24 #: terminal/serializers/session.py:19 terminal/serializers/session.py:45 #: terminal/serializers/storage.py:71 @@ -1708,12 +1721,12 @@ msgstr "クラウド サービス" #: assets/models/asset/common.py:94 assets/models/platform.py:17 #: settings/serializers/auth/radius.py:17 settings/serializers/auth/sms.py:72 -#: terminal/serializers/storage.py:133 +#: settings/serializers/msg.py:32 terminal/serializers/storage.py:133 #: xpack/plugins/cloud/serializers/account_attrs.py:73 msgid "Port" msgstr "ポート" -#: assets/models/asset/common.py:160 assets/serializers/asset/common.py:147 +#: assets/models/asset/common.py:160 assets/serializers/asset/common.py:150 msgid "Address" msgstr "アドレス" @@ -1731,13 +1744,13 @@ msgid "Domain" msgstr "ドメイン" #: assets/models/asset/common.py:165 assets/models/automations/base.py:18 -#: assets/models/cmd_filter.py:32 assets/models/node.py:553 +#: assets/models/cmd_filter.py:32 assets/models/node.py:546 #: perms/models/asset_permission.py:72 perms/serializers/permission.py:37 #: tickets/models/ticket/apply_asset.py:14 xpack/plugins/cloud/models.py:330 msgid "Node" msgstr "ノード" -#: assets/models/asset/common.py:167 assets/serializers/asset/common.py:380 +#: assets/models/asset/common.py:167 assets/serializers/asset/common.py:385 #: assets/serializers/asset/host.py:11 msgid "Gathered info" msgstr "資産ハードウェア情報の収集" @@ -1782,7 +1795,7 @@ msgstr "クライアントキー" msgid "Allow invalid cert" msgstr "証明書チェックを無視" -#: assets/models/asset/gpt.py:8 settings/serializers/feature.py:73 +#: assets/models/asset/gpt.py:8 settings/serializers/feature.py:84 msgid "Proxy" msgstr "プロキシー" @@ -1849,7 +1862,7 @@ msgstr "コマンドフィルタルール" msgid "Favorite asset" msgstr "お気に入りのアセット" -#: assets/models/gateway.py:34 assets/serializers/domain.py:17 +#: assets/models/gateway.py:34 assets/serializers/domain.py:18 msgid "Gateway" msgstr "ゲートウェイ" @@ -1867,11 +1880,11 @@ msgstr "デフォルト" msgid "Default asset group" msgstr "デフォルトアセットグループ" -#: assets/models/label.py:15 rbac/const.py:6 users/models/user.py:1026 +#: assets/models/label.py:15 rbac/const.py:6 users/models/user.py:1027 msgid "System" msgstr "システム" -#: assets/models/label.py:19 assets/models/node.py:539 +#: assets/models/label.py:19 assets/models/node.py:532 #: assets/serializers/cagegory.py:11 assets/serializers/cagegory.py:18 #: assets/serializers/cagegory.py:24 #: authentication/models/connection_token.py:29 @@ -1886,7 +1899,7 @@ msgstr "値" #: assets/serializers/platform.py:119 #: authentication/serializers/connect_token_secret.py:124 #: common/serializers/common.py:85 labels/models.py:17 labels/models.py:33 -#: labels/serializers.py:45 settings/serializers/msg.py:83 +#: labels/serializers.py:45 settings/serializers/msg.py:90 msgid "Label" msgstr "ラベル" @@ -1894,23 +1907,23 @@ msgstr "ラベル" msgid "New node" msgstr "新しいノード" -#: assets/models/node.py:467 audits/backends/db.py:65 audits/backends/db.py:66 +#: assets/models/node.py:460 audits/backends/db.py:65 audits/backends/db.py:66 msgid "empty" msgstr "空" -#: assets/models/node.py:538 perms/models/perm_node.py:28 +#: assets/models/node.py:531 perms/models/perm_node.py:28 msgid "Key" msgstr "キー" -#: assets/models/node.py:540 assets/serializers/node.py:20 +#: assets/models/node.py:533 assets/serializers/node.py:20 msgid "Full value" msgstr "フルバリュー" -#: assets/models/node.py:544 perms/models/perm_node.py:30 +#: assets/models/node.py:537 perms/models/perm_node.py:30 msgid "Parent key" msgstr "親キー" -#: assets/models/node.py:556 +#: assets/models/node.py:549 msgid "Can match node" msgstr "ノードを一致させることができます" @@ -2057,7 +2070,7 @@ msgstr "" "プラットフォームタイプがスキップされた資産に合致しない、資産内の一括更新プ" "ラットフォーム" -#: assets/serializers/asset/common.py:124 assets/serializers/platform.py:141 +#: assets/serializers/asset/common.py:127 assets/serializers/platform.py:141 #: authentication/serializers/connect_token_secret.py:30 #: authentication/serializers/connect_token_secret.py:75 #: perms/models/asset_permission.py:76 perms/serializers/permission.py:42 @@ -2066,29 +2079,29 @@ msgstr "" msgid "Protocols" msgstr "プロトコル" -#: assets/serializers/asset/common.py:126 -#: assets/serializers/asset/common.py:148 +#: assets/serializers/asset/common.py:129 +#: assets/serializers/asset/common.py:151 msgid "Node path" msgstr "ノードパスです" -#: assets/serializers/asset/common.py:145 -#: assets/serializers/asset/common.py:381 +#: assets/serializers/asset/common.py:148 +#: assets/serializers/asset/common.py:386 msgid "Auto info" msgstr "自動情報" -#: assets/serializers/asset/common.py:239 +#: assets/serializers/asset/common.py:245 msgid "Platform not exist" msgstr "プラットフォームが存在しません" -#: assets/serializers/asset/common.py:275 +#: assets/serializers/asset/common.py:281 msgid "port out of range (0-65535)" msgstr "ポート番号が範囲外です (0-65535)" -#: assets/serializers/asset/common.py:282 +#: assets/serializers/asset/common.py:288 msgid "Protocol is required: {}" msgstr "プロトコルが必要です: {}" -#: assets/serializers/asset/common.py:310 +#: assets/serializers/asset/common.py:316 msgid "Invalid data" msgstr "無効なデータ" @@ -2170,6 +2183,10 @@ msgstr "制約" msgid "Types" msgstr "タイプ" +#: assets/serializers/domain.py:53 perms/serializers/permission.py:188 +msgid "Assets amount" +msgstr "資産数量" + #: assets/serializers/gateway.py:23 common/validators.py:34 msgid "This field must be unique." msgstr "このフィールドは一意である必要があります。" @@ -2239,7 +2256,7 @@ msgstr "デフォルト ドメイン" msgid "type is required" msgstr "タイプ このフィールドは必須です." -#: assets/serializers/platform.py:211 +#: assets/serializers/platform.py:204 msgid "Protocols is required" msgstr "同意が必要です" @@ -2631,9 +2648,9 @@ msgstr "仮パスワード" msgid "Passkey" msgstr "Passkey" -#: audits/tasks.py:101 users/signal_handlers.py:166 +#: audits/tasks.py:101 msgid "Clean audits session task log" -msgstr "監査セッション タスク ログのクリーンアップ" +msgstr "資産監査セッションタスクログのクリーンアップ" #: audits/tasks.py:114 msgid "Upload FTP file to external storage" @@ -2682,16 +2699,16 @@ msgstr "ACL アクションはレビューです" msgid "Current user not support mfa type: {}" msgstr "現在のユーザーはmfaタイプをサポートしていません: {}" -#: authentication/api/password.py:34 terminal/api/session/session.py:305 -#: users/views/profile/reset.py:61 +#: authentication/api/password.py:33 terminal/api/session/session.py:305 +#: users/views/profile/reset.py:62 msgid "User does not exist: {}" msgstr "ユーザーが存在しない: {}" -#: authentication/api/password.py:34 users/views/profile/reset.py:163 +#: authentication/api/password.py:33 users/views/profile/reset.py:163 msgid "No user matched" msgstr "ユーザーにマッチしなかった" -#: authentication/api/password.py:38 +#: authentication/api/password.py:37 msgid "" "The user is from {}, please go to the corresponding system to change the " "password" @@ -2699,7 +2716,7 @@ msgstr "" "ユーザーは {}からです。対応するシステムにアクセスしてパスワードを変更してくだ" "さい。" -#: authentication/api/password.py:67 +#: authentication/api/password.py:65 #: authentication/templates/authentication/login.html:361 #: users/templates/users/forgot_password.html:27 #: users/templates/users/forgot_password.html:28 @@ -3019,7 +3036,7 @@ msgstr "メッセージ検証コードが無効" #: authentication/serializers/password_mfa.py:24 #: settings/serializers/auth/sms.py:32 users/forms/profile.py:104 #: users/forms/profile.py:109 users/templates/users/forgot_password.html:112 -#: users/views/profile/reset.py:98 +#: users/views/profile/reset.py:99 msgid "SMS" msgstr "メッセージ" @@ -3035,7 +3052,7 @@ msgstr "電話番号を設定して有効にする" msgid "Clear phone number to disable" msgstr "無効にする電話番号をクリアする" -#: authentication/middleware.py:94 settings/utils/ldap.py:677 +#: authentication/middleware.py:94 settings/utils/ldap.py:679 msgid "Authentication failed (before login check failed): {}" msgstr "認証に失敗しました (ログインチェックが失敗する前): {}" @@ -3297,7 +3314,7 @@ msgstr "コードエラー" #: authentication/templates/authentication/_msg_reset_password_code.html:9 #: authentication/templates/authentication/_msg_rest_password_success.html:2 #: authentication/templates/authentication/_msg_rest_public_key_success.html:2 -#: jumpserver/conf.py:455 +#: jumpserver/conf.py:460 #: perms/templates/perms/_msg_item_permissions_expire.html:3 #: perms/templates/perms/_msg_permed_items_expire.html:3 #: tickets/templates/tickets/approve_check_password.html:32 @@ -3469,7 +3486,7 @@ msgstr "" msgid "Do you want to retry ?" msgstr "再試行しますか?" -#: authentication/utils.py:23 common/utils/ip/geoip/utils.py:24 +#: authentication/utils.py:24 common/utils/ip/geoip/utils.py:24 #: xpack/plugins/cloud/const.py:32 msgid "LAN" msgstr "ローカルエリアネットワーク" @@ -3806,7 +3823,7 @@ msgstr "サポートされていません Elasticsearch8" msgid "Network error, please contact system administrator" msgstr "ネットワークエラー、システム管理者に連絡してください" -#: common/sdk/im/slack/__init__.py:79 +#: common/sdk/im/slack/__init__.py:77 msgid "Unknown error occur" msgstr "不明なエラーが発生しました" @@ -3901,15 +3918,15 @@ msgstr "無効なオプション: {}" msgid "Labels" msgstr "ラベル" -#: common/tasks.py:21 common/utils/verify_code.py:16 +#: common/tasks.py:31 common/utils/verify_code.py:16 msgid "Send email" msgstr "メールを送る" -#: common/tasks.py:48 +#: common/tasks.py:58 msgid "Send email attachment" msgstr "メールの添付ファイルを送信" -#: common/tasks.py:69 terminal/tasks.py:62 +#: common/tasks.py:80 terminal/tasks.py:62 msgid "Upload session replay to external storage" msgstr "セッションの記録を外部ストレージにアップロードする" @@ -3938,16 +3955,16 @@ msgstr "特殊文字を含むべきではない" msgid "The mobile phone number format is incorrect" msgstr "携帯電話番号の形式が正しくありません" -#: jumpserver/conf.py:450 +#: jumpserver/conf.py:454 #, python-brace-format msgid "The verification code is: {code}" msgstr "認証コードは: {code}" -#: jumpserver/conf.py:454 +#: jumpserver/conf.py:459 msgid "Create account successfully" msgstr "アカウントを正常に作成" -#: jumpserver/conf.py:456 +#: jumpserver/conf.py:461 msgid "Your account has been created successfully" msgstr "アカウントが正常に作成されました" @@ -4370,6 +4387,7 @@ msgid "Is finished" msgstr "終了しました" #: ops/serializers/job.py:66 +#: settings/templates/ldap/_msg_import_ldap_user.html:7 msgid "Time cost" msgstr "時を過ごす" @@ -4587,7 +4605,7 @@ msgid "today" msgstr "今日" #: perms/notifications.py:12 perms/notifications.py:44 -#: settings/serializers/feature.py:106 +#: settings/serializers/feature.py:117 msgid "day" msgstr "日" @@ -4607,6 +4625,19 @@ msgstr "資産権限の有効期限が近づいています" msgid "asset permissions of organization {}" msgstr "組織 {} の資産権限" +#: perms/serializers/permission.py:186 rbac/serializers/role.py:27 +#: users/serializers/group.py:54 users/serializers/group.py:60 +msgid "Users amount" +msgstr "ユーザー数" + +#: perms/serializers/permission.py:187 +msgid "User groups amount" +msgstr "ユーザーグループの数" + +#: perms/serializers/permission.py:189 +msgid "Nodes amount" +msgstr "ノード数" + #: perms/tasks.py:27 msgid "Check asset permission expired" msgstr "アセット認証ルールの有効期限が切れていることを確認する" @@ -4748,10 +4779,6 @@ msgstr "システムロールバインディング" msgid "Perms" msgstr "パーマ" -#: rbac/serializers/role.py:27 users/serializers/group.py:31 -msgid "Users amount" -msgstr "ユーザー数" - #: rbac/serializers/role.py:28 terminal/models/applet/applet.py:34 #: terminal/models/virtualapp/virtualapp.py:20 msgid "Display name" @@ -4823,7 +4850,7 @@ msgstr "リモートアプリケーション" msgid "Ticket comment" msgstr "チケットコメント" -#: rbac/tree.py:130 settings/serializers/feature.py:98 +#: rbac/tree.py:130 settings/serializers/feature.py:109 #: tickets/models/ticket/general.py:307 msgid "Ticket" msgstr "チケット" @@ -4846,7 +4873,7 @@ msgstr "チャットAIがオンになっていない" msgid "Test success" msgstr "テストの成功" -#: settings/api/email.py:21 +#: settings/api/email.py:22 msgid "Test mail sent to {}, please check" msgstr "{}に送信されたテストメールを確認してください" @@ -4949,6 +4976,10 @@ msgstr "他の設定を変えることができます" msgid "Chat prompt" msgstr "チャットのヒント" +#: settings/notifications.py:23 +msgid "Notification of Synchronized LDAP User Task Results" +msgstr "LDAPユーザータスクの結果通知を同期する" + #: settings/serializers/auth/base.py:12 msgid "LDAP Auth" msgstr "LDAP 認証" @@ -5104,7 +5135,7 @@ msgstr "接続タイムアウト (秒)" msgid "Search paged size (piece)" msgstr "ページサイズを検索 (じょう)" -#: settings/serializers/auth/ldap.py:81 +#: settings/serializers/auth/ldap.py:84 msgid "Enable LDAP auth" msgstr "LDAP認証の有効化" @@ -5321,7 +5352,7 @@ msgstr "認証コード長" #: settings/serializers/auth/sms.py:27 settings/serializers/auth/sms.py:49 #: settings/serializers/auth/sms.py:57 settings/serializers/auth/sms.py:66 -#: settings/serializers/auth/sms.py:77 settings/serializers/msg.py:76 +#: settings/serializers/auth/sms.py:77 settings/serializers/msg.py:83 msgid "Signature" msgstr "署名" @@ -5525,62 +5556,77 @@ msgid "Mount Point" msgstr "マウントポイント" #: settings/serializers/feature.py:60 +msgid "Historical accounts retained count" +msgstr "保持されている過去のアカウントの数" + +#: settings/serializers/feature.py:62 +msgid "" +"If the specific value is less than 999, the system will automatically " +"perform a task every night: check and delete historical accounts that exceed " +"the predetermined number. If the value reaches or exceeds 999, no historical " +"account deletion will be performed." +msgstr "" +"特定の値が 999 未満の場合、システムは毎晩自動的にタスクを実行します。つまり、" +"所定の数を超える履歴アカウントを確認して削除します。 値が 999 以上の場合、履" +"歴アカウントの削除は実行されません。" + +#: settings/serializers/feature.py:71 msgid "Chat AI" msgstr "チャットAI" -#: settings/serializers/feature.py:64 +#: settings/serializers/feature.py:75 msgid "Enable Chat AI" msgstr "チャットAIを起動する" -#: settings/serializers/feature.py:67 +#: settings/serializers/feature.py:78 msgid "Base Url" msgstr "基本的なUrl" -#: settings/serializers/feature.py:70 templates/_header_bar.html:90 +#: settings/serializers/feature.py:81 templates/_header_bar.html:90 msgid "API Key" msgstr "API Key" -#: settings/serializers/feature.py:76 +#: settings/serializers/feature.py:87 msgid "GPT Model" msgstr "GPTモデル" -#: settings/serializers/feature.py:100 +#: settings/serializers/feature.py:111 msgid "Enable tickets" msgstr "チケットを有効にする" -#: settings/serializers/feature.py:103 +#: settings/serializers/feature.py:114 msgid "Ticket authorize default time" msgstr "デフォルト製造オーダ承認時間" -#: settings/serializers/feature.py:106 +#: settings/serializers/feature.py:117 msgid "hour" msgstr "時" -#: settings/serializers/feature.py:107 +#: settings/serializers/feature.py:118 msgid "Ticket authorize default time unit" msgstr "デフォルト製造オーダ承認時間単位" -#: settings/serializers/feature.py:112 +#: settings/serializers/feature.py:123 msgid "Feature" msgstr "機能" -#: settings/serializers/feature.py:115 +#: settings/serializers/feature.py:126 msgid "Operation center" msgstr "職業センター" -#: settings/serializers/feature.py:116 +#: settings/serializers/feature.py:127 msgid "Allow user run batch command or not using ansible" msgstr "ユーザー実行バッチコマンドを許可するか、ansibleを使用しない" -#: settings/serializers/feature.py:120 +#: settings/serializers/feature.py:131 msgid "Operation center command blacklist" msgstr "オペレーション センター コマンド ブラックリスト" -#: settings/serializers/feature.py:121 +#: settings/serializers/feature.py:132 msgid "Commands that are not allowed execute." msgstr "実行が許可されていないコマンド" -#: settings/serializers/feature.py:126 +#: settings/serializers/feature.py:137 #: terminal/models/virtualapp/provider.py:17 #: terminal/models/virtualapp/virtualapp.py:36 #: terminal/models/virtualapp/virtualapp.py:97 @@ -5588,78 +5634,70 @@ msgstr "実行が許可されていないコマンド" msgid "Virtual app" msgstr "仮想アプリケーション" -#: settings/serializers/feature.py:129 +#: settings/serializers/feature.py:140 msgid "Enable virtual app" msgstr "仮想アプリケーションの有効化" -#: settings/serializers/msg.py:24 -msgid "SMTP host" -msgstr "SMTPホスト" - #: settings/serializers/msg.py:25 -msgid "SMTP port" -msgstr "SMTPポート" +msgid "SMTP" +msgstr "SMTP" #: settings/serializers/msg.py:26 -msgid "SMTP account" -msgstr "SMTPアカウント" +msgid "EXCHANGE" +msgstr "" -#: settings/serializers/msg.py:28 -msgid "SMTP password" -msgstr "SMTPパスワード" - -#: settings/serializers/msg.py:29 +#: settings/serializers/msg.py:36 msgid "Tips: Some provider use token except password" msgstr "ヒント: 一部のプロバイダーはパスワード以外のトークンを使用します" -#: settings/serializers/msg.py:32 +#: settings/serializers/msg.py:39 msgid "Send user" msgstr "ユーザーを送信" -#: settings/serializers/msg.py:33 +#: settings/serializers/msg.py:40 msgid "Tips: Send mail account, default SMTP account as the send account" msgstr "" "ヒント: 送信メールアカウント、送信アカウントとしてのデフォルトのSMTPアカウン" "ト" -#: settings/serializers/msg.py:36 +#: settings/serializers/msg.py:43 msgid "Test recipient" msgstr "テスト受信者" -#: settings/serializers/msg.py:37 +#: settings/serializers/msg.py:44 msgid "Tips: Used only as a test mail recipient" msgstr "ヒント: テストメールの受信者としてのみ使用" -#: settings/serializers/msg.py:41 +#: settings/serializers/msg.py:48 msgid "If SMTP port is 465, may be select" msgstr "SMTPポートが465の場合は、" -#: settings/serializers/msg.py:44 +#: settings/serializers/msg.py:51 msgid "Use TLS" msgstr "TLSの使用" -#: settings/serializers/msg.py:45 +#: settings/serializers/msg.py:52 msgid "If SMTP port is 587, may be select" msgstr "SMTPポートが587の場合は、" -#: settings/serializers/msg.py:48 +#: settings/serializers/msg.py:55 msgid "Subject prefix" msgstr "件名プレフィックス" -#: settings/serializers/msg.py:51 +#: settings/serializers/msg.py:58 msgid "Email suffix" msgstr "メールのサフィックス" -#: settings/serializers/msg.py:52 +#: settings/serializers/msg.py:59 msgid "" "This is used by default if no email is returned during SSO authentication" msgstr "これは、SSO認証中にメールが返されない場合にデフォルトで使用されます。" -#: settings/serializers/msg.py:61 +#: settings/serializers/msg.py:68 msgid "Create user email subject" msgstr "ユーザーメール件名の作成" -#: settings/serializers/msg.py:62 +#: settings/serializers/msg.py:69 msgid "" "Tips: When creating a user, send the subject of the email (eg:Create account " "successfully)" @@ -5667,20 +5705,20 @@ msgstr "" "ヒント: ユーザーを作成するときに、メールの件名を送信します (例: アカウントを" "正常に作成)" -#: settings/serializers/msg.py:66 +#: settings/serializers/msg.py:73 msgid "Create user honorific" msgstr "ユーザー敬語の作成" -#: settings/serializers/msg.py:67 +#: settings/serializers/msg.py:74 msgid "Tips: When creating a user, send the honorific of the email (eg:Hello)" msgstr "" "ヒント: ユーザーを作成するときは、メールの敬語を送信します (例: こんにちは)" -#: settings/serializers/msg.py:71 +#: settings/serializers/msg.py:78 msgid "Create user email content" msgstr "ユーザーのメールコンテンツを作成する" -#: settings/serializers/msg.py:73 +#: settings/serializers/msg.py:80 #, python-brace-format msgid "" "Tips: When creating a user, send the content of the email, support " @@ -5689,7 +5727,7 @@ msgstr "" "ヒント:ユーザーの作成時にパスワード設定メールの内容を送信し、{username}{name}" "{email}ラベルをサポートします。" -#: settings/serializers/msg.py:77 +#: settings/serializers/msg.py:84 msgid "Tips: Email signature (eg:jumpserver)" msgstr "ヒント: メール署名 (例: jumpserver)" @@ -6049,112 +6087,129 @@ msgstr "Razor の有効化" msgid "Enable SSH Client" msgstr "SSH Clientの有効化" -#: settings/tasks/ldap.py:24 +#: settings/tasks/ldap.py:28 msgid "Periodic import ldap user" msgstr "LDAP ユーザーを定期的にインポートする" -#: settings/tasks/ldap.py:45 +#: settings/tasks/ldap.py:66 msgid "Registration periodic import ldap user task" msgstr "登録サイクルLDAPユーザータスクのインポート" -#: settings/utils/ldap.py:492 +#: settings/templates/ldap/_msg_import_ldap_user.html:2 +msgid "Sync task Finish" +msgstr "同期タスクが完了しました" + +#: settings/templates/ldap/_msg_import_ldap_user.html:6 +#: terminal/models/session/session.py:45 +msgid "Date end" +msgstr "終了日" + +#: settings/templates/ldap/_msg_import_ldap_user.html:9 +msgid "Synced Organization" +msgstr "組織が同期されました" + +#: settings/templates/ldap/_msg_import_ldap_user.html:15 +msgid "Synced User" +msgstr "同期されたユーザー" + +#: settings/utils/ldap.py:494 msgid "ldap:// or ldaps:// protocol is used." msgstr "ldap:// または ldaps:// プロトコルが使用されます。" -#: settings/utils/ldap.py:503 +#: settings/utils/ldap.py:505 msgid "Host or port is disconnected: {}" msgstr "ホストまたはポートが切断されました: {}" -#: settings/utils/ldap.py:505 +#: settings/utils/ldap.py:507 msgid "The port is not the port of the LDAP service: {}" msgstr "ポートはLDAPサービスのポートではありません: {}" -#: settings/utils/ldap.py:507 +#: settings/utils/ldap.py:509 msgid "Please add certificate: {}" msgstr "証明書を追加してください: {}" -#: settings/utils/ldap.py:511 settings/utils/ldap.py:538 -#: settings/utils/ldap.py:568 settings/utils/ldap.py:596 +#: settings/utils/ldap.py:513 settings/utils/ldap.py:540 +#: settings/utils/ldap.py:570 settings/utils/ldap.py:598 msgid "Unknown error: {}" msgstr "不明なエラー: {}" -#: settings/utils/ldap.py:525 +#: settings/utils/ldap.py:527 msgid "Bind DN or Password incorrect" msgstr "DNまたはパスワードのバインドが正しくありません" -#: settings/utils/ldap.py:532 +#: settings/utils/ldap.py:534 msgid "Please enter Bind DN: {}" msgstr "バインドDN: {} を入力してください" -#: settings/utils/ldap.py:534 +#: settings/utils/ldap.py:536 msgid "Please enter Password: {}" msgstr "パスワードを入力してください: {}" -#: settings/utils/ldap.py:536 +#: settings/utils/ldap.py:538 msgid "Please enter correct Bind DN and Password: {}" msgstr "正しいバインドDNとパスワードを入力してください: {}" -#: settings/utils/ldap.py:554 +#: settings/utils/ldap.py:556 msgid "Invalid User OU or User search filter: {}" msgstr "無効なユーザー OU またはユーザー検索フィルター: {}" -#: settings/utils/ldap.py:585 +#: settings/utils/ldap.py:587 msgid "LDAP User attr map not include: {}" msgstr "LDAP ユーザーattrマップは含まれません: {}" -#: settings/utils/ldap.py:592 +#: settings/utils/ldap.py:594 msgid "LDAP User attr map is not dict" msgstr "LDAPユーザーattrマップはdictではありません" -#: settings/utils/ldap.py:611 +#: settings/utils/ldap.py:613 msgid "LDAP authentication is not enabled" msgstr "LDAP 認証が有効になっていない" -#: settings/utils/ldap.py:629 +#: settings/utils/ldap.py:631 msgid "Error (Invalid LDAP server): {}" msgstr "エラー (LDAPサーバーが無効): {}" -#: settings/utils/ldap.py:631 +#: settings/utils/ldap.py:633 msgid "Error (Invalid Bind DN): {}" msgstr "エラー (DNのバインドが無効): {}" -#: settings/utils/ldap.py:633 +#: settings/utils/ldap.py:635 msgid "Error (Invalid LDAP User attr map): {}" msgstr "エラー (LDAPユーザーattrマップが無効): {}" -#: settings/utils/ldap.py:635 +#: settings/utils/ldap.py:637 msgid "Error (Invalid User OU or User search filter): {}" msgstr "エラー (ユーザーOUまたはユーザー検索フィルターが無効): {}" -#: settings/utils/ldap.py:637 +#: settings/utils/ldap.py:639 msgid "Error (Not enabled LDAP authentication): {}" msgstr "エラー (LDAP認証が有効化されていません): {}" -#: settings/utils/ldap.py:639 +#: settings/utils/ldap.py:641 msgid "Error (Unknown): {}" msgstr "エラー (不明): {}" -#: settings/utils/ldap.py:642 +#: settings/utils/ldap.py:644 msgid "Succeed: Match {} s user" msgstr "成功: {} 人のユーザーに一致" -#: settings/utils/ldap.py:653 +#: settings/utils/ldap.py:655 msgid "Please test the connection first" msgstr "まず接続をテストしてください" -#: settings/utils/ldap.py:675 +#: settings/utils/ldap.py:677 msgid "Authentication failed (configuration incorrect): {}" msgstr "認証に失敗しました (設定が正しくありません): {}" -#: settings/utils/ldap.py:679 +#: settings/utils/ldap.py:681 msgid "Authentication failed (username or password incorrect): {}" msgstr "認証に失敗しました (ユーザー名またはパスワードが正しくありません): {}" -#: settings/utils/ldap.py:681 +#: settings/utils/ldap.py:683 msgid "Authentication failed (Unknown): {}" msgstr "認証に失敗しました (不明): {}" -#: settings/utils/ldap.py:684 +#: settings/utils/ldap.py:686 msgid "Authentication success: {}" msgstr "認証成功: {}" @@ -6767,10 +6822,6 @@ msgstr "ログイン元" msgid "Replay" msgstr "リプレイ" -#: terminal/models/session/session.py:45 -msgid "Date end" -msgstr "終了日" - #: terminal/models/session/session.py:47 terminal/serializers/session.py:65 msgid "Command amount" msgstr "コマンド量" @@ -7806,31 +7857,31 @@ msgstr "更新パスワードが必要" msgid "Date api key used" msgstr "Api key 最後に使用した日付" -#: users/models/user.py:984 +#: users/models/user.py:985 msgid "Can not delete admin user" msgstr "管理者ユーザーを削除できませんでした" -#: users/models/user.py:1011 +#: users/models/user.py:1012 msgid "Can invite user" msgstr "ユーザーを招待できます" -#: users/models/user.py:1012 +#: users/models/user.py:1013 msgid "Can remove user" msgstr "ユーザーを削除できます" -#: users/models/user.py:1013 +#: users/models/user.py:1014 msgid "Can match user" msgstr "ユーザーに一致できます" -#: users/models/user.py:1022 +#: users/models/user.py:1023 msgid "Administrator" msgstr "管理者" -#: users/models/user.py:1025 +#: users/models/user.py:1026 msgid "Administrator is the super user of system" msgstr "管理者はシステムのスーパーユーザーです" -#: users/models/user.py:1050 +#: users/models/user.py:1051 msgid "User password history" msgstr "ユーザーパスワード履歴" @@ -8025,6 +8076,10 @@ msgstr "" "管理者は「既存のユーザーのみログインを許可」をオンにしており、現在のユーザー" "はユーザーリストにありません。管理者に連絡してください。" +#: users/signal_handlers.py:166 +msgid "Clean up expired user sessions" +msgstr "期限切れのユーザー・セッションのパージ" + #: users/tasks.py:25 msgid "Check password expired" msgstr "パスワードの有効期限が切れていることを確認する" @@ -8279,7 +8334,7 @@ msgstr "OTP無効化成功、ログインページを返す" msgid "Password invalid" msgstr "パスワード無効" -#: users/views/profile/reset.py:64 +#: users/views/profile/reset.py:65 msgid "" "Non-local users can log in only from third-party platforms and cannot change " "their passwords: {}" @@ -9006,6 +9061,15 @@ msgstr "エンタープライズプロフェッショナル版" msgid "Ultimate edition" msgstr "エンタープライズ・フラッグシップ・エディション" +#~ msgid "SMTP port" +#~ msgstr "SMTPポート" + +#~ msgid "SMTP account" +#~ msgstr "SMTPアカウント" + +#~ msgid "SMTP password" +#~ msgstr "SMTPパスワード" + #~ msgid "Password can not contains `{{` or `}}`" #~ msgstr "パスワードには `{` または `}` 文字を含めることはできません" diff --git a/apps/locale/zh/LC_MESSAGES/django.mo b/apps/locale/zh/LC_MESSAGES/django.mo index 1fe3d019d..bf09fbd89 100644 --- a/apps/locale/zh/LC_MESSAGES/django.mo +++ b/apps/locale/zh/LC_MESSAGES/django.mo @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:80dd11dde678e4f9b64df18906175125218fd9f719bfe9aaa667ad6e2d055d40 -size 139012 +oid sha256:19d3a111cc245f9a9d36b860fd95447df916ad66c918bef672bacdad6bc77a8f +size 140119 diff --git a/apps/locale/zh/LC_MESSAGES/django.po b/apps/locale/zh/LC_MESSAGES/django.po index 472fb7b2e..73f1032a6 100644 --- a/apps/locale/zh/LC_MESSAGES/django.po +++ b/apps/locale/zh/LC_MESSAGES/django.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: JumpServer 0.3.3\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2023-12-26 14:13+0800\n" +"POT-Creation-Date: 2024-01-17 19:11+0800\n" "PO-Revision-Date: 2021-05-20 10:54+0800\n" "Last-Translator: ibuler \n" "Language-Team: JumpServer team\n" @@ -28,8 +28,9 @@ msgstr "参数 'action' 必须是 [{}]" #: authentication/confirm/password.py:26 authentication/forms.py:32 #: authentication/templates/authentication/login.html:330 #: settings/serializers/auth/ldap.py:25 settings/serializers/auth/ldap.py:47 -#: terminal/serializers/storage.py:123 terminal/serializers/storage.py:142 -#: users/forms/profile.py:22 users/serializers/user.py:104 +#: settings/serializers/msg.py:35 terminal/serializers/storage.py:123 +#: terminal/serializers/storage.py:142 users/forms/profile.py:22 +#: users/serializers/user.py:104 #: users/templates/users/_msg_user_created.html:13 #: users/templates/users/user_password_verify.html:18 #: xpack/plugins/cloud/serializers/account_attrs.py:28 @@ -114,8 +115,8 @@ msgstr "更改密码" msgid "Verify account" msgstr "验证账号" -#: accounts/const/automation.py:27 accounts/tasks/remove_account.py:14 -#: accounts/tasks/remove_account.py:23 +#: accounts/const/automation.py:27 accounts/tasks/remove_account.py:24 +#: accounts/tasks/remove_account.py:33 msgid "Remove account" msgstr "移除账号" @@ -199,10 +200,10 @@ msgstr "仅创建" #: authentication/serializers/password_mfa.py:16 #: authentication/serializers/password_mfa.py:24 #: notifications/backends/__init__.py:10 settings/serializers/msg.py:22 -#: settings/serializers/msg.py:57 users/forms/profile.py:102 +#: settings/serializers/msg.py:64 users/forms/profile.py:102 #: users/forms/profile.py:109 users/models/user.py:802 #: users/templates/users/forgot_password.html:117 -#: users/views/profile/reset.py:92 +#: users/views/profile/reset.py:93 msgid "Email" msgstr "邮箱" @@ -247,8 +248,7 @@ msgstr "用户 %s 查看/导出 了密码" #: accounts/templates/accounts/asset_account_change_info.html:7 #: acls/serializers/base.py:123 assets/models/asset/common.py:95 #: assets/models/asset/common.py:350 assets/models/cmd_filter.py:36 -#: assets/serializers/domain.py:20 audits/models.py:58 -#: authentication/models/connection_token.py:36 +#: audits/models.py:58 authentication/models/connection_token.py:36 #: perms/models/asset_permission.py:69 perms/serializers/permission.py:36 #: terminal/backends/command/models.py:17 terminal/models/session/session.py:31 #: terminal/notifications.py:155 terminal/serializers/command.py:17 @@ -287,11 +287,11 @@ msgstr "来源 ID" #: accounts/serializers/automations/change_secret.py:107 #: accounts/serializers/automations/change_secret.py:127 #: acls/serializers/base.py:124 acls/templates/acls/asset_login_reminder.html:7 -#: assets/serializers/asset/common.py:125 assets/serializers/gateway.py:28 +#: assets/serializers/asset/common.py:128 assets/serializers/gateway.py:28 #: audits/models.py:59 authentication/api/connection_token.py:405 #: ops/models/base.py:18 perms/models/asset_permission.py:75 -#: perms/serializers/permission.py:41 terminal/backends/command/models.py:18 -#: terminal/models/session/session.py:33 +#: perms/serializers/permission.py:41 settings/serializers/msg.py:33 +#: terminal/backends/command/models.py:18 terminal/models/session/session.py:33 #: terminal/templates/terminal/_msg_command_warning.html:8 #: terminal/templates/terminal/_msg_session_sharing.html:8 #: tickets/models/ticket/command_confirm.py:13 xpack/plugins/cloud/models.py:89 @@ -361,8 +361,9 @@ msgstr "账号备份计划" #: assets/models/automations/base.py:115 audits/models.py:65 #: ops/models/base.py:55 ops/models/celery.py:63 ops/models/job.py:235 #: ops/templates/ops/celery_task_log.html:75 -#: perms/models/asset_permission.py:78 terminal/models/applet/host.py:141 -#: terminal/models/session/session.py:44 +#: perms/models/asset_permission.py:78 +#: settings/templates/ldap/_msg_import_ldap_user.html:5 +#: terminal/models/applet/host.py:141 terminal/models/session/session.py:44 #: tickets/models/ticket/apply_application.py:30 #: tickets/models/ticket/apply_asset.py:19 msgid "Date start" @@ -371,6 +372,7 @@ msgstr "开始日期" #: accounts/models/automations/backup_account.py:122 #: authentication/templates/authentication/_msg_oauth_bind.html:11 #: notifications/notifications.py:186 +#: settings/templates/ldap/_msg_import_ldap_user.html:3 msgid "Time" msgstr "时间" @@ -446,6 +448,7 @@ msgstr "SSH 密钥推送方式" #: accounts/models/automations/gather_account.py:58 #: accounts/serializers/account/backup.py:41 #: accounts/serializers/automations/change_secret.py:56 +#: settings/serializers/auth/ldap.py:81 msgid "Recipient" msgstr "收件人" @@ -491,6 +494,7 @@ msgstr "状态" #: authentication/templates/authentication/passkey.html:173 #: authentication/views/base.py:42 authentication/views/base.py:43 #: authentication/views/base.py:44 common/const/choices.py:20 +#: settings/templates/ldap/_msg_import_ldap_user.html:22 msgid "Error" msgstr "错误" @@ -509,9 +513,8 @@ msgstr "最后登录日期" #: accounts/models/automations/gather_account.py:17 #: accounts/models/automations/push_account.py:15 accounts/models/base.py:65 #: accounts/serializers/account/virtual.py:21 acls/serializers/base.py:19 -#: acls/serializers/base.py:50 acls/templates/acls/asset_login_reminder.html:5 -#: acls/templates/acls/user_login_reminder.html:5 assets/models/_user.py:23 -#: audits/models.py:188 authentication/forms.py:25 authentication/forms.py:27 +#: acls/serializers/base.py:50 assets/models/_user.py:23 audits/models.py:188 +#: authentication/forms.py:25 authentication/forms.py:27 #: authentication/models/temp_token.py:9 #: authentication/templates/authentication/_msg_different_city.html:9 #: authentication/templates/authentication/_msg_oauth_bind.html:9 @@ -594,8 +597,8 @@ msgstr "密码规则" #: assets/models/asset/common.py:159 assets/models/cmd_filter.py:21 #: assets/models/domain.py:19 assets/models/group.py:17 #: assets/models/label.py:18 assets/models/platform.py:16 -#: assets/models/platform.py:95 assets/serializers/asset/common.py:146 -#: assets/serializers/platform.py:118 assets/serializers/platform.py:235 +#: assets/models/platform.py:95 assets/serializers/asset/common.py:149 +#: assets/serializers/platform.py:118 assets/serializers/platform.py:228 #: authentication/backends/passkey/models.py:10 #: authentication/serializers/connect_token_secret.py:113 #: authentication/serializers/connect_token_secret.py:168 labels/models.py:11 @@ -603,7 +606,7 @@ msgstr "密码规则" #: ops/models/celery.py:57 ops/models/job.py:136 ops/models/playbook.py:28 #: ops/serializers/job.py:18 orgs/models.py:82 #: perms/models/asset_permission.py:61 rbac/models/role.py:29 -#: settings/models.py:33 settings/models.py:181 settings/serializers/msg.py:82 +#: settings/models.py:33 settings/models.py:181 settings/serializers/msg.py:89 #: terminal/models/applet/applet.py:33 terminal/models/component/endpoint.py:12 #: terminal/models/component/endpoint.py:95 #: terminal/models/component/storage.py:26 terminal/models/component/task.py:13 @@ -738,8 +741,8 @@ msgstr "账号存在策略" #: accounts/serializers/account/account.py:193 applications/models.py:11 #: assets/models/label.py:21 assets/models/platform.py:96 -#: assets/serializers/asset/common.py:122 assets/serializers/cagegory.py:12 -#: assets/serializers/platform.py:140 assets/serializers/platform.py:236 +#: assets/serializers/asset/common.py:125 assets/serializers/cagegory.py:12 +#: assets/serializers/platform.py:140 assets/serializers/platform.py:229 #: perms/serializers/user_permission.py:26 settings/models.py:35 #: tickets/models/ticket/apply_application.py:13 users/models/preference.py:12 msgid "Category" @@ -750,7 +753,7 @@ msgstr "类别" #: acls/serializers/command_acl.py:19 applications/models.py:14 #: assets/models/_user.py:50 assets/models/automations/base.py:20 #: assets/models/cmd_filter.py:74 assets/models/platform.py:97 -#: assets/serializers/asset/common.py:123 assets/serializers/platform.py:120 +#: assets/serializers/asset/common.py:126 assets/serializers/platform.py:120 #: assets/serializers/platform.py:139 audits/serializers.py:53 #: audits/serializers.py:170 #: authentication/serializers/connect_token_secret.py:126 ops/models/job.py:144 @@ -811,11 +814,13 @@ msgstr "账号已存在" #: accounts/serializers/account/account.py:441 #: authentication/serializers/connect_token_secret.py:159 #: authentication/templates/authentication/_access_key_modal.html:30 -#: perms/models/perm_node.py:21 users/serializers/group.py:32 +#: perms/models/perm_node.py:21 users/serializers/group.py:33 msgid "ID" msgstr "ID" #: accounts/serializers/account/account.py:451 acls/serializers/base.py:116 +#: acls/templates/acls/asset_login_reminder.html:5 +#: acls/templates/acls/user_login_reminder.html:5 #: assets/models/cmd_filter.py:24 assets/models/label.py:16 audits/models.py:54 #: audits/models.py:90 audits/models.py:172 audits/models.py:269 #: audits/serializers.py:171 authentication/models/connection_token.py:32 @@ -829,8 +834,8 @@ msgstr "ID" #: terminal/notifications.py:205 terminal/serializers/command.py:16 #: terminal/templates/terminal/_msg_command_warning.html:6 #: terminal/templates/terminal/_msg_session_sharing.html:6 -#: tickets/models/comment.py:21 users/const.py:14 users/models/user.py:1003 -#: users/models/user.py:1040 users/serializers/group.py:19 +#: tickets/models/comment.py:21 users/const.py:14 users/models/user.py:1004 +#: users/models/user.py:1041 users/serializers/group.py:21 msgid "User" msgstr "用户" @@ -866,7 +871,7 @@ msgid "Key password" msgstr "密钥密码" #: accounts/serializers/account/base.py:78 -#: assets/serializers/asset/common.py:379 +#: assets/serializers/asset/common.py:384 msgid "Spec info" msgstr "特殊信息" @@ -981,17 +986,17 @@ msgstr "自动化任务执行历史" msgid "Success" msgstr "成功" -#: accounts/signal_handlers.py:46 +#: accounts/signal_handlers.py:47 #, python-format msgid "Push related accounts to assets: %s, by system" msgstr "推送账号到资产: %s, 由系统执行" -#: accounts/signal_handlers.py:55 +#: accounts/signal_handlers.py:56 #, python-format msgid "Add account: %s" msgstr "添加账号: %s" -#: accounts/signal_handlers.py:57 +#: accounts/signal_handlers.py:58 #, python-format msgid "Delete account: %s" msgstr "删除账号: %s" @@ -1016,6 +1021,14 @@ msgstr "收集资产上的账号" msgid "Push accounts to assets" msgstr "推送账号到资产" +#: accounts/tasks/remove_account.py:44 +msgid "Clean historical accounts" +msgstr "清理历史账号" + +#: accounts/tasks/remove_account.py:76 +msgid "Remove historical accounts that are out of range." +msgstr "删除超出范围的历史帐户。" + #: accounts/tasks/template.py:11 msgid "Template sync info to related accounts" msgstr "同步信息到关联的账号" @@ -1105,8 +1118,8 @@ msgid "Users" msgstr "用户管理" #: acls/models/base.py:98 assets/models/automations/base.py:17 -#: assets/models/cmd_filter.py:38 assets/serializers/asset/common.py:378 -#: perms/serializers/user_permission.py:75 rbac/tree.py:35 +#: assets/models/cmd_filter.py:38 perms/serializers/user_permission.py:75 +#: rbac/tree.py:35 msgid "Accounts" msgstr "账号管理" @@ -1187,7 +1200,7 @@ msgstr "登录资产访问控制" msgid "Login asset confirm" msgstr "登录资产复核" -#: acls/notifications.py:11 +#: acls/notifications.py:12 msgid "User login reminder" msgstr "用户登录提醒" @@ -1306,11 +1319,11 @@ msgstr "应用程序" msgid "Can match application" msgstr "匹配应用" -#: assets/api/asset/asset.py:182 +#: assets/api/asset/asset.py:179 msgid "Cannot create asset directly, you should create a host or other" msgstr "不能直接创建资产, 你应该创建主机或其他资产" -#: assets/api/domain.py:63 +#: assets/api/domain.py:64 msgid "Number required" msgstr "需要为数字" @@ -1407,8 +1420,8 @@ msgstr "脚本" #: assets/const/category.py:10 assets/models/asset/host.py:8 #: settings/serializers/auth/radius.py:16 settings/serializers/auth/sms.py:71 -#: settings/serializers/feature.py:49 terminal/models/component/endpoint.py:13 -#: terminal/serializers/applet.py:17 +#: settings/serializers/feature.py:49 settings/serializers/msg.py:31 +#: terminal/models/component/endpoint.py:13 terminal/serializers/applet.py:17 #: xpack/plugins/cloud/serializers/account_attrs.py:72 msgid "Host" msgstr "主机" @@ -1531,7 +1544,7 @@ msgid "We will consider login success when we see this prompt" msgstr "当我们看到这个提示时,我们将认为登录成功" #: assets/const/protocol.py:119 assets/models/asset/database.py:10 -#: settings/serializers/msg.py:40 +#: settings/serializers/msg.py:47 msgid "Use SSL" msgstr "使用 SSL" @@ -1609,7 +1622,7 @@ msgstr "SSH公钥" #: assets/models/_user.py:28 assets/models/automations/base.py:114 #: assets/models/cmd_filter.py:41 assets/models/group.py:19 #: audits/models.py:267 common/db/models.py:34 ops/models/base.py:54 -#: ops/models/job.py:234 users/models/user.py:1041 +#: ops/models/job.py:234 users/models/user.py:1042 msgid "Date created" msgstr "创建日期" @@ -1621,7 +1634,7 @@ msgstr "更新日期" #: assets/models/_user.py:30 assets/models/cmd_filter.py:44 #: assets/models/cmd_filter.py:91 assets/models/group.py:18 #: common/db/models.py:32 users/models/user.py:843 -#: users/serializers/group.py:30 +#: users/serializers/group.py:32 msgid "Created by" msgstr "创建者" @@ -1647,7 +1660,7 @@ msgstr "用户名与用户相同" #: assets/models/_user.py:52 authentication/models/connection_token.py:41 #: authentication/serializers/connect_token_secret.py:114 -#: terminal/models/applet/applet.py:42 +#: settings/serializers/msg.py:29 terminal/models/applet/applet.py:42 #: terminal/models/virtualapp/virtualapp.py:24 #: terminal/serializers/session.py:19 terminal/serializers/session.py:45 #: terminal/serializers/storage.py:71 @@ -1700,12 +1713,12 @@ msgstr "云服务" #: assets/models/asset/common.py:94 assets/models/platform.py:17 #: settings/serializers/auth/radius.py:17 settings/serializers/auth/sms.py:72 -#: terminal/serializers/storage.py:133 +#: settings/serializers/msg.py:32 terminal/serializers/storage.py:133 #: xpack/plugins/cloud/serializers/account_attrs.py:73 msgid "Port" msgstr "端口" -#: assets/models/asset/common.py:160 assets/serializers/asset/common.py:147 +#: assets/models/asset/common.py:160 assets/serializers/asset/common.py:150 msgid "Address" msgstr "地址" @@ -1723,13 +1736,13 @@ msgid "Domain" msgstr "网域" #: assets/models/asset/common.py:165 assets/models/automations/base.py:18 -#: assets/models/cmd_filter.py:32 assets/models/node.py:553 +#: assets/models/cmd_filter.py:32 assets/models/node.py:546 #: perms/models/asset_permission.py:72 perms/serializers/permission.py:37 #: tickets/models/ticket/apply_asset.py:14 xpack/plugins/cloud/models.py:330 msgid "Node" msgstr "节点" -#: assets/models/asset/common.py:167 assets/serializers/asset/common.py:380 +#: assets/models/asset/common.py:167 assets/serializers/asset/common.py:385 #: assets/serializers/asset/host.py:11 msgid "Gathered info" msgstr "收集资产硬件信息" @@ -1774,7 +1787,7 @@ msgstr "客户端密钥" msgid "Allow invalid cert" msgstr "忽略证书校验" -#: assets/models/asset/gpt.py:8 settings/serializers/feature.py:73 +#: assets/models/asset/gpt.py:8 settings/serializers/feature.py:84 msgid "Proxy" msgstr "代理" @@ -1841,7 +1854,7 @@ msgstr "命令过滤规则" msgid "Favorite asset" msgstr "收藏的资产" -#: assets/models/gateway.py:34 assets/serializers/domain.py:17 +#: assets/models/gateway.py:34 assets/serializers/domain.py:18 msgid "Gateway" msgstr "网关" @@ -1859,11 +1872,11 @@ msgstr "默认" msgid "Default asset group" msgstr "默认资产组" -#: assets/models/label.py:15 rbac/const.py:6 users/models/user.py:1026 +#: assets/models/label.py:15 rbac/const.py:6 users/models/user.py:1027 msgid "System" msgstr "系统" -#: assets/models/label.py:19 assets/models/node.py:539 +#: assets/models/label.py:19 assets/models/node.py:532 #: assets/serializers/cagegory.py:11 assets/serializers/cagegory.py:18 #: assets/serializers/cagegory.py:24 #: authentication/models/connection_token.py:29 @@ -1878,7 +1891,7 @@ msgstr "值" #: assets/serializers/platform.py:119 #: authentication/serializers/connect_token_secret.py:124 #: common/serializers/common.py:85 labels/models.py:17 labels/models.py:33 -#: labels/serializers.py:45 settings/serializers/msg.py:83 +#: labels/serializers.py:45 settings/serializers/msg.py:90 msgid "Label" msgstr "标签" @@ -1886,23 +1899,23 @@ msgstr "标签" msgid "New node" msgstr "新节点" -#: assets/models/node.py:467 audits/backends/db.py:65 audits/backends/db.py:66 +#: assets/models/node.py:460 audits/backends/db.py:65 audits/backends/db.py:66 msgid "empty" msgstr "空" -#: assets/models/node.py:538 perms/models/perm_node.py:28 +#: assets/models/node.py:531 perms/models/perm_node.py:28 msgid "Key" msgstr "键" -#: assets/models/node.py:540 assets/serializers/node.py:20 +#: assets/models/node.py:533 assets/serializers/node.py:20 msgid "Full value" msgstr "全称" -#: assets/models/node.py:544 perms/models/perm_node.py:30 +#: assets/models/node.py:537 perms/models/perm_node.py:30 msgid "Parent key" msgstr "ssh私钥" -#: assets/models/node.py:556 +#: assets/models/node.py:549 msgid "Can match node" msgstr "可以匹配节点" @@ -2047,7 +2060,7 @@ msgid "" "type" msgstr "资产中批量更新平台,不符合平台类型跳过的资产" -#: assets/serializers/asset/common.py:124 assets/serializers/platform.py:141 +#: assets/serializers/asset/common.py:127 assets/serializers/platform.py:141 #: authentication/serializers/connect_token_secret.py:30 #: authentication/serializers/connect_token_secret.py:75 #: perms/models/asset_permission.py:76 perms/serializers/permission.py:42 @@ -2056,29 +2069,29 @@ msgstr "资产中批量更新平台,不符合平台类型跳过的资产" msgid "Protocols" msgstr "协议组" -#: assets/serializers/asset/common.py:126 -#: assets/serializers/asset/common.py:148 +#: assets/serializers/asset/common.py:129 +#: assets/serializers/asset/common.py:151 msgid "Node path" msgstr "节点路径" -#: assets/serializers/asset/common.py:145 -#: assets/serializers/asset/common.py:381 +#: assets/serializers/asset/common.py:148 +#: assets/serializers/asset/common.py:386 msgid "Auto info" msgstr "自动化信息" -#: assets/serializers/asset/common.py:239 +#: assets/serializers/asset/common.py:245 msgid "Platform not exist" msgstr "平台不存在" -#: assets/serializers/asset/common.py:275 +#: assets/serializers/asset/common.py:281 msgid "port out of range (0-65535)" msgstr "端口超出范围 (0-65535)" -#: assets/serializers/asset/common.py:282 +#: assets/serializers/asset/common.py:288 msgid "Protocol is required: {}" msgstr "协议是必填的: {}" -#: assets/serializers/asset/common.py:310 +#: assets/serializers/asset/common.py:316 msgid "Invalid data" msgstr "无效的数据" @@ -2160,6 +2173,10 @@ msgstr "约束" msgid "Types" msgstr "类型" +#: assets/serializers/domain.py:53 perms/serializers/permission.py:188 +msgid "Assets amount" +msgstr "资产数量" + #: assets/serializers/gateway.py:23 common/validators.py:34 msgid "This field must be unique." msgstr "字段必须唯一" @@ -2224,7 +2241,7 @@ msgstr "默认网域" msgid "type is required" msgstr "类型 该字段是必填项。" -#: assets/serializers/platform.py:211 +#: assets/serializers/platform.py:204 msgid "Protocols is required" msgstr "协议是必填的" @@ -2614,9 +2631,9 @@ msgstr "临时密码" msgid "Passkey" msgstr "Passkey" -#: audits/tasks.py:101 users/signal_handlers.py:166 +#: audits/tasks.py:101 msgid "Clean audits session task log" -msgstr "清理审计会话任务日志" +msgstr "清理资产审计会话任务日志" #: audits/tasks.py:114 msgid "Upload FTP file to external storage" @@ -2663,22 +2680,22 @@ msgstr "ACL 动作是复核" msgid "Current user not support mfa type: {}" msgstr "当前用户不支持 MFA 类型: {}" -#: authentication/api/password.py:34 terminal/api/session/session.py:305 -#: users/views/profile/reset.py:61 +#: authentication/api/password.py:33 terminal/api/session/session.py:305 +#: users/views/profile/reset.py:62 msgid "User does not exist: {}" msgstr "用户不存在: {}" -#: authentication/api/password.py:34 users/views/profile/reset.py:163 +#: authentication/api/password.py:33 users/views/profile/reset.py:163 msgid "No user matched" msgstr "没有匹配到用户" -#: authentication/api/password.py:38 +#: authentication/api/password.py:37 msgid "" "The user is from {}, please go to the corresponding system to change the " "password" msgstr "用户来自 {} 请去相应系统修改密码" -#: authentication/api/password.py:67 +#: authentication/api/password.py:65 #: authentication/templates/authentication/login.html:361 #: users/templates/users/forgot_password.html:27 #: users/templates/users/forgot_password.html:28 @@ -2989,7 +3006,7 @@ msgstr "短信验证码校验失败" #: authentication/serializers/password_mfa.py:24 #: settings/serializers/auth/sms.py:32 users/forms/profile.py:104 #: users/forms/profile.py:109 users/templates/users/forgot_password.html:112 -#: users/views/profile/reset.py:98 +#: users/views/profile/reset.py:99 msgid "SMS" msgstr "短信" @@ -3005,7 +3022,7 @@ msgstr "设置手机号码启用" msgid "Clear phone number to disable" msgstr "清空手机号码禁用" -#: authentication/middleware.py:94 settings/utils/ldap.py:677 +#: authentication/middleware.py:94 settings/utils/ldap.py:679 msgid "Authentication failed (before login check failed): {}" msgstr "认证失败 (登录前检查失败): {}" @@ -3265,7 +3282,7 @@ msgstr "代码错误" #: authentication/templates/authentication/_msg_reset_password_code.html:9 #: authentication/templates/authentication/_msg_rest_password_success.html:2 #: authentication/templates/authentication/_msg_rest_public_key_success.html:2 -#: jumpserver/conf.py:455 +#: jumpserver/conf.py:460 #: perms/templates/perms/_msg_item_permissions_expire.html:3 #: perms/templates/perms/_msg_permed_items_expire.html:3 #: tickets/templates/tickets/approve_check_password.html:32 @@ -3425,7 +3442,7 @@ msgstr "本页面未使用 HTTPS 协议,请使用 HTTPS 协议以确保您的 msgid "Do you want to retry ?" msgstr "是否重试 ?" -#: authentication/utils.py:23 common/utils/ip/geoip/utils.py:24 +#: authentication/utils.py:24 common/utils/ip/geoip/utils.py:24 #: xpack/plugins/cloud/const.py:32 msgid "LAN" msgstr "局域网" @@ -3760,7 +3777,7 @@ msgstr "不支持 Elasticsearch8" msgid "Network error, please contact system administrator" msgstr "网络错误,请联系系统管理员" -#: common/sdk/im/slack/__init__.py:79 +#: common/sdk/im/slack/__init__.py:77 msgid "Unknown error occur" msgstr "发生未知错误" @@ -3857,15 +3874,15 @@ msgstr "标签管理" # msgid "Labels" # msgstr "标签管理" -#: common/tasks.py:21 common/utils/verify_code.py:16 +#: common/tasks.py:31 common/utils/verify_code.py:16 msgid "Send email" msgstr "发件邮件" -#: common/tasks.py:48 +#: common/tasks.py:58 msgid "Send email attachment" msgstr "发送邮件附件" -#: common/tasks.py:69 terminal/tasks.py:62 +#: common/tasks.py:80 terminal/tasks.py:62 msgid "Upload session replay to external storage" msgstr "上传会话录像到外部存储" @@ -3894,16 +3911,16 @@ msgstr "不能包含特殊字符" msgid "The mobile phone number format is incorrect" msgstr "手机号格式不正确" -#: jumpserver/conf.py:450 +#: jumpserver/conf.py:454 #, python-brace-format msgid "The verification code is: {code}" msgstr "验证码为: {code}" -#: jumpserver/conf.py:454 +#: jumpserver/conf.py:459 msgid "Create account successfully" msgstr "创建账号成功" -#: jumpserver/conf.py:456 +#: jumpserver/conf.py:461 msgid "Your account has been created successfully" msgstr "你的账号已创建成功" @@ -4319,6 +4336,7 @@ msgid "Is finished" msgstr "是否完成" #: ops/serializers/job.py:66 +#: settings/templates/ldap/_msg_import_ldap_user.html:7 msgid "Time cost" msgstr "花费时间" @@ -4535,7 +4553,7 @@ msgid "today" msgstr "今天" #: perms/notifications.py:12 perms/notifications.py:44 -#: settings/serializers/feature.py:106 +#: settings/serializers/feature.py:117 msgid "day" msgstr "天" @@ -4555,6 +4573,19 @@ msgstr "资产授权规则将要过期" msgid "asset permissions of organization {}" msgstr "组织 ({}) 的资产授权" +#: perms/serializers/permission.py:186 rbac/serializers/role.py:27 +#: users/serializers/group.py:54 users/serializers/group.py:60 +msgid "Users amount" +msgstr "用户数量" + +#: perms/serializers/permission.py:187 +msgid "User groups amount" +msgstr "用户组数量" + +#: perms/serializers/permission.py:189 +msgid "Nodes amount" +msgstr "节点数量" + #: perms/tasks.py:27 msgid "Check asset permission expired" msgstr "校验资产授权规则已过期" @@ -4695,10 +4726,6 @@ msgstr "系统角色绑定" msgid "Perms" msgstr "权限" -#: rbac/serializers/role.py:27 users/serializers/group.py:31 -msgid "Users amount" -msgstr "用户数量" - #: rbac/serializers/role.py:28 terminal/models/applet/applet.py:34 #: terminal/models/virtualapp/virtualapp.py:20 msgid "Display name" @@ -4770,7 +4797,7 @@ msgstr "远程应用" msgid "Ticket comment" msgstr "工单评论" -#: rbac/tree.py:130 settings/serializers/feature.py:98 +#: rbac/tree.py:130 settings/serializers/feature.py:109 #: tickets/models/ticket/general.py:307 msgid "Ticket" msgstr "工单管理" @@ -4793,7 +4820,7 @@ msgstr "聊天 AI 没有开启" msgid "Test success" msgstr "测试成功" -#: settings/api/email.py:21 +#: settings/api/email.py:22 msgid "Test mail sent to {}, please check" msgstr "邮件已经发送{}, 请检查" @@ -4894,6 +4921,10 @@ msgstr "其它设置" msgid "Chat prompt" msgstr "聊天提示" +#: settings/notifications.py:23 +msgid "Notification of Synchronized LDAP User Task Results" +msgstr "同步LDAP用户任务结果通知" + #: settings/serializers/auth/base.py:12 msgid "LDAP Auth" msgstr "LDAP 认证" @@ -5049,7 +5080,7 @@ msgstr "连接超时时间 (秒)" msgid "Search paged size (piece)" msgstr "搜索分页数量 (条)" -#: settings/serializers/auth/ldap.py:81 +#: settings/serializers/auth/ldap.py:84 msgid "Enable LDAP auth" msgstr "启用 LDAP 认证" @@ -5265,7 +5296,7 @@ msgstr "验证码长度" #: settings/serializers/auth/sms.py:27 settings/serializers/auth/sms.py:49 #: settings/serializers/auth/sms.py:57 settings/serializers/auth/sms.py:66 -#: settings/serializers/auth/sms.py:77 settings/serializers/msg.py:76 +#: settings/serializers/auth/sms.py:77 settings/serializers/msg.py:83 msgid "Signature" msgstr "签名" @@ -5466,62 +5497,76 @@ msgid "Mount Point" msgstr "挂载点" #: settings/serializers/feature.py:60 +msgid "Historical accounts retained count" +msgstr "历史账号保留数量" + +#: settings/serializers/feature.py:62 +msgid "" +"If the specific value is less than 999, the system will automatically " +"perform a task every night: check and delete historical accounts that exceed " +"the predetermined number. If the value reaches or exceeds 999, no historical " +"account deletion will be performed." +msgstr "" +"若特定数值小于999,系统将在每日晚间自动执行任务:检查并删除超出预定数量的历史" +"账号。如果该数值达到或超过999,则不进行任何历史账号的删除操作。" + +#: settings/serializers/feature.py:71 msgid "Chat AI" msgstr "聊天 AI" -#: settings/serializers/feature.py:64 +#: settings/serializers/feature.py:75 msgid "Enable Chat AI" msgstr "启动聊天 AI" -#: settings/serializers/feature.py:67 +#: settings/serializers/feature.py:78 msgid "Base Url" msgstr "基本地址" -#: settings/serializers/feature.py:70 templates/_header_bar.html:90 +#: settings/serializers/feature.py:81 templates/_header_bar.html:90 msgid "API Key" msgstr "API Key" -#: settings/serializers/feature.py:76 +#: settings/serializers/feature.py:87 msgid "GPT Model" msgstr "GPT 模型" -#: settings/serializers/feature.py:100 +#: settings/serializers/feature.py:111 msgid "Enable tickets" msgstr "启用工单" -#: settings/serializers/feature.py:103 +#: settings/serializers/feature.py:114 msgid "Ticket authorize default time" msgstr "默认工单授权时间" -#: settings/serializers/feature.py:106 +#: settings/serializers/feature.py:117 msgid "hour" msgstr "时" -#: settings/serializers/feature.py:107 +#: settings/serializers/feature.py:118 msgid "Ticket authorize default time unit" msgstr "默认工单授权时间单位" -#: settings/serializers/feature.py:112 +#: settings/serializers/feature.py:123 msgid "Feature" msgstr "功能" -#: settings/serializers/feature.py:115 +#: settings/serializers/feature.py:126 msgid "Operation center" msgstr "作业中心" -#: settings/serializers/feature.py:116 +#: settings/serializers/feature.py:127 msgid "Allow user run batch command or not using ansible" msgstr "是否允许用户使用 ansible 执行批量命令" -#: settings/serializers/feature.py:120 +#: settings/serializers/feature.py:131 msgid "Operation center command blacklist" msgstr "作业中心命令黑名单" -#: settings/serializers/feature.py:121 +#: settings/serializers/feature.py:132 msgid "Commands that are not allowed execute." msgstr "不允许执行的命令" -#: settings/serializers/feature.py:126 +#: settings/serializers/feature.py:137 #: terminal/models/virtualapp/provider.py:17 #: terminal/models/virtualapp/virtualapp.py:36 #: terminal/models/virtualapp/virtualapp.py:97 @@ -5529,94 +5574,86 @@ msgstr "不允许执行的命令" msgid "Virtual app" msgstr "虚拟应用" -#: settings/serializers/feature.py:129 +#: settings/serializers/feature.py:140 msgid "Enable virtual app" msgstr "启用虚拟应用" -#: settings/serializers/msg.py:24 -msgid "SMTP host" -msgstr "SMTP 主机" - #: settings/serializers/msg.py:25 -msgid "SMTP port" -msgstr "SMTP 端口" +msgid "SMTP" +msgstr "SMTP" #: settings/serializers/msg.py:26 -msgid "SMTP account" -msgstr "SMTP 账号" +msgid "EXCHANGE" +msgstr "" -#: settings/serializers/msg.py:28 -msgid "SMTP password" -msgstr "SMTP 密码" - -#: settings/serializers/msg.py:29 +#: settings/serializers/msg.py:36 msgid "Tips: Some provider use token except password" msgstr "提示:一些邮件提供商需要输入的是授权码" -#: settings/serializers/msg.py:32 +#: settings/serializers/msg.py:39 msgid "Send user" msgstr "发件人" -#: settings/serializers/msg.py:33 +#: settings/serializers/msg.py:40 msgid "Tips: Send mail account, default SMTP account as the send account" msgstr "提示:发送邮件账号,默认使用 SMTP 账号作为发送账号" -#: settings/serializers/msg.py:36 +#: settings/serializers/msg.py:43 msgid "Test recipient" msgstr "测试收件人" -#: settings/serializers/msg.py:37 +#: settings/serializers/msg.py:44 msgid "Tips: Used only as a test mail recipient" msgstr "提示:仅用来作为测试邮件收件人" -#: settings/serializers/msg.py:41 +#: settings/serializers/msg.py:48 msgid "If SMTP port is 465, may be select" msgstr "如果SMTP端口是465,通常需要启用 SSL" -#: settings/serializers/msg.py:44 +#: settings/serializers/msg.py:51 msgid "Use TLS" msgstr "使用 TLS" -#: settings/serializers/msg.py:45 +#: settings/serializers/msg.py:52 msgid "If SMTP port is 587, may be select" msgstr "如果SMTP端口是587,通常需要启用 TLS" -#: settings/serializers/msg.py:48 +#: settings/serializers/msg.py:55 msgid "Subject prefix" msgstr "主题前缀" -#: settings/serializers/msg.py:51 +#: settings/serializers/msg.py:58 msgid "Email suffix" msgstr "邮件后缀" -#: settings/serializers/msg.py:52 +#: settings/serializers/msg.py:59 msgid "" "This is used by default if no email is returned during SSO authentication" msgstr "SSO认证时,如果没有返回邮件地址,将使用该后缀" -#: settings/serializers/msg.py:61 +#: settings/serializers/msg.py:68 msgid "Create user email subject" msgstr "邮件主题" -#: settings/serializers/msg.py:62 +#: settings/serializers/msg.py:69 msgid "" "Tips: When creating a user, send the subject of the email (eg:Create account " "successfully)" msgstr "提示: 创建用户时,发送设置密码邮件的主题 (例如: 创建用户成功)" -#: settings/serializers/msg.py:66 +#: settings/serializers/msg.py:73 msgid "Create user honorific" msgstr "邮件问候语" -#: settings/serializers/msg.py:67 +#: settings/serializers/msg.py:74 msgid "Tips: When creating a user, send the honorific of the email (eg:Hello)" msgstr "提示: 创建用户时,发送设置密码邮件的敬语 (例如: 你好)" -#: settings/serializers/msg.py:71 +#: settings/serializers/msg.py:78 msgid "Create user email content" msgstr "邮件的内容" -#: settings/serializers/msg.py:73 +#: settings/serializers/msg.py:80 #, python-brace-format msgid "" "Tips: When creating a user, send the content of the email, support " @@ -5624,7 +5661,7 @@ msgid "" msgstr "" "提示: 创建用户时,发送设置密码邮件的内容, 支持 {username} {name} {email} 标签" -#: settings/serializers/msg.py:77 +#: settings/serializers/msg.py:84 msgid "Tips: Email signature (eg:jumpserver)" msgstr "邮件署名 (如:jumpserver)" @@ -5966,112 +6003,129 @@ msgstr "启用 Razor 服务" msgid "Enable SSH Client" msgstr "启用 SSH Client" -#: settings/tasks/ldap.py:24 +#: settings/tasks/ldap.py:28 msgid "Periodic import ldap user" msgstr "周期导入 LDAP 用户" -#: settings/tasks/ldap.py:45 +#: settings/tasks/ldap.py:66 msgid "Registration periodic import ldap user task" msgstr "注册周期导入 LDAP 用户 任务" -#: settings/utils/ldap.py:492 +#: settings/templates/ldap/_msg_import_ldap_user.html:2 +msgid "Sync task Finish" +msgstr "同步任务完成" + +#: settings/templates/ldap/_msg_import_ldap_user.html:6 +#: terminal/models/session/session.py:45 +msgid "Date end" +msgstr "结束日期" + +#: settings/templates/ldap/_msg_import_ldap_user.html:9 +msgid "Synced Organization" +msgstr "已同步组织" + +#: settings/templates/ldap/_msg_import_ldap_user.html:15 +msgid "Synced User" +msgstr "已同步用户" + +#: settings/utils/ldap.py:494 msgid "ldap:// or ldaps:// protocol is used." msgstr "使用 ldap:// 或 ldaps:// 协议" -#: settings/utils/ldap.py:503 +#: settings/utils/ldap.py:505 msgid "Host or port is disconnected: {}" msgstr "主机或端口不可连接: {}" -#: settings/utils/ldap.py:505 +#: settings/utils/ldap.py:507 msgid "The port is not the port of the LDAP service: {}" msgstr "端口不是LDAP服务端口: {}" -#: settings/utils/ldap.py:507 +#: settings/utils/ldap.py:509 msgid "Please add certificate: {}" msgstr "请添加证书" -#: settings/utils/ldap.py:511 settings/utils/ldap.py:538 -#: settings/utils/ldap.py:568 settings/utils/ldap.py:596 +#: settings/utils/ldap.py:513 settings/utils/ldap.py:540 +#: settings/utils/ldap.py:570 settings/utils/ldap.py:598 msgid "Unknown error: {}" msgstr "未知错误: {}" -#: settings/utils/ldap.py:525 +#: settings/utils/ldap.py:527 msgid "Bind DN or Password incorrect" msgstr "绑定DN或密码错误" -#: settings/utils/ldap.py:532 +#: settings/utils/ldap.py:534 msgid "Please enter Bind DN: {}" msgstr "请输入绑定DN: {}" -#: settings/utils/ldap.py:534 +#: settings/utils/ldap.py:536 msgid "Please enter Password: {}" msgstr "请输入密码: {}" -#: settings/utils/ldap.py:536 +#: settings/utils/ldap.py:538 msgid "Please enter correct Bind DN and Password: {}" msgstr "请输入正确的绑定DN和密码: {}" -#: settings/utils/ldap.py:554 +#: settings/utils/ldap.py:556 msgid "Invalid User OU or User search filter: {}" msgstr "不合法的用户OU或用户过滤器: {}" -#: settings/utils/ldap.py:585 +#: settings/utils/ldap.py:587 msgid "LDAP User attr map not include: {}" msgstr "LDAP属性映射没有包含: {}" -#: settings/utils/ldap.py:592 +#: settings/utils/ldap.py:594 msgid "LDAP User attr map is not dict" msgstr "LDAP属性映射不合法" -#: settings/utils/ldap.py:611 +#: settings/utils/ldap.py:613 msgid "LDAP authentication is not enabled" msgstr "LDAP认证没有启用" -#: settings/utils/ldap.py:629 +#: settings/utils/ldap.py:631 msgid "Error (Invalid LDAP server): {}" msgstr "错误 (不合法的LDAP服务器地址): {}" -#: settings/utils/ldap.py:631 +#: settings/utils/ldap.py:633 msgid "Error (Invalid Bind DN): {}" msgstr "错误 (不合法的绑定DN): {}" -#: settings/utils/ldap.py:633 +#: settings/utils/ldap.py:635 msgid "Error (Invalid LDAP User attr map): {}" msgstr "错误 (不合法的LDAP属性映射): {}" -#: settings/utils/ldap.py:635 +#: settings/utils/ldap.py:637 msgid "Error (Invalid User OU or User search filter): {}" msgstr "错误 (不合法的用户OU或用户过滤器): {}" -#: settings/utils/ldap.py:637 +#: settings/utils/ldap.py:639 msgid "Error (Not enabled LDAP authentication): {}" msgstr "错误 (没有启用LDAP认证): {}" -#: settings/utils/ldap.py:639 +#: settings/utils/ldap.py:641 msgid "Error (Unknown): {}" msgstr "错误 (未知): {}" -#: settings/utils/ldap.py:642 +#: settings/utils/ldap.py:644 msgid "Succeed: Match {} s user" msgstr "成功匹配 {} 个用户" -#: settings/utils/ldap.py:653 +#: settings/utils/ldap.py:655 msgid "Please test the connection first" msgstr "请先测试连接" -#: settings/utils/ldap.py:675 +#: settings/utils/ldap.py:677 msgid "Authentication failed (configuration incorrect): {}" msgstr "认证失败 (配置错误): {}" -#: settings/utils/ldap.py:679 +#: settings/utils/ldap.py:681 msgid "Authentication failed (username or password incorrect): {}" msgstr "认证失败 (用户名或密码不正确): {}" -#: settings/utils/ldap.py:681 +#: settings/utils/ldap.py:683 msgid "Authentication failed (Unknown): {}" msgstr "认证失败: (未知): {}" -#: settings/utils/ldap.py:684 +#: settings/utils/ldap.py:686 msgid "Authentication success: {}" msgstr "认证成功: {}" @@ -6674,10 +6728,6 @@ msgstr "登录来源" msgid "Replay" msgstr "回放" -#: terminal/models/session/session.py:45 -msgid "Date end" -msgstr "结束日期" - #: terminal/models/session/session.py:47 terminal/serializers/session.py:65 msgid "Command amount" msgstr "命令数量" @@ -7700,31 +7750,31 @@ msgstr "需要更新密码" msgid "Date api key used" msgstr "Api key 最后使用日期" -#: users/models/user.py:984 +#: users/models/user.py:985 msgid "Can not delete admin user" msgstr "无法删除管理员用户" -#: users/models/user.py:1011 +#: users/models/user.py:1012 msgid "Can invite user" msgstr "可以邀请用户" -#: users/models/user.py:1012 +#: users/models/user.py:1013 msgid "Can remove user" msgstr "可以移除用户" -#: users/models/user.py:1013 +#: users/models/user.py:1014 msgid "Can match user" msgstr "可以匹配用户" -#: users/models/user.py:1022 +#: users/models/user.py:1023 msgid "Administrator" msgstr "管理员" -#: users/models/user.py:1025 +#: users/models/user.py:1026 msgid "Administrator is the super user of system" msgstr "Administrator是初始的超级管理员" -#: users/models/user.py:1050 +#: users/models/user.py:1051 msgid "User password history" msgstr "用户密码历史" @@ -7914,6 +7964,10 @@ msgid "" msgstr "" "管理员已开启'仅允许已存在用户登录',当前用户不在用户列表中,请联系管理员。" +#: users/signal_handlers.py:166 +msgid "Clean up expired user sessions" +msgstr "清除过期的用户会话" + #: users/tasks.py:25 msgid "Check password expired" msgstr "校验密码已过期" @@ -8158,7 +8212,7 @@ msgstr "MFA(OTP) 禁用成功,返回登录页面" msgid "Password invalid" msgstr "用户名或密码无效" -#: users/views/profile/reset.py:64 +#: users/views/profile/reset.py:65 msgid "" "Non-local users can log in only from third-party platforms and cannot change " "their passwords: {}" @@ -8880,6 +8934,15 @@ msgstr "企业专业版" msgid "Ultimate edition" msgstr "企业旗舰版" +#~ msgid "SMTP port" +#~ msgstr "SMTP 端口" + +#~ msgid "SMTP account" +#~ msgstr "SMTP 账号" + +#~ msgid "SMTP password" +#~ msgstr "SMTP 密码" + #~ msgid "Password can not contains `{{` or `}}`" #~ msgstr "密码不能包含 `{{` 或 `}}` 字符" diff --git a/apps/ops/ansible/modules_utils/custom_common.py b/apps/ops/ansible/modules_utils/custom_common.py index 0cf1420d2..7015ff2f9 100644 --- a/apps/ops/ansible/modules_utils/custom_common.py +++ b/apps/ops/ansible/modules_utils/custom_common.py @@ -4,6 +4,21 @@ import time import paramiko from sshtunnel import SSHTunnelForwarder +from packaging import version + +if version.parse(paramiko.__version__) > version.parse("2.8.1"): + _preferred_pubkeys = ( + "ssh-ed25519", + "ecdsa-sha2-nistp256", + "ecdsa-sha2-nistp384", + "ecdsa-sha2-nistp521", + "ssh-rsa", + "rsa-sha2-256", + "rsa-sha2-512", + "ssh-dss", + ) + paramiko.transport.Transport._preferred_pubkeys = _preferred_pubkeys + def common_argument_spec(): options = dict( diff --git a/apps/orgs/signal_handlers/cache.py b/apps/orgs/signal_handlers/cache.py index b4e6001e3..4dc3c796e 100644 --- a/apps/orgs/signal_handlers/cache.py +++ b/apps/orgs/signal_handlers/cache.py @@ -75,7 +75,7 @@ model_cache_field_mapper = { class OrgResourceStatisticsRefreshUtil: @staticmethod - @merge_delay_run(ttl=5) + @merge_delay_run(ttl=30) def refresh_org_fields(org_fields=()): for org, cache_field_name in org_fields: OrgResourceStatisticsCache(org).expire(*cache_field_name) @@ -104,7 +104,7 @@ def on_post_delete_refresh_org_resource_statistics_cache(sender, instance, **kwa def _refresh_session_org_resource_statistics_cache(instance: Session): cache_field_name = [ 'total_count_online_users', 'total_count_online_sessions', - 'total_count_today_active_assets','total_count_today_failed_sessions' + 'total_count_today_active_assets', 'total_count_today_failed_sessions' ] org_cache = OrgResourceStatisticsCache(instance.org) diff --git a/apps/perms/api/asset_permission.py b/apps/perms/api/asset_permission.py index 750f41fb4..c72254d0d 100644 --- a/apps/perms/api/asset_permission.py +++ b/apps/perms/api/asset_permission.py @@ -1,5 +1,6 @@ # -*- coding: utf-8 -*- # + from orgs.mixins.api import OrgBulkModelViewSet from perms import serializers from perms.filters import AssetPermissionFilter @@ -13,7 +14,10 @@ class AssetPermissionViewSet(OrgBulkModelViewSet): 资产授权列表的增删改查api """ model = AssetPermission - serializer_class = serializers.AssetPermissionSerializer + serializer_classes = { + 'default': serializers.AssetPermissionSerializer, + 'list': serializers.AssetPermissionListSerializer, + } filterset_class = AssetPermissionFilter search_fields = ('name',) ordering = ('name',) diff --git a/apps/perms/api/user_permission/assets.py b/apps/perms/api/user_permission/assets.py index bc51dfe77..6db934c3b 100644 --- a/apps/perms/api/user_permission/assets.py +++ b/apps/perms/api/user_permission/assets.py @@ -7,8 +7,7 @@ from assets.models import Asset, Node from common.utils import get_logger, lazyproperty, is_uuid from orgs.utils import tmp_to_root_org from perms import serializers -from perms.pagination import AllPermedAssetPagination -from perms.pagination import NodePermedAssetPagination +from perms.pagination import NodePermedAssetPagination, AllPermedAssetPagination from perms.utils import UserPermAssetUtil, PermAssetDetailUtil from .mixin import ( SelfOrPKUserMixin diff --git a/apps/perms/api/user_permission/tree/asset.py b/apps/perms/api/user_permission/tree/asset.py index c620356ad..e5e2ab4d3 100644 --- a/apps/perms/api/user_permission/tree/asset.py +++ b/apps/perms/api/user_permission/tree/asset.py @@ -1,16 +1,14 @@ from django.conf import settings from rest_framework.response import Response -from assets.models import Asset from assets.api import SerializeToTreeNodeMixin +from assets.models import Asset from common.utils import get_logger - -from ..assets import UserAllPermedAssetsApi from .mixin import RebuildTreeMixin +from ..assets import UserAllPermedAssetsApi logger = get_logger(__name__) - __all__ = [ 'UserAllPermedAssetsAsTreeApi', 'UserUngroupAssetsAsTreeApi', @@ -31,7 +29,7 @@ class AssetTreeMixin(RebuildTreeMixin, SerializeToTreeNodeMixin): if request.query_params.get('search'): """ 限制返回数量, 搜索的条件不精准时,会返回大量的无意义数据 """ assets = assets[:999] - data = self.serialize_assets(assets, None) + data = self.serialize_assets(assets, 'root') return Response(data=data) @@ -42,6 +40,7 @@ class UserAllPermedAssetsAsTreeApi(AssetTreeMixin, UserAllPermedAssetsApi): class UserUngroupAssetsAsTreeApi(UserAllPermedAssetsAsTreeApi): """ 用户 '未分组节点的资产(直接授权的资产)' 作为树 """ + def get_assets(self): if settings.PERM_SINGLE_ASSET_TO_UNGROUP_NODE: return super().get_assets() diff --git a/apps/perms/api/user_permission/tree/node_with_asset.py b/apps/perms/api/user_permission/tree/node_with_asset.py index 0289b9d63..114c5475e 100644 --- a/apps/perms/api/user_permission/tree/node_with_asset.py +++ b/apps/perms/api/user_permission/tree/node_with_asset.py @@ -1,6 +1,4 @@ import abc -import re -from collections import defaultdict from urllib.parse import parse_qsl from django.conf import settings @@ -13,10 +11,10 @@ from rest_framework.response import Response from accounts.const import AliasAccount from assets.api import SerializeToTreeNodeMixin -from assets.const import AllTypes from assets.models import Asset from assets.utils import KubernetesTree from authentication.models import ConnectionToken +from common.exceptions import JMSException from common.utils import get_object_or_none, lazyproperty from common.utils.common import timeit from perms.hands import Node @@ -38,21 +36,36 @@ class BaseUserNodeWithAssetAsTreeApi( SelfOrPKUserMixin, RebuildTreeMixin, SerializeToTreeNodeMixin, ListAPIView ): + page_limit = 10000 def list(self, request, *args, **kwargs): - nodes, assets = self.get_nodes_assets() - tree_nodes = self.serialize_nodes(nodes, with_asset_amount=True) - tree_assets = self.serialize_assets(assets, node_key=self.node_key_for_serialize_assets) - data = list(tree_nodes) + list(tree_assets) - return Response(data=data) + offset = int(request.query_params.get('offset', 0)) + page_assets = self.get_page_assets() + + if not offset: + nodes, assets = self.get_nodes_assets() + page = page_assets[:self.page_limit] + assets = [*assets, *page] + tree_nodes = self.serialize_nodes(nodes, with_asset_amount=True) + tree_assets = self.serialize_assets(assets, **self.serialize_asset_kwargs) + data = list(tree_nodes) + list(tree_assets) + else: + page = page_assets[offset:(offset + self.page_limit)] + data = self.serialize_assets(page, **self.serialize_asset_kwargs) if page else [] + offset += len(page) + headers = {'X-JMS-TREE-OFFSET': offset} if offset else {} + return Response(data=data, headers=headers) @abc.abstractmethod def get_nodes_assets(self): return [], [] - @lazyproperty - def node_key_for_serialize_assets(self): - return None + def get_page_assets(self): + return [] + + @property + def serialize_asset_kwargs(self): + return {} class UserPermedNodesWithAssetsAsTreeApi(BaseUserNodeWithAssetAsTreeApi): @@ -61,7 +74,6 @@ class UserPermedNodesWithAssetsAsTreeApi(BaseUserNodeWithAssetAsTreeApi): def get_nodes_assets(self): self.query_node_util = UserPermNodeUtil(self.request.user) - self.query_asset_util = UserPermAssetUtil(self.request.user) ung_nodes, ung_assets = self._get_nodes_assets_for_ungrouped() fav_nodes, fav_assets = self._get_nodes_assets_for_favorite() all_nodes, all_assets = self._get_nodes_assets_for_all() @@ -69,31 +81,37 @@ class UserPermedNodesWithAssetsAsTreeApi(BaseUserNodeWithAssetAsTreeApi): assets = list(ung_assets) + list(fav_assets) + list(all_assets) return nodes, assets + def get_page_assets(self): + return self.query_asset_util.get_all_assets().annotate(parent_key=F('nodes__key')) + @timeit def _get_nodes_assets_for_ungrouped(self): if not settings.PERM_SINGLE_ASSET_TO_UNGROUP_NODE: return [], [] node = self.query_node_util.get_ungrouped_node() assets = self.query_asset_util.get_ungroup_assets() - assets = assets.annotate(parent_key=Value(node.key, output_field=CharField())) \ - .prefetch_related('platform') + assets = assets.annotate(parent_key=Value(node.key, output_field=CharField())) return [node], assets + @lazyproperty + def query_asset_util(self): + return UserPermAssetUtil(self.user) + @timeit def _get_nodes_assets_for_favorite(self): node = self.query_node_util.get_favorite_node() assets = self.query_asset_util.get_favorite_assets() - assets = assets.annotate(parent_key=Value(node.key, output_field=CharField())) \ - .prefetch_related('platform') + assets = assets.annotate(parent_key=Value(node.key, output_field=CharField())) return [node], assets + @timeit def _get_nodes_assets_for_all(self): nodes = self.query_node_util.get_whole_tree_nodes(with_special=False) if settings.PERM_SINGLE_ASSET_TO_UNGROUP_NODE: assets = self.query_asset_util.get_perm_nodes_assets() else: - assets = self.query_asset_util.get_all_assets() - assets = assets.annotate(parent_key=F('nodes__key')).prefetch_related('platform') + assets = Asset.objects.none() + assets = assets.annotate(parent_key=F('nodes__key')) return nodes, assets @@ -103,6 +121,7 @@ class UserPermedNodeChildrenWithAssetsAsTreeApi(BaseUserNodeWithAssetAsTreeApi): # 默认展开的节点key default_unfolded_node_key = None + @timeit def get_nodes_assets(self): query_node_util = UserPermNodeUtil(self.user) query_asset_util = UserPermAssetUtil(self.user) @@ -136,14 +155,14 @@ class UserPermedNodeChildrenWithAssetsAsTreeApi(BaseUserNodeWithAssetAsTreeApi): node_key = getattr(node, 'key', None) return node_key - @lazyproperty - def node_key_for_serialize_assets(self): - return self.query_node_key or self.default_unfolded_node_key + @property + def serialize_asset_kwargs(self): + return { + 'node_key': self.query_node_key or self.default_unfolded_node_key + } -class UserPermedNodeChildrenWithAssetsAsCategoryTreeApi( - SelfOrPKUserMixin, SerializeToTreeNodeMixin, ListAPIView -): +class UserPermedNodeChildrenWithAssetsAsCategoryTreeApi(BaseUserNodeWithAssetAsTreeApi): @property def is_sync(self): sync = self.request.query_params.get('sync', 0) @@ -151,66 +170,54 @@ class UserPermedNodeChildrenWithAssetsAsCategoryTreeApi( @property def tp(self): - return self.request.query_params.get('type') - - def get_assets(self): - query_asset_util = UserPermAssetUtil(self.user) - node = PermNode.objects.filter( - granted_node_rels__user=self.user, parent_key='').first() - if node: - __, assets = query_asset_util.get_node_all_assets(node.id) - else: - assets = Asset.objects.none() - return assets - - def to_tree_nodes(self, assets): - if not assets: - return [] - assets = assets.annotate(tp=F('platform__type')) - asset_type_map = defaultdict(list) - for asset in assets: - asset_type_map[asset.tp].append(asset) - tp = self.tp - if tp: - assets = asset_type_map.get(tp, []) - if not assets: - return [] - pid = f'ROOT_{str(assets[0].category).upper()}_{tp}' - return self.serialize_assets(assets, pid=pid) params = self.request.query_params - get_root = not list(filter(lambda x: params.get(x), ('type', 'n'))) - resource_platforms = assets.order_by('id').values_list('platform_id', flat=True) - node_all = AllTypes.get_tree_nodes(resource_platforms, get_root=get_root) - pattern = re.compile(r'\(0\)?') - nodes = [] - for node in node_all: - meta = node.get('meta', {}) - if pattern.search(node['name']) or meta.get('type') == 'platform': - continue - _type = meta.get('_type') - if _type: - node['type'] = _type - meta.setdefault('data', {}) - node['meta'] = meta - nodes.append(node) + return [params.get('category'), params.get('type')] - if not self.is_sync: - return nodes + @lazyproperty + def query_asset_util(self): + return UserPermAssetUtil(self.user) - asset_nodes = [] - for node in nodes: - node['open'] = True - tp = node.get('meta', {}).get('_type') - if not tp: - continue - assets = asset_type_map.get(tp, []) - asset_nodes += self.serialize_assets(assets, pid=node['id']) - return nodes + asset_nodes + @timeit + def get_assets(self): + return self.query_asset_util.get_all_assets() - def list(self, request, *args, **kwargs): - assets = self.get_assets() - nodes = self.to_tree_nodes(assets) - return Response(data=nodes) + def _get_tree_nodes_async(self): + if self.request.query_params.get('lv') == '0': + return [], [] + if not self.tp or not all(self.tp): + nodes = UserPermAssetUtil.get_type_nodes_tree_or_cached(self.user) + return nodes, [] + + category, tp = self.tp + assets = self.get_assets().filter(platform__type=tp, platform__category=category) + return [], assets + + def _get_tree_nodes_sync(self): + if self.request.query_params.get('lv'): + return [] + nodes = self.query_asset_util.get_type_nodes_tree() + return nodes, [] + + @property + def serialize_asset_kwargs(self): + return { + 'get_pid': lambda asset, platform: 'ROOT_{}_{}'.format(platform.category.upper(), platform.type), + } + + def serialize_nodes(self, nodes, with_asset_amount=False): + return nodes + + def get_nodes_assets(self): + if self.is_sync: + return self._get_tree_nodes_sync() + else: + return self._get_tree_nodes_async() + + def get_page_assets(self): + if self.is_sync: + return self.get_assets() + else: + return [] class UserGrantedK8sAsTreeApi(SelfOrPKUserMixin, ListAPIView): @@ -258,5 +265,8 @@ class UserGrantedK8sAsTreeApi(SelfOrPKUserMixin, ListAPIView): if not any([namespace, pod]) and not key: asset_node = k8s_tree_instance.as_asset_tree_node() tree.append(asset_node) - tree.extend(k8s_tree_instance.async_tree_node(namespace, pod)) - return Response(data=tree) + try: + tree.extend(k8s_tree_instance.async_tree_node(namespace, pod)) + return Response(data=tree) + except Exception as e: + raise JMSException(e) diff --git a/apps/perms/models/asset_permission.py b/apps/perms/models/asset_permission.py index 5ecf824c0..d8c7026e5 100644 --- a/apps/perms/models/asset_permission.py +++ b/apps/perms/models/asset_permission.py @@ -8,7 +8,7 @@ from django.utils.translation import gettext_lazy as _ from accounts.const import AliasAccount from accounts.models import Account from assets.models import Asset -from common.utils import date_expired_default +from common.utils import date_expired_default, lazyproperty from common.utils.timezone import local_now from labels.mixins import LabeledMixin from orgs.mixins.models import JMSOrgBaseModel @@ -105,6 +105,22 @@ class AssetPermission(LabeledMixin, JMSOrgBaseModel): return True return False + @lazyproperty + def users_amount(self): + return self.users.count() + + @lazyproperty + def user_groups_amount(self): + return self.user_groups.count() + + @lazyproperty + def assets_amount(self): + return self.assets.count() + + @lazyproperty + def nodes_amount(self): + return self.nodes.count() + def get_all_users(self): from users.models import User user_ids = self.users.all().values_list('id', flat=True) @@ -114,7 +130,7 @@ class AssetPermission(LabeledMixin, JMSOrgBaseModel): qs1_ids = User.objects.filter(id__in=user_ids).distinct().values_list('id', flat=True) qs2_ids = User.objects.filter(groups__id__in=group_ids).distinct().values_list('id', flat=True) qs_ids = list(qs1_ids) + list(qs2_ids) - qs = User.objects.filter(id__in=qs_ids) + qs = User.objects.filter(id__in=qs_ids, is_service_account=False) return qs def get_all_assets(self, flat=False): @@ -143,11 +159,14 @@ class AssetPermission(LabeledMixin, JMSOrgBaseModel): @classmethod def get_all_users_for_perms(cls, perm_ids, flat=False): - user_ids = cls.users.through.objects.filter(assetpermission_id__in=perm_ids) \ + user_ids = cls.users.through.objects \ + .filter(assetpermission_id__in=perm_ids) \ .values_list('user_id', flat=True).distinct() - group_ids = cls.user_groups.through.objects.filter(assetpermission_id__in=perm_ids) \ + group_ids = cls.user_groups.through.objects \ + .filter(assetpermission_id__in=perm_ids) \ .values_list('usergroup_id', flat=True).distinct() - group_user_ids = User.groups.through.objects.filter(usergroup_id__in=group_ids) \ + group_user_ids = User.groups.through.objects \ + .filter(usergroup_id__in=group_ids) \ .values_list('user_id', flat=True).distinct() user_ids = set(user_ids) | set(group_user_ids) if flat: diff --git a/apps/perms/serializers/permission.py b/apps/perms/serializers/permission.py index d09c33538..3e32b40e1 100644 --- a/apps/perms/serializers/permission.py +++ b/apps/perms/serializers/permission.py @@ -1,6 +1,6 @@ # -*- coding: utf-8 -*- # -from django.db.models import Q +from django.db.models import Q, Count from django.utils.translation import gettext_lazy as _ from rest_framework import serializers @@ -14,7 +14,7 @@ from orgs.mixins.serializers import BulkOrgResourceModelSerializer from perms.models import ActionChoices, AssetPermission from users.models import User, UserGroup -__all__ = ["AssetPermissionSerializer", "ActionChoicesField"] +__all__ = ["AssetPermissionSerializer", "ActionChoicesField", "AssetPermissionListSerializer"] class ActionChoicesField(BitChoicesField): @@ -142,8 +142,8 @@ class AssetPermissionSerializer(ResourceLabelsMixin, BulkOrgResourceModelSeriali def perform_display_create(instance, **kwargs): # 用户 users_to_set = User.objects.filter( - Q(name__in=kwargs.get("users_display")) - | Q(username__in=kwargs.get("users_display")) + Q(name__in=kwargs.get("users_display")) | + Q(username__in=kwargs.get("users_display")) ).distinct() instance.users.add(*users_to_set) # 用户组 @@ -153,8 +153,8 @@ class AssetPermissionSerializer(ResourceLabelsMixin, BulkOrgResourceModelSeriali instance.user_groups.add(*user_groups_to_set) # 资产 assets_to_set = Asset.objects.filter( - Q(address__in=kwargs.get("assets_display")) - | Q(name__in=kwargs.get("assets_display")) + Q(address__in=kwargs.get("assets_display")) | + Q(name__in=kwargs.get("assets_display")) ).distinct() instance.assets.add(*assets_to_set) # 节点 @@ -180,3 +180,27 @@ class AssetPermissionSerializer(ResourceLabelsMixin, BulkOrgResourceModelSeriali instance = super().create(validated_data) self.perform_display_create(instance, **display) return instance + + +class AssetPermissionListSerializer(AssetPermissionSerializer): + users_amount = serializers.IntegerField(read_only=True, label=_("Users amount")) + user_groups_amount = serializers.IntegerField(read_only=True, label=_("User groups amount")) + assets_amount = serializers.IntegerField(read_only=True, label=_("Assets amount")) + nodes_amount = serializers.IntegerField(read_only=True, label=_("Nodes amount")) + + class Meta(AssetPermissionSerializer.Meta): + amount_fields = ["users_amount", "user_groups_amount", "assets_amount", "nodes_amount"] + remove_fields = {"users", "assets", "nodes", "user_groups"} + fields = list(set(AssetPermissionSerializer.Meta.fields + amount_fields) - remove_fields) + + @classmethod + def setup_eager_loading(cls, queryset): + """Perform necessary eager loading of data.""" + queryset = queryset \ + .prefetch_related('labels', 'labels__label') \ + .annotate(users_amount=Count("users"), + user_groups_amount=Count("user_groups"), + assets_amount=Count("assets"), + nodes_amount=Count("nodes"), + ) + return queryset diff --git a/apps/perms/signal_handlers/refresh_perms.py b/apps/perms/signal_handlers/refresh_perms.py index 88a5fe674..5387bc33f 100644 --- a/apps/perms/signal_handlers/refresh_perms.py +++ b/apps/perms/signal_handlers/refresh_perms.py @@ -3,15 +3,13 @@ from django.db.models.signals import m2m_changed, pre_delete, pre_save, post_save from django.dispatch import receiver -from users.models import User, UserGroup from assets.models import Asset -from common.utils import get_logger, get_object_or_none -from common.exceptions import M2MReverseNotAllowed from common.const.signals import POST_ADD, POST_REMOVE, POST_CLEAR - +from common.exceptions import M2MReverseNotAllowed +from common.utils import get_logger, get_object_or_none from perms.models import AssetPermission from perms.utils import UserPermTreeExpireUtil - +from users.models import User, UserGroup logger = get_logger(__file__) @@ -38,7 +36,7 @@ def on_user_groups_change(sender, instance, action, reverse, pk_set, **kwargs): group = UserGroup.objects.get(id=list(group_ids)[0]) org_id = group.org_id - has_group_perm = AssetPermission.user_groups.through.objects\ + has_group_perm = AssetPermission.user_groups.through.objects \ .filter(usergroup_id__in=group_ids).exists() if not has_group_perm: return @@ -115,6 +113,7 @@ def on_asset_permission_user_groups_changed(sender, instance, action, pk_set, re def on_node_asset_change(action, instance, reverse, pk_set, **kwargs): if not need_rebuild_mapping_node(action): return + print("Asset node changed: ", action) if reverse: asset_ids = pk_set node_ids = [instance.id] diff --git a/apps/perms/utils/permission.py b/apps/perms/utils/permission.py index b9b5b01be..036dabef2 100644 --- a/apps/perms/utils/permission.py +++ b/apps/perms/utils/permission.py @@ -1,8 +1,7 @@ from django.db.models import QuerySet from assets.models import Node, Asset -from common.utils import get_logger - +from common.utils import get_logger, timeit from perms.models import AssetPermission logger = get_logger(__file__) @@ -13,6 +12,7 @@ __all__ = ['AssetPermissionUtil'] class AssetPermissionUtil(object): """ 资产授权相关的方法工具 """ + @timeit def get_permissions_for_user(self, user, with_group=True, flat=False): """ 获取用户的授权规则 """ perm_ids = set() diff --git a/apps/perms/utils/user_perm.py b/apps/perms/utils/user_perm.py index 42d6cc462..d06f18a83 100644 --- a/apps/perms/utils/user_perm.py +++ b/apps/perms/utils/user_perm.py @@ -1,13 +1,22 @@ -from django.conf import settings -from django.db.models import Q +import json +import re +from django.conf import settings +from django.core.cache import cache +from django.db.models import Q +from rest_framework.utils.encoders import JSONEncoder + +from assets.const import AllTypes from assets.models import FavoriteAsset, Asset -from common.utils.common import timeit +from common.utils.common import timeit, get_logger +from orgs.utils import current_org, tmp_to_root_org from perms.models import PermNode, UserAssetGrantedTreeNodeRelation from .permission import AssetPermissionUtil __all__ = ['AssetPermissionPermAssetUtil', 'UserPermAssetUtil', 'UserPermNodeUtil'] +logger = get_logger(__name__) + class AssetPermissionPermAssetUtil: @@ -15,30 +24,35 @@ class AssetPermissionPermAssetUtil: self.perm_ids = perm_ids def get_all_assets(self): - """ 获取所有授权的资产 """ - node_asset_ids = self.get_perm_nodes_assets(flat=True) - direct_asset_ids = self.get_direct_assets(flat=True) - asset_ids = list(node_asset_ids) + list(direct_asset_ids) - assets = Asset.objects.filter(id__in=asset_ids) - return assets + node_assets = self.get_perm_nodes_assets() + direct_assets = self.get_direct_assets() + # 比原来的查到所有 asset id 再搜索块很多,因为当资产量大的时候,搜索会很慢 + return (node_assets | direct_assets).distinct() + @timeit def get_perm_nodes_assets(self, flat=False): """ 获取所有授权节点下的资产 """ from assets.models import Node - nodes = Node.objects.prefetch_related('granted_by_permissions').filter( - granted_by_permissions__in=self.perm_ids).only('id', 'key') + from ..models import AssetPermission + nodes_ids = AssetPermission.objects \ + .filter(id__in=self.perm_ids) \ + .values_list('nodes', flat=True) + nodes = Node.objects.filter(id__in=nodes_ids).only('id', 'key') assets = PermNode.get_nodes_all_assets(*nodes) if flat: - return assets.values_list('id', flat=True) + return set(assets.values_list('id', flat=True)) return assets + @timeit def get_direct_assets(self, flat=False): """ 获取直接授权的资产 """ - assets = Asset.objects.order_by() \ - .filter(granted_by_permissions__id__in=self.perm_ids) \ - .distinct() + from ..models import AssetPermission + asset_ids = AssetPermission.objects \ + .filter(id__in=self.perm_ids) \ + .values_list('assets', flat=True) + assets = Asset.objects.filter(id__in=asset_ids).distinct() if flat: - return assets.values_list('id', flat=True) + return set(assets.values_list('id', flat=True)) return assets @@ -52,12 +66,62 @@ class UserPermAssetUtil(AssetPermissionPermAssetUtil): def get_ungroup_assets(self): return self.get_direct_assets() + @timeit def get_favorite_assets(self): - assets = self.get_all_assets() + assets = Asset.objects.all().valid() asset_ids = FavoriteAsset.objects.filter(user=self.user).values_list('asset_id', flat=True) assets = assets.filter(id__in=list(asset_ids)) return assets + def get_type_nodes_tree(self): + assets = self.get_all_assets() + resource_platforms = assets.order_by('id').values_list('platform_id', flat=True) + node_all = AllTypes.get_tree_nodes(resource_platforms, get_root=True) + pattern = re.compile(r'\(0\)?') + nodes = [] + for node in node_all: + meta = node.get('meta', {}) + if pattern.search(node['name']) or meta.get('type') == 'platform': + continue + _type = meta.get('_type') + if _type: + node['type'] = _type + node['category'] = meta.get('category') + meta.setdefault('data', {}) + node['meta'] = meta + nodes.append(node) + return nodes + + @classmethod + def get_type_nodes_tree_or_cached(cls, user): + key = f'perms:type-nodes-tree:{user.id}:{current_org.id}' + nodes = cache.get(key) + if nodes is None: + nodes = cls(user).get_type_nodes_tree() + nodes_json = json.dumps(nodes, cls=JSONEncoder) + cache.set(key, nodes_json, 60 * 60 * 24) + else: + nodes = json.loads(nodes) + return nodes + + def refresh_type_nodes_tree_cache(self): + logger.debug("Refresh type nodes tree cache") + key = f'perms:type-nodes-tree:{self.user.id}:{current_org.id}' + cache.delete(key) + + def refresh_favorite_assets(self): + favor_ids = FavoriteAsset.objects.filter(user=self.user).values_list('asset_id', flat=True) + favor_ids = set(favor_ids) + + with tmp_to_root_org(): + valid_ids = self.get_all_assets() \ + .filter(id__in=favor_ids) \ + .values_list('id', flat=True) + valid_ids = set(valid_ids) + + invalid_ids = favor_ids - valid_ids + FavoriteAsset.objects.filter(user=self.user, asset_id__in=invalid_ids).delete() + def get_node_assets(self, key): node = PermNode.objects.get(key=key) node.compute_node_from_and_assets_amount(self.user) @@ -90,6 +154,7 @@ class UserPermAssetUtil(AssetPermissionPermAssetUtil): assets = assets.filter(nodes__id=node.id).order_by().distinct() return assets + @timeit def _get_indirect_perm_node_all_assets(self, node): """ 获取间接授权节点下的所有资产 此算法依据 `UserAssetGrantedTreeNodeRelation` 的数据查询 @@ -134,7 +199,11 @@ class UserPermNodeUtil: self.perm_ids = AssetPermissionUtil().get_permissions_for_user(self.user, flat=True) def get_favorite_node(self): - assets_amount = UserPermAssetUtil(self.user).get_favorite_assets().count() + favor_ids = FavoriteAsset.objects \ + .filter(user=self.user) \ + .values_list('asset_id') \ + .distinct() + assets_amount = Asset.objects.all().valid().filter(id__in=favor_ids).count() return PermNode.get_favorite_node(assets_amount) def get_ungrouped_node(self): diff --git a/apps/perms/utils/user_perm_tree.py b/apps/perms/utils/user_perm_tree.py index b88b6db26..13577a9b1 100644 --- a/apps/perms/utils/user_perm_tree.py +++ b/apps/perms/utils/user_perm_tree.py @@ -3,11 +3,12 @@ from collections import defaultdict from django.conf import settings from django.core.cache import cache +from django.db import transaction from assets.models import Asset from assets.utils import NodeAssetsUtil from common.db.models import output_as_string -from common.decorators import on_transaction_commit +from common.decorators import on_transaction_commit, merge_delay_run from common.utils import get_logger from common.utils.common import lazyproperty, timeit from orgs.models import Organization @@ -23,6 +24,7 @@ from perms.models import ( PermNode ) from users.models import User +from . import UserPermAssetUtil from .permission import AssetPermissionUtil logger = get_logger(__name__) @@ -50,24 +52,74 @@ class UserPermTreeRefreshUtil(_UserPermTreeCacheMixin): def __init__(self, user): self.user = user - self.orgs = self.user.orgs.distinct() - self.org_ids = [str(o.id) for o in self.orgs] + + @lazyproperty + def orgs(self): + return self.user.orgs.distinct() + + @lazyproperty + def org_ids(self): + return [str(o.id) for o in self.orgs] @lazyproperty def cache_key_user(self): return self.get_cache_key(self.user.id) + @lazyproperty + def cache_key_time(self): + key = 'perms.user.node_tree.built_time.{}'.format(self.user.id) + return key + @timeit def refresh_if_need(self, force=False): - self._clean_user_perm_tree_for_legacy_org() + built_just_now = cache.get(self.cache_key_time) + if built_just_now: + logger.info('Refresh user perm tree just now, pass: {}'.format(built_just_now)) + return to_refresh_orgs = self.orgs if force else self._get_user_need_refresh_orgs() if not to_refresh_orgs: logger.info('Not have to refresh orgs') return - with UserGrantedTreeRebuildLock(self.user.id): + logger.info("Delay refresh user orgs: {} {}".format(self.user, [o.name for o in to_refresh_orgs])) + refresh_user_orgs_perm_tree(user_orgs=((self.user, tuple(to_refresh_orgs)),)) + refresh_user_favorite_assets(users=(self.user,)) + + @timeit + def refresh_tree_manual(self): + built_just_now = cache.get(self.cache_key_time) + if built_just_now: + logger.info('Refresh just now, pass: {}'.format(built_just_now)) + return + to_refresh_orgs = self._get_user_need_refresh_orgs() + if not to_refresh_orgs: + logger.info('Not have to refresh orgs for user: {}'.format(self.user)) + return + self.perform_refresh_user_tree(to_refresh_orgs) + + @timeit + def perform_refresh_user_tree(self, to_refresh_orgs): + # 再判断一次,毕竟构建树比较慢 + built_just_now = cache.get(self.cache_key_time) + if built_just_now: + logger.info('Refresh user perm tree just now, pass: {}'.format(built_just_now)) + return + + self._clean_user_perm_tree_for_legacy_org() + ttl = settings.PERM_TREE_REGEN_INTERVAL + cache.set(self.cache_key_time, int(time.time()), ttl) + + lock = UserGrantedTreeRebuildLock(self.user.id) + got = lock.acquire(blocking=False) + if not got: + logger.info('User perm tree rebuild lock not acquired, pass') + return + + try: for org in to_refresh_orgs: self._rebuild_user_perm_tree_for_org(org) - self._mark_user_orgs_refresh_finished(to_refresh_orgs) + self._mark_user_orgs_refresh_finished(to_refresh_orgs) + finally: + lock.release() def _rebuild_user_perm_tree_for_org(self, org): with tmp_to_org(org): @@ -75,7 +127,7 @@ class UserPermTreeRefreshUtil(_UserPermTreeCacheMixin): UserPermTreeBuildUtil(self.user).rebuild_user_perm_tree() end = time.time() logger.info( - 'Refresh user [{user}] org [{org}] perm tree, user {use_time:.2f}s' + 'Refresh user perm tree: [{user}] org [{org}] {use_time:.2f}s' ''.format(user=self.user, org=org, use_time=end - start) ) @@ -90,7 +142,7 @@ class UserPermTreeRefreshUtil(_UserPermTreeCacheMixin): cached_org_ids = self.client.smembers(self.cache_key_user) cached_org_ids = {oid.decode() for oid in cached_org_ids} to_refresh_org_ids = set(self.org_ids) - cached_org_ids - to_refresh_orgs = Organization.objects.filter(id__in=to_refresh_org_ids) + to_refresh_orgs = list(Organization.objects.filter(id__in=to_refresh_org_ids)) logger.info(f'Need to refresh orgs: {to_refresh_orgs}') return to_refresh_orgs @@ -128,7 +180,8 @@ class UserPermTreeExpireUtil(_UserPermTreeCacheMixin): self.expire_perm_tree_for_user_groups_orgs(group_ids, org_ids) def expire_perm_tree_for_user_groups_orgs(self, group_ids, org_ids): - user_ids = User.groups.through.objects.filter(usergroup_id__in=group_ids) \ + user_ids = User.groups.through.objects \ + .filter(usergroup_id__in=group_ids) \ .values_list('user_id', flat=True).distinct() self.expire_perm_tree_for_users_orgs(user_ids, org_ids) @@ -151,6 +204,21 @@ class UserPermTreeExpireUtil(_UserPermTreeCacheMixin): logger.info('Expire all user perm tree') +@merge_delay_run(ttl=20) +def refresh_user_orgs_perm_tree(user_orgs=()): + for user, orgs in user_orgs: + util = UserPermTreeRefreshUtil(user) + util.perform_refresh_user_tree(orgs) + + +@merge_delay_run(ttl=20) +def refresh_user_favorite_assets(users=()): + for user in users: + util = UserPermAssetUtil(user) + util.refresh_favorite_assets() + util.refresh_type_nodes_tree_cache() + + class UserPermTreeBuildUtil(object): node_only_fields = ('id', 'key', 'parent_key', 'org_id') @@ -161,13 +229,14 @@ class UserPermTreeBuildUtil(object): self._perm_nodes_key_node_mapper = {} def rebuild_user_perm_tree(self): - self.clean_user_perm_tree() - if not self.user_perm_ids: - logger.info('User({}) not have permissions'.format(self.user)) - return - self.compute_perm_nodes() - self.compute_perm_nodes_asset_amount() - self.create_mapping_nodes() + with transaction.atomic(): + self.clean_user_perm_tree() + if not self.user_perm_ids: + logger.info('User({}) not have permissions'.format(self.user)) + return + self.compute_perm_nodes() + self.compute_perm_nodes_asset_amount() + self.create_mapping_nodes() def clean_user_perm_tree(self): UserAssetGrantedTreeNodeRelation.objects.filter(user=self.user).delete() diff --git a/apps/rbac/permissions.py b/apps/rbac/permissions.py index 7c3f21610..cffc22e71 100644 --- a/apps/rbac/permissions.py +++ b/apps/rbac/permissions.py @@ -139,7 +139,7 @@ class RBACPermission(permissions.DjangoModelPermissions): if isinstance(perms, str): perms = [perms] has = request.user.has_perms(perms) - logger.debug('View require perms: {}, result: {}'.format(perms, has)) + logger.debug('Api require perms: {}, result: {}'.format(perms, has)) return has def has_object_permission(self, request, view, obj): diff --git a/apps/settings/api/email.py b/apps/settings/api/email.py index 1e8ef2286..3790752d5 100644 --- a/apps/settings/api/email.py +++ b/apps/settings/api/email.py @@ -4,11 +4,12 @@ from smtplib import SMTPSenderRefused from django.conf import settings -from django.core.mail import send_mail, get_connection +from django.core.mail import send_mail from django.utils.translation import gettext_lazy as _ from rest_framework.views import Response, APIView from common.utils import get_logger +from common.tasks import get_email_connection as get_connection from .. import serializers logger = get_logger(__file__) diff --git a/apps/settings/api/ldap.py b/apps/settings/api/ldap.py index 9c619e24d..f13a2e9af 100644 --- a/apps/settings/api/ldap.py +++ b/apps/settings/api/ldap.py @@ -137,7 +137,7 @@ class LDAPUserImportAPI(APIView): return Response({'msg': _('Get ldap users is None')}, status=400) orgs = self.get_orgs() - errors = LDAPImportUtil().perform_import(users, orgs) + new_users, errors = LDAPImportUtil().perform_import(users, orgs) if errors: return Response({'errors': errors}, status=400) diff --git a/apps/settings/notifications.py b/apps/settings/notifications.py new file mode 100644 index 000000000..5a80c966e --- /dev/null +++ b/apps/settings/notifications.py @@ -0,0 +1,36 @@ +from django.template.loader import render_to_string +from django.utils.translation import gettext as _ + +from common.utils import get_logger +from common.utils.timezone import local_now_display +from notifications.notifications import UserMessage + +logger = get_logger(__file__) + + +class LDAPImportMessage(UserMessage): + def __init__(self, user, extra_kwargs): + super().__init__(user) + self.orgs = extra_kwargs.pop('orgs', []) + self.end_time = extra_kwargs.pop('end_time', '') + self.start_time = extra_kwargs.pop('start_time', '') + self.time_start_display = extra_kwargs.pop('time_start_display', '') + self.new_users = extra_kwargs.pop('new_users', []) + self.errors = extra_kwargs.pop('errors', []) + self.cost_time = extra_kwargs.pop('cost_time', '') + + def get_html_msg(self) -> dict: + subject = _('Notification of Synchronized LDAP User Task Results') + context = { + 'orgs': self.orgs, + 'start_time': self.time_start_display, + 'end_time': local_now_display(), + 'cost_time': self.cost_time, + 'users': self.new_users, + 'errors': self.errors + } + message = render_to_string('ldap/_msg_import_ldap_user.html', context) + return { + 'subject': subject, + 'message': message + } diff --git a/apps/settings/serializers/auth/ldap.py b/apps/settings/serializers/auth/ldap.py index 054fe6144..a79c0081f 100644 --- a/apps/settings/serializers/auth/ldap.py +++ b/apps/settings/serializers/auth/ldap.py @@ -77,6 +77,9 @@ class LDAPSettingSerializer(serializers.Serializer): required=False, label=_('Connect timeout (s)'), ) AUTH_LDAP_SEARCH_PAGED_SIZE = serializers.IntegerField(required=False, label=_('Search paged size (piece)')) + AUTH_LDAP_SYNC_RECEIVERS = serializers.ListField( + required=False, label=_('Recipient'), max_length=36 + ) AUTH_LDAP = serializers.BooleanField(required=False, label=_('Enable LDAP auth')) diff --git a/apps/settings/serializers/feature.py b/apps/settings/serializers/feature.py index 083e2749a..a1a734d54 100644 --- a/apps/settings/serializers/feature.py +++ b/apps/settings/serializers/feature.py @@ -55,6 +55,17 @@ class VaultSettingSerializer(serializers.Serializer): max_length=256, allow_blank=True, required=False, label=_('Mount Point') ) + HISTORY_ACCOUNT_CLEAN_LIMIT = serializers.IntegerField( + default=999, max_value=999, min_value=1, + required=False, label=_('Historical accounts retained count'), + help_text=_( + 'If the specific value is less than 999, ' + 'the system will automatically perform a task every night: ' + 'check and delete historical accounts that exceed the predetermined number. ' + 'If the value reaches or exceeds 999, no historical account deletion will be performed.' + ) + ) + class ChatAISettingSerializer(serializers.Serializer): PREFIX_TITLE = _('Chat AI') diff --git a/apps/settings/serializers/msg.py b/apps/settings/serializers/msg.py index 07e8e7205..ace4ab42c 100644 --- a/apps/settings/serializers/msg.py +++ b/apps/settings/serializers/msg.py @@ -1,11 +1,12 @@ # coding: utf-8 # - +from django.db import models from django.utils.translation import gettext_lazy as _ from rest_framework import serializers from common.serializers.fields import EncryptedField + __all__ = [ 'MailTestSerializer', 'EmailSettingSerializer', 'EmailContentSettingSerializer', 'SMSBackendSerializer', @@ -18,14 +19,20 @@ class MailTestSerializer(serializers.Serializer): class EmailSettingSerializer(serializers.Serializer): - # encrypt_fields 现在使用 write_only 来判断了 PREFIX_TITLE = _('Email') - EMAIL_HOST = serializers.CharField(max_length=1024, required=True, label=_("SMTP host")) - EMAIL_PORT = serializers.CharField(max_length=5, required=True, label=_("SMTP port")) - EMAIL_HOST_USER = serializers.CharField(max_length=128, required=True, label=_("SMTP account")) + class EmailProtocol(models.TextChoices): + smtp = 'smtp', _('SMTP') + exchange = 'exchange', _('EXCHANGE') + + EMAIL_PROTOCOL = serializers.ChoiceField( + choices=EmailProtocol.choices, label=_("Protocol"), default=EmailProtocol.smtp + ) + EMAIL_HOST = serializers.CharField(max_length=1024, required=True, label=_("Host")) + EMAIL_PORT = serializers.CharField(max_length=5, required=True, label=_("Port")) + EMAIL_HOST_USER = serializers.CharField(max_length=128, required=True, label=_("Account")) EMAIL_HOST_PASSWORD = EncryptedField( - max_length=1024, required=False, label=_("SMTP password"), + max_length=1024, required=False, label=_("Password"), help_text=_("Tips: Some provider use token except password") ) EMAIL_FROM = serializers.CharField( diff --git a/apps/settings/tasks/ldap.py b/apps/settings/tasks/ldap.py index 0530680e8..e662eeaeb 100644 --- a/apps/settings/tasks/ldap.py +++ b/apps/settings/tasks/ldap.py @@ -1,15 +1,19 @@ # coding: utf-8 # +import time from celery import shared_task from django.conf import settings from django.utils.translation import gettext_lazy as _ from common.utils import get_logger +from common.utils.timezone import local_now_display from ops.celery.decorator import after_app_ready_start from ops.celery.utils import ( create_or_update_celery_periodic_tasks, disable_celery_periodic_task ) from orgs.models import Organization +from settings.notifications import LDAPImportMessage +from users.models import User from ..utils import LDAPSyncUtil, LDAPServerUtil, LDAPImportUtil __all__ = ['sync_ldap_user', 'import_ldap_user_periodic', 'import_ldap_user'] @@ -23,6 +27,8 @@ def sync_ldap_user(): @shared_task(verbose_name=_('Periodic import ldap user')) def import_ldap_user(): + start_time = time.time() + time_start_display = local_now_display() logger.info("Start import ldap user task") util_server = LDAPServerUtil() util_import = LDAPImportUtil() @@ -35,11 +41,26 @@ def import_ldap_user(): org_ids = [Organization.DEFAULT_ID] default_org = Organization.default() orgs = list(set([Organization.get_instance(org_id, default=default_org) for org_id in org_ids])) - errors = util_import.perform_import(users, orgs) + new_users, errors = util_import.perform_import(users, orgs) if errors: logger.error("Imported LDAP users errors: {}".format(errors)) else: logger.info('Imported {} users successfully'.format(len(users))) + if settings.AUTH_LDAP_SYNC_RECEIVERS: + user_ids = settings.AUTH_LDAP_SYNC_RECEIVERS + recipient_list = User.objects.filter(id__in=list(user_ids)) + end_time = time.time() + extra_kwargs = { + 'orgs': orgs, + 'end_time': end_time, + 'start_time': start_time, + 'time_start_display': time_start_display, + 'new_users': new_users, + 'errors': errors, + 'cost_time': end_time - start_time, + } + for user in recipient_list: + LDAPImportMessage(user, extra_kwargs).publish() @shared_task(verbose_name=_('Registration periodic import ldap user task')) diff --git a/apps/settings/templates/ldap/_msg_import_ldap_user.html b/apps/settings/templates/ldap/_msg_import_ldap_user.html new file mode 100644 index 000000000..f801dde36 --- /dev/null +++ b/apps/settings/templates/ldap/_msg_import_ldap_user.html @@ -0,0 +1,30 @@ +{% load i18n %} +

{% trans "Sync task Finish" %}

+{% trans 'Time' %}: +
    +
  • {% trans 'Date start' %}: {{ start_time }}
  • +
  • {% trans 'Date end' %}: {{ end_time }}
  • +
  • {% trans 'Time cost' %}: {{ cost_time| floatformat:0 }}s
  • +
+{% trans "Synced Organization" %}: +
    + {% for org in orgs %} +
  • {{ org }}
  • + {% endfor %} +
+{% trans "Synced User" %}: +
    + {% for user in users %} +
  • {{ user }}
  • + {% endfor %} +
+{% if errors %} + {% trans 'Error' %}: +
    + {% for error in errors %} +
  • {{ error }}
  • + {% endfor %} +
+{% endif %} + + diff --git a/apps/settings/utils/ldap.py b/apps/settings/utils/ldap.py index 23b7b3882..6333f0350 100644 --- a/apps/settings/utils/ldap.py +++ b/apps/settings/utils/ldap.py @@ -400,11 +400,14 @@ class LDAPImportUtil(object): logger.info('Start perform import ldap users, count: {}'.format(len(users))) errors = [] objs = [] + new_users = [] group_users_mapper = defaultdict(set) for user in users: groups = user.pop('groups', []) try: obj, created = self.update_or_create(user) + if created: + new_users.append(obj) objs.append(obj) except Exception as e: errors.append({user['username']: str(e)}) @@ -421,14 +424,13 @@ class LDAPImportUtil(object): for org in orgs: self.bind_org(org, objs, group_users_mapper) logger.info('End perform import ldap users') - return errors + return new_users, errors - @staticmethod - def exit_user_group(user_groups_mapper): + def exit_user_group(self, user_groups_mapper): # 通过对比查询本次导入用户需要移除的用户组 group_remove_users_mapper = defaultdict(set) for user, current_groups in user_groups_mapper.items(): - old_groups = set(user.groups.all()) + old_groups = set(user.groups.filter(name__startswith=self.user_group_name_prefix)) exit_groups = old_groups - current_groups logger.debug(f'Ldap user {user} exits user groups {exit_groups}') for g in exit_groups: diff --git a/apps/tickets/api/ticket.py b/apps/tickets/api/ticket.py index da60aefe8..ebac1c65a 100644 --- a/apps/tickets/api/ticket.py +++ b/apps/tickets/api/ticket.py @@ -4,6 +4,7 @@ from django.utils.translation import gettext_lazy as _ from rest_framework import viewsets from rest_framework.decorators import action from rest_framework.exceptions import MethodNotAllowed +from rest_framework.permissions import IsAuthenticated from rest_framework.response import Response from audits.handler import create_or_update_operate_log @@ -41,7 +42,6 @@ class TicketViewSet(CommonApiMixin, viewsets.ModelViewSet): ordering = ('-date_created',) rbac_perms = { 'open': 'tickets.view_ticket', - 'bulk': 'tickets.change_ticket', } def retrieve(self, request, *args, **kwargs): @@ -122,7 +122,7 @@ class TicketViewSet(CommonApiMixin, viewsets.ModelViewSet): self._record_operate_log(instance, TicketAction.close) return Response('ok') - @action(detail=False, methods=[PUT], permission_classes=[RBACPermission, ]) + @action(detail=False, methods=[PUT], permission_classes=[IsAuthenticated, ]) def bulk(self, request, *args, **kwargs): self.ticket_not_allowed() diff --git a/apps/users/api/group.py b/apps/users/api/group.py index 6cccfb4a2..1e34a7caa 100644 --- a/apps/users/api/group.py +++ b/apps/users/api/group.py @@ -6,7 +6,7 @@ from rest_framework.response import Response from orgs.mixins.api import OrgBulkModelViewSet from ..models import UserGroup, User -from ..serializers import UserGroupSerializer +from ..serializers import UserGroupSerializer, UserGroupListSerializer __all__ = ['UserGroupViewSet'] @@ -15,7 +15,10 @@ class UserGroupViewSet(OrgBulkModelViewSet): model = UserGroup filterset_fields = ("name",) search_fields = filterset_fields - serializer_class = UserGroupSerializer + serializer_classes = { + 'default': UserGroupSerializer, + 'list': UserGroupListSerializer, + } ordering = ('name',) rbac_perms = ( ("add_all_users", "users.add_usergroup"), diff --git a/apps/users/serializers/group.py b/apps/users/serializers/group.py index 2276b6e0e..4c0de20f6 100644 --- a/apps/users/serializers/group.py +++ b/apps/users/serializers/group.py @@ -1,7 +1,8 @@ # -*- coding: utf-8 -*- # -from django.db.models import Count +from django.db.models import Count, Q from django.utils.translation import gettext_lazy as _ +from rest_framework import serializers from common.serializers.fields import ObjectRelatedField from common.serializers.mixin import ResourceLabelsMixin @@ -10,7 +11,7 @@ from .. import utils from ..models import User, UserGroup __all__ = [ - 'UserGroupSerializer', + 'UserGroupSerializer', 'UserGroupListSerializer', ] @@ -29,7 +30,6 @@ class UserGroupSerializer(ResourceLabelsMixin, BulkOrgResourceModelSerializer): fields = fields_mini + fields_small + ['users', 'labels'] extra_kwargs = { 'created_by': {'label': _('Created by'), 'read_only': True}, - 'users_amount': {'label': _('Users amount')}, 'id': {'label': _('ID')}, } @@ -45,6 +45,17 @@ class UserGroupSerializer(ResourceLabelsMixin, BulkOrgResourceModelSerializer): @classmethod def setup_eager_loading(cls, queryset): """ Perform necessary eager loading of data. """ - queryset = queryset.prefetch_related('users', 'labels', 'labels__label') \ - .annotate(users_amount=Count('users')) + queryset = queryset.prefetch_related('labels', 'labels__label') \ + .annotate(users_amount=Count('users', filter=Q(users__is_service_account=False))) return queryset + + +class UserGroupListSerializer(UserGroupSerializer): + users_amount = serializers.IntegerField(label=_('Users amount'), read_only=True) + + class Meta(UserGroupSerializer.Meta): + fields = list(set(UserGroupSerializer.Meta.fields + ['users_amount']) - {'users'}) + extra_kwargs = { + **UserGroupSerializer.Meta.extra_kwargs, + 'users_amount': {'label': _('Users amount')}, + } diff --git a/apps/users/signal_handlers.py b/apps/users/signal_handlers.py index 6e53bb87b..8e1f92254 100644 --- a/apps/users/signal_handlers.py +++ b/apps/users/signal_handlers.py @@ -163,9 +163,9 @@ def on_openid_create_or_update_user(sender, request, user, created, name, userna user.save() -@shared_task(verbose_name=_('Clean audits session task log')) +@shared_task(verbose_name=_('Clean up expired user sessions')) @register_as_period_task(crontab=CRONTAB_AT_PM_TWO) -def clean_audits_log_period(): +def clean_expired_user_session_period(): UserSession.clear_expired_sessions() diff --git a/apps/users/views/profile/reset.py b/apps/users/views/profile/reset.py index 96d407302..b2eed3cdd 100644 --- a/apps/users/views/profile/reset.py +++ b/apps/users/views/profile/reset.py @@ -12,6 +12,7 @@ from django.utils.translation import gettext as _ from django.views.generic import FormView, RedirectView from authentication.errors import IntervalTooShort +from authentication.utils import check_user_property_is_correct from common.utils import FlashMessageUtil, get_object_or_none, random_string from common.utils.verify_code import SendAndVerifyCodeUtil from users.notifications import ResetPasswordSuccessMsg @@ -148,7 +149,6 @@ class UserForgotPasswordView(FormView): query_key = form_type if form_type == 'sms': query_key = 'phone' - target = target.lstrip('+') try: self.safe_verify_code(token, target, form_type, code) @@ -158,7 +158,7 @@ class UserForgotPasswordView(FormView): form.add_error('code', str(e)) return super().form_invalid(form) - user = get_object_or_none(User, **{'username': username, query_key: target}) + user = check_user_property_is_correct(username, **{query_key: target}) if not user: form.add_error('code', _('No user matched')) return super().form_invalid(form) diff --git a/poetry.lock b/poetry.lock index 4b7cac7ea..3271ee6c7 100644 --- a/poetry.lock +++ b/poetry.lock @@ -40,98 +40,111 @@ reference = "tsinghua" [[package]] name = "aiohttp" -version = "3.9.1" +version = "3.8.6" description = "Async http client/server framework (asyncio)" optional = false -python-versions = ">=3.8" +python-versions = ">=3.6" files = [ - {file = "aiohttp-3.9.1-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:e1f80197f8b0b846a8d5cf7b7ec6084493950d0882cc5537fb7b96a69e3c8590"}, - {file = "aiohttp-3.9.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:c72444d17777865734aa1a4d167794c34b63e5883abb90356a0364a28904e6c0"}, - {file = "aiohttp-3.9.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:9b05d5cbe9dafcdc733262c3a99ccf63d2f7ce02543620d2bd8db4d4f7a22f83"}, - {file = "aiohttp-3.9.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5c4fa235d534b3547184831c624c0b7c1e262cd1de847d95085ec94c16fddcd5"}, - {file = "aiohttp-3.9.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:289ba9ae8e88d0ba16062ecf02dd730b34186ea3b1e7489046fc338bdc3361c4"}, - {file = "aiohttp-3.9.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:bff7e2811814fa2271be95ab6e84c9436d027a0e59665de60edf44e529a42c1f"}, - {file = "aiohttp-3.9.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:81b77f868814346662c96ab36b875d7814ebf82340d3284a31681085c051320f"}, - {file = "aiohttp-3.9.1-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3b9c7426923bb7bd66d409da46c41e3fb40f5caf679da624439b9eba92043fa6"}, - {file = "aiohttp-3.9.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:8d44e7bf06b0c0a70a20f9100af9fcfd7f6d9d3913e37754c12d424179b4e48f"}, - {file = "aiohttp-3.9.1-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:22698f01ff5653fe66d16ffb7658f582a0ac084d7da1323e39fd9eab326a1f26"}, - {file = "aiohttp-3.9.1-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:ca7ca5abfbfe8d39e653870fbe8d7710be7a857f8a8386fc9de1aae2e02ce7e4"}, - {file = "aiohttp-3.9.1-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:8d7f98fde213f74561be1d6d3fa353656197f75d4edfbb3d94c9eb9b0fc47f5d"}, - {file = "aiohttp-3.9.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:5216b6082c624b55cfe79af5d538e499cd5f5b976820eac31951fb4325974501"}, - {file = "aiohttp-3.9.1-cp310-cp310-win32.whl", hash = "sha256:0e7ba7ff228c0d9a2cd66194e90f2bca6e0abca810b786901a569c0de082f489"}, - {file = "aiohttp-3.9.1-cp310-cp310-win_amd64.whl", hash = "sha256:c7e939f1ae428a86e4abbb9a7c4732bf4706048818dfd979e5e2839ce0159f23"}, - {file = "aiohttp-3.9.1-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:df9cf74b9bc03d586fc53ba470828d7b77ce51b0582d1d0b5b2fb673c0baa32d"}, - {file = "aiohttp-3.9.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ecca113f19d5e74048c001934045a2b9368d77b0b17691d905af18bd1c21275e"}, - {file = "aiohttp-3.9.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:8cef8710fb849d97c533f259103f09bac167a008d7131d7b2b0e3a33269185c0"}, - {file = "aiohttp-3.9.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bea94403a21eb94c93386d559bce297381609153e418a3ffc7d6bf772f59cc35"}, - {file = "aiohttp-3.9.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:91c742ca59045dce7ba76cab6e223e41d2c70d79e82c284a96411f8645e2afff"}, - {file = "aiohttp-3.9.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6c93b7c2e52061f0925c3382d5cb8980e40f91c989563d3d32ca280069fd6a87"}, - {file = "aiohttp-3.9.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ee2527134f95e106cc1653e9ac78846f3a2ec1004cf20ef4e02038035a74544d"}, - {file = "aiohttp-3.9.1-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:11ff168d752cb41e8492817e10fb4f85828f6a0142b9726a30c27c35a1835f01"}, - {file = "aiohttp-3.9.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b8c3a67eb87394386847d188996920f33b01b32155f0a94f36ca0e0c635bf3e3"}, - {file = "aiohttp-3.9.1-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:c7b5d5d64e2a14e35a9240b33b89389e0035e6de8dbb7ffa50d10d8b65c57449"}, - {file = "aiohttp-3.9.1-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:69985d50a2b6f709412d944ffb2e97d0be154ea90600b7a921f95a87d6f108a2"}, - {file = "aiohttp-3.9.1-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:c9110c06eaaac7e1f5562caf481f18ccf8f6fdf4c3323feab28a93d34cc646bd"}, - {file = "aiohttp-3.9.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d737e69d193dac7296365a6dcb73bbbf53bb760ab25a3727716bbd42022e8d7a"}, - {file = "aiohttp-3.9.1-cp311-cp311-win32.whl", hash = "sha256:4ee8caa925aebc1e64e98432d78ea8de67b2272252b0a931d2ac3bd876ad5544"}, - {file = "aiohttp-3.9.1-cp311-cp311-win_amd64.whl", hash = "sha256:a34086c5cc285be878622e0a6ab897a986a6e8bf5b67ecb377015f06ed316587"}, - {file = "aiohttp-3.9.1-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:f800164276eec54e0af5c99feb9494c295118fc10a11b997bbb1348ba1a52065"}, - {file = "aiohttp-3.9.1-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:500f1c59906cd142d452074f3811614be04819a38ae2b3239a48b82649c08821"}, - {file = "aiohttp-3.9.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:0b0a6a36ed7e164c6df1e18ee47afbd1990ce47cb428739d6c99aaabfaf1b3af"}, - {file = "aiohttp-3.9.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:69da0f3ed3496808e8cbc5123a866c41c12c15baaaead96d256477edf168eb57"}, - {file = "aiohttp-3.9.1-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:176df045597e674fa950bf5ae536be85699e04cea68fa3a616cf75e413737eb5"}, - {file = "aiohttp-3.9.1-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b796b44111f0cab6bbf66214186e44734b5baab949cb5fb56154142a92989aeb"}, - {file = "aiohttp-3.9.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f27fdaadce22f2ef950fc10dcdf8048407c3b42b73779e48a4e76b3c35bca26c"}, - {file = "aiohttp-3.9.1-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:bcb6532b9814ea7c5a6a3299747c49de30e84472fa72821b07f5a9818bce0f66"}, - {file = "aiohttp-3.9.1-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:54631fb69a6e44b2ba522f7c22a6fb2667a02fd97d636048478db2fd8c4e98fe"}, - {file = "aiohttp-3.9.1-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:4b4c452d0190c5a820d3f5c0f3cd8a28ace48c54053e24da9d6041bf81113183"}, - {file = "aiohttp-3.9.1-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:cae4c0c2ca800c793cae07ef3d40794625471040a87e1ba392039639ad61ab5b"}, - {file = "aiohttp-3.9.1-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:565760d6812b8d78d416c3c7cfdf5362fbe0d0d25b82fed75d0d29e18d7fc30f"}, - {file = "aiohttp-3.9.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:54311eb54f3a0c45efb9ed0d0a8f43d1bc6060d773f6973efd90037a51cd0a3f"}, - {file = "aiohttp-3.9.1-cp312-cp312-win32.whl", hash = "sha256:85c3e3c9cb1d480e0b9a64c658cd66b3cfb8e721636ab8b0e746e2d79a7a9eed"}, - {file = "aiohttp-3.9.1-cp312-cp312-win_amd64.whl", hash = "sha256:11cb254e397a82efb1805d12561e80124928e04e9c4483587ce7390b3866d213"}, - {file = "aiohttp-3.9.1-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:8a22a34bc594d9d24621091d1b91511001a7eea91d6652ea495ce06e27381f70"}, - {file = "aiohttp-3.9.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:598db66eaf2e04aa0c8900a63b0101fdc5e6b8a7ddd805c56d86efb54eb66672"}, - {file = "aiohttp-3.9.1-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:2c9376e2b09895c8ca8b95362283365eb5c03bdc8428ade80a864160605715f1"}, - {file = "aiohttp-3.9.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:41473de252e1797c2d2293804e389a6d6986ef37cbb4a25208de537ae32141dd"}, - {file = "aiohttp-3.9.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9c5857612c9813796960c00767645cb5da815af16dafb32d70c72a8390bbf690"}, - {file = "aiohttp-3.9.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ffcd828e37dc219a72c9012ec44ad2e7e3066bec6ff3aaa19e7d435dbf4032ca"}, - {file = "aiohttp-3.9.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:219a16763dc0294842188ac8a12262b5671817042b35d45e44fd0a697d8c8361"}, - {file = "aiohttp-3.9.1-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f694dc8a6a3112059258a725a4ebe9acac5fe62f11c77ac4dcf896edfa78ca28"}, - {file = "aiohttp-3.9.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:bcc0ea8d5b74a41b621ad4a13d96c36079c81628ccc0b30cfb1603e3dfa3a014"}, - {file = "aiohttp-3.9.1-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:90ec72d231169b4b8d6085be13023ece8fa9b1bb495e4398d847e25218e0f431"}, - {file = "aiohttp-3.9.1-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:cf2a0ac0615842b849f40c4d7f304986a242f1e68286dbf3bd7a835e4f83acfd"}, - {file = "aiohttp-3.9.1-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:0e49b08eafa4f5707ecfb321ab9592717a319e37938e301d462f79b4e860c32a"}, - {file = "aiohttp-3.9.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:2c59e0076ea31c08553e868cec02d22191c086f00b44610f8ab7363a11a5d9d8"}, - {file = "aiohttp-3.9.1-cp38-cp38-win32.whl", hash = "sha256:4831df72b053b1eed31eb00a2e1aff6896fb4485301d4ccb208cac264b648db4"}, - {file = "aiohttp-3.9.1-cp38-cp38-win_amd64.whl", hash = "sha256:3135713c5562731ee18f58d3ad1bf41e1d8883eb68b363f2ffde5b2ea4b84cc7"}, - {file = "aiohttp-3.9.1-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:cfeadf42840c1e870dc2042a232a8748e75a36b52d78968cda6736de55582766"}, - {file = "aiohttp-3.9.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:70907533db712f7aa791effb38efa96f044ce3d4e850e2d7691abd759f4f0ae0"}, - {file = "aiohttp-3.9.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:cdefe289681507187e375a5064c7599f52c40343a8701761c802c1853a504558"}, - {file = "aiohttp-3.9.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d7481f581251bb5558ba9f635db70908819caa221fc79ee52a7f58392778c636"}, - {file = "aiohttp-3.9.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:49f0c1b3c2842556e5de35f122fc0f0b721334ceb6e78c3719693364d4af8499"}, - {file = "aiohttp-3.9.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0d406b01a9f5a7e232d1b0d161b40c05275ffbcbd772dc18c1d5a570961a1ca4"}, - {file = "aiohttp-3.9.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8d8e4450e7fe24d86e86b23cc209e0023177b6d59502e33807b732d2deb6975f"}, - {file = "aiohttp-3.9.1-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3c0266cd6f005e99f3f51e583012de2778e65af6b73860038b968a0a8888487a"}, - {file = "aiohttp-3.9.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:ab221850108a4a063c5b8a70f00dd7a1975e5a1713f87f4ab26a46e5feac5a0e"}, - {file = "aiohttp-3.9.1-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:c88a15f272a0ad3d7773cf3a37cc7b7d077cbfc8e331675cf1346e849d97a4e5"}, - {file = "aiohttp-3.9.1-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:237533179d9747080bcaad4d02083ce295c0d2eab3e9e8ce103411a4312991a0"}, - {file = "aiohttp-3.9.1-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:02ab6006ec3c3463b528374c4cdce86434e7b89ad355e7bf29e2f16b46c7dd6f"}, - {file = "aiohttp-3.9.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:04fa38875e53eb7e354ece1607b1d2fdee2d175ea4e4d745f6ec9f751fe20c7c"}, - {file = "aiohttp-3.9.1-cp39-cp39-win32.whl", hash = "sha256:82eefaf1a996060602f3cc1112d93ba8b201dbf5d8fd9611227de2003dddb3b7"}, - {file = "aiohttp-3.9.1-cp39-cp39-win_amd64.whl", hash = "sha256:9b05d33ff8e6b269e30a7957bd3244ffbce2a7a35a81b81c382629b80af1a8bf"}, - {file = "aiohttp-3.9.1.tar.gz", hash = "sha256:8fc49a87ac269d4529da45871e2ffb6874e87779c3d0e2ccd813c0899221239d"}, + {file = "aiohttp-3.8.6-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:41d55fc043954cddbbd82503d9cc3f4814a40bcef30b3569bc7b5e34130718c1"}, + {file = "aiohttp-3.8.6-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:1d84166673694841d8953f0a8d0c90e1087739d24632fe86b1a08819168b4566"}, + {file = "aiohttp-3.8.6-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:253bf92b744b3170eb4c4ca2fa58f9c4b87aeb1df42f71d4e78815e6e8b73c9e"}, + {file = "aiohttp-3.8.6-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3fd194939b1f764d6bb05490987bfe104287bbf51b8d862261ccf66f48fb4096"}, + {file = "aiohttp-3.8.6-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6c5f938d199a6fdbdc10bbb9447496561c3a9a565b43be564648d81e1102ac22"}, + {file = "aiohttp-3.8.6-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2817b2f66ca82ee699acd90e05c95e79bbf1dc986abb62b61ec8aaf851e81c93"}, + {file = "aiohttp-3.8.6-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0fa375b3d34e71ccccf172cab401cd94a72de7a8cc01847a7b3386204093bb47"}, + {file = "aiohttp-3.8.6-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9de50a199b7710fa2904be5a4a9b51af587ab24c8e540a7243ab737b45844543"}, + {file = "aiohttp-3.8.6-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:e1d8cb0b56b3587c5c01de3bf2f600f186da7e7b5f7353d1bf26a8ddca57f965"}, + {file = "aiohttp-3.8.6-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:8e31e9db1bee8b4f407b77fd2507337a0a80665ad7b6c749d08df595d88f1cf5"}, + {file = "aiohttp-3.8.6-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:7bc88fc494b1f0311d67f29fee6fd636606f4697e8cc793a2d912ac5b19aa38d"}, + {file = "aiohttp-3.8.6-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:ec00c3305788e04bf6d29d42e504560e159ccaf0be30c09203b468a6c1ccd3b2"}, + {file = "aiohttp-3.8.6-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:ad1407db8f2f49329729564f71685557157bfa42b48f4b93e53721a16eb813ed"}, + {file = "aiohttp-3.8.6-cp310-cp310-win32.whl", hash = "sha256:ccc360e87341ad47c777f5723f68adbb52b37ab450c8bc3ca9ca1f3e849e5fe2"}, + {file = "aiohttp-3.8.6-cp310-cp310-win_amd64.whl", hash = "sha256:93c15c8e48e5e7b89d5cb4613479d144fda8344e2d886cf694fd36db4cc86865"}, + {file = "aiohttp-3.8.6-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:6e2f9cc8e5328f829f6e1fb74a0a3a939b14e67e80832975e01929e320386b34"}, + {file = "aiohttp-3.8.6-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:e6a00ffcc173e765e200ceefb06399ba09c06db97f401f920513a10c803604ca"}, + {file = "aiohttp-3.8.6-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:41bdc2ba359032e36c0e9de5a3bd00d6fb7ea558a6ce6b70acedf0da86458321"}, + {file = "aiohttp-3.8.6-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:14cd52ccf40006c7a6cd34a0f8663734e5363fd981807173faf3a017e202fec9"}, + {file = "aiohttp-3.8.6-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2d5b785c792802e7b275c420d84f3397668e9d49ab1cb52bd916b3b3ffcf09ad"}, + {file = "aiohttp-3.8.6-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1bed815f3dc3d915c5c1e556c397c8667826fbc1b935d95b0ad680787896a358"}, + {file = "aiohttp-3.8.6-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:96603a562b546632441926cd1293cfcb5b69f0b4159e6077f7c7dbdfb686af4d"}, + {file = "aiohttp-3.8.6-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d76e8b13161a202d14c9584590c4df4d068c9567c99506497bdd67eaedf36403"}, + {file = "aiohttp-3.8.6-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:e3f1e3f1a1751bb62b4a1b7f4e435afcdade6c17a4fd9b9d43607cebd242924a"}, + {file = "aiohttp-3.8.6-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:76b36b3124f0223903609944a3c8bf28a599b2cc0ce0be60b45211c8e9be97f8"}, + {file = "aiohttp-3.8.6-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:a2ece4af1f3c967a4390c284797ab595a9f1bc1130ef8b01828915a05a6ae684"}, + {file = "aiohttp-3.8.6-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:16d330b3b9db87c3883e565340d292638a878236418b23cc8b9b11a054aaa887"}, + {file = "aiohttp-3.8.6-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:42c89579f82e49db436b69c938ab3e1559e5a4409eb8639eb4143989bc390f2f"}, + {file = "aiohttp-3.8.6-cp311-cp311-win32.whl", hash = "sha256:efd2fcf7e7b9d7ab16e6b7d54205beded0a9c8566cb30f09c1abe42b4e22bdcb"}, + {file = "aiohttp-3.8.6-cp311-cp311-win_amd64.whl", hash = "sha256:3b2ab182fc28e7a81f6c70bfbd829045d9480063f5ab06f6e601a3eddbbd49a0"}, + {file = "aiohttp-3.8.6-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:fdee8405931b0615220e5ddf8cd7edd8592c606a8e4ca2a00704883c396e4479"}, + {file = "aiohttp-3.8.6-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d25036d161c4fe2225d1abff2bd52c34ed0b1099f02c208cd34d8c05729882f0"}, + {file = "aiohttp-3.8.6-cp36-cp36m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:5d791245a894be071d5ab04bbb4850534261a7d4fd363b094a7b9963e8cdbd31"}, + {file = "aiohttp-3.8.6-cp36-cp36m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0cccd1de239afa866e4ce5c789b3032442f19c261c7d8a01183fd956b1935349"}, + {file = "aiohttp-3.8.6-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1f13f60d78224f0dace220d8ab4ef1dbc37115eeeab8c06804fec11bec2bbd07"}, + {file = "aiohttp-3.8.6-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8a9b5a0606faca4f6cc0d338359d6fa137104c337f489cd135bb7fbdbccb1e39"}, + {file = "aiohttp-3.8.6-cp36-cp36m-musllinux_1_1_aarch64.whl", hash = "sha256:13da35c9ceb847732bf5c6c5781dcf4780e14392e5d3b3c689f6d22f8e15ae31"}, + {file = "aiohttp-3.8.6-cp36-cp36m-musllinux_1_1_i686.whl", hash = "sha256:4d4cbe4ffa9d05f46a28252efc5941e0462792930caa370a6efaf491f412bc66"}, + {file = "aiohttp-3.8.6-cp36-cp36m-musllinux_1_1_ppc64le.whl", hash = "sha256:229852e147f44da0241954fc6cb910ba074e597f06789c867cb7fb0621e0ba7a"}, + {file = "aiohttp-3.8.6-cp36-cp36m-musllinux_1_1_s390x.whl", hash = "sha256:713103a8bdde61d13490adf47171a1039fd880113981e55401a0f7b42c37d071"}, + {file = "aiohttp-3.8.6-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:45ad816b2c8e3b60b510f30dbd37fe74fd4a772248a52bb021f6fd65dff809b6"}, + {file = "aiohttp-3.8.6-cp36-cp36m-win32.whl", hash = "sha256:2b8d4e166e600dcfbff51919c7a3789ff6ca8b3ecce16e1d9c96d95dd569eb4c"}, + {file = "aiohttp-3.8.6-cp36-cp36m-win_amd64.whl", hash = "sha256:0912ed87fee967940aacc5306d3aa8ba3a459fcd12add0b407081fbefc931e53"}, + {file = "aiohttp-3.8.6-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:e2a988a0c673c2e12084f5e6ba3392d76c75ddb8ebc6c7e9ead68248101cd446"}, + {file = "aiohttp-3.8.6-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebf3fd9f141700b510d4b190094db0ce37ac6361a6806c153c161dc6c041ccda"}, + {file = "aiohttp-3.8.6-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3161ce82ab85acd267c8f4b14aa226047a6bee1e4e6adb74b798bd42c6ae1f80"}, + {file = "aiohttp-3.8.6-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d95fc1bf33a9a81469aa760617b5971331cdd74370d1214f0b3109272c0e1e3c"}, + {file = "aiohttp-3.8.6-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6c43ecfef7deaf0617cee936836518e7424ee12cb709883f2c9a1adda63cc460"}, + {file = "aiohttp-3.8.6-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ca80e1b90a05a4f476547f904992ae81eda5c2c85c66ee4195bb8f9c5fb47f28"}, + {file = "aiohttp-3.8.6-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:90c72ebb7cb3a08a7f40061079817133f502a160561d0675b0a6adf231382c92"}, + {file = "aiohttp-3.8.6-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:bb54c54510e47a8c7c8e63454a6acc817519337b2b78606c4e840871a3e15349"}, + {file = "aiohttp-3.8.6-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:de6a1c9f6803b90e20869e6b99c2c18cef5cc691363954c93cb9adeb26d9f3ae"}, + {file = "aiohttp-3.8.6-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:a3628b6c7b880b181a3ae0a0683698513874df63783fd89de99b7b7539e3e8a8"}, + {file = "aiohttp-3.8.6-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:fc37e9aef10a696a5a4474802930079ccfc14d9f9c10b4662169671ff034b7df"}, + {file = "aiohttp-3.8.6-cp37-cp37m-win32.whl", hash = "sha256:f8ef51e459eb2ad8e7a66c1d6440c808485840ad55ecc3cafefadea47d1b1ba2"}, + {file = "aiohttp-3.8.6-cp37-cp37m-win_amd64.whl", hash = "sha256:b2fe42e523be344124c6c8ef32a011444e869dc5f883c591ed87f84339de5976"}, + {file = "aiohttp-3.8.6-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:9e2ee0ac5a1f5c7dd3197de309adfb99ac4617ff02b0603fd1e65b07dc772e4b"}, + {file = "aiohttp-3.8.6-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:01770d8c04bd8db568abb636c1fdd4f7140b284b8b3e0b4584f070180c1e5c62"}, + {file = "aiohttp-3.8.6-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:3c68330a59506254b556b99a91857428cab98b2f84061260a67865f7f52899f5"}, + {file = "aiohttp-3.8.6-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:89341b2c19fb5eac30c341133ae2cc3544d40d9b1892749cdd25892bbc6ac951"}, + {file = "aiohttp-3.8.6-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:71783b0b6455ac8f34b5ec99d83e686892c50498d5d00b8e56d47f41b38fbe04"}, + {file = "aiohttp-3.8.6-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f628dbf3c91e12f4d6c8b3f092069567d8eb17814aebba3d7d60c149391aee3a"}, + {file = "aiohttp-3.8.6-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b04691bc6601ef47c88f0255043df6f570ada1a9ebef99c34bd0b72866c217ae"}, + {file = "aiohttp-3.8.6-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7ee912f7e78287516df155f69da575a0ba33b02dd7c1d6614dbc9463f43066e3"}, + {file = "aiohttp-3.8.6-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9c19b26acdd08dd239e0d3669a3dddafd600902e37881f13fbd8a53943079dbc"}, + {file = "aiohttp-3.8.6-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:99c5ac4ad492b4a19fc132306cd57075c28446ec2ed970973bbf036bcda1bcc6"}, + {file = "aiohttp-3.8.6-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:f0f03211fd14a6a0aed2997d4b1c013d49fb7b50eeb9ffdf5e51f23cfe2c77fa"}, + {file = "aiohttp-3.8.6-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:8d399dade330c53b4106160f75f55407e9ae7505263ea86f2ccca6bfcbdb4921"}, + {file = "aiohttp-3.8.6-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:ec4fd86658c6a8964d75426517dc01cbf840bbf32d055ce64a9e63a40fd7b771"}, + {file = "aiohttp-3.8.6-cp38-cp38-win32.whl", hash = "sha256:33164093be11fcef3ce2571a0dccd9041c9a93fa3bde86569d7b03120d276c6f"}, + {file = "aiohttp-3.8.6-cp38-cp38-win_amd64.whl", hash = "sha256:bdf70bfe5a1414ba9afb9d49f0c912dc524cf60141102f3a11143ba3d291870f"}, + {file = "aiohttp-3.8.6-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:d52d5dc7c6682b720280f9d9db41d36ebe4791622c842e258c9206232251ab2b"}, + {file = "aiohttp-3.8.6-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:4ac39027011414dbd3d87f7edb31680e1f430834c8cef029f11c66dad0670aa5"}, + {file = "aiohttp-3.8.6-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:3f5c7ce535a1d2429a634310e308fb7d718905487257060e5d4598e29dc17f0b"}, + {file = "aiohttp-3.8.6-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b30e963f9e0d52c28f284d554a9469af073030030cef8693106d918b2ca92f54"}, + {file = "aiohttp-3.8.6-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:918810ef188f84152af6b938254911055a72e0f935b5fbc4c1a4ed0b0584aed1"}, + {file = "aiohttp-3.8.6-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:002f23e6ea8d3dd8d149e569fd580c999232b5fbc601c48d55398fbc2e582e8c"}, + {file = "aiohttp-3.8.6-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4fcf3eabd3fd1a5e6092d1242295fa37d0354b2eb2077e6eb670accad78e40e1"}, + {file = "aiohttp-3.8.6-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:255ba9d6d5ff1a382bb9a578cd563605aa69bec845680e21c44afc2670607a95"}, + {file = "aiohttp-3.8.6-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:d67f8baed00870aa390ea2590798766256f31dc5ed3ecc737debb6e97e2ede78"}, + {file = "aiohttp-3.8.6-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:86f20cee0f0a317c76573b627b954c412ea766d6ada1a9fcf1b805763ae7feeb"}, + {file = "aiohttp-3.8.6-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:39a312d0e991690ccc1a61f1e9e42daa519dcc34ad03eb6f826d94c1190190dd"}, + {file = "aiohttp-3.8.6-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:e827d48cf802de06d9c935088c2924e3c7e7533377d66b6f31ed175c1620e05e"}, + {file = "aiohttp-3.8.6-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:bd111d7fc5591ddf377a408ed9067045259ff2770f37e2d94e6478d0f3fc0c17"}, + {file = "aiohttp-3.8.6-cp39-cp39-win32.whl", hash = "sha256:caf486ac1e689dda3502567eb89ffe02876546599bbf915ec94b1fa424eeffd4"}, + {file = "aiohttp-3.8.6-cp39-cp39-win_amd64.whl", hash = "sha256:3f0e27e5b733803333bb2371249f41cf42bae8884863e8e8965ec69bebe53132"}, + {file = "aiohttp-3.8.6.tar.gz", hash = "sha256:b0cf2a4501bff9330a8a5248b4ce951851e415bdcce9dc158e76cfd55e15085c"}, ] [package.dependencies] aiosignal = ">=1.1.2" +async-timeout = ">=4.0.0a3,<5.0" attrs = ">=17.3.0" +charset-normalizer = ">=2.0,<4.0" frozenlist = ">=1.1.1" multidict = ">=4.5,<7.0" yarl = ">=1.0,<2.0" [package.extras] -speedups = ["Brotli", "aiodns", "brotlicffi"] +speedups = ["Brotli", "aiodns", "cchardet"] [package.source] type = "legacy" @@ -254,16 +267,16 @@ reference = "tsinghua" [[package]] name = "alibabacloud-tea" -version = "0.3.3" +version = "0.3.5" description = "The tea module of alibabaCloud Python SDK." optional = false python-versions = ">=3.6" files = [ - {file = "alibabacloud-tea-0.3.3.tar.gz", hash = "sha256:90f1b3310552f7cb004f713e2b55d129acd4a885bd79342df6d621422de23775"}, + {file = "alibabacloud-tea-0.3.5.tar.gz", hash = "sha256:25a5d14ed955301e381e966f66de961544356a04ba954fcf65f007f75a5c3c26"}, ] [package.dependencies] -aiohttp = ">=3.7.0,<4.0.0" +aiohttp = ">=3.7.0,<3.9.0" requests = ">=2.21.0,<3.0.0" urllib3 = "<2.0.0" @@ -506,13 +519,13 @@ reference = "tsinghua" [[package]] name = "anyio" -version = "3.7.1" +version = "4.2.0" description = "High level compatibility layer for multiple asynchronous event loop implementations" optional = false -python-versions = ">=3.7" +python-versions = ">=3.8" files = [ - {file = "anyio-3.7.1-py3-none-any.whl", hash = "sha256:91dee416e570e92c64041bd18b900d1d6fa78dff7048769ce5ac5ddad004fbb5"}, - {file = "anyio-3.7.1.tar.gz", hash = "sha256:44a3c9aba0f5defa43261a8b3efb97891f2bd7d804e0e1f56419befa1adfc780"}, + {file = "anyio-4.2.0-py3-none-any.whl", hash = "sha256:745843b39e829e108e518c489b31dc757de7d2131d53fac32bd8df268227bfee"}, + {file = "anyio-4.2.0.tar.gz", hash = "sha256:e1875bb4b4e2de1669f4bc7869b6d3f54231cdced71605e6e64c9be77e3be50f"}, ] [package.dependencies] @@ -520,9 +533,9 @@ idna = ">=2.8" sniffio = ">=1.1" [package.extras] -doc = ["Sphinx", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme (>=1.2.2)", "sphinxcontrib-jquery"] -test = ["anyio[trio]", "coverage[toml] (>=4.5)", "hypothesis (>=4.0)", "mock (>=4)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (>=0.17)"] -trio = ["trio (<0.22)"] +doc = ["Sphinx (>=7)", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme"] +test = ["anyio[trio]", "coverage[toml] (>=7)", "exceptiongroup (>=1.2.0)", "hypothesis (>=4.0)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (>=0.17)"] +trio = ["trio (>=0.23)"] [package.source] type = "legacy" @@ -621,21 +634,22 @@ reference = "tsinghua" [[package]] name = "attrs" -version = "23.1.0" +version = "23.2.0" description = "Classes Without Boilerplate" optional = false python-versions = ">=3.7" files = [ - {file = "attrs-23.1.0-py3-none-any.whl", hash = "sha256:1f28b4522cdc2fb4256ac1a020c78acf9cba2c6b461ccd2c126f3aa8e8335d04"}, - {file = "attrs-23.1.0.tar.gz", hash = "sha256:6279836d581513a26f1bf235f9acd333bc9115683f14f7e8fae46c98fc50e015"}, + {file = "attrs-23.2.0-py3-none-any.whl", hash = "sha256:99b87a485a5820b23b879f04c2305b44b951b502fd64be915879d77a7e8fc6f1"}, + {file = "attrs-23.2.0.tar.gz", hash = "sha256:935dc3b529c262f6cf76e50877d35a4bd3c1de194fd41f47a2b7ae8f19971f30"}, ] [package.extras] cov = ["attrs[tests]", "coverage[toml] (>=5.3)"] -dev = ["attrs[docs,tests]", "pre-commit"] +dev = ["attrs[tests]", "pre-commit"] docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib-towncrier", "towncrier", "zope-interface"] tests = ["attrs[tests-no-zope]", "zope-interface"] -tests-no-zope = ["cloudpickle", "hypothesis", "mypy (>=1.1.1)", "pympler", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-xdist[psutil]"] +tests-mypy = ["mypy (>=1.6)", "pytest-mypy-plugins"] +tests-no-zope = ["attrs[tests-mypy]", "cloudpickle", "hypothesis", "pympler", "pytest (>=4.3.0)", "pytest-xdist[psutil]"] [package.source] type = "legacy" @@ -716,17 +730,18 @@ reference = "tsinghua" [[package]] name = "azure-core" -version = "1.29.5" +version = "1.29.6" description = "Microsoft Azure Core Library for Python" optional = false python-versions = ">=3.7" files = [ - {file = "azure-core-1.29.5.tar.gz", hash = "sha256:52983c89d394c6f881a121e5101c5fa67278ca3b1f339c8fb2ef39230c70e9ac"}, - {file = "azure_core-1.29.5-py3-none-any.whl", hash = "sha256:0fa04b7b1f7d44a4fb8468c4093deb2ea01fdf4faddbf802ed9205615f99d68c"}, + {file = "azure-core-1.29.6.tar.gz", hash = "sha256:13b485252ecd9384ae624894fe51cfa6220966207264c360beada239f88b738a"}, + {file = "azure_core-1.29.6-py3-none-any.whl", hash = "sha256:604a005bce6a49ba661bb7b2be84a9b169047e52fcfcd0a4e4770affab4178f7"}, ] [package.dependencies] -requests = ">=2.18.4" +anyio = ">=3.0,<5.0" +requests = ">=2.21.0" six = ">=1.11.0" typing-extensions = ">=4.6.0" @@ -1047,6 +1062,22 @@ type = "legacy" url = "https://pypi.tuna.tsinghua.edu.cn/simple" reference = "tsinghua" +[[package]] +name = "cached-property" +version = "1.5.2" +description = "A decorator for caching properties in classes." +optional = false +python-versions = "*" +files = [ + {file = "cached-property-1.5.2.tar.gz", hash = "sha256:9fa5755838eecbb2d234c3aa390bd80fbd3ac6b6869109bfc1b499f7bd89a130"}, + {file = "cached_property-1.5.2-py2.py3-none-any.whl", hash = "sha256:df4f613cf7ad9a588cc381aaf4a512d26265ecebd5eb9e1ba12f1319eb85a6a0"}, +] + +[package.source] +type = "legacy" +url = "https://pypi.tuna.tsinghua.edu.cn/simple" +reference = "tsinghua" + [[package]] name = "cachetools" version = "5.3.2" @@ -1796,15 +1827,31 @@ type = "legacy" url = "https://pypi.tuna.tsinghua.edu.cn/simple" reference = "tsinghua" +[[package]] +name = "defusedxml" +version = "0.7.1" +description = "XML bomb protection for Python stdlib modules" +optional = false +python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" +files = [ + {file = "defusedxml-0.7.1-py2.py3-none-any.whl", hash = "sha256:a352e7e428770286cc899e2542b6cdaedb2b4953ff269a210103ec58f6198a61"}, + {file = "defusedxml-0.7.1.tar.gz", hash = "sha256:1bb3032db185915b62d7c6209c5a8792be6a32ab2fedacc84e01b52c51aa3e69"}, +] + +[package.source] +type = "legacy" +url = "https://pypi.tuna.tsinghua.edu.cn/simple" +reference = "tsinghua" + [[package]] name = "distro" -version = "1.8.0" +version = "1.9.0" description = "Distro - an OS platform information API" optional = false python-versions = ">=3.6" files = [ - {file = "distro-1.8.0-py3-none-any.whl", hash = "sha256:99522ca3e365cac527b44bde033f64c6945d90eb9f769703caaec52b09bbd3ff"}, - {file = "distro-1.8.0.tar.gz", hash = "sha256:02e111d1dc6a50abb8eed6bf31c3e48ed8b0830d1ea2a1b78c61765c2513fdd8"}, + {file = "distro-1.9.0-py3-none-any.whl", hash = "sha256:7bffd925d65168f85027d8da9af6bddab658135b840670a223589bc0c8ef02b2"}, + {file = "distro-1.9.0.tar.gz", hash = "sha256:2fa77c6fd8940f116ee1d6b94a2f90b13b5ea8d019b98bc8bafdcabcdd9bdbed"}, ] [package.source] @@ -1814,13 +1861,13 @@ reference = "tsinghua" [[package]] name = "django" -version = "4.1.10" +version = "4.1.13" description = "A high-level Python web framework that encourages rapid development and clean, pragmatic design." optional = false python-versions = ">=3.8" files = [ - {file = "Django-4.1.10-py3-none-any.whl", hash = "sha256:26d0260c2fb8121009e62ffc548b2398dea2522b6454208a852fb0ef264c206c"}, - {file = "Django-4.1.10.tar.gz", hash = "sha256:56343019a9fd839e2e5bf203daf45f25af79d5bffa4c71d56eae4f4404d82ade"}, + {file = "Django-4.1.13-py3-none-any.whl", hash = "sha256:04ab3f6f46d084a0bba5a2c9a93a3a2eb3fe81589512367a75f79ee8acf790ce"}, + {file = "Django-4.1.13.tar.gz", hash = "sha256:94a3f471e833c8f124ee7a2de11e92f633991d975e3fa5bdd91e8abd66426318"}, ] [package.dependencies] @@ -1921,16 +1968,17 @@ reference = "tsinghua" [[package]] name = "django-cors-headers" -version = "4.3.0" +version = "4.3.1" description = "django-cors-headers is a Django application for handling the server headers required for Cross-Origin Resource Sharing (CORS)." optional = false python-versions = ">=3.8" files = [ - {file = "django_cors_headers-4.3.0-py3-none-any.whl", hash = "sha256:bd36c7aea0d070e462f3383f0dc9ef717e5fdc2b10a99c98c285f16da84ffba2"}, - {file = "django_cors_headers-4.3.0.tar.gz", hash = "sha256:25aabc94d4837678c1edf442c7f68a5f5fd151f6767b0e0b01c61a2179d02711"}, + {file = "django-cors-headers-4.3.1.tar.gz", hash = "sha256:0bf65ef45e606aff1994d35503e6b677c0b26cafff6506f8fd7187f3be840207"}, + {file = "django_cors_headers-4.3.1-py3-none-any.whl", hash = "sha256:0b1fd19297e37417fc9f835d39e45c8c642938ddba1acce0c1753d3edef04f36"}, ] [package.dependencies] +asgiref = ">=3.6" Django = ">=3.2" [package.source] @@ -2512,6 +2560,41 @@ type = "legacy" url = "https://pypi.tuna.tsinghua.edu.cn/simple" reference = "tsinghua" +[[package]] +name = "exchangelib" +version = "5.1.0" +description = "Client for Microsoft Exchange Web Services (EWS)" +optional = false +python-versions = ">=3.8" +files = [ + {file = "exchangelib-5.1.0-py2.py3-none-any.whl", hash = "sha256:28f492df84c3d74b1183d535d34daa8c7d7a80fe69cf6b35041770824781f4b0"}, + {file = "exchangelib-5.1.0.tar.gz", hash = "sha256:f835c14d380839dc74f53664f091cafc978a158855877a510c0c5554b85cdbac"}, +] + +[package.dependencies] +cached-property = "*" +defusedxml = ">=0.6.0" +dnspython = ">=2.2.0" +isodate = "*" +lxml = ">3.0" +oauthlib = "*" +pygments = "*" +requests = ">=2.7" +requests-ntlm = ">=0.2.0" +requests-oauthlib = "*" +tzdata = "*" +tzlocal = "*" + +[package.extras] +complete = ["requests-gssapi", "requests-negotiate-sspi"] +kerberos = ["requests-gssapi"] +sspi = ["requests-negotiate-sspi"] + +[package.source] +type = "legacy" +url = "https://pypi.tuna.tsinghua.edu.cn/simple" +reference = "tsinghua" + [[package]] name = "executing" version = "2.0.1" @@ -2593,72 +2676,88 @@ reference = "tsinghua" [[package]] name = "frozenlist" -version = "1.4.0" +version = "1.4.1" description = "A list-like structure which implements collections.abc.MutableSequence" optional = false python-versions = ">=3.8" files = [ - {file = "frozenlist-1.4.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:764226ceef3125e53ea2cb275000e309c0aa5464d43bd72abd661e27fffc26ab"}, - {file = "frozenlist-1.4.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:d6484756b12f40003c6128bfcc3fa9f0d49a687e171186c2d85ec82e3758c559"}, - {file = "frozenlist-1.4.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:9ac08e601308e41eb533f232dbf6b7e4cea762f9f84f6357136eed926c15d12c"}, - {file = "frozenlist-1.4.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d081f13b095d74b67d550de04df1c756831f3b83dc9881c38985834387487f1b"}, - {file = "frozenlist-1.4.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:71932b597f9895f011f47f17d6428252fc728ba2ae6024e13c3398a087c2cdea"}, - {file = "frozenlist-1.4.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:981b9ab5a0a3178ff413bca62526bb784249421c24ad7381e39d67981be2c326"}, - {file = "frozenlist-1.4.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e41f3de4df3e80de75845d3e743b3f1c4c8613c3997a912dbf0229fc61a8b963"}, - {file = "frozenlist-1.4.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6918d49b1f90821e93069682c06ffde41829c346c66b721e65a5c62b4bab0300"}, - {file = "frozenlist-1.4.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:0e5c8764c7829343d919cc2dfc587a8db01c4f70a4ebbc49abde5d4b158b007b"}, - {file = "frozenlist-1.4.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:8d0edd6b1c7fb94922bf569c9b092ee187a83f03fb1a63076e7774b60f9481a8"}, - {file = "frozenlist-1.4.0-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:e29cda763f752553fa14c68fb2195150bfab22b352572cb36c43c47bedba70eb"}, - {file = "frozenlist-1.4.0-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:0c7c1b47859ee2cac3846fde1c1dc0f15da6cec5a0e5c72d101e0f83dcb67ff9"}, - {file = "frozenlist-1.4.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:901289d524fdd571be1c7be054f48b1f88ce8dddcbdf1ec698b27d4b8b9e5d62"}, - {file = "frozenlist-1.4.0-cp310-cp310-win32.whl", hash = "sha256:1a0848b52815006ea6596c395f87449f693dc419061cc21e970f139d466dc0a0"}, - {file = "frozenlist-1.4.0-cp310-cp310-win_amd64.whl", hash = "sha256:b206646d176a007466358aa21d85cd8600a415c67c9bd15403336c331a10d956"}, - {file = "frozenlist-1.4.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:de343e75f40e972bae1ef6090267f8260c1446a1695e77096db6cfa25e759a95"}, - {file = "frozenlist-1.4.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ad2a9eb6d9839ae241701d0918f54c51365a51407fd80f6b8289e2dfca977cc3"}, - {file = "frozenlist-1.4.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:bd7bd3b3830247580de99c99ea2a01416dfc3c34471ca1298bccabf86d0ff4dc"}, - {file = "frozenlist-1.4.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bdf1847068c362f16b353163391210269e4f0569a3c166bc6a9f74ccbfc7e839"}, - {file = "frozenlist-1.4.0-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:38461d02d66de17455072c9ba981d35f1d2a73024bee7790ac2f9e361ef1cd0c"}, - {file = "frozenlist-1.4.0-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d5a32087d720c608f42caed0ef36d2b3ea61a9d09ee59a5142d6070da9041b8f"}, - {file = "frozenlist-1.4.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:dd65632acaf0d47608190a71bfe46b209719bf2beb59507db08ccdbe712f969b"}, - {file = "frozenlist-1.4.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:261b9f5d17cac914531331ff1b1d452125bf5daa05faf73b71d935485b0c510b"}, - {file = "frozenlist-1.4.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b89ac9768b82205936771f8d2eb3ce88503b1556324c9f903e7156669f521472"}, - {file = "frozenlist-1.4.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:008eb8b31b3ea6896da16c38c1b136cb9fec9e249e77f6211d479db79a4eaf01"}, - {file = "frozenlist-1.4.0-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:e74b0506fa5aa5598ac6a975a12aa8928cbb58e1f5ac8360792ef15de1aa848f"}, - {file = "frozenlist-1.4.0-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:490132667476f6781b4c9458298b0c1cddf237488abd228b0b3650e5ecba7467"}, - {file = "frozenlist-1.4.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:76d4711f6f6d08551a7e9ef28c722f4a50dd0fc204c56b4bcd95c6cc05ce6fbb"}, - {file = "frozenlist-1.4.0-cp311-cp311-win32.whl", hash = "sha256:a02eb8ab2b8f200179b5f62b59757685ae9987996ae549ccf30f983f40602431"}, - {file = "frozenlist-1.4.0-cp311-cp311-win_amd64.whl", hash = "sha256:515e1abc578dd3b275d6a5114030b1330ba044ffba03f94091842852f806f1c1"}, - {file = "frozenlist-1.4.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:f0ed05f5079c708fe74bf9027e95125334b6978bf07fd5ab923e9e55e5fbb9d3"}, - {file = "frozenlist-1.4.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:ca265542ca427bf97aed183c1676e2a9c66942e822b14dc6e5f42e038f92a503"}, - {file = "frozenlist-1.4.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:491e014f5c43656da08958808588cc6c016847b4360e327a62cb308c791bd2d9"}, - {file = "frozenlist-1.4.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:17ae5cd0f333f94f2e03aaf140bb762c64783935cc764ff9c82dff626089bebf"}, - {file = "frozenlist-1.4.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1e78fb68cf9c1a6aa4a9a12e960a5c9dfbdb89b3695197aa7064705662515de2"}, - {file = "frozenlist-1.4.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d5655a942f5f5d2c9ed93d72148226d75369b4f6952680211972a33e59b1dfdc"}, - {file = "frozenlist-1.4.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c11b0746f5d946fecf750428a95f3e9ebe792c1ee3b1e96eeba145dc631a9672"}, - {file = "frozenlist-1.4.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e66d2a64d44d50d2543405fb183a21f76b3b5fd16f130f5c99187c3fb4e64919"}, - {file = "frozenlist-1.4.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:88f7bc0fcca81f985f78dd0fa68d2c75abf8272b1f5c323ea4a01a4d7a614efc"}, - {file = "frozenlist-1.4.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:5833593c25ac59ede40ed4de6d67eb42928cca97f26feea219f21d0ed0959b79"}, - {file = "frozenlist-1.4.0-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:fec520865f42e5c7f050c2a79038897b1c7d1595e907a9e08e3353293ffc948e"}, - {file = "frozenlist-1.4.0-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:b826d97e4276750beca7c8f0f1a4938892697a6bcd8ec8217b3312dad6982781"}, - {file = "frozenlist-1.4.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:ceb6ec0a10c65540421e20ebd29083c50e6d1143278746a4ef6bcf6153171eb8"}, - {file = "frozenlist-1.4.0-cp38-cp38-win32.whl", hash = "sha256:2b8bcf994563466db019fab287ff390fffbfdb4f905fc77bc1c1d604b1c689cc"}, - {file = "frozenlist-1.4.0-cp38-cp38-win_amd64.whl", hash = "sha256:a6c8097e01886188e5be3e6b14e94ab365f384736aa1fca6a0b9e35bd4a30bc7"}, - {file = "frozenlist-1.4.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:6c38721585f285203e4b4132a352eb3daa19121a035f3182e08e437cface44bf"}, - {file = "frozenlist-1.4.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:a0c6da9aee33ff0b1a451e867da0c1f47408112b3391dd43133838339e410963"}, - {file = "frozenlist-1.4.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:93ea75c050c5bb3d98016b4ba2497851eadf0ac154d88a67d7a6816206f6fa7f"}, - {file = "frozenlist-1.4.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f61e2dc5ad442c52b4887f1fdc112f97caeff4d9e6ebe78879364ac59f1663e1"}, - {file = "frozenlist-1.4.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:aa384489fefeb62321b238e64c07ef48398fe80f9e1e6afeff22e140e0850eef"}, - {file = "frozenlist-1.4.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:10ff5faaa22786315ef57097a279b833ecab1a0bfb07d604c9cbb1c4cdc2ed87"}, - {file = "frozenlist-1.4.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:007df07a6e3eb3e33e9a1fe6a9db7af152bbd8a185f9aaa6ece10a3529e3e1c6"}, - {file = "frozenlist-1.4.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7f4f399d28478d1f604c2ff9119907af9726aed73680e5ed1ca634d377abb087"}, - {file = "frozenlist-1.4.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:c5374b80521d3d3f2ec5572e05adc94601985cc526fb276d0c8574a6d749f1b3"}, - {file = "frozenlist-1.4.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:ce31ae3e19f3c902de379cf1323d90c649425b86de7bbdf82871b8a2a0615f3d"}, - {file = "frozenlist-1.4.0-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:7211ef110a9194b6042449431e08c4d80c0481e5891e58d429df5899690511c2"}, - {file = "frozenlist-1.4.0-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:556de4430ce324c836789fa4560ca62d1591d2538b8ceb0b4f68fb7b2384a27a"}, - {file = "frozenlist-1.4.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:7645a8e814a3ee34a89c4a372011dcd817964ce8cb273c8ed6119d706e9613e3"}, - {file = "frozenlist-1.4.0-cp39-cp39-win32.whl", hash = "sha256:19488c57c12d4e8095a922f328df3f179c820c212940a498623ed39160bc3c2f"}, - {file = "frozenlist-1.4.0-cp39-cp39-win_amd64.whl", hash = "sha256:6221d84d463fb110bdd7619b69cb43878a11d51cbb9394ae3105d082d5199167"}, - {file = "frozenlist-1.4.0.tar.gz", hash = "sha256:09163bdf0b2907454042edb19f887c6d33806adc71fbd54afc14908bfdc22251"}, + {file = "frozenlist-1.4.1-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:f9aa1878d1083b276b0196f2dfbe00c9b7e752475ed3b682025ff20c1c1f51ac"}, + {file = "frozenlist-1.4.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:29acab3f66f0f24674b7dc4736477bcd4bc3ad4b896f5f45379a67bce8b96868"}, + {file = "frozenlist-1.4.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:74fb4bee6880b529a0c6560885fce4dc95936920f9f20f53d99a213f7bf66776"}, + {file = "frozenlist-1.4.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:590344787a90ae57d62511dd7c736ed56b428f04cd8c161fcc5e7232c130c69a"}, + {file = "frozenlist-1.4.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:068b63f23b17df8569b7fdca5517edef76171cf3897eb68beb01341131fbd2ad"}, + {file = "frozenlist-1.4.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5c849d495bf5154cd8da18a9eb15db127d4dba2968d88831aff6f0331ea9bd4c"}, + {file = "frozenlist-1.4.1-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9750cc7fe1ae3b1611bb8cfc3f9ec11d532244235d75901fb6b8e42ce9229dfe"}, + {file = "frozenlist-1.4.1-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a9b2de4cf0cdd5bd2dee4c4f63a653c61d2408055ab77b151c1957f221cabf2a"}, + {file = "frozenlist-1.4.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:0633c8d5337cb5c77acbccc6357ac49a1770b8c487e5b3505c57b949b4b82e98"}, + {file = "frozenlist-1.4.1-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:27657df69e8801be6c3638054e202a135c7f299267f1a55ed3a598934f6c0d75"}, + {file = "frozenlist-1.4.1-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:f9a3ea26252bd92f570600098783d1371354d89d5f6b7dfd87359d669f2109b5"}, + {file = "frozenlist-1.4.1-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:4f57dab5fe3407b6c0c1cc907ac98e8a189f9e418f3b6e54d65a718aaafe3950"}, + {file = "frozenlist-1.4.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:e02a0e11cf6597299b9f3bbd3f93d79217cb90cfd1411aec33848b13f5c656cc"}, + {file = "frozenlist-1.4.1-cp310-cp310-win32.whl", hash = "sha256:a828c57f00f729620a442881cc60e57cfcec6842ba38e1b19fd3e47ac0ff8dc1"}, + {file = "frozenlist-1.4.1-cp310-cp310-win_amd64.whl", hash = "sha256:f56e2333dda1fe0f909e7cc59f021eba0d2307bc6f012a1ccf2beca6ba362439"}, + {file = "frozenlist-1.4.1-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:a0cb6f11204443f27a1628b0e460f37fb30f624be6051d490fa7d7e26d4af3d0"}, + {file = "frozenlist-1.4.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:b46c8ae3a8f1f41a0d2ef350c0b6e65822d80772fe46b653ab6b6274f61d4a49"}, + {file = "frozenlist-1.4.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:fde5bd59ab5357e3853313127f4d3565fc7dad314a74d7b5d43c22c6a5ed2ced"}, + {file = "frozenlist-1.4.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:722e1124aec435320ae01ee3ac7bec11a5d47f25d0ed6328f2273d287bc3abb0"}, + {file = "frozenlist-1.4.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2471c201b70d58a0f0c1f91261542a03d9a5e088ed3dc6c160d614c01649c106"}, + {file = "frozenlist-1.4.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c757a9dd70d72b076d6f68efdbb9bc943665ae954dad2801b874c8c69e185068"}, + {file = "frozenlist-1.4.1-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f146e0911cb2f1da549fc58fc7bcd2b836a44b79ef871980d605ec392ff6b0d2"}, + {file = "frozenlist-1.4.1-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4f9c515e7914626b2a2e1e311794b4c35720a0be87af52b79ff8e1429fc25f19"}, + {file = "frozenlist-1.4.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:c302220494f5c1ebeb0912ea782bcd5e2f8308037b3c7553fad0e48ebad6ad82"}, + {file = "frozenlist-1.4.1-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:442acde1e068288a4ba7acfe05f5f343e19fac87bfc96d89eb886b0363e977ec"}, + {file = "frozenlist-1.4.1-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:1b280e6507ea8a4fa0c0a7150b4e526a8d113989e28eaaef946cc77ffd7efc0a"}, + {file = "frozenlist-1.4.1-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:fe1a06da377e3a1062ae5fe0926e12b84eceb8a50b350ddca72dc85015873f74"}, + {file = "frozenlist-1.4.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:db9e724bebd621d9beca794f2a4ff1d26eed5965b004a97f1f1685a173b869c2"}, + {file = "frozenlist-1.4.1-cp311-cp311-win32.whl", hash = "sha256:e774d53b1a477a67838a904131c4b0eef6b3d8a651f8b138b04f748fccfefe17"}, + {file = "frozenlist-1.4.1-cp311-cp311-win_amd64.whl", hash = "sha256:fb3c2db03683b5767dedb5769b8a40ebb47d6f7f45b1b3e3b4b51ec8ad9d9825"}, + {file = "frozenlist-1.4.1-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:1979bc0aeb89b33b588c51c54ab0161791149f2461ea7c7c946d95d5f93b56ae"}, + {file = "frozenlist-1.4.1-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:cc7b01b3754ea68a62bd77ce6020afaffb44a590c2289089289363472d13aedb"}, + {file = "frozenlist-1.4.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:c9c92be9fd329ac801cc420e08452b70e7aeab94ea4233a4804f0915c14eba9b"}, + {file = "frozenlist-1.4.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5c3894db91f5a489fc8fa6a9991820f368f0b3cbdb9cd8849547ccfab3392d86"}, + {file = "frozenlist-1.4.1-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ba60bb19387e13597fb059f32cd4d59445d7b18b69a745b8f8e5db0346f33480"}, + {file = "frozenlist-1.4.1-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8aefbba5f69d42246543407ed2461db31006b0f76c4e32dfd6f42215a2c41d09"}, + {file = "frozenlist-1.4.1-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:780d3a35680ced9ce682fbcf4cb9c2bad3136eeff760ab33707b71db84664e3a"}, + {file = "frozenlist-1.4.1-cp312-cp312-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9acbb16f06fe7f52f441bb6f413ebae6c37baa6ef9edd49cdd567216da8600cd"}, + {file = "frozenlist-1.4.1-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:23b701e65c7b36e4bf15546a89279bd4d8675faabc287d06bbcfac7d3c33e1e6"}, + {file = "frozenlist-1.4.1-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:3e0153a805a98f5ada7e09826255ba99fb4f7524bb81bf6b47fb702666484ae1"}, + {file = "frozenlist-1.4.1-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:dd9b1baec094d91bf36ec729445f7769d0d0cf6b64d04d86e45baf89e2b9059b"}, + {file = "frozenlist-1.4.1-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:1a4471094e146b6790f61b98616ab8e44f72661879cc63fa1049d13ef711e71e"}, + {file = "frozenlist-1.4.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:5667ed53d68d91920defdf4035d1cdaa3c3121dc0b113255124bcfada1cfa1b8"}, + {file = "frozenlist-1.4.1-cp312-cp312-win32.whl", hash = "sha256:beee944ae828747fd7cb216a70f120767fc9f4f00bacae8543c14a6831673f89"}, + {file = "frozenlist-1.4.1-cp312-cp312-win_amd64.whl", hash = "sha256:64536573d0a2cb6e625cf309984e2d873979709f2cf22839bf2d61790b448ad5"}, + {file = "frozenlist-1.4.1-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:20b51fa3f588ff2fe658663db52a41a4f7aa6c04f6201449c6c7c476bd255c0d"}, + {file = "frozenlist-1.4.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:410478a0c562d1a5bcc2f7ea448359fcb050ed48b3c6f6f4f18c313a9bdb1826"}, + {file = "frozenlist-1.4.1-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:c6321c9efe29975232da3bd0af0ad216800a47e93d763ce64f291917a381b8eb"}, + {file = "frozenlist-1.4.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:48f6a4533887e189dae092f1cf981f2e3885175f7a0f33c91fb5b7b682b6bab6"}, + {file = "frozenlist-1.4.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6eb73fa5426ea69ee0e012fb59cdc76a15b1283d6e32e4f8dc4482ec67d1194d"}, + {file = "frozenlist-1.4.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:fbeb989b5cc29e8daf7f976b421c220f1b8c731cbf22b9130d8815418ea45887"}, + {file = "frozenlist-1.4.1-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:32453c1de775c889eb4e22f1197fe3bdfe457d16476ea407472b9442e6295f7a"}, + {file = "frozenlist-1.4.1-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:693945278a31f2086d9bf3df0fe8254bbeaef1fe71e1351c3bd730aa7d31c41b"}, + {file = "frozenlist-1.4.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:1d0ce09d36d53bbbe566fe296965b23b961764c0bcf3ce2fa45f463745c04701"}, + {file = "frozenlist-1.4.1-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:3a670dc61eb0d0eb7080890c13de3066790f9049b47b0de04007090807c776b0"}, + {file = "frozenlist-1.4.1-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:dca69045298ce5c11fd539682cff879cc1e664c245d1c64da929813e54241d11"}, + {file = "frozenlist-1.4.1-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:a06339f38e9ed3a64e4c4e43aec7f59084033647f908e4259d279a52d3757d09"}, + {file = "frozenlist-1.4.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:b7f2f9f912dca3934c1baec2e4585a674ef16fe00218d833856408c48d5beee7"}, + {file = "frozenlist-1.4.1-cp38-cp38-win32.whl", hash = "sha256:e7004be74cbb7d9f34553a5ce5fb08be14fb33bc86f332fb71cbe5216362a497"}, + {file = "frozenlist-1.4.1-cp38-cp38-win_amd64.whl", hash = "sha256:5a7d70357e7cee13f470c7883a063aae5fe209a493c57d86eb7f5a6f910fae09"}, + {file = "frozenlist-1.4.1-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:bfa4a17e17ce9abf47a74ae02f32d014c5e9404b6d9ac7f729e01562bbee601e"}, + {file = "frozenlist-1.4.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:b7e3ed87d4138356775346e6845cccbe66cd9e207f3cd11d2f0b9fd13681359d"}, + {file = "frozenlist-1.4.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:c99169d4ff810155ca50b4da3b075cbde79752443117d89429595c2e8e37fed8"}, + {file = "frozenlist-1.4.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:edb678da49d9f72c9f6c609fbe41a5dfb9a9282f9e6a2253d5a91e0fc382d7c0"}, + {file = "frozenlist-1.4.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6db4667b187a6742b33afbbaf05a7bc551ffcf1ced0000a571aedbb4aa42fc7b"}, + {file = "frozenlist-1.4.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:55fdc093b5a3cb41d420884cdaf37a1e74c3c37a31f46e66286d9145d2063bd0"}, + {file = "frozenlist-1.4.1-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:82e8211d69a4f4bc360ea22cd6555f8e61a1bd211d1d5d39d3d228b48c83a897"}, + {file = "frozenlist-1.4.1-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:89aa2c2eeb20957be2d950b85974b30a01a762f3308cd02bb15e1ad632e22dc7"}, + {file = "frozenlist-1.4.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:9d3e0c25a2350080e9319724dede4f31f43a6c9779be48021a7f4ebde8b2d742"}, + {file = "frozenlist-1.4.1-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:7268252af60904bf52c26173cbadc3a071cece75f873705419c8681f24d3edea"}, + {file = "frozenlist-1.4.1-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:0c250a29735d4f15321007fb02865f0e6b6a41a6b88f1f523ca1596ab5f50bd5"}, + {file = "frozenlist-1.4.1-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:96ec70beabbd3b10e8bfe52616a13561e58fe84c0101dd031dc78f250d5128b9"}, + {file = "frozenlist-1.4.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:23b2d7679b73fe0e5a4560b672a39f98dfc6f60df63823b0a9970525325b95f6"}, + {file = "frozenlist-1.4.1-cp39-cp39-win32.whl", hash = "sha256:a7496bfe1da7fb1a4e1cc23bb67c58fab69311cc7d32b5a99c2007b4b2a0e932"}, + {file = "frozenlist-1.4.1-cp39-cp39-win_amd64.whl", hash = "sha256:e6a20a581f9ce92d389a8c7d7c3dd47c81fd5d6e655c8dddf341e14aa48659d0"}, + {file = "frozenlist-1.4.1-py3-none-any.whl", hash = "sha256:04ced3e6a46b4cfffe20f9ae482818e34eba9b5fb0ce4056e4cc9b6e212d09b7"}, + {file = "frozenlist-1.4.1.tar.gz", hash = "sha256:c037a86e8513059a2613aaba4d817bb90b9d9b6b69aace3ce9c877e8c8ed402b"}, ] [package.source] @@ -2722,13 +2821,13 @@ reference = "tsinghua" [[package]] name = "google-api-core" -version = "2.14.0" +version = "2.15.0" description = "Google API client core library" optional = false python-versions = ">=3.7" files = [ - {file = "google-api-core-2.14.0.tar.gz", hash = "sha256:5368a4502b793d9bbf812a5912e13e4e69f9bd87f6efb508460c43f5bbd1ce41"}, - {file = "google_api_core-2.14.0-py3-none-any.whl", hash = "sha256:de2fb50ed34d47ddbb2bd2dcf680ee8fead46279f4ed6b16de362aca23a18952"}, + {file = "google-api-core-2.15.0.tar.gz", hash = "sha256:abc978a72658f14a2df1e5e12532effe40f94f868f6e23d95133bd6abcca35ca"}, + {file = "google_api_core-2.15.0-py3-none-any.whl", hash = "sha256:2aa56d2be495551e66bbff7f729b790546f87d5c90e74781aa77233bcb395a8a"}, ] [package.dependencies] @@ -2757,13 +2856,13 @@ reference = "tsinghua" [[package]] name = "google-auth" -version = "2.23.4" +version = "2.25.2" description = "Google Authentication Library" optional = false python-versions = ">=3.7" files = [ - {file = "google-auth-2.23.4.tar.gz", hash = "sha256:79905d6b1652187def79d491d6e23d0cbb3a21d3c7ba0dbaa9c8a01906b13ff3"}, - {file = "google_auth-2.23.4-py2.py3-none-any.whl", hash = "sha256:d4bbc92fe4b8bfd2f3e8d88e5ba7085935da208ee38a134fc280e7ce682a05f2"}, + {file = "google-auth-2.25.2.tar.gz", hash = "sha256:42f707937feb4f5e5a39e6c4f343a17300a459aaf03141457ba505812841cc40"}, + {file = "google_auth-2.25.2-py2.py3-none-any.whl", hash = "sha256:473a8dfd0135f75bb79d878436e568f2695dce456764bf3a02b6f8c540b1d256"}, ] [package.dependencies] @@ -2785,18 +2884,18 @@ reference = "tsinghua" [[package]] name = "google-cloud-compute" -version = "1.13.0" +version = "1.15.0" description = "Google Cloud Compute API client library" optional = false python-versions = ">=3.7" files = [ - {file = "google-cloud-compute-1.13.0.tar.gz", hash = "sha256:93b72129c6443c898da5a060d2021bc2d11c2a57ef2fbb9306afbb5126a376b9"}, - {file = "google_cloud_compute-1.13.0-py2.py3-none-any.whl", hash = "sha256:0f75d6c09cc504e43f4eceb2a466de9e9eb6fca819ca8ffdcf098ca5b21c7dc1"}, + {file = "google-cloud-compute-1.15.0.tar.gz", hash = "sha256:fa675aeaf04c627a442cd3032196d6f36ad68443ba327c9767a6bfbc40a42b21"}, + {file = "google_cloud_compute-1.15.0-py2.py3-none-any.whl", hash = "sha256:9eb39cae22c32c89c20c7e4f44635a7c5985a558c89f279e0f6e97edeb291e8f"}, ] [package.dependencies] google-api-core = {version = ">=1.34.0,<2.0.dev0 || >=2.11.dev0,<3.0.0dev", extras = ["grpc"]} -proto-plus = {version = ">=1.22.2,<2.0.0dev", markers = "python_version >= \"3.11\""} +proto-plus = ">=1.22.3,<2.0.0dev" protobuf = ">=3.19.5,<3.20.0 || >3.20.0,<3.20.1 || >3.20.1,<4.21.0 || >4.21.0,<4.21.1 || >4.21.1,<4.21.2 || >4.21.2,<4.21.3 || >4.21.3,<4.21.4 || >4.21.4,<4.21.5 || >4.21.5,<5.0.0dev" [package.source] @@ -2806,13 +2905,13 @@ reference = "tsinghua" [[package]] name = "googleapis-common-protos" -version = "1.61.0" +version = "1.62.0" description = "Common protobufs used in Google APIs" optional = false python-versions = ">=3.7" files = [ - {file = "googleapis-common-protos-1.61.0.tar.gz", hash = "sha256:8a64866a97f6304a7179873a465d6eee97b7a24ec6cfd78e0f575e96b821240b"}, - {file = "googleapis_common_protos-1.61.0-py2.py3-none-any.whl", hash = "sha256:22f1915393bb3245343f6efe87f6fe868532efc12aa26b391b15132e1279f1c0"}, + {file = "googleapis-common-protos-1.62.0.tar.gz", hash = "sha256:83f0ece9f94e5672cced82f592d2a5edf527a96ed1794f0bab36d5735c996277"}, + {file = "googleapis_common_protos-1.62.0-py2.py3-none-any.whl", hash = "sha256:4750113612205514f9f6aa4cb00d523a94f3e8c06c5ad2fee466387dc4875f07"}, ] [package.dependencies] @@ -2903,60 +3002,69 @@ reference = "tsinghua" [[package]] name = "grpcio" -version = "1.56.2" +version = "1.60.0" description = "HTTP/2-based RPC framework" optional = false python-versions = ">=3.7" files = [ - {file = "grpcio-1.56.2-cp310-cp310-linux_armv7l.whl", hash = "sha256:bf0b9959e673505ee5869950642428046edb91f99942607c2ecf635f8a4b31c9"}, - {file = "grpcio-1.56.2-cp310-cp310-macosx_12_0_universal2.whl", hash = "sha256:5144feb20fe76e73e60c7d73ec3bf54f320247d1ebe737d10672480371878b48"}, - {file = "grpcio-1.56.2-cp310-cp310-manylinux_2_17_aarch64.whl", hash = "sha256:a72797549935c9e0b9bc1def1768c8b5a709538fa6ab0678e671aec47ebfd55e"}, - {file = "grpcio-1.56.2-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c3f3237a57e42f79f1e560726576aedb3a7ef931f4e3accb84ebf6acc485d316"}, - {file = "grpcio-1.56.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:900bc0096c2ca2d53f2e5cebf98293a7c32f532c4aeb926345e9747452233950"}, - {file = "grpcio-1.56.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:97e0efaebbfd222bcaac2f1735c010c1d3b167112d9d237daebbeedaaccf3d1d"}, - {file = "grpcio-1.56.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c0c85c5cbe8b30a32fa6d802588d55ffabf720e985abe9590c7c886919d875d4"}, - {file = "grpcio-1.56.2-cp310-cp310-win32.whl", hash = "sha256:06e84ad9ae7668a109e970c7411e7992751a116494cba7c4fb877656527f9a57"}, - {file = "grpcio-1.56.2-cp310-cp310-win_amd64.whl", hash = "sha256:10954662f77dc36c9a1fb5cc4a537f746580d6b5734803be1e587252682cda8d"}, - {file = "grpcio-1.56.2-cp311-cp311-linux_armv7l.whl", hash = "sha256:c435f5ce1705de48e08fcbcfaf8aee660d199c90536e3e06f2016af7d6a938dd"}, - {file = "grpcio-1.56.2-cp311-cp311-macosx_10_10_universal2.whl", hash = "sha256:6108e5933eb8c22cd3646e72d5b54772c29f57482fd4c41a0640aab99eb5071d"}, - {file = "grpcio-1.56.2-cp311-cp311-manylinux_2_17_aarch64.whl", hash = "sha256:8391cea5ce72f4a12368afd17799474015d5d3dc00c936a907eb7c7eaaea98a5"}, - {file = "grpcio-1.56.2-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:750de923b456ca8c0f1354d6befca45d1f3b3a789e76efc16741bd4132752d95"}, - {file = "grpcio-1.56.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fda2783c12f553cdca11c08e5af6eecbd717280dc8fbe28a110897af1c15a88c"}, - {file = "grpcio-1.56.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:9e04d4e4cfafa7c5264e535b5d28e786f0571bea609c3f0aaab13e891e933e9c"}, - {file = "grpcio-1.56.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:89a49cc5ad08a38b6141af17e00d1dd482dc927c7605bc77af457b5a0fca807c"}, - {file = "grpcio-1.56.2-cp311-cp311-win32.whl", hash = "sha256:6a007a541dff984264981fbafeb052bfe361db63578948d857907df9488d8774"}, - {file = "grpcio-1.56.2-cp311-cp311-win_amd64.whl", hash = "sha256:af4063ef2b11b96d949dccbc5a987272f38d55c23c4c01841ea65a517906397f"}, - {file = "grpcio-1.56.2-cp37-cp37m-linux_armv7l.whl", hash = "sha256:a6ff459dac39541e6a2763a4439c4ca6bc9ecb4acc05a99b79246751f9894756"}, - {file = "grpcio-1.56.2-cp37-cp37m-macosx_10_10_universal2.whl", hash = "sha256:f20fd21f7538f8107451156dd1fe203300b79a9ddceba1ee0ac8132521a008ed"}, - {file = "grpcio-1.56.2-cp37-cp37m-manylinux_2_17_aarch64.whl", hash = "sha256:d1fbad1f9077372b6587ec589c1fc120b417b6c8ad72d3e3cc86bbbd0a3cee93"}, - {file = "grpcio-1.56.2-cp37-cp37m-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6ee26e9dfb3996aff7c870f09dc7ad44a5f6732b8bdb5a5f9905737ac6fd4ef1"}, - {file = "grpcio-1.56.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a4c60abd950d6de3e4f1ddbc318075654d275c29c846ab6a043d6ed2c52e4c8c"}, - {file = "grpcio-1.56.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:1c31e52a04e62c8577a7bf772b3e7bed4df9c9e0dd90f92b6ffa07c16cab63c9"}, - {file = "grpcio-1.56.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:345356b307cce5d14355e8e055b4ca5f99bc857c33a3dc1ddbc544fca9cd0475"}, - {file = "grpcio-1.56.2-cp37-cp37m-win_amd64.whl", hash = "sha256:42e63904ee37ae46aa23de50dac8b145b3596f43598fa33fe1098ab2cbda6ff5"}, - {file = "grpcio-1.56.2-cp38-cp38-linux_armv7l.whl", hash = "sha256:7c5ede2e2558f088c49a1ddda19080e4c23fb5d171de80a726b61b567e3766ed"}, - {file = "grpcio-1.56.2-cp38-cp38-macosx_10_10_universal2.whl", hash = "sha256:33971197c47965cc1d97d78d842163c283e998223b151bab0499b951fd2c0b12"}, - {file = "grpcio-1.56.2-cp38-cp38-manylinux_2_17_aarch64.whl", hash = "sha256:d39f5d4af48c138cb146763eda14eb7d8b3ccbbec9fe86fb724cd16e0e914c64"}, - {file = "grpcio-1.56.2-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ded637176addc1d3eef35331c39acc598bac550d213f0a1bedabfceaa2244c87"}, - {file = "grpcio-1.56.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c90da4b124647547a68cf2f197174ada30c7bb9523cb976665dfd26a9963d328"}, - {file = "grpcio-1.56.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:3ccb621749a81dc7755243665a70ce45536ec413ef5818e013fe8dfbf5aa497b"}, - {file = "grpcio-1.56.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:4eb37dd8dd1aa40d601212afa27ca5be255ba792e2e0b24d67b8af5e012cdb7d"}, - {file = "grpcio-1.56.2-cp38-cp38-win32.whl", hash = "sha256:ddb4a6061933bd9332b74eac0da25f17f32afa7145a33a0f9711ad74f924b1b8"}, - {file = "grpcio-1.56.2-cp38-cp38-win_amd64.whl", hash = "sha256:8940d6de7068af018dfa9a959a3510e9b7b543f4c405e88463a1cbaa3b2b379a"}, - {file = "grpcio-1.56.2-cp39-cp39-linux_armv7l.whl", hash = "sha256:51173e8fa6d9a2d85c14426bdee5f5c4a0654fd5fddcc21fe9d09ab0f6eb8b35"}, - {file = "grpcio-1.56.2-cp39-cp39-macosx_10_10_universal2.whl", hash = "sha256:373b48f210f43327a41e397391715cd11cfce9ded2fe76a5068f9bacf91cc226"}, - {file = "grpcio-1.56.2-cp39-cp39-manylinux_2_17_aarch64.whl", hash = "sha256:42a3bbb2bc07aef72a7d97e71aabecaf3e4eb616d39e5211e2cfe3689de860ca"}, - {file = "grpcio-1.56.2-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:5344be476ac37eb9c9ad09c22f4ea193c1316bf074f1daf85bddb1b31fda5116"}, - {file = "grpcio-1.56.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c3fa3ab0fb200a2c66493828ed06ccd1a94b12eddbfb985e7fd3e5723ff156c6"}, - {file = "grpcio-1.56.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:b975b85d1d5efc36cf8b237c5f3849b64d1ba33d6282f5e991f28751317504a1"}, - {file = "grpcio-1.56.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:cbdf2c498e077282cd427cfd88bdce4668019791deef0be8155385ab2ba7837f"}, - {file = "grpcio-1.56.2-cp39-cp39-win32.whl", hash = "sha256:139f66656a762572ae718fa0d1f2dce47c05e9fbf7a16acd704c354405b97df9"}, - {file = "grpcio-1.56.2-cp39-cp39-win_amd64.whl", hash = "sha256:830215173ad45d670140ff99aac3b461f9be9a6b11bee1a17265aaaa746a641a"}, - {file = "grpcio-1.56.2.tar.gz", hash = "sha256:0ff789ae7d8ddd76d2ac02e7d13bfef6fc4928ac01e1dcaa182be51b6bcc0aaa"}, + {file = "grpcio-1.60.0-cp310-cp310-linux_armv7l.whl", hash = "sha256:d020cfa595d1f8f5c6b343530cd3ca16ae5aefdd1e832b777f9f0eb105f5b139"}, + {file = "grpcio-1.60.0-cp310-cp310-macosx_12_0_universal2.whl", hash = "sha256:b98f43fcdb16172dec5f4b49f2fece4b16a99fd284d81c6bbac1b3b69fcbe0ff"}, + {file = "grpcio-1.60.0-cp310-cp310-manylinux_2_17_aarch64.whl", hash = "sha256:20e7a4f7ded59097c84059d28230907cd97130fa74f4a8bfd1d8e5ba18c81491"}, + {file = "grpcio-1.60.0-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:452ca5b4afed30e7274445dd9b441a35ece656ec1600b77fff8c216fdf07df43"}, + {file = "grpcio-1.60.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:43e636dc2ce9ece583b3e2ca41df5c983f4302eabc6d5f9cd04f0562ee8ec1ae"}, + {file = "grpcio-1.60.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:6e306b97966369b889985a562ede9d99180def39ad42c8014628dd3cc343f508"}, + {file = "grpcio-1.60.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:f897c3b127532e6befdcf961c415c97f320d45614daf84deba0a54e64ea2457b"}, + {file = "grpcio-1.60.0-cp310-cp310-win32.whl", hash = "sha256:b87efe4a380887425bb15f220079aa8336276398dc33fce38c64d278164f963d"}, + {file = "grpcio-1.60.0-cp310-cp310-win_amd64.whl", hash = "sha256:a9c7b71211f066908e518a2ef7a5e211670761651039f0d6a80d8d40054047df"}, + {file = "grpcio-1.60.0-cp311-cp311-linux_armv7l.whl", hash = "sha256:fb464479934778d7cc5baf463d959d361954d6533ad34c3a4f1d267e86ee25fd"}, + {file = "grpcio-1.60.0-cp311-cp311-macosx_10_10_universal2.whl", hash = "sha256:4b44d7e39964e808b071714666a812049765b26b3ea48c4434a3b317bac82f14"}, + {file = "grpcio-1.60.0-cp311-cp311-manylinux_2_17_aarch64.whl", hash = "sha256:90bdd76b3f04bdb21de5398b8a7c629676c81dfac290f5f19883857e9371d28c"}, + {file = "grpcio-1.60.0-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:91229d7203f1ef0ab420c9b53fe2ca5c1fbeb34f69b3bc1b5089466237a4a134"}, + {file = "grpcio-1.60.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3b36a2c6d4920ba88fa98075fdd58ff94ebeb8acc1215ae07d01a418af4c0253"}, + {file = "grpcio-1.60.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:297eef542156d6b15174a1231c2493ea9ea54af8d016b8ca7d5d9cc65cfcc444"}, + {file = "grpcio-1.60.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:87c9224acba0ad8bacddf427a1c2772e17ce50b3042a789547af27099c5f751d"}, + {file = "grpcio-1.60.0-cp311-cp311-win32.whl", hash = "sha256:95ae3e8e2c1b9bf671817f86f155c5da7d49a2289c5cf27a319458c3e025c320"}, + {file = "grpcio-1.60.0-cp311-cp311-win_amd64.whl", hash = "sha256:467a7d31554892eed2aa6c2d47ded1079fc40ea0b9601d9f79204afa8902274b"}, + {file = "grpcio-1.60.0-cp312-cp312-linux_armv7l.whl", hash = "sha256:a7152fa6e597c20cb97923407cf0934e14224af42c2b8d915f48bc3ad2d9ac18"}, + {file = "grpcio-1.60.0-cp312-cp312-macosx_10_10_universal2.whl", hash = "sha256:7db16dd4ea1b05ada504f08d0dca1cd9b926bed3770f50e715d087c6f00ad748"}, + {file = "grpcio-1.60.0-cp312-cp312-manylinux_2_17_aarch64.whl", hash = "sha256:b0571a5aef36ba9177e262dc88a9240c866d903a62799e44fd4aae3f9a2ec17e"}, + {file = "grpcio-1.60.0-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6fd9584bf1bccdfff1512719316efa77be235469e1e3295dce64538c4773840b"}, + {file = "grpcio-1.60.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d6a478581b1a1a8fdf3318ecb5f4d0cda41cacdffe2b527c23707c9c1b8fdb55"}, + {file = "grpcio-1.60.0-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:77c8a317f0fd5a0a2be8ed5cbe5341537d5c00bb79b3bb27ba7c5378ba77dbca"}, + {file = "grpcio-1.60.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:1c30bb23a41df95109db130a6cc1b974844300ae2e5d68dd4947aacba5985aa5"}, + {file = "grpcio-1.60.0-cp312-cp312-win32.whl", hash = "sha256:2aef56e85901c2397bd557c5ba514f84de1f0ae5dd132f5d5fed042858115951"}, + {file = "grpcio-1.60.0-cp312-cp312-win_amd64.whl", hash = "sha256:e381fe0c2aa6c03b056ad8f52f8efca7be29fb4d9ae2f8873520843b6039612a"}, + {file = "grpcio-1.60.0-cp37-cp37m-linux_armv7l.whl", hash = "sha256:92f88ca1b956eb8427a11bb8b4a0c0b2b03377235fc5102cb05e533b8693a415"}, + {file = "grpcio-1.60.0-cp37-cp37m-macosx_10_10_universal2.whl", hash = "sha256:e278eafb406f7e1b1b637c2cf51d3ad45883bb5bd1ca56bc05e4fc135dfdaa65"}, + {file = "grpcio-1.60.0-cp37-cp37m-manylinux_2_17_aarch64.whl", hash = "sha256:a48edde788b99214613e440fce495bbe2b1e142a7f214cce9e0832146c41e324"}, + {file = "grpcio-1.60.0-cp37-cp37m-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:de2ad69c9a094bf37c1102b5744c9aec6cf74d2b635558b779085d0263166454"}, + {file = "grpcio-1.60.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:073f959c6f570797272f4ee9464a9997eaf1e98c27cb680225b82b53390d61e6"}, + {file = "grpcio-1.60.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:c826f93050c73e7769806f92e601e0efdb83ec8d7c76ddf45d514fee54e8e619"}, + {file = "grpcio-1.60.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:9e30be89a75ee66aec7f9e60086fadb37ff8c0ba49a022887c28c134341f7179"}, + {file = "grpcio-1.60.0-cp37-cp37m-win_amd64.whl", hash = "sha256:b0fb2d4801546598ac5cd18e3ec79c1a9af8b8f2a86283c55a5337c5aeca4b1b"}, + {file = "grpcio-1.60.0-cp38-cp38-linux_armv7l.whl", hash = "sha256:9073513ec380434eb8d21970e1ab3161041de121f4018bbed3146839451a6d8e"}, + {file = "grpcio-1.60.0-cp38-cp38-macosx_10_10_universal2.whl", hash = "sha256:74d7d9fa97809c5b892449b28a65ec2bfa458a4735ddad46074f9f7d9550ad13"}, + {file = "grpcio-1.60.0-cp38-cp38-manylinux_2_17_aarch64.whl", hash = "sha256:1434ca77d6fed4ea312901122dc8da6c4389738bf5788f43efb19a838ac03ead"}, + {file = "grpcio-1.60.0-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e61e76020e0c332a98290323ecfec721c9544f5b739fab925b6e8cbe1944cf19"}, + {file = "grpcio-1.60.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:675997222f2e2f22928fbba640824aebd43791116034f62006e19730715166c0"}, + {file = "grpcio-1.60.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:5208a57eae445ae84a219dfd8b56e04313445d146873117b5fa75f3245bc1390"}, + {file = "grpcio-1.60.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:428d699c8553c27e98f4d29fdc0f0edc50e9a8a7590bfd294d2edb0da7be3629"}, + {file = "grpcio-1.60.0-cp38-cp38-win32.whl", hash = "sha256:83f2292ae292ed5a47cdcb9821039ca8e88902923198f2193f13959360c01860"}, + {file = "grpcio-1.60.0-cp38-cp38-win_amd64.whl", hash = "sha256:705a68a973c4c76db5d369ed573fec3367d7d196673fa86614b33d8c8e9ebb08"}, + {file = "grpcio-1.60.0-cp39-cp39-linux_armv7l.whl", hash = "sha256:c193109ca4070cdcaa6eff00fdb5a56233dc7610216d58fb81638f89f02e4968"}, + {file = "grpcio-1.60.0-cp39-cp39-macosx_10_10_universal2.whl", hash = "sha256:676e4a44e740deaba0f4d95ba1d8c5c89a2fcc43d02c39f69450b1fa19d39590"}, + {file = "grpcio-1.60.0-cp39-cp39-manylinux_2_17_aarch64.whl", hash = "sha256:5ff21e000ff2f658430bde5288cb1ac440ff15c0d7d18b5fb222f941b46cb0d2"}, + {file = "grpcio-1.60.0-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4c86343cf9ff7b2514dd229bdd88ebba760bd8973dac192ae687ff75e39ebfab"}, + {file = "grpcio-1.60.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0fd3b3968ffe7643144580f260f04d39d869fcc2cddb745deef078b09fd2b328"}, + {file = "grpcio-1.60.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:30943b9530fe3620e3b195c03130396cd0ee3a0d10a66c1bee715d1819001eaf"}, + {file = "grpcio-1.60.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:b10241250cb77657ab315270b064a6c7f1add58af94befa20687e7c8d8603ae6"}, + {file = "grpcio-1.60.0-cp39-cp39-win32.whl", hash = "sha256:79a050889eb8d57a93ed21d9585bb63fca881666fc709f5d9f7f9372f5e7fd03"}, + {file = "grpcio-1.60.0-cp39-cp39-win_amd64.whl", hash = "sha256:8a97a681e82bc11a42d4372fe57898d270a2707f36c45c6676e49ce0d5c41353"}, + {file = "grpcio-1.60.0.tar.gz", hash = "sha256:2199165a1affb666aa24adf0c97436686d0a61bc5fc113c037701fb7c7fceb96"}, ] [package.extras] -protobuf = ["grpcio-tools (>=1.56.2)"] +protobuf = ["grpcio-tools (>=1.60.0)"] [package.source] type = "legacy" @@ -2965,18 +3073,18 @@ reference = "tsinghua" [[package]] name = "grpcio-status" -version = "1.56.2" +version = "1.60.0" description = "Status proto mapping for gRPC" optional = false python-versions = ">=3.6" files = [ - {file = "grpcio-status-1.56.2.tar.gz", hash = "sha256:a046b2c0118df4a5687f4585cca9d3c3bae5c498c4dff055dcb43fb06a1180c8"}, - {file = "grpcio_status-1.56.2-py3-none-any.whl", hash = "sha256:63f3842867735f59f5d70e723abffd2e8501a6bcd915612a1119e52f10614782"}, + {file = "grpcio-status-1.60.0.tar.gz", hash = "sha256:f10e0b6db3adc0fdc244b71962814ee982996ef06186446b5695b9fa635aa1ab"}, + {file = "grpcio_status-1.60.0-py3-none-any.whl", hash = "sha256:7d383fa36e59c1e61d380d91350badd4d12ac56e4de2c2b831b050362c3c572e"}, ] [package.dependencies] googleapis-common-protos = ">=1.5.5" -grpcio = ">=1.56.2" +grpcio = ">=1.60.0" protobuf = ">=4.21.6" [package.source] @@ -3089,19 +3197,19 @@ reference = "tsinghua" [[package]] name = "httpx" -version = "0.25.1" +version = "0.26.0" description = "The next generation HTTP client." optional = false python-versions = ">=3.8" files = [ - {file = "httpx-0.25.1-py3-none-any.whl", hash = "sha256:fec7d6cc5c27c578a391f7e87b9aa7d3d8fbcd034f6399f9f79b45bcc12a866a"}, - {file = "httpx-0.25.1.tar.gz", hash = "sha256:ffd96d5cf901e63863d9f1b4b6807861dbea4d301613415d9e6e57ead15fc5d0"}, + {file = "httpx-0.26.0-py3-none-any.whl", hash = "sha256:8915f5a3627c4d47b73e8202457cb28f1266982d1159bd5779d86a80c0eab1cd"}, + {file = "httpx-0.26.0.tar.gz", hash = "sha256:451b55c30d5185ea6b23c2c793abf9bb237d2a7dfb901ced6ff69ad37ec1dfaf"}, ] [package.dependencies] anyio = "*" certifi = "*" -httpcore = "*" +httpcore = "==1.*" idna = "*" sniffio = "*" @@ -3677,110 +3785,106 @@ reference = "tsinghua" [[package]] name = "lxml" -version = "4.9.3" +version = "5.0.0" description = "Powerful and Pythonic XML processing library combining libxml2/libxslt with the ElementTree API." optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, != 3.4.*" files = [ - {file = "lxml-4.9.3-cp27-cp27m-macosx_11_0_x86_64.whl", hash = "sha256:b0a545b46b526d418eb91754565ba5b63b1c0b12f9bd2f808c852d9b4b2f9b5c"}, - {file = "lxml-4.9.3-cp27-cp27m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:075b731ddd9e7f68ad24c635374211376aa05a281673ede86cbe1d1b3455279d"}, - {file = "lxml-4.9.3-cp27-cp27m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:1e224d5755dba2f4a9498e150c43792392ac9b5380aa1b845f98a1618c94eeef"}, - {file = "lxml-4.9.3-cp27-cp27m-win32.whl", hash = "sha256:2c74524e179f2ad6d2a4f7caf70e2d96639c0954c943ad601a9e146c76408ed7"}, - {file = "lxml-4.9.3-cp27-cp27m-win_amd64.whl", hash = "sha256:4f1026bc732b6a7f96369f7bfe1a4f2290fb34dce00d8644bc3036fb351a4ca1"}, - {file = "lxml-4.9.3-cp27-cp27mu-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:c0781a98ff5e6586926293e59480b64ddd46282953203c76ae15dbbbf302e8bb"}, - {file = "lxml-4.9.3-cp27-cp27mu-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:cef2502e7e8a96fe5ad686d60b49e1ab03e438bd9123987994528febd569868e"}, - {file = "lxml-4.9.3-cp310-cp310-macosx_11_0_x86_64.whl", hash = "sha256:b86164d2cff4d3aaa1f04a14685cbc072efd0b4f99ca5708b2ad1b9b5988a991"}, - {file = "lxml-4.9.3-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:42871176e7896d5d45138f6d28751053c711ed4d48d8e30b498da155af39aebd"}, - {file = "lxml-4.9.3-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:ae8b9c6deb1e634ba4f1930eb67ef6e6bf6a44b6eb5ad605642b2d6d5ed9ce3c"}, - {file = "lxml-4.9.3-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:411007c0d88188d9f621b11d252cce90c4a2d1a49db6c068e3c16422f306eab8"}, - {file = "lxml-4.9.3-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:cd47b4a0d41d2afa3e58e5bf1f62069255aa2fd6ff5ee41604418ca925911d76"}, - {file = "lxml-4.9.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:0e2cb47860da1f7e9a5256254b74ae331687b9672dfa780eed355c4c9c3dbd23"}, - {file = "lxml-4.9.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:1247694b26342a7bf47c02e513d32225ededd18045264d40758abeb3c838a51f"}, - {file = "lxml-4.9.3-cp310-cp310-win32.whl", hash = "sha256:cdb650fc86227eba20de1a29d4b2c1bfe139dc75a0669270033cb2ea3d391b85"}, - {file = "lxml-4.9.3-cp310-cp310-win_amd64.whl", hash = "sha256:97047f0d25cd4bcae81f9ec9dc290ca3e15927c192df17331b53bebe0e3ff96d"}, - {file = "lxml-4.9.3-cp311-cp311-macosx_11_0_universal2.whl", hash = "sha256:1f447ea5429b54f9582d4b955f5f1985f278ce5cf169f72eea8afd9502973dd5"}, - {file = "lxml-4.9.3-cp311-cp311-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:57d6ba0ca2b0c462f339640d22882acc711de224d769edf29962b09f77129cbf"}, - {file = "lxml-4.9.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:9767e79108424fb6c3edf8f81e6730666a50feb01a328f4a016464a5893f835a"}, - {file = "lxml-4.9.3-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:71c52db65e4b56b8ddc5bb89fb2e66c558ed9d1a74a45ceb7dcb20c191c3df2f"}, - {file = "lxml-4.9.3-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:d73d8ecf8ecf10a3bd007f2192725a34bd62898e8da27eb9d32a58084f93962b"}, - {file = "lxml-4.9.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:0a3d3487f07c1d7f150894c238299934a2a074ef590b583103a45002035be120"}, - {file = "lxml-4.9.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:9e28c51fa0ce5674be9f560c6761c1b441631901993f76700b1b30ca6c8378d6"}, - {file = "lxml-4.9.3-cp311-cp311-win32.whl", hash = "sha256:0bfd0767c5c1de2551a120673b72e5d4b628737cb05414f03c3277bf9bed3305"}, - {file = "lxml-4.9.3-cp311-cp311-win_amd64.whl", hash = "sha256:25f32acefac14ef7bd53e4218fe93b804ef6f6b92ffdb4322bb6d49d94cad2bc"}, - {file = "lxml-4.9.3-cp312-cp312-macosx_11_0_universal2.whl", hash = "sha256:d3ff32724f98fbbbfa9f49d82852b159e9784d6094983d9a8b7f2ddaebb063d4"}, - {file = "lxml-4.9.3-cp312-cp312-manylinux_2_28_aarch64.whl", hash = "sha256:48d6ed886b343d11493129e019da91d4039826794a3e3027321c56d9e71505be"}, - {file = "lxml-4.9.3-cp312-cp312-manylinux_2_28_x86_64.whl", hash = "sha256:9a92d3faef50658dd2c5470af249985782bf754c4e18e15afb67d3ab06233f13"}, - {file = "lxml-4.9.3-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:b4e4bc18382088514ebde9328da057775055940a1f2e18f6ad2d78aa0f3ec5b9"}, - {file = "lxml-4.9.3-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:fc9b106a1bf918db68619fdcd6d5ad4f972fdd19c01d19bdb6bf63f3589a9ec5"}, - {file = "lxml-4.9.3-cp312-cp312-win_amd64.whl", hash = "sha256:d37017287a7adb6ab77e1c5bee9bcf9660f90ff445042b790402a654d2ad81d8"}, - {file = "lxml-4.9.3-cp35-cp35m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:56dc1f1ebccc656d1b3ed288f11e27172a01503fc016bcabdcbc0978b19352b7"}, - {file = "lxml-4.9.3-cp35-cp35m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:578695735c5a3f51569810dfebd05dd6f888147a34f0f98d4bb27e92b76e05c2"}, - {file = "lxml-4.9.3-cp35-cp35m-win32.whl", hash = "sha256:704f61ba8c1283c71b16135caf697557f5ecf3e74d9e453233e4771d68a1f42d"}, - {file = "lxml-4.9.3-cp35-cp35m-win_amd64.whl", hash = "sha256:c41bfca0bd3532d53d16fd34d20806d5c2b1ace22a2f2e4c0008570bf2c58833"}, - {file = "lxml-4.9.3-cp36-cp36m-macosx_11_0_x86_64.whl", hash = "sha256:64f479d719dc9f4c813ad9bb6b28f8390360660b73b2e4beb4cb0ae7104f1c12"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:dd708cf4ee4408cf46a48b108fb9427bfa00b9b85812a9262b5c668af2533ea5"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5c31c7462abdf8f2ac0577d9f05279727e698f97ecbb02f17939ea99ae8daa98"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:e3cd95e10c2610c360154afdc2f1480aea394f4a4f1ea0a5eacce49640c9b190"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_28_x86_64.whl", hash = "sha256:4930be26af26ac545c3dffb662521d4e6268352866956672231887d18f0eaab2"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:4aec80cde9197340bc353d2768e2a75f5f60bacda2bab72ab1dc499589b3878c"}, - {file = "lxml-4.9.3-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:14e019fd83b831b2e61baed40cab76222139926b1fb5ed0e79225bc0cae14584"}, - {file = "lxml-4.9.3-cp36-cp36m-musllinux_1_1_aarch64.whl", hash = "sha256:0c0850c8b02c298d3c7006b23e98249515ac57430e16a166873fc47a5d549287"}, - {file = "lxml-4.9.3-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:aca086dc5f9ef98c512bac8efea4483eb84abbf926eaeedf7b91479feb092458"}, - {file = "lxml-4.9.3-cp36-cp36m-win32.whl", hash = "sha256:50baa9c1c47efcaef189f31e3d00d697c6d4afda5c3cde0302d063492ff9b477"}, - {file = "lxml-4.9.3-cp36-cp36m-win_amd64.whl", hash = "sha256:bef4e656f7d98aaa3486d2627e7d2df1157d7e88e7efd43a65aa5dd4714916cf"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:46f409a2d60f634fe550f7133ed30ad5321ae2e6630f13657fb9479506b00601"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:4c28a9144688aef80d6ea666c809b4b0e50010a2aca784c97f5e6bf143d9f129"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:141f1d1a9b663c679dc524af3ea1773e618907e96075262726c7612c02b149a4"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:53ace1c1fd5a74ef662f844a0413446c0629d151055340e9893da958a374f70d"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:17a753023436a18e27dd7769e798ce302963c236bc4114ceee5b25c18c52c693"}, - {file = "lxml-4.9.3-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:7d298a1bd60c067ea75d9f684f5f3992c9d6766fadbc0bcedd39750bf344c2f4"}, - {file = "lxml-4.9.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:081d32421db5df44c41b7f08a334a090a545c54ba977e47fd7cc2deece78809a"}, - {file = "lxml-4.9.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:23eed6d7b1a3336ad92d8e39d4bfe09073c31bfe502f20ca5116b2a334f8ec02"}, - {file = "lxml-4.9.3-cp37-cp37m-win32.whl", hash = "sha256:1509dd12b773c02acd154582088820893109f6ca27ef7291b003d0e81666109f"}, - {file = "lxml-4.9.3-cp37-cp37m-win_amd64.whl", hash = "sha256:120fa9349a24c7043854c53cae8cec227e1f79195a7493e09e0c12e29f918e52"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:4d2d1edbca80b510443f51afd8496be95529db04a509bc8faee49c7b0fb6d2cc"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:8d7e43bd40f65f7d97ad8ef5c9b1778943d02f04febef12def25f7583d19baac"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:71d66ee82e7417828af6ecd7db817913cb0cf9d4e61aa0ac1fde0583d84358db"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:6fc3c450eaa0b56f815c7b62f2b7fba7266c4779adcf1cece9e6deb1de7305ce"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:65299ea57d82fb91c7f019300d24050c4ddeb7c5a190e076b5f48a2b43d19c42"}, - {file = "lxml-4.9.3-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:eadfbbbfb41b44034a4c757fd5d70baccd43296fb894dba0295606a7cf3124aa"}, - {file = "lxml-4.9.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:3e9bdd30efde2b9ccfa9cb5768ba04fe71b018a25ea093379c857c9dad262c40"}, - {file = "lxml-4.9.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:fcdd00edfd0a3001e0181eab3e63bd5c74ad3e67152c84f93f13769a40e073a7"}, - {file = "lxml-4.9.3-cp38-cp38-win32.whl", hash = "sha256:57aba1bbdf450b726d58b2aea5fe47c7875f5afb2c4a23784ed78f19a0462574"}, - {file = "lxml-4.9.3-cp38-cp38-win_amd64.whl", hash = "sha256:92af161ecbdb2883c4593d5ed4815ea71b31fafd7fd05789b23100d081ecac96"}, - {file = "lxml-4.9.3-cp39-cp39-macosx_11_0_x86_64.whl", hash = "sha256:9bb6ad405121241e99a86efff22d3ef469024ce22875a7ae045896ad23ba2340"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:8ed74706b26ad100433da4b9d807eae371efaa266ffc3e9191ea436087a9d6a7"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:fbf521479bcac1e25a663df882c46a641a9bff6b56dc8b0fafaebd2f66fb231b"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:303bf1edce6ced16bf67a18a1cf8339d0db79577eec5d9a6d4a80f0fb10aa2da"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:5515edd2a6d1a5a70bfcdee23b42ec33425e405c5b351478ab7dc9347228f96e"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:690dafd0b187ed38583a648076865d8c229661ed20e48f2335d68e2cf7dc829d"}, - {file = "lxml-4.9.3-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:b6420a005548ad52154c8ceab4a1290ff78d757f9e5cbc68f8c77089acd3c432"}, - {file = "lxml-4.9.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:bb3bb49c7a6ad9d981d734ef7c7193bc349ac338776a0360cc671eaee89bcf69"}, - {file = "lxml-4.9.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:d27be7405547d1f958b60837dc4c1007da90b8b23f54ba1f8b728c78fdb19d50"}, - {file = "lxml-4.9.3-cp39-cp39-win32.whl", hash = "sha256:8df133a2ea5e74eef5e8fc6f19b9e085f758768a16e9877a60aec455ed2609b2"}, - {file = "lxml-4.9.3-cp39-cp39-win_amd64.whl", hash = "sha256:4dd9a263e845a72eacb60d12401e37c616438ea2e5442885f65082c276dfb2b2"}, - {file = "lxml-4.9.3-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:6689a3d7fd13dc687e9102a27e98ef33730ac4fe37795d5036d18b4d527abd35"}, - {file = "lxml-4.9.3-pp37-pypy37_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:f6bdac493b949141b733c5345b6ba8f87a226029cbabc7e9e121a413e49441e0"}, - {file = "lxml-4.9.3-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:05186a0f1346ae12553d66df1cfce6f251589fea3ad3da4f3ef4e34b2d58c6a3"}, - {file = "lxml-4.9.3-pp37-pypy37_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:c2006f5c8d28dee289f7020f721354362fa304acbaaf9745751ac4006650254b"}, - {file = "lxml-4.9.3-pp38-pypy38_pp73-macosx_11_0_x86_64.whl", hash = "sha256:5c245b783db29c4e4fbbbfc9c5a78be496c9fea25517f90606aa1f6b2b3d5f7b"}, - {file = "lxml-4.9.3-pp38-pypy38_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:4fb960a632a49f2f089d522f70496640fdf1218f1243889da3822e0a9f5f3ba7"}, - {file = "lxml-4.9.3-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:50670615eaf97227d5dc60de2dc99fb134a7130d310d783314e7724bf163f75d"}, - {file = "lxml-4.9.3-pp38-pypy38_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:9719fe17307a9e814580af1f5c6e05ca593b12fb7e44fe62450a5384dbf61b4b"}, - {file = "lxml-4.9.3-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:3331bece23c9ee066e0fb3f96c61322b9e0f54d775fccefff4c38ca488de283a"}, - {file = "lxml-4.9.3-pp39-pypy39_pp73-macosx_11_0_x86_64.whl", hash = "sha256:ed667f49b11360951e201453fc3967344d0d0263aa415e1619e85ae7fd17b4e0"}, - {file = "lxml-4.9.3-pp39-pypy39_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:8b77946fd508cbf0fccd8e400a7f71d4ac0e1595812e66025bac475a8e811694"}, - {file = "lxml-4.9.3-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:e4da8ca0c0c0aea88fd46be8e44bd49716772358d648cce45fe387f7b92374a7"}, - {file = "lxml-4.9.3-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:fe4bda6bd4340caa6e5cf95e73f8fea5c4bfc55763dd42f1b50a94c1b4a2fbd4"}, - {file = "lxml-4.9.3-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:f3df3db1d336b9356dd3112eae5f5c2b8b377f3bc826848567f10bfddfee77e9"}, - {file = "lxml-4.9.3.tar.gz", hash = "sha256:48628bd53a426c9eb9bc066a923acaa0878d1e86129fd5359aee99285f4eed9c"}, + {file = "lxml-5.0.0-cp27-cp27m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:73bfab795d354aaf2f4eb7a5b0db513031734fd371047342d5803834ce19ec18"}, + {file = "lxml-5.0.0-cp27-cp27m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:cb564bbe55ff0897d9cf1225041a44576d7ae87f06fd60163544c91de2623d3f"}, + {file = "lxml-5.0.0-cp27-cp27mu-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:6a5501438dd521bb7e0dde5008c40c7bfcfaafaf86eccb3f9bd27509abb793da"}, + {file = "lxml-5.0.0-cp27-cp27mu-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:7ba26a7dc929a1b3487d51bbcb0099afed2fc06e891b82845c8f37a2d7d7fbbd"}, + {file = "lxml-5.0.0-cp310-cp310-macosx_11_0_x86_64.whl", hash = "sha256:9b59c429e1a2246da86ae237ffc3565efcdc71c281cd38ca8b44d5fb6a3b993a"}, + {file = "lxml-5.0.0-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:3ffa066db40b0347e48334bd4465de768e295a3525b9a59831228b5f4f93162d"}, + {file = "lxml-5.0.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:8ce8b468ab50f9e944719d1134709ec11fe0d2840891a6cae369e22141b1094c"}, + {file = "lxml-5.0.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:583c0e15ae06adc81035346ae2abb2e748f0b5197e7740d8af31222db41bbf7b"}, + {file = "lxml-5.0.0-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:904d36165848b59c4e04ae5b969072e602bd987485076fca8ec42c6cd7a7aedc"}, + {file = "lxml-5.0.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:ac21aace6712472e77ea9dfc38329f53830c4259ece54c786107105ebb069053"}, + {file = "lxml-5.0.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:f92d73faa0b1a76d1932429d684b7ce95829e93c3eef3715ec9b98ab192c9d31"}, + {file = "lxml-5.0.0-cp310-cp310-win32.whl", hash = "sha256:03290e2f714f2e7431c8430c08b48167f657da7bc689c6248e828ff3c66d5b1b"}, + {file = "lxml-5.0.0-cp310-cp310-win_amd64.whl", hash = "sha256:3e6cbb68bf70081f036bfc018649cf4b46c4e7eaf7860a277cae92dee2a57f69"}, + {file = "lxml-5.0.0-cp311-cp311-macosx_11_0_universal2.whl", hash = "sha256:5382612ba2424cea5d2c89e2c29077023d8de88f8d60d5ceff5f76334516df9e"}, + {file = "lxml-5.0.0-cp311-cp311-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:07a900735bad9af7be3085480bf384f68ed5580ba465b39a098e6a882c060d6b"}, + {file = "lxml-5.0.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:980ba47c8db4b9d870014c7040edb230825b79017a6a27aa54cdb6fcc02d8cc0"}, + {file = "lxml-5.0.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:6507c58431dbd95b50654b3313c5ad54f90e54e5f2cdacf733de61eae478eec5"}, + {file = "lxml-5.0.0-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:4a45a278518e4308865c1e9dbb2c42ce84fb154efb03adeb16fdae3c1687c7c9"}, + {file = "lxml-5.0.0-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:59cea9ba1c675fbd6867ca1078fc717a113e7f5b7644943b74137b7cc55abebf"}, + {file = "lxml-5.0.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:dd39ef87fd1f7bb5c4aa53454936e6135cbfe03fe3744e8218be193f9e4fef16"}, + {file = "lxml-5.0.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:e6bb39d91bf932e7520cb5718ae3c2f498052aca53294d5d59fdd9068fe1a7f2"}, + {file = "lxml-5.0.0-cp311-cp311-win32.whl", hash = "sha256:21af2c3862db6f4f486cddf73ec1157b40d5828876c47cd880edcbad8240ea1b"}, + {file = "lxml-5.0.0-cp311-cp311-win_amd64.whl", hash = "sha256:c1249aa4eaced30b59ecf8b8cae0b1ccede04583c74ca7d10b6f8bbead908b2c"}, + {file = "lxml-5.0.0-cp312-cp312-macosx_11_0_universal2.whl", hash = "sha256:f30e697b6215e759d0824768b2c5b0618d2dc19abe6c67eeed2b0460f52470d1"}, + {file = "lxml-5.0.0-cp312-cp312-manylinux_2_28_aarch64.whl", hash = "sha256:d1bb64646480c36a4aa1b6a44a5b6e33d0fcbeab9f53f1b39072cd3bb2c6243a"}, + {file = "lxml-5.0.0-cp312-cp312-manylinux_2_28_x86_64.whl", hash = "sha256:4e69c36c8618707a90ed3fb6f48a6cc9254ffcdbf7b259e439a5ae5fbf9c5206"}, + {file = "lxml-5.0.0-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:9ca498f8554a09fbc3a2f8fc4b23261e07bc27bef99b3df98e2570688033f6fc"}, + {file = "lxml-5.0.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:0326e9b8176ea77269fb39e7af4010906e73e9496a9f8eaf06d253b1b1231ceb"}, + {file = "lxml-5.0.0-cp312-cp312-win32.whl", hash = "sha256:5fb988e15378d6e905ca8f60813950a0c56da9469d0e8e5d8fe785b282684ec5"}, + {file = "lxml-5.0.0-cp312-cp312-win_amd64.whl", hash = "sha256:bb58e8f4b2cfe012cd312239b8d5139995fe8f5945c7c26d5fbbbb1ddb9acd47"}, + {file = "lxml-5.0.0-cp35-cp35m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:81509dffd8aba3bdb43e90cbd218c9c068a1f4047d97bc9546b3ac9e3a4ae81d"}, + {file = "lxml-5.0.0-cp35-cp35m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:e675a4b95208e74c34ac0751cc4bab9170e7728b61601fb0f4746892c2bb7e0b"}, + {file = "lxml-5.0.0-cp36-cp36m-macosx_11_0_x86_64.whl", hash = "sha256:405e3760f83a8ba3bdb6e622ec79595cdc20db916ce37377bbcb95b5711fa4ca"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:f15844a1b93dcaa09c2b22e22a73384f3ae4502347c3881cfdd674e14ac04e21"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:88f559f8beb6b90e41a7faae4aca4c8173a4819874a9bf8e74c8d7c1d51f3162"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:e8c63f5c7d87e7044880b01851ac4e863c3349e6f6b6ab456fe218d9346e816d"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_28_x86_64.whl", hash = "sha256:0d277d4717756fe8816f0beeff229cb72f9dd02a43b70e1d3f07c8efadfb9fe1"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:c8954da15403db1acfc0544b3c3f963a6ef4e428283ab6555e3e298bbbff1cf6"}, + {file = "lxml-5.0.0-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:aebd8fd378e074b22e79cad329dcccd243c40ff1cafaa512d19276c5bb9554e1"}, + {file = "lxml-5.0.0-cp36-cp36m-musllinux_1_1_aarch64.whl", hash = "sha256:b6d4e148edee59c2ad38af15810dbcb8b5d7b13e5de3509d8cf3edfe74c0adca"}, + {file = "lxml-5.0.0-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:70ab4e02f7aa5fb4131c8b222a111ce7676f3767e36084fba3a4e7338dc82dcd"}, + {file = "lxml-5.0.0-cp36-cp36m-win32.whl", hash = "sha256:de1a8b54170024cf1c0c2718c82412bca42cd82e390556e3d8031af9541b416f"}, + {file = "lxml-5.0.0-cp36-cp36m-win_amd64.whl", hash = "sha256:5b39f63edbe7e018c2ac1cf0259ee0dd2355274e8a3003d404699b040782e55e"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:77b73952534967a4497d9e4f26fbeebfba19950cbc66b7cc3a706214429d8106"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:8cc0a951e5616ac626f7036309c41fb9774adcd4aa7db0886463da1ce5b65edb"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:4b9d5b01900a760eb3acf6cef50aead4ef2fa79e7ddb927084244e41dfe37b65"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:173bcead3af5d87c7bca9a030675073ddaad8e0a9f0b04be07cd9390453e7226"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:44fa9afd632210f1eeda51cf284ed8dbab0c7ec8b008dd39ba02818e0e114e69"}, + {file = "lxml-5.0.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:fef10f27d6318d2d7c88680e113511ddecf09ee4f9559b3623b73ee89fa8f6cc"}, + {file = "lxml-5.0.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:3663542aee845129a981889c19b366beab0b1dadcf5ca164696aabfe1aa51667"}, + {file = "lxml-5.0.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:7188495c1bf71bfda87d78ed50601e72d252119ce11710d6e71ff36e35fea5a0"}, + {file = "lxml-5.0.0-cp37-cp37m-win32.whl", hash = "sha256:6a2de85deabf939b0af89e2e1ea46bfb1239545e2da6f8ac96522755a388025f"}, + {file = "lxml-5.0.0-cp37-cp37m-win_amd64.whl", hash = "sha256:ea56825c1e23c9c8ea385a191dac75f9160477057285b88c88736d9305e6118f"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:3f908afd0477cace17f941d1b9cfa10b769fe1464770abe4cfb3d9f35378d0f8"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:52a9ab31853d3808e7cf0183b3a5f7e8ffd622ea4aee1deb5252dbeaefd5b40d"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:c7fe19abb3d3c55a9e65d289b12ad73b3a31a3f0bda3c539a890329ae9973bd6"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:1ef0793e1e2dd221fce7c142177008725680f7b9e4a184ab108d90d5d3ab69b7"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:581a78f299a9f5448b2c3aea904bfcd17c59bf83016d221d7f93f83633bb2ab2"}, + {file = "lxml-5.0.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:affdd833f82334fdb10fc9a1c7b35cdb5a86d0b672b4e14dd542e1fe7bcea894"}, + {file = "lxml-5.0.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:6bba06d8982be0f0f6432d289a8d104417a0ab9ed04114446c4ceb6d4a40c65d"}, + {file = "lxml-5.0.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:80209b31dd3908bc5b014f540fd192c97ea52ab179713a730456c5baf7ce80c1"}, + {file = "lxml-5.0.0-cp38-cp38-win32.whl", hash = "sha256:dac2733fe4e159b0aae0439db6813b7b1d23ff96d0b34c0107b87faf79208c4e"}, + {file = "lxml-5.0.0-cp38-cp38-win_amd64.whl", hash = "sha256:ee60f33456ff34b2dd1d048a740a2572798356208e4c494301c931de3a0ab3a2"}, + {file = "lxml-5.0.0-cp39-cp39-macosx_11_0_x86_64.whl", hash = "sha256:5eff173f0ff408bfa578cbdafd35a7e0ca94d1a9ffe09a8a48e0572d0904d486"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:78d6d8e5b54ed89dc0f0901eaaa579c384ad8d59fa43cc7fb06e9bb89115f8f4"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:71a7cee869578bc17b18050532bb2f0bc682a7b97dda77041741a1bd2febe6c7"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:7df433d08d4587dc3932f7fcfc3194519a6824824104854e76441fd3bc000d29"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:793be9b4945c2dfd69828fb5948d7d9569b78e0599e4a2e88d92affeb0ff3aa3"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:c7cfb6af73602c8d288581df8a225989d7e9d5aab0a174be0e19fcfa800b6797"}, + {file = "lxml-5.0.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:bfdc4668ac56687a89ca3eca44231144a2e9d02ba3b877558db74ba20e2bd9fa"}, + {file = "lxml-5.0.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:2992591e2294bb07faf7f5f6d5cb60710c046404f4bfce09fb488b85d2a8f58f"}, + {file = "lxml-5.0.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:4786b0af7511ea614fd86407a52a7bc161aa5772d311d97df2591ed2351de768"}, + {file = "lxml-5.0.0-cp39-cp39-win32.whl", hash = "sha256:016de3b29a262655fc3d2075dc1b2611f84f4c3d97a71d579c883d45e201eee4"}, + {file = "lxml-5.0.0-cp39-cp39-win_amd64.whl", hash = "sha256:52c0acc2f29b0a204efc11a5ed911a74f50a25eb7d7d5069c2b1fd3b3346ce11"}, + {file = "lxml-5.0.0-pp310-pypy310_pp73-macosx_11_0_x86_64.whl", hash = "sha256:96095bfc0c02072fc89afa67626013a253596ea5118b8a7f4daaae049dafa096"}, + {file = "lxml-5.0.0-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:992029258ed719f130d5a9c443d142c32843046f1263f2c492862b2a853be570"}, + {file = "lxml-5.0.0-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:db40e85cffd22f7d65dcce30e85af565a66401a6ed22fc0c56ed342cfa4ffc43"}, + {file = "lxml-5.0.0-pp38-pypy38_pp73-macosx_11_0_x86_64.whl", hash = "sha256:cfa8a4cdc3765574b7fd0c7cfa5fbd1e2108014c9dfd299c679e5152bea9a55e"}, + {file = "lxml-5.0.0-pp38-pypy38_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:049fef98d02513c34f5babd07569fc1cf1ed14c0f2fbff18fe72597f977ef3c2"}, + {file = "lxml-5.0.0-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:a85136d0ee18a41c91cc3e2844c683be0e72e6dda4cb58da9e15fcaef3726af7"}, + {file = "lxml-5.0.0-pp38-pypy38_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:766868f729f3ab84125350f1a0ea2594d8b1628a608a574542a5aff7355b9941"}, + {file = "lxml-5.0.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:99cad5c912f359e59e921689c04e54662cdd80835d80eeaa931e22612f515df7"}, + {file = "lxml-5.0.0-pp39-pypy39_pp73-macosx_11_0_x86_64.whl", hash = "sha256:c90c593aa8dd57d5dab0ef6d7d64af894008971d98e6a41b320fdd75258fbc6e"}, + {file = "lxml-5.0.0-pp39-pypy39_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_24_i686.whl", hash = "sha256:8134d5441d1ed6a682e3de3d7a98717a328dce619ee9c4c8b3b91f0cb0eb3e28"}, + {file = "lxml-5.0.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:f298ac9149037d6a3d5c74991bded39ac46292520b9c7c182cb102486cc87677"}, + {file = "lxml-5.0.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:894c5f71186b410679aaab5774543fcb9cbabe8893f0b31d11cf28a0740e80be"}, + {file = "lxml-5.0.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:9cd3d6c2c67d4fdcd795e4945e2ba5434909c96640b4cc09453bd0dc7e8e1bac"}, + {file = "lxml-5.0.0.zip", hash = "sha256:2219cbf790e701acf9a21a31ead75f983e73daf0eceb9da6990212e4d20ebefe"}, ] [package.extras] cssselect = ["cssselect (>=0.7)"] html5 = ["html5lib"] htmlsoup = ["BeautifulSoup4"] -source = ["Cython (>=0.29.35)"] +source = ["Cython (>=3.0.7)"] [package.source] type = "legacy" @@ -3814,16 +3918,6 @@ files = [ {file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:5bbe06f8eeafd38e5d0a4894ffec89378b6c6a625ff57e3028921f8ff59318ac"}, {file = "MarkupSafe-2.1.3-cp311-cp311-win32.whl", hash = "sha256:dd15ff04ffd7e05ffcb7fe79f1b98041b8ea30ae9234aed2a9168b5797c3effb"}, {file = "MarkupSafe-2.1.3-cp311-cp311-win_amd64.whl", hash = "sha256:134da1eca9ec0ae528110ccc9e48041e0828d79f24121a1a146161103c76e686"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:f698de3fd0c4e6972b92290a45bd9b1536bffe8c6759c62471efaa8acb4c37bc"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:aa57bd9cf8ae831a362185ee444e15a93ecb2e344c8e52e4d721ea3ab6ef1823"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ffcc3f7c66b5f5b7931a5aa68fc9cecc51e685ef90282f4a82f0f5e9b704ad11"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:47d4f1c5f80fc62fdd7777d0d40a2e9dda0a05883ab11374334f6c4de38adffd"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1f67c7038d560d92149c060157d623c542173016c4babc0c1913cca0564b9939"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:9aad3c1755095ce347e26488214ef77e0485a3c34a50c5a5e2471dff60b9dd9c"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:14ff806850827afd6b07a5f32bd917fb7f45b046ba40c57abdb636674a8b559c"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:8f9293864fe09b8149f0cc42ce56e3f0e54de883a9de90cd427f191c346eb2e1"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-win32.whl", hash = "sha256:715d3562f79d540f251b99ebd6d8baa547118974341db04f5ad06d5ea3eb8007"}, - {file = "MarkupSafe-2.1.3-cp312-cp312-win_amd64.whl", hash = "sha256:1b8dd8c3fd14349433c79fa8abeb573a55fc0fdd769133baac1f5e07abf54aeb"}, {file = "MarkupSafe-2.1.3-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:8e254ae696c88d98da6555f5ace2279cf7cd5b3f52be2b5cf97feafe883b58d2"}, {file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cb0932dc158471523c9637e807d9bfb93e06a95cbf010f1a38b98623b929ef2b"}, {file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9402b03f1a1b4dc4c19845e5c749e3ab82d5078d16a2a4c2cd2df62d57bb0707"}, @@ -3947,13 +4041,13 @@ reference = "tsinghua" [[package]] name = "mistune" -version = "0.8.4" -description = "The fastest markdown parser in pure Python" +version = "2.0.3" +description = "A sane Markdown parser with useful plugins and renderers" optional = false python-versions = "*" files = [ - {file = "mistune-0.8.4-py2.py3-none-any.whl", hash = "sha256:88a1051873018da288eee8538d476dffe1262495144b33ecb586c4ab266bb8d4"}, - {file = "mistune-0.8.4.tar.gz", hash = "sha256:59a3429db53c50b5c6bcc8a07f8848cb00d7dc8bdb431a4ab41920d201d4756e"}, + {file = "mistune-2.0.3-py2.py3-none-any.whl", hash = "sha256:e3964140c0775535fba50bd616fe180920044a64bc21850253267b07bff89924"}, + {file = "mistune-2.0.3.tar.gz", hash = "sha256:d7605b46b6156b53b7d52a465202b29a6f00f4ea4130ad5d25e9d5547d6b7e50"}, ] [package.source] @@ -3963,13 +4057,13 @@ reference = "tsinghua" [[package]] name = "msal" -version = "1.25.0" -description = "The Microsoft Authentication Library (MSAL) for Python library" +version = "1.26.0" +description = "The Microsoft Authentication Library (MSAL) for Python library enables your app to access the Microsoft Cloud by supporting authentication of users with Microsoft Azure Active Directory accounts (AAD) and Microsoft Accounts (MSA) using industry standard OAuth2 and OpenID Connect." optional = false python-versions = ">=2.7" files = [ - {file = "msal-1.25.0-py2.py3-none-any.whl", hash = "sha256:386df621becb506bc315a713ec3d4d5b5d6163116955c7dde23622f156b81af6"}, - {file = "msal-1.25.0.tar.gz", hash = "sha256:f44329fdb59f4f044c779164a34474b8a44ad9e4940afbc4c3a3a2bbe90324d9"}, + {file = "msal-1.26.0-py2.py3-none-any.whl", hash = "sha256:be77ba6a8f49c9ff598bbcdc5dfcf1c9842f3044300109af738e8c3e371065b5"}, + {file = "msal-1.26.0.tar.gz", hash = "sha256:224756079fe338be838737682b49f8ebc20a87c1c5eeaf590daae4532b83de15"}, ] [package.dependencies] @@ -3987,20 +4081,21 @@ reference = "tsinghua" [[package]] name = "msal-extensions" -version = "1.0.0" +version = "1.1.0" description = "Microsoft Authentication Library extensions (MSAL EX) provides a persistence API that can save your data on disk, encrypted on Windows, macOS and Linux. Concurrent data access will be coordinated by a file lock mechanism." optional = false -python-versions = "*" +python-versions = ">=3.7" files = [ - {file = "msal-extensions-1.0.0.tar.gz", hash = "sha256:c676aba56b0cce3783de1b5c5ecfe828db998167875126ca4b47dc6436451354"}, - {file = "msal_extensions-1.0.0-py2.py3-none-any.whl", hash = "sha256:91e3db9620b822d0ed2b4d1850056a0f133cba04455e62f11612e40f5502f2ee"}, + {file = "msal-extensions-1.1.0.tar.gz", hash = "sha256:6ab357867062db7b253d0bd2df6d411c7891a0ee7308d54d1e4317c1d1c54252"}, + {file = "msal_extensions-1.1.0-py3-none-any.whl", hash = "sha256:01be9711b4c0b1a151450068eeb2c4f0997df3bba085ac299de3a66f585e382f"}, ] [package.dependencies] msal = ">=0.4.1,<2.0.0" +packaging = "*" portalocker = [ - {version = ">=1.0,<3", markers = "python_version >= \"3.5\" and platform_system != \"Windows\""}, - {version = ">=1.6,<3", markers = "python_version >= \"3.5\" and platform_system == \"Windows\""}, + {version = ">=1.0,<3", markers = "platform_system != \"Windows\""}, + {version = ">=1.6,<3", markers = "platform_system == \"Windows\""}, ] [package.source] @@ -4236,13 +4331,13 @@ reference = "tsinghua" [[package]] name = "netaddr" -version = "0.9.0" +version = "0.10.0" description = "A network address manipulation library for Python" optional = false python-versions = "*" files = [ - {file = "netaddr-0.9.0-py3-none-any.whl", hash = "sha256:5148b1055679d2a1ec070c521b7db82137887fabd6d7e37f5199b44f775c3bb1"}, - {file = "netaddr-0.9.0.tar.gz", hash = "sha256:7b46fa9b1a2d71fd5de9e4a3784ef339700a53a08c8040f08baf5f1194da0128"}, + {file = "netaddr-0.10.0-py2.py3-none-any.whl", hash = "sha256:8752f96c8fc24162edbf5b73d3e464b5d88e62869917582daa37b2695b65afb4"}, + {file = "netaddr-0.10.0.tar.gz", hash = "sha256:4c30c54adf4ea4318b3c055ea3d8c7f6554a50aa2cd8aea4605a23caa0b0229e"}, ] [package.source] @@ -4332,23 +4427,23 @@ reference = "tsinghua" [[package]] name = "openai" -version = "1.3.7" +version = "1.6.1" description = "The official Python library for the openai API" optional = false python-versions = ">=3.7.1" files = [ - {file = "openai-1.3.7-py3-none-any.whl", hash = "sha256:e5c51367a910297e4d1cd33d2298fb87d7edf681edbe012873925ac16f95bee0"}, - {file = "openai-1.3.7.tar.gz", hash = "sha256:18074a0f51f9b49d1ae268c7abc36f7f33212a0c0d08ce11b7053ab2d17798de"}, + {file = "openai-1.6.1-py3-none-any.whl", hash = "sha256:bc9f774838d67ac29fb24cdeb2d58faf57de8b311085dcd1348f7aa02a96c7ee"}, + {file = "openai-1.6.1.tar.gz", hash = "sha256:d553ca9dbf9486b08e75b09e8671e4f638462aaadccfced632bf490fc3d75fa2"}, ] [package.dependencies] -anyio = ">=3.5.0,<4" +anyio = ">=3.5.0,<5" distro = ">=1.7.0,<2" httpx = ">=0.23.0,<1" pydantic = ">=1.9.0,<3" sniffio = "*" tqdm = ">4" -typing-extensions = ">=4.5,<5" +typing-extensions = ">=4.7,<5" [package.extras] datalib = ["numpy (>=1)", "pandas (>=1.2.3)", "pandas-stubs (>=1.1.0.11)"] @@ -4734,67 +4829,65 @@ reference = "tsinghua" [[package]] name = "pillow" -version = "10.0.0" +version = "10.0.1" description = "Python Imaging Library (Fork)" optional = false python-versions = ">=3.8" files = [ - {file = "Pillow-10.0.0-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:1f62406a884ae75fb2f818694469519fb685cc7eaff05d3451a9ebe55c646891"}, - {file = "Pillow-10.0.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:d5db32e2a6ccbb3d34d87c87b432959e0db29755727afb37290e10f6e8e62614"}, - {file = "Pillow-10.0.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:edf4392b77bdc81f36e92d3a07a5cd072f90253197f4a52a55a8cec48a12483b"}, - {file = "Pillow-10.0.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:520f2a520dc040512699f20fa1c363eed506e94248d71f85412b625026f6142c"}, - {file = "Pillow-10.0.0-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:8c11160913e3dd06c8ffdb5f233a4f254cb449f4dfc0f8f4549eda9e542c93d1"}, - {file = "Pillow-10.0.0-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:a74ba0c356aaa3bb8e3eb79606a87669e7ec6444be352870623025d75a14a2bf"}, - {file = "Pillow-10.0.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d5d0dae4cfd56969d23d94dc8e89fb6a217be461c69090768227beb8ed28c0a3"}, - {file = "Pillow-10.0.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:22c10cc517668d44b211717fd9775799ccec4124b9a7f7b3635fc5386e584992"}, - {file = "Pillow-10.0.0-cp310-cp310-win_amd64.whl", hash = "sha256:dffe31a7f47b603318c609f378ebcd57f1554a3a6a8effbc59c3c69f804296de"}, - {file = "Pillow-10.0.0-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:9fb218c8a12e51d7ead2a7c9e101a04982237d4855716af2e9499306728fb485"}, - {file = "Pillow-10.0.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:d35e3c8d9b1268cbf5d3670285feb3528f6680420eafe35cccc686b73c1e330f"}, - {file = "Pillow-10.0.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3ed64f9ca2f0a95411e88a4efbd7a29e5ce2cea36072c53dd9d26d9c76f753b3"}, - {file = "Pillow-10.0.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0b6eb5502f45a60a3f411c63187db83a3d3107887ad0d036c13ce836f8a36f1d"}, - {file = "Pillow-10.0.0-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:c1fbe7621c167ecaa38ad29643d77a9ce7311583761abf7836e1510c580bf3dd"}, - {file = "Pillow-10.0.0-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:cd25d2a9d2b36fcb318882481367956d2cf91329f6892fe5d385c346c0649629"}, - {file = "Pillow-10.0.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:3b08d4cc24f471b2c8ca24ec060abf4bebc6b144cb89cba638c720546b1cf538"}, - {file = "Pillow-10.0.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d737a602fbd82afd892ca746392401b634e278cb65d55c4b7a8f48e9ef8d008d"}, - {file = "Pillow-10.0.0-cp311-cp311-win_amd64.whl", hash = "sha256:3a82c40d706d9aa9734289740ce26460a11aeec2d9c79b7af87bb35f0073c12f"}, - {file = "Pillow-10.0.0-cp311-cp311-win_arm64.whl", hash = "sha256:bc2ec7c7b5d66b8ec9ce9f720dbb5fa4bace0f545acd34870eff4a369b44bf37"}, - {file = "Pillow-10.0.0-cp312-cp312-macosx_10_10_x86_64.whl", hash = "sha256:d80cf684b541685fccdd84c485b31ce73fc5c9b5d7523bf1394ce134a60c6883"}, - {file = "Pillow-10.0.0-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:76de421f9c326da8f43d690110f0e79fe3ad1e54be811545d7d91898b4c8493e"}, - {file = "Pillow-10.0.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:81ff539a12457809666fef6624684c008e00ff6bf455b4b89fd00a140eecd640"}, - {file = "Pillow-10.0.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ce543ed15570eedbb85df19b0a1a7314a9c8141a36ce089c0a894adbfccb4568"}, - {file = "Pillow-10.0.0-cp312-cp312-manylinux_2_28_aarch64.whl", hash = "sha256:685ac03cc4ed5ebc15ad5c23bc555d68a87777586d970c2c3e216619a5476223"}, - {file = "Pillow-10.0.0-cp312-cp312-manylinux_2_28_x86_64.whl", hash = "sha256:d72e2ecc68a942e8cf9739619b7f408cc7b272b279b56b2c83c6123fcfa5cdff"}, - {file = "Pillow-10.0.0-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:d50b6aec14bc737742ca96e85d6d0a5f9bfbded018264b3b70ff9d8c33485551"}, - {file = "Pillow-10.0.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:00e65f5e822decd501e374b0650146063fbb30a7264b4d2744bdd7b913e0cab5"}, - {file = "Pillow-10.0.0-cp312-cp312-win_amd64.whl", hash = "sha256:f31f9fdbfecb042d046f9d91270a0ba28368a723302786c0009ee9b9f1f60199"}, - {file = "Pillow-10.0.0-cp312-cp312-win_arm64.whl", hash = "sha256:1ce91b6ec08d866b14413d3f0bbdea7e24dfdc8e59f562bb77bc3fe60b6144ca"}, - {file = "Pillow-10.0.0-cp38-cp38-macosx_10_10_x86_64.whl", hash = "sha256:349930d6e9c685c089284b013478d6f76e3a534e36ddfa912cde493f235372f3"}, - {file = "Pillow-10.0.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:3a684105f7c32488f7153905a4e3015a3b6c7182e106fe3c37fbb5ef3e6994c3"}, - {file = "Pillow-10.0.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b4f69b3700201b80bb82c3a97d5e9254084f6dd5fb5b16fc1a7b974260f89f43"}, - {file = "Pillow-10.0.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3f07ea8d2f827d7d2a49ecf1639ec02d75ffd1b88dcc5b3a61bbb37a8759ad8d"}, - {file = "Pillow-10.0.0-cp38-cp38-manylinux_2_28_aarch64.whl", hash = "sha256:040586f7d37b34547153fa383f7f9aed68b738992380ac911447bb78f2abe530"}, - {file = "Pillow-10.0.0-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:f88a0b92277de8e3ca715a0d79d68dc82807457dae3ab8699c758f07c20b3c51"}, - {file = "Pillow-10.0.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:c7cf14a27b0d6adfaebb3ae4153f1e516df54e47e42dcc073d7b3d76111a8d86"}, - {file = "Pillow-10.0.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:3400aae60685b06bb96f99a21e1ada7bc7a413d5f49bce739828ecd9391bb8f7"}, - {file = "Pillow-10.0.0-cp38-cp38-win_amd64.whl", hash = "sha256:dbc02381779d412145331789b40cc7b11fdf449e5d94f6bc0b080db0a56ea3f0"}, - {file = "Pillow-10.0.0-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:9211e7ad69d7c9401cfc0e23d49b69ca65ddd898976d660a2fa5904e3d7a9baa"}, - {file = "Pillow-10.0.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:faaf07ea35355b01a35cb442dd950d8f1bb5b040a7787791a535de13db15ed90"}, - {file = "Pillow-10.0.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c9f72a021fbb792ce98306ffb0c348b3c9cb967dce0f12a49aa4c3d3fdefa967"}, - {file = "Pillow-10.0.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9f7c16705f44e0504a3a2a14197c1f0b32a95731d251777dcb060aa83022cb2d"}, - {file = "Pillow-10.0.0-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:76edb0a1fa2b4745fb0c99fb9fb98f8b180a1bbceb8be49b087e0b21867e77d3"}, - {file = "Pillow-10.0.0-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:368ab3dfb5f49e312231b6f27b8820c823652b7cd29cfbd34090565a015e99ba"}, - {file = "Pillow-10.0.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:608bfdee0d57cf297d32bcbb3c728dc1da0907519d1784962c5f0c68bb93e5a3"}, - {file = "Pillow-10.0.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5c6e3df6bdd396749bafd45314871b3d0af81ff935b2d188385e970052091017"}, - {file = "Pillow-10.0.0-cp39-cp39-win_amd64.whl", hash = "sha256:7be600823e4c8631b74e4a0d38384c73f680e6105a7d3c6824fcf226c178c7e6"}, - {file = "Pillow-10.0.0-pp310-pypy310_pp73-macosx_10_10_x86_64.whl", hash = "sha256:92be919bbc9f7d09f7ae343c38f5bb21c973d2576c1d45600fce4b74bafa7ac0"}, - {file = "Pillow-10.0.0-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8f8182b523b2289f7c415f589118228d30ac8c355baa2f3194ced084dac2dbba"}, - {file = "Pillow-10.0.0-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:38250a349b6b390ee6047a62c086d3817ac69022c127f8a5dc058c31ccef17f3"}, - {file = "Pillow-10.0.0-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:88af2003543cc40c80f6fca01411892ec52b11021b3dc22ec3bc9d5afd1c5334"}, - {file = "Pillow-10.0.0-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:c189af0545965fa8d3b9613cfdb0cd37f9d71349e0f7750e1fd704648d475ed2"}, - {file = "Pillow-10.0.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ce7b031a6fc11365970e6a5686d7ba8c63e4c1cf1ea143811acbb524295eabed"}, - {file = "Pillow-10.0.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:db24668940f82321e746773a4bc617bfac06ec831e5c88b643f91f122a785684"}, - {file = "Pillow-10.0.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:efe8c0681042536e0d06c11f48cebe759707c9e9abf880ee213541c5b46c5bf3"}, - {file = "Pillow-10.0.0.tar.gz", hash = "sha256:9c82b5b3e043c7af0d95792d0d20ccf68f61a1fec6b3530e718b688422727396"}, + {file = "Pillow-10.0.1-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:8f06be50669087250f319b706decf69ca71fdecd829091a37cc89398ca4dc17a"}, + {file = "Pillow-10.0.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:50bd5f1ebafe9362ad622072a1d2f5850ecfa44303531ff14353a4059113b12d"}, + {file = "Pillow-10.0.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e6a90167bcca1216606223a05e2cf991bb25b14695c518bc65639463d7db722d"}, + {file = "Pillow-10.0.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f11c9102c56ffb9ca87134bd025a43d2aba3f1155f508eff88f694b33a9c6d19"}, + {file = "Pillow-10.0.1-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:186f7e04248103482ea6354af6d5bcedb62941ee08f7f788a1c7707bc720c66f"}, + {file = "Pillow-10.0.1-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:0462b1496505a3462d0f35dc1c4d7b54069747d65d00ef48e736acda2c8cbdff"}, + {file = "Pillow-10.0.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d889b53ae2f030f756e61a7bff13684dcd77e9af8b10c6048fb2c559d6ed6eaf"}, + {file = "Pillow-10.0.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:552912dbca585b74d75279a7570dd29fa43b6d93594abb494ebb31ac19ace6bd"}, + {file = "Pillow-10.0.1-cp310-cp310-win_amd64.whl", hash = "sha256:787bb0169d2385a798888e1122c980c6eff26bf941a8ea79747d35d8f9210ca0"}, + {file = "Pillow-10.0.1-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:fd2a5403a75b54661182b75ec6132437a181209b901446ee5724b589af8edef1"}, + {file = "Pillow-10.0.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:2d7e91b4379f7a76b31c2dda84ab9e20c6220488e50f7822e59dac36b0cd92b1"}, + {file = "Pillow-10.0.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:19e9adb3f22d4c416e7cd79b01375b17159d6990003633ff1d8377e21b7f1b21"}, + {file = "Pillow-10.0.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:93139acd8109edcdeffd85e3af8ae7d88b258b3a1e13a038f542b79b6d255c54"}, + {file = "Pillow-10.0.1-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:92a23b0431941a33242b1f0ce6c88a952e09feeea9af4e8be48236a68ffe2205"}, + {file = "Pillow-10.0.1-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:cbe68deb8580462ca0d9eb56a81912f59eb4542e1ef8f987405e35a0179f4ea2"}, + {file = "Pillow-10.0.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:522ff4ac3aaf839242c6f4e5b406634bfea002469656ae8358644fc6c4856a3b"}, + {file = "Pillow-10.0.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:84efb46e8d881bb06b35d1d541aa87f574b58e87f781cbba8d200daa835b42e1"}, + {file = "Pillow-10.0.1-cp311-cp311-win_amd64.whl", hash = "sha256:898f1d306298ff40dc1b9ca24824f0488f6f039bc0e25cfb549d3195ffa17088"}, + {file = "Pillow-10.0.1-cp312-cp312-macosx_10_10_x86_64.whl", hash = "sha256:bcf1207e2f2385a576832af02702de104be71301c2696d0012b1b93fe34aaa5b"}, + {file = "Pillow-10.0.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:5d6c9049c6274c1bb565021367431ad04481ebb54872edecfcd6088d27edd6ed"}, + {file = "Pillow-10.0.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:28444cb6ad49726127d6b340217f0627abc8732f1194fd5352dec5e6a0105635"}, + {file = "Pillow-10.0.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:de596695a75496deb3b499c8c4f8e60376e0516e1a774e7bc046f0f48cd620ad"}, + {file = "Pillow-10.0.1-cp312-cp312-manylinux_2_28_aarch64.whl", hash = "sha256:2872f2d7846cf39b3dbff64bc1104cc48c76145854256451d33c5faa55c04d1a"}, + {file = "Pillow-10.0.1-cp312-cp312-manylinux_2_28_x86_64.whl", hash = "sha256:4ce90f8a24e1c15465048959f1e94309dfef93af272633e8f37361b824532e91"}, + {file = "Pillow-10.0.1-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:ee7810cf7c83fa227ba9125de6084e5e8b08c59038a7b2c9045ef4dde61663b4"}, + {file = "Pillow-10.0.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:b1be1c872b9b5fcc229adeadbeb51422a9633abd847c0ff87dc4ef9bb184ae08"}, + {file = "Pillow-10.0.1-cp312-cp312-win_amd64.whl", hash = "sha256:98533fd7fa764e5f85eebe56c8e4094db912ccbe6fbf3a58778d543cadd0db08"}, + {file = "Pillow-10.0.1-cp38-cp38-macosx_10_10_x86_64.whl", hash = "sha256:764d2c0daf9c4d40ad12fbc0abd5da3af7f8aa11daf87e4fa1b834000f4b6b0a"}, + {file = "Pillow-10.0.1-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:fcb59711009b0168d6ee0bd8fb5eb259c4ab1717b2f538bbf36bacf207ef7a68"}, + {file = "Pillow-10.0.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:697a06bdcedd473b35e50a7e7506b1d8ceb832dc238a336bd6f4f5aa91a4b500"}, + {file = "Pillow-10.0.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9f665d1e6474af9f9da5e86c2a3a2d2d6204e04d5af9c06b9d42afa6ebde3f21"}, + {file = "Pillow-10.0.1-cp38-cp38-manylinux_2_28_aarch64.whl", hash = "sha256:2fa6dd2661838c66f1a5473f3b49ab610c98a128fc08afbe81b91a1f0bf8c51d"}, + {file = "Pillow-10.0.1-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:3a04359f308ebee571a3127fdb1bd01f88ba6f6fb6d087f8dd2e0d9bff43f2a7"}, + {file = "Pillow-10.0.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:723bd25051454cea9990203405fa6b74e043ea76d4968166dfd2569b0210886a"}, + {file = "Pillow-10.0.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:71671503e3015da1b50bd18951e2f9daf5b6ffe36d16f1eb2c45711a301521a7"}, + {file = "Pillow-10.0.1-cp38-cp38-win_amd64.whl", hash = "sha256:44e7e4587392953e5e251190a964675f61e4dae88d1e6edbe9f36d6243547ff3"}, + {file = "Pillow-10.0.1-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:3855447d98cced8670aaa63683808df905e956f00348732448b5a6df67ee5849"}, + {file = "Pillow-10.0.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ed2d9c0704f2dc4fa980b99d565c0c9a543fe5101c25b3d60488b8ba80f0cce1"}, + {file = "Pillow-10.0.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f5bb289bb835f9fe1a1e9300d011eef4d69661bb9b34d5e196e5e82c4cb09b37"}, + {file = "Pillow-10.0.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3a0d3e54ab1df9df51b914b2233cf779a5a10dfd1ce339d0421748232cea9876"}, + {file = "Pillow-10.0.1-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:2cc6b86ece42a11f16f55fe8903595eff2b25e0358dec635d0a701ac9586588f"}, + {file = "Pillow-10.0.1-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:ca26ba5767888c84bf5a0c1a32f069e8204ce8c21d00a49c90dabeba00ce0145"}, + {file = "Pillow-10.0.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:f0b4b06da13275bc02adfeb82643c4a6385bd08d26f03068c2796f60d125f6f2"}, + {file = "Pillow-10.0.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:bc2e3069569ea9dbe88d6b8ea38f439a6aad8f6e7a6283a38edf61ddefb3a9bf"}, + {file = "Pillow-10.0.1-cp39-cp39-win_amd64.whl", hash = "sha256:8b451d6ead6e3500b6ce5c7916a43d8d8d25ad74b9102a629baccc0808c54971"}, + {file = "Pillow-10.0.1-pp310-pypy310_pp73-macosx_10_10_x86_64.whl", hash = "sha256:32bec7423cdf25c9038fef614a853c9d25c07590e1a870ed471f47fb80b244db"}, + {file = "Pillow-10.0.1-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b7cf63d2c6928b51d35dfdbda6f2c1fddbe51a6bc4a9d4ee6ea0e11670dd981e"}, + {file = "Pillow-10.0.1-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:f6d3d4c905e26354e8f9d82548475c46d8e0889538cb0657aa9c6f0872a37aa4"}, + {file = "Pillow-10.0.1-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:847e8d1017c741c735d3cd1883fa7b03ded4f825a6e5fcb9378fd813edee995f"}, + {file = "Pillow-10.0.1-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:7f771e7219ff04b79e231d099c0a28ed83aa82af91fd5fa9fdb28f5b8d5addaf"}, + {file = "Pillow-10.0.1-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:459307cacdd4138edee3875bbe22a2492519e060660eaf378ba3b405d1c66317"}, + {file = "Pillow-10.0.1-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:b059ac2c4c7a97daafa7dc850b43b2d3667def858a4f112d1aa082e5c3d6cf7d"}, + {file = "Pillow-10.0.1-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:d6caf3cd38449ec3cd8a68b375e0c6fe4b6fd04edb6c9766b55ef84a6e8ddf2d"}, + {file = "Pillow-10.0.1.tar.gz", hash = "sha256:d72967b06be9300fed5cfbc8b5bafceec48bf7cdc7dab66b1d2549035287191d"}, ] [package.extras] @@ -4873,13 +4966,13 @@ reference = "tsinghua" [[package]] name = "prompt-toolkit" -version = "3.0.41" +version = "3.0.43" description = "Library for building powerful interactive command lines in Python" optional = false python-versions = ">=3.7.0" files = [ - {file = "prompt_toolkit-3.0.41-py3-none-any.whl", hash = "sha256:f36fe301fafb7470e86aaf90f036eef600a3210be4decf461a5b1ca8403d3cb2"}, - {file = "prompt_toolkit-3.0.41.tar.gz", hash = "sha256:941367d97fc815548822aa26c2a269fdc4eb21e9ec05fc5d447cf09bad5d75f0"}, + {file = "prompt_toolkit-3.0.43-py3-none-any.whl", hash = "sha256:a11a29cb3bf0a28a387fe5122cdb649816a957cd9261dcedf8c9f1fef33eacf6"}, + {file = "prompt_toolkit-3.0.43.tar.gz", hash = "sha256:3527b7af26106cbc65a040bcc84839a3566ec1b051bb0bfe953631e704b0ff7d"}, ] [package.dependencies] @@ -4892,13 +4985,13 @@ reference = "tsinghua" [[package]] name = "proto-plus" -version = "1.22.3" +version = "1.23.0" description = "Beautiful, Pythonic protocol buffers." optional = false python-versions = ">=3.6" files = [ - {file = "proto-plus-1.22.3.tar.gz", hash = "sha256:fdcd09713cbd42480740d2fe29c990f7fbd885a67efc328aa8be6ee3e9f76a6b"}, - {file = "proto_plus-1.22.3-py3-none-any.whl", hash = "sha256:a49cd903bc0b6ab41f76bf65510439d56ca76f868adf0274e738bfdd096894df"}, + {file = "proto-plus-1.23.0.tar.gz", hash = "sha256:89075171ef11988b3fa157f5dbd8b9cf09d65fffee97e29ce403cd8defba19d2"}, + {file = "proto_plus-1.23.0-py3-none-any.whl", hash = "sha256:a829c79e619e1cf632de091013a4173deed13a55f326ef84f05af6f50ff4c82c"}, ] [package.dependencies] @@ -5251,18 +5344,18 @@ reference = "tsinghua" [[package]] name = "pydantic" -version = "2.5.2" +version = "2.5.3" description = "Data validation using Python type hints" optional = false python-versions = ">=3.7" files = [ - {file = "pydantic-2.5.2-py3-none-any.whl", hash = "sha256:80c50fb8e3dcecfddae1adbcc00ec5822918490c99ab31f6cf6140ca1c1429f0"}, - {file = "pydantic-2.5.2.tar.gz", hash = "sha256:ff177ba64c6faf73d7afa2e8cad38fd456c0dbe01c9954e71038001cd15a6edd"}, + {file = "pydantic-2.5.3-py3-none-any.whl", hash = "sha256:d0caf5954bee831b6bfe7e338c32b9e30c85dfe080c843680783ac2b631673b4"}, + {file = "pydantic-2.5.3.tar.gz", hash = "sha256:b3ef57c62535b0941697cce638c08900d87fcb67e29cfa99e8a68f747f393f7a"}, ] [package.dependencies] annotated-types = ">=0.4.0" -pydantic-core = "2.14.5" +pydantic-core = "2.14.6" typing-extensions = ">=4.6.1" [package.extras] @@ -5275,116 +5368,116 @@ reference = "tsinghua" [[package]] name = "pydantic-core" -version = "2.14.5" +version = "2.14.6" description = "" optional = false python-versions = ">=3.7" files = [ - {file = "pydantic_core-2.14.5-cp310-cp310-macosx_10_7_x86_64.whl", hash = "sha256:7e88f5696153dc516ba6e79f82cc4747e87027205f0e02390c21f7cb3bd8abfd"}, - {file = "pydantic_core-2.14.5-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:4641e8ad4efb697f38a9b64ca0523b557c7931c5f84e0fd377a9a3b05121f0de"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:774de879d212db5ce02dfbf5b0da9a0ea386aeba12b0b95674a4ce0593df3d07"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:ebb4e035e28f49b6f1a7032920bb9a0c064aedbbabe52c543343d39341a5b2a3"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:b53e9ad053cd064f7e473a5f29b37fc4cc9dc6d35f341e6afc0155ea257fc911"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8aa1768c151cf562a9992462239dfc356b3d1037cc5a3ac829bb7f3bda7cc1f9"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:eac5c82fc632c599f4639a5886f96867ffced74458c7db61bc9a66ccb8ee3113"}, - {file = "pydantic_core-2.14.5-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:d2ae91f50ccc5810b2f1b6b858257c9ad2e08da70bf890dee02de1775a387c66"}, - {file = "pydantic_core-2.14.5-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:6b9ff467ffbab9110e80e8c8de3bcfce8e8b0fd5661ac44a09ae5901668ba997"}, - {file = "pydantic_core-2.14.5-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:61ea96a78378e3bd5a0be99b0e5ed00057b71f66115f5404d0dae4819f495093"}, - {file = "pydantic_core-2.14.5-cp310-none-win32.whl", hash = "sha256:bb4c2eda937a5e74c38a41b33d8c77220380a388d689bcdb9b187cf6224c9720"}, - {file = "pydantic_core-2.14.5-cp310-none-win_amd64.whl", hash = "sha256:b7851992faf25eac90bfcb7bfd19e1f5ffa00afd57daec8a0042e63c74a4551b"}, - {file = "pydantic_core-2.14.5-cp311-cp311-macosx_10_7_x86_64.whl", hash = "sha256:4e40f2bd0d57dac3feb3a3aed50f17d83436c9e6b09b16af271b6230a2915459"}, - {file = "pydantic_core-2.14.5-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:ab1cdb0f14dc161ebc268c09db04d2c9e6f70027f3b42446fa11c153521c0e88"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:aae7ea3a1c5bb40c93cad361b3e869b180ac174656120c42b9fadebf685d121b"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:60b7607753ba62cf0739177913b858140f11b8af72f22860c28eabb2f0a61937"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2248485b0322c75aee7565d95ad0e16f1c67403a470d02f94da7344184be770f"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:823fcc638f67035137a5cd3f1584a4542d35a951c3cc68c6ead1df7dac825c26"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:96581cfefa9123accc465a5fd0cc833ac4d75d55cc30b633b402e00e7ced00a6"}, - {file = "pydantic_core-2.14.5-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:a33324437018bf6ba1bb0f921788788641439e0ed654b233285b9c69704c27b4"}, - {file = "pydantic_core-2.14.5-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:9bd18fee0923ca10f9a3ff67d4851c9d3e22b7bc63d1eddc12f439f436f2aada"}, - {file = "pydantic_core-2.14.5-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:853a2295c00f1d4429db4c0fb9475958543ee80cfd310814b5c0ef502de24dda"}, - {file = "pydantic_core-2.14.5-cp311-none-win32.whl", hash = "sha256:cb774298da62aea5c80a89bd58c40205ab4c2abf4834453b5de207d59d2e1651"}, - {file = "pydantic_core-2.14.5-cp311-none-win_amd64.whl", hash = "sha256:e87fc540c6cac7f29ede02e0f989d4233f88ad439c5cdee56f693cc9c1c78077"}, - {file = "pydantic_core-2.14.5-cp311-none-win_arm64.whl", hash = "sha256:57d52fa717ff445cb0a5ab5237db502e6be50809b43a596fb569630c665abddf"}, - {file = "pydantic_core-2.14.5-cp312-cp312-macosx_10_7_x86_64.whl", hash = "sha256:e60f112ac88db9261ad3a52032ea46388378034f3279c643499edb982536a093"}, - {file = "pydantic_core-2.14.5-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:6e227c40c02fd873c2a73a98c1280c10315cbebe26734c196ef4514776120aeb"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f0cbc7fff06a90bbd875cc201f94ef0ee3929dfbd5c55a06674b60857b8b85ed"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:103ef8d5b58596a731b690112819501ba1db7a36f4ee99f7892c40da02c3e189"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c949f04ecad823f81b1ba94e7d189d9dfb81edbb94ed3f8acfce41e682e48cef"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c1452a1acdf914d194159439eb21e56b89aa903f2e1c65c60b9d874f9b950e5d"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cb4679d4c2b089e5ef89756bc73e1926745e995d76e11925e3e96a76d5fa51fc"}, - {file = "pydantic_core-2.14.5-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:cf9d3fe53b1ee360e2421be95e62ca9b3296bf3f2fb2d3b83ca49ad3f925835e"}, - {file = "pydantic_core-2.14.5-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:70f4b4851dbb500129681d04cc955be2a90b2248d69273a787dda120d5cf1f69"}, - {file = "pydantic_core-2.14.5-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:59986de5710ad9613ff61dd9b02bdd2f615f1a7052304b79cc8fa2eb4e336d2d"}, - {file = "pydantic_core-2.14.5-cp312-none-win32.whl", hash = "sha256:699156034181e2ce106c89ddb4b6504c30db8caa86e0c30de47b3e0654543260"}, - {file = "pydantic_core-2.14.5-cp312-none-win_amd64.whl", hash = "sha256:5baab5455c7a538ac7e8bf1feec4278a66436197592a9bed538160a2e7d11e36"}, - {file = "pydantic_core-2.14.5-cp312-none-win_arm64.whl", hash = "sha256:e47e9a08bcc04d20975b6434cc50bf82665fbc751bcce739d04a3120428f3e27"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-macosx_10_7_x86_64.whl", hash = "sha256:af36f36538418f3806048f3b242a1777e2540ff9efaa667c27da63d2749dbce0"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-macosx_11_0_arm64.whl", hash = "sha256:45e95333b8418ded64745f14574aa9bfc212cb4fbeed7a687b0c6e53b5e188cd"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4e47a76848f92529879ecfc417ff88a2806438f57be4a6a8bf2961e8f9ca9ec7"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d81e6987b27bc7d101c8597e1cd2bcaa2fee5e8e0f356735c7ed34368c471550"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:34708cc82c330e303f4ce87758828ef6e457681b58ce0e921b6e97937dd1e2a3"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:652c1988019752138b974c28f43751528116bcceadad85f33a258869e641d753"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6e4d090e73e0725b2904fdbdd8d73b8802ddd691ef9254577b708d413bf3006e"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:5c7d5b5005f177764e96bd584d7bf28d6e26e96f2a541fdddb934c486e36fd59"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:a71891847f0a73b1b9eb86d089baee301477abef45f7eaf303495cd1473613e4"}, - {file = "pydantic_core-2.14.5-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:a717aef6971208f0851a2420b075338e33083111d92041157bbe0e2713b37325"}, - {file = "pydantic_core-2.14.5-cp37-none-win32.whl", hash = "sha256:de790a3b5aa2124b8b78ae5faa033937a72da8efe74b9231698b5a1dd9be3405"}, - {file = "pydantic_core-2.14.5-cp37-none-win_amd64.whl", hash = "sha256:6c327e9cd849b564b234da821236e6bcbe4f359a42ee05050dc79d8ed2a91588"}, - {file = "pydantic_core-2.14.5-cp38-cp38-macosx_10_7_x86_64.whl", hash = "sha256:ef98ca7d5995a82f43ec0ab39c4caf6a9b994cb0b53648ff61716370eadc43cf"}, - {file = "pydantic_core-2.14.5-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:c6eae413494a1c3f89055da7a5515f32e05ebc1a234c27674a6956755fb2236f"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dcf4e6d85614f7a4956c2de5a56531f44efb973d2fe4a444d7251df5d5c4dcfd"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:6637560562134b0e17de333d18e69e312e0458ee4455bdad12c37100b7cad706"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:77fa384d8e118b3077cccfcaf91bf83c31fe4dc850b5e6ee3dc14dc3d61bdba1"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:16e29bad40bcf97aac682a58861249ca9dcc57c3f6be22f506501833ddb8939c"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:531f4b4252fac6ca476fbe0e6f60f16f5b65d3e6b583bc4d87645e4e5ddde331"}, - {file = "pydantic_core-2.14.5-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:074f3d86f081ce61414d2dc44901f4f83617329c6f3ab49d2bc6c96948b2c26b"}, - {file = "pydantic_core-2.14.5-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:c2adbe22ab4babbca99c75c5d07aaf74f43c3195384ec07ccbd2f9e3bddaecec"}, - {file = "pydantic_core-2.14.5-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:0f6116a558fd06d1b7c2902d1c4cf64a5bd49d67c3540e61eccca93f41418124"}, - {file = "pydantic_core-2.14.5-cp38-none-win32.whl", hash = "sha256:fe0a5a1025eb797752136ac8b4fa21aa891e3d74fd340f864ff982d649691867"}, - {file = "pydantic_core-2.14.5-cp38-none-win_amd64.whl", hash = "sha256:079206491c435b60778cf2b0ee5fd645e61ffd6e70c47806c9ed51fc75af078d"}, - {file = "pydantic_core-2.14.5-cp39-cp39-macosx_10_7_x86_64.whl", hash = "sha256:a6a16f4a527aae4f49c875da3cdc9508ac7eef26e7977952608610104244e1b7"}, - {file = "pydantic_core-2.14.5-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:abf058be9517dc877227ec3223f0300034bd0e9f53aebd63cf4456c8cb1e0863"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:49b08aae5013640a3bfa25a8eebbd95638ec3f4b2eaf6ed82cf0c7047133f03b"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:c2d97e906b4ff36eb464d52a3bc7d720bd6261f64bc4bcdbcd2c557c02081ed2"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3128e0bbc8c091ec4375a1828d6118bc20404883169ac95ffa8d983b293611e6"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:88e74ab0cdd84ad0614e2750f903bb0d610cc8af2cc17f72c28163acfcf372a4"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c339dabd8ee15f8259ee0f202679b6324926e5bc9e9a40bf981ce77c038553db"}, - {file = "pydantic_core-2.14.5-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:3387277f1bf659caf1724e1afe8ee7dbc9952a82d90f858ebb931880216ea955"}, - {file = "pydantic_core-2.14.5-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:ba6b6b3846cfc10fdb4c971980a954e49d447cd215ed5a77ec8190bc93dd7bc5"}, - {file = "pydantic_core-2.14.5-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ca61d858e4107ce5e1330a74724fe757fc7135190eb5ce5c9d0191729f033209"}, - {file = "pydantic_core-2.14.5-cp39-none-win32.whl", hash = "sha256:ec1e72d6412f7126eb7b2e3bfca42b15e6e389e1bc88ea0069d0cc1742f477c6"}, - {file = "pydantic_core-2.14.5-cp39-none-win_amd64.whl", hash = "sha256:c0b97ec434041827935044bbbe52b03d6018c2897349670ff8fe11ed24d1d4ab"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-macosx_10_7_x86_64.whl", hash = "sha256:79e0a2cdbdc7af3f4aee3210b1172ab53d7ddb6a2d8c24119b5706e622b346d0"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-macosx_11_0_arm64.whl", hash = "sha256:678265f7b14e138d9a541ddabbe033012a2953315739f8cfa6d754cc8063e8ca"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:95b15e855ae44f0c6341ceb74df61b606e11f1087e87dcb7482377374aac6abe"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:09b0e985fbaf13e6b06a56d21694d12ebca6ce5414b9211edf6f17738d82b0f8"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:3ad873900297bb36e4b6b3f7029d88ff9829ecdc15d5cf20161775ce12306f8a"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:2d0ae0d8670164e10accbeb31d5ad45adb71292032d0fdb9079912907f0085f4"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:d37f8ec982ead9ba0a22a996129594938138a1503237b87318392a48882d50b7"}, - {file = "pydantic_core-2.14.5-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:35613015f0ba7e14c29ac6c2483a657ec740e5ac5758d993fdd5870b07a61d8b"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-macosx_10_7_x86_64.whl", hash = "sha256:ab4ea451082e684198636565224bbb179575efc1658c48281b2c866bfd4ddf04"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4ce601907e99ea5b4adb807ded3570ea62186b17f88e271569144e8cca4409c7"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fb2ed8b3fe4bf4506d6dab3b93b83bbc22237e230cba03866d561c3577517d18"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:70f947628e074bb2526ba1b151cee10e4c3b9670af4dbb4d73bc8a89445916b5"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:4bc536201426451f06f044dfbf341c09f540b4ebdb9fd8d2c6164d733de5e634"}, - {file = "pydantic_core-2.14.5-pp37-pypy37_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:f4791cf0f8c3104ac668797d8c514afb3431bc3305f5638add0ba1a5a37e0d88"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-macosx_10_7_x86_64.whl", hash = "sha256:038c9f763e650712b899f983076ce783175397c848da04985658e7628cbe873b"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-macosx_11_0_arm64.whl", hash = "sha256:27548e16c79702f1e03f5628589c6057c9ae17c95b4c449de3c66b589ead0520"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c97bee68898f3f4344eb02fec316db93d9700fb1e6a5b760ffa20d71d9a46ce3"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b9b759b77f5337b4ea024f03abc6464c9f35d9718de01cfe6bae9f2e139c397e"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:439c9afe34638ace43a49bf72d201e0ffc1a800295bed8420c2a9ca8d5e3dbb3"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:ba39688799094c75ea8a16a6b544eb57b5b0f3328697084f3f2790892510d144"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:ccd4d5702bb90b84df13bd491be8d900b92016c5a455b7e14630ad7449eb03f8"}, - {file = "pydantic_core-2.14.5-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:81982d78a45d1e5396819bbb4ece1fadfe5f079335dd28c4ab3427cd95389944"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-macosx_10_7_x86_64.whl", hash = "sha256:7f8210297b04e53bc3da35db08b7302a6a1f4889c79173af69b72ec9754796b8"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-macosx_11_0_arm64.whl", hash = "sha256:8c8a8812fe6f43a3a5b054af6ac2d7b8605c7bcab2804a8a7d68b53f3cd86e00"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:206ed23aecd67c71daf5c02c3cd19c0501b01ef3cbf7782db9e4e051426b3d0d"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c2027d05c8aebe61d898d4cffd774840a9cb82ed356ba47a90d99ad768f39789"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:40180930807ce806aa71eda5a5a5447abb6b6a3c0b4b3b1b1962651906484d68"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:615a0a4bff11c45eb3c1996ceed5bdaa2f7b432425253a7c2eed33bb86d80abc"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:f5e412d717366e0677ef767eac93566582518fe8be923361a5c204c1a62eaafe"}, - {file = "pydantic_core-2.14.5-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:513b07e99c0a267b1d954243845d8a833758a6726a3b5d8948306e3fe14675e3"}, - {file = "pydantic_core-2.14.5.tar.gz", hash = "sha256:6d30226dfc816dd0fdf120cae611dd2215117e4f9b124af8c60ab9093b6e8e71"}, + {file = "pydantic_core-2.14.6-cp310-cp310-macosx_10_7_x86_64.whl", hash = "sha256:72f9a942d739f09cd42fffe5dc759928217649f070056f03c70df14f5770acf9"}, + {file = "pydantic_core-2.14.6-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:6a31d98c0d69776c2576dda4b77b8e0c69ad08e8b539c25c7d0ca0dc19a50d6c"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5aa90562bc079c6c290f0512b21768967f9968e4cfea84ea4ff5af5d917016e4"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:370ffecb5316ed23b667d99ce4debe53ea664b99cc37bfa2af47bc769056d534"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f85f3843bdb1fe80e8c206fe6eed7a1caeae897e496542cee499c374a85c6e08"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:9862bf828112e19685b76ca499b379338fd4c5c269d897e218b2ae8fcb80139d"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:036137b5ad0cb0004c75b579445a1efccd072387a36c7f217bb8efd1afbe5245"}, + {file = "pydantic_core-2.14.6-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:92879bce89f91f4b2416eba4429c7b5ca22c45ef4a499c39f0c5c69257522c7c"}, + {file = "pydantic_core-2.14.6-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:0c08de15d50fa190d577e8591f0329a643eeaed696d7771760295998aca6bc66"}, + {file = "pydantic_core-2.14.6-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:36099c69f6b14fc2c49d7996cbf4f87ec4f0e66d1c74aa05228583225a07b590"}, + {file = "pydantic_core-2.14.6-cp310-none-win32.whl", hash = "sha256:7be719e4d2ae6c314f72844ba9d69e38dff342bc360379f7c8537c48e23034b7"}, + {file = "pydantic_core-2.14.6-cp310-none-win_amd64.whl", hash = "sha256:36fa402dcdc8ea7f1b0ddcf0df4254cc6b2e08f8cd80e7010d4c4ae6e86b2a87"}, + {file = "pydantic_core-2.14.6-cp311-cp311-macosx_10_7_x86_64.whl", hash = "sha256:dea7fcd62915fb150cdc373212141a30037e11b761fbced340e9db3379b892d4"}, + {file = "pydantic_core-2.14.6-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:ffff855100bc066ff2cd3aa4a60bc9534661816b110f0243e59503ec2df38421"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1b027c86c66b8627eb90e57aee1f526df77dc6d8b354ec498be9a757d513b92b"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:00b1087dabcee0b0ffd104f9f53d7d3eaddfaa314cdd6726143af6bc713aa27e"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:75ec284328b60a4e91010c1acade0c30584f28a1f345bc8f72fe8b9e46ec6a96"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:7e1f4744eea1501404b20b0ac059ff7e3f96a97d3e3f48ce27a139e053bb370b"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b2602177668f89b38b9f84b7b3435d0a72511ddef45dc14446811759b82235a1"}, + {file = "pydantic_core-2.14.6-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:6c8edaea3089bf908dd27da8f5d9e395c5b4dc092dbcce9b65e7156099b4b937"}, + {file = "pydantic_core-2.14.6-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:478e9e7b360dfec451daafe286998d4a1eeaecf6d69c427b834ae771cad4b622"}, + {file = "pydantic_core-2.14.6-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:b6ca36c12a5120bad343eef193cc0122928c5c7466121da7c20f41160ba00ba2"}, + {file = "pydantic_core-2.14.6-cp311-none-win32.whl", hash = "sha256:2b8719037e570639e6b665a4050add43134d80b687288ba3ade18b22bbb29dd2"}, + {file = "pydantic_core-2.14.6-cp311-none-win_amd64.whl", hash = "sha256:78ee52ecc088c61cce32b2d30a826f929e1708f7b9247dc3b921aec367dc1b23"}, + {file = "pydantic_core-2.14.6-cp311-none-win_arm64.whl", hash = "sha256:a19b794f8fe6569472ff77602437ec4430f9b2b9ec7a1105cfd2232f9ba355e6"}, + {file = "pydantic_core-2.14.6-cp312-cp312-macosx_10_7_x86_64.whl", hash = "sha256:667aa2eac9cd0700af1ddb38b7b1ef246d8cf94c85637cbb03d7757ca4c3fdec"}, + {file = "pydantic_core-2.14.6-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:cdee837710ef6b56ebd20245b83799fce40b265b3b406e51e8ccc5b85b9099b7"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2c5bcf3414367e29f83fd66f7de64509a8fd2368b1edf4351e862910727d3e51"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:26a92ae76f75d1915806b77cf459811e772d8f71fd1e4339c99750f0e7f6324f"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a983cca5ed1dd9a35e9e42ebf9f278d344603bfcb174ff99a5815f953925140a"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cb92f9061657287eded380d7dc455bbf115430b3aa4741bdc662d02977e7d0af"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e4ace1e220b078c8e48e82c081e35002038657e4b37d403ce940fa679e57113b"}, + {file = "pydantic_core-2.14.6-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:ef633add81832f4b56d3b4c9408b43d530dfca29e68fb1b797dcb861a2c734cd"}, + {file = "pydantic_core-2.14.6-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:7e90d6cc4aad2cc1f5e16ed56e46cebf4877c62403a311af20459c15da76fd91"}, + {file = "pydantic_core-2.14.6-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:e8a5ac97ea521d7bde7621d86c30e86b798cdecd985723c4ed737a2aa9e77d0c"}, + {file = "pydantic_core-2.14.6-cp312-none-win32.whl", hash = "sha256:f27207e8ca3e5e021e2402ba942e5b4c629718e665c81b8b306f3c8b1ddbb786"}, + {file = "pydantic_core-2.14.6-cp312-none-win_amd64.whl", hash = "sha256:b3e5fe4538001bb82e2295b8d2a39356a84694c97cb73a566dc36328b9f83b40"}, + {file = "pydantic_core-2.14.6-cp312-none-win_arm64.whl", hash = "sha256:64634ccf9d671c6be242a664a33c4acf12882670b09b3f163cd00a24cffbd74e"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-macosx_10_7_x86_64.whl", hash = "sha256:24368e31be2c88bd69340fbfe741b405302993242ccb476c5c3ff48aeee1afe0"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-macosx_11_0_arm64.whl", hash = "sha256:e33b0834f1cf779aa839975f9d8755a7c2420510c0fa1e9fa0497de77cd35d2c"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6af4b3f52cc65f8a0bc8b1cd9676f8c21ef3e9132f21fed250f6958bd7223bed"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d15687d7d7f40333bd8266f3814c591c2e2cd263fa2116e314f60d82086e353a"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:095b707bb287bfd534044166ab767bec70a9bba3175dcdc3371782175c14e43c"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:94fc0e6621e07d1e91c44e016cc0b189b48db053061cc22d6298a611de8071bb"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1ce830e480f6774608dedfd4a90c42aac4a7af0a711f1b52f807130c2e434c06"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:a306cdd2ad3a7d795d8e617a58c3a2ed0f76c8496fb7621b6cd514eb1532cae8"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:2f5fa187bde8524b1e37ba894db13aadd64faa884657473b03a019f625cee9a8"}, + {file = "pydantic_core-2.14.6-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:438027a975cc213a47c5d70672e0d29776082155cfae540c4e225716586be75e"}, + {file = "pydantic_core-2.14.6-cp37-none-win32.whl", hash = "sha256:f96ae96a060a8072ceff4cfde89d261837b4294a4f28b84a28765470d502ccc6"}, + {file = "pydantic_core-2.14.6-cp37-none-win_amd64.whl", hash = "sha256:e646c0e282e960345314f42f2cea5e0b5f56938c093541ea6dbf11aec2862391"}, + {file = "pydantic_core-2.14.6-cp38-cp38-macosx_10_7_x86_64.whl", hash = "sha256:db453f2da3f59a348f514cfbfeb042393b68720787bbef2b4c6068ea362c8149"}, + {file = "pydantic_core-2.14.6-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:3860c62057acd95cc84044e758e47b18dcd8871a328ebc8ccdefd18b0d26a21b"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:36026d8f99c58d7044413e1b819a67ca0e0b8ebe0f25e775e6c3d1fabb3c38fb"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:8ed1af8692bd8d2a29d702f1a2e6065416d76897d726e45a1775b1444f5928a7"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:314ccc4264ce7d854941231cf71b592e30d8d368a71e50197c905874feacc8a8"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:982487f8931067a32e72d40ab6b47b1628a9c5d344be7f1a4e668fb462d2da42"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2dbe357bc4ddda078f79d2a36fc1dd0494a7f2fad83a0a684465b6f24b46fe80"}, + {file = "pydantic_core-2.14.6-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:2f6ffc6701a0eb28648c845f4945a194dc7ab3c651f535b81793251e1185ac3d"}, + {file = "pydantic_core-2.14.6-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:7f5025db12fc6de7bc1104d826d5aee1d172f9ba6ca936bf6474c2148ac336c1"}, + {file = "pydantic_core-2.14.6-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:dab03ed811ed1c71d700ed08bde8431cf429bbe59e423394f0f4055f1ca0ea60"}, + {file = "pydantic_core-2.14.6-cp38-none-win32.whl", hash = "sha256:dfcbebdb3c4b6f739a91769aea5ed615023f3c88cb70df812849aef634c25fbe"}, + {file = "pydantic_core-2.14.6-cp38-none-win_amd64.whl", hash = "sha256:99b14dbea2fdb563d8b5a57c9badfcd72083f6006caf8e126b491519c7d64ca8"}, + {file = "pydantic_core-2.14.6-cp39-cp39-macosx_10_7_x86_64.whl", hash = "sha256:4ce8299b481bcb68e5c82002b96e411796b844d72b3e92a3fbedfe8e19813eab"}, + {file = "pydantic_core-2.14.6-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:b9a9d92f10772d2a181b5ca339dee066ab7d1c9a34ae2421b2a52556e719756f"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fd9e98b408384989ea4ab60206b8e100d8687da18b5c813c11e92fd8212a98e0"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4f86f1f318e56f5cbb282fe61eb84767aee743ebe32c7c0834690ebea50c0a6b"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:86ce5fcfc3accf3a07a729779d0b86c5d0309a4764c897d86c11089be61da160"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:3dcf1978be02153c6a31692d4fbcc2a3f1db9da36039ead23173bc256ee3b91b"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:eedf97be7bc3dbc8addcef4142f4b4164066df0c6f36397ae4aaed3eb187d8ab"}, + {file = "pydantic_core-2.14.6-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:d5f916acf8afbcab6bacbb376ba7dc61f845367901ecd5e328fc4d4aef2fcab0"}, + {file = "pydantic_core-2.14.6-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:8a14c192c1d724c3acbfb3f10a958c55a2638391319ce8078cb36c02283959b9"}, + {file = "pydantic_core-2.14.6-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:0348b1dc6b76041516e8a854ff95b21c55f5a411c3297d2ca52f5528e49d8411"}, + {file = "pydantic_core-2.14.6-cp39-none-win32.whl", hash = "sha256:de2a0645a923ba57c5527497daf8ec5df69c6eadf869e9cd46e86349146e5975"}, + {file = "pydantic_core-2.14.6-cp39-none-win_amd64.whl", hash = "sha256:aca48506a9c20f68ee61c87f2008f81f8ee99f8d7f0104bff3c47e2d148f89d9"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-macosx_10_7_x86_64.whl", hash = "sha256:d5c28525c19f5bb1e09511669bb57353d22b94cf8b65f3a8d141c389a55dec95"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-macosx_11_0_arm64.whl", hash = "sha256:78d0768ee59baa3de0f4adac9e3748b4b1fffc52143caebddfd5ea2961595277"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8b93785eadaef932e4fe9c6e12ba67beb1b3f1e5495631419c784ab87e975670"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a874f21f87c485310944b2b2734cd6d318765bcbb7515eead33af9641816506e"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:b89f4477d915ea43b4ceea6756f63f0288941b6443a2b28c69004fe07fde0d0d"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:172de779e2a153d36ee690dbc49c6db568d7b33b18dc56b69a7514aecbcf380d"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:dfcebb950aa7e667ec226a442722134539e77c575f6cfaa423f24371bb8d2e94"}, + {file = "pydantic_core-2.14.6-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:55a23dcd98c858c0db44fc5c04fc7ed81c4b4d33c653a7c45ddaebf6563a2f66"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-macosx_10_7_x86_64.whl", hash = "sha256:4241204e4b36ab5ae466ecec5c4c16527a054c69f99bba20f6f75232a6a534e2"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e574de99d735b3fc8364cba9912c2bec2da78775eba95cbb225ef7dda6acea24"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1302a54f87b5cd8528e4d6d1bf2133b6aa7c6122ff8e9dc5220fbc1e07bffebd"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:f8e81e4b55930e5ffab4a68db1af431629cf2e4066dbdbfef65348b8ab804ea8"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:c99462ffc538717b3e60151dfaf91125f637e801f5ab008f81c402f1dff0cd0f"}, + {file = "pydantic_core-2.14.6-pp37-pypy37_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:e4cf2d5829f6963a5483ec01578ee76d329eb5caf330ecd05b3edd697e7d768a"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-macosx_10_7_x86_64.whl", hash = "sha256:cf10b7d58ae4a1f07fccbf4a0a956d705356fea05fb4c70608bb6fa81d103cda"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-macosx_11_0_arm64.whl", hash = "sha256:399ac0891c284fa8eb998bcfa323f2234858f5d2efca3950ae58c8f88830f145"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9c6a5c79b28003543db3ba67d1df336f253a87d3112dac3a51b94f7d48e4c0e1"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:599c87d79cab2a6a2a9df4aefe0455e61e7d2aeede2f8577c1b7c0aec643ee8e"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:43e166ad47ba900f2542a80d83f9fc65fe99eb63ceec4debec160ae729824052"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:3a0b5db001b98e1c649dd55afa928e75aa4087e587b9524a4992316fa23c9fba"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:747265448cb57a9f37572a488a57d873fd96bf51e5bb7edb52cfb37124516da4"}, + {file = "pydantic_core-2.14.6-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:7ebe3416785f65c28f4f9441e916bfc8a54179c8dea73c23023f7086fa601c5d"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-macosx_10_7_x86_64.whl", hash = "sha256:86c963186ca5e50d5c8287b1d1c9d3f8f024cbe343d048c5bd282aec2d8641f2"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-macosx_11_0_arm64.whl", hash = "sha256:e0641b506486f0b4cd1500a2a65740243e8670a2549bb02bc4556a83af84ae03"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:71d72ca5eaaa8d38c8df16b7deb1a2da4f650c41b58bb142f3fb75d5ad4a611f"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:27e524624eace5c59af499cd97dc18bb201dc6a7a2da24bfc66ef151c69a5f2a"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:a3dde6cac75e0b0902778978d3b1646ca9f438654395a362cb21d9ad34b24acf"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-musllinux_1_1_aarch64.whl", hash = "sha256:00646784f6cd993b1e1c0e7b0fdcbccc375d539db95555477771c27555e3c556"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-musllinux_1_1_x86_64.whl", hash = "sha256:23598acb8ccaa3d1d875ef3b35cb6376535095e9405d91a3d57a8c7db5d29341"}, + {file = "pydantic_core-2.14.6-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:7f41533d7e3cf9520065f610b41ac1c76bc2161415955fbcead4981b22c7611e"}, + {file = "pydantic_core-2.14.6.tar.gz", hash = "sha256:1fd0c1d395372843fba13a51c28e3bb9d59bd7aebfeb17358ffaaa1e4dbbe948"}, ] [package.dependencies] @@ -5468,43 +5561,47 @@ reference = "tsinghua" [[package]] name = "pyfreerdp" -version = "0.0.1" -description = "" +version = "0.0.2" +description = "Python wrapper for FreeRDP" optional = false -python-versions = "*" +python-versions = ">=3.10" files = [ - {file = "pyfreerdp-0.0.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:74b4e757d879b1d01c0bd7e1f91c17ddc007b941b92766f11077696546758490"}, - {file = "pyfreerdp-0.0.1-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2c73dc9c87c185cd009c00561102a4727bb0cdff69e69eeb9af02a87b1ed627a"}, - {file = "pyfreerdp-0.0.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:363a9caea1b56f82726eea42bc42f47750440867ce1958e3855f5a01aed3d23a"}, - {file = "pyfreerdp-0.0.1-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:310a8471afb533d0ab4ff1fdb10c54106884883ed727e1ad6b61491a7fed466f"}, - {file = "pyfreerdp-0.0.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c869ca101e7e262dfa536472e3ac192c89999351f682328bfbcf056daa98aa99"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:1a48ac00d35a2c2fd7bacbbd93b9753995d7b80f3202b2cacd35e1ece3154cd9"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:f3c7c635316ab2ab8f0379f146b4fdec6636123ed45c0ef6edce6f9d615bcbba"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2edc5d938f2bbb337b70c46413a3a578257daf852211a4fb71ad592c57870436"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ee1439e6fc82ed5973ec098eb47c532abdb8de6d48f36b736cc39855f76df217"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:0ea400aaff3c00fa6b2fdcdf52696b27cfe16ce83feeffc22969eabebacfde1d"}, - {file = "pyfreerdp-0.0.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:4d5f3340086956bedbf8cf0b43bb974e516df1730f80e63e4914fd0c6001e17f"}, - {file = "pyfreerdp-0.0.1-cp37-cp37m-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f205f4d29da3bb118681bbc9ae732fb607fc86da210b04b4916a711fa1b67a9d"}, - {file = "pyfreerdp-0.0.1-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3d424c70a36280f5445b6d213f947f3fffca1142a4414e5b3bb56c870f114397"}, - {file = "pyfreerdp-0.0.1-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:38eafc6a60759a25d97ae45f030a0c4e6c8c8a018541fc2076115cf302fd9475"}, - {file = "pyfreerdp-0.0.1-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:9b26a9ff4e25d04631330da16f3bdad2e805948edb3367f175b5db4cc6eed573"}, - {file = "pyfreerdp-0.0.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:414ede648e851be7fb0b8bd7b2f38390c5561ef73ea2f15bce2689fbbdaecb8b"}, - {file = "pyfreerdp-0.0.1-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:5cec04cce9aa23268a0e8b1de78c65708b46a9fb8b7664f7bc00932761eed359"}, - {file = "pyfreerdp-0.0.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:75f31d916bcadc015c775167895c823be8909aff8286847bc61f1162dd751fc0"}, - {file = "pyfreerdp-0.0.1-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:352d30fe3d7f4323b37f474faaed34b21ea3f230a53911e834ec5a51e9cc747b"}, - {file = "pyfreerdp-0.0.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:dd3e4cf7f24fb8a3eef4bf2e1147d92437e3298027280eef29a6d08c84b3e7dd"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:1ba8c23643746d9638469c7a8981f9d57a9bdf068d03fa2c32c28728011db7cc"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-macosx_12_0_arm64.whl", hash = "sha256:05f0f16dc1621cfbd3da6b3f8acd292dcf09ac2cde3a578aec7af359a65174b9"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c4f577beba135c1b603e0cc3b1a71fbfc53bdb53a5aeedc7650f1120a5d52d14"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4c8311d355b54cdfadccc2dba7c9d8962aa8179f4c5a852ecb3a33bc9a6f0ee2"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:51ecfecc1a8a40a2461a5b4ff105bc92ef86a57fd6364c3c309c6fe7c66fb5e7"}, - {file = "pyfreerdp-0.0.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:48cf5c73d98d3f8edaf229c78884828652242036484dff3e61974bf1bce852a3"}, - {file = "pyfreerdp-0.0.1-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e3adaaf7bb2e32c2288a4bb939130fa0a3afb5d87a11c46c2d6f882c051ee43e"}, - {file = "pyfreerdp-0.0.1-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:2127d10afa600d691e4b4795f3c6e70cf227e9a65b536bc0ec096f93eb92b4dd"}, - {file = "pyfreerdp-0.0.1-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8ed7f0413e4e5c0c03c01f9bcf24eb3fe2b0223fc84947917352421fbd548de5"}, - {file = "pyfreerdp-0.0.1-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:40a91c509fe62ef74341e5ef66b3ac8530f989df87cf5477945de2eb8984522f"}, - {file = "pyfreerdp-0.0.1-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:509e1643fc87c597ec5bc1ab9505e2839b5e9ca049b5af95a3d70b828e8c4bfd"}, - {file = "pyfreerdp-0.0.1.tar.gz", hash = "sha256:946eca882741e6802794185cbdd47b49626c3181bce99dbd27c5746563c13d43"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:27ca63ac041dc5f657e0a87e81d05139ac0100124dcc84ea2ae7c5ae8daf28e8"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e7ce5d215c08601b938c61fa3ad75c975bb35bf5bdecd154437534c3962d6072"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ae5d310b578e1dbf1da191817266161a030ba987234bd8c675efbce8b1e8c6ac"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:25fc92f15b63ab9f018f36391464a102c32edee090a98932817827d24c69633c"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:78b8d8db814ef56c62c4582d27da44aab4f6630146b88d4428dfabbc1c754202"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:ed6a302ed8b475f7c0df1fe37922fd786706f5b632196e32b911ff566600f880"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:99dfe7bd0fcda0003dd41b72b80b76d24dddde0b66535b507d823a5ce073ec2a"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:881003ce2853d9a290c47a04c165941a5a0addd7ad360d033f275dec3eead192"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:a54ae7c62b3c92e4dba082e328e0bb190f83f45eb84cf59eabb894dfe24a07f7"}, + {file = "pyfreerdp-0.0.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:33c3e14664e306c31c2a792cb8dfdd6a381e35f79583a271dd20be25b14ad73d"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:c7df63da48b67a31d76b62ee70f5f0ffc964b79b34c4e6c610f67a24fba2aee1"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-macosx_12_0_x86_64.whl", hash = "sha256:df62184ef7fd8bc76f9efd172387e6e7cef9f3777a57bb14f3551b2972f55ef3"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4cfd97b8da87b1439407b40e7eda998f0df44332211353b0f4217e91d233bc53"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a9ce1a906e861335864bb8c976612a5b1d0595955b0cde35e3697eed7812c8b6"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9b630f604300323b3e1fe6b27d442636f9b0d247eba3cc4340a39721c6d85273"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:7ecd8bab19ab9a4b6bd22e82821e697ffe2b48de1f648e85064e1083b1dafbc7"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:22be067f8aa145726f73c893c820339f103e91abfa204fdf20647c6b866c3e27"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:26ffa208cd92c344f1003704a10e0cc2f92cfe935e077626b9e6564e351c306e"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:93ae2624af6eb117ff27137659d72362b46bbd6f0e3474183a44bcdca1808a3f"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:75ecac10e8879b9c163f68fef32bfb308d95d04fa9c89a37624aba34ce16e652"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:0cccf234d8b08ded94a76894608ad848c002d87b3c0998d1462863ad1117c298"}, + {file = "pyfreerdp-0.0.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:f9de9830825e6ef12536759fc04f51243451553909eb91c903a03f181da7a610"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e2016772418ea6708d07becc7334425b2a19610fea38f28597b0e9dd57c302f0"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f659cd917d8dd291a8d5d6198f23b84a9ac9835c642b80a578dba9d85c8db975"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1770a1bcfbf953448ad17cc871ba68ed14321f6168054a2bb7b185c2d967ee5d"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8aac97779172199a2e9a24889cf2284adc66ef0757c2214dce1f4307e381678b"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:36497154f63a5b5cc9cba0e821d17ee7890d7b2c00d73630be2c4ca512a72d45"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:9ecbf36edbc4fdc64e2ae5e513c8a5bf97d82fcb1634271b8d9a1c021e76a109"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:649884ef8642b732f4b24bcb5a8ca7c040b5b909ca5e97bcd297faf31510d108"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:f19b370c370e4ed18985455deb48b06e51f33cce6c3eb889e421a76f33fb13c0"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:4db29d2f12875b764baaed9d76251c3be739485cfce3dbf030977c2bd7d79fca"}, + {file = "pyfreerdp-0.0.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:caf6cf6b33bb08761b1a8680c41525170c139a8e6848441f2061eef96369da19"}, + {file = "pyfreerdp-0.0.2-pp310-pypy310_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:eb31b620013859a7142a391d9ce57c195f26c3c9991883f87bc5ef1703cf806f"}, + {file = "pyfreerdp-0.0.2-pp310-pypy310_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c839d3ed9c0cc4021129e26c06d3bc45982bdaba8a2a115051ad43c5f6108d11"}, + {file = "pyfreerdp-0.0.2-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d3c2a23db4a56903dfff9ac5e8b2b7aa713af694dce5a4f3905ef7703b4f9dcd"}, + {file = "pyfreerdp-0.0.2.tar.gz", hash = "sha256:caf4b422eb32a327095b548bb1a22a22b926b6e15819c9a83b6461050b11870d"}, ] [package.source] @@ -5719,11 +5816,9 @@ files = [ {file = "pymssql-2.2.8-cp310-cp310-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:049f2e3de919e8e02504780a21ebbf235e21ca8ed5c7538c5b6e705aa6c43d8c"}, {file = "pymssql-2.2.8-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0dd86d8e3e346e34f3f03d12e333747b53a1daa74374a727f4714d5b82ee0dd5"}, {file = "pymssql-2.2.8-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:508226a0df7cb6faeda9f8e84e85743690ca427d7b27af9a73d75fcf0c1eef6e"}, - {file = "pymssql-2.2.8-cp310-cp310-win_amd64.whl", hash = "sha256:47859887adeaf184766b5e0bc845dd23611f3808f9521552063bb36eabc10092"}, {file = "pymssql-2.2.8-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:d873e553374d5b1c57fe1c43bb75e3bcc2920678db1ef26f6bfed396c7d21b30"}, {file = "pymssql-2.2.8-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bf31b8b76634c826a91f9999e15b7bfb0c051a0f53b319fd56481a67e5b903bb"}, {file = "pymssql-2.2.8-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:821945c2214fe666fd456c61e09a29a00e7719c9e136c801bffb3a254e9c579b"}, - {file = "pymssql-2.2.8-cp311-cp311-win_amd64.whl", hash = "sha256:cc85b609b4e60eac25fa38bbac1ff854fd2c2a276e0ca4a3614c6f97efb644bb"}, {file = "pymssql-2.2.8-cp36-cp36m-macosx_10_14_x86_64.whl", hash = "sha256:ebe7f64d5278d807f14bea08951e02512bfbc6219fd4d4f15bb45ded885cf3d4"}, {file = "pymssql-2.2.8-cp36-cp36m-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:253af3d39fc0235627966817262d5c4c94ad09dcbea59664748063470048c29c"}, {file = "pymssql-2.2.8-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2c9d109df536dc5f7dd851a88d285a4c9cb12a9314b621625f4f5ab1197eb312"}, @@ -5739,13 +5834,11 @@ files = [ {file = "pymssql-2.2.8-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3906993300650844ec140aa58772c0f5f3e9e9d5709c061334fd1551acdcf066"}, {file = "pymssql-2.2.8-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:7309c7352e4a87c9995c3183ebfe0ff4135e955bb759109637673c61c9f0ca8d"}, {file = "pymssql-2.2.8-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:9b8d603cc1ec7ae585c5a409a1d45e8da067970c79dd550d45c238ae0aa0f79f"}, - {file = "pymssql-2.2.8-cp38-cp38-win_amd64.whl", hash = "sha256:293cb4d0339e221d877d6b19a1905082b658f0100a1e2ccc9dda10de58938901"}, {file = "pymssql-2.2.8-cp39-cp39-macosx_11_0_x86_64.whl", hash = "sha256:895041edd002a2e91d8a4faf0906b6fbfef29d9164bc6beb398421f5927fa40e"}, {file = "pymssql-2.2.8-cp39-cp39-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:6b2d9c6d38a416c6f2db36ff1cd8e69f9a5387a46f9f4f612623192e0c9404b1"}, {file = "pymssql-2.2.8-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d63d6f25cf40fe6a03c49be2d4d337858362b8ab944d6684c268e4990807cf0c"}, {file = "pymssql-2.2.8-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:c83ad3ad20951f3a94894b354fa5fa9666dcd5ebb4a635dad507c7d1dd545833"}, {file = "pymssql-2.2.8-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:3933f7f082be74698eea835df51798dab9bc727d94d3d280bffc75ab9265f890"}, - {file = "pymssql-2.2.8-cp39-cp39-win_amd64.whl", hash = "sha256:de313375b90b0f554058992f35c4a4beb3f6ec2f5912d8cd6afb649f95b03a9f"}, {file = "pymssql-2.2.8.tar.gz", hash = "sha256:9baefbfbd07d0142756e2dfcaa804154361ac5806ab9381350aad4e780c3033e"}, ] @@ -6234,7 +6327,6 @@ files = [ {file = "PyYAML-6.0.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:69b023b2b4daa7548bcfbd4aa3da05b3a74b772db9e23b982788168117739938"}, {file = "PyYAML-6.0.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:81e0b275a9ecc9c0c0c07b4b90ba548307583c125f54d5b6946cfee6360c733d"}, {file = "PyYAML-6.0.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ba336e390cd8e4d1739f42dfe9bb83a3cc2e80f567d8805e11b46f4a943f5515"}, - {file = "PyYAML-6.0.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:326c013efe8048858a6d312ddd31d56e468118ad4cdeda36c719bf5bb6192290"}, {file = "PyYAML-6.0.1-cp310-cp310-win32.whl", hash = "sha256:bd4af7373a854424dabd882decdc5579653d7868b8fb26dc7d0e99f823aa5924"}, {file = "PyYAML-6.0.1-cp310-cp310-win_amd64.whl", hash = "sha256:fd1592b3fdf65fff2ad0004b5e363300ef59ced41c2e6b3a99d4089fa8c5435d"}, {file = "PyYAML-6.0.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:6965a7bc3cf88e5a1c3bd2e0b5c22f8d677dc88a455344035f03399034eb3007"}, @@ -6242,15 +6334,8 @@ files = [ {file = "PyYAML-6.0.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:42f8152b8dbc4fe7d96729ec2b99c7097d656dc1213a3229ca5383f973a5ed6d"}, {file = "PyYAML-6.0.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:062582fca9fabdd2c8b54a3ef1c978d786e0f6b3a1510e0ac93ef59e0ddae2bc"}, {file = "PyYAML-6.0.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d2b04aac4d386b172d5b9692e2d2da8de7bfb6c387fa4f801fbf6fb2e6ba4673"}, - {file = "PyYAML-6.0.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:e7d73685e87afe9f3b36c799222440d6cf362062f78be1013661b00c5c6f678b"}, {file = "PyYAML-6.0.1-cp311-cp311-win32.whl", hash = "sha256:1635fd110e8d85d55237ab316b5b011de701ea0f29d07611174a1b42f1444741"}, {file = "PyYAML-6.0.1-cp311-cp311-win_amd64.whl", hash = "sha256:bf07ee2fef7014951eeb99f56f39c9bb4af143d8aa3c21b1677805985307da34"}, - {file = "PyYAML-6.0.1-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:855fb52b0dc35af121542a76b9a84f8d1cd886ea97c84703eaa6d88e37a2ad28"}, - {file = "PyYAML-6.0.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:40df9b996c2b73138957fe23a16a4f0ba614f4c0efce1e9406a184b6d07fa3a9"}, - {file = "PyYAML-6.0.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6c22bec3fbe2524cde73d7ada88f6566758a8f7227bfbf93a408a9d86bcc12a0"}, - {file = "PyYAML-6.0.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:8d4e9c88387b0f5c7d5f281e55304de64cf7f9c0021a3525bd3b1c542da3b0e4"}, - {file = "PyYAML-6.0.1-cp312-cp312-win32.whl", hash = "sha256:d483d2cdf104e7c9fa60c544d92981f12ad66a457afae824d146093b8c294c54"}, - {file = "PyYAML-6.0.1-cp312-cp312-win_amd64.whl", hash = "sha256:0d3304d8c0adc42be59c5f8a4d9e3d7379e6955ad754aa9d6ab7a398b59dd1df"}, {file = "PyYAML-6.0.1-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:50550eb667afee136e9a77d6dc71ae76a44df8b3e51e41b77f6de2932bfe0f47"}, {file = "PyYAML-6.0.1-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1fe35611261b29bd1de0070f0b2f47cb6ff71fa6595c077e42bd0c419fa27b98"}, {file = "PyYAML-6.0.1-cp36-cp36m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:704219a11b772aea0d8ecd7058d0082713c3562b4e271b849ad7dc4a5c90c13c"}, @@ -6267,7 +6352,6 @@ files = [ {file = "PyYAML-6.0.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a0cd17c15d3bb3fa06978b4e8958dcdc6e0174ccea823003a106c7d4d7899ac5"}, {file = "PyYAML-6.0.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:28c119d996beec18c05208a8bd78cbe4007878c6dd15091efb73a30e90539696"}, {file = "PyYAML-6.0.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7e07cbde391ba96ab58e532ff4803f79c4129397514e1413a7dc761ccd755735"}, - {file = "PyYAML-6.0.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:49a183be227561de579b4a36efbb21b3eab9651dd81b1858589f796549873dd6"}, {file = "PyYAML-6.0.1-cp38-cp38-win32.whl", hash = "sha256:184c5108a2aca3c5b3d3bf9395d50893a7ab82a38004c8f61c258d4428e80206"}, {file = "PyYAML-6.0.1-cp38-cp38-win_amd64.whl", hash = "sha256:1e2722cc9fbb45d9b87631ac70924c11d3a401b2d7f410cc0e3bbf249f2dca62"}, {file = "PyYAML-6.0.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:9eb6caa9a297fc2c2fb8862bc5370d0303ddba53ba97e71f08023b6cd73d16a8"}, @@ -6275,7 +6359,6 @@ files = [ {file = "PyYAML-6.0.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5773183b6446b2c99bb77e77595dd486303b4faab2b086e7b17bc6bef28865f6"}, {file = "PyYAML-6.0.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b786eecbdf8499b9ca1d697215862083bd6d2a99965554781d0d8d1ad31e13a0"}, {file = "PyYAML-6.0.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bc1bf2925a1ecd43da378f4db9e4f799775d6367bdb94671027b73b393a7c42c"}, - {file = "PyYAML-6.0.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:04ac92ad1925b2cff1db0cfebffb6ffc43457495c9b3c39d3fcae417d7125dc5"}, {file = "PyYAML-6.0.1-cp39-cp39-win32.whl", hash = "sha256:faca3bdcf85b2fc05d06ff3fbc1f83e1391b3e724afa3feba7d13eeab355484c"}, {file = "PyYAML-6.0.1-cp39-cp39-win_amd64.whl", hash = "sha256:510c9deebc5c0225e8c96813043e62b680ba2f9c50a08d3724c7f28a747d1486"}, {file = "PyYAML-6.0.1.tar.gz", hash = "sha256:bfdf460b1736c775f2ba9f6a92bca30bc2095067b8a9d77876d1fad6cc3b4a43"}, @@ -6568,13 +6651,13 @@ reference = "tsinghua" [[package]] name = "setuptools" -version = "69.0.2" +version = "69.0.3" description = "Easily download, build, install, upgrade, and uninstall Python packages" optional = false python-versions = ">=3.8" files = [ - {file = "setuptools-69.0.2-py3-none-any.whl", hash = "sha256:1e8fdff6797d3865f37397be788a4e3cba233608e9b509382a2777d25ebde7f2"}, - {file = "setuptools-69.0.2.tar.gz", hash = "sha256:735896e78a4742605974de002ac60562d286fa8051a7e2299445e8e8fbb01aa6"}, + {file = "setuptools-69.0.3-py3-none-any.whl", hash = "sha256:385eb4edd9c9d5c17540511303e39a147ce2fc04bc55289c322b9e5904fe2c05"}, + {file = "setuptools-69.0.3.tar.gz", hash = "sha256:be1af57fc409f93647f2e8e4573a142ed38724b8cdd389706a867bb4efcf1e78"}, ] [package.extras] @@ -6945,22 +7028,22 @@ reference = "tsinghua" [[package]] name = "tornado" -version = "6.3.3" +version = "6.4" description = "Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed." optional = false python-versions = ">= 3.8" files = [ - {file = "tornado-6.3.3-cp38-abi3-macosx_10_9_universal2.whl", hash = "sha256:502fba735c84450974fec147340016ad928d29f1e91f49be168c0a4c18181e1d"}, - {file = "tornado-6.3.3-cp38-abi3-macosx_10_9_x86_64.whl", hash = "sha256:805d507b1f588320c26f7f097108eb4023bbaa984d63176d1652e184ba24270a"}, - {file = "tornado-6.3.3-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1bd19ca6c16882e4d37368e0152f99c099bad93e0950ce55e71daed74045908f"}, - {file = "tornado-6.3.3-cp38-abi3-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7ac51f42808cca9b3613f51ffe2a965c8525cb1b00b7b2d56828b8045354f76a"}, - {file = "tornado-6.3.3-cp38-abi3-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:71a8db65160a3c55d61839b7302a9a400074c9c753040455494e2af74e2501f2"}, - {file = "tornado-6.3.3-cp38-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:ceb917a50cd35882b57600709dd5421a418c29ddc852da8bcdab1f0db33406b0"}, - {file = "tornado-6.3.3-cp38-abi3-musllinux_1_1_i686.whl", hash = "sha256:7d01abc57ea0dbb51ddfed477dfe22719d376119844e33c661d873bf9c0e4a16"}, - {file = "tornado-6.3.3-cp38-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:9dc4444c0defcd3929d5c1eb5706cbe1b116e762ff3e0deca8b715d14bf6ec17"}, - {file = "tornado-6.3.3-cp38-abi3-win32.whl", hash = "sha256:65ceca9500383fbdf33a98c0087cb975b2ef3bfb874cb35b8de8740cf7f41bd3"}, - {file = "tornado-6.3.3-cp38-abi3-win_amd64.whl", hash = "sha256:22d3c2fa10b5793da13c807e6fc38ff49a4f6e1e3868b0a6f4164768bb8e20f5"}, - {file = "tornado-6.3.3.tar.gz", hash = "sha256:e7d8db41c0181c80d76c982aacc442c0783a2c54d6400fe028954201a2e032fe"}, + {file = "tornado-6.4-cp38-abi3-macosx_10_9_universal2.whl", hash = "sha256:02ccefc7d8211e5a7f9e8bc3f9e5b0ad6262ba2fbb683a6443ecc804e5224ce0"}, + {file = "tornado-6.4-cp38-abi3-macosx_10_9_x86_64.whl", hash = "sha256:27787de946a9cffd63ce5814c33f734c627a87072ec7eed71f7fc4417bb16263"}, + {file = "tornado-6.4-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f7894c581ecdcf91666a0912f18ce5e757213999e183ebfc2c3fdbf4d5bd764e"}, + {file = "tornado-6.4-cp38-abi3-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e43bc2e5370a6a8e413e1e1cd0c91bedc5bd62a74a532371042a18ef19e10579"}, + {file = "tornado-6.4-cp38-abi3-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f0251554cdd50b4b44362f73ad5ba7126fc5b2c2895cc62b14a1c2d7ea32f212"}, + {file = "tornado-6.4-cp38-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:fd03192e287fbd0899dd8f81c6fb9cbbc69194d2074b38f384cb6fa72b80e9c2"}, + {file = "tornado-6.4-cp38-abi3-musllinux_1_1_i686.whl", hash = "sha256:88b84956273fbd73420e6d4b8d5ccbe913c65d31351b4c004ae362eba06e1f78"}, + {file = "tornado-6.4-cp38-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:71ddfc23a0e03ef2df1c1397d859868d158c8276a0603b96cf86892bff58149f"}, + {file = "tornado-6.4-cp38-abi3-win32.whl", hash = "sha256:6f8a6c77900f5ae93d8b4ae1196472d0ccc2775cc1dfdc9e7727889145c45052"}, + {file = "tornado-6.4-cp38-abi3-win_amd64.whl", hash = "sha256:10aeaa8006333433da48dec9fe417877f8bcc21f48dda8d661ae79da357b2a63"}, + {file = "tornado-6.4.tar.gz", hash = "sha256:72291fa6e6bc84e626589f1c29d90a5a6d593ef5ae68052ee2ef000dfd273dee"}, ] [package.source] @@ -7132,13 +7215,13 @@ reference = "tsinghua" [[package]] name = "typing-extensions" -version = "4.8.0" +version = "4.9.0" description = "Backported and Experimental Type Hints for Python 3.8+" optional = false python-versions = ">=3.8" files = [ - {file = "typing_extensions-4.8.0-py3-none-any.whl", hash = "sha256:8f92fc8806f9a6b641eaa5318da32b44d401efaac0f6678c9bc448ba3605faa0"}, - {file = "typing_extensions-4.8.0.tar.gz", hash = "sha256:df8e4339e9cb77357558cbdbceca33c303714cf861d1eef15e1070055ae8b7ef"}, + {file = "typing_extensions-4.9.0-py3-none-any.whl", hash = "sha256:af72aea155e91adfc61c3ae9e0e342dbc0cba726d6cba4b6c72c1f34e47291cd"}, + {file = "typing_extensions-4.9.0.tar.gz", hash = "sha256:23478f88c37f27d76ac8aee6c905017a143b0b1b886c3c9f66bc2fd94f9f5783"}, ] [package.source] @@ -7148,13 +7231,13 @@ reference = "tsinghua" [[package]] name = "tzdata" -version = "2023.3" +version = "2023.4" description = "Provider of IANA time zone data" optional = false python-versions = ">=2" files = [ - {file = "tzdata-2023.3-py2.py3-none-any.whl", hash = "sha256:7e65763eef3120314099b6939b5546db7adce1e7d6f2e179e3df563c70511eda"}, - {file = "tzdata-2023.3.tar.gz", hash = "sha256:11ef1e08e54acb0d4f95bdb1be05da659673de4acbd21bf9c69e94cc5e907a3a"}, + {file = "tzdata-2023.4-py2.py3-none-any.whl", hash = "sha256:aa3ace4329eeacda5b7beb7ea08ece826c28d761cda36e747cfbf97996d39bf3"}, + {file = "tzdata-2023.4.tar.gz", hash = "sha256:dd54c94f294765522c77399649b4fefd95522479a664a0cec87f41bebc6148c9"}, ] [package.source] @@ -7162,6 +7245,28 @@ type = "legacy" url = "https://pypi.tuna.tsinghua.edu.cn/simple" reference = "tsinghua" +[[package]] +name = "tzlocal" +version = "5.2" +description = "tzinfo object for the local timezone" +optional = false +python-versions = ">=3.8" +files = [ + {file = "tzlocal-5.2-py3-none-any.whl", hash = "sha256:49816ef2fe65ea8ac19d19aa7a1ae0551c834303d5014c6d5a62e4cbda8047b8"}, + {file = "tzlocal-5.2.tar.gz", hash = "sha256:8d399205578f1a9342816409cc1e46a93ebd5755e39ea2d85334bea911bf0e6e"}, +] + +[package.dependencies] +tzdata = {version = "*", markers = "platform_system == \"Windows\""} + +[package.extras] +devenv = ["check-manifest", "pytest (>=4.3)", "pytest-cov", "pytest-mock (>=3.3)", "zest.releaser"] + +[package.source] +type = "legacy" +url = "https://pypi.tuna.tsinghua.edu.cn/simple" +reference = "tsinghua" + [[package]] name = "ua-parser" version = "0.18.0" @@ -7604,101 +7709,101 @@ reference = "tsinghua" [[package]] name = "yarl" -version = "1.9.3" +version = "1.9.4" description = "Yet another URL library" optional = false python-versions = ">=3.7" files = [ - {file = "yarl-1.9.3-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:32435d134414e01d937cd9d6cc56e8413a8d4741dea36af5840c7750f04d16ab"}, - {file = "yarl-1.9.3-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:9a5211de242754b5e612557bca701f39f8b1a9408dff73c6db623f22d20f470e"}, - {file = "yarl-1.9.3-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:525cd69eff44833b01f8ef39aa33a9cc53a99ff7f9d76a6ef6a9fb758f54d0ff"}, - {file = "yarl-1.9.3-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fc94441bcf9cb8c59f51f23193316afefbf3ff858460cb47b5758bf66a14d130"}, - {file = "yarl-1.9.3-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e36021db54b8a0475805acc1d6c4bca5d9f52c3825ad29ae2d398a9d530ddb88"}, - {file = "yarl-1.9.3-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e0f17d1df951336a02afc8270c03c0c6e60d1f9996fcbd43a4ce6be81de0bd9d"}, - {file = "yarl-1.9.3-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c5f3faeb8100a43adf3e7925d556801d14b5816a0ac9e75e22948e787feec642"}, - {file = "yarl-1.9.3-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:aed37db837ecb5962469fad448aaae0f0ee94ffce2062cf2eb9aed13328b5196"}, - {file = "yarl-1.9.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:721ee3fc292f0d069a04016ef2c3a25595d48c5b8ddc6029be46f6158d129c92"}, - {file = "yarl-1.9.3-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:b8bc5b87a65a4e64bc83385c05145ea901b613d0d3a434d434b55511b6ab0067"}, - {file = "yarl-1.9.3-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:dd952b9c64f3b21aedd09b8fe958e4931864dba69926d8a90c90d36ac4e28c9a"}, - {file = "yarl-1.9.3-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:c405d482c320a88ab53dcbd98d6d6f32ada074f2d965d6e9bf2d823158fa97de"}, - {file = "yarl-1.9.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:9df9a0d4c5624790a0dea2e02e3b1b3c69aed14bcb8650e19606d9df3719e87d"}, - {file = "yarl-1.9.3-cp310-cp310-win32.whl", hash = "sha256:d34c4f80956227f2686ddea5b3585e109c2733e2d4ef12eb1b8b4e84f09a2ab6"}, - {file = "yarl-1.9.3-cp310-cp310-win_amd64.whl", hash = "sha256:cf7a4e8de7f1092829caef66fd90eaf3710bc5efd322a816d5677b7664893c93"}, - {file = "yarl-1.9.3-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:d61a0ca95503867d4d627517bcfdc28a8468c3f1b0b06c626f30dd759d3999fd"}, - {file = "yarl-1.9.3-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:73cc83f918b69110813a7d95024266072d987b903a623ecae673d1e71579d566"}, - {file = "yarl-1.9.3-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:d81657b23e0edb84b37167e98aefb04ae16cbc5352770057893bd222cdc6e45f"}, - {file = "yarl-1.9.3-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:26a1a8443091c7fbc17b84a0d9f38de34b8423b459fb853e6c8cdfab0eacf613"}, - {file = "yarl-1.9.3-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:fe34befb8c765b8ce562f0200afda3578f8abb159c76de3ab354c80b72244c41"}, - {file = "yarl-1.9.3-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2c757f64afe53a422e45e3e399e1e3cf82b7a2f244796ce80d8ca53e16a49b9f"}, - {file = "yarl-1.9.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:72a57b41a0920b9a220125081c1e191b88a4cdec13bf9d0649e382a822705c65"}, - {file = "yarl-1.9.3-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:632c7aeb99df718765adf58eacb9acb9cbc555e075da849c1378ef4d18bf536a"}, - {file = "yarl-1.9.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b0b8c06afcf2bac5a50b37f64efbde978b7f9dc88842ce9729c020dc71fae4ce"}, - {file = "yarl-1.9.3-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:1d93461e2cf76c4796355494f15ffcb50a3c198cc2d601ad8d6a96219a10c363"}, - {file = "yarl-1.9.3-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:4003f380dac50328c85e85416aca6985536812c082387255c35292cb4b41707e"}, - {file = "yarl-1.9.3-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:4d6d74a97e898c1c2df80339aa423234ad9ea2052f66366cef1e80448798c13d"}, - {file = "yarl-1.9.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:b61e64b06c3640feab73fa4ff9cb64bd8182de52e5dc13038e01cfe674ebc321"}, - {file = "yarl-1.9.3-cp311-cp311-win32.whl", hash = "sha256:29beac86f33d6c7ab1d79bd0213aa7aed2d2f555386856bb3056d5fdd9dab279"}, - {file = "yarl-1.9.3-cp311-cp311-win_amd64.whl", hash = "sha256:f7271d6bd8838c49ba8ae647fc06469137e1c161a7ef97d778b72904d9b68696"}, - {file = "yarl-1.9.3-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:dd318e6b75ca80bff0b22b302f83a8ee41c62b8ac662ddb49f67ec97e799885d"}, - {file = "yarl-1.9.3-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:c4b1efb11a8acd13246ffb0bee888dd0e8eb057f8bf30112e3e21e421eb82d4a"}, - {file = "yarl-1.9.3-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:c6f034386e5550b5dc8ded90b5e2ff7db21f0f5c7de37b6efc5dac046eb19c10"}, - {file = "yarl-1.9.3-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cd49a908cb6d387fc26acee8b7d9fcc9bbf8e1aca890c0b2fdfd706057546080"}, - {file = "yarl-1.9.3-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:aa4643635f26052401750bd54db911b6342eb1a9ac3e74f0f8b58a25d61dfe41"}, - {file = "yarl-1.9.3-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e741bd48e6a417bdfbae02e088f60018286d6c141639359fb8df017a3b69415a"}, - {file = "yarl-1.9.3-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7c86d0d0919952d05df880a1889a4f0aeb6868e98961c090e335671dea5c0361"}, - {file = "yarl-1.9.3-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3d5434b34100b504aabae75f0622ebb85defffe7b64ad8f52b8b30ec6ef6e4b9"}, - {file = "yarl-1.9.3-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:79e1df60f7c2b148722fb6cafebffe1acd95fd8b5fd77795f56247edaf326752"}, - {file = "yarl-1.9.3-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:44e91a669c43f03964f672c5a234ae0d7a4d49c9b85d1baa93dec28afa28ffbd"}, - {file = "yarl-1.9.3-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:3cfa4dbe17b2e6fca1414e9c3bcc216f6930cb18ea7646e7d0d52792ac196808"}, - {file = "yarl-1.9.3-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:88d2c3cc4b2f46d1ba73d81c51ec0e486f59cc51165ea4f789677f91a303a9a7"}, - {file = "yarl-1.9.3-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:cccdc02e46d2bd7cb5f38f8cc3d9db0d24951abd082b2f242c9e9f59c0ab2af3"}, - {file = "yarl-1.9.3-cp312-cp312-win32.whl", hash = "sha256:96758e56dceb8a70f8a5cff1e452daaeff07d1cc9f11e9b0c951330f0a2396a7"}, - {file = "yarl-1.9.3-cp312-cp312-win_amd64.whl", hash = "sha256:c4472fe53ebf541113e533971bd8c32728debc4c6d8cc177f2bff31d011ec17e"}, - {file = "yarl-1.9.3-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:126638ab961633f0940a06e1c9d59919003ef212a15869708dcb7305f91a6732"}, - {file = "yarl-1.9.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c99ddaddb2fbe04953b84d1651149a0d85214780e4d0ee824e610ab549d98d92"}, - {file = "yarl-1.9.3-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8dab30b21bd6fb17c3f4684868c7e6a9e8468078db00f599fb1c14e324b10fca"}, - {file = "yarl-1.9.3-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:828235a2a169160ee73a2fcfb8a000709edf09d7511fccf203465c3d5acc59e4"}, - {file = "yarl-1.9.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fc391e3941045fd0987c77484b2799adffd08e4b6735c4ee5f054366a2e1551d"}, - {file = "yarl-1.9.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:51382c72dd5377861b573bd55dcf680df54cea84147c8648b15ac507fbef984d"}, - {file = "yarl-1.9.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:28a108cb92ce6cf867690a962372996ca332d8cda0210c5ad487fe996e76b8bb"}, - {file = "yarl-1.9.3-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:8f18a7832ff85dfcd77871fe677b169b1bc60c021978c90c3bb14f727596e0ae"}, - {file = "yarl-1.9.3-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:7eaf13af79950142ab2bbb8362f8d8d935be9aaf8df1df89c86c3231e4ff238a"}, - {file = "yarl-1.9.3-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:66a6dbf6ca7d2db03cc61cafe1ee6be838ce0fbc97781881a22a58a7c5efef42"}, - {file = "yarl-1.9.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:1a0a4f3aaa18580038cfa52a7183c8ffbbe7d727fe581300817efc1e96d1b0e9"}, - {file = "yarl-1.9.3-cp37-cp37m-win32.whl", hash = "sha256:946db4511b2d815979d733ac6a961f47e20a29c297be0d55b6d4b77ee4b298f6"}, - {file = "yarl-1.9.3-cp37-cp37m-win_amd64.whl", hash = "sha256:2dad8166d41ebd1f76ce107cf6a31e39801aee3844a54a90af23278b072f1ccf"}, - {file = "yarl-1.9.3-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:bb72d2a94481e7dc7a0c522673db288f31849800d6ce2435317376a345728225"}, - {file = "yarl-1.9.3-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:9a172c3d5447b7da1680a1a2d6ecdf6f87a319d21d52729f45ec938a7006d5d8"}, - {file = "yarl-1.9.3-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:2dc72e891672343b99db6d497024bf8b985537ad6c393359dc5227ef653b2f17"}, - {file = "yarl-1.9.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b8d51817cf4b8d545963ec65ff06c1b92e5765aa98831678d0e2240b6e9fd281"}, - {file = "yarl-1.9.3-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:53ec65f7eee8655bebb1f6f1607760d123c3c115a324b443df4f916383482a67"}, - {file = "yarl-1.9.3-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cfd77e8e5cafba3fb584e0f4b935a59216f352b73d4987be3af51f43a862c403"}, - {file = "yarl-1.9.3-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e73db54c967eb75037c178a54445c5a4e7461b5203b27c45ef656a81787c0c1b"}, - {file = "yarl-1.9.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:09c19e5f4404574fcfb736efecf75844ffe8610606f3fccc35a1515b8b6712c4"}, - {file = "yarl-1.9.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:6280353940f7e5e2efaaabd686193e61351e966cc02f401761c4d87f48c89ea4"}, - {file = "yarl-1.9.3-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:c25ec06e4241e162f5d1f57c370f4078797ade95c9208bd0c60f484834f09c96"}, - {file = "yarl-1.9.3-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:7217234b10c64b52cc39a8d82550342ae2e45be34f5bff02b890b8c452eb48d7"}, - {file = "yarl-1.9.3-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:4ce77d289f8d40905c054b63f29851ecbfd026ef4ba5c371a158cfe6f623663e"}, - {file = "yarl-1.9.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:5f74b015c99a5eac5ae589de27a1201418a5d9d460e89ccb3366015c6153e60a"}, - {file = "yarl-1.9.3-cp38-cp38-win32.whl", hash = "sha256:8a2538806be846ea25e90c28786136932ec385c7ff3bc1148e45125984783dc6"}, - {file = "yarl-1.9.3-cp38-cp38-win_amd64.whl", hash = "sha256:6465d36381af057d0fab4e0f24ef0e80ba61f03fe43e6eeccbe0056e74aadc70"}, - {file = "yarl-1.9.3-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:2f3c8822bc8fb4a347a192dd6a28a25d7f0ea3262e826d7d4ef9cc99cd06d07e"}, - {file = "yarl-1.9.3-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:b7831566595fe88ba17ea80e4b61c0eb599f84c85acaa14bf04dd90319a45b90"}, - {file = "yarl-1.9.3-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ff34cb09a332832d1cf38acd0f604c068665192c6107a439a92abfd8acf90fe2"}, - {file = "yarl-1.9.3-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fe8080b4f25dfc44a86bedd14bc4f9d469dfc6456e6f3c5d9077e81a5fedfba7"}, - {file = "yarl-1.9.3-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8535e111a064f3bdd94c0ed443105934d6f005adad68dd13ce50a488a0ad1bf3"}, - {file = "yarl-1.9.3-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0d155a092bf0ebf4a9f6f3b7a650dc5d9a5bbb585ef83a52ed36ba46f55cc39d"}, - {file = "yarl-1.9.3-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:778df71c8d0c8c9f1b378624b26431ca80041660d7be7c3f724b2c7a6e65d0d6"}, - {file = "yarl-1.9.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b9f9cafaf031c34d95c1528c16b2fa07b710e6056b3c4e2e34e9317072da5d1a"}, - {file = "yarl-1.9.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:ca6b66f69e30f6e180d52f14d91ac854b8119553b524e0e28d5291a724f0f423"}, - {file = "yarl-1.9.3-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:e0e7e83f31e23c5d00ff618045ddc5e916f9e613d33c5a5823bc0b0a0feb522f"}, - {file = "yarl-1.9.3-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:af52725c7c39b0ee655befbbab5b9a1b209e01bb39128dce0db226a10014aacc"}, - {file = "yarl-1.9.3-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:0ab5baaea8450f4a3e241ef17e3d129b2143e38a685036b075976b9c415ea3eb"}, - {file = "yarl-1.9.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:6d350388ba1129bc867c6af1cd17da2b197dff0d2801036d2d7d83c2d771a682"}, - {file = "yarl-1.9.3-cp39-cp39-win32.whl", hash = "sha256:e2a16ef5fa2382af83bef4a18c1b3bcb4284c4732906aa69422cf09df9c59f1f"}, - {file = "yarl-1.9.3-cp39-cp39-win_amd64.whl", hash = "sha256:d92d897cb4b4bf915fbeb5e604c7911021a8456f0964f3b8ebbe7f9188b9eabb"}, - {file = "yarl-1.9.3-py3-none-any.whl", hash = "sha256:271d63396460b6607b588555ea27a1a02b717ca2e3f2cf53bdde4013d7790929"}, - {file = "yarl-1.9.3.tar.gz", hash = "sha256:4a14907b597ec55740f63e52d7fee0e9ee09d5b9d57a4f399a7423268e457b57"}, + {file = "yarl-1.9.4-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:a8c1df72eb746f4136fe9a2e72b0c9dc1da1cbd23b5372f94b5820ff8ae30e0e"}, + {file = "yarl-1.9.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:a3a6ed1d525bfb91b3fc9b690c5a21bb52de28c018530ad85093cc488bee2dd2"}, + {file = "yarl-1.9.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c38c9ddb6103ceae4e4498f9c08fac9b590c5c71b0370f98714768e22ac6fa66"}, + {file = "yarl-1.9.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d9e09c9d74f4566e905a0b8fa668c58109f7624db96a2171f21747abc7524234"}, + {file = "yarl-1.9.4-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:b8477c1ee4bd47c57d49621a062121c3023609f7a13b8a46953eb6c9716ca392"}, + {file = "yarl-1.9.4-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d5ff2c858f5f6a42c2a8e751100f237c5e869cbde669a724f2062d4c4ef93551"}, + {file = "yarl-1.9.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:357495293086c5b6d34ca9616a43d329317feab7917518bc97a08f9e55648455"}, + {file = "yarl-1.9.4-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:54525ae423d7b7a8ee81ba189f131054defdb122cde31ff17477951464c1691c"}, + {file = "yarl-1.9.4-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:801e9264d19643548651b9db361ce3287176671fb0117f96b5ac0ee1c3530d53"}, + {file = "yarl-1.9.4-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:e516dc8baf7b380e6c1c26792610230f37147bb754d6426462ab115a02944385"}, + {file = "yarl-1.9.4-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:7d5aaac37d19b2904bb9dfe12cdb08c8443e7ba7d2852894ad448d4b8f442863"}, + {file = "yarl-1.9.4-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:54beabb809ffcacbd9d28ac57b0db46e42a6e341a030293fb3185c409e626b8b"}, + {file = "yarl-1.9.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:bac8d525a8dbc2a1507ec731d2867025d11ceadcb4dd421423a5d42c56818541"}, + {file = "yarl-1.9.4-cp310-cp310-win32.whl", hash = "sha256:7855426dfbddac81896b6e533ebefc0af2f132d4a47340cee6d22cac7190022d"}, + {file = "yarl-1.9.4-cp310-cp310-win_amd64.whl", hash = "sha256:848cd2a1df56ddbffeb375535fb62c9d1645dde33ca4d51341378b3f5954429b"}, + {file = "yarl-1.9.4-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:35a2b9396879ce32754bd457d31a51ff0a9d426fd9e0e3c33394bf4b9036b099"}, + {file = "yarl-1.9.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:4c7d56b293cc071e82532f70adcbd8b61909eec973ae9d2d1f9b233f3d943f2c"}, + {file = "yarl-1.9.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:d8a1c6c0be645c745a081c192e747c5de06e944a0d21245f4cf7c05e457c36e0"}, + {file = "yarl-1.9.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4b3c1ffe10069f655ea2d731808e76e0f452fc6c749bea04781daf18e6039525"}, + {file = "yarl-1.9.4-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:549d19c84c55d11687ddbd47eeb348a89df9cb30e1993f1b128f4685cd0ebbf8"}, + {file = "yarl-1.9.4-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a7409f968456111140c1c95301cadf071bd30a81cbd7ab829169fb9e3d72eae9"}, + {file = "yarl-1.9.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e23a6d84d9d1738dbc6e38167776107e63307dfc8ad108e580548d1f2c587f42"}, + {file = "yarl-1.9.4-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d8b889777de69897406c9fb0b76cdf2fd0f31267861ae7501d93003d55f54fbe"}, + {file = "yarl-1.9.4-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:03caa9507d3d3c83bca08650678e25364e1843b484f19986a527630ca376ecce"}, + {file = "yarl-1.9.4-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4e9035df8d0880b2f1c7f5031f33f69e071dfe72ee9310cfc76f7b605958ceb9"}, + {file = "yarl-1.9.4-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:c0ec0ed476f77db9fb29bca17f0a8fcc7bc97ad4c6c1d8959c507decb22e8572"}, + {file = "yarl-1.9.4-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:ee04010f26d5102399bd17f8df8bc38dc7ccd7701dc77f4a68c5b8d733406958"}, + {file = "yarl-1.9.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:49a180c2e0743d5d6e0b4d1a9e5f633c62eca3f8a86ba5dd3c471060e352ca98"}, + {file = "yarl-1.9.4-cp311-cp311-win32.whl", hash = "sha256:81eb57278deb6098a5b62e88ad8281b2ba09f2f1147c4767522353eaa6260b31"}, + {file = "yarl-1.9.4-cp311-cp311-win_amd64.whl", hash = "sha256:d1d2532b340b692880261c15aee4dc94dd22ca5d61b9db9a8a361953d36410b1"}, + {file = "yarl-1.9.4-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:0d2454f0aef65ea81037759be5ca9947539667eecebca092733b2eb43c965a81"}, + {file = "yarl-1.9.4-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:44d8ffbb9c06e5a7f529f38f53eda23e50d1ed33c6c869e01481d3fafa6b8142"}, + {file = "yarl-1.9.4-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:aaaea1e536f98754a6e5c56091baa1b6ce2f2700cc4a00b0d49eca8dea471074"}, + {file = "yarl-1.9.4-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3777ce5536d17989c91696db1d459574e9a9bd37660ea7ee4d3344579bb6f129"}, + {file = "yarl-1.9.4-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9fc5fc1eeb029757349ad26bbc5880557389a03fa6ada41703db5e068881e5f2"}, + {file = "yarl-1.9.4-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ea65804b5dc88dacd4a40279af0cdadcfe74b3e5b4c897aa0d81cf86927fee78"}, + {file = "yarl-1.9.4-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:aa102d6d280a5455ad6a0f9e6d769989638718e938a6a0a2ff3f4a7ff8c62cc4"}, + {file = "yarl-1.9.4-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:09efe4615ada057ba2d30df871d2f668af661e971dfeedf0c159927d48bbeff0"}, + {file = "yarl-1.9.4-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:008d3e808d03ef28542372d01057fd09168419cdc8f848efe2804f894ae03e51"}, + {file = "yarl-1.9.4-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:6f5cb257bc2ec58f437da2b37a8cd48f666db96d47b8a3115c29f316313654ff"}, + {file = "yarl-1.9.4-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:992f18e0ea248ee03b5a6e8b3b4738850ae7dbb172cc41c966462801cbf62cf7"}, + {file = "yarl-1.9.4-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:0e9d124c191d5b881060a9e5060627694c3bdd1fe24c5eecc8d5d7d0eb6faabc"}, + {file = "yarl-1.9.4-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:3986b6f41ad22988e53d5778f91855dc0399b043fc8946d4f2e68af22ee9ff10"}, + {file = "yarl-1.9.4-cp312-cp312-win32.whl", hash = "sha256:4b21516d181cd77ebd06ce160ef8cc2a5e9ad35fb1c5930882baff5ac865eee7"}, + {file = "yarl-1.9.4-cp312-cp312-win_amd64.whl", hash = "sha256:a9bd00dc3bc395a662900f33f74feb3e757429e545d831eef5bb280252631984"}, + {file = "yarl-1.9.4-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:63b20738b5aac74e239622d2fe30df4fca4942a86e31bf47a81a0e94c14df94f"}, + {file = "yarl-1.9.4-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d7d7f7de27b8944f1fee2c26a88b4dabc2409d2fea7a9ed3df79b67277644e17"}, + {file = "yarl-1.9.4-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c74018551e31269d56fab81a728f683667e7c28c04e807ba08f8c9e3bba32f14"}, + {file = "yarl-1.9.4-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ca06675212f94e7a610e85ca36948bb8fc023e458dd6c63ef71abfd482481aa5"}, + {file = "yarl-1.9.4-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5aef935237d60a51a62b86249839b51345f47564208c6ee615ed2a40878dccdd"}, + {file = "yarl-1.9.4-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2b134fd795e2322b7684155b7855cc99409d10b2e408056db2b93b51a52accc7"}, + {file = "yarl-1.9.4-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:d25039a474c4c72a5ad4b52495056f843a7ff07b632c1b92ea9043a3d9950f6e"}, + {file = "yarl-1.9.4-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:f7d6b36dd2e029b6bcb8a13cf19664c7b8e19ab3a58e0fefbb5b8461447ed5ec"}, + {file = "yarl-1.9.4-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:957b4774373cf6f709359e5c8c4a0af9f6d7875db657adb0feaf8d6cb3c3964c"}, + {file = "yarl-1.9.4-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:d7eeb6d22331e2fd42fce928a81c697c9ee2d51400bd1a28803965883e13cead"}, + {file = "yarl-1.9.4-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:6a962e04b8f91f8c4e5917e518d17958e3bdee71fd1d8b88cdce74dd0ebbf434"}, + {file = "yarl-1.9.4-cp37-cp37m-win32.whl", hash = "sha256:f3bc6af6e2b8f92eced34ef6a96ffb248e863af20ef4fde9448cc8c9b858b749"}, + {file = "yarl-1.9.4-cp37-cp37m-win_amd64.whl", hash = "sha256:ad4d7a90a92e528aadf4965d685c17dacff3df282db1121136c382dc0b6014d2"}, + {file = "yarl-1.9.4-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:ec61d826d80fc293ed46c9dd26995921e3a82146feacd952ef0757236fc137be"}, + {file = "yarl-1.9.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:8be9e837ea9113676e5754b43b940b50cce76d9ed7d2461df1af39a8ee674d9f"}, + {file = "yarl-1.9.4-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:bef596fdaa8f26e3d66af846bbe77057237cb6e8efff8cd7cc8dff9a62278bbf"}, + {file = "yarl-1.9.4-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2d47552b6e52c3319fede1b60b3de120fe83bde9b7bddad11a69fb0af7db32f1"}, + {file = "yarl-1.9.4-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:84fc30f71689d7fc9168b92788abc977dc8cefa806909565fc2951d02f6b7d57"}, + {file = "yarl-1.9.4-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4aa9741085f635934f3a2583e16fcf62ba835719a8b2b28fb2917bb0537c1dfa"}, + {file = "yarl-1.9.4-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:206a55215e6d05dbc6c98ce598a59e6fbd0c493e2de4ea6cc2f4934d5a18d130"}, + {file = "yarl-1.9.4-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:07574b007ee20e5c375a8fe4a0789fad26db905f9813be0f9fef5a68080de559"}, + {file = "yarl-1.9.4-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:5a2e2433eb9344a163aced6a5f6c9222c0786e5a9e9cac2c89f0b28433f56e23"}, + {file = "yarl-1.9.4-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:6ad6d10ed9b67a382b45f29ea028f92d25bc0bc1daf6c5b801b90b5aa70fb9ec"}, + {file = "yarl-1.9.4-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:6fe79f998a4052d79e1c30eeb7d6c1c1056ad33300f682465e1b4e9b5a188b78"}, + {file = "yarl-1.9.4-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:a825ec844298c791fd28ed14ed1bffc56a98d15b8c58a20e0e08c1f5f2bea1be"}, + {file = "yarl-1.9.4-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:8619d6915b3b0b34420cf9b2bb6d81ef59d984cb0fde7544e9ece32b4b3043c3"}, + {file = "yarl-1.9.4-cp38-cp38-win32.whl", hash = "sha256:686a0c2f85f83463272ddffd4deb5e591c98aac1897d65e92319f729c320eece"}, + {file = "yarl-1.9.4-cp38-cp38-win_amd64.whl", hash = "sha256:a00862fb23195b6b8322f7d781b0dc1d82cb3bcac346d1e38689370cc1cc398b"}, + {file = "yarl-1.9.4-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:604f31d97fa493083ea21bd9b92c419012531c4e17ea6da0f65cacdcf5d0bd27"}, + {file = "yarl-1.9.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:8a854227cf581330ffa2c4824d96e52ee621dd571078a252c25e3a3b3d94a1b1"}, + {file = "yarl-1.9.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ba6f52cbc7809cd8d74604cce9c14868306ae4aa0282016b641c661f981a6e91"}, + {file = "yarl-1.9.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a6327976c7c2f4ee6816eff196e25385ccc02cb81427952414a64811037bbc8b"}, + {file = "yarl-1.9.4-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8397a3817d7dcdd14bb266283cd1d6fc7264a48c186b986f32e86d86d35fbac5"}, + {file = "yarl-1.9.4-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e0381b4ce23ff92f8170080c97678040fc5b08da85e9e292292aba67fdac6c34"}, + {file = "yarl-1.9.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:23d32a2594cb5d565d358a92e151315d1b2268bc10f4610d098f96b147370136"}, + {file = "yarl-1.9.4-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ddb2a5c08a4eaaba605340fdee8fc08e406c56617566d9643ad8bf6852778fc7"}, + {file = "yarl-1.9.4-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:26a1dc6285e03f3cc9e839a2da83bcbf31dcb0d004c72d0730e755b33466c30e"}, + {file = "yarl-1.9.4-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:18580f672e44ce1238b82f7fb87d727c4a131f3a9d33a5e0e82b793362bf18b4"}, + {file = "yarl-1.9.4-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:29e0f83f37610f173eb7e7b5562dd71467993495e568e708d99e9d1944f561ec"}, + {file = "yarl-1.9.4-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:1f23e4fe1e8794f74b6027d7cf19dc25f8b63af1483d91d595d4a07eca1fb26c"}, + {file = "yarl-1.9.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:db8e58b9d79200c76956cefd14d5c90af54416ff5353c5bfd7cbe58818e26ef0"}, + {file = "yarl-1.9.4-cp39-cp39-win32.whl", hash = "sha256:c7224cab95645c7ab53791022ae77a4509472613e839dab722a72abe5a684575"}, + {file = "yarl-1.9.4-cp39-cp39-win_amd64.whl", hash = "sha256:824d6c50492add5da9374875ce72db7a0733b29c2394890aef23d533106e2b15"}, + {file = "yarl-1.9.4-py3-none-any.whl", hash = "sha256:928cecb0ef9d5a7946eb6ff58417ad2fe9375762382f1bf5c55e61645f2c43ad"}, + {file = "yarl-1.9.4.tar.gz", hash = "sha256:566db86717cf8080b99b58b083b773a908ae40f06681e87e589a976faf8246bf"}, ] [package.dependencies] @@ -7771,4 +7876,4 @@ reference = "tsinghua" [metadata] lock-version = "2.0" python-versions = "^3.11" -content-hash = "19950a5300f8a4425e3e3c9a096fc3782cb544e02152e92ac1bc09d1d9b5274a" +content-hash = "3d6e2ccd4d1c1943d9bda901601872db7eb0564858a258372ad7ccf02c978378" diff --git a/pyproject.toml b/pyproject.toml index 58b9991f6..c25951966 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -78,7 +78,7 @@ geoip2 = "4.7.0" ipip-ipdb = "1.6.1" pywinrm = "0.4.3" python-nmap = "0.7.1" -django = "4.1.10" +django = "4.1.13" django-bootstrap3 = "23.4" django-filter = "23.2" django-formtools = "2.4.1" @@ -97,7 +97,7 @@ drf-yasg = "1.21.7" coreapi = "2.3.3" coreschema = "0.0.4" openapi-codec = "1.3.2" -pillow = "10.0.0" +pillow = "10.0.1" pytz = "2023.3" django-proxy = "1.2.2" python-daemon = "3.0.1" @@ -127,7 +127,7 @@ python-redis-lock = "4.0.0" pyopenssl = "23.2.0" redis = "4.6.0" pymongo = "4.4.1" -pyfreerdp = "0.0.1" +pyfreerdp = "0.0.2" ipython = "8.14.0" forgerypy3 = "0.3.1" django-debug-toolbar = "4.1.0" @@ -143,9 +143,10 @@ fido2 = "^1.1.2" ua-parser = "^0.18.0" user-agents = "^2.2.0" django-cors-headers = "^4.3.0" -mistune = "0.8.4" +mistune = "2.0.3" openai = "^1.3.7" xlsxwriter = "^3.1.9" +exchangelib = "^5.1.0" [tool.poetry.group.xpack.dependencies] @@ -154,8 +155,7 @@ azure-mgmt-subscription = "3.1.1" azure-identity = "1.13.0" azure-mgmt-compute = "30.0.0" azure-mgmt-network = "23.1.0" -google-cloud-compute = "1.13.0" -grpcio = "1.56.2" +google-cloud-compute = "1.15.0" alibabacloud-dysmsapi20170525 = "2.0.24" python-novaclient = "18.3.0" python-keystoneclient = "5.1.0" diff --git a/utils/generate_fake_data/generate.py b/utils/generate_fake_data/generate.py index 0931cca8f..cda1bbaed 100644 --- a/utils/generate_fake_data/generate.py +++ b/utils/generate_fake_data/generate.py @@ -17,6 +17,7 @@ from resources.assets import AssetsGenerator, NodesGenerator, PlatformGenerator from resources.users import UserGroupGenerator, UserGenerator from resources.perms import AssetPermissionGenerator from resources.terminal import CommandGenerator, SessionGenerator +from resources.accounts import AccountGenerator resource_generator_mapper = { 'asset': AssetsGenerator, @@ -27,6 +28,7 @@ resource_generator_mapper = { 'asset_permission': AssetPermissionGenerator, 'command': CommandGenerator, 'session': SessionGenerator, + 'account': AccountGenerator, 'all': None # 'stat': StatGenerator } @@ -45,6 +47,7 @@ def main(): parser.add_argument('-o', '--org', type=str, default='') args = parser.parse_args() resource, count, batch_size, org_id = args.resource, args.count, args.batch_size, args.org + resource = resource.lower().rstrip('s') generator_cls = [] if resource == 'all': diff --git a/utils/generate_fake_data/resources/accounts.py b/utils/generate_fake_data/resources/accounts.py new file mode 100644 index 000000000..9b0fc75d5 --- /dev/null +++ b/utils/generate_fake_data/resources/accounts.py @@ -0,0 +1,32 @@ +import random + +import forgery_py + +from accounts.models import Account +from assets.models import Asset +from .base import FakeDataGenerator + + +class AccountGenerator(FakeDataGenerator): + resource = 'account' + + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + self.assets = list(list(Asset.objects.all()[:5000])) + + def do_generate(self, batch, batch_size): + accounts = [] + for i in batch: + asset = random.choice(self.assets) + name = forgery_py.internet.user_name(True) + '-' + str(i) + d = { + 'username': name, + 'name': name, + 'asset': asset, + 'secret': name, + 'secret_type': 'password', + 'is_active': True, + 'privileged': False, + } + accounts.append(Account(**d)) + Account.objects.bulk_create(accounts, ignore_conflicts=True) diff --git a/utils/generate_fake_data/resources/assets.py b/utils/generate_fake_data/resources/assets.py index 517122c9b..a8e3ce239 100644 --- a/utils/generate_fake_data/resources/assets.py +++ b/utils/generate_fake_data/resources/assets.py @@ -48,7 +48,7 @@ class AssetsGenerator(FakeDataGenerator): def pre_generate(self): self.node_ids = list(Node.objects.all().values_list('id', flat=True)) - self.platform_ids = list(Platform.objects.all().values_list('id', flat=True)) + self.platform_ids = list(Platform.objects.filter(category='host').values_list('id', flat=True)) def set_assets_nodes(self, assets): for asset in assets: @@ -72,6 +72,17 @@ class AssetsGenerator(FakeDataGenerator): assets.append(Asset(**data)) creates = Asset.objects.bulk_create(assets, ignore_conflicts=True) self.set_assets_nodes(creates) + self.set_asset_platform(creates) + + @staticmethod + def set_asset_platform(assets): + protocol = random.choice(['ssh', 'rdp', 'telnet', 'vnc']) + protocols = [] + + for asset in assets: + port = 22 if protocol == 'ssh' else 3389 + protocols.append(Protocol(asset=asset, name=protocol, port=port)) + Protocol.objects.bulk_create(protocols, ignore_conflicts=True) def after_generate(self): pass diff --git a/utils/generate_fake_data/resources/base.py b/utils/generate_fake_data/resources/base.py index 39942d5f1..dd02c65f7 100644 --- a/utils/generate_fake_data/resources/base.py +++ b/utils/generate_fake_data/resources/base.py @@ -41,7 +41,7 @@ class FakeDataGenerator: start = time.time() self.do_generate(batch, self.batch_size) end = time.time() - using = end - start + using = round(end - start, 3) from_size = created created += len(batch) print('Generate %s: %s-%s [%s]' % (self.resource, from_size, created, using)) diff --git a/utils/generate_fake_data/resources/users.py b/utils/generate_fake_data/resources/users.py index c05e0793b..5ed159b53 100644 --- a/utils/generate_fake_data/resources/users.py +++ b/utils/generate_fake_data/resources/users.py @@ -1,9 +1,11 @@ -from random import choice, sample +from random import sample + import forgery_py -from .base import FakeDataGenerator - +from orgs.utils import current_org +from rbac.models import RoleBinding, Role from users.models import * +from .base import FakeDataGenerator class UserGroupGenerator(FakeDataGenerator): @@ -47,3 +49,12 @@ class UserGenerator(FakeDataGenerator): users.append(u) users = User.objects.bulk_create(users, ignore_conflicts=True) self.set_groups(users) + self.set_to_org(users) + + def set_to_org(self, users): + bindings = [] + role = Role.objects.get(name='OrgUser') + for u in users: + b = RoleBinding(user=u, role=role, org_id=current_org.id, scope='org') + bindings.append(b) + RoleBinding.objects.bulk_create(bindings, ignore_conflicts=True)