├── .idea ├── auto_test.iml ├── deployment.xml ├── inspectionProfiles │ └── profiles_settings.xml ├── misc.xml ├── modules.xml ├── vcs.xml └── workspace.xml ├── README.md ├── __pycache__ └── manage.cpython-37.pyc ├── apps ├── __init__.py ├── __pycache__ │ └── __init__.cpython-37.pyc ├── api_test │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-37.pyc │ │ ├── admin.cpython-37.pyc │ │ ├── apps.cpython-37.pyc │ │ ├── models.cpython-37.pyc │ │ ├── performance2.cpython-37.pyc │ │ ├── urls.cpython-37.pyc │ │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ │ ├── 0001_initial.py │ │ ├── 0002_apis.py │ │ ├── 0003_auto_20200417_0906.py │ │ ├── 0004_auto_20200417_0936.py │ │ ├── __init__.py │ │ └── __pycache__ │ │ │ ├── 0001_initial.cpython-37.pyc │ │ │ ├── 0002_apis.cpython-37.pyc │ │ │ ├── 0003_auto_20200417_0906.cpython-37.pyc │ │ │ ├── 0004_auto_20200417_0936.cpython-37.pyc │ │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── performance2.py │ ├── templates │ │ ├── api_step_manage.html │ │ ├── api_test_manage.html │ │ ├── apis_manage.html │ │ ├── home.html │ │ ├── left.html │ │ ├── login.html │ │ ├── report.html │ │ ├── report_example.html │ │ └── welcome.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── app_test │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-37.pyc │ │ ├── admin.cpython-37.pyc │ │ ├── apps.cpython-37.pyc │ │ ├── models.cpython-37.pyc │ │ ├── urls.cpython-37.pyc │ │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ │ ├── 0001_initial.py │ │ ├── 0002_auto_20200417_0936.py │ │ ├── __init__.py │ │ └── __pycache__ │ │ │ ├── 0001_initial.cpython-37.pyc │ │ │ ├── 0002_auto_20200417_0936.cpython-37.pyc │ │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── templates │ │ ├── app_case_manage.html │ │ └── app_case_step_manage.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── bug │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-37.pyc │ │ ├── admin.cpython-37.pyc │ │ ├── models.cpython-37.pyc │ │ ├── urls.cpython-37.pyc │ │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ │ ├── 0001_initial.py │ │ ├── 0002_auto_20200416_1400.py │ │ ├── __init__.py │ │ └── __pycache__ │ │ │ ├── 0001_initial.cpython-37.pyc │ │ │ ├── 0002_auto_20200416_1400.cpython-37.pyc │ │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── templates │ │ └── bug_manage.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── product │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-37.pyc │ │ ├── admin.cpython-37.pyc │ │ ├── apps.cpython-37.pyc │ │ ├── models.cpython-37.pyc │ │ ├── urls.cpython-37.pyc │ │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ │ ├── 0001_initial.py │ │ ├── __init__.py │ │ └── __pycache__ │ │ │ ├── 0001_initial.cpython-37.pyc │ │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── templates │ │ └── product_manage.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── set │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-37.pyc │ │ ├── admin.cpython-37.pyc │ │ ├── apps.cpython-37.pyc │ │ ├── models.cpython-37.pyc │ │ ├── urls.cpython-37.pyc │ │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ │ ├── 0001_initial.py │ │ ├── __init__.py │ │ └── __pycache__ │ │ │ ├── 0001_initial.cpython-37.pyc │ │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── templates │ │ ├── set_manage.html │ │ └── set_user.html │ ├── tests.py │ ├── urls.py │ └── views.py └── web_test │ ├── __init__.py │ ├── __pycache__ │ ├── __init__.cpython-37.pyc │ ├── admin.cpython-37.pyc │ ├── apps.cpython-37.pyc │ ├── models.cpython-37.pyc │ ├── urls.cpython-37.pyc │ └── views.cpython-37.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ ├── 0001_initial.py │ ├── __init__.py │ └── __pycache__ │ │ ├── 0001_initial.cpython-37.pyc │ │ └── __init__.cpython-37.pyc │ ├── models.py │ ├── templates │ ├── web_case_manage.html │ └── web_case_step_manage.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── auto_test ├── __init__.py ├── __pycache__ │ ├── __init__.cpython-37.pyc │ ├── settings.cpython-37.pyc │ ├── urls.cpython-37.pyc │ └── wsgi.cpython-37.pyc ├── settings.py ├── urls.py └── wsgi.py ├── auto_test01.sql ├── manage.py ├── requirements.txt ├── static ├── admin │ ├── css │ │ ├── autocomplete.css │ │ ├── base.css │ │ ├── changelists.css │ │ ├── dashboard.css │ │ ├── fonts.css │ │ ├── forms.css │ │ ├── login.css │ │ ├── responsive.css │ │ ├── responsive_rtl.css │ │ ├── rtl.css │ │ ├── vendor │ │ │ └── select2 │ │ │ │ ├── LICENSE-SELECT2.md │ │ │ │ ├── select2.css │ │ │ │ └── select2.min.css │ │ └── widgets.css │ ├── fonts │ │ ├── LICENSE.txt │ │ ├── README.txt │ │ ├── Roboto-Bold-webfont.woff │ │ ├── Roboto-Light-webfont.woff │ │ └── Roboto-Regular-webfont.woff │ ├── img │ │ ├── LICENSE │ │ ├── README.txt │ │ ├── calendar-icons.svg │ │ ├── gis │ │ │ ├── move_vertex_off.svg │ │ │ └── move_vertex_on.svg │ │ ├── icon-addlink.svg │ │ ├── icon-alert.svg │ │ ├── icon-calendar.svg │ │ ├── icon-changelink.svg │ │ ├── icon-clock.svg │ │ ├── icon-deletelink.svg │ │ ├── icon-no.svg │ │ ├── icon-unknown-alt.svg │ │ ├── icon-unknown.svg │ │ ├── icon-yes.svg │ │ ├── inline-delete.svg │ │ ├── search.svg │ │ ├── selector-icons.svg │ │ ├── sorting-icons.svg │ │ ├── tooltag-add.svg │ │ └── tooltag-arrowright.svg │ └── js │ │ ├── SelectBox.js │ │ ├── SelectFilter2.js │ │ ├── actions.js │ │ ├── actions.min.js │ │ ├── admin │ │ ├── DateTimeShortcuts.js │ │ └── RelatedObjectLookups.js │ │ ├── autocomplete.js │ │ ├── calendar.js │ │ ├── cancel.js │ │ ├── change_form.js │ │ ├── collapse.js │ │ ├── collapse.min.js │ │ ├── core.js │ │ ├── inlines.js │ │ ├── inlines.min.js │ │ ├── jquery.init.js │ │ ├── popup_response.js │ │ ├── prepopulate.js │ │ ├── prepopulate.min.js │ │ ├── prepopulate_init.js │ │ ├── timeparse.js │ │ ├── urlify.js │ │ └── vendor │ │ ├── jquery │ │ ├── LICENSE-JQUERY.txt │ │ ├── jquery.js │ │ └── jquery.min.js │ │ ├── select2 │ │ ├── LICENSE-SELECT2.md │ │ ├── i18n │ │ │ ├── ar.js │ │ │ ├── az.js │ │ │ ├── bg.js │ │ │ ├── ca.js │ │ │ ├── cs.js │ │ │ ├── da.js │ │ │ ├── de.js │ │ │ ├── el.js │ │ │ ├── en.js │ │ │ ├── es.js │ │ │ ├── et.js │ │ │ ├── eu.js │ │ │ ├── fa.js │ │ │ ├── fi.js │ │ │ ├── fr.js │ │ │ ├── gl.js │ │ │ ├── he.js │ │ │ ├── hi.js │ │ │ ├── hr.js │ │ │ ├── hu.js │ │ │ ├── id.js │ │ │ ├── is.js │ │ │ ├── it.js │ │ │ ├── ja.js │ │ │ ├── km.js │ │ │ ├── ko.js │ │ │ ├── lt.js │ │ │ ├── lv.js │ │ │ ├── mk.js │ │ │ ├── ms.js │ │ │ ├── nb.js │ │ │ ├── nl.js │ │ │ ├── pl.js │ │ │ ├── pt-BR.js │ │ │ ├── pt.js │ │ │ ├── ro.js │ │ │ ├── ru.js │ │ │ ├── sk.js │ │ │ ├── sr-Cyrl.js │ │ │ ├── sr.js │ │ │ ├── sv.js │ │ │ ├── th.js │ │ │ ├── tr.js │ │ │ ├── uk.js │ │ │ ├── vi.js │ │ │ ├── zh-CN.js │ │ │ └── zh-TW.js │ │ ├── select2.full.js │ │ └── select2.full.min.js │ │ └── xregexp │ │ ├── LICENSE-XREGEXP.txt │ │ ├── xregexp.js │ │ └── xregexp.min.js ├── css │ ├── base.css │ ├── bootstrap.min.css │ └── login.css ├── fonts │ ├── glyphicons-halflings-regular.eot │ ├── glyphicons-halflings-regular.svg │ ├── glyphicons-halflings-regular.ttf │ ├── glyphicons-halflings-regular.woff │ └── glyphicons-halflings-regular.woff2 ├── git_images │ ├── 01.png │ ├── 02.png │ ├── 03.png │ ├── 04.png │ ├── 05.png │ ├── 06.png │ ├── 07.png │ ├── 08.png │ ├── 09.png │ └── 10.png └── js │ ├── bootstrap.min.js │ └── jquery.min.js └── templates ├── base.html └── step_base.html /.idea/auto_test.iml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 27 | 28 | -------------------------------------------------------------------------------- /.idea/deployment.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /.idea/inspectionProfiles/profiles_settings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 6 | -------------------------------------------------------------------------------- /.idea/misc.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | -------------------------------------------------------------------------------- /.idea/modules.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /.idea/vcs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | #### [附图 Word 版本](https://shimo.im/docs/PD8qwKwVJk8TWDQg/ 《Django 自动化测试平台》,可复制链接后用石墨文档 App 打开) 2 | 3 | #### [视频演示](https://www.bilibili.com/video/BV1354y1X7fD/) 4 | 5 | #### 平台介绍 6 | 7 | > 支持 `API、AppUI、WebUI` 等自动化测试,集成实现测试用例管理、产品管理、任务计划、测试报告、定时任务或持续集成等功能模块。使自动化测试的过程达到数据、脚本、任务分离易于维护和管理,成本更低、数据更直观、产出更快等目标。 8 | > 9 | > - 当前已完成:用户可以按步骤,通过前端页面输入控件定位元素,以及对控件的操作动作,完成对产品、`Api` 接口、`App` 测试、`Web` 测试的用例管理以及 `bug` 管理 10 | 11 | #### 待优化改进 12 | 13 | > - 根据实际公司业务,结合 `PO` 模型,使用 `selenium` + `unittest` 框架,开发自动化测试脚本 14 | > - 测试报告模块及其邮件通知模块的优化 15 | > - 持续集成 16 | > - 数据存储优化:缓存--`Redis` 17 | 18 | #### 整体开发架构 19 | 20 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/01.png) 21 | 22 | #### 启动配置 23 | 24 | > - 运行终端,切换到相应的项目目录下,输入命令:`pip install -r requirements.txt`,安装所需的插件与库 25 | > 26 | > - 配置 `settings.py` 文件中的参数,包括数据库,静态文件路径,语言等 27 | > - 导入 `auto_test01.sql` 数据到 `MySQL` 中 28 | > - 运行项目,在浏览器输入 `http://127.0.0.1:8000/login`,用户名为 `admin`,密码为 `test123qwe`。 29 | 30 | 31 | 32 | **利用 `Django` 自带的 `admin` 后台管理,完成各模块的版面** 33 | 34 | > - 产品管理 35 | > 36 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/02.png) 37 | 38 | > - 流程场景接口 39 | > 40 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/03.png) 41 | 42 | > - 单一场景接口 43 | > 44 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/04.png) 45 | 46 | > - Bug 管理 47 | > 48 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/05.png) 49 | 50 | > - 系统设置 51 | > 52 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/06.png) 53 | 54 | > - `App` 测试用例管理 55 | > 56 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/07.png) 57 | 58 | > - Web 测试用例管理 59 | > 60 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/08.png) 61 | 62 | > - 搜索功能实现 63 | > 64 | > ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/09.png) 65 | 66 | > - 性能测试 67 | > 68 | > - `Locust` :一个开源负载测试工具。使用 Python 代码定义用户行为,也可以仿真百万个用户。是完全基于时间的,因此单个机器支持几千个并发用户。相比其他许多事件驱动的应用,Locust 不使用回调,而是使用轻量级的处理方式 [gevent](http://www.oschina.net/p/gevent)。 69 | > 70 | > - 安装方法:`pip install locust`;`pip install pyzmp` 71 | > 72 | > - 使用: 73 | > 74 | > 1. 编写脚本文件: 75 | > 76 | > ```python 77 | > from locust import HttpLocust, TaskSet, task 78 | > 79 | > 80 | > class WebsiteTasks(TaskSet): 81 | > @task 82 | > def login(self): 83 | > self.client.post("/test", { 84 | > "username": "admin", 85 | > "password": "test123qwe" 86 | > }) 87 | > 88 | > 89 | > class WebsiteUser(HttpLocust): 90 | > task_set = WebsiteTasks 91 | > min_wait = 100 92 | > max_wait = 1000 93 | > ``` 94 | > 95 | > - 在脚本文件的路径下,进入终端,输入 Locust 启动命令:`locust -f (脚本文件名称) --host=( IP 地址)`;例如:`locust -f performance.py --host=http://127.0.0.1` 96 | > 97 | > - 在浏览器中输入 `localhost:8089`,进行访问 98 | > 99 | > - 输入虚拟并发用户数,每秒增加用户数,点击开始即可,结果如下图所示 100 | > 101 | > - ![image](https://github.com/Leofighting/Django_auto_test_platform_V2/blob/master/static/git_images/10.png) 102 | 103 | 104 | 105 | -------------------------------------------------------------------------------- /__pycache__/manage.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/__pycache__/manage.cpython-37.pyc -------------------------------------------------------------------------------- /apps/__init__.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" -------------------------------------------------------------------------------- /apps/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__init__.py: -------------------------------------------------------------------------------- 1 | default_app_config = "apps.api_test.apps.ApiTestConfig" 2 | -------------------------------------------------------------------------------- /apps/api_test/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/apps.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/apps.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/performance2.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/performance2.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | from apps.api_test.models import ApiTest, ApiStep, Apis 3 | 4 | 5 | class ApiStepAdmin(admin.TabularInline): 6 | list_display = ["api_name", "api_url", "api_param_value", "api_method", 7 | "api_result", "api_status", "create_time", "id", "api_test"] 8 | model = ApiStep 9 | extra = 1 10 | 11 | 12 | class ApisAdmin(admin.TabularInline): 13 | list_display = ["api_name", "api_url", "api_param_value", "api_method", 14 | "api_result", "api_status", "create_time", "id", "product"] 15 | 16 | 17 | class ApisAdmin1(admin.ModelAdmin): 18 | list_display = ["api_name", "api_url", "api_param_value", "api_method", 19 | "api_result", "api_status", "create_time", "id", "product"] 20 | 21 | 22 | class ApiTestAdmin(admin.ModelAdmin): 23 | list_display = ["api_test_name", "api_tester", "api_test_result", "create_time", "id"] 24 | inlines = [ApiStepAdmin] 25 | 26 | 27 | admin.site.register(ApiTest, ApiTestAdmin) 28 | admin.site.register(Apis, ApisAdmin1) 29 | -------------------------------------------------------------------------------- /apps/api_test/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class ApiTestConfig(AppConfig): 5 | name = 'apps.api_test' 6 | verbose_name = "接口测试" 7 | -------------------------------------------------------------------------------- /apps/api_test/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-15 06:40 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | initial = True 10 | 11 | dependencies = [ 12 | ('product', '0001_initial'), 13 | ] 14 | 15 | operations = [ 16 | migrations.CreateModel( 17 | name='ApiStep', 18 | fields=[ 19 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 20 | ('api_name', models.CharField(max_length=100, verbose_name='接口名称')), 21 | ('api_url', models.CharField(max_length=200, verbose_name='url地址')), 22 | ('api_step', models.CharField(max_length=100, null=True, verbose_name='测试步骤')), 23 | ('api_param_value', models.CharField(max_length=800, verbose_name='请求参数和值')), 24 | ('api_method', models.CharField(choices=[('get', 'get'), ('post', 'post'), ('put', 'put'), ('delete', 'delete'), ('patch', 'patch')], default='get', max_length=200, null=True, verbose_name='请求方法')), 25 | ('api_result', models.CharField(max_length=200, verbose_name='预期结果')), 26 | ('api_status', models.BooleanField(verbose_name='是否通过')), 27 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 28 | ], 29 | ), 30 | migrations.CreateModel( 31 | name='ApiTest', 32 | fields=[ 33 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 34 | ('api_test_name', models.CharField(max_length=64, verbose_name='流程接口名称')), 35 | ('api_test_desc', models.CharField(max_length=200, null=True, verbose_name='描述')), 36 | ('api_tester', models.CharField(max_length=64, verbose_name='测试负责人')), 37 | ('api_test_result', models.BooleanField(verbose_name='测试结果')), 38 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 39 | ('product', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='product.Product', verbose_name='产品名称')), 40 | ], 41 | options={ 42 | 'verbose_name': '流程场景接口', 43 | 'verbose_name_plural': '流程场景接口', 44 | 'ordering': ['id'], 45 | }, 46 | ), 47 | migrations.AddField( 48 | model_name='apistep', 49 | name='api_test', 50 | field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='api_test.ApiTest'), 51 | ), 52 | ] 53 | -------------------------------------------------------------------------------- /apps/api_test/migrations/0002_apis.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-16 02:22 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | dependencies = [ 10 | ('product', '0001_initial'), 11 | ('api_test', '0001_initial'), 12 | ] 13 | 14 | operations = [ 15 | migrations.CreateModel( 16 | name='Apis', 17 | fields=[ 18 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 19 | ('api_name', models.CharField(max_length=100, verbose_name='接口名称')), 20 | ('api_url', models.CharField(max_length=200, verbose_name='url 地址')), 21 | ('api_param_value', models.CharField(max_length=800, verbose_name='请求参数和值')), 22 | ('api_method', models.CharField(choices=[('0', 'get'), ('1', 'post'), ('2', 'put'), ('3', 'delete'), ('4', 'patch')], default='0', max_length=10, verbose_name='请求方法')), 23 | ('api_result', models.CharField(max_length=200, verbose_name='预期结果')), 24 | ('api_status', models.BooleanField(verbose_name='是否通过')), 25 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 26 | ('product', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='product.Product')), 27 | ], 28 | options={ 29 | 'verbose_name': '单一场景接口', 30 | 'verbose_name_plural': '单一场景接口', 31 | }, 32 | ), 33 | ] 34 | -------------------------------------------------------------------------------- /apps/api_test/migrations/0003_auto_20200417_0906.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-17 01:06 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | dependencies = [ 10 | ('api_test', '0002_apis'), 11 | ] 12 | 13 | operations = [ 14 | migrations.AlterField( 15 | model_name='apistep', 16 | name='api_test', 17 | field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='api_step', to='api_test.ApiTest'), 18 | ), 19 | ] 20 | -------------------------------------------------------------------------------- /apps/api_test/migrations/0004_auto_20200417_0936.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-17 01:36 2 | 3 | from django.db import migrations 4 | 5 | 6 | class Migration(migrations.Migration): 7 | 8 | dependencies = [ 9 | ('api_test', '0003_auto_20200417_0906'), 10 | ] 11 | 12 | operations = [ 13 | migrations.AlterModelOptions( 14 | name='apistep', 15 | options={'ordering': ['id']}, 16 | ), 17 | ] 18 | -------------------------------------------------------------------------------- /apps/api_test/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__init__.py -------------------------------------------------------------------------------- /apps/api_test/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/migrations/__pycache__/0002_apis.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__pycache__/0002_apis.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/migrations/__pycache__/0003_auto_20200417_0906.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__pycache__/0003_auto_20200417_0906.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/migrations/__pycache__/0004_auto_20200417_0936.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__pycache__/0004_auto_20200417_0936.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/api_test/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/api_test/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | from apps.product.models import Product 4 | 5 | 6 | class ApiTest(models.Model): 7 | """api测试""" 8 | product = models.ForeignKey("product.Product", on_delete=models.CASCADE, null=True, verbose_name="产品名称") 9 | api_test_name = models.CharField("流程接口名称", max_length=64) 10 | api_test_desc = models.CharField("描述", max_length=200, null=True) 11 | api_tester = models.CharField("测试负责人", max_length=64) 12 | api_test_result = models.BooleanField("测试结果") 13 | create_time = models.DateTimeField("创建时间", auto_now=True) 14 | 15 | class Meta: 16 | verbose_name = "流程场景接口" 17 | verbose_name_plural = verbose_name 18 | ordering = ["id"] 19 | 20 | def __str__(self): 21 | return self.api_test_name 22 | 23 | 24 | class ApiStep(models.Model): 25 | """测试步骤""" 26 | REQUEST_METHOD = (("get", "get"), ("post", "post"), ("put", "put"), ("delete", "delete"), ("patch", "patch")) 27 | 28 | api_test = models.ForeignKey("ApiTest", on_delete=models.CASCADE, related_name="api_step") 29 | api_step = models.CharField("测试步骤", max_length=100, null=True) 30 | api_name = models.CharField("接口名称", max_length=100) 31 | api_url = models.CharField("url地址", max_length=200) 32 | api_param_value = models.CharField("请求参数和值", max_length=800) 33 | api_method = models.CharField("请求方法", choices=REQUEST_METHOD, default="get", max_length=200, null=True) 34 | api_result = models.CharField("预期结果", max_length=200) 35 | api_status = models.BooleanField("是否通过") 36 | create_time = models.DateTimeField("创建时间", auto_now=True) 37 | 38 | class Meta: 39 | ordering = ["id"] 40 | 41 | def __str__(self): 42 | return self.api_name 43 | 44 | 45 | class Apis(models.Model): 46 | """单一接口测试""" 47 | REQUEST_METHOD = (("0", "get"), ("1", "post"), ("2", "put"), ("3", "delete"), ("4", "patch")) 48 | product = models.ForeignKey("product.Product", on_delete=models.CASCADE, null=True) 49 | api_name = models.CharField("接口名称", max_length=100) 50 | api_url = models.CharField("url 地址", max_length=200) 51 | api_param_value = models.CharField("请求参数和值", max_length=800) 52 | api_method = models.CharField("请求方法", choices=REQUEST_METHOD, default="0", max_length=10) 53 | api_result = models.CharField("预期结果", max_length=200) 54 | api_status = models.BooleanField("是否通过") 55 | create_time = models.DateTimeField("创建时间", auto_now=True) 56 | 57 | class Meta: 58 | verbose_name = "单一场景接口" 59 | verbose_name_plural = verbose_name 60 | ordering = ["id"] 61 | 62 | def __str__(self): 63 | return self.api_name 64 | -------------------------------------------------------------------------------- /apps/api_test/performance2.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from locust import HttpLocust, TaskSet, task 5 | 6 | 7 | class WebsiteTasks(TaskSet): 8 | @task 9 | def login(self): 10 | self.client.post("/test", { 11 | "username": "admin", 12 | "password": "test123qwe" 13 | }) 14 | 15 | 16 | class WebsiteUser(HttpLocust): 17 | task_set = WebsiteTasks 18 | min_wait = 100 19 | max_wait = 1000 20 | -------------------------------------------------------------------------------- /apps/api_test/templates/api_step_manage.html: -------------------------------------------------------------------------------- 1 | {% extends 'step_base.html' %} 2 | 3 | {% block title %} 4 | Api 测试步骤 5 | {% endblock %} 6 | 7 | {% block main %} 8 |
9 | 10 |
11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | {% for apistep in api_steps %} 27 | 28 | {% if apistep.api_test.id == api_test.id %} 29 | 30 | 31 | 32 | 33 | 34 | 35 | 42 | 43 | {% endif %} 44 | 45 | {% endfor %} 46 | 47 |
ID接口名称接口名称参数值方法预期结果测试结果时间
{{ apistep.id }}{{ apistep.api_name }}{{ apistep.api_url }}{{ apistep.api_param_value }}{{ apistep.api_method }}{{ apistep.api_result }} 36 | {% if apistep.api_status == 1 %} 37 | {{ apistep.api_status }} 38 | {% else %} 39 | {{ apistep.api_status }} 40 | {% endif %} 41 | {{ apistep.create_time }}
48 |
49 |
50 | 51 | 52 |
53 | 54 | 55 | 返回返回 56 | 57 | 58 | 59 | 60 | 62 | 编辑 63 | 64 |
65 | 66 | 67 | {# 把翻页功能固定显示在右下角#} 68 |
69 |
    70 | {# 上一页链接开始#} 71 | {% if api_steps.has_previous %} 72 | {# 如果有上一页则正常显示上一页的链接#} 73 | {# 上一页标签 #} 75 | {% else %} 76 | {# 如果当前不存在上一页则上一页的链接不可单击#} 77 | {% endif %} 78 | {# 上一页链接开始#} 79 | 80 | {% for num in api_steps.paginator.page_range %} 81 | 82 | {% if num == current_page %} 83 |
  • {{ num }}
  • 84 | {#显示当前页数链接#} 85 | {% else %} 86 |
  • {{ num }}
  • 87 | {% endif %} 88 | {% endfor %} 89 | 90 | {# 下一页链接开始#} 91 | {% if api_steps.has_next %} {# 如果有下一页,则正常显示下一页的链接#} 92 | 94 | {% else %} 95 | 96 | {% endif %} 97 | {# 下一页链接结束#} 98 |
99 |
100 |
101 |
102 | {% endblock %} 103 | -------------------------------------------------------------------------------- /apps/api_test/templates/home.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 自动化测试平台 6 | 7 | 8 | 9 | {# #} 10 | 11 | 12 | 13 | <body> 14 | </body> 15 | 16 | -------------------------------------------------------------------------------- /apps/api_test/templates/left.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {% load bootstrap4 %} 4 | {% bootstrap_css %} 5 | {% bootstrap_javascript %} 6 | 7 | 8 | 9 | autotestplat 10 | 11 | 12 | 15 |
16 | 17 | 18 | 19 |
  • 20 | 21 | 22 | 产品中心 23 | 24 |
  • 25 | 26 | 27 | 28 | 29 |   30 | 31 | 32 | 33 |
  • 34 | 35 | 36 | 用例管理 37 | 38 |
  • 39 | 40 | 41 | 42 | 43 | 44 |   45 | 46 | 47 | 48 |
  • 49 | 50 | 51 | 定时任务 52 | 53 |
  • 54 | 55 | 56 | 57 | 58 |   59 | 60 | 61 | 62 | 63 |
  • 64 | 65 | 66 | bug 管理 67 | 68 |
  • 69 | 70 | 71 | 72 | 73 |   74 | 75 | 76 | 77 |
  • 78 | 79 | 80 | 测试报告 81 | 82 |
  • 83 | 84 | 85 | 86 | 87 |   88 | 89 | 90 | 91 | 92 |
  • 93 | 94 | 95 | 系统设置 96 | 97 |
  • 98 | 99 | 100 | 101 | 102 |   103 | 104 | 105 | 106 |
  • 107 | 108 | 109 | 性能测试 110 | 111 |
  • 112 | 113 | 114 | 115 |   116 | 117 | 118 |
    119 | 120 | 121 | -------------------------------------------------------------------------------- /apps/api_test/templates/login.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | AutotestPlat 7 | 8 | 9 | 10 |
    11 | 12 |

    自动化平台测试开发

    13 | 14 |
    15 | {% csrf_token %} 16 |
      用户名: 17 |

      密    码: 18 |
    {{ error }}
    19 |   20 | 21 |
    22 |
    23 | 29 | 30 | -------------------------------------------------------------------------------- /apps/api_test/templates/welcome.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {% load bootstrap4 %} 4 | {% bootstrap_css %} 5 | {% bootstrap_javascript %} 6 | autotestplat-自动化平台测试开发 7 | 8 | 11 | 12 | 13 | 14 | 25 |
    26 |
    27 | 28 |

    欢迎您,来到 autotestplat V1.0

    29 |
    30 |
    31 |
    32 |
    33 |
    34 | 35 | 单击进入测试报告 36 | 37 |
    38 |
    39 | 40 | -------------------------------------------------------------------------------- /apps/api_test/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/api_test/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.api_test import views 7 | 8 | urlpatterns = [ 9 | path("test_manage/", views.api_test_manage, name="api_test_manage"), 10 | path("step_manage/", views.api_step_manage, name="api_step_manage"), 11 | path("apis_manage/", views.apis_manage, name="apis_manage"), 12 | path("apis_search/", views.apis_search, name="apis_search"), 13 | path("api_search/", views.api_search, name="api_search"), 14 | ] 15 | -------------------------------------------------------------------------------- /apps/app_test/__init__.py: -------------------------------------------------------------------------------- 1 | default_app_config = "apps.app_test.apps.AppTestConfig" 2 | -------------------------------------------------------------------------------- /apps/app_test/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/__pycache__/apps.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/apps.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | from apps.app_test.models import AppCaseStep, AppCase 4 | 5 | 6 | class AppCaseStepAdmin(admin.TabularInline): 7 | list_display = [ 8 | "app_test_step", "app_test_obj_name", "app_find_method", 9 | "app_element", "app_opt_method", "app_assert_data", 10 | "app_test_result", "create_time", "id", "app_case" 11 | ] 12 | 13 | model = AppCaseStep 14 | extra = 1 15 | 16 | 17 | class AppCaseAdmin(admin.ModelAdmin): 18 | list_display = [ 19 | "app_case_name", "app_test_result", "create_time", "id" 20 | ] 21 | inlines = [AppCaseStepAdmin] 22 | 23 | 24 | admin.site.register(AppCase, AppCaseAdmin) 25 | -------------------------------------------------------------------------------- /apps/app_test/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class AppTestConfig(AppConfig): 5 | name = 'apps.app_test' 6 | verbose_name = "App 测试" 7 | -------------------------------------------------------------------------------- /apps/app_test/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-16 06:28 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | initial = True 10 | 11 | dependencies = [ 12 | ('product', '0001_initial'), 13 | ] 14 | 15 | operations = [ 16 | migrations.CreateModel( 17 | name='AppCase', 18 | fields=[ 19 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 20 | ('app_case_name', models.CharField(max_length=64, verbose_name='用例名称')), 21 | ('app_test_result', models.BooleanField(verbose_name='测试结果')), 22 | ('app_tester', models.CharField(max_length=24, verbose_name='测试负责人')), 23 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 24 | ('product', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='product.Product')), 25 | ], 26 | options={ 27 | 'verbose_name': 'app 测试用例', 28 | 'verbose_name_plural': 'app 测试用例', 29 | }, 30 | ), 31 | migrations.CreateModel( 32 | name='AppCaseStep', 33 | fields=[ 34 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 35 | ('app_test_step', models.CharField(max_length=255, verbose_name='测试步骤')), 36 | ('app_test_obj_name', models.CharField(max_length=200, verbose_name='测试对象名称描述')), 37 | ('app_find_method', models.CharField(max_length=200, verbose_name='定位方式')), 38 | ('app_element', models.CharField(max_length=800, verbose_name='控件元素')), 39 | ('app_opt_method', models.CharField(max_length=200, verbose_name='操作方法')), 40 | ('app_test_data', models.CharField(max_length=200, null=True, verbose_name='测试数据')), 41 | ('app_assert_data', models.CharField(max_length=200, verbose_name='验证数据')), 42 | ('app_test_result', models.BooleanField(verbose_name='测试结果')), 43 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 44 | ('app_case', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='app_test.AppCase')), 45 | ], 46 | ), 47 | ] 48 | -------------------------------------------------------------------------------- /apps/app_test/migrations/0002_auto_20200417_0936.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-17 01:36 2 | 3 | from django.db import migrations 4 | 5 | 6 | class Migration(migrations.Migration): 7 | 8 | dependencies = [ 9 | ('app_test', '0001_initial'), 10 | ] 11 | 12 | operations = [ 13 | migrations.AlterModelOptions( 14 | name='appcasestep', 15 | options={'ordering': ['id']}, 16 | ), 17 | ] 18 | -------------------------------------------------------------------------------- /apps/app_test/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/migrations/__init__.py -------------------------------------------------------------------------------- /apps/app_test/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/migrations/__pycache__/0002_auto_20200417_0936.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/migrations/__pycache__/0002_auto_20200417_0936.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/app_test/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/app_test/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | 4 | class AppCase(models.Model): 5 | """APP 用例管理""" 6 | product = models.ForeignKey("product.Product", on_delete=models.CASCADE, null=True) 7 | app_case_name = models.CharField("用例名称", max_length=64) 8 | app_test_result = models.BooleanField("测试结果") 9 | app_tester = models.CharField("测试负责人", max_length=24) 10 | create_time = models.DateTimeField("创建时间", auto_now=True) 11 | 12 | class Meta: 13 | verbose_name = "app 测试用例" 14 | verbose_name_plural = verbose_name 15 | ordering = ["id"] 16 | 17 | def __str__(self): 18 | return self.app_case_name 19 | 20 | 21 | class AppCaseStep(models.Model): 22 | """APP 用例测试步骤""" 23 | app_case = models.ForeignKey("AppCase", on_delete=models.CASCADE) 24 | app_test_step = models.CharField("测试步骤", max_length=255) 25 | app_test_obj_name = models.CharField("测试对象名称描述", max_length=200) 26 | app_find_method = models.CharField("定位方式", max_length=200) 27 | app_element = models.CharField("控件元素", max_length=800) 28 | app_opt_method = models.CharField("操作方法", max_length=200) 29 | app_test_data = models.CharField("测试数据", max_length=200, null=True) 30 | app_assert_data = models.CharField("验证数据", max_length=200) 31 | app_test_result = models.BooleanField("测试结果") 32 | create_time = models.DateTimeField("创建时间", auto_now=True) 33 | 34 | class Meta: 35 | ordering = ["id"] 36 | 37 | def __str__(self): 38 | return self.app_test_step 39 | -------------------------------------------------------------------------------- /apps/app_test/templates/app_case_step_manage.html: -------------------------------------------------------------------------------- 1 | {% extends 'step_base.html' %} 2 | 3 | {% block title %} 4 | App 测试步骤 5 | {% endblock %} 6 | 7 | {% block main %} 8 |
    9 | 10 | 11 |
    12 |
    13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | {% for appcasestep in app_case_steps %} 30 | 31 | {% if appcasestep.app_case.id == app_case.id %} 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 46 | 47 | {% endif %} 48 | 49 | {% endfor %} 50 | 51 |
    所属产品所属用例步骤定位方式控件元素操作方法测试数据验证数据测试结果时间
    {{ appcasestep.app_case.product.product_name }}case{{ appcasestep.app_case.id }}:{{ appcasestep.app_case.app_case_name }}{{ appcasestep.app_test_step }}:{{ appcasestep.app_test_obj_name }}{{ appcasestep.app_find_method }}{{ appcasestep.app_element }}{{ appcasestep.app_opt_method }}{{ appcasestep.app_test_data }}{{ appcasestep.app_assert_data }}{% if appcasestep.app_test_result == 1 %} 41 | {{ appcasestep.app_test_result }} 42 | {% else %} 43 | {{ appcasestep.app_test_result }} 44 | {% endif %} 45 | {{ appcasestep.create_time }}
    52 |
    53 |
    54 | 55 | 56 |
    57 | 58 | 59 | 返回返回 60 | 61 | 62 | 63 | 65 | 编辑 66 | 67 |
    68 | 69 | 70 | {# 把翻页功能固定显示在右下角#} 71 |
    72 |
      73 | {# 上一页链接开始#} 74 | {% if appcasesteps.has_previous %} 75 | {# 如果有上一页,则正常显示上一页的链接#} 76 | 78 | {# 上一页标签 #} 79 | {% else %} 80 | {# 如果当前不存在上一页,则上一页的链接不可单击#} 81 | {% endif %} 82 | {# 上一页链接开始#} 83 | 84 | {% for num in appcasesteps.paginator.page_range %} 85 | 86 | {% if num == current_page %} 87 |
    • {{ num }}
    • {#显示当前页数链接#} 89 | {% else %} 90 |
    • {{ num }}
    • 91 | {% endif %} 92 | {% endfor %} 93 | 94 | {# 下一页链接开始#} 95 | {% if appcasesteps.has_next %} {# 如果有下一页,则正常显示下一页的链接#} 96 | 98 | {% else %} 99 | 100 | {% endif %} 101 | {# 下一页链接结束#} 102 |
    103 |
    104 |
    105 |
    106 | {% endblock %} -------------------------------------------------------------------------------- /apps/app_test/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/app_test/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.app_test import views 7 | 8 | urlpatterns = [ 9 | path("app_mange/", views.app_case_manage, name="app_case_manage"), 10 | path("app_step/", views.app_case_step_manage, name="app_case_step_manage"), 11 | path("app_search/", views.app_search, name="app_search"), 12 | ] 13 | -------------------------------------------------------------------------------- /apps/app_test/views.py: -------------------------------------------------------------------------------- 1 | from django.contrib.auth.decorators import login_required 2 | from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage 3 | from django.shortcuts import render 4 | 5 | from apps.app_test.models import AppCase, AppCaseStep 6 | 7 | 8 | @login_required 9 | def app_case_manage(request): 10 | """ 11 | app 用例管理 12 | :param request: 13 | :return: 跳转到app用例管理页面 14 | """ 15 | app_case_list = AppCase.objects.all() 16 | app_case_count = app_case_list.count() 17 | username = request.session.get("user", "") 18 | paginator = Paginator(app_case_list, 5) 19 | page = request.GET.get("page", 1) 20 | current_page = int(page) 21 | try: 22 | app_case_list = paginator.page(current_page) 23 | except PageNotAnInteger: 24 | app_case_list = paginator.page(1) 25 | except EmptyPage: 26 | app_case_list = paginator.page(paginator.num_pages) 27 | return render(request, "app_case_manage.html", { 28 | "user": username, 29 | "app_cases": app_case_list, 30 | "app_case_counts": app_case_count 31 | }) 32 | 33 | 34 | @login_required 35 | def app_case_step_manage(request): 36 | """APP 测试用例步骤管理""" 37 | username = request.session.get("user", "") 38 | app_case_step_list = AppCaseStep.objects.all() 39 | app_case_id = request.GET.get("app_case.id", None) 40 | app_case = AppCase.objects.get(id=app_case_id) 41 | paginator = Paginator(app_case_step_list, 5) 42 | page = request.GET.get("page", 1) 43 | current_page = int(page) 44 | try: 45 | app_case_step_list = paginator.page(current_page) 46 | except PageNotAnInteger: 47 | app_case_step_list = paginator.page(1) 48 | except EmptyPage: 49 | app_case_step_list = paginator.page(paginator.num_pages) 50 | return render(request, "app_case_step_manage.html", { 51 | "user": username, 52 | "app_case_steps": app_case_step_list, 53 | "app_case": app_case 54 | }) 55 | 56 | 57 | @login_required 58 | def app_search(request): 59 | """app 测试搜索""" 60 | username = request.session.get("user", "") 61 | search_app_case_name = request.GET.get("app_case_name", "") 62 | app_case_list = AppCase.objects.filter(app_case_name__icontains=search_app_case_name) 63 | return render(request, "app_case_manage.html", { 64 | "user": username, 65 | "app_cases": app_case_list 66 | }) 67 | -------------------------------------------------------------------------------- /apps/bug/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__init__.py -------------------------------------------------------------------------------- /apps/bug/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | from apps.bug.models import Bug 4 | 5 | 6 | class BugAdmin(admin.ModelAdmin): 7 | list_display = ["bug_name", "bug_detail", "bug_status", "bug_level", 8 | "bug_creat", "bug_assign", "create_time", "id"] 9 | 10 | 11 | admin.site.register(Bug, BugAdmin) 12 | -------------------------------------------------------------------------------- /apps/bug/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class BugConfig(AppConfig): 5 | name = 'apps.bug' 6 | -------------------------------------------------------------------------------- /apps/bug/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-16 02:46 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | initial = True 10 | 11 | dependencies = [ 12 | ('product', '0001_initial'), 13 | ] 14 | 15 | operations = [ 16 | migrations.CreateModel( 17 | name='Bug', 18 | fields=[ 19 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 20 | ('bug_name', models.CharField(max_length=64, verbose_name='bug 名称')), 21 | ('bug_detail', models.CharField(max_length=200, verbose_name='bug 详情')), 22 | ('bug_status', models.CharField(choices=[('激活', '激活'), ('已解决', '已解决'), ('已关闭', '已关闭')], default='激活', max_length=200, null=True, verbose_name='解决状态')), 23 | ('bug_level', models.CharField(choices=[('1', '1'), ('2', '2'), ('3', '3')], default='3', max_length=10, null=True, verbose_name='严重程度')), 24 | ('bug_creat', models.CharField(max_length=32, verbose_name='创建人')), 25 | ('bug_assign', models.CharField(max_length=32, verbose_name='分配给')), 26 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 27 | ('product', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='product.Product')), 28 | ], 29 | options={ 30 | 'verbose_name': 'bug 管理', 31 | 'verbose_name_plural': 'bug 管理', 32 | }, 33 | ), 34 | ] 35 | -------------------------------------------------------------------------------- /apps/bug/migrations/0002_auto_20200416_1400.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-16 06:00 2 | 3 | from django.db import migrations 4 | 5 | 6 | class Migration(migrations.Migration): 7 | 8 | dependencies = [ 9 | ('bug', '0001_initial'), 10 | ] 11 | 12 | operations = [ 13 | migrations.AlterModelOptions( 14 | name='bug', 15 | options={'ordering': ['id'], 'verbose_name': 'bug 管理', 'verbose_name_plural': 'bug 管理'}, 16 | ), 17 | ] 18 | -------------------------------------------------------------------------------- /apps/bug/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/migrations/__init__.py -------------------------------------------------------------------------------- /apps/bug/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/migrations/__pycache__/0002_auto_20200416_1400.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/migrations/__pycache__/0002_auto_20200416_1400.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/bug/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/bug/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | from apps.product.models import Product 4 | 5 | 6 | class Bug(models.Model): 7 | """bug""" 8 | BUG_STATUS = (("激活", "激活"), ("已解决", "已解决"), ("已关闭", "已关闭")) 9 | BUG_LEVEL = (("1", "1"), ("2", "2"), ("3", "3")) 10 | 11 | product = models.ForeignKey("product.Product", on_delete=models.CASCADE, null=True) 12 | bug_name = models.CharField("bug 名称", max_length=64) 13 | bug_detail = models.CharField("bug 详情", max_length=200) 14 | bug_status = models.CharField("解决状态", choices=BUG_STATUS, default="激活", max_length=200, null=True) 15 | bug_level = models.CharField("严重程度", choices=BUG_LEVEL, default="3", max_length=10, null=True) 16 | bug_creat = models.CharField("创建人", max_length=32) 17 | bug_assign = models.CharField("分配给", max_length=32) 18 | create_time = models.DateTimeField("创建时间", auto_now=True) 19 | 20 | class Meta: 21 | verbose_name = "bug 管理" 22 | verbose_name_plural = verbose_name 23 | ordering = ["id"] 24 | 25 | def __str__(self): 26 | return self.bug_name 27 | -------------------------------------------------------------------------------- /apps/bug/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/bug/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.bug import views 7 | 8 | urlpatterns = [ 9 | path("bug_manage/", views.bug_manage, name="bug_manage"), 10 | path("bug_search/", views.bug_search, name="bug_search"), 11 | ] 12 | -------------------------------------------------------------------------------- /apps/bug/views.py: -------------------------------------------------------------------------------- 1 | from django.contrib.auth.decorators import login_required 2 | from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage 3 | from django.shortcuts import render 4 | 5 | from apps.bug.models import Bug 6 | 7 | 8 | def bug_manage(request): 9 | """ 10 | bug 管理 11 | :param request: 12 | :return: 跳转到 bug 管理页面 13 | """ 14 | username = request.session.get("user", "") 15 | bug_list = Bug.objects.all() 16 | bug_count = bug_list.count() 17 | paginator = Paginator(bug_list, 5) 18 | page = request.GET.get("page", 1) 19 | current_page = int(page) 20 | try: 21 | bug_list = paginator.page(current_page) 22 | except PageNotAnInteger: 23 | bug_list = paginator.page(1) 24 | except EmptyPage: 25 | bug_list = paginator.page(paginator.num_pages) 26 | return render(request, "bug_manage.html", { 27 | "user": username, 28 | "bugs": bug_list, 29 | "bug_counts": bug_count 30 | }) 31 | 32 | 33 | @login_required 34 | def bug_search(request): 35 | """bug 搜索""" 36 | username = request.session.get("user", "") 37 | search_bug_name = request.GET.get("bug_name", "") 38 | bug_list = Bug.objects.filter(bug_name__icontains=search_bug_name) 39 | return render(request, "bug_manage.html", { 40 | "user": username, 41 | "bugs": bug_list 42 | }) 43 | -------------------------------------------------------------------------------- /apps/product/__init__.py: -------------------------------------------------------------------------------- 1 | default_app_config = "apps.product.apps.ProductConfig" 2 | -------------------------------------------------------------------------------- /apps/product/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/__pycache__/apps.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/apps.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | from apps.api_test.models import Apis 4 | from apps.app_test.models import AppCase 5 | from apps.product.models import Product 6 | from apps.web_test.models import WebCase 7 | 8 | 9 | class ApisAdmin(admin.TabularInline): 10 | list_display = ["api_name", "api_url", "api_param_value", "api_method", 11 | "api_result", "api_status", "create_time", "id", "product"] 12 | 13 | model = Apis 14 | extra = 1 15 | 16 | 17 | class AppCaseAdmin(admin.TabularInline): 18 | list_display = ["app_case_name", "app_test_result", "create_time", "product"] 19 | model = AppCase 20 | extra = 1 21 | 22 | 23 | class WebCaseAdmin(admin.TabularInline): 24 | list_display = [ 25 | "web_case_name", "web_test_result", "create_time", "id", "product" 26 | ] 27 | model = WebCase 28 | extra = 1 29 | 30 | 31 | class ProductAdmin(admin.ModelAdmin): 32 | list_display = ["product_name", "product_desc", "product_owner", "create_time", "id"] 33 | inlines = [ApisAdmin, AppCaseAdmin, WebCaseAdmin] 34 | 35 | 36 | admin.site.register(Product, ProductAdmin) 37 | -------------------------------------------------------------------------------- /apps/product/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class ProductConfig(AppConfig): 5 | name = 'apps.product' 6 | verbose_name = "产品" 7 | -------------------------------------------------------------------------------- /apps/product/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-15 06:08 2 | 3 | from django.db import migrations, models 4 | 5 | 6 | class Migration(migrations.Migration): 7 | 8 | initial = True 9 | 10 | dependencies = [ 11 | ] 12 | 13 | operations = [ 14 | migrations.CreateModel( 15 | name='Product', 16 | fields=[ 17 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 18 | ('product_name', models.CharField(max_length=64, verbose_name='产品名称')), 19 | ('product_desc', models.CharField(max_length=200, verbose_name='产品描述')), 20 | ('product_owner', models.CharField(max_length=200, verbose_name='产品负责人')), 21 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 22 | ], 23 | options={ 24 | 'verbose_name': '产品管理', 25 | 'verbose_name_plural': '产品管理', 26 | 'ordering': ['id'], 27 | }, 28 | ), 29 | ] 30 | -------------------------------------------------------------------------------- /apps/product/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/migrations/__init__.py -------------------------------------------------------------------------------- /apps/product/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/product/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/product/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | 4 | class Product(models.Model): 5 | """产品""" 6 | product_name = models.CharField("产品名称", max_length=64) 7 | product_desc = models.CharField("产品描述", max_length=200) 8 | product_owner = models.CharField("产品负责人", max_length=200) 9 | create_time = models.DateTimeField("创建时间", auto_now=True) 10 | 11 | class Meta: 12 | verbose_name = "产品管理" 13 | verbose_name_plural = verbose_name 14 | ordering = ["id"] 15 | 16 | def __str__(self): 17 | return self.product_name 18 | -------------------------------------------------------------------------------- /apps/product/templates/product_manage.html: -------------------------------------------------------------------------------- 1 | {% extends "base.html" %} 2 | 3 | {% block title %} 4 | 产品管理 5 | {% endblock %} 6 | 7 | {% block main %} 8 |
    9 | 10 | 17 | 18 | 19 |
    20 | 23 | 25 | 修改 26 | 27 | 29 | 增加增加 30 | 31 |
    32 | 33 | 34 |
    35 |
    36 | 37 | 38 | {% comment %} 39 | 40 | {% endcomment %} 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | {% for product in products %} 53 | 54 | 55 | 56 | 57 | 58 | 59 | 64 | 69 | 70 | 71 | {% endfor %} 72 | 73 |
     
    ID产品名称产品描述产品负责人创建时间编辑删除
    {{ product.id }}{{ product.product_name }}{{ product.product_desc }}{{ product.product_owner }}{{ product.create_time }} 63 | 68 |
    74 |
    75 |
    76 | 77 | {# 把翻页功能固定显示在右下角#} 78 |
    79 | 总数{{ product_counts }} {# 前端读取定义的变量#} 80 |
    81 |
    82 |
      83 | {# 上一页链接开始#} 84 | {% if products.has_previous %} 85 | {# 如果有上一页则正常显示上一页的链接#} 86 | {# 上一页标签 #} 88 | {% else %} 89 | {# 如果当前不存在上一页则上一页的链接不可单击#} 90 | {% endif %} 91 | {# 上一页链接开始#} 92 | 93 | {% for num in products.paginator.page_range %} 94 | 95 | {% if num == current_page %} 96 |
    • {{ num }}
    • 97 | {#显示当页数链接#} 98 | {% else %} 99 |
    • {{ num }}
    • 100 | {% endif %} 101 | {% endfor %} 102 | 103 | {# 下一页链接开始#} 104 | {% if products.has_next %} {# 如果有下一页,则正常显示下一页的链接#} 105 | 107 | {% else %} 108 | 109 | {% endif %} 110 | {# 下一页链接结束#} 111 |
    112 |
    113 |
    114 |
    115 | {% endblock %} -------------------------------------------------------------------------------- /apps/product/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/product/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.product import views 7 | 8 | urlpatterns = [ 9 | path("manage/", views.product_manage, name="product_manage"), 10 | path("product_search/", views.product_search, name="product_search"), 11 | ] 12 | -------------------------------------------------------------------------------- /apps/product/views.py: -------------------------------------------------------------------------------- 1 | from django.contrib.auth.decorators import login_required 2 | from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage 3 | from django.shortcuts import render 4 | 5 | from apps.product.models import Product 6 | 7 | 8 | def product_manage(request): 9 | """ 10 | 产品管理 11 | :param request: 12 | :return: 跳转到产品管理页面 13 | """ 14 | username = request.session.get("user", "") 15 | product_list = Product.objects.all() 16 | product_count = product_list.count() 17 | paginator = Paginator(product_list, 5) 18 | page = request.GET.get("page", 1) 19 | current_page = int(page) 20 | try: 21 | product_list = paginator.page(current_page) 22 | except PageNotAnInteger: 23 | product_list = paginator.page(1) 24 | except EmptyPage: 25 | product_list = paginator.page(paginator.num_pages) 26 | return render(request, "product_manage.html", { 27 | "user": username, 28 | "products": product_list, 29 | "product_counts": product_count 30 | }) 31 | 32 | 33 | @login_required 34 | def product_search(request): 35 | """ 36 | 产品搜索 37 | :param request: 38 | :return: 按产品名搜索, 输出符合搜索条件的产品管理页面 39 | """ 40 | username = request.session.get("user", "") 41 | search_product_name = request.GET.get("product_name", "") 42 | product_list = Product.objects.filter(product_name__icontains=search_product_name) 43 | return render(request, "product_manage.html", { 44 | "user": username, 45 | "products": product_list 46 | }) 47 | -------------------------------------------------------------------------------- /apps/set/__init__.py: -------------------------------------------------------------------------------- 1 | default_app_config = "apps.set.apps.SetConfig" 2 | -------------------------------------------------------------------------------- /apps/set/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/__pycache__/apps.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/apps.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | from apps.set.models import Set 4 | 5 | 6 | class SetAdmin(admin.ModelAdmin): 7 | list_display = ["set_name", "set_value", "id"] 8 | 9 | 10 | admin.site.register(Set, SetAdmin) 11 | -------------------------------------------------------------------------------- /apps/set/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class SetConfig(AppConfig): 5 | name = 'apps.set' 6 | verbose_name = "设置" 7 | -------------------------------------------------------------------------------- /apps/set/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-16 06:00 2 | 3 | from django.db import migrations, models 4 | 5 | 6 | class Migration(migrations.Migration): 7 | 8 | initial = True 9 | 10 | dependencies = [ 11 | ] 12 | 13 | operations = [ 14 | migrations.CreateModel( 15 | name='Set', 16 | fields=[ 17 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 18 | ('set_name', models.CharField(max_length=64, verbose_name='系统名称')), 19 | ('set_value', models.CharField(max_length=200, verbose_name='系统设置')), 20 | ], 21 | options={ 22 | 'verbose_name': '系统设置', 23 | 'verbose_name_plural': '系统设置', 24 | }, 25 | ), 26 | ] 27 | -------------------------------------------------------------------------------- /apps/set/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/migrations/__init__.py -------------------------------------------------------------------------------- /apps/set/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/set/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/set/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | 4 | class Set(models.Model): 5 | set_name = models.CharField("系统名称", max_length=64) 6 | set_value = models.CharField("系统设置", max_length=200) 7 | 8 | class Meta: 9 | verbose_name = "系统设置" 10 | verbose_name_plural = verbose_name 11 | 12 | def __str__(self): 13 | return self.set_name 14 | -------------------------------------------------------------------------------- /apps/set/templates/set_manage.html: -------------------------------------------------------------------------------- 1 | {% extends "base.html" %} 2 | 3 | {% block title %} 4 | 设置管理 5 | {% endblock %} 6 | 7 | {% block main %} 8 |
    9 | 10 | 17 | 18 | 19 |
    20 | 23 | 25 | 修改 26 | 27 | 29 | 增加增加 30 | 31 |
    32 | 33 | 34 |
    35 |
    36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | {% for set in sets %} 48 | 49 | 50 | 51 | 52 | 57 | 62 | 63 | {% endfor %} 64 | 65 |
    ID设置名称设置的值编辑删除
    {{ set.id }}{{ set.set_name }}{{ set.set_value }} 56 | 61 |
    66 |
    67 |
    68 | 69 | 70 | {# 把翻页功能固定显示在右下角#} 71 |
    72 |
      73 | {# 上一页链接开始#} 74 | {% if sets.has_previous %} 75 | {# 如果有上一页,则正常显示上一页的链接#} 76 | {# 上一页标签 #} 78 | {% else %} 79 | {# 如果当前不存在上一页,则上一页的链接不可单击#} 80 | {% endif %} 81 | {# 上一页链接开始#} 82 | {% for num in sets.paginator.page_range %} 83 | {% if num == current_page %} 84 |
    • {{ num }}
    • {#显示当前页数链接#} 85 | {% else %} 86 |
    • {{ num }}
    • 87 | {% endif %} 88 | {% endfor %} 89 | 90 | {# 下一页链接开始#} 91 | {% if sets.has_next %} {# 如果有下一页则正常显示下一页的链接#} 92 | 93 | {% else %} 94 | 95 | {% endif %} 96 | {# 下一页链接结束#} 97 |
    98 |
    99 |
    100 |
    101 | {% endblock %} 102 | -------------------------------------------------------------------------------- /apps/set/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/set/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.set import views 7 | 8 | urlpatterns = [ 9 | path("manage/", views.set_manage, name="set_manage"), 10 | path("user/", views.set_user, name="set_user"), 11 | path("set_search/", views.set_search, name="set_search"), 12 | path("user_search/", views.user_search, name="user_search"), 13 | ] 14 | -------------------------------------------------------------------------------- /apps/set/views.py: -------------------------------------------------------------------------------- 1 | from django.contrib.auth.decorators import login_required 2 | from django.contrib.auth.models import User 3 | from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage 4 | from django.shortcuts import render 5 | 6 | from apps.set.models import Set 7 | 8 | 9 | def set_manage(request): 10 | """设置管理""" 11 | username = request.session.get("user", "") 12 | set_list = Set.objects.all() 13 | paginator = Paginator(set_list, 5) 14 | page = request.GET.get("page", 1) 15 | current_page = int(page) 16 | try: 17 | set_list = paginator.page(current_page) 18 | except PageNotAnInteger: 19 | set_list = paginator.page(1) 20 | except EmptyPage: 21 | set_list = paginator.page(paginator.num_pages) 22 | return render(request, "set_manage.html", { 23 | "user": username, 24 | "sets": set_list 25 | }) 26 | 27 | 28 | def set_user(request): 29 | """用户设置""" 30 | user_list = User.objects.all() 31 | username = request.session.get("user", "") 32 | 33 | return render(request, "set_user.html", { 34 | "user": username, 35 | "users": user_list 36 | }) 37 | 38 | 39 | @login_required 40 | def set_search(request): 41 | """设置搜索""" 42 | username = request.session.get("user", "") 43 | search_set_name = request.GET.get("set_name", "") 44 | set_list = Set.objects.filter(set_name__icontains=search_set_name) 45 | return render(request, "set_manage.html", { 46 | "user": username, 47 | "sets": set_list 48 | }) 49 | 50 | 51 | @login_required 52 | def user_search(request): 53 | """用户搜索""" 54 | username = request.session.get("user", "") 55 | search_username = request.GET.get("username", "") 56 | user_list = User.objects.filter(username__icontains=search_username) 57 | return render(request, "set_user.html", { 58 | "user": username, 59 | "users": user_list 60 | }) 61 | -------------------------------------------------------------------------------- /apps/web_test/__init__.py: -------------------------------------------------------------------------------- 1 | default_app_config = "apps.web_test.apps.WebTestConfig" 2 | -------------------------------------------------------------------------------- /apps/web_test/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/__pycache__/admin.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/admin.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/__pycache__/apps.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/apps.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/__pycache__/models.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/models.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/__pycache__/views.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/__pycache__/views.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | from apps.web_test.models import WebCaseStep, WebCase 4 | 5 | 6 | class WebCaseStepAdmin(admin.TabularInline): 7 | list_display = [ 8 | "web_test_step", "web_case_name", "web_test_obj_name", "web_find_method", "web_element", 9 | "web_opt_method", "web_assert_data", "web_test_result", "create_time", "id", "web_case" 10 | ] 11 | model = WebCaseStep 12 | extra = 1 13 | 14 | 15 | class WebCaseAdmin(admin.ModelAdmin): 16 | list_display = ["web_case_name", "web_test_result", "create_time", "id"] 17 | inlines = [WebCaseStepAdmin] 18 | 19 | 20 | admin.site.register(WebCase, WebCaseAdmin) 21 | -------------------------------------------------------------------------------- /apps/web_test/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class WebTestConfig(AppConfig): 5 | name = 'apps.web_test' 6 | verbose_name = "Web 测试" 7 | -------------------------------------------------------------------------------- /apps/web_test/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # Generated by Django 2.0.13 on 2020-04-17 01:36 2 | 3 | from django.db import migrations, models 4 | import django.db.models.deletion 5 | 6 | 7 | class Migration(migrations.Migration): 8 | 9 | initial = True 10 | 11 | dependencies = [ 12 | ('product', '0001_initial'), 13 | ] 14 | 15 | operations = [ 16 | migrations.CreateModel( 17 | name='WebCase', 18 | fields=[ 19 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 20 | ('web_case_name', models.CharField(max_length=64, verbose_name='用例名称')), 21 | ('web_test_result', models.BooleanField(verbose_name='测试结果')), 22 | ('web_tester', models.CharField(max_length=24, verbose_name='测试负责人')), 23 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 24 | ('product', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='product.Product')), 25 | ], 26 | options={ 27 | 'verbose_name': 'web 测试用例', 28 | 'verbose_name_plural': 'web 测试用例', 29 | }, 30 | ), 31 | migrations.CreateModel( 32 | name='WebCaseStep', 33 | fields=[ 34 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 35 | ('web_case_name', models.CharField(max_length=100, verbose_name='测试用例标题')), 36 | ('web_test_step', models.CharField(max_length=255, verbose_name='测试步骤')), 37 | ('web_test_obj_name', models.CharField(max_length=200, verbose_name='测试对象名称描述')), 38 | ('web_find_method', models.CharField(max_length=200, verbose_name='定位方式')), 39 | ('web_element', models.CharField(max_length=800, verbose_name='控件元素')), 40 | ('web_opt_method', models.CharField(max_length=200, verbose_name='操作方法')), 41 | ('web_test_data', models.CharField(max_length=200, null=True, verbose_name='测试数据')), 42 | ('web_assert_data', models.CharField(max_length=200, verbose_name='验证数据')), 43 | ('web_test_result', models.BooleanField(verbose_name='测试结果')), 44 | ('create_time', models.DateTimeField(auto_now=True, verbose_name='创建时间')), 45 | ('web_case', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='web_test.WebCase')), 46 | ], 47 | ), 48 | ] 49 | -------------------------------------------------------------------------------- /apps/web_test/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/migrations/__init__.py -------------------------------------------------------------------------------- /apps/web_test/migrations/__pycache__/0001_initial.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/migrations/__pycache__/0001_initial.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/migrations/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/apps/web_test/migrations/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /apps/web_test/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | 4 | class WebCase(models.Model): 5 | """web 用例管理""" 6 | product = models.ForeignKey("product.Product", on_delete=models.CASCADE, null=True) 7 | web_case_name = models.CharField("用例名称", max_length=64) 8 | web_test_result = models.BooleanField("测试结果") 9 | web_tester = models.CharField("测试负责人", max_length=24) 10 | create_time = models.DateTimeField("创建时间", auto_now=True) 11 | 12 | class Meta: 13 | verbose_name = "web 测试用例" 14 | verbose_name_plural = verbose_name 15 | ordering = ["id"] 16 | 17 | def __str__(self): 18 | return self.web_case_name 19 | 20 | 21 | class WebCaseStep(models.Model): 22 | """web 用例测试步骤""" 23 | web_case = models.ForeignKey("WebCase", on_delete=models.CASCADE) 24 | web_test_step = models.CharField("测试步骤", max_length=255) 25 | web_case_name = models.CharField("测试用例标题", max_length=100) 26 | web_test_obj_name = models.CharField("测试对象名称描述", max_length=200) 27 | web_find_method = models.CharField("定位方式", max_length=200) 28 | web_element = models.CharField("控件元素", max_length=800) 29 | web_opt_method = models.CharField("操作方法", max_length=200) 30 | web_test_data = models.CharField("测试数据", max_length=200, null=True) 31 | web_assert_data = models.CharField("验证数据", max_length=200) 32 | web_test_result = models.BooleanField("测试结果") 33 | create_time = models.DateTimeField("创建时间", auto_now=True) 34 | 35 | def __str__(self): 36 | return self.web_case_name 37 | -------------------------------------------------------------------------------- /apps/web_test/templates/web_case_step_manage.html: -------------------------------------------------------------------------------- 1 | {% extends 'step_base.html' %} 2 | 3 | {% block title %} 4 | Web 测试步骤 5 | {% endblock %} 6 | 7 | {% block main %} 8 |
    9 | 10 |
    11 |
    12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | {% for webcasestep in web_case_steps %} 29 | 30 | {% if webcasestep.web_case.id == web_case.id %} 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | {% endif %} 43 | 44 | {% endfor %} 45 | 46 |
    所属产品所属用例步骤定位方式控件元素操作方法测试数据验证数据测试结果时间
    {{ webcasestep.web_case.product.product_name }}case{{ webcasestep.web_case.id }}:{{ webcasestep.web_case.web_case_name }}{{ webcasestep.web_test_step }}:{{ webcasestep.web_test_obj_name }}{{ webcasestep.web_find_method }}{{ webcasestep.web_element }}{{ webcasestep.web_opt_method }}{{ webcasestep.web_test_data }}{{ webcasestep.web_assert_data }}{{ webcasestep.web_test_result }}{{ webcasestep.create_time }}
    47 |
    48 |
    49 | 50 | 51 |
    52 | 53 | 54 | 返回返回 55 | 56 | 57 | 58 | 60 | 编辑 61 | 62 |
    63 | 64 | 65 | {# 把翻页功能固定显示在右下角#} 66 |
    67 |
      68 | {# 上一页链接开始#} 69 | {% if webcasesteps.has_previous %} 70 | {# 如果有上一页则正常显示上一页的链接#} 71 | {# 上一页标签 #} 73 | {% else %} 74 | {# 如果当前不存在上一页,则上一页的链接不可单击#} 75 | {% endif %} 76 | {# 上一页链接开始#} 77 | 78 | {% for num in webcasesteps.paginator.page_range %} 79 | 80 | {% if num == current_page %} 81 |
    • {{ num }}
    • {#显示当前页数链接#} 83 | {% else %} 84 |
    • {{ num }}
    • 85 | {% endif %} 86 | {% endfor %} 87 | 88 | {# 下一页链接开始#} 89 | {% if webcasesteps.has_next %} {# 如果有下一页,则正常显示下一页链接#} 90 | 92 | {% else %} 93 | 94 | {% endif %} 95 | {# 下一页链接结束#} 96 |
    97 |
    98 |
    99 |
    100 | {% endblock %} -------------------------------------------------------------------------------- /apps/web_test/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /apps/web_test/urls.py: -------------------------------------------------------------------------------- 1 | # -*- coding:utf-8 -*- 2 | __author__ = "leo" 3 | 4 | from django.urls import path 5 | 6 | from apps.web_test import views 7 | 8 | urlpatterns = [ 9 | path("manage/", views.web_case_manage, name="web_case_manage"), 10 | path("step/", views.web_case_step_manage, name="web_case_step_manage"), 11 | path("web_search/", views.web_search, name="web_search"), 12 | ] 13 | -------------------------------------------------------------------------------- /apps/web_test/views.py: -------------------------------------------------------------------------------- 1 | from django.contrib.auth.decorators import login_required 2 | from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage 3 | from django.shortcuts import render 4 | 5 | from apps.web_test.models import WebCase, WebCaseStep 6 | 7 | 8 | @login_required 9 | def web_case_manage(request): 10 | """web 测试用例管理""" 11 | web_case_list = WebCase.objects.all() 12 | web_case_count = web_case_list.count() 13 | username = request.session.get("user", "") 14 | paginator = Paginator(web_case_list, 5) 15 | page = request.GET.get("page", 1) 16 | current_page = int(page) 17 | try: 18 | web_case_list = paginator.page(current_page) 19 | except PageNotAnInteger: 20 | web_case_list = paginator.page(1) 21 | except EmptyPage: 22 | web_case_list = paginator.page(paginator.num_pages) 23 | return render(request, "web_case_manage.html", { 24 | "user": username, 25 | "web_cases": web_case_list, 26 | "web_case_counts": web_case_count, 27 | 28 | }) 29 | 30 | 31 | @login_required 32 | def web_case_step_manage(request): 33 | """web 测试用例步骤管理""" 34 | web_case_step_list = WebCaseStep.objects.all() 35 | username = request.session.get("user", "") 36 | web_case_id = request.GET.get("web_case.id", None) 37 | web_case = WebCase.objects.get(id=web_case_id) 38 | paginator = Paginator(web_case_step_list, 5) 39 | page = request.GET.get("page", 1) 40 | current_page = int(page) 41 | try: 42 | web_case_step_list = paginator.page(current_page) 43 | except PageNotAnInteger: 44 | web_case_step_list = paginator.page(1) 45 | except EmptyPage: 46 | web_case_step_list = paginator.page(paginator.num_pages) 47 | return render(request, "web_case_step_manage.html", { 48 | "user": username, 49 | "web_case_steps": web_case_step_list, 50 | "web_case": web_case 51 | }) 52 | 53 | 54 | @login_required 55 | def web_search(request): 56 | """web测试搜索""" 57 | username = request.session.get("user", "") 58 | search_web_case_name = request.GET.get("web_case_name", "") 59 | web_case_list = WebCase.objects.filter(web_case_name__icontains=search_web_case_name) 60 | return render(request, "web_case_manage.html", { 61 | "user": username, 62 | "web_cases": web_case_list 63 | }) 64 | -------------------------------------------------------------------------------- /auto_test/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/auto_test/__init__.py -------------------------------------------------------------------------------- /auto_test/__pycache__/__init__.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/auto_test/__pycache__/__init__.cpython-37.pyc -------------------------------------------------------------------------------- /auto_test/__pycache__/settings.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/auto_test/__pycache__/settings.cpython-37.pyc -------------------------------------------------------------------------------- /auto_test/__pycache__/urls.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/auto_test/__pycache__/urls.cpython-37.pyc -------------------------------------------------------------------------------- /auto_test/__pycache__/wsgi.cpython-37.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/auto_test/__pycache__/wsgi.cpython-37.pyc -------------------------------------------------------------------------------- /auto_test/settings.py: -------------------------------------------------------------------------------- 1 | """ 2 | Django settings for auto_test project. 3 | 4 | Generated by 'django-admin startproject' using Django 2.0.13. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/2.0/topics/settings/ 8 | 9 | For the full list of settings and their values, see 10 | https://docs.djangoproject.com/en/2.0/ref/settings/ 11 | """ 12 | 13 | import os 14 | 15 | # Build paths inside the project like this: os.path.join(BASE_DIR, ...) 16 | BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 17 | 18 | # Quick-start development settings - unsuitable for production 19 | # See https://docs.djangoproject.com/en/2.0/howto/deployment/checklist/ 20 | 21 | # SECURITY WARNING: keep the secret key used in production secret! 22 | SECRET_KEY = 'g(vh)2rz^nodu2k)6$jy$k0i(m48&zf&y-t#qok5l^muj!oby)' 23 | 24 | # SECURITY WARNING: don't run with debug turned on in production! 25 | DEBUG = True 26 | 27 | ALLOWED_HOSTS = [] 28 | 29 | # Application definition 30 | 31 | INSTALLED_APPS = [ 32 | 'django.contrib.admin', 33 | 'django.contrib.auth', 34 | 'django.contrib.contenttypes', 35 | 'django.contrib.sessions', 36 | 'django.contrib.messages', 37 | 'django.contrib.staticfiles', 38 | "apps.api_test", 39 | "apps.product", 40 | "bootstrap4", 41 | "apps.bug", 42 | "apps.set", 43 | "apps.app_test", 44 | "apps.web_test", 45 | ] 46 | 47 | MIDDLEWARE = [ 48 | 'django.middleware.security.SecurityMiddleware', 49 | 'django.contrib.sessions.middleware.SessionMiddleware', 50 | 'django.middleware.common.CommonMiddleware', 51 | 'django.middleware.csrf.CsrfViewMiddleware', 52 | 'django.contrib.auth.middleware.AuthenticationMiddleware', 53 | 'django.contrib.messages.middleware.MessageMiddleware', 54 | 'django.middleware.clickjacking.XFrameOptionsMiddleware', 55 | ] 56 | 57 | ROOT_URLCONF = 'auto_test.urls' 58 | 59 | TEMPLATES = [ 60 | { 61 | 'BACKEND': 'django.template.backends.django.DjangoTemplates', 62 | 'DIRS': [os.path.join(BASE_DIR, 'templates')] 63 | , 64 | 'APP_DIRS': True, 65 | 'OPTIONS': { 66 | 'context_processors': [ 67 | 'django.template.context_processors.debug', 68 | 'django.template.context_processors.request', 69 | 'django.contrib.auth.context_processors.auth', 70 | 'django.contrib.messages.context_processors.messages', 71 | ], 72 | "builtins": [ 73 | "django.templatetags.static", # 配置 static 标签 74 | ] 75 | }, 76 | }, 77 | ] 78 | 79 | WSGI_APPLICATION = 'auto_test.wsgi.application' 80 | 81 | # Database 82 | # https://docs.djangoproject.com/en/2.0/ref/settings/#databases 83 | 84 | DATABASES = { 85 | 'default': { 86 | 'ENGINE': 'django.db.backends.mysql', # 选择数据库类型 87 | 'NAME': "auto_test01", # 数据库名称 88 | "HOST": "localhost", # IP地址 89 | "PORT": "3306", # 端口号 90 | "USER": "root", # 数据库用户 91 | "PASSWORD": "123456" # 数据库密码 92 | } 93 | } 94 | 95 | # Password validation 96 | # https://docs.djangoproject.com/en/2.0/ref/settings/#auth-password-validators 97 | 98 | AUTH_PASSWORD_VALIDATORS = [ 99 | { 100 | 'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator', 101 | }, 102 | { 103 | 'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator', 104 | }, 105 | { 106 | 'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator', 107 | }, 108 | { 109 | 'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator', 110 | }, 111 | ] 112 | 113 | # Internationalization 114 | # https://docs.djangoproject.com/en/2.0/topics/i18n/ 115 | 116 | LANGUAGE_CODE = 'zh-Hans' 117 | 118 | TIME_ZONE = 'Asia/Shanghai' 119 | 120 | USE_I18N = True 121 | 122 | USE_L10N = True 123 | 124 | USE_TZ = True 125 | 126 | # Static files (CSS, JavaScript, Images) 127 | # https://docs.djangoproject.com/en/2.0/howto/static-files/ 128 | 129 | STATIC_URL = '/static/' 130 | STATICFILES_DIRS = [ 131 | os.path.join(BASE_DIR, "static") 132 | ] 133 | -------------------------------------------------------------------------------- /auto_test/urls.py: -------------------------------------------------------------------------------- 1 | """auto_test URL Configuration 2 | 3 | The `urlpatterns` list routes URLs to views. For more information please see: 4 | https://docs.djangoproject.com/en/2.0/topics/http/urls/ 5 | Examples: 6 | Function views 7 | 1. Add an import: from my_app import views 8 | 2. Add a URL to urlpatterns: path('', views.home, name='home') 9 | Class-based views 10 | 1. Add an import: from other_app.views import Home 11 | 2. Add a URL to urlpatterns: path('', Home.as_view(), name='home') 12 | Including another URLconf 13 | 1. Import the include() function: from django.urls import include, path 14 | 2. Add a URL to urlpatterns: path('blog/', include('blog.urls')) 15 | """ 16 | from django.contrib import admin 17 | from django.urls import path, include 18 | 19 | from apps.api_test import views 20 | 21 | urlpatterns = [ 22 | path("", views.login), 23 | path('admin/', admin.site.urls), 24 | path('login/', views.login, name="login"), 25 | path('logout/', views.logout, name="logout"), 26 | path('home/', views.home, name="home"), 27 | path('welcome/', views.welcome, name="welcome"), 28 | path('left/', views.left, name="left"), 29 | path('test_report/', views.test_report, name="test_report"), 30 | # 产品管理 31 | path("product/", include("apps.product.urls")), 32 | # api 流程接口管理 33 | path("api_test/", include("apps.api_test.urls")), 34 | # bug 管理 35 | path("bug/", include("apps.bug.urls")), 36 | # 设置管理 37 | path("set/", include("apps.set.urls")), 38 | # App 测试管理 39 | path("app_test/", include("apps.app_test.urls")), 40 | # web 测试管理 41 | path("web_test/", include("apps.web_test.urls")), 42 | ] 43 | -------------------------------------------------------------------------------- /auto_test/wsgi.py: -------------------------------------------------------------------------------- 1 | """ 2 | WSGI config for auto_test project. 3 | 4 | It exposes the WSGI callable as a module-level variable named ``application``. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/2.0/howto/deployment/wsgi/ 8 | """ 9 | 10 | import os 11 | 12 | from django.core.wsgi import get_wsgi_application 13 | 14 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "auto_test.settings") 15 | 16 | application = get_wsgi_application() 17 | -------------------------------------------------------------------------------- /manage.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | import os 3 | import sys 4 | 5 | if __name__ == "__main__": 6 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "auto_test.settings") 7 | try: 8 | from django.core.management import execute_from_command_line 9 | except ImportError as exc: 10 | raise ImportError( 11 | "Couldn't import Django. Are you sure it's installed and " 12 | "available on your PYTHONPATH environment variable? Did you " 13 | "forget to activate a virtual environment?" 14 | ) from exc 15 | execute_from_command_line(sys.argv) 16 | -------------------------------------------------------------------------------- /requirements.txt: -------------------------------------------------------------------------------- 1 | amqp==1.4.9 2 | anyjson==0.3.3 3 | atomicwrites==1.3.0 4 | attrs==19.3.0 5 | beautifulsoup4==4.9.0 6 | billiard==3.3.0.23 7 | celery==3.1.26.post2 8 | certifi==2020.4.5.1 9 | cffi==1.14.0 10 | chardet==3.0.4 11 | click==7.1.1 12 | colorama==0.4.3 13 | ConfigArgParse==1.2.1 14 | configparser==5.0.0 15 | Django==2.0.13 16 | django-bootstrap4==1.1.1 17 | django-celery==3.3.1 18 | Flask==1.1.2 19 | gevent==1.5a3 20 | geventhttpclient-wheels==1.3.1.dev2 21 | greenlet==0.4.15 22 | hupper==1.10.2 23 | idna==2.9 24 | importlib-metadata==1.6.0 25 | itsdangerous==1.1.0 26 | Jinja2==2.11.2 27 | kombu==3.0.37 28 | locust==0.0 29 | locustio==0.14.5 30 | MarkupSafe==1.1.1 31 | more-itertools==8.2.0 32 | msgpack==1.0.0 33 | mysqlclient==1.4.6 34 | packaging==20.3 35 | PasteDeploy==2.1.0 36 | plaster==1.0 37 | plaster-pastedeploy==0.7 38 | pluggy==0.13.1 39 | psutil==5.7.0 40 | py==1.8.1 41 | pycparser==2.20 42 | PyMySQL==0.9.3 43 | pyparsing==2.4.7 44 | pyramid==1.10.4 45 | pyramid-celery==3.0.0 46 | pytest==5.4.1 47 | pytest-timeout==1.3.4 48 | pytz==2019.3 49 | pyzmp==0.0.17 50 | pyzmq==19.0.0 51 | requests==2.23.0 52 | six==1.14.0 53 | soupsieve==2.0 54 | tblib==1.6.0 55 | translationstring==1.3 56 | urllib3==1.25.8 57 | venusian==3.0.0 58 | wcwidth==0.1.9 59 | WebOb==1.8.6 60 | Werkzeug==1.0.1 61 | zipp==3.1.0 62 | zope.deprecation==4.4.0 63 | zope.interface==5.1.0 64 | -------------------------------------------------------------------------------- /static/admin/css/dashboard.css: -------------------------------------------------------------------------------- 1 | /* DASHBOARD */ 2 | 3 | .dashboard .module table th { 4 | width: 100%; 5 | } 6 | 7 | .dashboard .module table td { 8 | white-space: nowrap; 9 | } 10 | 11 | .dashboard .module table td a { 12 | display: block; 13 | padding-right: .6em; 14 | } 15 | 16 | /* RECENT ACTIONS MODULE */ 17 | 18 | .module ul.actionlist { 19 | margin-left: 0; 20 | } 21 | 22 | ul.actionlist li { 23 | list-style-type: none; 24 | overflow: hidden; 25 | text-overflow: ellipsis; 26 | -o-text-overflow: ellipsis; 27 | } 28 | -------------------------------------------------------------------------------- /static/admin/css/fonts.css: -------------------------------------------------------------------------------- 1 | @font-face { 2 | font-family: 'Roboto'; 3 | src: url('../fonts/Roboto-Bold-webfont.woff'); 4 | font-weight: 700; 5 | font-style: normal; 6 | } 7 | 8 | @font-face { 9 | font-family: 'Roboto'; 10 | src: url('../fonts/Roboto-Regular-webfont.woff'); 11 | font-weight: 400; 12 | font-style: normal; 13 | } 14 | 15 | @font-face { 16 | font-family: 'Roboto'; 17 | src: url('../fonts/Roboto-Light-webfont.woff'); 18 | font-weight: 300; 19 | font-style: normal; 20 | } 21 | -------------------------------------------------------------------------------- /static/admin/css/login.css: -------------------------------------------------------------------------------- 1 | /* LOGIN FORM */ 2 | 3 | body.login { 4 | background: #f8f8f8; 5 | } 6 | 7 | .login #header { 8 | height: auto; 9 | padding: 5px 16px; 10 | } 11 | 12 | .login #header h1 { 13 | font-size: 18px; 14 | } 15 | 16 | .login #header h1 a { 17 | color: #fff; 18 | } 19 | 20 | .login #content { 21 | padding: 20px 20px 0; 22 | } 23 | 24 | .login #container { 25 | background: #fff; 26 | border: 1px solid #eaeaea; 27 | border-radius: 4px; 28 | overflow: hidden; 29 | width: 28em; 30 | min-width: 300px; 31 | margin: 100px auto; 32 | } 33 | 34 | .login #content-main { 35 | width: 100%; 36 | } 37 | 38 | .login .form-row { 39 | padding: 4px 0; 40 | float: left; 41 | width: 100%; 42 | border-bottom: none; 43 | } 44 | 45 | .login .form-row label { 46 | padding-right: 0.5em; 47 | line-height: 2em; 48 | font-size: 1em; 49 | clear: both; 50 | color: #333; 51 | } 52 | 53 | .login .form-row #id_username, .login .form-row #id_password { 54 | clear: both; 55 | padding: 8px; 56 | width: 100%; 57 | -webkit-box-sizing: border-box; 58 | -moz-box-sizing: border-box; 59 | box-sizing: border-box; 60 | } 61 | 62 | .login span.help { 63 | font-size: 10px; 64 | display: block; 65 | } 66 | 67 | .login .submit-row { 68 | clear: both; 69 | padding: 1em 0 0 9.4em; 70 | margin: 0; 71 | border: none; 72 | background: none; 73 | text-align: left; 74 | } 75 | 76 | .login .password-reset-link { 77 | text-align: center; 78 | } 79 | -------------------------------------------------------------------------------- /static/admin/css/responsive_rtl.css: -------------------------------------------------------------------------------- 1 | /* TABLETS */ 2 | 3 | @media (max-width: 1024px) { 4 | [dir="rtl"] .colMS { 5 | margin-right: 0; 6 | } 7 | 8 | [dir="rtl"] #user-tools { 9 | text-align: right; 10 | } 11 | 12 | [dir="rtl"] #changelist .actions label { 13 | padding-left: 10px; 14 | padding-right: 0; 15 | } 16 | 17 | [dir="rtl"] #changelist .actions select { 18 | margin-left: 0; 19 | margin-right: 15px; 20 | } 21 | 22 | [dir="rtl"] .change-list .filtered .results, 23 | [dir="rtl"] .change-list .filtered .paginator, 24 | [dir="rtl"] .filtered #toolbar, 25 | [dir="rtl"] .filtered div.xfull, 26 | [dir="rtl"] .filtered .actions { 27 | margin-right: 0; 28 | margin-left: 230px; 29 | } 30 | 31 | [dir="rtl"] .inline-group ul.tools a.add, 32 | [dir="rtl"] .inline-group div.add-row a, 33 | [dir="rtl"] .inline-group .tabular tr.add-row td a { 34 | padding: 8px 26px 8px 10px; 35 | background-position: calc(100% - 8px) 9px; 36 | } 37 | 38 | [dir="rtl"] .related-widget-wrapper-link + .selector { 39 | margin-right: 0; 40 | margin-left: 15px; 41 | } 42 | 43 | [dir="rtl"] .selector .selector-filter label { 44 | margin-right: 0; 45 | margin-left: 8px; 46 | } 47 | 48 | [dir="rtl"] .object-tools li { 49 | float: right; 50 | } 51 | 52 | [dir="rtl"] .object-tools li + li { 53 | margin-left: 0; 54 | margin-right: 15px; 55 | } 56 | 57 | [dir="rtl"] .dashboard .module table td a { 58 | padding-left: 0; 59 | padding-right: 16px; 60 | } 61 | } 62 | 63 | /* MOBILE */ 64 | 65 | @media (max-width: 767px) { 66 | [dir="rtl"] .change-list .filtered .results, 67 | [dir="rtl"] .change-list .filtered .paginator, 68 | [dir="rtl"] .filtered #toolbar, 69 | [dir="rtl"] .filtered div.xfull, 70 | [dir="rtl"] .filtered .actions { 71 | margin-left: 0; 72 | } 73 | 74 | [dir="rtl"] .aligned .add-another, 75 | [dir="rtl"] .aligned .related-lookup, 76 | [dir="rtl"] .aligned .datetimeshortcuts { 77 | margin-left: 0; 78 | margin-right: 15px; 79 | } 80 | } 81 | -------------------------------------------------------------------------------- /static/admin/css/rtl.css: -------------------------------------------------------------------------------- 1 | body { 2 | direction: rtl; 3 | } 4 | 5 | /* LOGIN */ 6 | 7 | .login .form-row { 8 | float: right; 9 | } 10 | 11 | .login .form-row label { 12 | float: right; 13 | padding-left: 0.5em; 14 | padding-right: 0; 15 | text-align: left; 16 | } 17 | 18 | .login .submit-row { 19 | clear: both; 20 | padding: 1em 9.4em 0 0; 21 | } 22 | 23 | /* GLOBAL */ 24 | 25 | th { 26 | text-align: right; 27 | } 28 | 29 | .module h2, .module caption { 30 | text-align: right; 31 | } 32 | 33 | .module ul, .module ol { 34 | margin-left: 0; 35 | margin-right: 1.5em; 36 | } 37 | 38 | .addlink, .changelink { 39 | padding-left: 0; 40 | padding-right: 16px; 41 | background-position: 100% 1px; 42 | } 43 | 44 | .deletelink { 45 | padding-left: 0; 46 | padding-right: 16px; 47 | background-position: 100% 1px; 48 | } 49 | 50 | .object-tools { 51 | float: left; 52 | } 53 | 54 | thead th:first-child, 55 | tfoot td:first-child { 56 | border-left: none; 57 | } 58 | 59 | /* LAYOUT */ 60 | 61 | #user-tools { 62 | right: auto; 63 | left: 0; 64 | text-align: left; 65 | } 66 | 67 | div.breadcrumbs { 68 | text-align: right; 69 | } 70 | 71 | #content-main { 72 | float: right; 73 | } 74 | 75 | #content-related { 76 | float: left; 77 | margin-left: -300px; 78 | margin-right: auto; 79 | } 80 | 81 | .colMS { 82 | margin-left: 300px; 83 | margin-right: 0; 84 | } 85 | 86 | /* SORTABLE TABLES */ 87 | 88 | table thead th.sorted .sortoptions { 89 | float: left; 90 | } 91 | 92 | thead th.sorted .text { 93 | padding-right: 0; 94 | padding-left: 42px; 95 | } 96 | 97 | /* dashboard styles */ 98 | 99 | .dashboard .module table td a { 100 | padding-left: .6em; 101 | padding-right: 16px; 102 | } 103 | 104 | /* changelists styles */ 105 | 106 | .change-list .filtered table { 107 | border-left: none; 108 | border-right: 0px none; 109 | } 110 | 111 | #changelist-filter { 112 | right: auto; 113 | left: 0; 114 | border-left: none; 115 | border-right: none; 116 | } 117 | 118 | .change-list .filtered .results, .change-list .filtered .paginator, .filtered #toolbar, .filtered div.xfull { 119 | margin-right: 0; 120 | margin-left: 280px; 121 | } 122 | 123 | #changelist-filter li.selected { 124 | border-left: none; 125 | padding-left: 10px; 126 | margin-left: 0; 127 | border-right: 5px solid #eaeaea; 128 | padding-right: 10px; 129 | margin-right: -15px; 130 | } 131 | 132 | .filtered .actions { 133 | margin-left: 280px; 134 | margin-right: 0; 135 | } 136 | 137 | #changelist table tbody td:first-child, #changelist table tbody th:first-child { 138 | border-right: none; 139 | border-left: none; 140 | } 141 | 142 | /* FORMS */ 143 | 144 | .aligned label { 145 | padding: 0 0 3px 1em; 146 | float: right; 147 | } 148 | 149 | .submit-row { 150 | text-align: left 151 | } 152 | 153 | .submit-row p.deletelink-box { 154 | float: right; 155 | } 156 | 157 | .submit-row input.default { 158 | margin-left: 0; 159 | } 160 | 161 | .vDateField, .vTimeField { 162 | margin-left: 2px; 163 | } 164 | 165 | .aligned .form-row input { 166 | margin-left: 5px; 167 | } 168 | 169 | form .aligned p.help, form .aligned div.help { 170 | clear: right; 171 | } 172 | 173 | form ul.inline li { 174 | float: right; 175 | padding-right: 0; 176 | padding-left: 7px; 177 | } 178 | 179 | input[type=submit].default, .submit-row input.default { 180 | float: left; 181 | } 182 | 183 | fieldset .field-box { 184 | float: right; 185 | margin-left: 20px; 186 | margin-right: 0; 187 | } 188 | 189 | .errorlist li { 190 | background-position: 100% 12px; 191 | padding: 0; 192 | } 193 | 194 | .errornote { 195 | background-position: 100% 12px; 196 | padding: 10px 12px; 197 | } 198 | 199 | /* WIDGETS */ 200 | 201 | .calendarnav-previous { 202 | top: 0; 203 | left: auto; 204 | right: 10px; 205 | } 206 | 207 | .calendarnav-next { 208 | top: 0; 209 | right: auto; 210 | left: 10px; 211 | } 212 | 213 | .calendar caption, .calendarbox h2 { 214 | text-align: center; 215 | } 216 | 217 | .selector { 218 | float: right; 219 | } 220 | 221 | .selector .selector-filter { 222 | text-align: right; 223 | } 224 | 225 | .inline-deletelink { 226 | float: left; 227 | } 228 | 229 | form .form-row p.datetime { 230 | overflow: hidden; 231 | } 232 | 233 | .related-widget-wrapper { 234 | float: right; 235 | } 236 | 237 | /* MISC */ 238 | 239 | .inline-related h2, .inline-group h2 { 240 | text-align: right 241 | } 242 | 243 | .inline-related h3 span.delete { 244 | padding-right: 20px; 245 | padding-left: inherit; 246 | left: 10px; 247 | right: inherit; 248 | float:left; 249 | } 250 | 251 | .inline-related h3 span.delete label { 252 | margin-left: inherit; 253 | margin-right: 2px; 254 | } 255 | 256 | /* IE7 specific bug fixes */ 257 | 258 | div.colM { 259 | position: relative; 260 | } 261 | 262 | .submit-row input { 263 | float: left; 264 | } 265 | -------------------------------------------------------------------------------- /static/admin/css/vendor/select2/LICENSE-SELECT2.md: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2012-2015 Kevin Brown, Igor Vaynberg, and Select2 contributors 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /static/admin/fonts/README.txt: -------------------------------------------------------------------------------- 1 | Roboto webfont source: https://www.google.com/fonts/specimen/Roboto 2 | Weights used in this project: Light (300), Regular (400), Bold (700) 3 | -------------------------------------------------------------------------------- /static/admin/fonts/Roboto-Bold-webfont.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/admin/fonts/Roboto-Bold-webfont.woff -------------------------------------------------------------------------------- /static/admin/fonts/Roboto-Light-webfont.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/admin/fonts/Roboto-Light-webfont.woff -------------------------------------------------------------------------------- /static/admin/fonts/Roboto-Regular-webfont.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/admin/fonts/Roboto-Regular-webfont.woff -------------------------------------------------------------------------------- /static/admin/img/LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2014 Code Charm Ltd 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of 6 | this software and associated documentation files (the "Software"), to deal in 7 | the Software without restriction, including without limitation the rights to 8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 9 | the Software, and to permit persons to whom the Software is furnished to do so, 10 | subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /static/admin/img/README.txt: -------------------------------------------------------------------------------- 1 | All icons are taken from Font Awesome (http://fontawesome.io/) project. 2 | The Font Awesome font is licensed under the SIL OFL 1.1: 3 | - http://scripts.sil.org/OFL 4 | 5 | SVG icons source: https://github.com/encharm/Font-Awesome-SVG-PNG 6 | Font-Awesome-SVG-PNG is licensed under the MIT license (see file license 7 | in current folder). 8 | -------------------------------------------------------------------------------- /static/admin/img/calendar-icons.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /static/admin/img/gis/move_vertex_off.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /static/admin/img/gis/move_vertex_on.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /static/admin/img/icon-addlink.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-alert.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-calendar.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /static/admin/img/icon-changelink.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-clock.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /static/admin/img/icon-deletelink.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-no.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-unknown-alt.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-unknown.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/icon-yes.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/inline-delete.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/search.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/selector-icons.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /static/admin/img/sorting-icons.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /static/admin/img/tooltag-add.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/img/tooltag-arrowright.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /static/admin/js/actions.min.js: -------------------------------------------------------------------------------- 1 | (function(a){var f;a.fn.actions=function(e){var b=a.extend({},a.fn.actions.defaults,e),g=a(this),k=!1,l=function(){a(b.acrossClears).hide();a(b.acrossQuestions).show();a(b.allContainer).hide()},m=function(){a(b.acrossClears).show();a(b.acrossQuestions).hide();a(b.actionContainer).toggleClass(b.selectedClass);a(b.allContainer).show();a(b.counterContainer).hide()},n=function(){a(b.acrossClears).hide();a(b.acrossQuestions).hide();a(b.allContainer).hide();a(b.counterContainer).show()},p=function(){n(); 2 | a(b.acrossInput).val(0);a(b.actionContainer).removeClass(b.selectedClass)},q=function(c){c?l():n();a(g).prop("checked",c).parent().parent().toggleClass(b.selectedClass,c)},h=function(){var c=a(g).filter(":checked").length,d=a(".action-counter").data("actionsIcnt");a(b.counterContainer).html(interpolate(ngettext("%(sel)s of %(cnt)s selected","%(sel)s of %(cnt)s selected",c),{sel:c,cnt:d},!0));a(b.allToggle).prop("checked",function(){var a;c===g.length?(a=!0,l()):(a=!1,p());return a})};a(b.counterContainer).show(); 3 | a(this).filter(":checked").each(function(c){a(this).parent().parent().toggleClass(b.selectedClass);h();1===a(b.acrossInput).val()&&m()});a(b.allToggle).show().click(function(){q(a(this).prop("checked"));h()});a("a",b.acrossQuestions).click(function(c){c.preventDefault();a(b.acrossInput).val(1);m()});a("a",b.acrossClears).click(function(c){c.preventDefault();a(b.allToggle).prop("checked",!1);p();q(0);h()});f=null;a(g).click(function(c){c||(c=window.event);var d=c.target?c.target:c.srcElement;if(f&& 4 | a.data(f)!==a.data(d)&&!0===c.shiftKey){var e=!1;a(f).prop("checked",d.checked).parent().parent().toggleClass(b.selectedClass,d.checked);a(g).each(function(){if(a.data(this)===a.data(f)||a.data(this)===a.data(d))e=e?!1:!0;e&&a(this).prop("checked",d.checked).parent().parent().toggleClass(b.selectedClass,d.checked)})}a(d).parent().parent().toggleClass(b.selectedClass,d.checked);f=d;h()});a("form#changelist-form table#result_list tr").on("change","td:gt(0) :input",function(){k=!0});a('form#changelist-form button[name="index"]').click(function(a){if(k)return confirm(gettext("You have unsaved changes on individual editable fields. If you run an action, your unsaved changes will be lost."))}); 5 | a('form#changelist-form input[name="_save"]').click(function(c){var d=!1;a("select option:selected",b.actionContainer).each(function(){a(this).val()&&(d=!0)});if(d)return k?confirm(gettext("You have selected an action, but you haven't saved your changes to individual fields yet. Please click OK to save. You'll need to re-run the action.")):confirm(gettext("You have selected an action, and you haven't made any changes on individual fields. You're probably looking for the Go button rather than the Save button."))})}; 6 | a.fn.actions.defaults={actionContainer:"div.actions",counterContainer:"span.action-counter",allContainer:"div.actions span.all",acrossInput:"div.actions input.select-across",acrossQuestions:"div.actions span.question",acrossClears:"div.actions span.clear",allToggle:"#action-toggle",selectedClass:"selected"};a(document).ready(function(){var e=a("tr input.action-select");0' + gettext("Show") + 11 | ')'); 12 | } 13 | }); 14 | // Add toggle to anchor tag 15 | $("fieldset.collapse a.collapse-toggle").click(function(ev) { 16 | if ($(this).closest("fieldset").hasClass("collapsed")) { 17 | // Show 18 | $(this).text(gettext("Hide")).closest("fieldset").removeClass("collapsed").trigger("show.fieldset", [$(this).attr("id")]); 19 | } else { 20 | // Hide 21 | $(this).text(gettext("Show")).closest("fieldset").addClass("collapsed").trigger("hide.fieldset", [$(this).attr("id")]); 22 | } 23 | return false; 24 | }); 25 | }); 26 | })(django.jQuery); 27 | -------------------------------------------------------------------------------- /static/admin/js/collapse.min.js: -------------------------------------------------------------------------------- 1 | var $jscomp={scope:{},findInternal:function(a,c,b){a instanceof String&&(a=String(a));for(var d=a.length,e=0;e'+gettext("Show")+")")});a("fieldset.collapse a.collapse-toggle").click(function(c){a(this).closest("fieldset").hasClass("collapsed")?a(this).text(gettext("Hide")).closest("fieldset").removeClass("collapsed").trigger("show.fieldset",[a(this).attr("id")]):a(this).text(gettext("Show")).closest("fieldset").addClass("collapsed").trigger("hide.fieldset", 5 | [a(this).attr("id")]);return!1})})})(django.jQuery); 6 | -------------------------------------------------------------------------------- /static/admin/js/jquery.init.js: -------------------------------------------------------------------------------- 1 | /*global django:true, jQuery:false*/ 2 | /* Puts the included jQuery into our own namespace using noConflict and passing 3 | * it 'true'. This ensures that the included jQuery doesn't pollute the global 4 | * namespace (i.e. this preserves pre-existing values for both window.$ and 5 | * window.jQuery). 6 | */ 7 | var django = django || {}; 8 | django.jQuery = jQuery.noConflict(true); 9 | -------------------------------------------------------------------------------- /static/admin/js/popup_response.js: -------------------------------------------------------------------------------- 1 | /*global opener */ 2 | (function() { 3 | 'use strict'; 4 | var initData = JSON.parse(document.getElementById('django-admin-popup-response-constants').dataset.popupResponse); 5 | switch(initData.action) { 6 | case 'change': 7 | opener.dismissChangeRelatedObjectPopup(window, initData.value, initData.obj, initData.new_value); 8 | break; 9 | case 'delete': 10 | opener.dismissDeleteRelatedObjectPopup(window, initData.value); 11 | break; 12 | default: 13 | opener.dismissAddRelatedObjectPopup(window, initData.value, initData.obj); 14 | break; 15 | } 16 | })(); 17 | -------------------------------------------------------------------------------- /static/admin/js/prepopulate.js: -------------------------------------------------------------------------------- 1 | /*global URLify*/ 2 | (function($) { 3 | 'use strict'; 4 | $.fn.prepopulate = function(dependencies, maxLength, allowUnicode) { 5 | /* 6 | Depends on urlify.js 7 | Populates a selected field with the values of the dependent fields, 8 | URLifies and shortens the string. 9 | dependencies - array of dependent fields ids 10 | maxLength - maximum length of the URLify'd string 11 | allowUnicode - Unicode support of the URLify'd string 12 | */ 13 | return this.each(function() { 14 | var prepopulatedField = $(this); 15 | 16 | var populate = function() { 17 | // Bail if the field's value has been changed by the user 18 | if (prepopulatedField.data('_changed')) { 19 | return; 20 | } 21 | 22 | var values = []; 23 | $.each(dependencies, function(i, field) { 24 | field = $(field); 25 | if (field.val().length > 0) { 26 | values.push(field.val()); 27 | } 28 | }); 29 | prepopulatedField.val(URLify(values.join(' '), maxLength, allowUnicode)); 30 | }; 31 | 32 | prepopulatedField.data('_changed', false); 33 | prepopulatedField.change(function() { 34 | prepopulatedField.data('_changed', true); 35 | }); 36 | 37 | if (!prepopulatedField.val()) { 38 | $(dependencies.join(',')).keyup(populate).change(populate).focus(populate); 39 | } 40 | }); 41 | }; 42 | })(django.jQuery); 43 | -------------------------------------------------------------------------------- /static/admin/js/prepopulate.min.js: -------------------------------------------------------------------------------- 1 | (function(c){c.fn.prepopulate=function(e,f,g){return this.each(function(){var a=c(this),b=function(){if(!a.data("_changed")){var b=[];c.each(e,function(a,d){d=c(d);01&&(n+="a"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Моля въведете още "+t+" символ";return t>1&&(n+="a"),n},loadingMore:function(){return"Зареждат се още…"},maximumSelected:function(e){var t="Можете да направите до "+e.maximum+" ";return e.maximum>1?t+="избора":t+="избор",t},noResults:function(){return"Няма намерени съвпадения"},searching:function(){return"Търсене…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ca.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ca",[],function(){return{errorLoading:function(){return"La càrrega ha fallat"},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Si us plau, elimina "+t+" car";return t==1?n+="àcter":n+="àcters",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Si us plau, introdueix "+t+" car";return t==1?n+="àcter":n+="àcters",n},loadingMore:function(){return"Carregant més resultats…"},maximumSelected:function(e){var t="Només es pot seleccionar "+e.maximum+" element";return e.maximum!=1&&(t+="s"),t},noResults:function(){return"No s'han trobat resultats"},searching:function(){return"Cercant…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/cs.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/cs",[],function(){function e(e,t){switch(e){case 2:return t?"dva":"dvě";case 3:return"tři";case 4:return"čtyři"}return""}return{errorLoading:function(){return"Výsledky nemohly být načteny."},inputTooLong:function(t){var n=t.input.length-t.maximum;return n==1?"Prosím zadejte o jeden znak méně":n<=4?"Prosím zadejte o "+e(n,!0)+" znaky méně":"Prosím zadejte o "+n+" znaků méně"},inputTooShort:function(t){var n=t.minimum-t.input.length;return n==1?"Prosím zadejte ještě jeden znak":n<=4?"Prosím zadejte ještě další "+e(n,!0)+" znaky":"Prosím zadejte ještě dalších "+n+" znaků"},loadingMore:function(){return"Načítají se další výsledky…"},maximumSelected:function(t){var n=t.maximum;return n==1?"Můžete zvolit jen jednu položku":n<=4?"Můžete zvolit maximálně "+e(n,!1)+" položky":"Můžete zvolit maximálně "+n+" položek"},noResults:function(){return"Nenalezeny žádné položky"},searching:function(){return"Vyhledávání…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/da.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/da",[],function(){return{errorLoading:function(){return"Resultaterne kunne ikke indlæses."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Angiv venligst "+t+" tegn mindre";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Angiv venligst "+t+" tegn mere";return n},loadingMore:function(){return"Indlæser flere resultater…"},maximumSelected:function(e){var t="Du kan kun vælge "+e.maximum+" emne";return e.maximum!=1&&(t+="r"),t},noResults:function(){return"Ingen resultater fundet"},searching:function(){return"Søger…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/de.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/de",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum;return"Bitte "+t+" Zeichen weniger eingeben"},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Bitte "+t+" Zeichen mehr eingeben"},loadingMore:function(){return"Lade mehr Ergebnisse…"},maximumSelected:function(e){var t="Sie können nur "+e.maximum+" Eintr";return e.maximum===1?t+="ag":t+="äge",t+=" auswählen",t},noResults:function(){return"Keine Übereinstimmungen gefunden"},searching:function(){return"Suche…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/el.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/el",[],function(){return{errorLoading:function(){return"Τα αποτελέσματα δεν μπόρεσαν να φορτώσουν."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Παρακαλώ διαγράψτε "+t+" χαρακτήρ";return t==1&&(n+="α"),t!=1&&(n+="ες"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Παρακαλώ συμπληρώστε "+t+" ή περισσότερους χαρακτήρες";return n},loadingMore:function(){return"Φόρτωση περισσότερων αποτελεσμάτων…"},maximumSelected:function(e){var t="Μπορείτε να επιλέξετε μόνο "+e.maximum+" επιλογ";return e.maximum==1&&(t+="ή"),e.maximum!=1&&(t+="ές"),t},noResults:function(){return"Δεν βρέθηκαν αποτελέσματα"},searching:function(){return"Αναζήτηση…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/en.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/en",[],function(){return{errorLoading:function(){return"The results could not be loaded."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Please delete "+t+" character";return t!=1&&(n+="s"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Please enter "+t+" or more characters";return n},loadingMore:function(){return"Loading more results…"},maximumSelected:function(e){var t="You can only select "+e.maximum+" item";return e.maximum!=1&&(t+="s"),t},noResults:function(){return"No results found"},searching:function(){return"Searching…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/es.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/es",[],function(){return{errorLoading:function(){return"La carga falló"},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Por favor, elimine "+t+" car";return t==1?n+="ácter":n+="acteres",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Por favor, introduzca "+t+" car";return t==1?n+="ácter":n+="acteres",n},loadingMore:function(){return"Cargando más resultados…"},maximumSelected:function(e){var t="Sólo puede seleccionar "+e.maximum+" elemento";return e.maximum!=1&&(t+="s"),t},noResults:function(){return"No se encontraron resultados"},searching:function(){return"Buscando…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/et.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/et",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Sisesta "+t+" täht";return t!=1&&(n+="e"),n+=" vähem",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Sisesta "+t+" täht";return t!=1&&(n+="e"),n+=" rohkem",n},loadingMore:function(){return"Laen tulemusi…"},maximumSelected:function(e){var t="Saad vaid "+e.maximum+" tulemus";return e.maximum==1?t+="e":t+="t",t+=" valida",t},noResults:function(){return"Tulemused puuduvad"},searching:function(){return"Otsin…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/eu.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/eu",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Idatzi ";return t==1?n+="karaktere bat":n+=t+" karaktere",n+=" gutxiago",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Idatzi ";return t==1?n+="karaktere bat":n+=t+" karaktere",n+=" gehiago",n},loadingMore:function(){return"Emaitza gehiago kargatzen…"},maximumSelected:function(e){return e.maximum===1?"Elementu bakarra hauta dezakezu":e.maximum+" elementu hauta ditzakezu soilik"},noResults:function(){return"Ez da bat datorrenik aurkitu"},searching:function(){return"Bilatzen…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/fa.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/fa",[],function(){return{errorLoading:function(){return"امکان بارگذاری نتایج وجود ندارد."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="لطفاً "+t+" کاراکتر را حذف نمایید";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="لطفاً تعداد "+t+" کاراکتر یا بیشتر وارد نمایید";return n},loadingMore:function(){return"در حال بارگذاری نتایج بیشتر..."},maximumSelected:function(e){var t="شما تنها می‌توانید "+e.maximum+" آیتم را انتخاب نمایید";return t},noResults:function(){return"هیچ نتیجه‌ای یافت نشد"},searching:function(){return"در حال جستجو..."}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/fi.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/fi",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum;return"Ole hyvä ja anna "+t+" merkkiä vähemmän"},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Ole hyvä ja anna "+t+" merkkiä lisää"},loadingMore:function(){return"Ladataan lisää tuloksia…"},maximumSelected:function(e){return"Voit valita ainoastaan "+e.maximum+" kpl"},noResults:function(){return"Ei tuloksia"},searching:function(){}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/fr.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/fr",[],function(){return{errorLoading:function(){return"Les résultats ne peuvent pas être chargés."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Supprimez "+t+" caractère";return t!==1&&(n+="s"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Saisissez "+t+" caractère";return t!==1&&(n+="s"),n},loadingMore:function(){return"Chargement de résultats supplémentaires…"},maximumSelected:function(e){var t="Vous pouvez seulement sélectionner "+e.maximum+" élément";return e.maximum!==1&&(t+="s"),t},noResults:function(){return"Aucun résultat trouvé"},searching:function(){return"Recherche en cours…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/gl.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/gl",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Elimine ";return t===1?n+="un carácter":n+=t+" caracteres",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Engada ";return t===1?n+="un carácter":n+=t+" caracteres",n},loadingMore:function(){return"Cargando máis resultados…"},maximumSelected:function(e){var t="Só pode ";return e.maximum===1?t+="un elemento":t+=e.maximum+" elementos",t},noResults:function(){return"Non se atoparon resultados"},searching:function(){return"Buscando…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/he.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/he",[],function(){return{errorLoading:function(){return"שגיאה בטעינת התוצאות"},inputTooLong:function(e){var t=e.input.length-e.maximum,n="נא למחוק ";return t===1?n+="תו אחד":n+=t+" תווים",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="נא להכניס ";return t===1?n+="תו אחד":n+=t+" תווים",n+=" או יותר",n},loadingMore:function(){return"טוען תוצאות נוספות…"},maximumSelected:function(e){var t="באפשרותך לבחור עד ";return e.maximum===1?t+="פריט אחד":t+=e.maximum+" פריטים",t},noResults:function(){return"לא נמצאו תוצאות"},searching:function(){return"מחפש…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/hi.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/hi",[],function(){return{errorLoading:function(){return"परिणामों को लोड नहीं किया जा सका।"},inputTooLong:function(e){var t=e.input.length-e.maximum,n=t+" अक्षर को हटा दें";return t>1&&(n=t+" अक्षरों को हटा दें "),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="कृपया "+t+" या अधिक अक्षर दर्ज करें";return n},loadingMore:function(){return"अधिक परिणाम लोड हो रहे है..."},maximumSelected:function(e){var t="आप केवल "+e.maximum+" आइटम का चयन कर सकते हैं";return t},noResults:function(){return"कोई परिणाम नहीं मिला"},searching:function(){return"खोज रहा है..."}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/hr.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/hr",[],function(){function e(e){var t=" "+e+" znak";return e%10<5&&e%10>0&&(e%100<5||e%100>19)?e%10>1&&(t+="a"):t+="ova",t}return{errorLoading:function(){return"Preuzimanje nije uspjelo."},inputTooLong:function(t){var n=t.input.length-t.maximum;return"Unesite "+e(n)},inputTooShort:function(t){var n=t.minimum-t.input.length;return"Unesite još "+e(n)},loadingMore:function(){return"Učitavanje rezultata…"},maximumSelected:function(e){return"Maksimalan broj odabranih stavki je "+e.maximum},noResults:function(){return"Nema rezultata"},searching:function(){return"Pretraga…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/hu.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/hu",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum;return"Túl hosszú. "+t+" karakterrel több, mint kellene."},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Túl rövid. Még "+t+" karakter hiányzik."},loadingMore:function(){return"Töltés…"},maximumSelected:function(e){return"Csak "+e.maximum+" elemet lehet kiválasztani."},noResults:function(){return"Nincs találat."},searching:function(){return"Keresés…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/id.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/id",[],function(){return{errorLoading:function(){return"Data tidak boleh diambil."},inputTooLong:function(e){var t=e.input.length-e.maximum;return"Hapuskan "+t+" huruf"},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Masukkan "+t+" huruf lagi"},loadingMore:function(){return"Mengambil data…"},maximumSelected:function(e){return"Anda hanya dapat memilih "+e.maximum+" pilihan"},noResults:function(){return"Tidak ada data yang sesuai"},searching:function(){return"Mencari…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/is.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/is",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Vinsamlegast styttið texta um "+t+" staf";return t<=1?n:n+"i"},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Vinsamlegast skrifið "+t+" staf";return t>1&&(n+="i"),n+=" í viðbót",n},loadingMore:function(){return"Sæki fleiri niðurstöður…"},maximumSelected:function(e){return"Þú getur aðeins valið "+e.maximum+" atriði"},noResults:function(){return"Ekkert fannst"},searching:function(){return"Leita…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/it.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/it",[],function(){return{errorLoading:function(){return"I risultati non possono essere caricati."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Per favore cancella "+t+" caratter";return t!==1?n+="i":n+="e",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Per favore inserisci "+t+" o più caratteri";return n},loadingMore:function(){return"Caricando più risultati…"},maximumSelected:function(e){var t="Puoi selezionare solo "+e.maximum+" element";return e.maximum!==1?t+="i":t+="o",t},noResults:function(){return"Nessun risultato trovato"},searching:function(){return"Sto cercando…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ja.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ja",[],function(){return{errorLoading:function(){return"結果が読み込まれませんでした"},inputTooLong:function(e){var t=e.input.length-e.maximum,n=t+" 文字を削除してください";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="少なくとも "+t+" 文字を入力してください";return n},loadingMore:function(){return"読み込み中…"},maximumSelected:function(e){var t=e.maximum+" 件しか選択できません";return t},noResults:function(){return"対象が見つかりません"},searching:function(){return"検索しています…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/km.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/km",[],function(){return{errorLoading:function(){return"មិនអាចទាញយកទិន្នន័យ"},inputTooLong:function(e){var t=e.input.length-e.maximum,n="សូមលុបចេញ "+t+" អក្សរ";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="សូមបញ្ចូល"+t+" អក្សរ រឺ ច្រើនជាងនេះ";return n},loadingMore:function(){return"កំពុងទាញយកទិន្នន័យបន្ថែម..."},maximumSelected:function(e){var t="អ្នកអាចជ្រើសរើសបានតែ "+e.maximum+" ជម្រើសប៉ុណ្ណោះ";return t},noResults:function(){return"មិនមានលទ្ធផល"},searching:function(){return"កំពុងស្វែងរក..."}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ko.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ko",[],function(){return{errorLoading:function(){return"결과를 불러올 수 없습니다."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="너무 깁니다. "+t+" 글자 지워주세요.";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="너무 짧습니다. "+t+" 글자 더 입력해주세요.";return n},loadingMore:function(){return"불러오는 중…"},maximumSelected:function(e){var t="최대 "+e.maximum+"개까지만 선택 가능합니다.";return t},noResults:function(){return"결과가 없습니다."},searching:function(){return"검색 중…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/lt.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/lt",[],function(){function e(e,t,n,r){return e%10===1&&(e%100<11||e%100>19)?t:e%10>=2&&e%10<=9&&(e%100<11||e%100>19)?n:r}return{inputTooLong:function(t){var n=t.input.length-t.maximum,r="Pašalinkite "+n+" simbol";return r+=e(n,"į","ius","ių"),r},inputTooShort:function(t){var n=t.minimum-t.input.length,r="Įrašykite dar "+n+" simbol";return r+=e(n,"į","ius","ių"),r},loadingMore:function(){return"Kraunama daugiau rezultatų…"},maximumSelected:function(t){var n="Jūs galite pasirinkti tik "+t.maximum+" element";return n+=e(t.maximum,"ą","us","ų"),n},noResults:function(){return"Atitikmenų nerasta"},searching:function(){return"Ieškoma…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/lv.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/lv",[],function(){function e(e,t,n,r){return e===11?t:e%10===1?n:r}return{inputTooLong:function(t){var n=t.input.length-t.maximum,r="Lūdzu ievadiet par "+n;return r+=" simbol"+e(n,"iem","u","iem"),r+" mazāk"},inputTooShort:function(t){var n=t.minimum-t.input.length,r="Lūdzu ievadiet vēl "+n;return r+=" simbol"+e(n,"us","u","us"),r},loadingMore:function(){return"Datu ielāde…"},maximumSelected:function(t){var n="Jūs varat izvēlēties ne vairāk kā "+t.maximum;return n+=" element"+e(t.maximum,"us","u","us"),n},noResults:function(){return"Sakritību nav"},searching:function(){return"Meklēšana…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/mk.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/mk",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Ве молиме внесете "+e.maximum+" помалку карактер";return e.maximum!==1&&(n+="и"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Ве молиме внесете уште "+e.maximum+" карактер";return e.maximum!==1&&(n+="и"),n},loadingMore:function(){return"Вчитување резултати…"},maximumSelected:function(e){var t="Можете да изберете само "+e.maximum+" ставк";return e.maximum===1?t+="а":t+="и",t},noResults:function(){return"Нема пронајдено совпаѓања"},searching:function(){return"Пребарување…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ms.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ms",[],function(){return{errorLoading:function(){return"Keputusan tidak berjaya dimuatkan."},inputTooLong:function(e){var t=e.input.length-e.maximum;return"Sila hapuskan "+t+" aksara"},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Sila masukkan "+t+" atau lebih aksara"},loadingMore:function(){return"Sedang memuatkan keputusan…"},maximumSelected:function(e){return"Anda hanya boleh memilih "+e.maximum+" pilihan"},noResults:function(){return"Tiada padanan yang ditemui"},searching:function(){return"Mencari…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/nb.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/nb",[],function(){return{errorLoading:function(){return"Kunne ikke hente resultater."},inputTooLong:function(e){var t=e.input.length-e.maximum;return"Vennligst fjern "+t+" tegn"},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Vennligst skriv inn ";return t>1?n+=" flere tegn":n+=" tegn til",n},loadingMore:function(){return"Laster flere resultater…"},maximumSelected:function(e){return"Du kan velge maks "+e.maximum+" elementer"},noResults:function(){return"Ingen treff"},searching:function(){return"Søker…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/nl.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/nl",[],function(){return{errorLoading:function(){return"De resultaten konden niet worden geladen."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Gelieve "+t+" karakters te verwijderen";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Gelieve "+t+" of meer karakters in te voeren";return n},loadingMore:function(){return"Meer resultaten laden…"},maximumSelected:function(e){var t=e.maximum==1?"kan":"kunnen",n="Er "+t+" maar "+e.maximum+" item";return e.maximum!=1&&(n+="s"),n+=" worden geselecteerd",n},noResults:function(){return"Geen resultaten gevonden…"},searching:function(){return"Zoeken…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/pl.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/pl",[],function(){var e=["znak","znaki","znaków"],t=["element","elementy","elementów"],n=function(t,n){if(t===1)return n[0];if(t>1&&t<=4)return n[1];if(t>=5)return n[2]};return{errorLoading:function(){return"Nie można załadować wyników."},inputTooLong:function(t){var r=t.input.length-t.maximum;return"Usuń "+r+" "+n(r,e)},inputTooShort:function(t){var r=t.minimum-t.input.length;return"Podaj przynajmniej "+r+" "+n(r,e)},loadingMore:function(){return"Trwa ładowanie…"},maximumSelected:function(e){return"Możesz zaznaczyć tylko "+e.maximum+" "+n(e.maximum,t)},noResults:function(){return"Brak wyników"},searching:function(){return"Trwa wyszukiwanie…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/pt-BR.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/pt-BR",[],function(){return{errorLoading:function(){return"Os resultados não puderam ser carregados."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Apague "+t+" caracter";return t!=1&&(n+="es"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Digite "+t+" ou mais caracteres";return n},loadingMore:function(){return"Carregando mais resultados…"},maximumSelected:function(e){var t="Você só pode selecionar "+e.maximum+" ite";return e.maximum==1?t+="m":t+="ns",t},noResults:function(){return"Nenhum resultado encontrado"},searching:function(){return"Buscando…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/pt.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/pt",[],function(){return{errorLoading:function(){return"Os resultados não puderam ser carregados."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Por favor apague "+t+" ";return n+=t!=1?"caracteres":"carácter",n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Introduza "+t+" ou mais caracteres";return n},loadingMore:function(){return"A carregar mais resultados…"},maximumSelected:function(e){var t="Apenas pode seleccionar "+e.maximum+" ";return t+=e.maximum!=1?"itens":"item",t},noResults:function(){return"Sem resultados"},searching:function(){return"A procurar…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ro.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ro",[],function(){return{errorLoading:function(){return"Rezultatele nu au putut fi incărcate."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Vă rugăm să ștergeți"+t+" caracter";return t!==1&&(n+="e"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Vă rugăm să introduceți "+t+"sau mai multe caractere";return n},loadingMore:function(){return"Se încarcă mai multe rezultate…"},maximumSelected:function(e){var t="Aveți voie să selectați cel mult "+e.maximum;return t+=" element",e.maximum!==1&&(t+="e"),t},noResults:function(){return"Nu au fost găsite rezultate"},searching:function(){return"Căutare…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/ru.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/ru",[],function(){function e(e,t,n,r){return e%10<5&&e%10>0&&e%100<5||e%100>20?e%10>1?n:t:r}return{errorLoading:function(){return"Невозможно загрузить результаты"},inputTooLong:function(t){var n=t.input.length-t.maximum,r="Пожалуйста, введите на "+n+" символ";return r+=e(n,"","a","ов"),r+=" меньше",r},inputTooShort:function(t){var n=t.minimum-t.input.length,r="Пожалуйста, введите еще хотя бы "+n+" символ";return r+=e(n,"","a","ов"),r},loadingMore:function(){return"Загрузка данных…"},maximumSelected:function(t){var n="Вы можете выбрать не более "+t.maximum+" элемент";return n+=e(t.maximum,"","a","ов"),n},noResults:function(){return"Совпадений не найдено"},searching:function(){return"Поиск…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/sk.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/sk",[],function(){var e={2:function(e){return e?"dva":"dve"},3:function(){return"tri"},4:function(){return"štyri"}};return{inputTooLong:function(t){var n=t.input.length-t.maximum;return n==1?"Prosím, zadajte o jeden znak menej":n>=2&&n<=4?"Prosím, zadajte o "+e[n](!0)+" znaky menej":"Prosím, zadajte o "+n+" znakov menej"},inputTooShort:function(t){var n=t.minimum-t.input.length;return n==1?"Prosím, zadajte ešte jeden znak":n<=4?"Prosím, zadajte ešte ďalšie "+e[n](!0)+" znaky":"Prosím, zadajte ešte ďalších "+n+" znakov"},loadingMore:function(){return"Loading more results…"},maximumSelected:function(t){return t.maximum==1?"Môžete zvoliť len jednu položku":t.maximum>=2&&t.maximum<=4?"Môžete zvoliť najviac "+e[t.maximum](!1)+" položky":"Môžete zvoliť najviac "+t.maximum+" položiek"},noResults:function(){return"Nenašli sa žiadne položky"},searching:function(){return"Vyhľadávanie…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/sr-Cyrl.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/sr-Cyrl",[],function(){function e(e,t,n,r){return e%10==1&&e%100!=11?t:e%10>=2&&e%10<=4&&(e%100<12||e%100>14)?n:r}return{errorLoading:function(){return"Преузимање није успело."},inputTooLong:function(t){var n=t.input.length-t.maximum,r="Обришите "+n+" симбол";return r+=e(n,"","а","а"),r},inputTooShort:function(t){var n=t.minimum-t.input.length,r="Укуцајте бар још "+n+" симбол";return r+=e(n,"","а","а"),r},loadingMore:function(){return"Преузимање још резултата…"},maximumSelected:function(t){var n="Можете изабрати само "+t.maximum+" ставк";return n+=e(t.maximum,"у","е","и"),n},noResults:function(){return"Ништа није пронађено"},searching:function(){return"Претрага…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/sr.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/sr",[],function(){function e(e,t,n,r){return e%10==1&&e%100!=11?t:e%10>=2&&e%10<=4&&(e%100<12||e%100>14)?n:r}return{errorLoading:function(){return"Preuzimanje nije uspelo."},inputTooLong:function(t){var n=t.input.length-t.maximum,r="Obrišite "+n+" simbol";return r+=e(n,"","a","a"),r},inputTooShort:function(t){var n=t.minimum-t.input.length,r="Ukucajte bar još "+n+" simbol";return r+=e(n,"","a","a"),r},loadingMore:function(){return"Preuzimanje još rezultata…"},maximumSelected:function(t){var n="Možete izabrati samo "+t.maximum+" stavk";return n+=e(t.maximum,"u","e","i"),n},noResults:function(){return"Ništa nije pronađeno"},searching:function(){return"Pretraga…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/sv.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/sv",[],function(){return{errorLoading:function(){return"Resultat kunde inte laddas."},inputTooLong:function(e){var t=e.input.length-e.maximum,n="Vänligen sudda ut "+t+" tecken";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Vänligen skriv in "+t+" eller fler tecken";return n},loadingMore:function(){return"Laddar fler resultat…"},maximumSelected:function(e){var t="Du kan max välja "+e.maximum+" element";return t},noResults:function(){return"Inga träffar"},searching:function(){return"Söker…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/th.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/th",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="โปรดลบออก "+t+" ตัวอักษร";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="โปรดพิมพ์เพิ่มอีก "+t+" ตัวอักษร";return n},loadingMore:function(){return"กำลังค้นข้อมูลเพิ่ม…"},maximumSelected:function(e){var t="คุณสามารถเลือกได้ไม่เกิน "+e.maximum+" รายการ";return t},noResults:function(){return"ไม่พบข้อมูล"},searching:function(){return"กำลังค้นข้อมูล…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/tr.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/tr",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n=t+" karakter daha girmelisiniz";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="En az "+t+" karakter daha girmelisiniz";return n},loadingMore:function(){return"Daha fazla…"},maximumSelected:function(e){var t="Sadece "+e.maximum+" seçim yapabilirsiniz";return t},noResults:function(){return"Sonuç bulunamadı"},searching:function(){return"Aranıyor…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/uk.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/uk",[],function(){function e(e,t,n,r){return e%100>10&&e%100<15?r:e%10===1?t:e%10>1&&e%10<5?n:r}return{errorLoading:function(){return"Неможливо завантажити результати"},inputTooLong:function(t){var n=t.input.length-t.maximum;return"Будь ласка, видаліть "+n+" "+e(t.maximum,"літеру","літери","літер")},inputTooShort:function(e){var t=e.minimum-e.input.length;return"Будь ласка, введіть "+t+" або більше літер"},loadingMore:function(){return"Завантаження інших результатів…"},maximumSelected:function(t){return"Ви можете вибрати лише "+t.maximum+" "+e(t.maximum,"пункт","пункти","пунктів")},noResults:function(){return"Нічого не знайдено"},searching:function(){return"Пошук…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/vi.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/vi",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="Vui lòng nhập ít hơn "+t+" ký tự";return t!=1&&(n+="s"),n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="Vui lòng nhập nhiều hơn "+t+' ký tự"';return n},loadingMore:function(){return"Đang lấy thêm kết quả…"},maximumSelected:function(e){var t="Chỉ có thể chọn được "+e.maximum+" lựa chọn";return t},noResults:function(){return"Không tìm thấy kết quả"},searching:function(){return"Đang tìm…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/zh-CN.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/zh-CN",[],function(){return{errorLoading:function(){return"无法载入结果。"},inputTooLong:function(e){var t=e.input.length-e.maximum,n="请删除"+t+"个字符";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="请再输入至少"+t+"个字符";return n},loadingMore:function(){return"载入更多结果…"},maximumSelected:function(e){var t="最多只能选择"+e.maximum+"个项目";return t},noResults:function(){return"未找到结果"},searching:function(){return"搜索中…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/select2/i18n/zh-TW.js: -------------------------------------------------------------------------------- 1 | /*! Select2 4.0.3 | https://github.com/select2/select2/blob/master/LICENSE.md */ 2 | 3 | (function(){if(jQuery&&jQuery.fn&&jQuery.fn.select2&&jQuery.fn.select2.amd)var e=jQuery.fn.select2.amd;return e.define("select2/i18n/zh-TW",[],function(){return{inputTooLong:function(e){var t=e.input.length-e.maximum,n="請刪掉"+t+"個字元";return n},inputTooShort:function(e){var t=e.minimum-e.input.length,n="請再輸入"+t+"個字元";return n},loadingMore:function(){return"載入中…"},maximumSelected:function(e){var t="你只能選擇最多"+e.maximum+"項";return t},noResults:function(){return"沒有找到相符的項目"},searching:function(){return"搜尋中…"}}}),{define:e.define,require:e.require}})(); -------------------------------------------------------------------------------- /static/admin/js/vendor/xregexp/LICENSE-XREGEXP.txt: -------------------------------------------------------------------------------- 1 | The MIT License 2 | 3 | Copyright (c) 2007-2012 Steven Levithan 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /static/css/base.css: -------------------------------------------------------------------------------- 1 | .main { 2 | width: 88%; 3 | margin: 0 auto; 4 | } 5 | 6 | .page-header { 7 | float: left; 8 | padding-top: 80px; 9 | } 10 | 11 | .add { 12 | float: right; 13 | width: 40%; 14 | padding-top: 80px; 15 | } 16 | 17 | .row { 18 | float: left; 19 | width: 100%; 20 | } 21 | 22 | li { 23 | list-style: none; 24 | } 25 | 26 | .back_edit { 27 | position:relative; 28 | float: left; 29 | left: 45%; 30 | margin-top: 20px; 31 | } -------------------------------------------------------------------------------- /static/css/login.css: -------------------------------------------------------------------------------- 1 | body{ 2 | text-align:center 3 | } 4 | 5 | button { 6 | width: 200px; 7 | height: 25px; 8 | border-radius: 5px; 9 | } 10 | 11 | footer { 12 | margin-top: 300px; 13 | } 14 | 15 | .header { 16 | margin-top: 100px; 17 | 18 | } -------------------------------------------------------------------------------- /static/fonts/glyphicons-halflings-regular.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/fonts/glyphicons-halflings-regular.eot -------------------------------------------------------------------------------- /static/fonts/glyphicons-halflings-regular.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/fonts/glyphicons-halflings-regular.ttf -------------------------------------------------------------------------------- /static/fonts/glyphicons-halflings-regular.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/fonts/glyphicons-halflings-regular.woff -------------------------------------------------------------------------------- /static/fonts/glyphicons-halflings-regular.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/fonts/glyphicons-halflings-regular.woff2 -------------------------------------------------------------------------------- /static/git_images/01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/01.png -------------------------------------------------------------------------------- /static/git_images/02.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/02.png -------------------------------------------------------------------------------- /static/git_images/03.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/03.png -------------------------------------------------------------------------------- /static/git_images/04.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/04.png -------------------------------------------------------------------------------- /static/git_images/05.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/05.png -------------------------------------------------------------------------------- /static/git_images/06.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/06.png -------------------------------------------------------------------------------- /static/git_images/07.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/07.png -------------------------------------------------------------------------------- /static/git_images/08.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/08.png -------------------------------------------------------------------------------- /static/git_images/09.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/09.png -------------------------------------------------------------------------------- /static/git_images/10.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Leofighting/Django_auto_test_platform_V2/e67cbeac51ee19164a23beafb4dc9af6187bed1e/static/git_images/10.png -------------------------------------------------------------------------------- /templates/base.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {% load bootstrap4 %} 4 | {% bootstrap_css %} 5 | {% bootstrap_javascript %} 6 | {% block title %} 7 | 8 | {% endblock %} 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 46 | 47 | {% block main %} 48 | 49 | {% endblock %} 50 | 51 | -------------------------------------------------------------------------------- /templates/step_base.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {% load bootstrap4 %} 4 | {% bootstrap_css %} 5 | {% bootstrap_javascript %} 6 | 7 | {% block title %} 8 | 9 | {% endblock %} 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 28 | 29 | 30 | 31 | 50 | 51 | {% block main %} 52 | 53 | {% endblock %} 54 | 55 | --------------------------------------------------------------------------------