蓝鲸SaaS开发搭建Django+Vue前后端分离的开发框架

python manage.py migrate
python manage.py startapp task

获取用户名

#add redis for celery
redis==2.10.6
djangorestframework==3.11.0
Jinja2==2.11.2


    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.sqlite3',
            'NAME': os.path.join(BASE_DIR, APP_CODE),
        }
    }
    login_user_data = client.bk_login.get_user({
        "bk_token": request.COOKIES.get("bk_token")
    })
    username = request.user.username
    if login_user_data['result']:
        username = login_user_data['data']['bk_username']
    sys_time = datetime.datetime.now()
    sys_time_str = sys_time.strftime('%Y-%m-%d %H:%M:%S')
   # python3 b64encode 需要转码
   data = client.job.fast_execute_script({
        "bk_biz_id": bk_biz_id,
        "task_name": task_name,
        "account": account,
        "script_content": str(base64.b64encode(script_content.encode('utf-8')), "utf-8"),
        "script_param": str(base64.b64encode(script_param.encode('utf-8')), "utf-8"),
        "script_type": script_type,
        "ip_list": ip_list,
    })
    ####
    job_detail = client.job.get_job_detail({
        'bk_biz_id': int(biz_id),
        'bk_job_id': int(job_id)
    })
    steps = []
    job_detail_steps = job_detail['data']['steps']
    i = 1
    for step in job_detail_steps:
        steps.append({"step_id": step['step_id'],
                      "script_param": str(base64.b64encode(key_word.encode('utf-8')), encoding='utf-8'),
                      "ip_list": [{"bk_cloud_id": 0, "ip": host_ip}]})
    job_log = client.job.execute_job({
        'bk_biz_id': int(biz_id),
        'bk_job_id': int(job_id),
        'steps': steps  # job_detail['data']['steps']
    })
    job_instance_id = job_log['data']['job_instance_id']


    ###
    log_info = client.job.get_job_instance_log({
        "bk_biz_id": bk_biz_id,
        "job_instance_id": job_instance_id
    })
    while not log_info['data'][0]["is_finished"]:
        # sleep(1)
        log_info = log_info = client.job.get_job_instance_log({
            "bk_biz_id": bk_biz_id,
            "job_instance_id": job_instance_id
        })
        if log_info['data'][0]["is_finished"]:
            return log_info
    return log_info

python celery note

@periodic_task(run_every=crontab(minute='*/1', hour='*', day_of_week="*", day_of_month='*', month_of_year='*'))
def task(**kwargs):
    pass

## 延迟执行
@task()
def start_task(client, to_user, key):
    pass
### call start task
start_task.apply_async(args=[client, to_user, key], eta=now + datetime.timedelta(seconds=10))
    
## create celery tasks with interval
    interval_schedule = {
        "every": 5,
        "period": 'seconds'
    }
    kwargs = dict(
        biz_id=biz_id,
        job_instance_id=job_instance_id,
    )
    interval = IntervalSchedule.objects.create(**interval_schedule)
    interval.save()
    now = datetime.datetime.now()
    task = PeriodicTask.objects.create(name='get_log_{}'.format(job_instance_id),
                                                       kwargs=json.dumps(kwargs),
                                                       interval=interval,
                                                       enabled=True,
                                                       expires=now + datetime.timedelta(minutes=1),
                                                       task="task.celery_tasks.get_instance_log")

django paginator 以及 serializers 使用

    qs = ScriptLog.objects.filter()
    page_num = request.GET.get('page')
    page_size = request.GET.get('page_size')
    paginator = Paginator(qs, page_size)  # 每页25条
    page = paginator.page(page_num)
    data = []
    obj_list = json.loads(serializers.serialize('json', page.object_list))
    for obj in obj_list:
        data.append(obj.get('fields'))

vue.config.js

var env = process.env.NODE_ENV
var isProduction = env === 'production'
let publicPath = '/'
if (isProduction) {
  publicPath = './static/build'
}

module.exports = {
  lintOnSave: 'error',
  publicPath: publicPath,
  indexPath: '../../templates/index.html',
  devServer: {
    proxy: 'http://127.0.0.1:8000',
    disableHostCheck: true,
    port: 8080
  }
}

pacakge.json   ../static/build

main.js


import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';
import axios from 'axios'

const http = axios.create({
  baseURL: process.env.NODE_ENV === 'production' ? window.site_url : '/',
  headers: { 'X-Requested-With': 'XMLHttpRequest' },
  xsrfCookieName: 'csrftoken',
  xsrfHeaderName: 'X-CSRFToken',
  withCredentials: true
})
Vue.prototype.$http = http
Vue.use(ElementUI);

index.html


menu nav

    

json

{
    "module": "demo",
    "name": "snippet",
    "search_forms": [
          {"prop": "title", "label": "标题", "type": "input", "rules": [
              {"required": "true", "message": "请输入标题", "trigger": "blur"}
          ]},
    ],
    "forms": [
        {"prop": "title", "label": "标题", "type": "input", "rules": [
            {"required": "true", "message": "请输入标题", "trigger": "blur"}
        ]},
    ],
    "columns": [
        {"prop": "title", "label": "标题"}
    ]
}

data_list






edit






viewset

# -*- coding: utf-8 -*-
from rest_framework import viewsets
from rest_framework.decorators import action
from rest_framework.pagination import PageNumberPagination
from rest_framework.response import Response
from blueapps.utils.logger import logger
from config.default import PROJECT_CONFIG
from {{ app_name }}.models import {{ name }}
from {{ app_name }}.serializers import {{ name }}Serializer


class {{ name }}ViewSet(viewsets.ModelViewSet):
    """
    此视图自动提供`list`,`create`,`retrieve`,`update`和`destroy`操作。

    另外我们还提供了一个额外的`execute`操作。
    """
    # queryset = {{ name }}.objects.all()
    serializer_class = {{ name }}Serializer

    @action(methods=['get'], detail=False)
    def execute(self, request, *args, **kwargs):
        logger.info('>>> execute start ')
        result = {"result": True}
        return Response(result)

    def list(self, request, *args, **kwargs):
        logger.info('>>>> {{ name }}ViewSet list')
        page_queryset = {{ name }}.objects.filter()
        page_size = PROJECT_CONFIG['PAGE_SIZE']
        if request.query_params.get("page_size"):
            page_size = int(request.query_params.get("page_size"))
        # 实例化产生一个加密分页对象
        pagination = PageNumberPagination()
        pagination.page_size = page_size  # 每页显示的个数
        pagination.max_page_size = 50  # 每页最多显示多少条
        page_list = pagination.paginate_queryset(page_queryset, request)
        ser = {{ name }}Serializer(instance=page_list, many=True)
        result = {"result": True,
                  'count': pagination.page.paginator.count,
                  'data': ser.data}
        return Response(result)

    def create(self, request, *args, **kwargs):
        logger.info('>>>> {{ name }}ViewSet create')
        ser = {{ name }}Serializer(data=request.data)
        if ser.is_valid():
            ser.save()
            result = {"result": True, 'data': ser.data}
            return Response(result)
        result = {"result": False}
        return Response(result)

    def retrieve(self, request, pk=None, **kwargs):
        logger.info('>>> {{ name }}ViewSet retrieve by pk = {} '.format(pk))
        obj ={{ name }}.objects.get(pk=pk)
        ser ={{ name }}Serializer(instance=obj)
        result = {"result": True, 'data': ser.data}
        return Response(result)

    def update(self, request, pk=None, **kwargs):
        logger.info('>>>> update')
        result = {"result": True}
        obj ={{ name }}.objects.get(pk=pk)
        ser ={{ name }}Serializer(instance=obj)
        ser.is_valid(raise_exception=True)
        ser.save()
        return Response(result)

    def destroy(self, request, pk=None, **kwargs):
        logger.info('>>>> {{ name }}ViewSet update pk {pk}'.format(pk=pk))
        obj ={{ name }}.objects.get(pk=pk)
        ser ={{ name }}Serializer(instance=obj)
        obj.delete()
        result = {"result": True, 'data': ser.data}
        return Response(result)

ggg templates

# -*- coding: utf-8 -*-
import json
import os
import re

from jinja2 import Environment, PackageLoader

from config import BASE_DIR


def get_jinjia_env():
    env = Environment(loader=PackageLoader('common.generator'))
    return env

def get_json_obj(config_file):
    with open('./config/{json_file}'.format(json_file=config_file), 'r', encoding='utf-8') as f:
        json_data = f.read()
        json_obj = json.loads(json_data)
    return json_obj

def gen_vue_file(config_file, override=False):
    json_obj = get_json_obj(config_file)
    template = get_jinjia_env().get_template('data_list.j2')
    template_form = get_jinjia_env().get_template('edit_form.j2')
    gen_vue_comp(json_obj, override=override, template=template)
    gen_vue_comp(json_obj, override=override, template=template_form, is_edit=True)


def gen_vue_comp(json_obj, override, template, is_edit=False):
    searchForms = json_obj['search_forms']
    forms = json_obj['forms']
    tableColumns = json_obj['columns']
    module = json_obj['module']
    name = json_obj['name']
    content = template.render(module=module,
                              name=name,
                              searchForms=searchForms,
                              forms=forms,
                              tableColumns=tableColumns)
    blank_line_re = re.compile('\\s+\\n')
    content = blank_line_re.sub('\n', content)
    folder = os.path.join(BASE_DIR, 'vue_app') + '/src/views/{module}'.format(module=module)
    if is_edit:
        folder = os.path.join(BASE_DIR, 'vue_app') + '/src/views/{module}/components'.format(module=module)
    if not os.path.exists(folder):
        os.makedirs(name=folder)
    file_path = '{folder}/{name}.vue'.format(folder=folder, name=name)
    if is_edit:
        file_path = '{folder}/Edit{name}.vue'.format(folder=folder, name=name.capitalize())
    if override:
        with open(file_path, 'w', encoding='utf-8') as fp:
            fp.write(content)
        print('>>> gen vue success!!!')
    else:
        print('>>> file already exists, you can pass extra arg: override = True, to override exists file...')


def gen_view_set(app_name, name, override=False):
    template = get_jinjia_env().get_template('SampleViewSet.j2')
    content = template.render(app_name=app_name, name=name)
    folder = os.path.join(BASE_DIR, app_name) + '/views'
    file_path = '{folder}/{name}ViewSet.py'.format(folder=folder, name=name)
    if not os.path.exists(folder):
        os.makedirs(name=folder)
    if override:
        with open(file_path, 'w', encoding='utf-8') as fp:
            fp.write(content)
        print('>>> gen view set success!!!')
    else:
        print('>>> file already exists, you can pass extra arg: override = True, to override exists file...')


urls

# -*- coding: utf-8 -*-

from django.conf.urls import url
from django.urls import include
from rest_framework.routers import DefaultRouter

from .views import views
from .views.BogViewSet import BLogViewSet

router = DefaultRouter()
router.register(r'blog', BLogViewSet, basename='blog')

urlpatterns = (
    url(r'^$', views.home),
    url(r'^home/', include(router.urls)),
    url(r'^api/test/$', views.api_test),
)

你可能感兴趣的:(蓝鲸SaaS开发搭建Django+Vue前后端分离的开发框架)