get rid of six
This commit is contained in:
@@ -1,7 +1,6 @@
|
||||
import weakref
|
||||
|
||||
from bson import DBRef
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine.common import _import_class
|
||||
from mongoengine.errors import DoesNotExist, MultipleObjectsReturned
|
||||
@@ -360,7 +359,7 @@ class StrictDict(object):
|
||||
_classes = {}
|
||||
|
||||
def __init__(self, **kwargs):
|
||||
for k, v in iteritems(kwargs):
|
||||
for k, v in kwargs.items():
|
||||
setattr(self, k, v)
|
||||
|
||||
def __getitem__(self, key):
|
||||
@@ -408,7 +407,7 @@ class StrictDict(object):
|
||||
return (key for key in self.__slots__ if hasattr(self, key))
|
||||
|
||||
def __len__(self):
|
||||
return len(list(iteritems(self)))
|
||||
return len(list(self.items()))
|
||||
|
||||
def __eq__(self, other):
|
||||
return list(self.items()) == list(other.items())
|
||||
|
||||
@@ -5,8 +5,6 @@ from functools import partial
|
||||
|
||||
from bson import DBRef, ObjectId, SON, json_util
|
||||
import pymongo
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine import signals
|
||||
from mongoengine.base.common import get_document
|
||||
@@ -110,7 +108,7 @@ class BaseDocument(object):
|
||||
# Assign default values to the instance.
|
||||
# We set default values only for fields loaded from DB. See
|
||||
# https://github.com/mongoengine/mongoengine/issues/399 for more info.
|
||||
for key, field in iteritems(self._fields):
|
||||
for key, field in self._fields.items():
|
||||
if self._db_field_map.get(key, key) in __only_fields:
|
||||
continue
|
||||
value = getattr(self, key, None)
|
||||
@@ -122,14 +120,14 @@ class BaseDocument(object):
|
||||
# Set passed values after initialisation
|
||||
if self._dynamic:
|
||||
dynamic_data = {}
|
||||
for key, value in iteritems(values):
|
||||
for key, value in values.items():
|
||||
if key in self._fields or key == "_id":
|
||||
setattr(self, key, value)
|
||||
else:
|
||||
dynamic_data[key] = value
|
||||
else:
|
||||
FileField = _import_class("FileField")
|
||||
for key, value in iteritems(values):
|
||||
for key, value in values.items():
|
||||
key = self._reverse_db_field_map.get(key, key)
|
||||
if key in self._fields or key in ("id", "pk", "_cls"):
|
||||
if __auto_convert and value is not None:
|
||||
@@ -145,7 +143,7 @@ class BaseDocument(object):
|
||||
|
||||
if self._dynamic:
|
||||
self._dynamic_lock = False
|
||||
for key, value in iteritems(dynamic_data):
|
||||
for key, value in dynamic_data.items():
|
||||
setattr(self, key, value)
|
||||
|
||||
# Flag initialised
|
||||
@@ -575,7 +573,7 @@ class BaseDocument(object):
|
||||
if not hasattr(data, "items"):
|
||||
iterator = enumerate(data)
|
||||
else:
|
||||
iterator = iteritems(data)
|
||||
iterator = data.items()
|
||||
|
||||
for index_or_key, value in iterator:
|
||||
item_key = "%s%s." % (base_key, index_or_key)
|
||||
@@ -741,7 +739,7 @@ class BaseDocument(object):
|
||||
# Convert SON to a data dict, making sure each key is a string and
|
||||
# corresponds to the right db field.
|
||||
data = {}
|
||||
for key, value in iteritems(son):
|
||||
for key, value in son.items():
|
||||
key = str(key)
|
||||
key = cls._db_field_map.get(key, key)
|
||||
data[key] = value
|
||||
@@ -756,7 +754,7 @@ class BaseDocument(object):
|
||||
if not _auto_dereference:
|
||||
fields = copy.deepcopy(fields)
|
||||
|
||||
for field_name, field in iteritems(fields):
|
||||
for field_name, field in fields.items():
|
||||
field._auto_dereference = _auto_dereference
|
||||
if field.db_field in data:
|
||||
value = data[field.db_field]
|
||||
@@ -781,7 +779,7 @@ class BaseDocument(object):
|
||||
|
||||
# In STRICT documents, remove any keys that aren't in cls._fields
|
||||
if cls.STRICT:
|
||||
data = {k: v for k, v in iteritems(data) if k in cls._fields}
|
||||
data = {k: v for k, v in data.items() if k in cls._fields}
|
||||
|
||||
obj = cls(
|
||||
__auto_convert=False, _created=created, __only_fields=only_fields, **data
|
||||
|
||||
@@ -4,7 +4,6 @@ import weakref
|
||||
|
||||
from bson import DBRef, ObjectId, SON
|
||||
import pymongo
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine.base.common import UPDATE_OPERATORS
|
||||
from mongoengine.base.datastructures import BaseDict, BaseList, EmbeddedDocumentList
|
||||
@@ -418,11 +417,11 @@ class ComplexBaseField(BaseField):
|
||||
if self.field:
|
||||
value_dict = {
|
||||
key: self.field._to_mongo_safe_call(item, use_db_field, fields)
|
||||
for key, item in iteritems(value)
|
||||
for key, item in value.items()
|
||||
}
|
||||
else:
|
||||
value_dict = {}
|
||||
for k, v in iteritems(value):
|
||||
for k, v in value.items():
|
||||
if isinstance(v, Document):
|
||||
# We need the id from the saved object to create the DBRef
|
||||
if v.pk is None:
|
||||
@@ -461,8 +460,8 @@ class ComplexBaseField(BaseField):
|
||||
"""If field is provided ensure the value is valid."""
|
||||
errors = {}
|
||||
if self.field:
|
||||
if hasattr(value, "iteritems") or hasattr(value, "items"):
|
||||
sequence = iteritems(value)
|
||||
if hasattr(value, "items"):
|
||||
sequence = value.items()
|
||||
else:
|
||||
sequence = enumerate(value)
|
||||
for k, v in sequence:
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
import itertools
|
||||
import warnings
|
||||
|
||||
from six import iteritems, itervalues
|
||||
|
||||
from mongoengine.base.common import _document_registry
|
||||
from mongoengine.base.fields import BaseField, ComplexBaseField, ObjectIdField
|
||||
from mongoengine.common import _import_class
|
||||
@@ -68,7 +66,7 @@ class DocumentMetaclass(type):
|
||||
# Standard object mixin - merge in any Fields
|
||||
if not hasattr(base, "_meta"):
|
||||
base_fields = {}
|
||||
for attr_name, attr_value in iteritems(base.__dict__):
|
||||
for attr_name, attr_value in base.__dict__.items():
|
||||
if not isinstance(attr_value, BaseField):
|
||||
continue
|
||||
attr_value.name = attr_name
|
||||
@@ -80,7 +78,7 @@ class DocumentMetaclass(type):
|
||||
|
||||
# Discover any document fields
|
||||
field_names = {}
|
||||
for attr_name, attr_value in iteritems(attrs):
|
||||
for attr_name, attr_value in attrs.items():
|
||||
if not isinstance(attr_value, BaseField):
|
||||
continue
|
||||
attr_value.name = attr_name
|
||||
@@ -110,9 +108,7 @@ class DocumentMetaclass(type):
|
||||
|
||||
attrs["_fields_ordered"] = tuple(
|
||||
i[1]
|
||||
for i in sorted(
|
||||
(v.creation_counter, v.name) for v in itervalues(doc_fields)
|
||||
)
|
||||
for i in sorted((v.creation_counter, v.name) for v in doc_fields.values())
|
||||
)
|
||||
|
||||
#
|
||||
@@ -190,7 +186,7 @@ class DocumentMetaclass(type):
|
||||
# f.__dict__.update({"im_self": getattr(f, "__self__")})
|
||||
|
||||
# Handle delete rules
|
||||
for field in itervalues(new_class._fields):
|
||||
for field in new_class._fields.values():
|
||||
f = field
|
||||
if f.owner_document is None:
|
||||
f.owner_document = new_class
|
||||
@@ -399,7 +395,7 @@ class TopLevelDocumentMetaclass(DocumentMetaclass):
|
||||
new_class.objects = QuerySetManager()
|
||||
|
||||
# Validate the fields and set primary key if needed
|
||||
for field_name, field in iteritems(new_class._fields):
|
||||
for field_name, field in new_class._fields.items():
|
||||
if field.primary_key:
|
||||
# Ensure only one primary key is set
|
||||
current_pk = new_class._meta.get("id_field")
|
||||
@@ -476,7 +472,7 @@ class MetaDict(dict):
|
||||
_merge_options = ("indexes",)
|
||||
|
||||
def merge(self, new_options):
|
||||
for k, v in iteritems(new_options):
|
||||
for k, v in new_options.items():
|
||||
if k in self._merge_options:
|
||||
self[k] = self.get(k, []) + v
|
||||
else:
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
from contextlib import contextmanager
|
||||
|
||||
from pymongo.write_concern import WriteConcern
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine.common import _import_class
|
||||
from mongoengine.connection import DEFAULT_CONNECTION_NAME, get_db
|
||||
@@ -123,7 +122,7 @@ class no_dereference(object):
|
||||
|
||||
self.deref_fields = [
|
||||
k
|
||||
for k, v in iteritems(self.cls._fields)
|
||||
for k, v in self.cls._fields.items()
|
||||
if isinstance(v, (ReferenceField, GenericReferenceField, ComplexBaseField))
|
||||
]
|
||||
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
from bson import DBRef, SON
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine.base import (
|
||||
BaseDict,
|
||||
@@ -79,7 +77,7 @@ class DeReference(object):
|
||||
|
||||
def _get_items_from_dict(items):
|
||||
new_items = {}
|
||||
for k, v in iteritems(items):
|
||||
for k, v in items.items():
|
||||
value = v
|
||||
if isinstance(v, list):
|
||||
value = _get_items_from_list(v)
|
||||
@@ -120,7 +118,7 @@ class DeReference(object):
|
||||
depth += 1
|
||||
for item in iterator:
|
||||
if isinstance(item, (Document, EmbeddedDocument)):
|
||||
for field_name, field in iteritems(item._fields):
|
||||
for field_name, field in item._fields.items():
|
||||
v = item._data.get(field_name, None)
|
||||
if isinstance(v, LazyReference):
|
||||
# LazyReference inherits DBRef but should not be dereferenced here !
|
||||
@@ -136,7 +134,7 @@ class DeReference(object):
|
||||
getattr(field, "field", None), "document_type", None
|
||||
)
|
||||
references = self._find_references(v, depth)
|
||||
for key, refs in iteritems(references):
|
||||
for key, refs in references.items():
|
||||
if isinstance(
|
||||
field_cls, (Document, TopLevelDocumentMetaclass)
|
||||
):
|
||||
@@ -153,7 +151,7 @@ class DeReference(object):
|
||||
)
|
||||
elif isinstance(item, (dict, list, tuple)) and depth - 1 <= self.max_depth:
|
||||
references = self._find_references(item, depth - 1)
|
||||
for key, refs in iteritems(references):
|
||||
for key, refs in references.items():
|
||||
reference_map.setdefault(key, set()).update(refs)
|
||||
|
||||
return reference_map
|
||||
@@ -162,7 +160,7 @@ class DeReference(object):
|
||||
"""Fetch all references and convert to their document objects
|
||||
"""
|
||||
object_map = {}
|
||||
for collection, dbrefs in iteritems(self.reference_map):
|
||||
for collection, dbrefs in self.reference_map.items():
|
||||
|
||||
# we use getattr instead of hasattr because hasattr swallows any exception under python2
|
||||
# so it could hide nasty things without raising exceptions (cfr bug #1688))
|
||||
@@ -174,7 +172,7 @@ class DeReference(object):
|
||||
dbref for dbref in dbrefs if (col_name, dbref) not in object_map
|
||||
]
|
||||
references = collection.objects.in_bulk(refs)
|
||||
for key, doc in iteritems(references):
|
||||
for key, doc in references.items():
|
||||
object_map[(col_name, key)] = doc
|
||||
else: # Generic reference: use the refs data to convert to document
|
||||
if isinstance(doc_type, (ListField, DictField, MapField)):
|
||||
@@ -250,7 +248,7 @@ class DeReference(object):
|
||||
data = []
|
||||
else:
|
||||
is_list = False
|
||||
iterator = iteritems(items)
|
||||
iterator = items.items()
|
||||
data = {}
|
||||
|
||||
depth += 1
|
||||
|
||||
@@ -4,8 +4,6 @@ import warnings
|
||||
from bson.dbref import DBRef
|
||||
import pymongo
|
||||
from pymongo.read_preferences import ReadPreference
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine import signals
|
||||
from mongoengine.base import (
|
||||
@@ -55,7 +53,7 @@ class InvalidCollectionError(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class EmbeddedDocument(six.with_metaclass(DocumentMetaclass, BaseDocument)):
|
||||
class EmbeddedDocument(BaseDocument, metaclass=DocumentMetaclass):
|
||||
"""A :class:`~mongoengine.Document` that isn't stored in its own
|
||||
collection. :class:`~mongoengine.EmbeddedDocument`\ s should be used as
|
||||
fields on :class:`~mongoengine.Document`\ s through the
|
||||
@@ -103,7 +101,7 @@ class EmbeddedDocument(six.with_metaclass(DocumentMetaclass, BaseDocument)):
|
||||
return data
|
||||
|
||||
|
||||
class Document(six.with_metaclass(TopLevelDocumentMetaclass, BaseDocument)):
|
||||
class Document(BaseDocument, metaclass=TopLevelDocumentMetaclass):
|
||||
"""The base class used for defining the structure and properties of
|
||||
collections of documents stored in MongoDB. Inherit from this class, and
|
||||
add fields as class attributes to define a document's structure.
|
||||
@@ -632,7 +630,7 @@ class Document(six.with_metaclass(TopLevelDocumentMetaclass, BaseDocument)):
|
||||
|
||||
# Delete FileFields separately
|
||||
FileField = _import_class("FileField")
|
||||
for name, field in iteritems(self._fields):
|
||||
for name, field in self._fields.items():
|
||||
if isinstance(field, FileField):
|
||||
getattr(self, name).delete()
|
||||
|
||||
@@ -1029,7 +1027,7 @@ class Document(six.with_metaclass(TopLevelDocumentMetaclass, BaseDocument)):
|
||||
return {"missing": missing, "extra": extra}
|
||||
|
||||
|
||||
class DynamicDocument(six.with_metaclass(TopLevelDocumentMetaclass, Document)):
|
||||
class DynamicDocument(Document, metaclass=TopLevelDocumentMetaclass):
|
||||
"""A Dynamic Document class allowing flexible, expandable and uncontrolled
|
||||
schemas. As a :class:`~mongoengine.Document` subclass, acts in the same
|
||||
way as an ordinary document but has expanded style properties. Any data
|
||||
@@ -1060,7 +1058,7 @@ class DynamicDocument(six.with_metaclass(TopLevelDocumentMetaclass, Document)):
|
||||
super(DynamicDocument, self).__delattr__(*args, **kwargs)
|
||||
|
||||
|
||||
class DynamicEmbeddedDocument(six.with_metaclass(DocumentMetaclass, EmbeddedDocument)):
|
||||
class DynamicEmbeddedDocument(EmbeddedDocument, metaclass=DocumentMetaclass):
|
||||
"""A Dynamic Embedded Document class allowing flexible, expandable and
|
||||
uncontrolled schemas. See :class:`~mongoengine.DynamicDocument` for more
|
||||
information about dynamic documents.
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
from collections import defaultdict
|
||||
|
||||
from six import iteritems
|
||||
|
||||
__all__ = (
|
||||
"NotRegistered",
|
||||
@@ -125,7 +124,7 @@ class ValidationError(AssertionError):
|
||||
def build_dict(source):
|
||||
errors_dict = {}
|
||||
if isinstance(source, dict):
|
||||
for field_name, error in iteritems(source):
|
||||
for field_name, error in source.items():
|
||||
errors_dict[field_name] = build_dict(error)
|
||||
elif isinstance(source, ValidationError) and source.errors:
|
||||
return build_dict(source.errors)
|
||||
@@ -146,15 +145,15 @@ class ValidationError(AssertionError):
|
||||
if isinstance(value, list):
|
||||
value = " ".join([generate_key(k) for k in value])
|
||||
elif isinstance(value, dict):
|
||||
value = " ".join([generate_key(v, k) for k, v in iteritems(value)])
|
||||
value = " ".join([generate_key(v, k) for k, v in value.items()])
|
||||
|
||||
results = "%s.%s" % (prefix, value) if prefix else value
|
||||
return results
|
||||
|
||||
error_dict = defaultdict(list)
|
||||
for k, v in iteritems(self.to_dict()):
|
||||
for k, v in self.to_dict().items():
|
||||
error_dict[generate_key(v)].append(k)
|
||||
return " ".join(["%s: %s" % (k, v) for k, v in iteritems(error_dict)])
|
||||
return " ".join(["%s: %s" % (k, v) for k, v in error_dict.items()])
|
||||
|
||||
|
||||
class DeprecatedError(Exception):
|
||||
|
||||
@@ -13,8 +13,6 @@ from bson.int64 import Int64
|
||||
import gridfs
|
||||
import pymongo
|
||||
from pymongo import ReturnDocument
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
try:
|
||||
import dateutil
|
||||
@@ -205,7 +203,7 @@ class EmailField(StringField):
|
||||
)
|
||||
|
||||
UTF8_USER_REGEX = LazyRegexCompiler(
|
||||
six.u(
|
||||
(
|
||||
# RFC 6531 Section 3.3 extends `atext` (used by dot-atom) to
|
||||
# include `UTF8-non-ascii`.
|
||||
r"(^[-!#$%&'*+/=?^_`{}|~0-9A-Z\u0080-\U0010FFFF]+(\.[-!#$%&'*+/=?^_`{}|~0-9A-Z\u0080-\U0010FFFF]+)*\Z"
|
||||
@@ -387,7 +385,7 @@ class FloatField(BaseField):
|
||||
return value
|
||||
|
||||
def validate(self, value):
|
||||
if isinstance(value, six.integer_types):
|
||||
if isinstance(value, int):
|
||||
try:
|
||||
value = float(value)
|
||||
except OverflowError:
|
||||
@@ -868,12 +866,12 @@ class DynamicField(BaseField):
|
||||
value = {k: v for k, v in enumerate(value)}
|
||||
|
||||
data = {}
|
||||
for k, v in iteritems(value):
|
||||
for k, v in value.items():
|
||||
data[k] = self.to_mongo(v, use_db_field, fields)
|
||||
|
||||
value = data
|
||||
if is_list: # Convert back to a list
|
||||
value = [v for k, v in sorted(iteritems(data), key=itemgetter(0))]
|
||||
value = [v for k, v in sorted(data.items(), key=itemgetter(0))]
|
||||
return value
|
||||
|
||||
def to_python(self, value):
|
||||
@@ -1607,10 +1605,10 @@ class BinaryField(BaseField):
|
||||
return Binary(value)
|
||||
|
||||
def validate(self, value):
|
||||
if not isinstance(value, (six.binary_type, Binary)):
|
||||
if not isinstance(value, (bytes, Binary)):
|
||||
self.error(
|
||||
"BinaryField only accepts instances of "
|
||||
"(%s, %s, Binary)" % (six.binary_type.__name__, Binary.__name__)
|
||||
"(%s, %s, Binary)" % (bytes.__name__, Binary.__name__)
|
||||
)
|
||||
|
||||
if self.max_bytes is not None and len(value) > self.max_bytes:
|
||||
@@ -1829,7 +1827,7 @@ class FileField(BaseField):
|
||||
key = self.name
|
||||
if (
|
||||
hasattr(value, "read") and not isinstance(value, GridFSProxy)
|
||||
) or isinstance(value, (six.binary_type, str)):
|
||||
) or isinstance(value, (bytes, str)):
|
||||
# using "FileField() = file/string" notation
|
||||
grid_file = instance._data.get(self.name)
|
||||
# If a file already exists, delete it
|
||||
|
||||
@@ -9,8 +9,6 @@ import pymongo
|
||||
import pymongo.errors
|
||||
from pymongo.collection import ReturnDocument
|
||||
from pymongo.common import validate_read_preference
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine import signals
|
||||
from mongoengine.base import get_document
|
||||
@@ -252,12 +250,12 @@ class BaseQuerySet(object):
|
||||
queryset = queryset.filter(*q_objs, **query)
|
||||
|
||||
try:
|
||||
result = six.next(queryset)
|
||||
result = next(queryset)
|
||||
except StopIteration:
|
||||
msg = "%s matching query does not exist." % queryset._document._class_name
|
||||
raise queryset._document.DoesNotExist(msg)
|
||||
try:
|
||||
six.next(queryset)
|
||||
next(queryset)
|
||||
except StopIteration:
|
||||
return result
|
||||
|
||||
@@ -1567,7 +1565,7 @@ class BaseQuerySet(object):
|
||||
if self._limit == 0 or self._none:
|
||||
raise StopIteration
|
||||
|
||||
raw_doc = six.next(self._cursor)
|
||||
raw_doc = next(self._cursor)
|
||||
|
||||
if self._as_pymongo:
|
||||
return raw_doc
|
||||
@@ -1812,13 +1810,13 @@ class BaseQuerySet(object):
|
||||
}
|
||||
"""
|
||||
total, data, types = self.exec_js(freq_func, field)
|
||||
values = {types.get(k): int(v) for k, v in iteritems(data)}
|
||||
values = {types.get(k): int(v) for k, v in data.items()}
|
||||
|
||||
if normalize:
|
||||
values = {k: float(v) / total for k, v in values.items()}
|
||||
|
||||
frequencies = {}
|
||||
for k, v in iteritems(values):
|
||||
for k, v in values.items():
|
||||
if isinstance(k, float):
|
||||
if int(k) == k:
|
||||
k = int(k)
|
||||
|
||||
@@ -1,5 +1,3 @@
|
||||
import six
|
||||
|
||||
from mongoengine.errors import OperationError
|
||||
from mongoengine.queryset.base import (
|
||||
BaseQuerySet,
|
||||
@@ -127,8 +125,8 @@ class QuerySet(BaseQuerySet):
|
||||
# Pull in ITER_CHUNK_SIZE docs from the database and store them in
|
||||
# the result cache.
|
||||
try:
|
||||
for _ in six.moves.range(ITER_CHUNK_SIZE):
|
||||
self._result_cache.append(six.next(self))
|
||||
for _ in range(ITER_CHUNK_SIZE):
|
||||
self._result_cache.append(next(self))
|
||||
except StopIteration:
|
||||
# Getting this exception means there are no more docs in the
|
||||
# db cursor. Set _has_more to False so that we can use that
|
||||
@@ -180,9 +178,9 @@ class QuerySetNoCache(BaseQuerySet):
|
||||
return ".. queryset mid-iteration .."
|
||||
|
||||
data = []
|
||||
for _ in six.moves.range(REPR_OUTPUT_SIZE + 1):
|
||||
for _ in range(REPR_OUTPUT_SIZE + 1):
|
||||
try:
|
||||
data.append(six.next(self))
|
||||
data.append(next(self))
|
||||
except StopIteration:
|
||||
break
|
||||
|
||||
|
||||
@@ -3,8 +3,6 @@ from collections import defaultdict
|
||||
from bson import ObjectId, SON
|
||||
from bson.dbref import DBRef
|
||||
import pymongo
|
||||
import six
|
||||
from six import iteritems
|
||||
|
||||
from mongoengine.base import UPDATE_OPERATORS
|
||||
from mongoengine.common import _import_class
|
||||
@@ -180,7 +178,7 @@ def query(_doc_cls=None, **kwargs):
|
||||
"$near" in value_dict or "$nearSphere" in value_dict
|
||||
):
|
||||
value_son = SON()
|
||||
for k, v in iteritems(value_dict):
|
||||
for k, v in value_dict.items():
|
||||
if k == "$maxDistance" or k == "$minDistance":
|
||||
continue
|
||||
value_son[k] = v
|
||||
|
||||
Reference in New Issue
Block a user