澳门新浦京娱乐场网站-www.146.net-新浦京娱乐场官网
做最好的网站

澳门新浦京娱乐场网站:Python的Django框架中的表

巡风xunfeng----巡风源码阅读与剖判

Python的Django框架中的表单管理示例,pythondjango

创设七个关于书籍、笔者、出版社的事例:

from django.db import models

class Publisher(models.Model):
  name = models.CharField(max_length=30)
  address = models.CharField(max_length=50)
  city = models.CharField(max_length=60)
  state_province = models.CharField(max_length=30)
  country = models.CharField(max_length=50)
  website = models.URLField()

class Author(models.Model):
  first_name = models.CharField(max_length=30)
  last_name = models.CharField(max_length=40)
  email = models.EmailField()

class Book(models.Model):
  title = models.CharField(max_length=100)
  authors = models.ManyToManyField(Author)
  publisher = models.ForeignKey(Publisher)
  publication_date = models.DateField()

小编们以后来创制三个简练的view函数以便让客户能够因而书名从数据库中搜索书籍。
日常性,表单开垦分为多少个部分: 前端HTML页面顾客接口和后台view函数对所提交数据的处理进度。 第后生可畏某些相当的轻巧;今后大家来创设个view来呈现壹个查找表单:

from django.shortcuts import render_to_response

def search_form(request):
  return render_to_response('search_form.html')

那么些view函数能够放置Python的搜寻路线的别样地方。 为了便于商讨,大家将它身处 books/views.py 里。

这个 search_form.html 模板,恐怕看起来是如此的:

<html>
<head>
  <title>Search</title>
</head>
<body>
  <form action="/search/" method="get">
    <input type="text" name="q">
    <input type="submit" value="Search">
  </form>
</body>
</html>

而 urls.py 中的 UCR-VLpattern 或许是这么的:

from mysite.books import views

urlpatterns = patterns('',
  # ...
  (r'^search-form/$', views.search_form),
  # ...
)

(注意,我们间接将views模块import进来了,并非用雷同 from mysite.views import search_form 那样的言语,因为前端看起来更不难。卡塔 尔(阿拉伯语:قطر‎

当今,如若您运营 runserver 命令,然后访谈 非常轻松。

不过,当您通过这么些form提交数据时,你会拿到一个Django 404荒唐。 那么些Form指向的U帕杰罗L /search/ 还从未被完结。 让大家抬高第三个视图函数并设置U酷路泽L:

# urls.py

urlpatterns = patterns('',
  # ...
  (r'^search-form/$', views.search_form),
  (r'^search/$', views.search),
  # ...
)

# views.py

def search(request):
  if 'q' in request.GET:
    message = 'You searched for: %r' % request.GET['q']
  else:
    message = 'You submitted an empty form.'
  return HttpResponse(message)

一时半刻先只显示顾客寻觅的字词,以鲜明寻找数据被科学地付诸给了Django,那样你就能够领会寻觅数据是何等在这里个种类中传送的。 同理可得:

    在HTML里我们定义了一个变量q。当提交表单时,变量q的值通过GET(method=”get”)附加在U奥迪Q3L /search/上。

    管理/search/(search()卡塔 尔(阿拉伯语:قطر‎的视图通过request.GET来收获q的值。

需求在乎的是在这里边料定地认清q是还是不是含有在request.GET中。就如下边request.META小节里边涉及,对于客户提交过来的数据,以至是未可厚非的数量,都亟需举行过滤。 在那若未有张开检验,那么客商提交三个空的表单将吸引KeyError卓殊:

# BAD!
def bad_search(request):
  # The following line will raise KeyError if 'q' hasn't
  # been submitted!
  message = 'You searched for: %r' % request.GET['q']
  return HttpResponse(message)

询问字符串参数

因为运用GET方法的数额是通过查询字符串的艺术传送的(例如/search/?q=django卡塔尔,所以大家能够动用requet.GET来收获那个数量。大家掌握在视图里能够选拔request.GET来得到古板U宝马X3L里的查询字符串(比方hours=3卡塔尔。

获取使用POST方法的数码与GET的近似,只是选择request.POST取代了request.GET。那么,POST与GET之间有何样区别?当大家付出表单仅仅必要获取数据时就可以用GET; 而当大家付出表单时索要改造服务器数据的情景,恐怕说发送e-mail,也许其余不独有是收获并出示数据的时候就接受POST。 在这里个寻找书籍的事例里,大家应用GET,因为那些查询不会转移服务器数据的景观。 (假设您风野趣了然越多关于GET和POST的知识,能够崇敬)

既然已经承认顾客所提交的数据是卓有成效的,那么接下去就足以从数据库中查询这一个有效的数目(相仿,在views.py里操作卡塔尔国:

from django.http import HttpResponse
from django.shortcuts import render_to_response
from mysite.books.models import Book

def search(request):
  if 'q' in request.GET and request.GET['q']:
    q = request.GET['q']
    books = Book.objects.filter(title__icontains=q)
    return render_to_response('search_results.html',
      {'books': books, 'query': q})
  else:
    return HttpResponse('Please submit a search term.')

让我们来解析一下地方的代码:

  •     除了检查q是不是留存于request.GET之外,我们还检查来reuqest.GET[‘q']的值是还是不是为空。
  •     我们应用Book.objects.filter(title__icontains=q)获取数据库中标题包涵q的图书。 icontains是一个询问关键字。那一个讲话能够精通为取得标题里含有q的书本,不区分轻重缓急写。
  •     那是贯彻书籍查询的叁个一点也不细略的方法。 大家不引入在叁个包括大量出品的数据库中使用icontains查询,因为那会一点也不快。 (在实际的案例中,大家能够利用以某种分类的自定义查询系统。 在英特网查找“开源 全文字笔迹核准索”看看是否有好的章程卡塔 尔(阿拉伯语:قطر‎

    最后,我们给模板传递来books,二个分包Book对象的列表。 查询结果的呈现模板search_results.html如下所示:

<p>You searched for: <strong>{{ query }}</strong></p>

{% if books %}
  <p>Found {{ books|length }} book{{ books|pluralize }}.</p>
  <ul>
    {% for book in books %}
    <li>{{ book.title }}</li>
    {% endfor %}
  </ul>
{% else %}
  <p>No books matched your search criteria.</p>
{% endif %}

    注意这里pluralize的使用,那几个过滤器在适度的时候会输出s(比如找到多本书籍卡塔 尔(英语:State of Qatar)。

构建三个有关书籍、作者、出版社的例证: from django.db import modelsclass Publisher(models.Model): na...

 

望风简单介绍

HTML表单是交互作用式网址的支柱,从Google的十足寻找框的轻便性到无处不在的博顾客议提交表单,到复杂的自定义数据输入分界面。 本章将介绍如何运用Django来访问顾客提交的表单数据,并对其进展表明和管理。 一路走来,大家将介绍HttpRequest和Form对象。

望风是风流洒脱款适用于公司内网的漏洞火速应急、巡航扫描系统,通过搜索功能可清晰的询问此中互连网资金财产布满情形,而且可内定漏洞插件对搜索结果进行快捷漏洞检查实验并出口结果报表。

文本地方:views/lib/QueryLogic.py

巡风是大器晚成款适用于集团内网的漏洞快速应急、巡航扫描系统,通过查找效果可清楚的询问当中网络资金财产遍布景况,並且可内定漏洞插件对找寻结果进行火速漏洞检测并出口结果报表。其主体分为两片段:网络资产识别引擎漏洞检测引擎

从倡议对象获取数据

自己在第二章介绍了HttpRequest对象,那时候咱们先是介绍了视图函数,可是及时自个儿尚未太多的话要说。 回顾一下,在我们的hello(卡塔 尔(英语:State of Qatar)视图中,各样视图函数都将HttpRequest对象作为其首先个参数:

from django.http import HttpResponse

def hello(request):
   return HttpResponse("Hello world")

HttpRequest对象,举个例子此处的变量须求,有后生可畏对你应当熟识的有意思的质量和方式,以便你了然如何是或然的。 在进行view函数的时候,你能够应用这几个属性来收获有关当前倡议的新闻(即,在Django支持的网址上加载当前页面包车型地铁顾客/ Web浏览器卡塔尔国。

 

 

互连网资产识别引擎会经过客商配置的IP范围定期自动的展发轫口探测(扶助调用MASSCAN卡塔 尔(阿拉伯语:قطر‎,并开展指纹识别,识别内容蕴含:服务类型、组件容器、脚本语言、CMS。

关于URL的信息

HttpRequest对象蕴涵关于当前央浼的UMuranoL的几条音讯(表6-1卡塔尔国。

表6-1:HttpRequest方法和属性

澳门新浦京娱乐场网站 1

HttpRequest属性和方法.png

从来使用这一个属性/方法,实际不是在视图中对网站举行硬编码。 那使得更加灵敏的代码能够在别的地点重复使用。 一个简单的例子:

# BAD!
def current_url_view_bad(request):
    return HttpResponse("Welcome to the page at /current/")

# GOOD
def current_url_view_good(request):
    return HttpResponse("Welcome to the page at %s"
% request.path)

关于央求的别的消息
request.META是二个Python字典,包括给定央浼的具备可用的HTTP南阳,包罗客商的IP地址和顾客代理(常常是Web浏览器的称谓和本子卡塔尔。 请注意,可用咸阳的总体列表决议于客户发送了哪些衡阳以至你的Web服务器设置了什么样湛江。 本词典中的一些常用键是:

  • HTTP_REFEREENVISION - 援引的U奥迪Q3L,倘若某个话。 (注意REFERE奥迪Q5的拼写错误。卡塔尔国
  • HTTP_USER_AGENT - 顾客浏览器的客户代理字符串(借使有卡塔尔国。 那看起来疑似:“Mozilla / 5.0(X11; U; Linux`` i686; fr-FR; rv:1.8.1.17)Gecko / 20080829 Firefox / 2.0.0.17”。
  • REMOTE_ADDLX570 - 客商端的IP地址,比如“12.345.67.89”。 (假设需要已经通过其他代理,那么那大概是以逗号分隔的IP地址列表,比方“12.345.67.89,23.456.78.90”卡塔 尔(英语:State of Qatar)。

请留意,因为request.META只是二个大旨的Python字典,所以若是你尝试访谈海市蜃楼的密钥,将会拿走一个KeyError至极。 (因为HTTP咸阳是表面数据 - 也便是说,它们是由客商的浏览器提交的 - 它们不该被信赖,并且只要一定标头为空或然不设有,您应该风姿浪漫味将应用程序设计为尊贵地退步。 卡塔 尔(英语:State of Qatar)您应该利用try / except子句或get(卡塔尔国方法来拍卖未定义键的景色:

# BAD!
def ua_display_bad(request):
   ua = request.META['HTTP_USER_AGENT']  # Might raise KeyError!
   return HttpResponse("Your browser is %s" % ua)

# GOOD (VERSION 1)
def ua_display_good1(request):
   try:
       ua = request.META['HTTP_USER_AGENT']
   except KeyError:
       ua = 'unknown'
   return HttpResponse("Your browser is %s" % ua)

# GOOD (VERSION 2)
def ua_display_good2(request):
   ua = request.META.get('HTTP_USER_AGENT', 'unknown')
   return HttpResponse("Your browser is %s" % ua)

自身激励你写二个小视图,突显全数的伸手。META数据,所以您可以驾驭里面有怎么着。 以下是以此意见:

def display_meta(request):
    values = request.META   
    html = []
    for k in sorted(values):
        html.append('<tr><td>%s</td><td>%s</td></tr>' % (k, values[k]))
    return HttpResponse('<table>%s</table>' % 'n'.join(html))

查看必要对象蕴涵怎么着新闻的另叁个好法子是在系统崩溃时稳重翻看Django错误页面

  • 这里有恢宏得力的消息,满含具有HTTP头和此外央浼对象(恳求 比方.path卡塔尔国。

环境:

Querylogic()

漏洞检查评定引擎会基于用户钦命的任务规则拓展期限恐怕三次性的错误疏失检查评定,其帮助2种插件类型、标示符与剧本,均可因此web调节台进行加多。(转自

至于提交数据的新闻

除了关于必要的基本元数据外,HttpRequest对象还应该有两性子子,包括客户提交的新闻:request.GET和request.POST。 那七个都是相近字典的目的,能够让您访谈GET和POST数据。 POST数据平日是从HTML <form>提交的,而GET数据足以来自<form>或页面U奥迪Q5L中的查询字符串。

字典式的对象

当本人说request.GET和request.POST是“相仿字典”的靶牛时,作者的情致是它们的行为与标准的Python字典相符,不过在才干上并不是字面包车型客车。 举例,request.GET和request.POST都有get(卡塔 尔(阿拉伯语:قطر‎,keys(卡塔 尔(阿拉伯语:قطر‎和values(卡塔尔国方法,而且能够通过在request.GET中实践键遍历键。

那为何那一个不一致吗?

因为request.GET和request.POST都有健康字典未有的增大措施。 我们会在短期内步向那几个。 您可能遇到相通于“类公事对象”的术语 - 具备多少个为主办法的Python对象,比如read(卡塔尔,它们可以用作“真实”文件对象的垫脚石。

望风是基于python的flask框架写的,数据库为mongodb。

 

只要您也跟小编相通,正在建设公司的音讯安全,大概往大了说建立三个SRC,针对厂商内网,那么些开源的扫视系统或然不错的选拔。

叁个总结的Django表单管理示例

世襲正在进展的书本,小编和出版商的例子,让我们创立三个简易的视图,让客商按标题寻找我们的书籍数据库。 日常,开荒表单有两部分:处理提交数据的HTML顾客分界面和后端视图代码。 第大器晚成有的比较轻便, 让我们成立三个人展览馆示搜索表单的视图。 当您使用startapp创制书籍应用程序时,Django会在 books文件夹中为你创造四个新的views.py文件。 继续,并累积二个新的视图到那几个文件:

# booksviews.py

from django.shortcuts import render

def search_form(request):
    return render(request, 'books/search_form.html')

下一步是创制模板,可是大家先是必要为模板创设一些新的文件夹。 如果你未曾改观它,你的装置文件中的“应用软件_DILacrosseS”被设置为True。 这象征Django将寻觅您具有的应用程序以搜索名称叫 templates的文书夹。

在图书应用程序文件夹中创设叁个新的 templates文件夹。 然后持续在新的 templates文件夹中成立另多少个文本夹并将其称为书籍。 您的结尾文件夹结构将为books templates books 。

本条里面书籍文件夹对命名空间模板比较重大。 由于Django将找出全部应用程序的极度模板,为应用程序模板创建三个称谓空间可确认保证Django使用准确的沙盘(要是八个应用程序使用同风流罗曼蒂克的模版名称卡塔尔国。

成立以下search_form.html文件并将其保存到新文件夹中:

# mysite_projectmysitebookstemplatesbookssearch_form.html

<html>
<head>
    <title>Search</title>
</head>
<body>
    <form action="/search/" method="get">
        <input type="text" name="q">
        <input type="submit" value="Search">
    </form>
</body>
</html>

以后我们需求创建多少个U君越Lconf,以便Django能够找到我们的新视图。 在您的books文件夹中,创制一个新的urls.py文件(startapp不会创立该公文卡塔 尔(英语:State of Qatar)。 将以下网站格式加多到这些新的urls.py中:

# mysitebooksurls.py

from django.conf.urls import url
from books import views

urlpatterns = [
    url(r'^search-form/$', views.search_form),
]

(请在意,大家直接导入views模块,实际不是从books.views导入search_form形似的东西,因为后面一个不那么冗长,我们就要第7章详细介绍那几个导入方法。

终极风流洒脱件事 - 当Django搜索ULANDL方式时,除非咱们领会地含有来自此外应用程序的U瑞虎L形式,否则它只会找出基本的mysite urls.py文件。 所以,让我们世襲并改善大家的网站urlpatterns:

# mysiteurls.py

from django.conf.urls import include, url

urlpatterns = [
# ...
    url(r'^', include('books.urls')),
]

以此新的UXC90L情势必得被加多到urlpatterns列表的末段。 那是因为r'^'正则表明式将具有内容发送到books.urls,因而大家要保险其他情势都不合作,然后再发送Django来检查books urls.py中是还是不是有同盟的形式。

后天,假诺您运营开辟服务器并会见http://127.0.0.1:8000/search-form/,您将见到寻找分界面(图6.1卡塔 尔(阿拉伯语:قطر‎。 很简短。

澳门新浦京娱乐场网站 2

单搜索表单.png

品尝提交表单,然而,你会获得三个Django的404不当。 表单指向U君越L / search /,它还还未被完结。 让我们用第三个视图函数来消除那些标题:

# books/urls.py

urlpatterns = [
    url(r'^search-form/$', views.search_form),
    url(r'^search/$', views.search),
]

# books/views.py

from django.http import HttpResponse

# ...

def search(request):
    if 'q' in request.GET:
        message = 'You searched for: %r' % request.GET['q']
    else:
        message = 'You submitted an empty form.'
    return HttpResponse(message)

当下,那只是显示顾客的寻觅词,所以大家得以确定保证数据科学提交给Django,那样你就能够认为到找出词是什么样流经系统的(图6-2卡塔尔。

澳门新浦京娱乐场网站 3

图6-2。 结果从轻巧的搜寻表单重返.png

简单来讲:

  1. HTML <form>定义了三个变量q。 提交时,q的值通过GET(method =“get”卡塔 尔(阿拉伯语:قطر‎发送到U昂CoraL / search /。
  2. 拍卖U景逸SUVL / search /(search(卡塔尔卡塔 尔(阿拉伯语:قطر‎的Django视图可以访谈request.GET中的q值。

此地提出的多个关键的业务是,我们精通地反省request.GET中是或不是存在“q”。 正如笔者在上边的META部分中所提议的这样,您不应该相信客户提交的任何内容,以致不会感到他们早已提交了其余事物。 借使我们从不增加那个检查,任何空表单的提交都会在视图中抓住KeyError:

# BAD!
def bad_search(request):
    # The following line will raise KeyError if 'q' hasn't been submitted!
    message = 'You searched for: %r' % request.GET['q']
    return HttpResponse(message)

可设置在Windows  OSX  Linux  Docker

# 搜索逻辑
def querylogic(list):
    query = {}
    if len(list) > 1 or len(list[0].split(':')) > 1:
        for _ in list:
            if _.find(':') > -1:
                q_key, q_value = _.split(':', 1)
                if q_key == 'port':
                    query['port'] = int(q_value)
                elif q_key == 'banner':
                    zhPattern = re.compile(u'[u4e00-u9fa5] ')
                    contents = q_value
                    match = zhPattern.search(contents)
                    # 如果没有中文用全文索引
                    if match:
                        query['banner'] = {"$regex": q_value, '$options': 'i'}
                    else:
                        text_query = mgo_text_split(q_value)
                        query['$text'] = {'$search': text_query, '$caseSensitive':True}
                elif q_key == 'ip':
                    query['ip'] = {"$regex": q_value}
                elif q_key == 'server':
                    query['server'] = q_value.lower()
                elif q_key == 'title':
                    query['webinfo.title'] = {"$regex": q_value, '$options': 'i'}
                elif q_key == 'tag':
                    query['webinfo.tag'] = q_value.lower()
                elif q_key == 'hostname':
                    query['hostname'] = {"$regex": q_value, '$options': 'i'}
                elif q_key == 'all':
                    filter_lst = []
                    for i in ('ip', 'banner', 'port', 'time', 'webinfo.tag', 'webinfo.title', 'server', 'hostname'):
                        filter_lst.append({i: {"$regex": q_value, '$options': 'i'}})
                    query['$or'] = filter_lst
                else:
                    query[q_key] = q_value
    else:
        filter_lst = []
        for i in ('ip', 'banner', 'port', 'time', 'webinfo.tag', 'webinfo.title', 'server', 'hostname'):
            filter_lst.append({i: {"$regex": list[0], '$options': 'i'}})
        query['$or'] = filter_lst
    return query

安装Ubuntu就不说了,说下国内的超快的源吧,省的网速不佳,只好干等

询问字符串参数

因为GET数据在查询字符串中传递(比方,/ search /?q = django卡塔尔国,所以能够利用request.GET来会见问调查询字符串变量。在第2章介绍Django的U奇骏Lconf系统时,小编将Django的理想的UEscortL与更古板的PHP / Java U福特ExplorerL(举个例子/ time / plus?hours = 3卡塔尔国实行了相比较,并在第6章介绍了什么形成那或多或少。

以后你理解怎样在视图中拜见问调查询字符串参数(举例在这里个事例中hours = 3卡塔尔国 - 使用request.GET。 POST数据与GET数据的办事办法相近 - 只需使用request.POST实际不是request.GET。 GET和POST有哪些界别?

Python2.7  pip  mongodb

  

Ubuntu 17.04的付出代号是Zesty Zapus,以下是Ubuntu 17.04和讯源:

当提交表单的行为只是三个“获取”数据的乞求时利用GET。每当提交表单的行事都会发出部分副作用

变动数据,发送电子邮件或任何不轻松呈现数据的业务时,请使用POST。在大家的书本找寻示例中,大家接受GET,因为查询不会转移大家服务器上的别的数据。 (借使您想询问有关GET和POST的越多消息,请参阅w3.org网址。卡塔 尔(英语:State of Qatar)

于今大家早已认证了request.GET正在被科学传递,让大家把顾客的物色查询连采纳大家的书籍数据库(再一次,在views.py中卡塔尔:

from django.http import HttpResponse
from django.shortcuts import render
from books.models import Book

def search(request):
    if 'q' in request.GET and request.GET['q']:
        q = request.GET['q']
        books = Book.objects.filter(title__icontains=q)
        return render(request, 'books/search_results.html',
                      {'books': books, 'query': q})
    else:
        return HttpResponse('Please submit a search term.')

有关我们在那所做的有的证实:

  • 除去检查request.GET中是或不是留存“q”,我们还要保险request.GET ['q']在传递给数据库查询在此之前是非空值。

  • 咱俩选拔Book.objects.filter(title__icontains = q卡塔 尔(英语:State of Qatar)来询问我们的图书表,查找全体满含给定提交的书本。 icontains是生龙活虎种检索类型(如第4章和附录B中所述卡塔 尔(英语:State of Qatar),该语句能够大致翻译为“获取标题满含q的书本,而不区分轻重缓急写”。

那是叁个特轻巧的图书寻觅方式。 笔者不提议在巨型分娩数据库上利用轻巧的Logo查询,因为它恐怕会一点也不快。 (在切实可行世界中,你想要使用某种自定义的搜寻系统,在互连网上探究开源全文字笔迹查证索,以通晓大概性。卡塔 尔(英语:State of Qatar)

我们将书籍(Book对象列表卡塔尔国传递给模板。 要使大家的新搜索表单寻常干活,大家来创造search_results.html文件:

# bookstemplatesbookssearch_results.html

<html>     
    <head>         
    <title>Book Search</title>     
    </head>     
    <body>       
        <p>You searched for: <strong>{{ query }}</strong></p>

        {% if books %}           
            <p>Found {{ books|length }} book{{ books|pluralize }}.</p>
            <ul>               
                {% for book in books %}               
                <li>{{ book.title }}</li>               
                {% endfor %}           
            </ul>       
        {% else %}           
            <p>No books matched your search criteria.</p>       
        {% endif %}     
    </body>
</html>

请留意复数模板过滤器的利用景况,依据找到的书本数量输出适当的“s”。

近日,当你运转开垦服务器并拜见http://127.0.0.1:8000/search-form/时,您的找出词应该回到更有效的结果(图6-3卡塔尔国。

澳门新浦京娱乐场网站 4

图6-3。 从我们改革的搜索表单再次回到的结果.png

安装:

 

sudo nano /etc/apt/source.list

改进大家大致的方式管理示例

正如前方的章节,笔者早就向你突显了也可能有效的最简便的事体。 今后小编将提出部分主题素材,并告诉你怎么样改良它。 首先,我们的search(卡塔 尔(英语:State of Qatar)视图对一个空查询的拍卖相当差 - 大家只是显示叁个“请提交三个搜索词”音信,必要客商点击浏览器的滞后开关。 那是骇然的和不正规的,尽管你实在在郊外达成那样的东西,你的Django权限将被打消。

再次突显表单要好得多,何况上边有三个不当,以便顾客能够致时再度尝试。 最简易的艺术是再一次渲染模板,如下所示:

from django.shortcuts import render
from django.http import HttpResponse
from books.models import Book

def search_form(request):
    return render(request, 'books/search_form.html')

def search(request):
    error = False
    if 'q' in request.GET:
        q = request.GET['q']
        if not q:
            error = True
        else:
            books = Book.objects.filter(title__icontains=q)
            return render(request, 'books/search_results.html', {'books': books, 'query': q})
    return render(request, 'books/search_form.html', {'error': error})

(请在意,我在那处带有了search_form(卡塔 尔(阿拉伯语:قطر‎,所以你能够在二个地点看看多个视图。卡塔尔在这里处,大家修正了search(卡塔 尔(英语:State of Qatar)来重新渲染search_form.html模板,就算查询是空的。 何况因为大家须求在该模板中显示错误新闻,所以大家传递二个模板变量。 现在大家可以编写search_form.html来检查错误变量:

<html>
<head>
    <title>Search</title>
</head>
<body>
    {% if error %}
        <p style="color: red;">Please submit a search term.</p>
    {% endif %}
    <form action="/search/" method="get">
        <input type="text" name="q">
        <input type="submit" value="Search">
    </form>
</body>
</html>

咱俩依然能够在原始视图search_form(卡塔尔国中利用那个模板,因为search_form(卡塔 尔(阿拉伯语:قطر‎不会将错误传递给模板

  • 进而在此种情状下错误消息不会展现出来(图6-4卡塔尔。

澳门新浦京娱乐场网站 5

图6-4。 现在,大家修改的检索表单展现和错误音信,当未有检索条目款项输入。.png

有了那几个改过,那是一个越来越好的应用程序,但它今后建议了二个主题材料:是或不是有至关重要特地的search_form(卡塔 尔(阿拉伯语:قطر‎视图? 就最近来讲,对U凯雷德L / search /(不带其余GET参数卡塔尔的号令将展现空的表单(但有错误卡塔尔。 大家能够去除search_form(卡塔 尔(阿拉伯语:قطر‎视图及其有关的UTiggoLpattern,只要大家退换search(卡塔尔国来掩藏不当音讯,当有人访谈/search/未有GET参数时:

def search(request):
    error = False
    if 'q' in request.GET:
        q = request.GET['q']
        if not q:
            error = True
        else:
            books = Book.objects.filter(title__icontains=q)
            return render(request, 'books/search_results.html', {'books': books, 'query': q})
    return render(request, 'books/search_form.html', {'error': error})

在这里个立异后的视图中,假如顾客访谈/找出/未有GET参数,他们将见到没有错误音信的搜索表单。 要是顾客提交的表单中蕴藏'q'的空值,他们将会看出带有错误音讯的追寻表单。 最终,借使顾客提交的表单中隐含“q”的非空值,他们将见到搜索结果。

咱俩得以对此应用程序实行末段的改正,以消灭一些冗余。 以后大家曾经将多个视图和U巴博斯 SLS级L合併为一个,而search / handle同一时候管理搜索表单展现和结果展现,search_form.html中的HTML <form>无需对UWranglerL举办硬编码。 并非那样:

<form action="/search/" method="get">

能够改造为:

<form action="" method="get">

action =""表示“将表单提交到当前页面所在的U酷威L”。通过这种转移,如若你将search(卡塔 尔(阿拉伯语:قطر‎视图挂接到另一个U凯雷德L,则没有供给记住纠正操作。

自己设置在window,用于轻便阅读代码和调养。

传过来的是二个列表

deb http://mirrors.163.com/ubuntu/ zesty main restricted universe multiverse
deb http://mirrors.163.com/ubuntu/ zesty-security main restricted universe multiverse
deb http://mirrors.163.com/ubuntu/ zesty-updates main restricted universe multiverse
deb http://mirrors.163.com/ubuntu/ zesty-proposed main restricted universe multiverse
deb http://mirrors.163.com/ubuntu/ zesty-backports main restricted universe multiverse
deb-src http://mirrors.163.com/ubuntu/ zesty main restricted universe multiverse
deb-src http://mirrors.163.com/ubuntu/ zesty-security main restricted universe multiverse
deb-src http://mirrors.163.com/ubuntu/ zesty-updates main restricted universe multiverse
deb-src http://mirrors.163.com/ubuntu/ zesty-proposed main restricted universe multiverse
deb-src http://mirrors.163.com/ubuntu/ zesty-backports main restricted universe multiverse

https://github.com/ysrc/xunfeng  

大家先看列表长度为1,而且还没“:”的气象:

保存后

下载后接着官方网址的window安装教程就能够。

else:
    filter_lst = []
    for i in ('ip', 'banner', 'port', 'time', 'webinfo.tag', 'webinfo.title', 'server', 'hostname'):
        filter_lst.append({i: {"$regex": list[0], '$options': 'i'}})
    query['$or'] = filter_lst
sudo apt-get update &&sudo apt-get upgrade&& sudo apt-get dist-upgrade

然后运维 Run.bat (得利用管理员运营,不然没影响。。卡塔 尔(阿拉伯语:قطر‎

  

要是你在虚构机中搭建景况,笔者墙裂建议您先安装快速照相。

 澳门新浦京娱乐场网站 6

再次回到三个对象,相近那样的: {'$or': [{'ip': {'$options': 'i', '$regex': '127.0.0.1'}},....]}将数组中那一个值构产生地点的样式,然后用’$or’ 简单估量是要将规范代入查询,用or来一而再接二连三。

澳门新浦京娱乐场网站:Python的Django框架中的表单处理示例,巡风源码阅读与分析。好了,开干!

 

再看列表长度不为1,也许有“:”的状态:

#0x00前言

安装成功。

for _ in list:

望风须求在python2.7mongodb3.2本子以上条件上安装 

阅读:

if _.find(':') > -1:

(作者根据巡风GitHub上的链接安装好mongodb,才发觉是3.0的本子,为了持续绕开晋级mongodb的坑,所以不用选错版本啊,可是坑坑更NB啊卡塔尔

使用的ide为pycharm
Run.bat

遍历列表,找到有“:”的动静。  然后区划  ,如果是查port就转为整型。 查banner的话,先推断是或不是存在普通话,要是有汉语就构形成

#0x01条件安插

 澳门新浦京娱乐场网站 7

{'banner': {'$options': 'i', '$regex': u'u963fu8428u5fb7aaa'}} 那样的,代入查询。

第一步安装时区——增添壹在这之中华新加坡的地面,然后点东京动用就能够更新为法国巴黎时间

 

从未有过汉语的话:mgo_text_split()那么些函数:

澳门新浦京娱乐场网站 8

mogod.exe 用于运行mongodb

def mgo_text_split(query_text):
    ''' split text to support mongodb $text match on a phrase '''
    sep = r'[`-=~!@#$%^&*()_ []{};'\:"|<,./<>?]'
    word_lst = re.split(sep, query_text)
    text_query = ' '.join('"{}"'.format(w) for w in word_lst)
    return text_query

第二步安装操作系统信赖

Run.py 启动web网站

 

sudo apt-get update && sudo apt-get install gcc libssl-dev libffi-dev python-dev libpcap-dev

Aider.py  # 扶植验证脚本

先按这几个特殊符号分割,然后连接成三个字符串 ”xxx” “xxx” “xxx”。

第三步安装Python环境

VulScan.py  # 漏洞检验引擎

 text_query = ' '.join('"{}"'.format(w) for w in word_lst)

那边用pip来设置python正视库,所以首先切换成root顾客设置pip(如果没有为root设置密码就先安装密码 sudo passwd root卡塔 尔(阿拉伯语:قطر‎,不是root安装pip会有警告提示(好疑似有的权力难点卡塔 尔(阿拉伯语:قطر‎,如下图

NAScan.py  # 互联网资金财产消息抓取引擎

那句能够看做:

澳门新浦京娱乐场网站 9

 

L =[]
for w in word_lst:
    L.append('"{}"'.format(w))
text_query = ' '.join(L)

su root(以下都在root下举行设置卡塔 尔(阿拉伯语:قطر‎

 

  

wget https://sec.ly.com/mirror/get-pip.py --no-check-certificate && python get-pip.py

Run.py

然后构造成这样:{'$text': {'$caseSensitive': True, '$search': '"xxx" "xxx" "xxx"'}}代入查询。

 澳门新浦京娱乐场网站 10

from views.View import app

if __name__ == '__main__':
    #app.debug = True
    app.run(threaded=True, port=8888,host='')

上边代码均生龙活虎致。

成功后更新pip到最新版本

 

最后else 就是q_key都并未有定义的话,就是{'key':’value’}

pip install -U pip

去到views/View.py

 

进而下载巡风文件包(没安装git的 sudo apt-get install git 一下)

 

 

sudo git clone https://github.com/ysrc/xunfeng

一共有24个方法。

$regex 是运用正则查询 $options 等于 i 则是不区分抑扬顿挫写。

完了后选拔pip安装python依赖库,先切换成xunfeng路线下(因为必要读取requirements.txt卡塔 尔(阿拉伯语:قطر‎

二个办法二个办法来看。

$search 文本索引查询 。$caseSensitive  是不是区分朗朗上口写。

pip install -r requirements.txt -i https://pypi.doubanio.com/simple/

 

 

澳门新浦京娱乐场网站 11

1.Search()

这一个MongoDB的标准,在此篇博客均有。

第四步设置mongo3.2以上版本数据库(小编这里用3.2版本卡塔 尔(阿拉伯语:قطر‎

# 搜索页
@app.route('/filter')
@logincheck
def Search():
    return render_template('search.html')

合法安装步骤

  

 

(1卡塔尔国安装公钥

@logincheck 使用了装饰器函数。跟过去翻开views/lib/Login.py

总得来讲那些函数正是将寻找的值转成mongoDB能查询的语句。

sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv EA312927
# 登录状态检查
def logincheck(f):
    @wraps(f)
    def wrapper(*args, **kwargs):
        try:
            if session.has_key('login'):
                if session['login'] == 'loginsuccess':
                    return f(*args, **kwargs)
                else:
                    return redirect(url_for('Login'))
            else:
                return redirect(url_for('Login'))
        except Exception, e:
            print e
            return redirect(url_for('Error'))

    return wrapper

 

(2)添加3.2的源

  

echo "deb http://repo.mongodb.org/apt/ubuntu xenial/mongodb-org/3.2 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-org-3.2.list

例如seesion中的login等于loginsuccess 就继续施行view.py下的函数。不然跳转掉Error模板。就是检查测量试验是还是不是有记名。

(3)Reload local package database

 

sudo apt-get update

回到Search() 加载search.html模板

以上3步截图

 

澳门新浦京娱乐场网站 12

 

(4卡塔尔国安装数据库

2.Deleteall()

sudo apt-get install -y mongodb-org

 

 (5卡塔尔国近些日子巡风陈设在3.2版本上,其余版本未有开展测量试验,为了牢固,这里不期望mongodb自个儿进级,故执行以下代码(不精晓有没有领悟对官方网址的情趣,有例外思想的弟兄,能够跟作者沟通卡塔尔国

# 删除所有
@app.route('/deleteall', methods=['post'])
@logincheck
@anticsrf
def Deleteall():
    Mongo.coll['Task'].remove({})
    return 'success'
echo "mongodb-org hold" | sudo dpkg --set-selections
echo "mongodb-org-server hold" | sudo dpkg --set-selections
echo "mongodb-org-shell hold" | sudo dpkg --set-selections
echo "mongodb-org-mongos hold" | sudo dpkg --set-selections
echo "mongodb-org-tools hold" | sudo dpkg --set-selections

  

(6卡塔 尔(阿拉伯语:قطر‎创制一个种类服务的公文,私下认可装完,是不能够直接运营service mongdb start

 

sudo nano /etc/systemd/system/mongodb.service

先推断了登入景况,多了一个@anticsrf 装饰器函数。跟过去查看views/lib/AntiCSLX570F.py

在此中输入

# 检查referer
def anticsrf(f):
    @wraps(f)
    def wrapper(*args, **kwargs):
        try:
            if request.referrer and request.referrer.replace('http://', '').split('/')[0] == request.host:
                return f(*args, **kwargs)
            else:
                return redirect(url_for('NotFound'))
        except Exception, e:
            print e
            return redirect(url_for('Error'))

    return wrapper
[Unit]
Description=High-performance, schema-free document-oriented database
After=network.target
Documentation=https://docs.mongodb.org/manual

[Service]
User=mongodb
Group=mongodb
ExecStart=/usr/bin/mongod --quiet --config /etc/mongod.conf

[Install]
WantedBy=multi-user.target

  

保留并退出

 

(7)启动mongodb服务

看清是不是有referrer头,并且将 再分割取第生龙活虎有的,也正是抽出网址的host,然后与本站host相相比。看是或不是同样。分化的话,跳转404页面。不然就继续实施。

sudo systemctl start mongodb

@anticsrf 就是防范CS凯雷德F漏洞的。

能够印证下mongodb是或不是不荒谬张开``

 

sudo systemctl status mongodb

回到Deleteall()

澳门新浦京娱乐场网站 13

Mongo 跟过去察觉是接连mongoDB。选择Task这么些数据表,移除全部数据。

PS:假若报错提醒说地点早已被侵占什么的,重启下系统再展开,应该就会得逞。

不畏将职务总的数量全部刨除。

(8卡塔 尔(英语:State of Qatar)设置mongodb服务开机运维

 澳门新浦京娱乐场网站 14

sudo systemctl enable mongodb

 

#0x02陈设和配置

 

 mongodb增加认证

3.Main()

  mongo
> use xunfeng
> db.createUser({user:'scan',pwd:'your password',roles:[{role:'dbOwner',db:'xunfeng'}]})
> exit
# 搜索结果页
@app.route('/')
@logincheck
def Main():
    q = request.args.get('q', '')
    page = int(request.args.get('page', '1'))
    plugin = Mongo.coll['Plugin'].find()  # 插件列表
    plugin_type = plugin.distinct('type')  # 插件类型列表
    if q:  # 基于搜索条件显示结果
        result = q.strip().split(';')
        query = querylogic(result)
        cursor = Mongo.coll['Info'].find(query).sort('time', -1).limit(page_size).skip((page - 1) * page_size)
        return render_template('main.html', item=cursor, plugin=plugin, itemcount=cursor.count(),
                               plugin_type=plugin_type, query=q)
    else:  # 自定义,无任何结果,用户手工添加
        return render_template('main.html', item=[], plugin=plugin, itemcount=0, plugin_type=plugin_type)

 这里的 your password 须要改造为你的申明密码,作者是DC老爷死忠粉,所以就用了batman

  

澳门新浦京娱乐场网站 15

看清是不是登陆(下同卡塔 尔(英语:State of Qatar)

澳门新浦京娱乐场网站 16

先获得传入的q 和page 。

 退出后切换来你的xunfeng/db路线下,导入数据库,推行(注意不忘记了最终的拾叁分“.”卡塔 尔(英语:State of Qatar)

plugin = Mongo.coll['Plugin'].find()  #连接数据库,列出Plugin中所有清单。

plugin_type = plugin.distinct('type') #从查询的所有清单里面获取名字是 type的数据。
mongorestore -h 127.0.0.1 --port 27017 -d xunfeng .

  

澳门新浦京娱乐场网站 17

接下来将q实行剪切“;”首尽管分开形似这种的 q= 127.0.0.1;127.8.8.1  

回到xunfeng路径下

分为列表传入querylogic()函数。 跟过去拜望views/lib/QueryLogic.py(详细:)

cd ..

nano Config.py

将寻找的值q转成mongoDB能查询的言辞。

校勘相关的配备文件,这里最首要改良数据库的端口(mongodb暗许端口号是27017卡塔 尔(阿拉伯语:قطر‎和你刚安装的数据库密码(小编这里是batman卡塔尔

cursor = Mongo.coll['Info'].find(query).sort('time', -1).limit(page_size).skip((page - 1) * page_size)

澳门新浦京娱乐场网站 18

在info表里把尺度代入查询sort()排序 limit()分页

 还有Run.sh文件

末尾传给视图

澳门新浦京娱乐场网站 19

 

 实现后,运行就可以

 

sh Run.sh

4.Getplugin()

澳门新浦京娱乐场网站 20

# 获取插件信息异步
@app.route('/getplugin', methods=['get', 'post'])
@logincheck
def Getplugin():
    type = request.form.get('type', '')
    risk = request.form.get('risk', '')
    search = request.form.get('search', '')
    query = {}
    if type:
        query['type'] = type
    if risk:
        query['level'] = risk
    if search:
        search = unquote(search)
        query['name'] = {"$regex": search, '$options': 'i'}
    cursor = Mongo.coll['Plugin'].find(query)
    rsp = []
    for i in cursor:
        result = {'name': i['name'], 'info': i['info']}
        rsp.append(result)
    return json.dumps(rsp)

 #0x03浏览器运营巡风

  

暗中同意地址127.0.0.1,80端口,使用admin/xunfeng321登入就能够

 

澳门新浦京娱乐场网站 21

获得了type risk search 是还是不是有值

澳门新浦京娱乐场网站 22

并没有的话,就满门询问。有的话 在Plugin表代入条件查询。然后将插件名字和新闻转json格式重临。

设置步骤到此基本停止 

 

接纳办法的录制演示

5.Addtask()

澳门新浦京娱乐场网站 23

# 新增任务异步
@app.route('/addtask', methods=['get', 'post'])
@logincheck
@anticsrf
def Addtask():
    title = request.form.get('title', '')
    plugin = request.form.get('plugin', '')
    condition = unquote(request.form.get('condition', ''))
    plan = request.form.get('plan', 0)
    ids = request.form.get('ids', '')
    isupdate = request.form.get('isupdate', '0')
    resultcheck = request.form.get('resultcheck', '0')
    result = 'fail'
    if plugin:
        targets = []
        if resultcheck == 'true':  # 结果集全选
            list = condition.strip().split(';')
            query = querylogic(list)
            cursor = Mongo.coll['Info'].find(query)
            for i in cursor:
                tar = [i['ip'], i['port']]
                targets.append(tar)
        else:  # 当前页结果选择
            for i in ids.split(','):
                tar = [i.split(':')[0], int(i.split(':')[1])]
                targets.append(tar)
        temp_result = True
        for p in plugin.split(','):
            query = querylogic(condition.strip().split(';'))
            item = {'status': 0, 'title': title, 'plugin': p, 'condition': condition, 'time': datetime.now(),
                    'target': targets, 'plan': int(plan), 'isupdate': int(isupdate), 'query': dumps(query)}
            insert_reuslt = Mongo.coll['Task'].insert(item)
            if not insert_reuslt:
                temp_result = False
        if temp_result:
            result = 'success'
    return result

  

 

先拿到了页面传了的值 先暗中认可result为fail

未有plugin的话一直回到fail

有的话,先判别结果集是或不是全选,将结果集的ip和port都走入列表,不然将当前页的ip将入列表。 然后推行插入。成功重回success

 

6.Task()

# 任务列表页面
@app.route('/task')
@logincheck
def Task():
    page = int(request.args.get('page', '1'))
    cursor = Mongo.coll['Task'].find().sort('time', -1).limit(page_size).skip((page - 1) * page_size)
    return render_template('task.html', item=cursor)

查询出职务消息,体现。

 澳门新浦京娱乐场网站 24

 

7.Recheck()

# 复测任务异步
@app.route('/taskrecheck')
@logincheck
@anticsrf
def Recheck():
    tid = request.args.get('taskid', '')
    task = Mongo.coll['Task'].find_one({'_id': ObjectId(tid)})
    result = 'fail'
    if task and task['plan'] == 0 and task['status'] == 2:  # 一次性任务,并且已经扫描完成
        result = Mongo.coll['Task'].update({'_id': ObjectId(tid)}, {'$set': {'status': 0}})
        if result:
            result = 'success'
    return result

  

找到任务后,推断扫描完毕后,更新数据库。再次来到success。

 

8.TaskDetail()

# 任务详情页面
@app.route('/taskdetail')
@logincheck
def TaskDetail():
    id = request.args.get('taskid', '')
    page = int(request.args.get('page', '1'))
    taskdate = request.args.get('taskdate', "")
    plugin_name = ''
    task_info = Mongo.coll['Task'].find_one({'_id': ObjectId(id)})
    if task_info:
        plugin_name = task_info['plugin']
    vulcount = 0
    lastscan = Mongo.coll["Result"].distinct('task_date', {'task_id': ObjectId(id)})
    result_list = []
    if len(lastscan) > 0:
        lastscan.sort(reverse=True)
        if taskdate:  # 根据扫描批次查看结果
            cursor = Mongo.coll['Result'].find(
                {'task_id': ObjectId(id), 'task_date': datetime.strptime(taskdate, "%Y-%m-%d %H:%M:%S.%f")}).sort(
                'time', -1).limit(page_size).skip((page - 1) * page_size)
        else:  # 查看最新批次结果
            taskdate = lastscan[0].strftime("%Y-%m-%d %H:%M:%S.%f")
            cursor = Mongo.coll['Result'].find(
                {'task_id': ObjectId(id), 'task_date': lastscan[0]}).sort('time', -1).limit(page_size).skip(
                (page - 1) * page_size)
        vulcount = cursor.count()
        for _ in cursor:
            result_list.append(
                {'ip': _['ip'], 'port': _['port'], 'info': _['info'], 'vul_level': _['vul_info']['vul_level'],
                 'time': _['time']})

        # 速度优化,数据量多采取不同的方式查询
        if len(result_list) > 100:
            ip_hostname = {}
            hostname = Mongo.coll['Info'].aggregate(
                [{'$match': {'hostname': {'$ne': None}}}, {'$project': {'_id': 0, 'ip': 1, 'hostname': 1}}])
            for _ in hostname:
                if 'hostname' in hostname:
                    ip_hostname[_["ip"]] = _["hostname"]
            for _ in result_list:
                if 'ip' in ip_hostname:
                    _['hostname'] = ip_hostname[_["ip"]]
                else:
                    _['hostname'] = ''
        else:
            for _ in result_list:
                hostname = Mongo.coll['Info'].find_one({'ip': _['ip']})
                if hostname and 'hostname' in hostname:
                    _['hostname'] = hostname['hostname']
                else:
                    _['hostname'] = ''
    return render_template('detail.html', item=result_list, count=vulcount, id=id, taskdate=taskdate,
                           plugin_name=plugin_name, scanlist=lastscan)

  

透过id找到职分详细的情况,然后将详细情况体现出来。有taskdate正是足以查询钦命的日期。未有那么些参数就是询问最新日期。当结果大于100,使用优化的查询语句。

 

 

9.DeleteTask()

# 删除任务异步
@app.route('/deletetask', methods=['get', 'post'])
@logincheck
@anticsrf
def DeleteTask():
    oid = request.form.get('oid', '')
    if oid:
        result = Mongo.coll['Task'].delete_one({'_id': ObjectId(oid)})
        if result.deleted_count > 0:
            result = Mongo.coll['Result'].delete_many({'task_id': ObjectId(oid)})
            if result:
                return 'success'
    return 'fail'

  

 

删去职责操作

 

10.Downloadxls()

# 下载excel报表异步
@app.route('/downloadxls', methods=['get', 'post'])
@logincheck
@anticsrf
def DownloadXls():
    tid = request.args.get('taskid', '')
    taskdate = request.args.get('taskdate', '')
    result_list = []
    if tid:  # 有任务id
        if taskdate:  # 从任务中拉取指定批次扫描结果
            taskdate = datetime.strptime(taskdate, "%Y-%m-%d %H:%M:%S.%f")
            cursor = Mongo.coll['Result'].find({'task_id': ObjectId(tid), 'task_date': taskdate}).sort(
                'time', -1)
        else:  # 从任务中直接取该任务最新一次扫描结果
            lastscan = Mongo.coll["Result"].distinct('task_date', {'task_id': ObjectId(tid)})
            if len(lastscan) == 0:
                cursor = []
                taskdate = datetime.now()
            else:
                lastscan.sort(reverse=True)
                taskdate = lastscan[0]
                cursor = Mongo.coll['Result'].find({'task_id': ObjectId(tid), 'task_date': taskdate}).sort(
                    'time', -1)
        title = Mongo.coll['Task'].find_one({'_id': ObjectId(tid)})['title']
        for _ in cursor:
            hostname = ''
            result = Mongo.coll['Info'].find_one({'ip': _['ip']})
            if result and 'hostname' in result:
                hostname = result['hostname']
            result_list.append(
                {'ip': _['ip'], 'port': _['port'], 'info': _['info'], 'vul_level': _['vul_info']['vul_level'],
                 'time': _['time'], 'vul_name': _['vul_info']['vul_name'], 'lastscan': taskdate, 'title': title,
                 'hostname': hostname})
        response = make_response(CreateTable(result_list, taskdate.strftime("%Y%m%d-%H%M%S")))
        if taskdate == '':
            response.headers["Content-Disposition"] = "attachment; filename=nodata.xls;"
        else:
            response.headers["Content-Disposition"] = "attachment; filename="   quote(
                title.encode('utf-8'))   taskdate.strftime(
                "%Y-%m-%d-%H-%M-%S")   ".xls;"
    else:  # 下载综合报表
        tasks = Mongo.coll['Task'].find({})
        t_list = []
        for t in tasks:
            name = t['title']
            lastscan = Mongo.coll["Result"].distinct('task_date', {'task_id': t['_id']})
            if len(lastscan) == 0:
                cursor = Mongo.coll['Result'].find({'task_id': t['_id']})
                taskdate = None
            else:
                lastscan.sort(reverse=True)
                taskdate = lastscan[0]
                cursor = Mongo.coll['Result'].find({'task_id': t['_id'], 'task_date': taskdate})
            for _ in cursor:  # 单任务详情
                hostname = Mongo.coll['Info'].find_one({'ip': _['ip']})
                if hostname:
                    _['hostname'] = hostname['hostname']
                else:
                    _['hostname'] = None
                _['title'] = name
                _['vul_level'] = _['vul_info']['vul_level']
                _['vul_name'] = _['vul_info']['vul_name']
                _['lastscan'] = taskdate
                t_list.append(_)
        response = make_response(CreateTable(t_list, 'all_data'))
        response.headers["Content-Disposition"] = "attachment; filename=all_data.xls;"
    response.headers["Content-Type"] = "application/x-xls"
    return response

  

 

216-243行 将围观结果查询出来后加到result_list

response = make_response(CreateTable(result_list, taskdate.strftime("%Y%m%d-%H%M%S")))

  

跟CreateTable()函数  View/lib/CreateExcel.py

def CreateTable(cursor, id):
    item = []
    item.append(['IP', '端口', '主机名', '风险等级', '漏洞描述', '插件类型', '任务名称', '时间', '扫描批次'])
    for i in cursor:
        if i['lastscan']:
            _ = [i['ip'], i['port'], i['hostname'], i['vul_level'], i['info'],
                 i['vul_name'], i['title'], i['time'].strftime('%Y-%m-%d %H:%M:%S'),
                 i['lastscan'].strftime('%Y-%m-%d %H:%M:%S')]
        else:
            _ = [i['ip'], i['port'], i['hostname'], i['vul_level'], i['info'],
                 i['vul_name'], i['title'], i['time'].strftime('%Y-%m-%d %H:%M:%S'), '']
        item.append(_)
    file = write_data(item, id)
    return file.getvalue()

  

创办个列表,将数据参预列表和陈说对应起来。write_data()函数

def write_data(data, tname):
    file = xlwt.Workbook(encoding='utf-8')
    table = file.add_sheet(tname, cell_overwrite_ok=True)
    l = 0
    for line in data:
        c = 0
        for _ in line:
            table.write(l, c, line[c])
            c  = 1
        l  = 1
    sio = StringIO.StringIO()
    file.save(sio)
    return sio

 

因此xlwt包,将数据生龙活虎行行写到文件里, 然后保存,文件名称为时间格式。

 

回到view/view.py

make_response(卡塔 尔(英语:State of Qatar)重返文件名。 245-250行设置了http头和下载文件名字。前面重返下载。

251-277行同上。

 

 

11.search_result_xls()

# 搜索结果报表下载接口
@app.route('/searchxls', methods=['get'])
@logincheck
@anticsrf
def search_result_xls():
    query = request.args.get('query', '')
    if query:
        result = query.strip().split(';')
        filter_ = querylogic(result)
        cursor = Mongo.coll['Info'].find(filter_).sort('time', -1)
        title_tup = ('IP', '端口号', '主机名', '服务类型')
        xls = [title_tup, ]
        for info in cursor:
            item = (
                info.get('ip'), info.get('port'),
                info.get('hostname'), info.get('server')
            )
            xls.append(item)
        file = write_data(xls, 'search_result')
        resp = make_response(file.getvalue())
        resp.headers["Content-Disposition"] = "attachment; filename=search_result.xls;"
        resp.headers["Content-Type"] = "application/x-xls"
        resp.headers["X-Content-Type-Options"] = "nosniff"
        return resp
    else:
        redirect(url_for('NotFound'))

 

搜求结果有个话,写入文件下载。未有的话NotFound

 

12.Plugin()

# 插件列表页
@app.route('/plugin')
@logincheck
def Plugin():
    page = int(request.args.get('page', '1'))
    cursor = Mongo.coll['Plugin'].find().limit(page_size).skip((page - 1) * page_size)
    return render_template('plugin.html', cursor=cursor, vultype=cursor.distinct('type'), count=cursor.count())

  

 

查询-展示

 

13.AddPlugin()

独自剖判 ()

 

14.DeletePlugin()

# 删除插件异步
@app.route('/deleteplugin', methods=['get', 'post'])
@logincheck
@anticsrf
def DeletePlugin():
    oid = request.form.get('oid', '')
    if oid:
        result = Mongo.coll['Plugin'].find_one_and_delete({'_id': ObjectId(oid)}, remove=True)
        if not result['filename'].find('.') > -1:
            result['filename'] = result['filename']   '.py'
        if os.path.exists(file_path   result['filename']):
            os.remove(file_path   result['filename'])
            return 'success'
    return 'fail'

  

 

删去插件,从数据库中删去况且删除文件

 

 

15.Analysis

# 统计页面
@app.route('/analysis')
@logincheck
def Analysis():
    ip = len(Mongo.coll['Info'].distinct('ip'))
    record = Mongo.coll['Info'].find().count()
    task = Mongo.coll['Task'].find().count()
    vul = int(Mongo.coll['Plugin'].group([], {}, {'count': 0},'function(doc,prev){prev.count = prev.count   doc.count}')[0]['count'])
    plugin = Mongo.coll['Plugin'].find().count()
    vultype = Mongo.coll['Plugin'].group(['type'], {"count":{"$ne":0}}, {'count': 0},'function(doc,prev){prev.count = prev.count   doc.count}')
    cur = Mongo.coll['Statistics'].find().sort('date', -1).limit(30)
    trend = []
    for i in cur:
        trend.append(
            {'time': i['date'], 'add': i['info']['add'], 'update': i['info']['update'], 'delete': i['info']['delete']})
    vulbeat = Mongo.coll['Heartbeat'].find_one({'name': 'load'})
    scanbeat = Mongo.coll['Heartbeat'].find_one({'name': 'heartbeat'})
    if vulbeat == None or scanbeat == None:
        taskpercent = 0
        taskalive = False
        scanalive = False
    else:
        taskpercent = vulbeat['value'] * 100
        taskalive = (datetime.now() - vulbeat['up_time']).seconds
        scanalive = (datetime.now() - scanbeat['up_time']).seconds
        taskalive = True if taskalive < 120 else False
        scanalive = True if scanalive < 120 else False
    server_type = Mongo.coll['Info'].aggregate(
        [{'$group': {'_id': '$server', 'count': {'$sum': 1}}}, {'$sort': {'count': -1}}])
    web_type = Mongo.coll['Info'].aggregate([{'$match': {'server': 'web'}}, {'$unwind': '$webinfo.tag'},
                                             {'$group': {'_id': '$webinfo.tag', 'count': {'$sum': 1}}},
                                             {'$sort': {'count': -1}}])
    return render_template('analysis.html', ip=ip, record=record, task=task, vul=vul, plugin=plugin, vultype=vultype,
                           trend=sorted(trend, key=lambda x: x['time']), taskpercent=taskpercent, taskalive=taskalive,
                           scanalive=scanalive, server_type=server_type, web_type=web_type)

  澳门新浦京娱乐场网站 25

看了页面回来看代码,那一个法子正是将数据库中的值查询出来然后显示,不具体解析语句。

 

 

16.Config()

# 配置页面
@app.route('/config')
@logincheck
def Config():
    val = []
    table = request.args.get('config', '')
    if table in ("vulscan", "nascan"):
        dict = Mongo.coll['Config'].find_one({'type': table})
        if dict and 'config' in dict:
            dict = dict['config']
            for _ in dict:
                if _.find('_') > 0:
                    item_type = "list"
                else:
                    item_type = "word"
                val.append({"show": item_type, "type": _, "info": dict[_]["info"], "help": dict[_]["help"],
                            "value": dict[_]["value"]})
    val = sorted(val, key=lambda x: x["show"], reverse=True)
    return render_template('config.html', values=val)

  

 

判断是爬虫引擎依旧扫描引擎,然后分别查询出多少。

 

17.UpdateConfig()

# 配置更新异步
@app.route('/updateconfig', methods=['get', 'post'])
@logincheck
@anticsrf
def UpdateConfig():
    rsp = 'fail'
    name = request.form.get('name', 'default')
    value = request.form.get('value', '')
    conftype = request.form.get('conftype', '')
    if name and value and conftype:
        if name == 'Masscan' or name == 'Port_list':
            origin_value = Mongo.coll['Config'].find_one({'type': 'nascan'})["config"][name]["value"]
            value = origin_value.split('|')[0]   '|'   value
        elif name == 'Port_list_Flag':
            name = 'Port_list'
            origin_value = Mongo.coll['Config'].find_one({'type': 'nascan'})["config"]['Port_list']["value"]
            value = value   '|'   origin_value.split('|')[1]
        elif name == 'Masscan_Flag':
            name = 'Masscan'
            path = Mongo.coll['Config'].find_one({'type': 'nascan'})["config"]["Masscan"]["value"]
            if len(path.split('|')) == 3:
                path = path.split('|')[1]   "|"   path.split('|')[2]
            else:
                path = path.split('|')[1]
            if value == '1':
                value = '1|'   path
            else:
                value = '0|'   path
        result = Mongo.coll['Config'].update({"type": conftype}, {'$set': {'config.'   name   '.value': value}})
        if result:
            rsp = 'success'
    return rsp

  澳门新浦京娱乐场网站 26 

先判断是纠正哪二个安插。

 

依照name来剖断是哪个配置,就从数据库去取对应的值,然后把提交过来的value加上去更新。

 

18.PullUpdate()

19.checkupdate()

20.installplugin()

# 拉取线上最新插件异步
@app.route('/pullupdate')
@logincheck
@anticsrf
def PullUpdate():
    rsp = 'err'
    f = urlopen('https://sec.ly.com/xunfeng/getlist')
    j = f.read().strip()
    if j:
        try:
            remotelist = json.loads(j)
            #remotelist_temp = copy.deepcopy(remotelist)
            plugin = Mongo.coll['Plugin'].find({'source': 1})
            for p in plugin:
                for remote in remotelist:
                    if p['name'] == remote['name'] and remote['coverage'] == 0:
                        remotelist.remove(remote)
            locallist = Mongo.coll['Update'].aggregate([{'$project': {'_id': 0, 'unicode': 1}}])
            local = []
            for i in locallist:
                local.append(i['unicode'])
            ret = [i for i in remotelist if i['unicode'] not in local]
            for i in ret:
                i['isInstall'] = 0
                Mongo.coll['Update'].insert(i)
            rsp = 'true'
        except:
            pass
    return rsp


# 检查本地已知的线上插件列表异步
@app.route('/checkupdate')
@logincheck
@anticsrf
def CheckUpdate():
    json = []
    notinstall = Mongo.coll['Update'].find({'isInstall': 0}).sort('unicode', -1)
    for _ in notinstall:
        json.append({'unicode': _['unicode'], 'name': _['name'], 'info': _['info'], 'time': _['pushtime'],
                     'author': _['author']})
    return dumps(json)


# 安装/下载插件异步
@app.route('/installplugin')
@logincheck
@anticsrf
def installplugin():
    rsp = 'fail'
    unicode = request.args.get('unicode', '')
    item = Mongo.coll['Update'].find_one({'unicode': unicode})
    json_string = {'add_time': datetime.now(), 'count': 0, 'source': 1}
    file_name = secure_filename(item['location'].split('/')[-1])
    if os.path.exists(file_path   file_name):
        if ".py" in file_name:
            db_record = Mongo.coll['Plugin'].find_one({'filename': file_name.split('.')[0]})
        else:
            db_record = Mongo.coll['Plugin'].find_one({'filename': file_name})
        if not db_record or not db_record['source'] == 1:
            file_name = file_name.split('.')[0]   '_'   str(datetime.now().second)   '.'   
                        file_name.split('.')[-1]
        else:
            db_record = Mongo.coll['Plugin'].delete_one({'filename': file_name.split('.')[0]})
    if item['location'].find('/') == -1:
        urlretrieve('https://sec.ly.com/xunfeng/getplugin?name='   item['location'], file_path   file_name)
    else:
        urlretrieve(item['location'], file_path   file_name)  # 兼容旧的插件源
    if os.path.exists(file_path   file_name):
        try:
            if file_name.split('.')[-1] == 'py':
                module = __import__(file_name.split('.')[0])
                mark_json = module.get_plugin_info()
                json_string['filename'] = file_name.split('.')[0]
            else:
                json_text = open(file_path   file_name, 'r').read()
                mark_json = json.loads(json_text)
                json_string['filename'] = file_name
                mark_json.pop('plugin')
            json_string.update(mark_json)
            Mongo.coll['Plugin'].insert(json_string)
            Mongo.coll['Update'].update_one({'unicode': unicode}, {'$set': {'isInstall': 1}})
            rsp = 'success'
        except:
            pass
    return rsp

  

 

均为立异插件的,不细分析。

在 查询出新型插件,然后与数据库对比。

翻看是还是不是本地有安装。

https://sec.ly.com/xunfeng/getplugin?name= 在那完结下载。

 

21.Login()

22.Loginout()

# 登录
@app.route('/login', methods=['get', 'post'])
def Login():
    if request.method == 'GET':
        return render_template('login.html')
    else:
        account = request.form.get('account')
        password = request.form.get('password')
        if account == app.config.get('ACCOUNT') and password == app.config.get('PASSWORD'):
            session['login'] = 'loginsuccess'
            return redirect(url_for('Search'))
        else:
            return redirect(url_for('Login'))


# 登出异步
@app.route('/loginout')
@logincheck
def LoginOut():
    session['login'] = ''
    return redirect(url_for('Login'))

  

 

二个登录二个登载。

 

 

23.NotFound()

24.Error()

@app.route('/404')
def NotFound():
    return render_template('404.html')


@app.route('/500')
def Error():
    return render_template('500.html')

  

显示404 或500

 

开卷了view.py 里的种种方法具体都以干嘛的,对巡风扫描器全部有八个差不离领会。

感谢ysrc开源。

 

本文由澳门新浦京娱乐场网站发布于www.146.net,转载请注明出处:澳门新浦京娱乐场网站:Python的Django框架中的表