用python做课表_python模拟登陆urp教务处选课&抓取课表

!!!选课功能已添加!!!

本文地址

csdn

前段时间小编写了一篇利用爬虫做词云分析的帖子,有粉丝反馈说想进一步学习爬虫,所以小编今天就用爬虫模拟登陆学校的教务处为例和大家共同学习。坊间有传言说好多同学们学会爬虫后,第一个最想爬取的或者说第一个最想练手的网站就是学校的教务处系统,我相信这也是计算机类专业学生都想做的事儿吧?!

思路解析:

A 、先打开登陆页面,获取cookies;B、再访问验证码的地址,因为验证码是动态的,每次打开都是不同的,所以我们需要保存之前的cookie,保证获取的验证码和后续要提交的表单是同步的。C、然后就是识别验证码的环节,登陆成功后为了避免网页的重定向,所以还需要用requests的session函数禁止重定向。D、构建post表单请求数据,然后将数据提交给网站 F、获取响应头信息,通过返回的网页内容来判断是否登陆成功。

一、模拟登陆

在开题之前,先带大家认识一下:浏览器请求网页的流程。

在web应用中,服务器把网页传给浏览器,实际上就是把网页的HTML发送给浏览器。但是在没有携带cookie的情况下,如果IP短时间高并发的请求网站,该IP就会被封。这里解释一下cookie,cookie是一种回话机制,可以用来存储很多信息,也经常用于反爬。我们一般处理cookie有两种方法:1、cookie的保存 2、cookie的读取。然后登陆部分的处理通常采用的方法就是将爬虫模拟成浏览器,有:1、通过opener添加headers 2、通过requests添加headers 3、批量添加headers 。小编采用的是第二种方法。

用浏览器打开教务处网页的界面如图:

login.PNG

上面提到的headers,cookie等参数的获取,也是有两种方法获取。1、在登陆页面按F12进入开发者模式,选择network,再选中preserve log,选中login页面 ,如图操作:

requests.png

给大家解释下上图的主要信息,在伪装浏览器部分中,重点是获取请求的头部信息和服务器返回的响应头(response headers)。

1 request url : 是浏览器真实请求的域名地址

2 accept :告诉服务器自己接受什么类型

3 accept language:浏览器所希望的语言种类,当服务器能够提供一种以上的语言版本时要用到

4 Connection 表示是否持久连接。如果后面的value值为 ”keep alive“,或者看到请求使用的是Http1.1(默认进行持久连接)

5 host 初始 url 中的主机端口

6 User-Agent 浏览器类型

浏览器向服务器提交的内容的获取:

我们可以故意输错账号或密码 得到提交的表单信息 ,可以通过进入开发者工具或者fiddler得到表单信息 。如下图:

post.PNG

第二种方法就是通过fiddler抓包分析(简单粗暴),个人比较喜欢。(有关 fiddler 的用法,小编会随后为大家更新)

话不多说,给大家上代码:

import requests

import http.cookiejar

from PIL import Image

from bs4 import BeautifulSoup

#导包

cookies = {} #构建一个空字典用来存放cookies

#伪装成浏览器进行网页请求

headers = {

'Connection': 'Keep-Alive',

'Accept-Language': 'zh-CN,zh;q=0.8',

'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',

'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36 SE 2.X MetaSr 1.0',

'Accept-Encoding': 'gzip, deflate',

'Upgrade-Insecure-Requests':'1',

'Referer': 'http://172******8******',

'X-Requested-With': 'XMLHttpRequest',

'Host': '172.*********',

}

#

#

#构建提交表单

def login(username, password, code):

url = 'http://172.************/loginAction.do'

form = {

'zjh1': '',

'tips': '',

'lx': '',

'evalue': '',

'eflag': '',

'fs': '',

'dzslh': '',

'zjh': username,

'mm': password,

'v_yzm': code

}

resp = requests.post(url, headers=headers, data=form, cookies=cookies)

写到这里,实在是忍不住要吐槽urp教务系统,代码写得像**一样,小编在看源码时就看懂一个参数“mm”=密码,其他的参数,,,,,,

验证码的识别

一般来讲,验证码的识别有三种方法:

1 人工识别

2 调用tesseract-ocr,自动识别

3 接入付费接口进行识别

这里小编采用的是人工识别,我尝试了tesseract的pillow库来识别,额,,,,,效果嘛,因为是免费的,所以识别的成功率一言难尽啊。数字“2”和英文字母“Z”分不清楚,“N”和"M“也容易混淆,特别是字母”q",我也真的是醉了,给大家看下我们教务系统的验证码

checkcode.jpg

没有经过任何的噪声处理,成功率仅为百分之25.真的是 # 很无语 #。

再给大家看一下识别的案例(为了提高识别率,做了灰度处理):

案例.png

思路就是将验证码保存到本地,然后再调用PIL的image库,把验证码呈现出来,手动输入,完成表单的提交。其实我更想爬取所有的验证码,然后利用神经网络和机器学习做一个训练集,进行自动识别。

imgurl = '验证码图片的请求链接'

mysession = requests.Session()

html = mysession.get(imgurl,timeout=60*4)

checkcode = mysession.get(imgurl,timeout=60*4)

with open('checkcode.png','wb') as f:

f.write(checkcode.content)

check_img = Image.open("checkcode.png")

check_img.show()

v_yzm = input("code:")

然后我们就可以通过页面返回内容来判断是否登陆成功,小编选取的是课表查询

#课表查询

def get_classinfo():

url = 'http://172.20.139.153/xkAction.do?actionType=6'

resp = requests.get(url, headers=headers, cookies=cookies)

soup = BeautifulSoup(resp.text,'lxml')

class = soup.find_all("td")

print(class)

选课的过程跟小编前段时间做的我校图书馆选座的流程差不多,也是提交一系列的表单

!!!!选课

def ch_class(clanum):

url = "http://172.@*0.1##.153/xkAction.do?"

# resp = requests.get(url,headers = headers,cookies = cookies)

form_1= {

'actionType':'2',

'pageNumber':'-1',

'oper 1':'ori'

}

form_2 = {

'kch':clanum,

'actionType':'2',

'oper2':'gl',

'pageNumber' :'-1'

}

form_3={

'kch':clanum + '_01',

'preActionType':'2',

'actionType':'9'

}

url_1 = 'http://172**.1*3/xkAction.do?@@2*8*'

response = requests.post(url,data = form_1,cookies = cookies)

responce = requests.post(url_1,data = form_2,cookies = cookies,allow_redirects=False)

soup = BeautifulSoup(responce.content,'lxml')

pagecon=soup.find("strong") #检测是否选课成功,可以用bool判断

#大家可以在这里增加死循环,不停的提交表单,直到输出不为空

print(pagecon)

爬取结果如图:

(ps:这是没有经过字符串处理的,后续小编会系统化输出结果以及完善成绩查询和选课内容)

mmexport1536506596352.jpg

代码写得有点恶心,希望大家多多指教。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: ASE_URP是一个Unity的Shader插件,它可以用于在Universal Render Pipeline中创建自定义的阴影渲染效果。 ASE_URP通过添加Shader Graph节点来实现仅渲染阴影的效果。在创建Shader Graph时,我们可以使用Directional Light节点来控制主光源,然后使用Shadow Collector节点来收集阴影信息。接下来,可以通过Shadow Color节点来设置阴影的颜色和透明度。最后,我们可以将此Shader Graph应用于我们的模型上,从而实现仅渲染阴影的效果。 渲染只有阴影的场景可以帮助我们在视觉上强调物体之间的关系和方向。例如,在一个房间中,灯光透过窗户投射出的阴影可以帮助我们感知光线的方向和空间的深度。对于游戏开发人员来说,使用ASE_URP的仅渲染阴影效果可以增加游戏场景的真实感和氛围。 值得注意的是,ASE_URP只是帮助我们创建只渲染阴影的Shader,具体的渲染结果还需要依赖于Universal Render Pipeline的渲染管线和渲染设置。同时,为了达到更好的渲染效果,我们可能需要正确设置光源属性和材质属性。 ### 回答2: ase_urp是Unity的通用渲染管线(Universal Render Pipeline)中的一个功能模块,用于实现阴影的渲染。 在使用ase_urp渲染方法时,可以通过特定的设置实现只渲染阴影的效果。首先,需要将渲染设置从默认的Forward Renderer切换为Universal Render Pipeline,然后启用阴影渲染模式。 在Universal Render Pipeline中,有一种渲染模式称为Shadow Caster Pass,可以单独渲染物体的阴影。在shader中,通过设置材质的阴影参数为ShadowCaster来使用这个渲染模式。这样,只有被设置为ShadowCaster的物体才会被渲染为阴影,其他物体将不会被渲染。 此外,还可以使用阴影接收器(ShadowReceiver)功能来控制阴影的显示。通过设置接收器属性,可以选择性地使物体接收阴影,或者将阴影强度降低或增加。 总的来说,使用ase_urp渲染阴影的方法是通过将渲染管线切换为Universal Render Pipeline,并设置特定的阴影渲染模式和阴影接收器属性,来实现只渲染阴影的效果。 ### 回答3: ase_urp是一种渲染技术,它专门用于在Unity的URP(通用渲染管线)中只渲染阴影。它可以通过在模型上设置渲染层和使用相应的阴影材质来实现。 首先,我们需要将模型的渲染层设置为一个新的层,例如"ShadowLayer"。在Unity的Inspector面板中,选择该模型,然后在Layer属性中选择"ShadowLayer"。 接下来,我们需要创建一个新的阴影材质。在项目资源中,右键点击并选择Create -> Material,然后将其命名为"ShadowMaterial"。在Inspector面板中,选择该材质并开启"Receive Shadows"以及"Cast Shadows"选项。可以根据需求,调整材质的其他属性如颜色和透明度等。 然后,将新创建的阴影材质应用到模型上。在Inspector面板中,选择该模型并将其Renderer组件的Material属性设置为"ShadowMaterial"。 最后,需要将Camera的渲染设置进行调整,以便仅渲染阴影并隐藏其他部分。选中Camera对象,在Inspector面板中将其Culling Mask设置为只包括"ShadowLayer"层。然后,将该Camera的Clear Flags设置为"Depth Only",这样只有模型的深度信息被渲染出来。 通过以上步骤,我们就可以实现使用ase_urp仅渲染阴影。请注意,这只会在URP渲染管线中生效,如果使用其他管线,需要根据对应的渲染设置进行调整。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值