, который находится в позиции [0]. news_info = soup.findAll("p")[0] print(news_info.text Собираем все вместе: from bs4 import BeautifulSoup import requests web_data = requests.get("https://www.lithuania.travel/en/category/what-is-lithuania", headers={"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/112.0.0.0 Safari/537.36"}) soup = BeautifulSoup(web_data.content, features="html.parser") news_info = soup.findAll("p")[0] print(news_info.text) И получим вот такой результат: Код и результат Плюсы использования файла requirements.txt Управление зависимостями: перечислив зависимости вашего проекта в файле requirements.txt, вы сможете легко понять, какие пакеты и какие версии вам нужны. Совместное использование вашего проекта с другими разработчиками: если вы делитесь своим проектом с другими разработчиками, вы можете добавить в него файл requirements.txt, чтобы они могли установить все необходимые пакеты. Это может сэкономить им время и нервы. Кроме того, это гарантирует тот факт, что все будут использовать одни и те же версии пакетов. Заключение Из этой статьи мы узнали, как можно создать файл requirements.txt, а также в чем преимущества его использования. А еще я рекомендуют вам попробовать с ним поработать, а также добавить его к нескольким своим проектам.
Существует огромное количество пакетов Python, с помощью которых мы решаем задачи программирования на ежедневной основе. Возьмем, например, библиотеку Beautiful Soup. Она не встроена в Python по умолчанию, ее нужно устанавливать отдельно.
В основе многих проектов лежат библиотеки и всякие другие зависимости, и процесс установки каждой из них может оказаться довольно утомительным и времязатратным.
И вот тут-то в игру вступает файл requirements.txt – файл, содержащий список пакетов и библиотек, которые необходимы для работы с проектом и которые можно установить вместе с этим файлом. Это обеспечивает тот факт, что ваша среда будет согласованной, а совместная работа непринужденной.
Формат файла requirements.txt
Схема, показывающая поле, содержащее имя файла «requirements.txt», и поле под ним, содержащее основной текст вида «имя_пакета == версия»
На изображении, представленном выше, продемонстрирован образец созданного файла requirements.txt, который содержит список пакетов и версий их установки.
Ключевые понятия
Я уже успел упомянуть несколько понятий, с которыми вы, возможно, не знакомы. Ниже я расскажу, что они значат, а также упомяну и другие не менее важные термины, с которыми вы столкнетесь при работе с файлом requirements.txt:
Зависимости
– это программные компоненты, в которых нуждается программа для правильной работы. Это могут быть библиотеки, фреймворки и прочие программы.
Пакеты
– это способ группировки связанных зависимостей. С их помощью устанавливать и управлять зависимостями становится гораздо проще.
Виртуальная среда
– это каталог, который содержит копию интерпретатора Python и всех пакетов, необходимых для определенного проекта.
Pip
– это диспетчер пакетов для Python. Вы можете использовать его для того, чтобы устанавливать, удалять пакеты Python и управлять ими.
Как создать файл requirements.txt
Для того, чтобы создать файл requirements.txt, вам нужно настроить виртуальную среду. Если вы используете PyCharm, то виртуальная среда уже настроена (.venv). Но если вы работаете в Visual Studio Code, вам придется создать виртуальную среду самостоятельно.
Для создания файла requirements.txt вы можете использовать терминал или командную строку. Ниже приведены шаги, которые вам нужно выполнить, чтобы создать файл.
Для начала откройте терминал или командную строку. Далее проверьте, является ли указанный путь к файлу вашим рабочим каталогом. Для этого введите вот эту команду:
$ cd folder-name #cd - change directory
Замените в этой команде
folder-name
на имя каталога, к которому вы хотите получить доступ.
Настройка каталога проекта в командной строке
После чего запустите следующую команду:
$ pip freeze > requirements.txt
И вы увидите, что файл requirements.txt был добавлен:
Только что созданный файл requirements.txt
А вот так выглядит созданный файл requirements.txt внутри:
Список пакетов в файле requirements.txt
На изображении, представленном выше, продемонстрированы зависимости, с которыми вы можете работать, а также их версии.
Как работать с файлом requirements.txt
Теперь, когда у нас есть файл requirements.txt, вы можете увидеть, что внутри него находится длинный список различных пакетов.
Для того, чтобы работать с этими пакетами, вам нужно их установить. Вы можете это сделать через терминал или командную строку.
Введите вот эту команду:
pip install -r requirements.txt
И вы увидите примерно следующее:
Установка пакетов, находящихся в файле requirements.txt
Итак, все зависимости установлены, и теперь вы можете работать с файлом requirements.txt.
Пример использования файла requirements.txt
В этом примере мы будем работать с двумя библиотеками:
beautifulsoup4
и
requests
. С их помощью мы будем извлекать информацию с сайта.
Рабочие библиотеки в файле requiremets.txt для данного примера
На изображении, представленном выше, вы видим, что в файле requirements.txt есть обе эти библиотеки, и, кроме того, указаны их версии. Так вот, раз мы установили их ранее, мы можем с ними работать.
Импортируем библиотеку
BeautifulSoup
из пакета
bs4
(
beautifulsoup4
). Также импортируем библиотеку
requests
.
from bs4 import BeautifulSoup
import requests
Для того, чтобы получить информацию с веб-сайта по его URL-адресу, нам нужно подключиться к библиотеке
requests
, а для этого нам понадобиться метод
.get()
.
web_data = requests.get("https://www.lithuania.travel/en/category/what-is-lithuania", headers={"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/112.0.0.0 Safari/537.36"})
Теперь, когда мы получили доступ к URL-адресу, библиотека
BeautifulSoup
принимает
web_data
и возвращает все содержимое HTML, которое в нем есть.
soup = BeautifulSoup(web_data.content, features="html.parser")
В итоге я решил вернуть элементы с тегом
Первоначально BGP был разработан как протокол Внешнего шлюза (Exterior Gateway Protocol - EGP), что означает, что он предназначался для подключения сетей или автономных систем (AS), а не устройств. Если BGP является EGP, это должно означать, что другие протоколы маршрутизации, такие как RIP, EIGRP, OSPF и IS-IS, должны быть протоколами внутренних шлюзов (Interior Gateway Protocols- IGP). Четкое определение внутренних и внешних шлюзов оказалось полезным при проектировании и эксплуатации крупномасштабных сетей. BGP является уникальным среди широко распространенных протоколов в том, что касается расчета пути без петель. Существует три широко используемых протокола векторов расстояний (Spanning Tree, RIP и EIGRP). Существует два широко используемых протокола состояния канала связи (OSPF и IS-IS). И есть еще много примеров этих двух типов протоколов, разработанных и внедренных в то, что можно было бы считать нишевыми рынками. BGP, однако, является единственным широко развернутым протоколом вектора пути.
Каковы наиболее важные цели EGP? Первый - это, очевидно, выбор путей без петель, но это явно не означает кратчайшего пути. Причина, по которой кратчайший путь не так важен в EGP, как в IGP, заключается в том, что EGP используются для соединения объектов, таких как поставщики услуг, поставщики контента и корпоративные сети. Подключение сетей на этом уровне означает сосредоточение внимания на политике, а не на эффективности - с точки зрения сложности, повышение состояния с помощью механизмов политики при одновременном снижении общей оптимизации сети с точки зрения передачи чистого трафика.
BGP-пиринг
BGP не обеспечивает надежной передачи информации. Вместо этого BGP полагается на TCP для передачи информации между одноранговыми узлами BGP. Использование TCP гарантирует:
Обнаружение MTU обрабатывается даже для соединений, пересекающих несколько переходов (или маршрутизаторов).
Управление потоком осуществляется базовым транспортом, поэтому BGP не нуждается в непосредственном управлении потоком (хотя большинство реализаций BGP действительно взаимодействуют со стеком TCP на локальном хосте, чтобы повысить пропускную способность, в частности, для BGP).
Двусторонняя связь между одноранговыми узлами обеспечивается трехсторонним рукопожатием, реализованным в TCP.
Несмотря на то, что BGP полагается на базовое TCP-соединение для многих функций, которые плоскости управления должны решать при построении смежности, по-прежнему существует ряд функций, которые TCP не может предоставить. Следовательно, необходимо более подробно рассмотреть процесс пиринга BGP.
Рисунок 1 позволяет изучить этот процесс.
Сеанс пиринга BGP начинается в состоянии ожидания (idle state).
A отправляет TCP open на порт 179. B отвечает на временный порт (ephemeral port) на A. После завершения трехстороннего подтверждения TCP (сеанс TCP успешен), BGP перемещает состояние пиринга для подключения. Если пиринговый сеанс формируется через какой-либо тип фильтрации на основе состояния, такой как брандмауэр, важно, чтобы открытое TCP-сообщение передавалось «изнутри» фильтрующего устройства.
В случае сбоя TCP-соединения состояние пиринга BGP переводится в активное.
A отправляет BGP open в B и переводит B в состояние opensent. В этот момент A ожидает от B отправки сообщения keepalive. Если B не отправляет сообщение keepalive в течение определенного периода, A вернет сеанс обратно в состояние ожидания (idle state). Открытое сообщение содержит ряд параметров, например, какие семейства адресов поддерживают два спикера BGP и hold timer. Это называется согласованием возможностей. Самый низкий (минимальный) hold timer из двух объявленных выбирается в качестве hold timer для однорангового сеанса.
Когда B отправляет A сообщение keepalive, A переводит B в состояние openconfirm.
На этом этапе A отправит B сообщение keepalive для проверки соединения. Когда A и B получают сообщения поддержки активности друг друга, пиринговый сеанс переходит в established state.
Два узла BGP обмениваются маршрутами, поэтому их таблицы обновлены. A и B обмениваются только своими лучшими путями, если какая-либо форма многонаправленного распространения BGP не поддерживается и не настроена на двух спикерах.
Чтобы уведомить A, что он завершил отправку всей своей локальной таблицы, B отправляет A сигнал End of Table (EOT) или End of RIB (EOR).
Существует два типа пиринговых отношений BGP: одноранговые узлы BGP в одной и той же автономной системе (AS, что обычно означает набор маршрутизаторов в одном административном домене, хотя это довольно общее определение) называются внутренними одноранговыми узлами BGP (internal BGP - iBGP) и Одноранговые узлы BGP между автономными системами называются внешними (или внешними - exterior) узлами BGP (eBGP). Хотя два типа пиринговых отношений BGP построены одинаково, у них разные правила объявления.
Процесс выбора оптимального пути BGP
Поскольку BGP предназначен для соединения автономных систем, алгоритм наилучшего пути ориентирован в первую очередь на политику, а не на отсутствие петель. Фактически, если вы изучите какое-либо стандартное объяснение процесса наилучшего пути BGP, то, является ли конкретный путь свободным от петель, вообще не будет учитываться в процессе принятия решения. Как же тогда BGP определяет, что конкретный узел объявляет маршрут без петель? Рисунок 2 демонстрирует это.
На рисунке 2 каждый маршрутизатор находится в отдельной AS, поэтому каждая пара спикеров BGP будет формировать сеанс пиринга eBGP. A, который подключен к 2001: db8: 3e8: 100 :: / 64, объявляет этот маршрут к B и C. Объявления маршрута BGP несут ряд атрибутов, одним из которых является путь AS. Перед тем, как A объявит 100 :: / 64 для B, он добавляет свой номер AS в атрибут AS Path. B получает маршрут и объявляет его D. Перед объявлением маршрута к D он добавляет AS65001 к AS Path. Тогда путь AS, прослеживающийся от A до C, на каждом шаге выглядит примерно так:
Получено B: [AS65000]
Получено C: [AS65000, AS65001]
Получено D: [AS65000, AS65001, AS65003]
Когда D получил маршрут от B, он анонсирует его обратно в C (в BGP нет split horizon). Предположим, что C, в свою очередь, объявляет обратный маршрут к A по какой-то причине (в этой ситуации это не так, потому что путь через A был бы лучшим путем к месту назначения, а просто для демонстрации предотвращения петель), A будет проверять AS Path и обнаружение его локальной AS находится в AS Path. Это явно петля, поэтому A просто игнорирует маршрут. Поскольку этот маршрут игнорируется, он никогда не помещается в таблицу топологии BGP. Следовательно, с использованием процесса наилучшего пути BGP сравниваются только маршруты без петель.
В большинстве реализаций процесс наилучшего пути BGP состоит из 13 шагов (первый шаг реализуется не всегда, так как это локальное решение со стороны узла BGP):
Выбирается маршрут с наибольшим весом. Некоторые реализации не используют вес маршрута.
Выбирается маршрут с наивысшим местным предпочтением (local preference- LOCAL PREF). Local preference собой политику выхода локальной AS - какую точку выхода из доступных точек выхода предпочел бы владелец этой AS, как и узел BGP.
Предпочитайте маршрут с локальным происхождением, то есть на этом узле BGP. Этот шаг редко используется в процессе принятия решения.
Предпочитайте путь с самым коротким AS Path. Этот шаг предназначен для выбора наиболее эффективного пути через объединенную сеть, выбора пути, который будет проходить через наименьшее количество автономных систем для достижения пункта назначения. Операторы часто добавляют записи AS Path, чтобы повлиять на этот шаг в процессе принятия решения.
Предпочитайте путь с наименьшим значением координат. Маршруты, которые перераспределяются из IGP, предпочтительнее маршрутов с неизвестным происхождением. Этот шаг редко оказывает какое - либо влияние на процесс принятия решений.
Предпочитайте путь с самым низким multiexit discriminator (MED). MED представляет входную политику удаленной AS. Таким образом, MED сравнивается только в том случае, если от одной и той же соседней AS было получено несколько маршрутов. Если один и тот же маршрут получен от двух разных соседних автономных систем, MED игнорируется.
Предпочитайте маршруты eBGP маршрутам iBGP.
Предпочитайте маршрут с наименьшей стоимостью IGP до следующего перехода. Если политика локального выхода не задана (в форме локального предпочтения), и соседняя AS не установила политику входа (в форме MED), то путь с ближайшим выходом из локального маршрутизатора выбирается как точка выхода.
Определите, следует ли устанавливать несколько путей в таблице маршрутизации (настроена некоторая форма multipath).
При сравнении двух внешних маршрутов (полученных от однорангового узла eBGP) предпочтите самый старый маршрут или маршрут, изученный первым. Это правило предотвращает отток маршрутов только потому, что маршруты обновляются.
Предпочитайте маршрут, полученный от однорангового узла с наименьшим идентификатором маршрутизатора. Это просто средство разрешения конфликтов для предотвращения оттока в таблице маршрутизации.
Предпочитайте маршрут с наименьшей длиной кластера.
Предпочитайте маршрут, полученный от однорангового узла с наименьшим адресом пиринга. Это, опять же, просто тай-брейк, выбранный произвольно, чтобы предотвратить ненужные связи и вызвать отток в таблице маршрутизации, и обычно используется, когда два одноранговых узла BGP соединены по двум параллельным каналам.
Хотя это кажется долгим процессом, почти каждое решение наилучшего пути в BGP сводится к четырем факторам: локальному предпочтению (local preference), MED, длине AS Path и стоимости IGP.
Правила объявления BGP
BGP имеет два простых правила для определения того, где объявлять маршрут:
Объявляйте лучший путь к каждому пункту назначения каждому узлу eBGP.
Объявляйте лучший путь, полученный от однорангового узла eBGP, для каждого однорангового узла iBGP.
Еще один способ сформулировать эти два правила: никогда не объявлять маршрут, полученный от iBGP, другому узлу iBGP. Рассмотрим рисунок 3.
На рисунке 3 A и B - это одноранговые узлы eBGP, а B и C, а также C и D - одноранговые узлы iBGP. Предположим, A объявляет 2001: db8: 3e8: 100 :: / 64 для B. Поскольку B получил это объявление маршрута от однорангового узла eBGP, он объявит 100 :: / 64 на C, который является одноранговым узлом iBGP. C, изучив этот маршрут, не будет объявлять маршрут к D, поскольку C получил маршрут от однорангового узла iBGP, а D также является одноранговым узлом iBGP. Таким образом, на этом рисунке D не узнает о 100 :: / 64. Это не очень полезно в реальном мире, однако ограничение присутствует не просто так.
Рассмотрим, как BGP предотвращает образование петель маршрутизации - передавая список автономных систем, через которые прошел маршрут, в самом объявлении маршрута. При объявлении маршрута от одного спикера iBGP к другому AS Path не изменяется. Если узлы iBGP объявляют маршруты, полученные от одноранговых узлов iBGP, одноранговым узлам iBGP, петли маршрутизации могут быть легко сформированы. Одним из решений этой проблемы является простое построение многоуровневых пиринговых отношений между B и D (помните, что BGP работает поверх TCP. Пока существует IP-соединение между двумя узлами BGP, они могут построить пиринговые отношения). Предположим, что B строит пиринговые отношения с D через C, и ни B, ни D не строят пиринговые отношения с C. Что произойдет, когда трафик переключается на 100 :: / 64 посредством D на C? Что будет с пакетами в этом потоке на C? У C не будет маршрута к 100 :: / 64, поэтому он сбросит трафик. Это может быть решено несколькими способами - например, B и D могут туннелировать трафик через C, поэтому C не обязательно должен иметь доступность к внешнему пункту назначения. BGP также можно настроить для перераспределения маршрутов в любой основной запущенный IGP (это плохо - не делайте этого).
Для решения этой проблемы были стандартизированы рефлекторы маршрутов BGP. Рисунок 4 иллюстрирует работу отражателей маршрута.
На рисунке 4 E сконфигурирован как рефлектор маршрута. B, C и D настроены как клиенты рефлектора маршрутов (в частности, как клиенты E). A объявляет маршрут 2001: db8: 3e8: 100 :: / 64 к B. B объявляет этот маршрут E, потому что он был получен от однорангового узла eBGP, а E является одноранговым узлом iBGP. E добавляет новый атрибут к маршруту, список кластеров, который указывает путь обновления в AS через кластеры отражателя маршрута. Затем E объявит маршрут каждому из своих клиентов. Предотвращение зацикливания в этом случае обрабатывается списком кластеров.
Подведение итогов о BGP
Хотя изначально BGP был разработан для соединения автономных систем, его использование распространилось на центры обработки данных, передачу информации о виртуальных частных сетях. Фактически, использование BGP практически безгранично. Постепенно BGP превратился в очень сложный протокол.
BGP можно описать как:
Проактивный протокол, который узнает о достижимых местах назначения через конфигурацию, локальную информацию и другие протоколы.
Протокол вектора пути, который объявляет только лучший путь к каждому соседу и не предотвращает образование петель в автономной системе (если не развернуты рефлекторы маршрута или какая-либо дополнительная функция)
Выбор путей без петель путем изучения пути, по которому может быть достигнут пункт назначения
Проверка двустороннего подключения и MTU за счет использования TCP в качестве основы для передачи информации.
Система записи телефонных разговоров, позволяет компаниям иметь возможность оценивать качество работы сотрудников, отслеживать различные показатели взаимодействия с клиентом, разрешать спорные ситуации. Запись телефонных разговоров - это мощный инструмент, который позволяет оптимизировать работу компании, улучшить качество обслуживания и компетенции сотрудников.
На сегодняшний день, лидерами рынка систем записи являются ZOOM, Verint, Nice, Cisco (MediaSense).
По какому принципу работает система записи? На этот вопрос мы постараемся ответить.
Запись телефонных разговоров как правило делят на два типа: активная и пассивная. Активная (SPANLess) запись – это возможность телефонного аппарата напрямую отправлять RTP поток на сервер записи, а сигнальный трафик приходит через JTAPI*.
*JTAPI (Java Telephony Application Programming Interface) – специальный телефонный «эй-пи-ай», позволяющий интегрировать телефонные события.
Данный вариант зачастую реализуется при действующем кластере CUCM версией выше 6.0(Cisco Unified Communications Manager) и телефонах с поддержкой Built-in-Bridge.
Давайте посмотрим на схему работы активной записи:
Активный режим записи разговоров
В данном примере, пользователь А, звонит пользователю В. На телефоне пользователя А включен режим Built-in Bridge, и настроен соответствующий профиль записи. CUCM в этот момент фиксирует, что телефон пользователя В подлежит записи и начинает дублировать сигнализацию на интерфейс сервера записи. Вместе с тем, на сервер приходит и RTP поток от пользователя В. Медиа поток декодируется и соотносится с сигнализацией. По окончании обработки, через GUI системы записи мы видим наш разговор, с временными метками, DNIS, ANI и некоторые другие. В контактных центрах, так же возможна интеграция с платформой UCCX, UCCE, Genesys ,Avaya Communication Manager. В результате интеграции с данной платформой, будет возможно передавать агентскую информацию, CallType и многие другие параметры.
Давайте теперь разберемся с пассивной записью. Пассивная запись организуется путем настройки SPAN** – сессий для RTP траффика и сигнализации.
**SPAN (Switched Port Analyzer) – мониторинговая сессия, которая позволяет дублировать сетевой трафик с одного интерфейса на другой.
Чтобы на сервер записи не приходил ненужный трафик, как правило, настраивают RSPAN в сочетании листами доступа (access-list).
Давайте снова посмотрим на схему:
Пассивный (устаревший) режим записи разговоров
На схеме сверху, можно заметить, что роль CUCM сводится к управлению сигнализацией (SCCP или SIP). Предположим, что на центральном коммутаторе есть следующие настройки:
SPAN_SW(config)#monitor session 1 source interface f0/1
SPAN_SW(config)#monitor session 1 destination interface f0/3
Все, теперь траффик в обе стороны, как на прием, так и на передаче, с порта Fa 0/1 будет дублироваться на порт Fa 0/3. Можно вводить ограничения по SPAN-сессиям, например:
SPAN_SW(config)#monitor session 1 source interface f0/1 tx
SPAN_SW(config)#monitor session 1 destination interface f0/3
Это ограничение будет дублировать только исходящий (с порта) траффик. Таким образом, мы рассмотрели архитектурные особенности систем записи. Наша компания имеет большой опыт в инсталляции и поддержке систем записи.