Django项目:堡垒机(Linux服务器主机管理系统)--02--02堡垒机设计后台交互程序
1 #main.py 2 #本文件写所有的连接交互动作程序 3 #————————————————02堡垒机设计后台交互程序 开始———————————————— 4 from django.contrib.auth import authenticate #验证用户的证书 5 import getpass#输入密码时不显示密码 6 #用户登陆堡垒机后的交互程序 7 class HostManager(object): 8 def __init__(self): 9 self.user = None #当前账号 10 11 def interactive(self):#交互脚本 12 # ————————————————登录堡垒机 开始———————————————— 13 print("----开始 运行交互脚本----") 14 count = 0 #用户名密码试错的次数 15 while count < 6:#用户名密码试错的次数 16 username = input("请输入你的用户名:").strip()#用户名 17 password = getpass.getpass("请输入你的密码:").strip()#密码 18 user = authenticate(username=username,password=password)#验证用户名密码 19 if user: #验证成功 20 print("欢迎 %s 登陆使用!".center(50,'-') % user.name ) 21 self.user = user #验证成功,赋值 22 break #退出无限循环 23 else: 24 print("用户名或密码错误!") 25 count += 1#用户名密码试错的次数 26 else: 27 print("----结束 运行交互脚本----") 28 exit("用户名密码试错的次数到了,再见。") 29 """ 30 #————从外部调用django的方法 开始———— 31 #注意写,从外部调用django的方法 E:\堡垒机\eye\fortess_manage.py 32 #注意,到admin后台配置主机给账户 33 # ———————————— 34 #运行 Terminal 35 #E:\堡垒机\eye>python fortess_manage.py 36 #Username:admin@qq.com 37 #Password:admin123456 38 #————从外部调用django的方法 结束———— 39 """ 40 # ————————————————登录堡垒机 结束———————————————— 41 #————————————————02堡垒机设计后台交互程序 结束————————————————
1 #fortess_manage.py 2 #————————————————02堡垒机设计后台交互程序 开始———————————————— 3 #————从外部调用django的方法 开始———— 4 import os #操作系统 5 if __name__ == "__main__": 6 os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'eye.settings')#找路径,环境变量 7 import django #导入django 8 django.setup()#安装django 9 from Fortress.backend import main #从backend导入main.py 10 obj = main.HostManager() #实例化类#main.py的类 11 obj.interactive() #调用类的函数 #交互脚本 12 #————从外部调用django的方法 结束———— 13 #————————————————02堡垒机设计后台交互程序 结束————————————————
1 #models.py 2 #————————————————01堡垒机重写DJANGO账户表 开始———————————————— 3 from django.db import models #模型 4 from django.contrib.auth.models import BaseUserManager,AbstractBaseUser,PermissionsMixin#DJANGO账户继承重写 5 #重写DJAGO账号表 6 class UserProfileManager(BaseUserManager): 7 def create_user(self, email, name, password=None):#创建并保存一个普通用户给定的邮箱地址,密码。 8 if not email: 9 raise ValueError('用户必须有一个电子邮箱地址') 10 user = self.model(email=self.normalize_email(email),#验证邮箱格式 11 name=name,)#创建一条普通用户记录 12 user.set_password(password)#对密码加密 13 user.save(using=self._db)#从临时文件读取出来数据,进行保存。 14 return user 15 def create_superuser(self, email,name,password):#创建并保存一个超级用户给定的邮箱地址,密码。 16 user = self.create_user(email,name=name,password=password)#创建一条超级用户记录 17 user.is_admin = True#管理员 18 user.save(using=self._db)#从临时文件读取出来数据,进行保存。 19 return user 20 21 #重写DJAGO账号表 22 class UserProfile(AbstractBaseUser,PermissionsMixin): 23 # ————#DJANGO账号必须要有的字段 开始———— 24 email = models.EmailField( max_length=255,unique=True,verbose_name='邮箱地址') 25 name = models.CharField(max_length=32,verbose_name='昵称') 26 is_active = models.BooleanField(default=True,verbose_name='是否启用') 27 is_admin = models.BooleanField(default=False,verbose_name='管理员',help_text='指定用户是否可以登录管理网站并且拥有全部权限',) 28 is_staff = models.BooleanField(default=True,verbose_name='员工状态',help_text='指定用户是否可以登录管理网站',) 29 # ————#DJANGO账号必须要有的字段 结束———— 30 31 # ————————————————02堡垒机设计后台交互程序 开始———————————————— 32 bind_hosts = models.ManyToManyField('BindHost',blank=True,verbose_name="关联的主机") 33 host_groups = models.ManyToManyField('HostGroups',blank=True,verbose_name="关联的分组") 34 # ————————————————02堡垒机设计后台交互程序 结束———————————————— 35 36 #————#创建用户记录 开始———— 37 objects = UserProfileManager()#创建用户记录,固定的变量名(objects) 38 USERNAME_FIELD = 'email' #用于登录的字段 39 REQUIRED_FIELDS = ['name']#必须填写 40 # ————#创建用户记录 结束———— 41 # ————#DJANGO账号必须要有的方法 开始———— 42 def get_full_name(self):#用户确认的电子邮件地址 43 return self.email 44 def get_short_name(self):#用户确认的电子邮件地址 45 return self.email 46 # ————#DJANGO账号必须要有的方法 结束———— 47 def __str__(self):# __unicode__ on Python 2 48 return self.email 49 # ————#DJANGO账号权限 开始———— 50 def has_perm(self, perm, obj=None):#权限#用户有一个特定的许可吗? 51 return True 52 def has_module_perms(self, app_label):#用户有权限查看应用名称吗? 53 return True 54 # ————#DJANGO账号权限 结束———— 55 class Meta: 56 verbose_name_plural='00账户' 57 # ————自定制admin 开始———— 58 #到admin.py里给DJANGO账户注册显示 #E:\堡垒机\eye\Fortress\admin.py 59 # ————自定制admin 结束———— 60 # ————注册到配置文件 开始———— 61 #到配置文件里给DJANGO账户指定模型 #E:\堡垒机\eye\eye\settings.py 62 #AUTH_USER_MODEL = 'web.UserProfile' 63 # ————注册到配置文件 结束———— 64 #————————————————01堡垒机重写DJANGO账户表 结束———————————————— 65 #————————————————02堡垒机设计后台交互程序 开始———————————————— 66 #01标签 67 class Tag(models.Model): 68 name = models.CharField(max_length=64,unique=True) #标签名#CharField定长文本#最长度=64字节#不可以重复 69 class Meta:#通过一个内嵌类 "class Meta" 给你的 model 定义元数据 70 verbose_name_plural = "01标签" #verbose_name_plural给你的模型类起一个更可读的名字 71 def __str__(self): # __str__()是Python的一个“魔幻”方法,这个方法定义了当object调用str()时应该返回的值。 72 return self.name # 返回 #标签名 73 #02机房 74 class IDC(models.Model): 75 name = models.CharField(max_length=64, unique=True,verbose_name="机房名") 76 address=models.CharField(max_length=256,blank=True,null=True,verbose_name="机房地址") 77 memo = models.CharField(max_length=128,blank=True,null=True,verbose_name="机房的备注") 78 tag = models.ManyToManyField("Tag",blank=True,verbose_name="标签")#多对多关联到 标签表 79 date = models.DateTimeField(auto_now_add=True,verbose_name='创建时间') 80 class Meta: 81 verbose_name_plural='02机房' 82 def __str__(self): 83 return self.name 84 #03主机 85 class Host(models.Model): 86 hostname = models.CharField(max_length=64,unique=True,verbose_name="主机名") 87 ip_addr = models.GenericIPAddressField(verbose_name="主机IP地址") 88 port = models.SmallIntegerField(default=22,verbose_name="主机端口") 89 idc = models.ForeignKey('IDC',blank=True,null=True,on_delete=models.CASCADE,verbose_name="主机所在的机房") 90 system_type_choices = ((0,'Linux'),(1,'Windows')) 91 system_type = models.SmallIntegerField(choices=system_type_choices,default=0,verbose_name="操作系统类型") 92 enabled = models.BooleanField(default=1,verbose_name="是否启用本机") 93 memo = models.CharField(max_length=128,blank=True,null=True,verbose_name="主机的备注") 94 tag = models.ManyToManyField("Tag",blank=True,verbose_name="标签")#多对多关联到 标签表 95 date = models.DateTimeField(auto_now_add=True,verbose_name='创建时间') 96 class Meta: 97 verbose_name_plural='03主机' 98 unique_together = ('ip_addr','port') 99 def __str__(self): 100 return "%s(%s)" % (self.hostname, self.ip_addr) 101 #04账号密码 102 class RemoteUser(models.Model): 103 auth_type_choices =((0,'ssh-password'), (1,'ssh-key')) 104 auth_type = models.SmallIntegerField(choices=auth_type_choices,default=0,verbose_name="连接方式,密码或者密钥") 105 userlevel=models.CharField(max_length=128,blank=True,null=True,verbose_name="用户等级") 106 username = models.CharField(max_length=128,verbose_name="用户名") 107 password = models.CharField(max_length=256,verbose_name="密码或者密钥",help_text="如果连接方式选择为ssh-key,那此处就应该是key的路径") 108 memo = models.CharField(max_length=128,blank=True,null=True,verbose_name="账号密码的备注") 109 host_prompt=models.ManyToManyField("Host",blank=True,verbose_name="可关联的主机",help_text="关联主机与账号密码提示") 110 tag = models.ManyToManyField("Tag",blank=True,verbose_name="标签")#多对多关联到 标签表 111 date = models.DateTimeField(auto_now_add=True,verbose_name='创建时间') 112 class Meta: 113 verbose_name_plural='04账号密码' 114 unique_together = ('auth_type', 'username', 'password') # 联合唯一 115 def __str__(self): 116 return "%s:%s:%s" %(self.id,self.username,self.memo) 117 #05关联主机与账号密码 118 class BindHost(models.Model): 119 host = models.ForeignKey('Host',on_delete=models.CASCADE,verbose_name="远程主机名") 120 remote_user = models.ForeignKey('RemoteUser',on_delete=models.CASCADE,verbose_name="远程用户名") 121 memo = models.CharField(max_length=128,blank=True,null=True,verbose_name="关联的备注") 122 tag = models.ManyToManyField("Tag",blank=True,verbose_name="标签")#多对多关联到 标签表 123 date = models.DateTimeField(auto_now_add=True,verbose_name='创建时间') 124 class Meta: 125 verbose_name_plural = '05关联主机与账号密码' 126 unique_together = ('host', 'remote_user')#联合唯一 127 def __str__(self): 128 return "<%s:%s:%s>" %(self.host.id,self.host.hostname,self.remote_user.username) 129 #06主机分组 130 class HostGroups(models.Model): 131 name = models.CharField(max_length=64,unique=True,verbose_name="分组名称") 132 memo = models.CharField(max_length=128,blank=True,null=True,verbose_name="主机分组的备注") 133 bind_hosts = models.ManyToManyField('BindHost',blank=True,verbose_name="远程主机") 134 tag = models.ManyToManyField("Tag",blank=True,verbose_name="标签")#多对多关联到 标签表 135 date = models.DateTimeField(auto_now_add=True,verbose_name='创建时间') 136 class Meta: 137 verbose_name_plural='06主机分组' 138 def __str__(self): 139 return self.name 140 #————————————————02堡垒机设计后台交互程序 结束———————————————— 141 142 """ 143 # ————————————————Django中使用中国时区和中文 开始———————————————— 144 到settings.py里修改#E:\堡垒机\eye\eye\settings.py 145 LANGUAGE_CODE = 'zh-Hans' 146 TIME_ZONE = 'Asia/Shanghai' 147 如果需要全局配置默认时区和语言,可在django下的conf模块下的global_settings.py中进行配置 148 所有可选的语言选项可通过python输入以下代码查看: 149 from django.conf.locale import LANG_INFO 150 {key: LANG_INFO[key]['name_local'] for key in LANG_INFO if 'name_local' in LANG_INFO[key]} 151 # ————————时间扩展 开始———————— 152 USE_TZ = True 153 当设置了 USE_TZ 为 True 时,Django 与其他系统或服务的交流将强制使用 UTC 时间。 154 1.保证存储到数据库中的是 UTC 时间; 155 2.在函数之间传递时间参数时,确保时间已经转换成 UTC 时间; 156 # ——Django中跨时区 开始—— 157 一般不跨时区的应用,可以不使用时区,即在settings.py设置 158 USE_TZ = False 159 这样存储的时间就是无时区的时间。 160 # ——Django中跨时区 结束—— 161 # ————————时间扩展 结束———————— 162 # ————————————————Django中使用中国时区和中文 结束———————————————— 163 # ————————————————Django数据库生成 开始———————————————— 164 运行 Terminal 165 生成 数据表 166 E:\堡垒机\eye>python manage.py makemigrations 167 数据表 迁移 168 E:\堡垒机\eye>python manage.py migrate 169 # ————————————————Django数据库生成 结束———————————————— 170 # ————————————————重写Django账号表后的创建方法 开始———————————————— 171 E:\堡垒机\eye>python manage.py createsuperuser 172 邮箱地址: admin@qq.com 173 昵称: admin 174 Password: admin123456 175 Password (again): admin123456 176 Superuser created successfully. 177 # ————————————————重写Django账号表后的创建方法 结束———————————————— 178 #启动 DJANGO 服务 179 E:\堡垒机\eye>python manage.py runserver 127.0.0.1:8000 180 """
1 #admin.py 2 #————————————————01堡垒机重写DJANGO账户表 开始———————————————— 3 #————————同目录下可以用 . 开始———————— 4 #from Fortress import models#数据库 #重写DJAGO账号表 5 from . import models#数据库 #重写DJAGO账号表 6 #————————同目录下可以用 . 结束———————— 7 from django import forms #django的字段验证 8 from django.contrib.auth.admin import UserAdmin as BaseUserAdmin ##表单添加和更改用户实例 9 from django.contrib.auth.forms import ReadOnlyPasswordHashField#只读密码散列字段 10 from django.contrib import admin #注册类到admin 11 #创建新用户 12 class UserCreationForm(forms.ModelForm): 13 password1 = forms.CharField(label='设置密码', widget=forms.PasswordInput)#密码 14 password2 = forms.CharField(label='确认密码', widget=forms.PasswordInput)#确认密码 15 class Meta: 16 model = models.UserProfile 17 fields = ['email', 'name'] 18 def clean_password2(self): #检查两个密码条目是否一样(匹配) 19 password1 = self.cleaned_data.get("password1") 20 password2 = self.cleaned_data.get("password2") 21 if password1 and password2 and password1 != password2: 22 raise forms.ValidationError("密码不匹配") 23 return password2 24 def save(self, commit=True): #保存密码(散列的格式提供) 25 user = super(UserCreationForm, self).save(commit=False) 26 user.set_password(self.cleaned_data["password1"]) 27 if commit: 28 user.save()#保存 29 return user 30 # 修改用户密码 31 class UserChangeForm(forms.ModelForm): 32 password = ReadOnlyPasswordHashField(label="修改密码", 33 help_text=("原始密码不存储,所以没有办法看到" 34 "这个用户的密码,但是你可以改变密码 " 35 "使用 <a href=\"../password/\">修改密码</a>."))#哈值#只读密码散列字段 36 class Meta: 37 model = models.UserProfile 38 fields = ['email', 'password', 'name', 'is_active', 'is_admin'] 39 def clean_password(self):#不管用户提供什么,返回初始值。 40 return self.initial["password"] 41 42 #表单添加和更改用户实例 43 class UserProfileAdmin(BaseUserAdmin): 44 form = UserChangeForm #修改 45 add_form = UserCreationForm#创建 46 # 字段用于显示用户模型。 47 # 这些覆盖定义UserAdmin固定在底座上 48 # auth.User参考特定字段。 49 list_display = ['email', 'name','is_staff', 'is_admin']#后台显示的字段 50 list_filter = ['is_admin','is_staff']#后台过滤的字段 51 fieldsets = (('账号密码', {'fields': ('email', 'password')}), 52 ('个人信息', {'fields': ('name',)}), 53 # ————————————————02堡垒机设计后台交互程序 开始———————————————— 54 ('堡垒机主机授权', {'fields': ('bind_hosts', 'host_groups')}), 55 # ————————————————02堡垒机设计后台交互程序 结束———————————————— 56 ('权限', {'fields': ('is_admin','is_staff','user_permissions','groups')}),) 57 #添加账户时显示要填写的字段 58 add_fieldsets = (('添加账户', {'classes': ('wide',),#wide(宽屏样式) 59 'fields': ('email', 'name', 'password1', 'password2')}),) 60 search_fields = ['email']#后台搜索的字段 61 ordering = ['email']#后台排序的字段 62 filter_horizontal =['user_permissions','groups',#必须覆盖的变量#后台复选框的字段 63 # ————————————————02堡垒机设计后台交互程序 开始———————————————— 64 'bind_hosts', 'host_groups', 65 # ————————————————02堡垒机设计后台交互程序 结束———————————————— 66 ] 67 admin.site.register(models.UserProfile, UserProfileAdmin)#现在注册这个新UserProfileAdmin 68 # ——可选——使用Django的内置权限 开始———— 69 #from django.contrib.auth.models import Group #权限组 70 #admin.site.unregister(Group)#权限组#因为我们不使用Django的内置权限, 71 # ——可选——使用Django的内置权限 结束———— 72 #————————————————01堡垒机重写DJANGO账户表 结束———————————————— 73 74 75 #————————————————02堡垒机设计后台交互程序 开始———————————————— 76 #01标签 77 class TagAdmin(admin.ModelAdmin): 78 list_display = ['id','name'] #显示字段表头 79 list_editable = ['name'] #可编辑 80 search_fields = ['name'] #搜索 81 admin.site.register(models.Tag, TagAdmin) 82 #02机房 83 class IDCAdmin(admin.ModelAdmin): 84 list_display = ['id','name','address','memo','date'] #显示字段表头 85 list_editable = ['name','address', 'memo'] #可编辑 86 search_fields = ['name','tag'] #搜索 87 filter_horizontal = ['tag'] #复选框 88 admin.site.register(models.IDC, IDCAdmin) 89 #03主机 90 class HostAdmin(admin.ModelAdmin): 91 list_display = ['id','hostname','ip_addr','port','memo','enabled','date'] #显示字段表头 92 list_editable = ['hostname','ip_addr','port','memo','enabled'] #可编辑 93 search_fields = ['hostname','ip_addr','port','tag'] #搜索 94 filter_horizontal = ['tag'] #复选框 95 admin.site.register(models.Host, HostAdmin) 96 #04账号密码 97 class RemoteUserAdmin(admin.ModelAdmin): 98 list_display = ['id','userlevel','username','memo','date'] #显示字段表头 99 list_editable = ['memo'] #可编辑 100 search_fields = ['userlevel','username','tag'] #搜索 101 filter_horizontal = ['host_prompt','tag'] #复选框 102 admin.site.register(models.RemoteUser,RemoteUserAdmin) 103 #05关联主机与账号密码 104 class BindHostAdmin(admin.ModelAdmin): 105 list_display = ['id','host','remote_user','memo','date']#显示字段表头 106 list_editable = ['host','remote_user','memo'] #可编辑 107 search_fields = ['host','remote_user','tag'] #搜索 108 filter_horizontal = ['tag'] #复选框 109 ordering = ['host','remote_user'] #自定义排序 110 admin.site.register(models.BindHost,BindHostAdmin) 111 #06主机分组 112 class HostGroupsAdmin(admin.ModelAdmin): 113 list_display = ['id','name','memo','date']#显示字段表头 114 list_editable = ['name','memo'] #可编辑 115 search_fields = ['name','tag'] #搜索 116 filter_horizontal = ['bind_hosts','tag'] #复选框 117 admin.site.register(models.HostGroups, HostGroupsAdmin) 118 #————————————————02堡垒机设计后台交互程序 结束————————————————
1 #main.py 2 #本文件写所有的连接交互动作程序 3 #————————————————02堡垒机设计后台交互程序 开始———————————————— 4 from django.contrib.auth import authenticate #验证用户的证书 5 #用户登陆堡垒机后的交互程序 6 class HostManager(object): 7 def __init__(self): 8 self.user = None #当前账号 9 def interactive(self):#交互脚本 10 # ————————————————登录堡垒机 开始———————————————— 11 print("----开始 运行交互脚本----") 12 count = 0 #用户名密码试错的次数 13 while count < 6:#用户名密码试错的次数 14 username = input("Username:").strip()#用户名 15 password = input("Password:").strip()#密码 16 user = authenticate(username=username,password=password)#验证用户名密码 17 if user: #验证成功 18 print("欢迎 %s 登陆使用!".center(50,'-') % user.name ) 19 self.user = user #验证成功,赋值 20 break #退出无限循环 21 else: 22 print("用户名或密码错误!") 23 count += 1#用户名密码试错的次数 24 else: 25 print("----结束 运行交互脚本----") 26 exit("用户名密码试错的次数到了,再见。") 27 """ 28 #————从外部调用django的方法 开始———— 29 #注意写,从外部调用django的方法 E:\堡垒机\eye\fortess_manage.py 30 #注意,到admin后台配置主机给账户 31 # ———————————— 32 #运行 Terminal 33 #E:\堡垒机\eye>python fortess_manage.py 34 #Username:admin@qq.com 35 #Password:admin123456 36 #————从外部调用django的方法 结束———— 37 """ 38 # ————————————————登录堡垒机 结束———————————————— 39 # ——————————————选择要连接的主机 开始———————————— 40 if self.user: #验证登录成功 41 while True: 42 #————————打印当前账户所有的可以登录主机 开始—————— 43 for index,host_group in enumerate(self.user.host_groups.all()): #select_related() 44 print("%s.\t%s[%s]" %(index,host_group.name, host_group.bind_hosts.count())) 45 print("z.\t未分组主机[%s]" %(self.user.bind_hosts.count())) 46 #————————打印当前账户所有的可以登录主机 结束—————— 47 # ————————开始选择分组 开始—————— 48 choice = input("%s>>:"% self.user).strip()#输入选择 49 if len(choice) == 0:#长度等于0 50 continue#跳过这次循环 51 selected_host_group = None #选择分组 52 if choice.isdigit():#检测字符串是否只由数字组成 53 choice = int(choice)#转成整数 54 if choice >=0 and choice <= index: #判断输入的选项是否合法 55 selected_host_group = self.user.host_groups.all()[choice]#迭代选择分组 56 elif choice == 'z':#未分组 57 selected_host_group = self.user 58 # ————————开始选择分组 结束—————— 59 # ————————开始选择主机 开始—————— 60 if selected_host_group: #选择分组后选择主机 61 while True: 62 print("当前选择的分组: %s ".center(50,'-') %selected_host_group) 63 # ————————打印分组里的所有主机 开始—————— 64 for index, bind_host in enumerate(selected_host_group.bind_hosts.all()): 65 print("%s.\t%s" % (index, bind_host)) 66 print("返回上级菜单,请按 b ") 67 # ————————打印分组里的所有主机 结束—————— 68 # ————————选择分组里的主机 开始—————— 69 choice = input("%s>>>:" % self.user).strip()#输入选择 70 if choice.isdigit():#检测字符串是否只由数字组成 71 choice = int(choice)#转成整数 72 if choice >= 0 and choice <= index:#判断输入的选项是否合法 73 bind_host = selected_host_group.bind_hosts.all()[choice]#迭代选择主机 74 print("准备登录 %s 主机".center(50,'-') %bind_host) 75 # ————————选择分组里的主机 结束—————— 76 elif choice == 'b':#退出 77 break #终止无限循环 78 # ————————开始选择主机 结束—————— 79 # ——————————————选择要连接的主机 结束———————————— 80 #————————————————02堡垒机设计后台交互程序 结束————————————————
您的资助是我最大的动力!
金额随意,欢迎来赏!
如果,您希望更容易地发现我的新博客,不妨点击一下绿色通道的
因为,我的写作热情也离不开您的肯定支持,感谢您的阅读,我是【颜言】!