6.3
- mib browser的使用
载入mib文件,树状分析oid
分到最细的oid有名字,有介绍,有oid具体值
可以是oid也可以是字符串
模板定义自动发现规则
1.创建自定义发现规则
2.设置监控项原型
6.4
item key
proc.num[
, , , ]
user为主机的用户名, cmdline为ps-ef查询出的进程信息描述
在weblogic中,可以使用它的java进程目录是否在进程中存在来判断weblogic是否挂掉
6.5
6.10
- zabbix media mediatype user.addmedia
- zabbix 采集器(zabbix trapper)
zabbix_sender -z 192.168.1.66 -p 10051 -s 'oracle' -k 'version' -o 'ok' -vv
- 自动发现规则
- 企业微信的用户列表获取
文档 https://work.weixin.qq.com/api/doc#90000/90135/90664
- 问题
- py脚本可以像shell脚本一样 ./xxx.py执行
- xshell
- py2 和 py3 的区别
datetime.datetime.timestamp(datetime.datetime.now()) 在3中能用,2 中不能用
6.11
- openpyxl
- zabbix
6.12
1.字典操作
python与 oracle客户端的关系
6.13
6.14
- 低版本的zabbix server 无法监控高版本的zabbix agent 反之,高版本的server可以监控agent
- excel类中的fill是对[]中指定的列的值进行判断,可在format_cell方法中编辑逻辑,对示警度进行范围指定
check 是一个字典,指定了列数和值,与fill配合使用 agent的配置
HostMetadataItem=system.uname
应用:主机元数据,应用在自动注册的动作上
syste.uname >>> Linux zabbix 3.10.0-327.el7.x86_64 #1 SMP Thu Nov 19 22:10:57 UTC 2015 x86_646.17
orm中创建新对象,create get_or_create() 对于NOT NULL的字段,不给他赋值也能创建? 为啥?
es 用索引中的内容来匹配相应的索引,再删除。
POST twitter/_delete_by_query
{
"query": {
"match": {
"message": "some message"
}
}
}
6.18
- 通过删除原文件夹,增加新文件夹的方式来更新相关代码,django没有自动重启,debug也开的呢,为啥?
screen命令的使用
screen -r monitor 进入运行monitor进程的screen,进入屏幕后,就跟直接运行一样,类似于windows的虚拟桌面,在一台主机上开了第二个linux屏幕。
在screen内,ctrl + a +d 退出当前屏幕,- datetime.datetime.today() >> datetime.datetime(2019, 6, 18, 17, 59, 9, 748551)
datetime.date.today() >> datetime.date(2019, 6, 18) es的快照在恢复时,需保证这条索引已经被删除,才能恢复成功
6.19
- django迁移模型的时候,可以指定单个app。
在迁移logminer的时候,python manager.py makemigartions logminer.esbackup 迁移出错。logminer的models包含了底下所有子应用的models,
解决:使用 python manager.py makemigartions logminer 不指定下一层的应用了。 tzinfo的问题。datetime对象是可以比较大小的。
6.20
- django中user类的指定,drf中的token的使用,此token使用key作为主键,
class Token(models.Model):
"""
The default authorization token model.
"""
key = models.CharField("Key", max_length=40, primary_key=True)
user = models.ForeignKey(
settings.AUTH_USER_MODEL, related_name="auth_token",
on_delete=models.CASCADE, verbose_name="User"
)
created = models.DateTimeField("Created", auto_now_add=True)
class Meta:
db_table = 'token'
verbose_name = "Token"
verbose_name_plural = "Tokens"
def save(self, *args, **kwargs):
if not self.key:
self.key = self.generate_key()
return super(Token, self).save(*args, **kwargs)
def generate_key(self):
return binascii.hexlify(os.urandom(20)).decode()
def __str__(self):
return self.key
- 在创建django项目时,名称不能有特殊字符,使用xx-xx,提示名字不规范,
在创建项目时,后面可以指定路径,在git上拉下来创建的仓库,进入仓库目录,django-admin startproject xxxxx . 注意这个 . 指的就是在当前目录下创建项目 - calendar 日历模块
https://blog.csdn.net/tz_zs/article/details/86629959
使用此脚本获取全年月份及天数,通过一个api来获取节假日
import calendar
import datetime
import json
import requests
tmp = {}
year = 2019
for i in range(1, 13):
days = calendar.monthcalendar(year=2019, month=i)
for k in days:
for v in k:
if v != 0:
if i < 10:
if v < 10:
tmp[int(str(year) + '0' + str(i) + '0' + str(v))] = ''
else:
tmp[int(str(year) + '0' + str(i) + str(v))] = ''
else:
if v < 10:
tmp[int(str(year) + str(i) + '0' + str(v))] = ''
else:
tmp[int(str(year) + str(i) + str(v))] = ''
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.131 Safari/537.36"
}
# 返回数据:工作日对应结果为 0, 休息日对应结果为3, 节假日对应的结果为1
for k in tmp.keys():
url = 'http://api.goseek.cn/Tools/holiday?date=%d' % k
res = requests.get(url=url, headers=headers)
if res.status_code == 200:
data = json.loads(res.text)['data']
if data == 0:
tmp[k] = 0
elif data == 1:
tmp[k] = 1
elif data == 3:
tmp[k] = 3
with open('%s年节假日对照表.txt'%datetime.date.today().year, 'w') as f:
f.write(json.dumps(str))
这个api可能存在访问不良,还需要多加判断,
- 在配置django项目,没注意哪个配置项除了问题,导致报错
django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet.
不知道啥情况,重新删了走一次好了。 - 把字典写入文件的时候可以直接写入字符串 str(dict),从文件中读取也是读取的字符串,要继续使用字典格式,可以使用eval (eval(str)) >>>> 将字符串类型的dict转换回来。虽然可取,但还是使用json的转换把
and or的使用
使用and 起到了两层if的作用,先对and前的条件进行判断,通过在对and后的条件进行判断,两个都过变量得到and后的值,如果两个条件中有一个不通,变量就得到or后的值,一般在变量初始化好用6.21
- django模型的datefield字段自动增加的时间,默认是以utc走的。datefield字段可以置为空null=True,在模型类中要更新这个字段可以使用datetime对象,在存入数据库的时候,django会自动做转换,例如当前是2019年6月21日14:18:39,存入时就转为utc时间2019年6月21日06:18:39,
xxx.objects.filter(id=1).update(updatetime = datetime.datetime.today() )
另外,update可以同时更新好几个字段。 - shell 脚本使用$数字来接收外部传入的参数,0为脚本本身,1为第一个参数,2为第二个参数。以此类推,shell中的判等也是使用== !=表示不等
shell中的if判断,中括号中要有空格
if [ $1 == shell ]
then
xxxxx要做的事
fi
- 当使用一个标记来判断使用哪个函数,可以把这个标记作为函数名来传入,使用eval来定义一个函数变量,最后加括号执行,
def a():
pass
def b():
pass
def c():
pass
func = eval(var)
var = 'a'传入时。func 等价于 a函数的内存地址
func() 等价于 a(),调用函数
6.24
- 不要在windows上玩celery,不要在windows上玩celery,不要在windows上玩celery,不然死都不知道怎么死的。搞bug搞得头大。
报错
解决方案:
第一种: Try to uninstall celery 4.1.0 and replace to 3.1.24
第二种: pip install eventlet, 启动celeryworker时: celery -A celery_app worker --loglevel=info -P eventlet
@app.task
def add(x, y):
time.sleep(3)
return x + y
import task
if __name__ == '__main__':
# 之前这样写,直接就执行 函数
task.add()
# 现在把函数添加到执行队列中,参数写在delay中
# result不是函数的执行结果,他是个对象
# delay是延迟执行,在调用执行的
方式一:
result = task.add.delay(2, 3)
方式二:
result = task.add.apply_async(args=[4, 3], eta=task_time)
跟delay差不多
# 立即执行的,
# task.add.s()(2,3)
# 这个任务唯一的id
print(result.id)
查看任务结果
celery任务执行结果又九种状态,
from celery.result import AsyncResult
from task import app
# 用获取到的任务id,指定任务名称
async = AsyncResult(id='ac2a7e52-ef66-4caa-bffd-81414d869f85', app=app)
if async.successful():
# successful()方法是AsyncResult对状态的封装,实际上就是任务执行完得到的对象的state == 'SUCCESS'。
# 任务执行的结果,也就是返回值
# 这里的get有个坑,他会等待任务就绪,也就是说,任务不就绪的话会一直卡住,
result = async.get()
print(result)
elif async.failed(): #是FAILED的封装
print('执行失败')
elif async.status == 'PENDING':
print('任务等待中被执行')
elif async.status == 'RETRY':
print('任务异常后正在重试')
elif async.status == 'STARTED':
print('任务已经开始被执行')
执行命令
celery worker -A celery_app_task -l info
- 信息发送服务,不仅仅只是把任务扔给celery执行,还要查看执行结果,对不成功的任务要重试,还有发送邮件这些的,如果网络不通畅,连接服务器就失败的,就别提发送了,所以,要对容易出现问题的地方添加重试操作。以确保信息能够成功发送出去。
而且还要考虑celery执行任务的特殊情况,例如很多任务挤进去但立马执行不了,该如何处理, drf的token验证机制
django 的 MIDDLEWARE 中包含的以下两个 MIDDLEWARE'django.contrib.sessions.middleware.SessionMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
可以在一个 request 进来的时候,将request里的 cookie 里面的 session_id 转换成我们的 user !!!!! 也就是我们之前看到的 request.user 。
配置drf的中间件
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework.authentication.BasicAuthentication',
'rest_framework.authentication.SessionAuthentication',
)}
官方文档显示 restful 提供的 auth 有三种 :
BasicAuthentication 、 TokenAuthentication 、 SessionAuthentication 。
SessionAuthentication :跟django中的机制是一样的, 常用于浏览器,
因为浏览器会自动设置 cookie ,并将他的 cooike 和session 带到服务器,
所以前后端分离的系统用这种机制比较少见,但是还是可以做。
TokenAuthentication : 是需要重点关注的,使用他前 ,必须先将 'rest_framework.authtoken'
添加到 django 的 INSTALLED_APPS 中。
INSTALLED_APPS = ( ... 'rest_framework.authtoken' )
这个tokenauth会给我们创建一张表,外键关联到user表,凡是有表的app都要加入到app中,不然不会生成表。
迁移
python manage.py makemigrations
python manage.py migrate
使用python manage.py createsuperuser 创建超级用户
from rest_framework.authtoken.models import Token
token需要我们自己创建,使用Token.objects.create(user=self.request.user)
表中的key字段就是我们要的token
此时,前端在访问的时候就可以使用这个token来表述用户身份了
HTTP头中
Authorization: Token xxxxxxxxx
注意token后的空格,key一般40长
settings文件中配置REST_FRAMEWORK
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework.authentication.BasicAuthentication',
'rest_framework.authentication.SessionAuthentication',
\#token验证
'rest_framework.authentication.TokenAuthentication',)}
此时,就可以在视图中添加验证类,
from rest_framework.authentication import TokenAuthentication(或者IsAuthentication都行)
这样,就把django自带的token用起来了
缺点:
1.这个token是存在服务器中的,如果一个分布式系统要用同一套的验证系统,就会出现问题。除非两个服务器有同一份用户数据,
- 这个token 是没有过期时间的,而且泄露了别人可以一直用。
6.25
- Django中解决redis-py versions 3.2.0 or later. You have 2.10.6
http://www.yanup.cn/article/13 - 从数据库中取出的参数信息,更改数据库中的数据,如果当下参数没有变更过来,考虑缓存中的数据,清一下试试就好,
- 在django-admin中配置参数,如果参数中混有换行符
\n
,前端在往数据库中存储的时候自动加上了转义符\
,所以,当要使用这个参数进行splitlines()的时候,可能是切割不成功的。
解决:分开配置各个参数,不放到一个字符串中。 - 问题:要根据celery的结果状态来保存发送任务的记录,不知道该怎么使用这个状态,看了看celery的chord函数,只是将前一个celery任务的结果作为后一个celery任务的传入参数,觉得还是少了状态的判断,可能会在记录的时候出现错误。
不过celery号称每分钟解决百万级任务,这种小规模的发送任务只要是celery任务启动,就应该能够在纳秒级解决异步任务,
解决:
方法1:
在celery调用的函数中添加返回值,对通过celery的执行结果来get()这个值,用这个值作为标记来判断celery的状态,再执行后续的操作。
方法2:
应该chord也可以使用,方法和1差不多,chord调用的是两个celery任务,在前一个celery任务中使用调用函数的返回值,作为传入递交给第二个celery任务,在第二个celery任务中对传入进行判断在进行操作。 - 邮件服务配置
import smtplib
from email.header import Header
from email.mime.text import MIMEText
#配置邮箱服务
smtp = smtplib.SMTP('smtp_server,'25')
smtp.helo('plain')
smtp.ehlo()
smtp.starttls()
smtp.set_debuglevel(1)
#登录
smtp.login('username',pwd')
#构造消息
msg = MIMEText('要发送的消息', 'plain', 'utf-8')
msg['From'] = u'Sdata Monitor <从哪儿发送>'
msg['Subject'] = Header(u'标题', 'utf-8').encode()
msg['To'] = ['[email protected]']
msg['To'] = ','.join(['[email protected]'])
#发送邮件
#注意msg的as_string()方法
smtp.sendmail('smtp_server', ['接收者邮箱‘’], msg.as_string())
#msg
'Content-Type: text/plain; charset="utf-8"\nMIME-Version: 1.0\nContent-Transfer-Encoding: base64\nFrom: xxxxx <xxxxxx>\nSubject: =?utf-8?q?xxxxxx?=\nTo: [email protected]\n\nYXNkYXNkYXNkYXNk\n'
- 在使用发送邮件时,有好几次服务器连不上的情况,不知道啥情况,上一次还好的,下一次就不凶了
- 微信发送消息
{
"touser" : "UserID1|UserID2|UserID3",
"toparty" : "PartyID1|PartyID2",
"totag" : "TagID1 | TagID2",
"msgtype" : "text",
"agentid" : 1,
"text" : {
"content" : "你的快递已到,请携带工卡前往邮件中心领取。\n出发前可查看<a href=\"http://work.weixin.qq.com\">邮件中心视频实况</a>,聪明避开排队。"
},
"safe":0
}
touser、toparty、totag根据情境选择,可以为空,但不能同时为空
setting_manager类里面已经包含了从缓存中取数据的函数。缓存中取不到就去数据库中取。
6.26
- 导出项目的依赖包
pip list >> requirements.txt
直接到处的格式并不能直接使用pip install -r xxxx.txt
处理:
with open('requirements.txt','r') as r:
with open('requirements_new.txt','w') as w:
data = r.read()
data.pop(0)
data.pop(0)
for i in data:
i = i.split(' ',1)
i[1] = i[1].strip()
i = '=='.join(i)
w.write(i)
- zabbix的值映射,
- 背景:在视图中使用了两个celery任务,后一个celery任务依赖上一个celery任务的结果,通过上一个celery返回的结果进行下一步操作
问题:想的是要用异步的,可是这两个任务产生了关联,后一个任务还是有等待,其实成了同步了,不好
解决:将状态判断统统移到第二个celery任务中,缺什么参数就传什么参数,
但是这样还是有一个问题,将判断移动到第二个任务中,两个任务可能是在视图调用时并发的启动的,第二个任务需要用到第一个任务的task_id值,有可能当下获取不到,导致celery状态一直是pending
解决,做一个time.sleep()间隔自己定,然后做一个while循环,
while 1:
res = AsyncResult(id=task_id, app=send_msg)
if res.ready():
break
else:
time.sleep(0.5)
continue
条件没达成,就休眠0.5秒继续执行一次任务,知道条件达成,break
觉得这种方式还是不好,以后还得改
消息发送平台的重点在权限,不同账号登陆的用户用不同的key调用第三方短信平台,再记录下发送记录供以后审计使用。三张表,用户表,介质表,设置表,用介质表做中介,连接用户和设置,使用户和设置项配对起来。
setting.objects.filter(media_id=media.objects.get(user_id=self.request.user.id).value).values()这样就得到所有符合条件的数据,再循环遍历得到一个字典6.27
- 今天的代码跟实际情况一结合,就不能用了,实际情况不是想能想到的,所以得重新写,在重写的时候,因为加了新的条件,改动较大,我老固化到原来的逻辑中,不想新方法,或者用其他方法达成。纠结了好久,最后把那一块全部推掉重新来一遍,思路一理清,代码就撸了出来。
有一个比较有意思的
#一个列表
l = [a 20 b 30 c 40 d 60]
#要把这个做成一个字典
#这样来
data = dict(zip( [i for i in l[::2]], [j for j in l[1::2]] ))
这样就可以得到想要的字典, 切片设置步长和起始位置是很有用的
- 在zabbix的接口调用中。search真的是一个神器,类似于contains,只要条件中的字段包含,就能被检索出来,但是只能定义一个条件, api.xxx.get(search={'key':'xxx'}),但是filter可以使用一个数组 api.xxx.get(filter={'name':['条件1','条件2']})
- zabbix的接口调用中,trend的获取可以把 time_from time_till设置成同一个整点值,意在只去那一个时间点的信息。
- 在变量传递的时候,设置一个中建量来接收真的是一个不错的选择。
还需要多练啊,想的东西还是太少,需求下来要先好好把关键点记下来,舍本取末,真的菜。
6.28
- 需求理解还是问题,get不到点事真的恶心,做出来的东西都是错的。
- requests模块的使用,发送post请求的时候,最好发送json数据,假如是字典结构,在发送时进行json.dump()最好。还有就是在请求头的构造中,加上contenttype=json,accept都加上,不然django服务端老返回415解码错误。
- 在本地启动的服务,假如要让外部主机连接,如果这个ip不加到ALLOW_HOST中则返回400错误,可以将ALLOW_HOST设置为 * 允许所有的外部ip访问
在django-admin中,可以创建类,创建方法,对模型的展示进行定制化。