def handle(self, *args, **options): """Загрузка email ов для формирования xlsx для загрузки в спам лист для рассылки""" fname = 'clients_emails' link = 'https://223-223.ru/media/%s.json' % fname r = requests.get(link) rows = json.loads(r.text) folder = 'spamcha' make_folder(folder) xls_file = '%s.xlsx' % fname dest = full_path(os.path.join(folder, xls_file)) book = xlsxwriter.Workbook(dest) sheet = book.add_worksheet('Лист 1') row_number = 0 titles = ( 'client_id', 'client_name', 'dest', 'name', ) for i, title in enumerate(titles): sheet.write(row_number, i, title) for row in rows: row_number += 1 for i, field in enumerate(row): sheet.write(row_number, i, field) book.close()
def create_orders_xml(dest: str = 'orders.xml', scheme_version: str = '2.03'): """Создание xml с заказами :param dest: выходной файл (абсолютный путь) :param scheme_version: версия схемы xml """ now = datetime.datetime.today() content = '<?xml version="1.0" encoding="UTF-8"?>\n' #content += '\n<КоммерческаяИнформация ВерсияСхемы="%s" ДатаФормирования="%s">\n' % (scheme_version, now.strftime('%Y-%m-%d %H:%M:%S')) by = 50 tab = ' ' query = Orders.objects.select_related('shopper').all() total_records = query.aggregate(Count('id'))['id__count'] pages = int(total_records / by) + 1 for i in range(pages): orders = query[i * by:i * by + by] for order in orders: content += fill_document(order) + '\n' if not dest.startswith('/'): dest = full_path(dest) #content += '\n</КоммерческаяИнформация>' with open(dest, 'w+', encoding='utf-8') as f: f.write(content)
def handle(self, *args, **options): html_path = 'mammoth' html_files = ListDir(html_path) result = [] for html_file in html_files: if not html_file.endswith('.html'): continue cur_html = os.path.join(html_path, html_file) content = '' with open_file(cur_html, 'r') as f: content = f.read() tree = lxml_html.fromstring(content) tables = tree.xpath('//table') for table in tables: ths = table.xpath('.//thead/tr/th/p') if ths: th = ths[0] if '№ п/п' in th.text: result += accumulate_result( table, html_file.replace('.html', '')) dest = full_path('joint_table_from_html.xlsx') book = xlsxwriter.Workbook(dest) sheet = book.add_worksheet('Лист 1') row_number = 0 sheet.write(row_number, 0, 'Файл') sheet.write(row_number, 1, '№ п/п') sheet.write(row_number, 2, '№ стыка') sheet.write(row_number, 3, 'Клеймо') sheet.write(row_number, 4, 'Материал') sheet.write(row_number, 5, 'Диаметр,мм') sheet.write(row_number, 6, 'Толщина,мм') sheet.write(row_number, 7, 'Дата') sheet.write(row_number, 8, 'Тип сварки') sheet.write(row_number, 9, 'Вид соединения') sheet.write(row_number, 10, 'Соединение') for item in result: row_number += 1 size = item.get('size', 'x').split('/')[0] sizes = size.split('x') diameter = sizes[0] side_thickness = sizes[1] sheet.write(row_number, 0, item.get('file')) sheet.write(row_number, 1, item.get('n')) sheet.write(row_number, 2, item.get('number')) sheet.write(row_number, 3, item.get('stigma')) sheet.write(row_number, 4, item.get('material')) sheet.write(row_number, 5, diameter) sheet.write(row_number, 6, side_thickness) sheet.write(row_number, 7, item.get('date')) sheet.write(row_number, 8, item.get('welding_type')) sheet.write(row_number, 9, item.get('conn_view')) sheet.write(row_number, 10, ' - '.join(item.get('elements', []))) book.close()
def handle(self, *args, **options): #source_folder = 'spinner360/light_bee' source_folder = 'spinner360/light_bee_s' #source_folder = 'spinner360/test360' #drop_half_files(source_folder) items = ListDir(source_folder) z = 0 for item in items: if not item.endswith('.jpg'): continue src = os.path.join(source_folder, item) if not isForD(src) == 'file': continue z += 1 digit = z if z < 100: digit = '0%s' % z if z < 10: digit = '00%s' % z dest = os.path.join(source_folder, 'frame_%s.jpg' % digit) os.rename(full_path(src), full_path(dest))
def handle(self, *args, **options): path = 'price/Price_{}.xml' # 28.01.2021 now = datetime.date.today() path = path.format(now.strftime('%d.%m.%Y')) if check_path(path): logger.info('[ERROR]: file %s not exists' % path) return parser = xml.sax.make_parser() handler = XMLHandler() parser.setContentHandler(handler) parser.parse(full_path(path)) logger.info('[UPDATED]: %s, %s' % (len(handler.updated), handler.updated))
def ReturnFile(request, link): """Возвращаем файл""" if not link.startswith('/'): link = '/%s' % link # Заебал этот фавикон, думаю, # одна проверка на него не напряжет if link == '/favicon.ico': path = '%s/img/favicon.ico' % settings.STATIC_ROOT.rstrip('/') with open(path, 'rb') as f: response = HttpResponse(f.read(), content_type='image/x-icon') response['Content-Length'] = file_size(path) response['Content-Disposition'] = 'inline; filename=%s' % (path, ) return response elif link == '/sitemap.xml': context = {} sitemap = SitemapXML() context['managers'] = sitemap.get_menu_managers() template = 'sitemap_index.html' return render(request, template, context, content_type='text/xml') elif link.startswith('/sitemap/'): context = {} sitemap = SitemapXML() context['blocks'] = sitemap.get_manager(link) template = 'sitemap_xml.html' return render(request, template, context, content_type='text/xml') search_files = Files.objects.filter(link=link, is_active=True) # Если мультидомен, # то ищем в том числе специфический для домена файл, # но если нету, то возвращаем без домена if settings.IS_DOMAINS: domain = get_domain(request) search_file_with_domain = search_files.filter( domain=domain['pk']).values_list('id', flat=True) if search_file_with_domain: search_files = search_files.filter(domain=domain['pk']) search_file = search_files.first() if search_file: path = '%s%s' % (search_file.get_folder(), search_file.path) if not check_path(path): with open(full_path(path), 'rb') as f: response = HttpResponse(f.read(), content_type=search_file.mime) response['Content-Length'] = file_size(path) response['Content-Disposition'] = 'inline; filename=%s' % (path, ) return response else: # файл не найден - лучше 404 отдать raise Http404 return redirect("/")
def link_callback(uri, rel): """ Convert HTML URIs to absolute system paths so xhtml2pdf can access those resources """ if uri.startswith(settings.MEDIA_ROOT): path = full_path(uri) elif uri.startswith(settings.STATIC_ROOT): path = os.path.join(settings.MEDIA_ROOT, uri.replace(settings.MEDIA_ROOT, '')) else: return uri if not os.path.isfile(path): raise Exception('media URI not found %s' % path) return path
def drop_media(self): """Удаление папки экземпляра модели""" if not self.id: return folder = self.get_folder() drop_folder(folder) parent_folder = os.path.split(folder.rstrip('/'))[0] if check_path(parent_folder): return pass_items = ('.DS_Store', ) parent_folder_fp = full_path(parent_folder) items_in_folder = [ item for item in os.listdir(parent_folder_fp) if not item in pass_items ] if not items_in_folder: os.rmdir(parent_folder_fp)
def save(self, *args, **kwargs): cid = kill_quotes(self.cid, 'int') if cid.startswith('7'): cid = '8%s' % (cid[1:], ) self.cid = cid super(FSUser, self).save(*args, **kwargs) if not self.is_active or not self.user or not self.passwd or not self.context or not self.cid: self.drop_extension() return extension = """ <include> <user id="{}"> <params> <param name="password" value="{}"/> </params> <variables> <variable name="toll_allow" value="domestic,international,local"/> <variable name="accountcode" value="{}"/> <variable name="user_context" value="{}"/> <variable name="effective_caller_id_name" value="{}"/> <variable name="effective_caller_id_number" value="{}"/> <variable name="outbound_caller_id_name" value="{}"/> <variable name="outbound_caller_id_number" value="{}"/> <variable name="callgroup" value="{}"/> </variables> </user> </include>""".format(self.user.username, self.passwd, self.user.username, self.context, self.user.username, self.user.username, self.cid, self.cid, self.callgroup) fname = full_path('%s/fs_user_%s.xml' % (self.FOLDER, self.id)) if check_path(fname): make_folder(self.FOLDER) with open(fname, 'w+') as f: f.write(extension) FreeswitchBackend(settings.FREESWITCH_URI).reloadxml()
def save(self, *args, **kwargs): super(Redirects, self).save(*args, **kwargs) if not self.is_active: self.drop_extension() return extension = """ <extension name="redirect_{}"> <condition field="destination_number" expression="^([78]{})$"> <action application="set" data="effective_caller_id_number={}"/> <action application="set" data="effective_caller_id_name={}"/> <action application="set" data="ringback={}"/> <action application="export" data="hold_music={}"/> <action application="set" data="ignore_early_media=true" /> <action application="set" data="record_file_name={}"/> <action application="set" data="media_bug_answer_req=true"/> <action application="export" data="execute_on_answer=record_session {}"/> <action application="set" data="sip_h_Diversion="{}" <sip: {}@{}>;reason=unconditional;"/> <action application="bridge" data="sofia/gateway/{}/{}"/> </condition> </extension>""".format(self.phone, kill_quotes(self.phone[1:], 'int'), '${caller_id_number}', '${caller_id_number}', '${us-ring}', '$${hold_music}', '$${base_dir}/${context}/${strftime(%Y-%m-%d)}/${destination_number}_${uuid}.wav', '${record_file_name}', '${diversion_phone}', '${diversion_phone}', '${diversion_domain}', self.gw, kill_quotes(self.dest, 'int')) fname = full_path('%s/redirect_%s.xml' % (self.FOLDER, self.id)) if check_path(fname): make_folder(self.FOLDER) with open(fname, 'w+') as f: f.write(extension) FreeswitchBackend(settings.FREESWITCH_URI).reloadxml()
def get_text_msg(self, msg_type: str = 'plain', **kwargs): """Сформировать текстовое сообщение для отправки :param msg_type: html или plain :param kwargs: доп параметры client_id, email - для редиректов images_with_watermarks - вотермарчить изображения watermark_rotate - поворот вотермарки """ if not self.msg: return if not msg_type in ('plain', 'html'): msg_type = 'plain' # Доп. параметры dest_email = kwargs.get('email') client_id = kwargs.get('client_id') client_name = kwargs.get('client_name') or '' images_with_watermarks = kwargs.get('images_with_watermarks') or '' if msg_type == 'html': html_part = MIMEMultipart(_subtype='related') search_images = REGA_IMG.findall(self.msg) images = [] for i, img in enumerate(search_images): cid = 'inline_imga_%s' % i self.msg = self.msg.replace(img, 'cid:%s' % cid) if images_with_watermarks and img.startswith( '/media/') and img.endswith('.png'): source, img_name = os.path.split(img) source = source.replace('/media/', '') # Заливаем случайным изображением, # со случайным поворотом mark = 'demo_mark.png' color = ( random.randrange(0, 255), random.randrange(0, 255), random.randrange(0, 255), ) demo_mark = blank_image('300x300', color) demo_mark.save(full_path(mark)) rotate = kwargs.get('watermark_rotate', 0) watermark_image(img_name, source, size='', mark=mark, position='tile', opacity=0.02, folder='resized', rotate=rotate) img = os.path.join(source, 'resized', 'watermark_%s' % img_name) img_path = full_path(img) with open(img_path, 'rb') as f: img_data = f.read() html_img = MIMEImage(img_data) # angle brackets are important html_img.add_header('Content-Id', '<%s>' % cid) html_img.add_header('Content-Disposition', 'inline') images.append(html_img) #html_part.attach(html_img) search_hrefs = REGA_A.findall(self.msg) if search_hrefs: hrefs = set(search_hrefs) for href in hrefs: # Хардкод, чтобы базу не долбить if '/srdr/goto/' in href: old_href = href.split('?')[0] new_href = '%s?email=%s&client_id=%s' % ( old_href, dest_email, client_id) self.msg = self.msg.replace(href, new_href) html_text = MIMEText(self.msg, msg_type, 'utf-8') html_part.attach(html_text) for image in images: html_part.attach(image) msg = html_part else: msg = MIMEText(self.msg, msg_type, 'utf-8') subject = '%s. %s' % (self.name, client_name) msg['Subject'] = Header(subject, 'utf-8') #msg['From'] = account.email #msg['To'] = ', '.join(recipients) # Не надо - а то как спам распознавать будет (проверить) #if self.reply_to: # msg.add_header('reply-to', self.reply_to) return msg
def edit_conclusion_file(request, action: str, row_id: int = None, *args, **kwargs): """Создание/редактирование файлов для заключений на заявку""" mh_vars = conclusion_files_vars.copy() mh = create_model_helper(mh_vars, request, CUR_APP, action) mh.select_related_add('joint_conclusion') mh.select_related_add('joint_conclusion__welding_joint') row = mh.get_row(row_id) context = mh.context if mh.error: return redirect('%s?error=not_found' % (mh.root_url, )) if request.method == 'GET': if action == 'create': mh.breadcrumbs_add({ 'link': mh.url_create, 'name': '%s %s' % (mh.action_create, mh.rp_singular_obj), }) elif action == 'edit' and row: mh.breadcrumbs_add({ 'link': mh.url_edit, 'name': '%s %s' % (mh.action_edit, mh.rp_singular_obj), }) elif action == 'drop' and row: if mh.permissions['drop']: if mh.row.joint_conclusion.welding_joint.state == 3: context['error'] = 'Нельзя изменить принятую заявку' else: row.delete() mh.row = None context['success'] = '%s удалено' % (mh.singular_obj, ) else: context['error'] = 'Недостаточно прав' elif action == 'download' and row: # Возвращаем файл по имени path = '%s%s' % (row.file.get_folder(), row.file.path) if not check_path(path): with open(full_path(path), 'rb') as f: response = HttpResponse(f.read(), content_type=row.file.mime) response['Content-Disposition'] = row.file.content_disposition_for_cyrillic_name(row.file.name) return response elif request.method == 'POST': pass_fields = () mh.post_vars(pass_fields=pass_fields) if action == 'create' or (action == 'edit' and row): if action == 'create': if mh.permissions['create']: mh.row = mh.model() mh.save_row() context['success'] = 'Данные успешно записаны' else: context['error'] = 'Недостаточно прав' if action == 'edit': if mh.permissions['edit']: if mh.row.welding_joint.state == 3: context['error'] = 'Нельзя изменить принятую заявку' else: mh.save_row() context['success'] = 'Данные успешно записаны' else: context['error'] = 'Недостаточно прав' elif action == 'img' and request.FILES: mh.uploads() if mh.row: context['row'] = object_fields(mh.row) if mh.row.file: context['row']['file'] = object_fields(mh.row.file) context['redirect'] = mh.get_url_edit() if request.is_ajax() or action == 'img': return JsonResponse(context, safe=False) template = '%sedit.html' % (mh.template_prefix, ) return render(request, template, context)
def edit_conclusion(request, action: str, row_id: int = None, *args, **kwargs): """Создание/редактирование заключений (актов)""" mh_vars = conclusions_vars.copy() mh = create_model_helper(mh_vars, request, CUR_APP, action) mh.select_related_add('welding_joint') mh.select_related_add('welding_joint__joint') mh.select_related_add('vik_controller') mh.select_related_add('vik_director') mh.select_related_add('rk_defectoscopist1') mh.select_related_add('rk_defectoscopist2') mh.select_related_add('rk_defectoscopist3') mh.select_related_add('pvk_director') mh.select_related_add('pvk_defectoscopist') mh.select_related_add('uzk_defectoscopist1') mh.select_related_add('uzk_defectoscopist2') mh.select_related_add('uzk_defectoscopist3') mh.select_related_add('uzk_operator') # pdf mh.select_related_add('welding_joint__joint__line') mh.select_related_add('welding_joint__joint__line__titul') mh.select_related_add('welding_joint__joint__line__titul__subject') mh.select_related_add('welding_joint__joint__line__titul__subject__company') row = mh.get_row(row_id) context = mh.context # Права на файлы к заключению context['files_permissions'] = get_user_permissions(request.user, JointConclusionFile) context['welding_joint_state_permissions'] = get_user_permissions(request.user, WeldingJointState) if mh.error: return redirect('%s?error=not_found' % (mh.root_url, )) if request.method == 'GET': # --------------------------------------------------- # Вытаскиваем заявку, по которой создается заключение # --------------------------------------------------- welding_joint_str = request.GET.get('welding_joint') if welding_joint_str and not mh.row: welding_joint = WeldingJoint.objects.select_related('joint').filter(pk=welding_joint_str).first() if not welding_joint: return redirect('%s?error=not_found' % (mh.root_url, )) welding_joint.join_type_from = welding_joint.joint.get_join_type_from_display() welding_joint.join_type_to = welding_joint.joint.get_join_type_to_display() welding_joint.material = welding_joint.joint.get_material_display() welding_joint.welding_conn_view = welding_joint.joint.get_welding_conn_view_display() context['welding_joint'] = welding_joint_fields(welding_joint) context['welders'] = {} if welding_joint.joint: context['welders'] = welding_joint.joint.get_welders() context['welding_type'] = '?' for item in WELDING_TYPE_DESCRIPTIONS: if welding_joint.joint.welding_type == item[0]: context['welding_type'] = item[1] break if action in ('create', 'edit'): context['welding_type_descriptions'] = WELDING_TYPE_DESCRIPTIONS context['conclusion_states'] = CONCLUSION_STATES context['pvk_control_choices'] = JointConclusion.pvk_control_choices context['state_choices'] = WELDING_JOINT_STATES if action in ('edit', 'pdf_vik', 'pdf_rk', 'pdf_pvk', 'pdf_uzk'): context['welding_type'] = '%s и %s' % ( WELDING_TYPE_DESCRIPTIONS[0][1], WELDING_TYPE_DESCRIPTIONS[1][1], ) for item in WELDING_TYPE_DESCRIPTIONS: if row.welding_joint.joint.welding_type == item[0]: context['welding_type'] = item[1] break context['rk_frames'] = row.rkframes_set.all().order_by('position') # Номера заключений context.update(row.get_conclusion_numbers(row.welding_joint)) if action == 'create': mh.breadcrumbs_add({ 'link': mh.url_create, 'name': '%s %s' % (mh.action_create, mh.rp_singular_obj), }) elif action == 'edit' and row: mh.breadcrumbs_add({ 'link': mh.url_edit, 'name': '%s %s' % (mh.action_edit, mh.rp_singular_obj), }) if row.welding_joint: context['welding_joint'] = welding_joint_fields(row.welding_joint) context['all_conclusions'] = JointConclusion.objects.filter(welding_joint=row.welding_joint).values_list('id', flat=True).order_by('repair') context['files'] = row.get_files() context['welders'] = {} if row.welding_joint.joint: context['welders'] = row.welding_joint.joint.get_welders() elif action == 'drop' and row: if mh.permissions['drop']: row.delete() mh.row = None context['success'] = '%s удален' % (mh.singular_obj, ) else: context['error'] = 'Недостаточно прав' elif action in ('pdf_vik', 'pdf_rk', 'pdf_pvk', 'pdf_uzk') and row: pdf_type = action.replace('pdf_', '') context.update({ 'row': row, 'logo': full_path('misc/logo_standard.png'), 'pdf_type': pdf_type, 'joint': row.welding_joint.joint, 'today': datetime.datetime.today(), }) context['welders'] = {} if row.welding_joint and row.welding_joint.joint: context['welders'] = row.welding_joint.joint.get_welders() template = 'pdf/conclusion_%s_form.html' % pdf_type return render_pdf( request, template = template, context = context, download = False, fname = 'conclusion_%s_%s' % ( pdf_type, row.welding_joint.joint.id, ) ) elif request.method == 'POST': # Общий статус ставится в save по заключениям pass_fields = ('state', 'repair') mh.post_vars(pass_fields=pass_fields) if action == 'create' or (action == 'edit' and row): # --------------------------------- # Без заявки стыка нельзя сохранить # --------------------------------- welding_joint = None welding_joint_str = mh.row_vars.get('welding_joint') if welding_joint_str: welding_joint = WeldingJoint.objects.filter(pk=welding_joint_str).first() if not welding_joint: context['error'] = 'Выберите заявку на стык' return JsonResponse(context) else: analog = JointConclusion.objects.filter(welding_joint=welding_joint).order_by('-repair').first() if not mh.row and analog: context['error'] = 'Вы создаете дубликат, переадресовываем на заключение...' link = reverse( '%s:%s' % (CUR_APP, mh_vars['edit_urla']), kwargs={'action': 'edit', 'row_id': analog.id} ) context['redirect_on_error'] = link return JsonResponse(context) if action == 'create': if mh.permissions['create']: mh.row = mh.model() mh.save_row() if mh.error: context['error'] = mh.error else: context['success'] = 'Данные успешно записаны' fill_rk_frames(request, mh.row) else: context['error'] = 'Недостаточно прав' if action == 'edit': if mh.permissions['edit']: # ----------------------- # Изменить заявку на стык # не даем в заключении # ----------------------- mh.save_row(set_fields={'welding_joint': mh.row.welding_joint}) if mh.error: context['error'] = mh.error else: context['success'] = 'Данные успешно записаны' fill_rk_frames(request, mh.row) else: context['error'] = 'Недостаточно прав' elif action == 'file' and request.FILES: # Принятую заявку не редактируем if mh.row.welding_joint.state == 3: context['error'] = 'Нельзя изменить принятую заявку' else: # Загрузка файла в JointConclusionFile mh.files_add('path') new_file = Files.objects.create( desc = mh.row.welding_joint.request_number, name = request.FILES['path'].name, ) mh.uploads(row=new_file) if new_file.path: joint_file = JointConclusionFile.objects.create( joint_conclusion=mh.row, file=new_file, ) new_file.update_mimetype() context['success'] = 'Файл загружен' context['file'] = { 'id': joint_file.id, 'path': new_file.path, 'name': new_file.name, 'mime': new_file.mime, 'folder': new_file.get_folder(), } else: new_file.delete() context['error'] = 'Не удалось загрузить файл' if not mh.error and mh.row: if not 'row' in context: context['row'] = object_fields(mh.row) context['redirect'] = mh.get_url_edit() if request.is_ajax() or action in ('img', 'file'): return JsonResponse(context, safe=False) template = '%sedit.html' % (mh.template_prefix, ) return render(request, template, context)
def handle(self, *args, **options): """Работа с демонами""" if options.get('logs'): cmd = '/bin/journalctl -u %s -b --no-pager' % (options['logs'], ) logger.info(cmd) os.system(cmd) return if options.get('watch'): cmd = '/bin/journalctl -u %s -f' % (options['watch'], ) logger.info(cmd) os.system(cmd) return if options.get('restart'): cmd = '/bin/systemctl restart %s' % (options['restart'], ) logger.info(cmd) os.system(cmd) return if options.get('stop'): cmd = '/bin/systemctl stop %s' % (options['stop'], ) logger.info(cmd) os.system(cmd) return if options.get('status'): cmd = '/bin/systemctl status %s' % (options['status'], ) logger.info(cmd) os.system(cmd) return daemons_folder = '/etc/systemd/system/' # --------------------------- # Убиваем все, что не активно # --------------------------- folder_items = os.listdir(daemons_folder) logger.info(folder_items) for item in folder_items: script = os.path.join(daemons_folder, item) if isForD(script) == 'file' and item.endswith( '.service') and item.startswith('daemon_'): cmd = '/bin/systemctl disable %s' % (item, ) logger.info(cmd) os.system(cmd) cmd = '/bin/systemctl stop %s' % (item, ) logger.info(cmd) os.system(cmd) logger.info('dropping %s' % (item, )) os.unlink(script) cmd = '/bin/systemctl daemon-reload' logger.info(cmd) os.system(cmd) # ------------------------------ # Перезапускаем все, что активно # ------------------------------ folder = 'demonology' folder_items = ListDir(folder) logger.info(folder_items) for item in folder_items: script = os.path.join(folder, item) if isForD(script) == 'file' and item.endswith('.service'): fname = os.path.join(daemons_folder, item) if os.path.exists(fname): logger.info('%s exists, dropping' % (item, )) os.unlink(fname) cmd = '/bin/cp %s %s' % (full_path(script), daemons_folder) logger.info(cmd) os.system(cmd) cmd = '/bin/systemctl daemon-reload' logger.info(cmd) os.system(cmd) cmd = '/bin/systemctl enable %s' % (item, ) logger.info(cmd) os.system(cmd) cmd = '/bin/systemctl restart %s' % (item, ) logger.info(cmd) os.system(cmd)
def titul_docx2excel(html_path: str): """Запихиваем все в эксельку :param html_path: путь до папки с html файлами """ dest_fname = 'result.xlsx' html_files = ListDir(html_path) result = [] rows = [] for html_file in html_files: cur_html = os.path.join(html_path, html_file) if not html_file.endswith('.html'): drop_file(cur_html) continue content = '' with open_file(cur_html, 'r') as f: content = f.read() # Поиск проблем if search_problem(content, ''): print(cur_html) else: drop_file(cur_html) tree = lxml_html.fromstring(content) tables = tree.xpath('//table') line_str = None # Поиск линии for table in tables: search_line = table.xpath('.//tr/td') for item in search_line: par = item.xpath('.//p') if not par or not par[0].text: continue if 'Линия' in par[0].text: if len(par) == 1: line_str = par[0].text.replace('Линия', '').strip() else: line_str = par[1].text break for table in tables: ths = table.xpath('.//thead/tr/th/p') if ths: th = ths[0] if '№ п/п' in th.text: name = html_file.replace('.html', '') if '___' in name: name = name.split('___')[1] result += titul_parse_html(table, line_str, name) dest = full_path(os.path.join(html_path, dest_fname)) book = xlsxwriter.Workbook(dest) sheet = book.add_worksheet('Лист 1') row_number = 0 titles = ( ('Файл', ''), ('Линия', 'line'), ('№ стыка', 'joint'), ('Материал', 'material'), ('Диаметр,мм', 'diameter'), ('Толщина,мм', 'side_thickness'), ('Дата', 'welding_date'), ('Тип сварки', 'welding_type'), ('Вид соединения', 'welding_conn_view'), ('Свар элемент 1', 'join_type_from'), ('Свар элемент 2', 'join_type_to'), ('Клеймо', 'stigma'), # Фуфел из вордовского файла баз разбора ('Без анализа - Стык', ''), ('Без анализа - Клеймо', ''), ('Без анализа - Материал', ''), ('Без анализа - Размер', ''), ('Без анализа - Дата', ''), ('Без анализа - Тип сварки', ''), ) for i, title in enumerate(titles): sheet.write(row_number, i, title[0]) sheet.write(row_number + 1, i, title[1]) row_number += 1 result_len = len(result) for item in result: row_number += 1 number = item.get('number') if not number: continue if number.startswith('Ст'): number = number[2:] number = number.replace('.', '') diameter = side_thickness = '' size = item.get('size') if size: size = size.replace(',', '.') diameter, side_thickness = size.split('x') diameter = rega_digit.sub('', diameter) side_thickness = rega_digit.sub('', side_thickness) if not diameter: size = item.get('alt_size') if size: size = size.replace(',', '.') diameter, side_thickness = size.split('x') diameter = rega_digit.sub('', diameter) side_thickness = rega_digit.sub('', side_thickness) welding_date = item.get('date') if welding_date: # Вставляем год правильно welding_date = welding_date.strip() if welding_date and len(welding_date.strip()) == 8: welding_date = '%s20%s' % (welding_date[:6], welding_date[6:]) stigma = item.get('stigma') try: stigma = replace_rus2eng(stigma) except Exception: pass row = ( item.get('fname'), item.get('line'), number, item.get('material'), diameter, side_thickness, welding_date, item.get('welding_type'), item.get('conn_view'), item.get(0), item.get(1), stigma, # Фуфел из вордовского файла без разбора item.get('raw_number_joint'), item.get('raw_stigma'), item.get('raw_material'), item.get('raw_size'), item.get('raw_date'), item.get('raw_welding_type'), ) for i, field in enumerate(row): sheet.write(row_number, i, field) book.close() result = {'errors': []} if result_len < MAX_ROWS_PREVIEW: welders = Welder.objects.all().only('id', 'stigma') stigmas = {welder.stigma: welder for welder in welders} result = prepare_data_from_excel( full_path(os.path.join(html_path, dest_fname)), stigmas=stigmas, ) result['result'] = os.path.join('/media/', html_path, dest_fname) return result
def edit_welding(request, action: str, row_id: int = None, *args, **kwargs): """Создание/редактирование бланк-заявок :param request: HttpRequest :param action: действие над объектом (создание/редактирование/удаление) :param row_id: ид записи """ mh_vars = welding_vars.copy() mh = create_model_helper(mh_vars, request, CUR_APP, action) mh.select_related_add('joint') mh.select_related_add('joint__line') mh.select_related_add('joint__line__titul') mh.select_related_add('joint__line__titul__subject') mh.select_related_add('joint__line__titul__subject__company') mh.select_related_add('requester') mh.select_related_add('receiver') row = mh.get_row(row_id) context = mh.context # Права на файлы к заявке context['files_permissions'] = get_user_permissions( request.user, WeldingJointFile) context['welding_joint_state_permissions'] = get_user_permissions( request.user, WeldingJointState) context['repair_choices'] = WeldingJoint.repair_choices context['workshift_choices'] = WeldingJoint.workshift_choices context['control_choices'] = WeldingJoint.control_choices context['welding_type_choices'] = WELDING_TYPES context['category_choices'] = WeldingJoint.category_choices context['conclusion_states'] = CONCLUSION_STATES context['material_choices'] = MATERIALS context['join_types'] = JOIN_TYPES context['welding_conn_view_choices'] = Joint.welding_conn_view_choices context['state_choices'] = WELDING_JOINT_STATES context['today'] = datetime.datetime.today().strftime('%d.%m.%Y') if mh.error: return redirect('%s?error=not_found' % (mh.root_url, )) if request.method == 'GET': # ---------------------------------------------- # Вытаскиваем узел, по которому создается заявка # ---------------------------------------------- joint_str = request.GET.get('joint') if joint_str and not mh.row: joint = Joint.objects.select_related( 'line', 'line__titul', 'line__base', #'line__titul__subject', #'line__titul__subject__company', ).filter(pk=joint_str).first() context['row'] = { 'joint': object_fields(joint), } context['welders'] = joint.get_welders() if not joint: return redirect('%s?error=not_found' % (mh.root_url, )) # ------------------------------------- # На один стык должна быть одна заявка, # если на данный стык уже есть заявка, # тогда переадресовываем на нее # ------------------------------------- analog = WeldingJoint.objects.filter(joint=joint).first() if analog: link = reverse('%s:%s' % (CUR_APP, mh_vars['edit_urla']), kwargs={ 'action': 'form', 'row_id': analog.id }) return redirect(link) if action in ('edit', 'form', 'pdf') and row: if row.id: context['welders'] = {} if row.joint: context['welders'] = row.joint.get_welders() if row.requester: context['requester'] = { 'name': '%s' % row.requester.customuser, 'function': '%s' % row.requester.customuser.function, 'login': row.requester.username, 'id': row.requester.id, } if row.receiver: context['receiver'] = { 'name': '%s' % row.receiver.customuser, 'function': '%s' % row.receiver.customuser.function, 'login': row.receiver.username, 'id': row.receiver.id, } context['files'] = row.get_files() if row.joint and row.joint.line: context['total_joints'] = row.joint.line.get_total_joints() if action == 'create': mh.breadcrumbs_add({ 'link': mh.url_create, 'name': '%s %s' % (mh.action_create, mh.rp_singular_obj), }) elif action in ('edit', 'form') and mh.row: mh.breadcrumbs_add({ 'link': mh.url_edit, 'name': '%s %s' % (mh.action_edit, mh.rp_singular_obj), }) context['joint'] = mh.row.joint context['state'] = mh.row.get_state_display() # Берем по последнему ремонту context['joint_conclusion'] = JointConclusion.objects.filter( welding_joint=mh.row).order_by('-repair').first() elif action == 'drop' and row: if mh.permissions['drop']: row.delete() mh.row = None context['success'] = '%s удален' % (mh.singular_obj, ) # Пересчитать готовность линии recalc_joints(row.joint.line) else: context['error'] = 'Недостаточно прав' elif action == 'pdf' and row: context['row'] = row context['logo'] = full_path('misc/logo_standard.png') return render_pdf( request, template='pdf/welding_form.html', context=context, download=False, fname='welding_joint_%s' % row.joint.id, ) elif action == 'conclusion' and row: # Если по акту нет заключения, # переадресовываем на создание, # Если есть - берем последнее по ремонту conclusion = JointConclusion.objects.filter( welding_joint=row).order_by('-repair').first() # ------------------------------- # Ссылки не импортирую тупо меняю # welding на conclusion # ------------------------------- create_conclusion = mh_vars['create_urla'].replace( 'welding', 'conclusion') edit_conclusion = mh_vars['edit_urla'].replace( 'welding', 'conclusion') if conclusion: link = reverse('%s:%s' % (CUR_APP, edit_conclusion), kwargs={ 'action': 'edit', 'row_id': conclusion.id }) return redirect(link) link = reverse('%s:%s' % (CUR_APP, create_conclusion), kwargs={'action': 'create'}) return redirect('%s?welding_joint=%s' % (link, row.id)) elif request.method == 'POST': pass_fields = () mh.post_vars(pass_fields=pass_fields) if action in ('create', 'form') or (action == 'edit' and row): if action == 'create': # ------------------------- # Создание пока что бреем, # используем form действие, # ------------------------- assert False if mh.permissions['create']: mh.row = mh.model() mh.save_row() update_welding_joint_state(request, mh) context['success'] = 'Данные успешно записаны' else: context['error'] = 'Недостаточно прав' elif action == 'edit' and mh.row: # ------------------------------ # Редактирование пока что бреем, # используем form действие, # ------------------------------ assert False if mh.permissions['edit']: mh.save_row() update_welding_joint_state(request, mh) context['success'] = 'Данные успешно записаны' else: context['error'] = 'Недостаточно прав' elif action == 'form': # Заявки в ремонте даем редактировать, # чтобы гондоны смогли хотя бы со второго # раза правильно подать, а кто то с пятого if mh.row and mh.row.state in (1, 5) and mh.permissions['repair']: mh.permissions['edit'] = True if mh.permissions['edit'] and mh.row: # Принятую заявку не редактируем if mh.row.state == 3: context['error'] = 'Нельзя изменить принятую заявку' else: # ------------------------------- # Изменять на другой стык не даем # 1 стык = 1 заявка # ------------------------------- mh.save_row(set_fields={'joint': mh.row.joint}) update_welding_joint_state(request, mh) context['success'] = 'Данные успешно записаны' elif mh.permissions['create'] and not mh.row: # NOT! # -------------------------- # Без стыка нельзя сохранить # -------------------------- joint = None joint_str = mh.row_vars.get('joint') if joint_str: joint = Joint.objects.filter(pk=joint_str).first() if not joint: context['error'] = 'Выберите стык' return JsonResponse(context) else: analog = WeldingJoint.objects.filter( joint=joint).first() if analog: context[ 'error'] = 'Вы создаете дубликат, переадресовываем на заявку...' link = reverse('%s:%s' % (CUR_APP, mh_vars['edit_urla']), kwargs={ 'action': 'form', 'row_id': analog.id }) context['redirect_on_error'] = link return JsonResponse(context) mh.row = mh.model() mh.save_row() update_welding_joint_state(request, mh) context['success'] = 'Данные успешно записаны' else: context['error'] = 'Недостаточно прав' # Если не удалось сохранить, значит не выбран стык if not mh.row or not mh.row.id: context['error'] = 'Выберите стык' elif action == 'file' and request.FILES: # Принятую заявку не редактируем if mh.row.state == 3: context['error'] = 'Нельзя изменить принятую заявку' else: # Загрузка файла в WeldingJointFile mh.files_add('path') new_file = Files.objects.create( desc=mh.row.request_number, name=request.FILES['path'].name, ) mh.uploads(row=new_file) if new_file.path: joint_file = WeldingJointFile.objects.create( welding_joint=mh.row, file=new_file, ) new_file.update_mimetype() context['success'] = 'Файл загружен' context['file'] = { 'id': joint_file.id, 'path': new_file.path, 'name': new_file.name, 'mime': new_file.mime, 'folder': new_file.get_folder(), } else: new_file.delete() context['error'] = 'Не удалось загрузить файл' elif action == 'img' and request.FILES: mh.uploads() elif action == 'state' and row: # Смена статуса заявки на стык if update_welding_joint_state(request, mh): context['success'] = 'Статус заявки обновлен' else: context['error'] = 'Статус заявки не обновлен' if mh.row: mh.url_form = reverse('%s:%s' % (CUR_APP, mh_vars['edit_urla']), kwargs={ 'action': 'form', 'row_id': mh.row.id }) context['url_form'] = mh.url_form context['row'] = object_fields(mh.row, pass_fields=('password', )) context['row']['folder'] = mh.row.get_folder() # Не надо инфу о пользователях сливать context['row']['receiver'] = None context['row']['requester'] = None context['redirect'] = mh.get_url_edit() if action == 'form': context['redirect'] = mh.url_form else: mh.url_form = reverse('%s:%s' % (CUR_APP, mh_vars['create_urla']), kwargs={'action': 'form'}) if request.is_ajax() or action in ('img', 'file', 'state'): return JsonResponse(context, safe=False) template = '%sedit.html' % (mh.template_prefix, ) if action == 'form': mh.breadcrumbs_add({ 'link': mh.url_form, 'name': '%s' % (mh.singular_obj, ), }) template = '%sform.html' % (mh.template_prefix, ) return render(request, template, context)