first commit to github

This commit is contained in:
pycook
2015-12-29 10:35:10 +08:00
committed by pycook
parent 755725a1b7
commit a91f409525
55 changed files with 5210 additions and 0 deletions

View File

@@ -0,0 +1,24 @@
# -*- coding:utf-8 -*-
def row2dict(row):
d = dict()
for c in row.__table__.columns:
if not isinstance(getattr(row, c.name),
(basestring, long, int, float, list, tuple, dict)) \
and getattr(row, c.name):
d[c.name] = getattr(row, c.name).strftime("%Y-%m-%d %H:%M:%S")
else:
d[c.name] = getattr(row, c.name)
return d
from account import *
from attribute import *
from ci import *
from ci_relation import *
from ci_type import *
from ci_type_relation import *
from ci_value import *
from history import *
from statis import *

230
cmdb-api/models/account.py Normal file
View File

@@ -0,0 +1,230 @@
# -*- coding:utf-8 -*-
import hashlib
import copy
from datetime import datetime
from werkzeug.utils import cached_property
from flask.ext.sqlalchemy import BaseQuery
from flask.ext.principal import RoleNeed
from flask.ext.principal import UserNeed
from flask.ext.principal import Permission
from extensions import db
from extensions import cache
from permissions import admin
from models import row2dict
class UserQuery(BaseQuery):
def from_identity(self, identity):
"""
Loads user from flask.ext.principal.Identity instance and
assigns permissions from user.
A "user" instance is monkey patched to the identity instance.
If no user found then None is returned.
"""
try:
_id = identity.id
if _id:
_id = int(_id)
user = self.get(_id)
except ValueError:
user = None
except Exception:
user = None
if user:
identity.provides.update(user.provides)
identity.user = user
return user
def authenticate(self, login, password):
user = self.filter(db.or_(User.username == login,
User.email == login)).first()
if user:
authenticated = user.check_password(password)
else:
authenticated = False
return user, authenticated
def authenticate_with_key(self, key, secret, args, path):
user = self.filter(User.key == key).filter(User.block == 0).first()
if not user:
return None, False
if user and hashlib.sha1('%s%s%s' % (
path, user.secret, "".join(args))).hexdigest() == secret:
authenticated = True
else:
authenticated = False
return row2dict(user), authenticated
def search(self, key):
query = self.filter(db.or_(User.email == key,
User.nickname.ilike('%' + key + '%'),
User.username.ilike('%' + key + '%')))
return query
def get_by_username(self, username):
user = self.filter(User.username == username).first()
return user
def get_by_nickname(self, nickname):
user = self.filter(User.nickname == nickname).first()
return user
def get(self, uid):
user = self.filter(User.uid == uid).first()
return copy.deepcopy(user)
def is_exits(self, username):
user = self.filter(User.username == username).first()
return user is not None
class User(db.Model):
__tablename__ = 'users'
query_class = UserQuery
ADMIN = 1
uid = db.Column(db.Integer, primary_key=True, autoincrement=True)
username = db.Column(db.String(32), unique=True)
nickname = db.Column(db.String(20), nullable=True)
department = db.Column(db.String(20))
catalog = db.Column(db.String(64))
email = db.Column(db.String(100), unique=True, nullable=False)
mobile = db.Column(db.String(14), unique=True)
_password = db.Column("password", db.String(80), nullable=False)
key = db.Column(db.String(32), nullable=False)
secret = db.Column(db.String(32), nullable=False)
date_joined = db.Column(db.DateTime, default=datetime.utcnow)
last_login = db.Column(db.DateTime, default=datetime.utcnow)
block = db.Column(db.Boolean, default=False)
has_logined = db.Column(db.Boolean, default=False)
class Permissions(object):
def __init__(self, obj):
self.obj = obj
@cached_property
def is_admin(self):
return Permission(UserNeed(self.obj.id)) & admin
def __init__(self, *args, **kwargs):
super(User, self).__init__(*args, **kwargs)
def __str__(self):
return self.username
@cached_property
def permissions(self):
return self.Permissions(self)
def _get_password(self):
return self._password
def _set_password(self, password):
self._password = password
password = db.synonym("_password", descriptor=property(
_get_password, _set_password))
def check_password(self, password):
return self.password == password
@cached_property
def provides(self):
needs = [RoleNeed('authenticated'), UserNeed(self.uid)]
for r in self.rolenames:
needs.append(RoleNeed(r))
if self.is_admin:
needs.append(RoleNeed('admin'))
return needs
@property
def roles(self):
urs = db.session.query(UserRole.rid).filter(
UserRole.uid == self.uid).all()
return [x.rid for x in urs]
@property
def rolenames(self):
return [db.session.query(Role.role_name).filter(
Role.rid == rid).first().role_name for rid in self.roles]
@property
def is_admin(self):
return self.ADMIN in self.roles
class Role(db.Model):
__tablename__ = 'roles'
rid = db.Column(db.Integer, primary_key=True, autoincrement=True)
role_name = db.Column(db.String(64), nullable=False, unique=True)
class UserRole(db.Model):
__tablename__ = 'users_roles'
uid = db.Column(db.Integer, db.ForeignKey('users.uid'), primary_key=True)
rid = db.Column(db.Integer, db.ForeignKey('roles.rid'), primary_key=True)
class UserCache(object):
@classmethod
def get(cls, key):
user = cache.get("User::uid::%s" % key) or \
cache.get("User::username::%s" % key) or \
cache.get("User::nickname::%s" % key)
if not user:
user = User.query.get(key) or \
User.query.get_by_username(key) or \
User.query.get_by_nickname(key)
if user:
cls.set(user)
return user
@classmethod
def set(cls, user):
cache.set("User::uid::%s" % user.uid, user)
cache.set("User::username::%s" % user.username, user)
cache.set("User::nickname::%s" % user.nickname, user)
@classmethod
def clean(cls, user):
cache.delete("User::uid::%s" % user.uid)
cache.delete("User::username::%s" % user.username)
cache.delete("User::nickname::%s" % user.nickname)
class RoleCache(object):
@classmethod
def get(cls, rid):
role = None
if isinstance(rid, (int, long)):
role = cache.get("Role::rid::%s" % rid)
if not role:
role = db.session.query(Role).filter(Role.rid == rid).first()
cls.set(role)
elif isinstance(rid, basestring):
role = cache.get("Role::role_name::%s" % rid)
if not role:
role = db.session.query(Role).filter(
Role.role_name == rid).first()
cls.set(role)
return role
@classmethod
def set(cls, role):
cache.set("Role::rid::%s" % role.rid, role)
cache.set("Role::role_name::%s" % role.role_name, role)
@classmethod
def clean(cls, role):
cache.delete("Role::rid::%s" % role.rid, role)
cache.delete("Role::role_name::%s" % role.role_name, role)

View File

@@ -0,0 +1,87 @@
# -*- coding:utf-8 -*-
from extensions import db, cache
class CIAttribute(db.Model):
__tablename__ = "ci_attributes"
attr_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
attr_name = db.Column(db.String(32), nullable=False, unique=True)
attr_alias = db.Column(db.String(32), nullable=False, unique=True)
value_type = db.Column(
db.String(8),
db.Enum("int", "float", "text", "datetime", name='value_type'),
default="text",
nullable=False)
is_choice = db.Column(db.Boolean, default=False)
is_multivalue = db.Column(db.Boolean, default=False)
is_uniq = db.Column(db.Boolean, default=False)
is_index = db.Column(db.Boolean, default=False)
class IntegerChoice(db.Model):
__tablename__ = 'choice_integers'
choice_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
attr = db.relationship("CIAttribute", backref="choice_integers")
value = db.Column(db.Integer, nullable=False)
class FloatChoice(db.Model):
__tablename__ = 'choice_floats'
choice_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
attr = db.relationship("CIAttribute", backref="choice_floats")
value = db.Column(db.Float, nullable=False)
class TextChoice(db.Model):
__tablename__ = 'choice_texts'
choice_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
attr = db.relationship("CIAttribute", backref="choice_texts")
value = db.Column(db.Text, nullable=False)
class CIAttributeCache(object):
@classmethod
def get(cls, key):
if key is None:
return
attr = cache.get('Field::Name::%s' % key) or \
cache.get('Field::ID::%s' % key) or \
cache.get('Field::Alias::%s' % key)
if attr is None:
attr = db.session.query(CIAttribute).filter_by(
attr_name=key).first() or \
db.session.query(CIAttribute).filter(
CIAttribute.attr_id == key).first() or \
db.session.query(CIAttribute).filter(
CIAttribute.attr_alias == key).first()
db.session.close()
if attr is not None:
CIAttributeCache.set(attr)
return attr
@classmethod
def set(cls, attr):
cache.set('Field::ID::%s' % attr.attr_id, attr)
cache.set('Field::Name::%s' % attr.attr_name, attr)
cache.set('Field::Alias::%s' % attr.attr_alias, attr)
@classmethod
def clean(cls, attr):
if cache.get('Field::ID::%s' % attr.attr_id):
cache.delete('Field::ID::%s' % attr.attr_id)
cache.delete('Field::Name::%s' % attr.attr_name)
cache.delete('Field::Alias::%s' % attr.attr_alias)

20
cmdb-api/models/ci.py Normal file
View File

@@ -0,0 +1,20 @@
# -*- coding:utf-8 -*-
import datetime
from extensions import db
class CI(db.Model):
__tablename__ = "cis"
ci_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
uuid = db.Column(db.String(32), nullable=False)
type_id = db.Column(db.Integer,
db.ForeignKey("ci_types.type_id"),
nullable=False)
ci_type = db.relationship("CIType", backref="cis")
status = db.Column(db.String(8),
db.Enum("review", "validate", name="stauts"))
created_time = db.Column(db.DateTime, default=datetime.datetime.now())
heartbeat = db.Column(db.DateTime, default=datetime.datetime.now())

View File

@@ -0,0 +1,26 @@
# -*- coding:utf-8 -*-
from extensions import db
class CIRelation(db.Model):
__tablename__ = "ci_relations"
cr_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
first_ci_id = db.Column(db.Integer,
db.ForeignKey("cis.ci_id"),
primary_key=True)
second_ci_id = db.Column(db.Integer,
db.ForeignKey("cis.ci_id"),
primary_key=True)
first_ci = db.relationship("CI",
primaryjoin="CI.ci_id==CIRelation.first_ci_id")
second_ci = db.relationship(
"CI", primaryjoin="CI.ci_id==CIRelation.second_ci_id")
relation_type = db.Column(
db.String(8), db.Enum("connect", "deploy", "install", "contain",
name="relation_type"), nullable=False)
more = db.Column(db.Integer, db.ForeignKey("cis.ci_id"))
__table_args__ = (db.UniqueConstraint("first_ci_id", "second_ci_id",
name="first_second_uniq"), )

128
cmdb-api/models/ci_type.py Normal file
View File

@@ -0,0 +1,128 @@
# -*- coding:utf-8 -*-
from extensions import db
from extensions import cache
class CIType(db.Model):
__tablename__ = "ci_types"
type_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
type_name = db.Column(db.String(32))
type_alias = db.Column(db.String(32))
uniq_id = db.Column(db.Integer,
db.ForeignKey("ci_attributes.attr_id"),
nullable=False)
uniq_key = db.relationship("CIAttribute", backref="ci_types")
enabled = db.Column(db.Boolean, default=True, nullable=False)
is_attached = db.Column(db.Boolean, default=False, nullable=False)
icon_url = db.Column(db.String(256))
order = db.Column(db.SmallInteger, default=0, nullable=False)
class CITypeAttribute(db.Model):
__tablename__ = "type_attributes"
type_id = db.Column(db.Integer,
db.ForeignKey("ci_types.type_id"),
primary_key=True)
attr_id = db.Column(db.Integer,
db.ForeignKey("ci_attributes.attr_id"),
primary_key=True)
is_required = db.Column(db.Boolean, default=False)
__table_args__ = (db.UniqueConstraint("type_id", "attr_id",
name="type_attr_uniq"), )
class CITypeCache(object):
@classmethod
def get(cls, key):
if key is None:
return
ct = cache.get("CIType::ID::%s" % key) or \
cache.get("CIType::Name::%s" % key)
if ct is None:
ct = db.session.query(CIType).filter(
CIType.type_name == key).first() or \
db.session.query(CIType).filter(CIType.type_id == key).first()
if ct is not None:
CITypeCache.set(ct)
return ct
@classmethod
def set(cls, ct):
cache.set("CIType::Name::%s" % ct.type_name, ct)
cache.set("CIType::ID::%d" % ct.type_id, ct)
@classmethod
def clean(cls, key):
ct = CITypeCache.get(key)
if ct is not None:
cache.delete("CIType::Name::%s" % ct.type_name)
cache.delete("CIType::ID::%s" % ct.type_id)
class CITypeSpecCache(object):
@classmethod
def get(cls, key):
if key is None:
return
ct = cache.get("CITypeSPEC::ID::%d" % key)
if ct is None:
ct = db.session.query(CIType).filter(CIType.type_id == key).first()
if ct is not None:
CITypeSpecCache.set(ct)
return ct
@classmethod
def set(cls, ct):
cache.set("CITypeSPEC::ID::%d" % ct.type_id, ct)
@classmethod
def clean(cls, key):
ct = CITypeCache.get(key)
if ct is not None:
cache.delete("CITypeSPEC::ID::%d" % ct.type_id)
class CITypeAttributeCache(object):
"""
key is type_id or type_name
"""
@classmethod
def get(cls, key):
if key is None:
return
if isinstance(key, basestring) and isinstance(key, unicode):
key = unicode(key, 'utf8')
citypes = cache.get("CITypeAttribute::Name::%s" % key) or \
cache.get("CITypeAttribute::ID::%s" % key)
if not citypes:
citypes = db.session.query(CITypeAttribute).filter(
CITypeAttribute.type_id == key).all()
if citypes is None:
ci_type = db.session.query(CIType).filter(
CIType.type_name == key).first()
if ci_type is not None:
citypes = db.session.query(CITypeAttribute).filter_by(
type_id=ci_type.type_id).all()
if citypes is not None:
CITypeAttributeCache.set(key, citypes)
return citypes
@classmethod
def set(cls, key, values):
citype = CITypeCache.get(key)
if citype is not None:
cache.set("CITypeAttribute::ID::%s" % citype.type_id, values)
cache.set("CITypeAttribute::Name::%s" % citype.type_name, values)
@classmethod
def clean(cls, key):
citype = CITypeCache.get(key)
attrs = CITypeAttributeCache.get(key)
if attrs is not None and citype:
cache.delete("CITypeAttribute::ID::%s" % citype.type_id)
cache.delete("CITypeAttribute::Name::%s" % citype.type_name)

View File

@@ -0,0 +1,27 @@
# -*- coding:utf-8 -*-
from extensions import db
class CITypeRelation(db.Model):
__tablename__ = "ci_type_relations"
ctr_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
parent_id = db.Column(db.Integer,
db.ForeignKey("ci_types.type_id"),
primary_key=True)
parent = db.relationship(
"CIType", primaryjoin="CIType.type_id==CITypeRelation.parent_id")
child_id = db.Column(db.Integer,
db.ForeignKey("ci_types.type_id"),
primary_key=True)
child = db.relationship(
"CIType", primaryjoin="CIType.type_id==CITypeRelation.child_id")
relation_type = db.Column(
db.String(7),
db.Enum("contain", "connect", "deploy", "install",
name="relation_type"),
default="contain")
__table_args__ = (db.UniqueConstraint("parent_id", "child_id",
name="parent_child_uniq"), )

117
cmdb-api/models/ci_value.py Normal file
View File

@@ -0,0 +1,117 @@
# -*- coding:utf-8 -*-
from extensions import db
from sqlalchemy import Index
class CIIndexValueInteger(db.Model):
__tablename__ = "index_integers"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="index_integers")
attr = db.relationship("CIAttribute", backref="index_integers")
value = db.Column(db.Integer, nullable=False)
__table_args__ = (Index("attr_value_index", "attr_id", "value"), )
class CIIndexValueFloat(db.Model):
__tablename__ = "index_floats"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="index_floats")
attr = db.relationship("CIAttribute", backref="index_floats")
value = db.Column(db.Float, nullable=False)
__table_args__ = (Index("attr_value_index", "attr_id", "value"), )
class CIIndexValueText(db.Model):
__tablename__ = "index_texts"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="index_texts")
attr = db.relationship("CIAttribute", backref="index_texts")
value = db.Column(db.String(128), nullable=False)
__table_args__ = (Index("attr_value_index", "attr_id", "value"), )
class CIIndexValueDateTime(db.Model):
__tablename__ = "index_datetime"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="index_datetime")
attr = db.relationship("CIAttribute", backref="index_datetime")
value = db.Column(db.DateTime, nullable=False)
__table_args__ = (Index("attr_value_index", "attr_id", "value"), )
class CIValueInteger(db.Model):
__tablename__ = "integers"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="integers")
attr = db.relationship("CIAttribute", backref="integers")
value = db.Column(db.Integer, nullable=False)
class CIValueFloat(db.Model):
__tablename__ = "floats"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="floats")
attr = db.relationship("CIAttribute", backref="floats")
value = db.Column(db.Float, nullable=False)
class CIValueText(db.Model):
__tablename__ = "texts"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="texts")
attr = db.relationship("CIAttribute", backref="texts")
value = db.Column(db.Text, nullable=False)
class CIValueDateTime(db.Model):
__tablename__ = "datetime"
value_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
ci_id = db.Column(db.Integer, db.ForeignKey('cis.ci_id'), nullable=False)
attr_id = db.Column(db.Integer,
db.ForeignKey('ci_attributes.attr_id'),
nullable=False)
ci = db.relationship("CI", backref="datetime")
attr = db.relationship("CIAttribute", backref="datetime")
value = db.Column(db.DateTime, nullable=False)

View File

@@ -0,0 +1,51 @@
# -*- coding:utf-8 -*-
import datetime
from extensions import db
class OperationRecord(db.Model):
__tablename__ = "records"
record_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
uid = db.Column(db.Integer, db.ForeignKey('users.uid'), nullable=False)
timestamp = db.Column(db.DateTime,
nullable=False,
default=datetime.datetime.now())
origin = db.Column(db.String(32))
ticket_id = db.Column(db.String(32))
reason = db.Column(db.Text)
class CIAttributeHistory(db.Model):
__tablename__ = "histories"
h_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
operate_type = db.Column(db.String(6), db.Enum("add", "delete", "update",
name="operate_type"))
record_id = db.Column(db.Integer,
db.ForeignKey("records.record_id"),
nullable=False)
ci_id = db.Column(db.Integer, nullable=False)
attr_id = db.Column(db.Integer, nullable=False)
old = db.Column(db.Text)
new = db.Column(db.Text)
class CIRelationHistory(db.Model):
__tablename__ = "relation_histories"
rh_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
operate_type = db.Column(db.String(6),
db.Enum("add", "delete", name="operate_type"))
record_id = db.Column(db.Integer,
db.ForeignKey("records.record_id"),
nullable=False)
first_ci_id = db.Column(db.Integer)
second_ci_id = db.Column(db.Integer)
relation_type = db.Column(
db.String(8), db.Enum("connect", "deploy", "install", "contain",
name="relation_type"))
relation = db.Column(db.Integer, nullable=False)

20
cmdb-api/models/statis.py Normal file
View File

@@ -0,0 +1,20 @@
# -*- coding:utf-8 -*-
import datetime
from extensions import db
class UrlRecord(db.Model):
url_id = db.Column(db.Integer, primary_key=True, autoincrement=True)
url = db.Column(db.String(64), nullable=False)
response_time = db.Column(db.Float, nullable=False)
is_ok = db.Column(db.Boolean, default=True)
source = db.Column(db.String(32))
remote_addr = db.Column(db.String(20))
hits = db.Column(db.Integer)
method = db.Column(db.String(5), default="GET")
created_at = db.Column(db.DateTime, default=datetime.datetime.now())