Selenium初探之自动备份设备配置文件及上传

发表于:2019-4-15 14:04

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:hackerbaba    来源:freebuf

  一、背景介绍
  在传统的网络安全架构中,难免会有一些重要的安全设备或是软件配置需要定期备份,统一归档。一是为了满足合规,二是在设备变更出现问题的时候,能够快速回滚。手工定期备份难免会有遗漏,且浪费大量人力。
  为了满足这一需求,我利用Selenium浏览器自动化测试框架)实现这个自动备份功能,当然其他的python爬虫模块(比如request)也能实现这个功能(大体步骤都差不多),这个后续会继续分享给大家,这次就不在这里讨论。实现自动备份后,再利用python  FTP模块实现统一归档到FTP服务器。备份周期直接利用cron命令即可。既然有脚本自然少不了是否备份成功告警,利用logging模块记录日志,然后再通过rsyslog或第三方转发器传至日志分析平台即可实现告警,我们公司由于使用的splunk,利用splunk forward传输日志即可。有些人可能对Selenium不是太了解,下面我稍微简单介绍一下Selenium。
  二、Selenium+Chrome配置及功能说明
  Selenium是一个浏览器自动化测试框架。Selenium测试直接运行在浏览器中,就像真正的用户在操作一样。Selenium在爬虫中的运用主要就是查找html相应元素并进行元素交互操作,常见的8种元素定位的方法如下:
   find_element_by_name
  find_element_by_id
  find_element_by_xpath
  find_element_by_link_text
  find_element_by_partial_link_text
  find_element_by_tag_name
  find_element_by_class_name
  find_element_by_css_selector
  其中最常用的就是find_element_by_name/id/xpath/link_text,其中xpath推荐使用浏览器插件定位元素。火狐浏览器一般使用 firebug 和 firepath 定位元素;谷歌浏览器一般使用xpath helper插件定位元素。
  Windows/linux除了安装Selenium模块外,一般需要下载浏览器对应的webdriver驱动到相应文件夹声明并调用浏览器,一个简单的示例如下:
  from selenium import webdriver
  browser = webdriver.Chrome() 或 browser =webdriver.Firefox()   #调用谷歌或者火狐浏览器
  browser.get(“http://www.baidu.com“)  #浏览器打开百度
  print(browser.page_source)  #打印百度首页的源码
  browser.close()  #关闭浏览器
  在linux系统中,还需要声明一些“无头”配置,具体见实现见脚本。
  三、python+selenium+无头Chrome具体实现脚本
  Python环境:3.7.0  selenium:3.141.0  chrome:72.0.3626.119
  Webdriver下载地址  https://chromedriver.storage.googleapis.com/index.html
  自动备份对象:某品牌WAF设备,其他设备更改IP地址、定位相关html元素即可。
   #coding=utf-8
  import os
  import time
  import logging
  import ftplib
  from ftplib import FTP
  from selenium import webdriver
  from selenium.webdriver.common.by import By
  from selenium.webdriver.common.keys importKeys
  from selenium.webdriver.support.ui import Select
  from selenium.webdriver importDesiredCapabilities
  from selenium.webdriver.chrome.optionsimport Options
  Device = 'WAF'     #定义设备类型
  IP = 'x.x.x.x'         #目标IP
  dir_time = time.strftime('%Y-%m-%d',time.localtime())
  #输出当前"年-月-日"时间
  dir_backup =f'/opt/sec_backup/{IP}_{Device}/{dir_time}'
  #chrome下载的地址备份文件的路径
  log_name =f'/opt/sec_backup/log/{IP}/{dir_time}.log'
  #存放日志文件的路径
  if os.path.exists(dir_backup):
  pass
  else:
  os.mkdir(f'/opt/sec_backup/{IP}_{Device}/{dir_time}')
  #创建dir_backup路径
  host = 'X.X.X.X'
  port = 21
  user = 'XXXX'
  pwd = 'XXXXX'
  #以上定义FTP服务器相关信息
  logging.basicConfig(filename=log_name,level=logging.INFO,format='%(asctime)s - %(name)s - %(levelname)s - %(message)s')
  logger = logging.getLogger(__name__)
  #定义日志输出格式
  try:
  opts = Options()
  opts.headless=True
  opts.add_argument('--no-sandbox')
  opts.add_argument('--disable-gpu')
  capabilities = DesiredCapabilities.CHROME.copy()
  capabilities['acceptSslCerts'] = True
  capabilities['acceptInsecureCerts'] = True
  prefs = {'download.prompt_for_download': False,
  'download.directory_upgrade': True,
  'safebrowsing.enabled': False,
  'safebrowsing.disable_download_protection': True}
  opts.add_experimental_option('prefs', prefs)
  driver = webdriver.Chrome(options=opts,desired_capabilities=capabilities)
  #以上是“无头”的一些配置,具体就不一一展开
  driver.implicitly_wait(10)
  #设置超时时间10秒钟
  driver.command_executor._commands["send_command"] =("POST",'/session/$sessionId/chromium/send_command')
  driver.desired_capabilities['browserName'] = 'ur mum'
  params = {'cmd': 'Page.setDownloadBehavior', 'params': {'behavior':'allow', 'downloadPath': '%s' %dir_backup }}
  driver.execute("send_command", params)
  #Chrome下载备份文件到dir_backup目录
  driver.get(f"https://{IP}/login/requireLogin")
  driver.find_element_by_id("username").send_keys("xxx")
  driver.find_element_by_id("password").send_keys("xxx")
  driver.find_element_by_id("loginButton").click()
  driver.find_element_by_id("one3").click()
  driver.find_element_by_id("two32").click()
  driver.switch_to.frame("mainFrame")
  driver.find_element_by_link_text("配置同步").click()
  driver.find_element_by_xpath("(//input[@id='tmp'])[2]").click()
  time.sleep(30)
  driver.switch_to.alert.accept()
  driver.find_element_by_xpath("//*[@id='backpointtable']/tbody/tr[2]/td[5]/img[3]").click()
  while True:
  if os.listdir(dir_backup) andos.listdir(dir_backup)[0].endswith('.wafc'):
  #备份周期是天,一天只生成一个固定目录,里面只有一个备份文件,故判断是否有文件即可
  logger.info('备份成功')
  break
  else:
  continue
  driver.find_element_by_link_text("配置同步").click()
  driver.find_element_by_xpath("//*[@id='backpointtable']/tbody/tr[2]/td[5]/img[4]").click()
  confirm2 = driver.switch_to.alert
  confirm2.accept()
  driver.quit()
  #logger.info('删除旧备份成功')
  except Exception as e:
  logger.info(f"自动备份出现异常,异常内容:{e}")
  def ftpconnect():
  ftp_server = host
  username = user
  password = pwd
  ftp = FTP()
  ftp.set_debuglevel(0)
  ftp.connect(ftp_server, 21)
  ftp.login(username, password)
  return ftp
  def uploadfile():
  try:
  ftp = ftpconnect()
  remotepath = ftp.mkd(f'/{IP}-{Device}/{dir_time}')
  except:
  pass
  ftp.cwd(remotepath)
  bufsize = 1024
  localfile = dir_backup + '/' + os.listdir(dir_backup)[0]
  remotefile = os.listdir(dir_backup)[0]
  print(localfile)
  fp = open(localfile, 'rb')
  ftp.storbinary('STOR ' + remotefile, fp, bufsize)
  #上传本地localfile,至remotepath,并命名remotefile
  ftp.set_debuglevel(0)
  #关闭ftp的调试模式,如果设置为2,则输出详细信息
  fp.close()
  if __name__ == '__main__':
  try:
  uploadfile()
  except Exception as e:
  logger.info(f"文件上传出现异常,异常内容:{e}")
  else:
  logger.info('文件上传成功')
  四、效果图
  

      上文内容不用于商业目的,如涉及知识产权问题,请权利人联系博为峰小编(021-64471599-8017),我们将立即处理。
《2023软件测试行业现状调查报告》独家发布~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2024
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号