persona-dsl 26.1.20.8__tar.gz → 26.1.20.9__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- persona_dsl-26.1.20.9/PKG-INFO +222 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/pyproject.toml +2 -1
- persona_dsl-26.1.20.9/src/persona_dsl.egg-info/PKG-INFO +222 -0
- persona_dsl-26.1.20.8/PKG-INFO +0 -35
- persona_dsl-26.1.20.8/src/persona_dsl.egg-info/PKG-INFO +0 -35
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/MANIFEST.in +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/README.md +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/setup.cfg +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/action.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/base_step.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/combined_step.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/expectation.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/fact.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/goal.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/ops.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/components/step.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/contains_item.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/contains_the_text.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/has_entries.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/is_equal.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/is_greater_than.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/path_equal.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/is_displayed.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/matches_aria_snapshot.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/matches_screenshot.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/generators/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/generators/api_generator.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/generators/cli.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/generators/page_generator.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/api/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/api/json_as.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/api/json_response.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/api/send_request.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/db/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/db/execute_sql.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/db/fetch_all.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/db/fetch_one.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/kafka/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/kafka/message_in_topic.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/kafka/send_message.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/soap/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/soap/call_operation.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/soap/operation_result.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/aria_snapshot.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/click.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/current_path.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/element_attribute.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/element_is_visible.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/element_text.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/elements_count.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/fill.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/generate_page_object.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/input_value.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/navigate.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/press_key.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/rich_aria_snapshot.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/screenshot.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/table_data.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/wait_for_navigation.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/pages/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/pages/elements.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/pages/page.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/pages/virtual_page.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/persona.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/pytest_plugin.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/runtime/dist/persona_bundle.js +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/core/base.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/core/skill_definition.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/use_api.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/use_browser.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/use_database.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/use_kafka.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/use_soap.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/__init__.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/artifacts.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/config.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/data_providers.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/decorators.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/metrics.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/naming.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/path.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/retry.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/taas_integration.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/utils/waits.py +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/SOURCES.txt +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/dependency_links.txt +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/entry_points.txt +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/requires.txt +0 -0
- {persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/top_level.txt +0 -0
|
@@ -0,0 +1,222 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: persona-dsl
|
|
3
|
+
Version: 26.1.20.9
|
|
4
|
+
Summary: DSL для реализации паттерна Screenplay в Python-тестах.
|
|
5
|
+
Requires-Python: >=3.9
|
|
6
|
+
Description-Content-Type: text/markdown
|
|
7
|
+
Requires-Dist: playwright==1.55.0
|
|
8
|
+
Requires-Dist: pytest
|
|
9
|
+
Requires-Dist: pytest-cov
|
|
10
|
+
Requires-Dist: allure-pytest
|
|
11
|
+
Requires-Dist: python-dotenv
|
|
12
|
+
Requires-Dist: pyyaml
|
|
13
|
+
Requires-Dist: pydantic<3,>=2
|
|
14
|
+
Requires-Dist: requests
|
|
15
|
+
Requires-Dist: pyhamcrest
|
|
16
|
+
Requires-Dist: redis
|
|
17
|
+
Requires-Dist: Faker
|
|
18
|
+
Requires-Dist: pillow
|
|
19
|
+
Requires-Dist: zeep
|
|
20
|
+
Requires-Dist: pg8000
|
|
21
|
+
Requires-Dist: oracledb
|
|
22
|
+
Requires-Dist: kafka-python
|
|
23
|
+
Requires-Dist: Unidecode>=1.3
|
|
24
|
+
Requires-Dist: black
|
|
25
|
+
Provides-Extra: dev
|
|
26
|
+
Requires-Dist: black; extra == "dev"
|
|
27
|
+
Requires-Dist: ruff; extra == "dev"
|
|
28
|
+
Requires-Dist: mypy; extra == "dev"
|
|
29
|
+
Requires-Dist: pytest-cov; extra == "dev"
|
|
30
|
+
Requires-Dist: pre-commit; extra == "dev"
|
|
31
|
+
Requires-Dist: types-requests; extra == "dev"
|
|
32
|
+
Requires-Dist: types-PyYAML; extra == "dev"
|
|
33
|
+
Requires-Dist: types-redis; extra == "dev"
|
|
34
|
+
Requires-Dist: pytest-asyncio; extra == "dev"
|
|
35
|
+
Requires-Dist: pytest-timeout; extra == "dev"
|
|
36
|
+
Requires-Dist: pytest-xdist; extra == "dev"
|
|
37
|
+
|
|
38
|
+
# persona-dsl: Руководство пользователя
|
|
39
|
+
|
|
40
|
+
`persona-dsl` — это ядро фреймворка, реализующее легковесную версию паттерна **Screenplay** для написания автотестов на Python. Оно спроектировано так, чтобы дать вам полный контроль над базовыми инструментами (`Playwright`, `Allure`), предоставляя при этом выразительный и читаемый DSL для описания тестов.
|
|
41
|
+
|
|
42
|
+
## 1. Основные концепции
|
|
43
|
+
|
|
44
|
+
В основе фреймворка лежат шесть ключевых компонентов, которые вместе описывают любое взаимодействие с системой.
|
|
45
|
+
|
|
46
|
+
- **Persona**: "Действующее лицо" или актор, который выполняет действия в тесте. Это главный объект, через который вы будете работать.
|
|
47
|
+
- **Skill**: "Навык" или способность Персоны взаимодействовать с системой. Например, `UseBrowser` для работы с веб-интерфейсом или `UseAPI` для запросов к API.
|
|
48
|
+
- **Ops**: Низкоуровневая, техническая операция (клик, HTTP-запрос). Единственный компонент, который может напрямую использовать `Skill`.
|
|
49
|
+
- **Action**: "Действие", атомарная бизнес-операция, которая может изменять состояние системы. Состоит из последовательности `Ops`.
|
|
50
|
+
- **Fact**: "Факт" о состоянии системы. Действие, которое *не изменяет* состояние, а только запрашивает данные. Также состоит из `Ops`.
|
|
51
|
+
- **Expectation**: "Ожидание", которое проверяет, соответствует ли `Fact` определенному условию (например, `IsEqualTo("some text")`).
|
|
52
|
+
- **Goal**: "Цель", высокоуровневый бизнес-сценарий, объединяющий несколько `Action` и `Fact`.
|
|
53
|
+
|
|
54
|
+
## 2. Стиль написания тестов
|
|
55
|
+
|
|
56
|
+
Фреймворк предлагает единый, пошаговый стиль написания тестов, который легко читать и поддерживать.
|
|
57
|
+
|
|
58
|
+
- **Выполнение действий**: `persona.make(Action(...), Goal(...))`
|
|
59
|
+
- **Получение данных**: `data = persona.get(Fact(...))`
|
|
60
|
+
- **Проверки**: `persona.check(data, Expectation(...))`
|
|
61
|
+
|
|
62
|
+
```python
|
|
63
|
+
# test_login.py
|
|
64
|
+
from persona_dsl.ops.web import NavigateTo, Fill, Click
|
|
65
|
+
from persona_dsl.facts.web import CurrentPath
|
|
66
|
+
from persona_dsl.expectations.generic import IsEqualTo
|
|
67
|
+
from tests.pages.login_page import LoginPage # Пример объекта страницы
|
|
68
|
+
|
|
69
|
+
def test_login_flow(persona):
|
|
70
|
+
login_page = LoginPage()
|
|
71
|
+
|
|
72
|
+
# Действия
|
|
73
|
+
persona.make(
|
|
74
|
+
NavigateTo("/login"),
|
|
75
|
+
Fill(login_page.username_field, "testuser"),
|
|
76
|
+
Fill(login_page.password_field, "password"),
|
|
77
|
+
Click(login_page.submit_button)
|
|
78
|
+
)
|
|
79
|
+
|
|
80
|
+
# Получение факта
|
|
81
|
+
current_path = persona.get(CurrentPath())
|
|
82
|
+
|
|
83
|
+
# Проверка
|
|
84
|
+
persona.check(current_path, IsEqualTo("/dashboard"))
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
## 3. Встроенная функциональность ("Батарейки в комплекте")
|
|
88
|
+
|
|
89
|
+
Ядро поставляется с `pytest-плагином`, который предоставляет полезные фикстуры и автоматизирует рутинные задачи.
|
|
90
|
+
|
|
91
|
+
### 3.1. Фикстуры
|
|
92
|
+
|
|
93
|
+
- `persona`: Главная фикстура. Создает экземпляр `Persona` для теста и автоматически наделяет её нужными навыками.
|
|
94
|
+
- `config`: Загружает конфигурацию из файлов `config/*.yaml` и секреты из `.env.*` в зависимости от окружения (`--env=...`).
|
|
95
|
+
- `testdata`: Удобная фабрика для загрузки тестовых данных из `tests/data/*.{yaml,yml,json}`.
|
|
96
|
+
|
|
97
|
+
### 3.2. Автоматическая интеграция с Allure
|
|
98
|
+
|
|
99
|
+
Вам не нужно вручную создавать шаги в отчете, фреймворк делает это за вас:
|
|
100
|
+
- Каждый вызов `persona.make()`, `persona.get()` и `persona.check()` **автоматически** оборачивается в `allure.step()`.
|
|
101
|
+
- Текст шага генерируется из метода `_get_step_description()`, который вы реализуете в своих компонентах.
|
|
102
|
+
- Результат, полученный `Фактом` (`Fact`), автоматически логируется во вложенном шаге.
|
|
103
|
+
- Навык `UseAPI` по явной настройке (`log_bodies=True`) прикрепляет к отчёту полные тела запросов и ответов.
|
|
104
|
+
|
|
105
|
+
### 3.3. Автоматические артефакты при падении теста
|
|
106
|
+
|
|
107
|
+
При падении любого теста, который использовал браузер, фреймворк автоматически собирает артефакты для отладки и прикладывает их к Allure-отчету:
|
|
108
|
+
- **Скриншот** последней активной страницы.
|
|
109
|
+
- **HTML-код** страницы (`page source`).
|
|
110
|
+
|
|
111
|
+
Оба этих параметра включены по умолчанию. Их можно отключить в файле `config/{env}.yaml` в секции `reporting`:
|
|
112
|
+
|
|
113
|
+
```yaml
|
|
114
|
+
# config/dev.yaml
|
|
115
|
+
reporting:
|
|
116
|
+
screenshot_on_fail: false
|
|
117
|
+
pagesource_on_fail: false
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
### 3.4. Декораторы для тестов
|
|
121
|
+
|
|
122
|
+
Ядро предоставляет удобные декораторы для работы с `pytest`:
|
|
123
|
+
|
|
124
|
+
- `@tag("smoke", "regression")`: Позволяет назначать тестам теги (`pytest-маркеры`).
|
|
125
|
+
- `@data_driven(...)`: Упрощает параметризацию тестов, позволяя загружать тестовые данные из списков или файлов в `tests/data/*.{yaml,yml,json}`.
|
|
126
|
+
- `@parametrize_simple(...)`: Обёртка над `pytest.mark.parametrize` для простых наборов данных.
|
|
127
|
+
|
|
128
|
+
#### Динамические данные в `@data_driven` (SystemVar)
|
|
129
|
+
Вы можете использовать генераторы данных (`SystemVar`) прямо в ваших YAML/JSON файлах для параметризации.
|
|
130
|
+
|
|
131
|
+
Для этого используется специальная JSON-структура:
|
|
132
|
+
```json
|
|
133
|
+
{
|
|
134
|
+
"kind": "system",
|
|
135
|
+
"name": "имя_провайдера",
|
|
136
|
+
"args": { "аргумент": "значение" }
|
|
137
|
+
}
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
**Доступные провайдеры (`name`):**
|
|
141
|
+
- `uuid()`: Детерминированный UUID v4.
|
|
142
|
+
- `randomInt(min, max)`: Случайное целое число.
|
|
143
|
+
- `randomFloat(min, max, precision)`: Случайное число с плавающей точкой.
|
|
144
|
+
- `randomString(length, alphabet?)`: Случайная строка.
|
|
145
|
+
- `now(fmt?, tz?)`: Текущая дата/время.
|
|
146
|
+
- `dateShift(days, fmt?, tz?)`: Дата со сдвигом.
|
|
147
|
+
- `fromEnv(name, default?)`: Значение из переменной окружения.
|
|
148
|
+
- `faker(provider, locale?, ...)`: Данные из библиотеки Faker.
|
|
149
|
+
- `sequence(name, seed?)`: Детерминированная числовая последовательность.
|
|
150
|
+
- `concat(parts: list)`: Склеивает строки.
|
|
151
|
+
- `template(pattern, variables)`: Форматирует строку по шаблону.
|
|
152
|
+
|
|
153
|
+
**Пример (`tests/data/dynamic_users.yaml`):**
|
|
154
|
+
```yaml
|
|
155
|
+
- test_id: "user-1"
|
|
156
|
+
payload:
|
|
157
|
+
username:
|
|
158
|
+
kind: system
|
|
159
|
+
name: randomString
|
|
160
|
+
args: { length: 8 }
|
|
161
|
+
email:
|
|
162
|
+
kind: system
|
|
163
|
+
name: faker
|
|
164
|
+
args: { provider: "email" }
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
Все значения генерируются детерминированно на основе `run_id`, `env` и `variant_id` (`test_id`), что обеспечивает воспроизводимость тестов.
|
|
168
|
+
|
|
169
|
+
## 4. Конфигурация и Декларация (`conftest.py`)
|
|
170
|
+
|
|
171
|
+
Вся настройка фреймворка — декларативная и сосредоточена в `tests/conftest.py`.
|
|
172
|
+
|
|
173
|
+
### 4.1. Декларация в `conftest.py`
|
|
174
|
+
|
|
175
|
+
1. **`class Roles(BaseRole)`**: Enum-класс для объявления всех кастомных ролей (например, `ADMIN`).
|
|
176
|
+
2. **`class Skills(BaseSkill)`**: Класс для объявления всех именованных навыков (например, `REPORTING_API`).
|
|
177
|
+
3. **`PERSONA_SKILLS = [...]`**: Список всех навыков, используемых в проекте, для строгой валидации конфигурации.
|
|
178
|
+
4. **`PERSONA_ROLES = Roles`**: Регистрация ролей для валидации.
|
|
179
|
+
|
|
180
|
+
```python
|
|
181
|
+
# tests/conftest.py
|
|
182
|
+
from persona_dsl import BaseRole, BaseSkill, SkillId
|
|
183
|
+
|
|
184
|
+
class Roles(BaseRole):
|
|
185
|
+
ADMIN = "admin"
|
|
186
|
+
|
|
187
|
+
class Skills(BaseSkill):
|
|
188
|
+
REPORTING_API = (SkillId.API, "reporting")
|
|
189
|
+
|
|
190
|
+
PERSONA_ROLES = Roles
|
|
191
|
+
PERSONA_SKILLS = [
|
|
192
|
+
BaseSkill.BROWSER,
|
|
193
|
+
BaseSkill.API,
|
|
194
|
+
Skills.REPORTING_API,
|
|
195
|
+
]
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
### 4.2. Структура конфигурации
|
|
199
|
+
|
|
200
|
+
- **`config/{env}.yaml`**: Параметры для окружения (URL, настройки headless и т.д.).
|
|
201
|
+
- **`config/auth.yaml`**: Секреты и учетные данные.
|
|
202
|
+
|
|
203
|
+
При запуске плагин автоматически проверяет, что для каждой роли и навыка из `conftest.py` есть соответствующая конфигурация в YAML.
|
|
204
|
+
|
|
205
|
+
## 5. Готовые компоненты (Ops)
|
|
206
|
+
|
|
207
|
+
Ядро `persona-dsl` поставляется с набором готовых `Ops` для всех поддерживаемых `Skill`'ов.
|
|
208
|
+
|
|
209
|
+
- **`persona_dsl.ops.web`**: `NavigateTo`, `Click`, `Fill`, `PressKey`, `ElementText`, `ElementIsVisible`, `PageScreenshot`, `PageAriaSnapshot` и др.
|
|
210
|
+
- **`persona_dsl.ops.api`**: `JsonAs` (для отправки запросов и валидации ответа по Pydantic модели), `SendRequest`.
|
|
211
|
+
- **`persona_dsl.ops.db`**: `FetchOne`, `FetchAll`, `ExecuteSQL`.
|
|
212
|
+
- **`persona_dsl.ops.kafka`**: `SendMessage`, `MessageInTopic`.
|
|
213
|
+
- **`persona_dsl.ops.soap`**: `CallOperation`, `OperationResult`.
|
|
214
|
+
|
|
215
|
+
## 6. Генераторы кода
|
|
216
|
+
|
|
217
|
+
Для ускорения разработки `persona-dsl` включает два генератора:
|
|
218
|
+
|
|
219
|
+
- **`persona-page-gen`**: Интерактивно создает классы `Page` из ARIA-снимка веб-страницы.
|
|
220
|
+
- **`persona-api-gen`**: Генерирует Pydantic-модели и классы `Action`/`Fact` из спецификации OpenAPI.
|
|
221
|
+
|
|
222
|
+
Это позволяет быстро создавать основу для PageObjects и API-клиентов, сокращая рутинную работу.
|
|
@@ -4,8 +4,9 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "persona-dsl"
|
|
7
|
-
version = "26.01.20.
|
|
7
|
+
version = "26.01.20.009"
|
|
8
8
|
description = "DSL для реализации паттерна Screenplay в Python-тестах."
|
|
9
|
+
readme = "README.md"
|
|
9
10
|
requires-python = ">=3.9"
|
|
10
11
|
dependencies = [
|
|
11
12
|
"playwright==1.55.0",
|
|
@@ -0,0 +1,222 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: persona-dsl
|
|
3
|
+
Version: 26.1.20.9
|
|
4
|
+
Summary: DSL для реализации паттерна Screenplay в Python-тестах.
|
|
5
|
+
Requires-Python: >=3.9
|
|
6
|
+
Description-Content-Type: text/markdown
|
|
7
|
+
Requires-Dist: playwright==1.55.0
|
|
8
|
+
Requires-Dist: pytest
|
|
9
|
+
Requires-Dist: pytest-cov
|
|
10
|
+
Requires-Dist: allure-pytest
|
|
11
|
+
Requires-Dist: python-dotenv
|
|
12
|
+
Requires-Dist: pyyaml
|
|
13
|
+
Requires-Dist: pydantic<3,>=2
|
|
14
|
+
Requires-Dist: requests
|
|
15
|
+
Requires-Dist: pyhamcrest
|
|
16
|
+
Requires-Dist: redis
|
|
17
|
+
Requires-Dist: Faker
|
|
18
|
+
Requires-Dist: pillow
|
|
19
|
+
Requires-Dist: zeep
|
|
20
|
+
Requires-Dist: pg8000
|
|
21
|
+
Requires-Dist: oracledb
|
|
22
|
+
Requires-Dist: kafka-python
|
|
23
|
+
Requires-Dist: Unidecode>=1.3
|
|
24
|
+
Requires-Dist: black
|
|
25
|
+
Provides-Extra: dev
|
|
26
|
+
Requires-Dist: black; extra == "dev"
|
|
27
|
+
Requires-Dist: ruff; extra == "dev"
|
|
28
|
+
Requires-Dist: mypy; extra == "dev"
|
|
29
|
+
Requires-Dist: pytest-cov; extra == "dev"
|
|
30
|
+
Requires-Dist: pre-commit; extra == "dev"
|
|
31
|
+
Requires-Dist: types-requests; extra == "dev"
|
|
32
|
+
Requires-Dist: types-PyYAML; extra == "dev"
|
|
33
|
+
Requires-Dist: types-redis; extra == "dev"
|
|
34
|
+
Requires-Dist: pytest-asyncio; extra == "dev"
|
|
35
|
+
Requires-Dist: pytest-timeout; extra == "dev"
|
|
36
|
+
Requires-Dist: pytest-xdist; extra == "dev"
|
|
37
|
+
|
|
38
|
+
# persona-dsl: Руководство пользователя
|
|
39
|
+
|
|
40
|
+
`persona-dsl` — это ядро фреймворка, реализующее легковесную версию паттерна **Screenplay** для написания автотестов на Python. Оно спроектировано так, чтобы дать вам полный контроль над базовыми инструментами (`Playwright`, `Allure`), предоставляя при этом выразительный и читаемый DSL для описания тестов.
|
|
41
|
+
|
|
42
|
+
## 1. Основные концепции
|
|
43
|
+
|
|
44
|
+
В основе фреймворка лежат шесть ключевых компонентов, которые вместе описывают любое взаимодействие с системой.
|
|
45
|
+
|
|
46
|
+
- **Persona**: "Действующее лицо" или актор, который выполняет действия в тесте. Это главный объект, через который вы будете работать.
|
|
47
|
+
- **Skill**: "Навык" или способность Персоны взаимодействовать с системой. Например, `UseBrowser` для работы с веб-интерфейсом или `UseAPI` для запросов к API.
|
|
48
|
+
- **Ops**: Низкоуровневая, техническая операция (клик, HTTP-запрос). Единственный компонент, который может напрямую использовать `Skill`.
|
|
49
|
+
- **Action**: "Действие", атомарная бизнес-операция, которая может изменять состояние системы. Состоит из последовательности `Ops`.
|
|
50
|
+
- **Fact**: "Факт" о состоянии системы. Действие, которое *не изменяет* состояние, а только запрашивает данные. Также состоит из `Ops`.
|
|
51
|
+
- **Expectation**: "Ожидание", которое проверяет, соответствует ли `Fact` определенному условию (например, `IsEqualTo("some text")`).
|
|
52
|
+
- **Goal**: "Цель", высокоуровневый бизнес-сценарий, объединяющий несколько `Action` и `Fact`.
|
|
53
|
+
|
|
54
|
+
## 2. Стиль написания тестов
|
|
55
|
+
|
|
56
|
+
Фреймворк предлагает единый, пошаговый стиль написания тестов, который легко читать и поддерживать.
|
|
57
|
+
|
|
58
|
+
- **Выполнение действий**: `persona.make(Action(...), Goal(...))`
|
|
59
|
+
- **Получение данных**: `data = persona.get(Fact(...))`
|
|
60
|
+
- **Проверки**: `persona.check(data, Expectation(...))`
|
|
61
|
+
|
|
62
|
+
```python
|
|
63
|
+
# test_login.py
|
|
64
|
+
from persona_dsl.ops.web import NavigateTo, Fill, Click
|
|
65
|
+
from persona_dsl.facts.web import CurrentPath
|
|
66
|
+
from persona_dsl.expectations.generic import IsEqualTo
|
|
67
|
+
from tests.pages.login_page import LoginPage # Пример объекта страницы
|
|
68
|
+
|
|
69
|
+
def test_login_flow(persona):
|
|
70
|
+
login_page = LoginPage()
|
|
71
|
+
|
|
72
|
+
# Действия
|
|
73
|
+
persona.make(
|
|
74
|
+
NavigateTo("/login"),
|
|
75
|
+
Fill(login_page.username_field, "testuser"),
|
|
76
|
+
Fill(login_page.password_field, "password"),
|
|
77
|
+
Click(login_page.submit_button)
|
|
78
|
+
)
|
|
79
|
+
|
|
80
|
+
# Получение факта
|
|
81
|
+
current_path = persona.get(CurrentPath())
|
|
82
|
+
|
|
83
|
+
# Проверка
|
|
84
|
+
persona.check(current_path, IsEqualTo("/dashboard"))
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
## 3. Встроенная функциональность ("Батарейки в комплекте")
|
|
88
|
+
|
|
89
|
+
Ядро поставляется с `pytest-плагином`, который предоставляет полезные фикстуры и автоматизирует рутинные задачи.
|
|
90
|
+
|
|
91
|
+
### 3.1. Фикстуры
|
|
92
|
+
|
|
93
|
+
- `persona`: Главная фикстура. Создает экземпляр `Persona` для теста и автоматически наделяет её нужными навыками.
|
|
94
|
+
- `config`: Загружает конфигурацию из файлов `config/*.yaml` и секреты из `.env.*` в зависимости от окружения (`--env=...`).
|
|
95
|
+
- `testdata`: Удобная фабрика для загрузки тестовых данных из `tests/data/*.{yaml,yml,json}`.
|
|
96
|
+
|
|
97
|
+
### 3.2. Автоматическая интеграция с Allure
|
|
98
|
+
|
|
99
|
+
Вам не нужно вручную создавать шаги в отчете, фреймворк делает это за вас:
|
|
100
|
+
- Каждый вызов `persona.make()`, `persona.get()` и `persona.check()` **автоматически** оборачивается в `allure.step()`.
|
|
101
|
+
- Текст шага генерируется из метода `_get_step_description()`, который вы реализуете в своих компонентах.
|
|
102
|
+
- Результат, полученный `Фактом` (`Fact`), автоматически логируется во вложенном шаге.
|
|
103
|
+
- Навык `UseAPI` по явной настройке (`log_bodies=True`) прикрепляет к отчёту полные тела запросов и ответов.
|
|
104
|
+
|
|
105
|
+
### 3.3. Автоматические артефакты при падении теста
|
|
106
|
+
|
|
107
|
+
При падении любого теста, который использовал браузер, фреймворк автоматически собирает артефакты для отладки и прикладывает их к Allure-отчету:
|
|
108
|
+
- **Скриншот** последней активной страницы.
|
|
109
|
+
- **HTML-код** страницы (`page source`).
|
|
110
|
+
|
|
111
|
+
Оба этих параметра включены по умолчанию. Их можно отключить в файле `config/{env}.yaml` в секции `reporting`:
|
|
112
|
+
|
|
113
|
+
```yaml
|
|
114
|
+
# config/dev.yaml
|
|
115
|
+
reporting:
|
|
116
|
+
screenshot_on_fail: false
|
|
117
|
+
pagesource_on_fail: false
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
### 3.4. Декораторы для тестов
|
|
121
|
+
|
|
122
|
+
Ядро предоставляет удобные декораторы для работы с `pytest`:
|
|
123
|
+
|
|
124
|
+
- `@tag("smoke", "regression")`: Позволяет назначать тестам теги (`pytest-маркеры`).
|
|
125
|
+
- `@data_driven(...)`: Упрощает параметризацию тестов, позволяя загружать тестовые данные из списков или файлов в `tests/data/*.{yaml,yml,json}`.
|
|
126
|
+
- `@parametrize_simple(...)`: Обёртка над `pytest.mark.parametrize` для простых наборов данных.
|
|
127
|
+
|
|
128
|
+
#### Динамические данные в `@data_driven` (SystemVar)
|
|
129
|
+
Вы можете использовать генераторы данных (`SystemVar`) прямо в ваших YAML/JSON файлах для параметризации.
|
|
130
|
+
|
|
131
|
+
Для этого используется специальная JSON-структура:
|
|
132
|
+
```json
|
|
133
|
+
{
|
|
134
|
+
"kind": "system",
|
|
135
|
+
"name": "имя_провайдера",
|
|
136
|
+
"args": { "аргумент": "значение" }
|
|
137
|
+
}
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
**Доступные провайдеры (`name`):**
|
|
141
|
+
- `uuid()`: Детерминированный UUID v4.
|
|
142
|
+
- `randomInt(min, max)`: Случайное целое число.
|
|
143
|
+
- `randomFloat(min, max, precision)`: Случайное число с плавающей точкой.
|
|
144
|
+
- `randomString(length, alphabet?)`: Случайная строка.
|
|
145
|
+
- `now(fmt?, tz?)`: Текущая дата/время.
|
|
146
|
+
- `dateShift(days, fmt?, tz?)`: Дата со сдвигом.
|
|
147
|
+
- `fromEnv(name, default?)`: Значение из переменной окружения.
|
|
148
|
+
- `faker(provider, locale?, ...)`: Данные из библиотеки Faker.
|
|
149
|
+
- `sequence(name, seed?)`: Детерминированная числовая последовательность.
|
|
150
|
+
- `concat(parts: list)`: Склеивает строки.
|
|
151
|
+
- `template(pattern, variables)`: Форматирует строку по шаблону.
|
|
152
|
+
|
|
153
|
+
**Пример (`tests/data/dynamic_users.yaml`):**
|
|
154
|
+
```yaml
|
|
155
|
+
- test_id: "user-1"
|
|
156
|
+
payload:
|
|
157
|
+
username:
|
|
158
|
+
kind: system
|
|
159
|
+
name: randomString
|
|
160
|
+
args: { length: 8 }
|
|
161
|
+
email:
|
|
162
|
+
kind: system
|
|
163
|
+
name: faker
|
|
164
|
+
args: { provider: "email" }
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
Все значения генерируются детерминированно на основе `run_id`, `env` и `variant_id` (`test_id`), что обеспечивает воспроизводимость тестов.
|
|
168
|
+
|
|
169
|
+
## 4. Конфигурация и Декларация (`conftest.py`)
|
|
170
|
+
|
|
171
|
+
Вся настройка фреймворка — декларативная и сосредоточена в `tests/conftest.py`.
|
|
172
|
+
|
|
173
|
+
### 4.1. Декларация в `conftest.py`
|
|
174
|
+
|
|
175
|
+
1. **`class Roles(BaseRole)`**: Enum-класс для объявления всех кастомных ролей (например, `ADMIN`).
|
|
176
|
+
2. **`class Skills(BaseSkill)`**: Класс для объявления всех именованных навыков (например, `REPORTING_API`).
|
|
177
|
+
3. **`PERSONA_SKILLS = [...]`**: Список всех навыков, используемых в проекте, для строгой валидации конфигурации.
|
|
178
|
+
4. **`PERSONA_ROLES = Roles`**: Регистрация ролей для валидации.
|
|
179
|
+
|
|
180
|
+
```python
|
|
181
|
+
# tests/conftest.py
|
|
182
|
+
from persona_dsl import BaseRole, BaseSkill, SkillId
|
|
183
|
+
|
|
184
|
+
class Roles(BaseRole):
|
|
185
|
+
ADMIN = "admin"
|
|
186
|
+
|
|
187
|
+
class Skills(BaseSkill):
|
|
188
|
+
REPORTING_API = (SkillId.API, "reporting")
|
|
189
|
+
|
|
190
|
+
PERSONA_ROLES = Roles
|
|
191
|
+
PERSONA_SKILLS = [
|
|
192
|
+
BaseSkill.BROWSER,
|
|
193
|
+
BaseSkill.API,
|
|
194
|
+
Skills.REPORTING_API,
|
|
195
|
+
]
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
### 4.2. Структура конфигурации
|
|
199
|
+
|
|
200
|
+
- **`config/{env}.yaml`**: Параметры для окружения (URL, настройки headless и т.д.).
|
|
201
|
+
- **`config/auth.yaml`**: Секреты и учетные данные.
|
|
202
|
+
|
|
203
|
+
При запуске плагин автоматически проверяет, что для каждой роли и навыка из `conftest.py` есть соответствующая конфигурация в YAML.
|
|
204
|
+
|
|
205
|
+
## 5. Готовые компоненты (Ops)
|
|
206
|
+
|
|
207
|
+
Ядро `persona-dsl` поставляется с набором готовых `Ops` для всех поддерживаемых `Skill`'ов.
|
|
208
|
+
|
|
209
|
+
- **`persona_dsl.ops.web`**: `NavigateTo`, `Click`, `Fill`, `PressKey`, `ElementText`, `ElementIsVisible`, `PageScreenshot`, `PageAriaSnapshot` и др.
|
|
210
|
+
- **`persona_dsl.ops.api`**: `JsonAs` (для отправки запросов и валидации ответа по Pydantic модели), `SendRequest`.
|
|
211
|
+
- **`persona_dsl.ops.db`**: `FetchOne`, `FetchAll`, `ExecuteSQL`.
|
|
212
|
+
- **`persona_dsl.ops.kafka`**: `SendMessage`, `MessageInTopic`.
|
|
213
|
+
- **`persona_dsl.ops.soap`**: `CallOperation`, `OperationResult`.
|
|
214
|
+
|
|
215
|
+
## 6. Генераторы кода
|
|
216
|
+
|
|
217
|
+
Для ускорения разработки `persona-dsl` включает два генератора:
|
|
218
|
+
|
|
219
|
+
- **`persona-page-gen`**: Интерактивно создает классы `Page` из ARIA-снимка веб-страницы.
|
|
220
|
+
- **`persona-api-gen`**: Генерирует Pydantic-модели и классы `Action`/`Fact` из спецификации OpenAPI.
|
|
221
|
+
|
|
222
|
+
Это позволяет быстро создавать основу для PageObjects и API-клиентов, сокращая рутинную работу.
|
persona_dsl-26.1.20.8/PKG-INFO
DELETED
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
Metadata-Version: 2.4
|
|
2
|
-
Name: persona-dsl
|
|
3
|
-
Version: 26.1.20.8
|
|
4
|
-
Summary: DSL для реализации паттерна Screenplay в Python-тестах.
|
|
5
|
-
Requires-Python: >=3.9
|
|
6
|
-
Requires-Dist: playwright==1.55.0
|
|
7
|
-
Requires-Dist: pytest
|
|
8
|
-
Requires-Dist: pytest-cov
|
|
9
|
-
Requires-Dist: allure-pytest
|
|
10
|
-
Requires-Dist: python-dotenv
|
|
11
|
-
Requires-Dist: pyyaml
|
|
12
|
-
Requires-Dist: pydantic<3,>=2
|
|
13
|
-
Requires-Dist: requests
|
|
14
|
-
Requires-Dist: pyhamcrest
|
|
15
|
-
Requires-Dist: redis
|
|
16
|
-
Requires-Dist: Faker
|
|
17
|
-
Requires-Dist: pillow
|
|
18
|
-
Requires-Dist: zeep
|
|
19
|
-
Requires-Dist: pg8000
|
|
20
|
-
Requires-Dist: oracledb
|
|
21
|
-
Requires-Dist: kafka-python
|
|
22
|
-
Requires-Dist: Unidecode>=1.3
|
|
23
|
-
Requires-Dist: black
|
|
24
|
-
Provides-Extra: dev
|
|
25
|
-
Requires-Dist: black; extra == "dev"
|
|
26
|
-
Requires-Dist: ruff; extra == "dev"
|
|
27
|
-
Requires-Dist: mypy; extra == "dev"
|
|
28
|
-
Requires-Dist: pytest-cov; extra == "dev"
|
|
29
|
-
Requires-Dist: pre-commit; extra == "dev"
|
|
30
|
-
Requires-Dist: types-requests; extra == "dev"
|
|
31
|
-
Requires-Dist: types-PyYAML; extra == "dev"
|
|
32
|
-
Requires-Dist: types-redis; extra == "dev"
|
|
33
|
-
Requires-Dist: pytest-asyncio; extra == "dev"
|
|
34
|
-
Requires-Dist: pytest-timeout; extra == "dev"
|
|
35
|
-
Requires-Dist: pytest-xdist; extra == "dev"
|
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
Metadata-Version: 2.4
|
|
2
|
-
Name: persona-dsl
|
|
3
|
-
Version: 26.1.20.8
|
|
4
|
-
Summary: DSL для реализации паттерна Screenplay в Python-тестах.
|
|
5
|
-
Requires-Python: >=3.9
|
|
6
|
-
Requires-Dist: playwright==1.55.0
|
|
7
|
-
Requires-Dist: pytest
|
|
8
|
-
Requires-Dist: pytest-cov
|
|
9
|
-
Requires-Dist: allure-pytest
|
|
10
|
-
Requires-Dist: python-dotenv
|
|
11
|
-
Requires-Dist: pyyaml
|
|
12
|
-
Requires-Dist: pydantic<3,>=2
|
|
13
|
-
Requires-Dist: requests
|
|
14
|
-
Requires-Dist: pyhamcrest
|
|
15
|
-
Requires-Dist: redis
|
|
16
|
-
Requires-Dist: Faker
|
|
17
|
-
Requires-Dist: pillow
|
|
18
|
-
Requires-Dist: zeep
|
|
19
|
-
Requires-Dist: pg8000
|
|
20
|
-
Requires-Dist: oracledb
|
|
21
|
-
Requires-Dist: kafka-python
|
|
22
|
-
Requires-Dist: Unidecode>=1.3
|
|
23
|
-
Requires-Dist: black
|
|
24
|
-
Provides-Extra: dev
|
|
25
|
-
Requires-Dist: black; extra == "dev"
|
|
26
|
-
Requires-Dist: ruff; extra == "dev"
|
|
27
|
-
Requires-Dist: mypy; extra == "dev"
|
|
28
|
-
Requires-Dist: pytest-cov; extra == "dev"
|
|
29
|
-
Requires-Dist: pre-commit; extra == "dev"
|
|
30
|
-
Requires-Dist: types-requests; extra == "dev"
|
|
31
|
-
Requires-Dist: types-PyYAML; extra == "dev"
|
|
32
|
-
Requires-Dist: types-redis; extra == "dev"
|
|
33
|
-
Requires-Dist: pytest-asyncio; extra == "dev"
|
|
34
|
-
Requires-Dist: pytest-timeout; extra == "dev"
|
|
35
|
-
Requires-Dist: pytest-xdist; extra == "dev"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/has_entries.py
RENAMED
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/is_equal.py
RENAMED
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/generic/path_equal.py
RENAMED
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/__init__.py
RENAMED
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/expectations/web/is_displayed.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/generators/page_generator.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/kafka/message_in_topic.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/soap/operation_result.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/element_attribute.py
RENAMED
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/element_is_visible.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/generate_page_object.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/rich_aria_snapshot.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/ops/web/wait_for_navigation.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/runtime/dist/persona_bundle.js
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl/skills/core/skill_definition.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{persona_dsl-26.1.20.8 → persona_dsl-26.1.20.9}/src/persona_dsl.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|