You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
177 lines
4.8 KiB
177 lines
4.8 KiB
import datetime
|
|
from pprint import pprint
|
|
|
|
import natsort
|
|
import pydash as _;
|
|
from django.core import validators
|
|
from django.core.exceptions import ObjectDoesNotExist
|
|
from django.core.files.storage import FileSystemStorage
|
|
from django.shortcuts import _get_queryset
|
|
from django.utils import timezone
|
|
|
|
_.map = _.map_;
|
|
_.filter = _.filter_
|
|
import random
|
|
import string
|
|
|
|
|
|
def take(coll, n):
|
|
chunk = coll[0:n]
|
|
del coll[0:n]
|
|
return chunk
|
|
|
|
|
|
def take_random(coll, n):
|
|
if n == 0:
|
|
return []
|
|
|
|
chunk = _.sample(coll, n)
|
|
|
|
for item in chunk:
|
|
coll.remove(item)
|
|
|
|
return chunk
|
|
|
|
|
|
def take_one_random(coll):
|
|
if len(coll) == 0:
|
|
return None
|
|
|
|
return coll.pop(_.random(0, len(coll) - 1))
|
|
|
|
|
|
def random_phone():
|
|
return '+7' + str(_.sample((917, 964, 965, 987, 912, 935))) + str(_.random(1000000, 9999999))
|
|
|
|
|
|
def random_date():
|
|
return timezone.utc.localize(timezone.datetime(_.random(2012, 2018), _.random(1, 12), _.random(1, 28)))
|
|
|
|
|
|
def random_amount():
|
|
return random.random() * random.choice((100, 1000, 10000))
|
|
|
|
|
|
def get_or_none(klass, *args, **kwargs):
|
|
queryset = _get_queryset(klass)
|
|
|
|
try:
|
|
return queryset.get(*args, **kwargs)
|
|
except queryset.model.DoesNotExist:
|
|
return None
|
|
|
|
|
|
def get_related_or_none(obj, attr):
|
|
try:
|
|
rel = getattr(obj, attr)
|
|
except ObjectDoesNotExist:
|
|
rel = None
|
|
|
|
return rel
|
|
|
|
|
|
def has_related(obj, attr):
|
|
try:
|
|
return bool(getattr(obj, attr))
|
|
except ObjectDoesNotExist:
|
|
return False
|
|
|
|
|
|
def get_attr_or_none(klass, *args, attr=None, **kwargs):
|
|
object = get_or_none(klass, *args, **kwargs)
|
|
|
|
if object and attr and isinstance(attr, str):
|
|
return getattr(object, attr, None)
|
|
|
|
|
|
def model_fields(model, width=200):
|
|
fields = natsort.natsorted(model._meta.get_fields(), key=lambda f: f.name)
|
|
|
|
pprint([(
|
|
f.name,
|
|
'Relation? %s' % f.is_relation,
|
|
'Null? %s' % getattr(f, 'null', None),
|
|
'Blank? %s' % getattr(f, 'blank', None),
|
|
) for f in fields], width=width)
|
|
|
|
|
|
def lorem(words=None, sentences=5):
|
|
vocab = _.split((
|
|
'a ac adipiscing amet ante arcu at auctor augue bibendum commodo condimentum consectetur consequat convallis curabitur'
|
|
'cursus diam dictum dignissim dolor donec duis efficitur eget eleifend elit enim erat et eu ex facilisis faucibus feugiat'
|
|
'finibus gravida iaculis id imperdiet in integer ipsum lacinia lacus laoreet lectus leo libero ligula lobortis lorem'
|
|
'luctus maecenas mauris metus mi mollis morbi nam nec neque nisi non nulla nullam nunc odio orci ornare pellentesque'
|
|
'pharetra phasellus porta porttitor posuere pretium proin pulvinar purus quam quis rhoncus rutrum sapien sed sem semper'
|
|
'sit sollicitudin tempor tempus tincidunt tortor turpis ullamcorper ultricies ut varius vehicula vel velit vestibulum'
|
|
'vitae viverra volutpat vulputate'
|
|
), ' ')
|
|
|
|
return _.join(_.times(lambda i_: _.capitalize(_.join(_.sample(vocab, words or _.random(5, 30)), ' ')), sentences),
|
|
'. ')
|
|
|
|
|
|
def decap(s):
|
|
if not isinstance(s, str):
|
|
raise TypeError('String expected')
|
|
|
|
return s[0].lower() + s[1:] if len(s) > 0 else s
|
|
|
|
|
|
def random_ident(length=8):
|
|
return ''.join(
|
|
[random.choice(string.ascii_lowercase)] +
|
|
_.times(lambda x_: random.choice(string.ascii_letters + string.digits), length - 1)
|
|
)
|
|
|
|
|
|
def validate_phone(text):
|
|
text = text.replace(' ', '').replace('-', '')
|
|
|
|
validate = validators.RegexValidator(
|
|
regex=r'^((\+7|8)(\(\d{3}\)|(\d{3}))\d{7})$',
|
|
message='Неверный номер телефона. Формат: +71112223344',
|
|
)
|
|
|
|
validate(text)
|
|
|
|
|
|
def to_local_datetime(obj):
|
|
if not isinstance(obj, datetime.date):
|
|
raise TypeError('Date expected')
|
|
|
|
if not isinstance(obj, datetime.datetime):
|
|
obj = datetime.datetime.combine(obj, datetime.time.min)
|
|
|
|
if not getattr(obj, 'tzinfo', None):
|
|
obj = timezone.utc.localize(obj)
|
|
|
|
return obj
|
|
|
|
|
|
def morph(number, words):
|
|
CHOICES = (2, 0, 1, 1, 1, 2)
|
|
|
|
if 4 < number % 100 < 20:
|
|
choice = 2
|
|
else:
|
|
choice = CHOICES[number % 10 if number % 10 < 5 else 5]
|
|
|
|
return words[choice]
|
|
|
|
|
|
# # Example:
|
|
#
|
|
# words = ['яблоко', 'яблока', 'яблок']
|
|
#
|
|
# for i in range(0, 30):
|
|
# print(i, morph(i, words))
|
|
|
|
|
|
class ASCIIFileSystemStorage(FileSystemStorage):
|
|
def get_valid_name(self, name):
|
|
symbols = (u"абвгдеёжзийклмнопрстуфхцчшщъыьэюяАБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ",
|
|
u"abvgdeejzijklmnoprstufhzcss_y_euaABVGDEEJZIJKLMNOPRSTUFHZCSS_Y_EUA")
|
|
|
|
tr = {ord(a): ord(b) for a, b in zip(*symbols)}
|
|
name = name.translate(tr)
|
|
return super().get_valid_name(name)
|
|
|