新增模块
- Nav 模型(applications/models/admin_nav.py):公开导航表,与 admin_power 解耦
- NavOutSchema / NavManageSchema(applications/schemas/admin_nav.py)
- 前台公开视图 applications/view/public/nav.py:/site/、/site/category/<name>、/site/api/navs,无需登录
- 后台管理视图 applications/view/system/nav.py:CRUD + 启用/禁用,挂入 system_bp
- 前台模板 templates/public/{base,index,category}.html(独立配色,无需登录即可访问)
- 后台模板 templates/system/nav/{main,add,edit}.html(Layui table + form)
调整
- applications/view/__init__.py:注册前台蓝图到根
- applications/view/system/__init__.py:注册后台 nav 子蓝图
- applications/common/script/admin.py:admin init/export 支持 navs 数组
- applications/common/script/app_data/init.json:新增 10 条导航种子 + 4 条 system:nav 权限
数据库
- 新增 public_nav 表(含 category 索引)
- migration: 38751d88d42c_add_public_nav_table.py
100 lines
3.9 KiB
HTML
100 lines
3.9 KiB
HTML
<!DOCTYPE html>
|
|
<html>
|
|
<head>
|
|
<meta charset="utf-8">
|
|
<title>编辑导航</title>
|
|
{% include 'system/common/header.html' %}
|
|
</head>
|
|
<body>
|
|
<div class="layui-form" lay-filter="nav-form" style="padding: 20px 30px 0 0;">
|
|
<input type="hidden" name="id" value="{{ nav.id }}">
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">分类</label>
|
|
<div class="layui-input-block">
|
|
<input type="text" name="category" required lay-verify="required" value="{{ nav.category }}"
|
|
autocomplete="off" class="layui-input">
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">标题</label>
|
|
<div class="layui-input-block">
|
|
<input type="text" name="title" required lay-verify="required" value="{{ nav.title }}"
|
|
autocomplete="off" class="layui-input">
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">链接 URL</label>
|
|
<div class="layui-input-block">
|
|
<input type="text" name="url" required lay-verify="required|url" value="{{ nav.url }}"
|
|
autocomplete="off" class="layui-input">
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">简介</label>
|
|
<div class="layui-input-block">
|
|
<textarea name="description" class="layui-textarea">{{ nav.description or '' }}</textarea>
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">图标</label>
|
|
<div class="layui-input-block">
|
|
<input type="text" name="icon" value="{{ nav.icon }}" autocomplete="off" class="layui-input">
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">排序</label>
|
|
<div class="layui-input-inline">
|
|
<input type="number" name="sort" value="{{ nav.sort }}" autocomplete="off" class="layui-input">
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">类型</label>
|
|
<div class="layui-input-block">
|
|
<input type="radio" name="isExternal" value="1" title="外链(新窗口)" {% if nav.is_external == 1 %}checked{% endif %}>
|
|
<input type="radio" name="isExternal" value="0" title="站内(当前窗口)" {% if nav.is_external != 1 %}checked{% endif %}>
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<label class="layui-form-label">状态</label>
|
|
<div class="layui-input-block">
|
|
<input type="radio" name="status" value="1" title="启用" {% if nav.status == 1 %}checked{% endif %}>
|
|
<input type="radio" name="status" value="0" title="禁用" {% if nav.status != 1 %}checked{% endif %}>
|
|
</div>
|
|
</div>
|
|
<div class="layui-form-item">
|
|
<div class="layui-input-block">
|
|
<button class="layui-btn" lay-submit lay-filter="nav-submit">保存</button>
|
|
<button type="button" class="layui-btn layui-btn-primary" onclick="parent.layer.closeAll();">取消</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
{% include 'system/common/footer.html' %}
|
|
<script>
|
|
layui.use(['form', 'layer'], function(){
|
|
var form = layui.form;
|
|
var layer = layui.layer;
|
|
var $ = layui.$;
|
|
|
|
form.on('submit(nav-submit)', function(data){
|
|
$.ajax({
|
|
url: '/system/nav/update',
|
|
type: 'PUT',
|
|
contentType: 'application/json',
|
|
data: JSON.stringify(data.field),
|
|
success: function(res){
|
|
if (res.success) {
|
|
layer.msg(res.msg, {icon: 1});
|
|
parent.layui.table.reload('nav-table');
|
|
setTimeout(function(){ parent.layer.closeAll(); }, 800);
|
|
} else {
|
|
layer.msg(res.msg, {icon: 2});
|
|
}
|
|
}
|
|
});
|
|
return false;
|
|
});
|
|
});
|
|
</script>
|
|
</body>
|
|
</html> |