Уведомления

Группа в Telegram: @pythonsu

#1 Апрель 6, 2017 03:39:43

Serggg
Зарегистрирован: 2017-04-06
Сообщения: 12
Репутация: +  0  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Друзья, очень надеюсь на ваше гостеприимство и выручки в решении этой нелегкой задачи.
Сам я с этой задачей не смогу справится, очень нужна реализация на любом скриптовом языке. Выбор пал на python как на самый лаконичный язык.

Есть 17 файлов - 1.txt и .xsh. Все файлы содержат текстовые данные и лежат в одной папке. В первом файле содержится список айпи адресов начиная со второй строчки и до 17ой. В 1ой строке записан Username.

Задача: Взять из файла 1.txt Username и вписать его в каждый файл .xsh в строку UserName= после знака “=”. А после этого взять с каждой строчки IP-адрес и вписать его в СООТВЕТСТВУЮЩИЙ файл в порядке простой очереди: 2ая строка - в 1ый файл, 3я строка во 2ой файл и т.д. Вписывать IP-адрес необходимо в строку содержащую Host= так же после знака равно. В обоих случаях ввода данных в файлы необходимо будет заменить данные после знака =, то есть строки уже будут содержать какой-то Username и IP-адрес.

Невероятно сильно выручите если напишите код этого несложно для профессионала скрипта. Надеюсь на вашу помощь. Оба файла прилагаю для тестов. Очень жду сообщений

Прикреплённый файлы:
attachment tech.nix355_1_1.xsh (3,3 KБ)

Офлайн

#2 Апрель 6, 2017 03:39:54

Serggg
Зарегистрирован: 2017-04-06
Сообщения: 12
Репутация: +  0  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Адреса

Прикреплённый файлы:
attachment 1.txt (91 байт)

Офлайн

#3 Апрель 6, 2017 04:48:57

scidam
Зарегистрирован: 2016-06-15
Сообщения: 288
Репутация: +  35  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Для парсинга ini-подобных конфигурационных файлов очень хорошо подходит configparser;
Если я правильно понял, то следующий код практически решает вашу задачу, или очень близок к решению

 import configparser
parser = configparser.ConfigParser()
parser.optionxform = str
parser.read('tech.nix355_1_1.xsh')
with open('1.txt', 'r') as fi:
    data = fi.readlines()
    username = data[0].strip()
    hosts = map(str.strip, data[1:])
    for ind, host in enumerate(hosts):
        with open('newfile_%s.xsh' % ind, 'w') as fp:
            parser['CONNECTION']['Host'] = host
            parser['CONNECTION:AUTHENTICATION']['UserName'] = username
            parser.write(fp)


Офлайн

#4 Апрель 6, 2017 05:12:55

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9716
Репутация: +  842  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Serggg
Задача: …
Это надо преобразовать файлы в текстовые строки.
Потом подготовить строки для замены, проанализировав текстовые строки из файлов.
Потом заменить в текстовых строках по регулярному выражению одни строки на подготовленные строки.
Потом сохранить получившиеся текстовые строки в новые файлы.
Когда новые файлы сохранились, старые файлы удалить и новые поместить на их место.

Вот в общем случае это так делается. Для каждого действия (этапа или шага алгоритма) делается своя функция с параметрами. А потом вызовы этих функций с определёнными параметрами соединяются в общую программу, которая делает всё от начала до конца.

scidam
или очень близок к решению
Да, близок к решению, но тебе повезло, что у него нечто похожее на ini-файл. А вдруг придётся работать с другим форматом или этот окажется не совсем ini? Придётся новую программу писать от начала до конца. А когда общую программу пишешь, то из-за работы с простым текстом формат не важен и при новом формате можно просто немножко поменять параметры скрипта или сам скрипт за пять минут и всё будет работать по-новому (но, главное, точно).



Отредактировано py.user.next (Апрель 6, 2017 05:16:40)

Офлайн

#5 Апрель 6, 2017 22:55:33

Serggg
Зарегистрирован: 2017-04-06
Сообщения: 12
Репутация: +  0  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

scidam
Для парсинга ini-подобных конфигурационных файлов очень хорошо подходит configparser;Если я правильно понял, то следующий код практически решает вашу задачу, или очень близок к решению
Благодарю за отличный пример кода, который как раз выполняет что нужно. Скрипт необходимо немного доработать и после ломания головы над учебником питона я понял что без вас не справлюсь.
1) Динамическое имя файла для записи, берется из переменной username - тут вроде получилось.
2) цикл перебора файлов надо сделать двойным - первый от 1 до 3 , второй внутренний от 1 до 6, так как файлы имеют такую структуру:

filename_1_1 … filename_1_2 … filename_1_6
filename_2_1 … filename_2_2 … filename_2_2, а записывать в них айпиадреса в прямом порядке, как и написано Вами в скрипте. С этим пунктом трудность возникла
3) и добавить в условие цикла динамическое формирование имени за счёт двух счётчиков из циклов for.

Поставил вам + в репу сразу как увидел код, вместо поучений типичных))) Спасибо вам
 import configparser
parser = configparser.ConfigParser()
parser.optionxform = str


with open('ip.txt', 'r') as fi:
data = fi.readlines()
username = data[0].strip()

//передвинул чтение данных после определение переменной username
parser.read('%username_1_1.xsh')
hosts = map(str.strip, data[1:])

//двойной вложенный цикл нужен. 1ый уровень от 1 до 3, второй от 1 до 6
//и динамическое имя редактируемого файла. как сделать ?
for ind, host in enumerate(hosts):
with open('%username_%s.xsh' % ind, 'w') as fp:
parser['CONNECTION']['Host'] = host
parser['CONNECTION:AUTHENTICATION']['UserName'] = username
parser.write(fp)

Отредактировано Serggg (Апрель 6, 2017 22:55:51)

Офлайн

#6 Апрель 7, 2017 01:28:40

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9716
Репутация: +  842  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Serggg
Поставил вам + в репу сразу как увидел код, вместо поучений типичных)))
Это не для тебя поучения, а для scidam'а и других, кто захочет тебе писать код. Про тебя-то мы поняли, что ты и строчки написать не можешь, а программу эту простую (которую ты называешь СЛОЖНОЙ :o ) тем более не потянешь. Для этого структурное программирование надо знать, а в книжках по питону про него не пишут.

А так получается, что он наскоряк накидал, а ты ему пишешь в итоге
Serggg
Скрипт необходимо немного доработать
И сейчас он тебе его не доработает, потому что изначально код написан так, что не предрасположен к доработке. (Есть правила определённые по написанию программ, чтобы они были легко меняемы. Программа должна быть правильной, понятной и легко меняемой. И вот для поддержки меняемости программы ответственность за действия программы распределяется по функциям. Программа представляет из себя такую змею как бы, где для изменения определённого поведения нужно залезть у неё только в один конкретный кусок, так что вся змея этого как бы не заметит, но в целом начнёт работать по-новому в нужном месте.)



Отредактировано py.user.next (Апрель 7, 2017 01:38:32)

Офлайн

#7 Апрель 7, 2017 05:37:23

scidam
Зарегистрирован: 2016-06-15
Сообщения: 288
Репутация: +  35  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

py.user.next
И сейчас он тебе его не доработает, потому что изначально код написан так, что не предрасположен к доработке

Да тут и программы-то нет, несколько строк для автоматизации действий; однако, когда первоначально я читал задание, я его не понял – а именно, что такое в порядке очереди для файлов, вторую строку в перый файл и т.п. нужно этот порядок определить, в списке эти файлы выписать, например;

py.user.next
И сейчас он тебе его не доработает
Да, похоже на правду …

Serggg
Serggg
и добавить в условие цикла динамическое формирование имени за счёт двух счётчиков из циклов for.

Попробую чуть дописать, раз начал уже…

 for ind1 in [1, 2, 3]: # Здесь так мало цифр, что это даже короче, чем range...
     for ind2 in range(1, 7):
           with open('%username_%s.xsh' % ind, 'rw') as fp:
                 parser.read_string(fp.read())
                 #Здесь необходимые изменения, HOST, etc. 
                 parser.write(fp)

Однако, здесь мы сразу читаем файл, парсим, и в него же пишем – это ненадежно; py.user.next в предыдущем посте подробно описал как должно быть, чтобы все было надежно; В общем, для экспериментов, следует сделать сначала дубликат всего и работать с ним.
Если эта работа “одноразовая”, то можно и на дубликате сделать, если понравится оставить и ничего не мудрить. Но если нужно регулярно делать такие изменения в файлах, то тогда нужно обязательно следовать тому, что описал py.user.next, а то вдруг какой сбой и можно содержимое файлов потерять.






Офлайн

#8 Апрель 7, 2017 06:34:03

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9716
Репутация: +  842  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

scidam
Однако, здесь мы сразу читаем файл, парсим, и в него же пишем
Это не проблема, можно на копии всё делать. Тут проблема в другом: ещё пару таких доработок и программа сначала станет нечитаемой, а потом начнёт ломать сама себя же при любом мелком исправлении. (Правило инкапсуляции кода нарушено.)

Например, вот у тебя отрывок
scidam
 with open('%username_%s.xsh' % ind, 'rw') as fp:
А что если имя надо будет формировать по-другому (с вычислением даты, например, или около того), тут явно нужна функция по формированию имени, в которую можно спрятать весь код получения имени, каким бы сложным он ни был.

Тут ещё баг нашёл
  
>>> '%username_%s.xsh' % 1
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: not enough arguments for format string
>>>



Отредактировано py.user.next (Апрель 7, 2017 06:39:05)

Офлайн

#9 Апрель 7, 2017 08:05:34

scidam
Зарегистрирован: 2016-06-15
Сообщения: 288
Репутация: +  35  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

py.user.next
Например, вот у тебя отрывок….Тут ещё баг нашёл
Да. согласен, скопировал у Serggg с поста последнего; по его шаблону, видимо должно быть “filename_%s_%s” %(ind1, ind2).


Офлайн

#10 Апрель 13, 2017 04:38:14

Serggg
Зарегистрирован: 2017-04-06
Сообщения: 12
Репутация: +  0  -
Профиль   Отправить e-mail  

Прошу помощи. Супер сложное задание!

Доброй ночи scidam и py.user.next. Насколько долго меня хватило так это на разбор ошибки с неверными отступами - в питоне оказывается отступы влияют на структуру кода(небольшое открытия дня для меня :rolleyes, на правку строки с именем файла(спасибо знаниям С), и на добавление функции unicode для верного считывания строки из файла.

Загвоздка на последней стадии этого грандиозного проекта). Для меня именно так сие чудо и ощущается.
Как работает изменение строки Host и Username через следующий код:

parser['CONNECTION']['Host'] = host
parser['CONNECTION:AUTHENTICATION']['UserName'] = username
я вот точно уверен, что это не двумерный ассоциированный массив). Интерпретатор питона ругается, что host не определен, а на hostS - TypeError: option values must be strings


Текущая версия скрипта:

 import configparser
parser = configparser.ConfigParser()
parser.optionxform = str
with open('ip.txt', 'r') as fi:
    data = fi.readlines()
    username = data[0].strip()
    hosts = map(str.strip, data[1:])
	
    for ind1 in [1, 2, 3]:
     for ind2 in range(1, 7):
           with open('%s_%s_%s.xsh' %(username, ind1, ind2)) as fp:
             parser.read_string(unicode(fp.read()))
parser['CONNECTION']['Host'] = host
parser['CONNECTION:AUTHENTICATION']['UserName'] = username
parser.write(fp)

Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version