• 设为首页
  • 点击收藏
  • 手机版
    手机扫一扫访问
    迪恩网络手机版
  • 关注官方公众号
    微信扫一扫关注
    公众号

quasar-sika-design-admin: quasar-sika-design-admin是一套企业级中后台管理系统解决 ...

原作者: [db:作者] 来自: 网络 收藏 邀请

开源软件名称:

quasar-sika-design-admin

开源软件地址:

https://gitee.com/sikadai/quasar-sika-design-admin

开源软件介绍:

quasar-sika-design-admin

English | 简体中文

Quasar Sika Design Admin

An out-of-box UI solution for enterprise applications as a Vue boilerplate. based on Quasar

LicenseRelease

项目介绍

  • quasar-sika-design-admin是一套企业级中后台管理系统解决方案,Quasar Sika Design Admin 是一个企业级中后台前端 / 设计解决方案,中后台管理模板,我们秉承 Ant Design 的设计价值观,致力于在设计规范和基础组件的基础上,继续向上构建,提炼出典型模板 / 业务组件 / 配套设计资源,进一步提升企业级中后台产品设计研发过程中的『用户』和『设计者』的体验

项目初衷

起于 Sika Design,不止于 Sika Design,每一个细节都是极致体验愿景:开源改变世界,Sika Design Admin 让世界没有难写的代码。

项目特色

前端

  • 优雅美观:基于 Ant Design 体系精心设计
  • 常见设计模式:开源改变世界,Sika Design 让世界没有难写的代码
  • 最新技术栈:使用 Quasar&Vue&echarts 等前端前沿技术开发
  • 响应式:针对不同屏幕大小设计
  • 主题:可配置的主题满足多样化的品牌诉求
  • 最佳实践:良好的工程实践助你持续产出高质量代码

后端

  • 优雅、简洁、规范而不失个性
  • 抽象基础组件
  • 约束代码规范
  • 特色的领域驱动设计实践【上下文对象context+executor执行者】
  • 完整的代码生成器-新模块基础功能零开发

组织结构

- quasar-sika-design-admin  - quasar-sika-design // 前端-基于vue+quasar构建  - quasar-sika-design-server // 后端服务-基于springboot+mybatis    - doc // 文档说明      - sql // sql脚本    - quasar-sika-design-server-common // 基础公共模块;包括业务的constant+dto+query以及baseDTO+baseSrvice等等    - quasar-sika-design-server-core // 核心业务模块;包括业务的service,核心领域实现逻辑等等    - quasar-sika-design-server-ataaccess // 数据库访问层    - quasar-sika-design-server-generator // 代码生成器模块【无须开发】    - quasar-sika-design-server-web // controller层    - sika-code-cor // 核心公共组件,包括且不限于缓存组件、代码生成器组件、公共组件、数据访问、分布式锁、脚手架规范      - cache // 缓存组件      - code-generator // 代码生成器组件      - common // 公共组件      - databasse // 数据库访问组件      - hutool-starter // hutool基础集成      - lock // 分布式组件      - standard-footer // 标准脚手架组件

技术选型

后端技术

技术官网备注
Spring Frameworkhttp://projects.spring.io/spring-framework/容器
spring-boot-dependencieshttps://spring.io/projects/spring-boot/不解释
Apache Shirohttp://shiro.apache.org/安全框架
MyBatishttp://www.mybatis.org/mybatis-3/zh/index.htmlORM框架
MyBatisPlushttps://mp.baomidou.com/ORM增强框架
Mybatis-plus-boot-starterhttps://mp.baomidou.com/ORM增强框架
Mybatis-Plus-Generatorhttps://baomidou.gitee.io/mybatis-plus-doc/#/generate-code/ORM增强框架
HikariCPhttps://github.com/brettwooldridge/HikariCP/数据库连接池
ShardingSpherehttps://shardingsphere.apache.org/分库分表组件
Redishttps://redis.io/分布式缓存数据库
commons-collectionshttp://commons.apache.org/proper/commons-collections/集合工具组件
Log4Jhttp://logging.apache.org/log4j/1.2/日志组件
FastJsonhttps://mvnrepository.com/artifact/com.alibaba/fastjson/JSON序列化和反序列化组件
Lombokhttps://www.projectlombok.org/简化JAVA代码组件
Hutoolhttp://hutool.mydoc.io/符合国人习惯的工具组件
MapStructhttp://mapstruct.org/实体转化组件

前端技术

技术官网备注
Vuehttps://cn.vuejs.org/渐进式JavaScript 框架
Quasarhttp://www.quasarchs.com/基于Vue实现的前端UI框架
Echartshttps://echarts.apache.org/zh/index.html/基于 JavaScript 的开源可视化图表库
Lodashihttps://www.lodashjs.com/一致性、模块化、高性能的 JavaScript 实用工具库

Overview

基于 Quasar 实现的 Quasar Sika Design_Admin

PC端示例




mobile端示例


服务端代码示例

Controller 由代码生成器生成

package com.quasar.sika.design.server.business.menu.controller;import java.util.List;import com.sika.code.result.Result;import com.sika.code.standard.base.controller.BaseStandardController;import com.quasar.sika.design.server.business.menu.service.MenuService;import com.quasar.sika.design.server.business.menu.pojo.dto.MenuDTO;import com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.web.bind.annotation.RequestBody;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.RestController;/** * <p> * 菜单权限表 前端控制器 * </p> * * @author daiqi * @since 2021-01-07 23:35:13 */@RestController(value = "menuController")@RequestMapping("menu")public class MenuController extends BaseStandardController {    @Autowired    private MenuService menuService;    @RequestMapping(value = "save")    public Result save(@RequestBody MenuDTO menuDto) {        return super.success(menuService.save(menuDto));    }    @RequestMapping(value = "save_batch")    public Result saveBatch(@RequestBody List<MenuDTO> menuDtos) {        return super.success(menuService.saveForBatch(menuDtos));    }    @RequestMapping(value = "update_by_id")    public Result updateById(@RequestBody MenuDTO menuDto) {        return super.success(menuService.updateById(menuDto));    }    @RequestMapping(value = "page")    public Result page(@RequestBody MenuQuery menuQuery) {        return super.success(menuService.page(menuQuery));    }    @RequestMapping(value = "find")    public Result find(@RequestBody MenuQuery menuQuery) {        return super.success(menuService.find(menuQuery));    }    @RequestMapping(value = "list")    public Result list(@RequestBody MenuQuery menuQuery) {        return super.success(menuService.list(menuQuery));    }}

Service 由代码生成器生成

package com.quasar.sika.design.server.business.menu.service;import com.quasar.sika.design.server.business.menu.pojo.dto.MenuDTO;import com.sika.code.standard.base.service.BaseStandardService;import java.util.List;/** * <p> * 菜单权限表 服务类 * </p> * * @author daiqi * @since 2021-01-07 23:35:09 */public interface MenuService extends BaseStandardService<MenuDTO> {}

ServiceImpl 由代码生成器生成

package com.quasar.sika.design.server.business.menu.service.impl;import cn.hutool.core.collection.CollUtil;import com.google.common.collect.Lists;import com.quasar.sika.design.server.business.menu.convert.MenuConvert;import com.quasar.sika.design.server.business.menu.entity.MenuEntity;import com.quasar.sika.design.server.business.menu.mapper.MenuMapper;import com.quasar.sika.design.server.business.menu.pojo.dto.MenuDTO;import com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery;import com.quasar.sika.design.server.business.menu.service.MenuService;import com.quasar.sika.design.server.business.rolemenu.service.RoleMenuService;import com.sika.code.standard.base.convert.BaseConvert;import com.sika.code.standard.base.service.impl.BaseStandardServiceImpl;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.stereotype.Service;import java.util.List;import java.util.Set;/** * <p> * 菜单权限表 服务实现类 * </p> * * @author daiqi * @since 2021-01-07 23:35:10 */@Service(value = "menuService")public class MenuServiceImpl extends BaseStandardServiceImpl<MenuMapper, MenuEntity, MenuDTO> implements MenuService {    @Autowired    private MenuMapper menuMapper;    @Override    protected BaseConvert<MenuEntity, MenuDTO> convert() {        return MenuConvert.INSTANCE;    }}

Mapper 由代码生成器生成

package com.quasar.sika.design.server.business.menu.mapper;import com.quasar.sika.design.server.business.menu.entity.MenuEntity;import org.springframework.stereotype.Repository;import com.sika.code.standard.base.basemapper.BaseStandardMapper;/** * <p> * 菜单权限表 Mapper 接口 * </p> * * @author daiqi * @since 2021-01-07 23:35:08 */@Repositorypublic interface MenuMapper extends BaseStandardMapper<MenuEntity> {}

Xml 由代码生成器生成

<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"><mapper namespace="com.quasar.sika.design.server.business.menu.mapper.MenuMapper">    <!-- 通用查询映射结果 -->    <resultMap id="ResultMap" type="com.quasar.sika.design.server.business.menu.entity.MenuEntity">        <result column="id" property="id" />        <result column="create_by" property="createBy" />        <result column="update_by" property="updateBy" />        <result column="create_date" property="createDate" />        <result column="update_date" property="updateDate" />        <result column="version" property="version" />        <result column="available" property="available" />        <result column="is_deleted" property="isDeleted" />        <result column="remark" property="remark" />        <result column="menu_name" property="menuName" />        <result column="parent_id" property="parentId" />        <result column="order_num" property="orderNum" />        <result column="url" property="url" />        <result column="target" property="target" />        <result column="menu_type" property="menuType" />        <result column="visible" property="visible" />        <result column="perms" property="perms" />        <result column="icon" property="icon" />    </resultMap>    <!-- 通用查询结果列 -->    <sql id="columnList">        id, create_by, update_by, create_date, update_date, version, available, is_deleted, remark, menu_name, parent_id, order_num, url, target, menu_type, visible, perms, icon    </sql>    <!-- 根据查询条件获取列表信息 -->    <select id="listByQuery" resultMap="ResultMap" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT <include refid="columnList" />        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>    </select>    <!-- 根据查询条件获取Id列表信息 -->    <select id="listIdByQuery" resultType="java.lang.Long" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT id        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>    </select>    <!-- 根据查询条件获取实体信息 -->    <select id="findByQuery" resultMap="ResultMap" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT <include refid="columnList" />        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>        LIMIT 1    </select>    <!-- 根据查询条件获取表id -->    <select id="findIdByQuery" resultType="java.lang.Long" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT id        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>        LIMIT 1    </select>    <!-- 根据查询条件获取分页信息 -->    <select id="pageByQuery" resultMap="ResultMap" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT <include refid="columnList" />        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>        <include refid="order_by_sql"/>    </select>    <!-- 根据查询条件获取总数量信息 -->    <select id="totalCountByQuery" resultType="Integer" parameterType="com.quasar.sika.design.server.business.menu.pojo.query.MenuQuery" >        SELECT count(*)        FROM sika_menu        <where>            is_deleted = 0            <include refid="query_sql" />        </where>    </select>    <!-- 根据查询条件SQL -->    <sql id="query_sql" >        <if test="query.id != null">AND id = #{query.id}</if>        <if test="query.menuId != null">AND id = #{query.menuId}</if>        <if test="query.menuName != null">AND menu_name = #{query.menuName}</if>        <if test="query.parentId != null">AND parent_id = #{query.parentId}</if>        <if test="query.orderNum != null">AND order_num = #{query.orderNum}</if>        <if test="query.url != null">AND url = #{query.url}</if>        <if test="query.target != null">AND target = #{query.target}</if>        <if test="query.menuType != null">AND menu_type = #{query.menuType}</if>        <if test="query.visible != null">AND visible = #{query.visible}</if>        <if test="query.perms != null">AND perms = #{query.perms}</if>        <if test="query.icon != null">AND icon = #{query.icon}</if>        <if test="query.ids != null and query.ids.size() > 0">            AND id in            <foreach item="item" collection="query.ids" separator="," open="(" close=")" index="">                #{item}            </foreach>        </if>    </sql>    <!-- 排序的sql -->    <sql id="order_by_sql">        <if test="query.sortColumn != null and query.sortType != null" >            ORDER BY            <include refid="order_by_column_sql"/>            <include refid="order_by_type_sql"/>        </if>    </sql>    <!-- 排序列名的sql -->    <sql id="order_by_column_sql">        <choose>            <when test="query.sortColumn == 'menuId'">                id            </when>            <otherwise>                id            </otherwise>        </choose>    </sql>    <!-- 排序类型的sql -->    <sql id="order_by_type_sql">        <choose>            <when test="query.sortType == 'DESC'">                DESC            </when>            <otherwise>                ASC            </otherwise>        </choose>    </sql></mapper>

Context【领域上下文对象】

package com.quasar.sika.design.server.common.auth.context;import com.quasar.sika.design.server.common.auth.executor.AuthRegisterRequestExecutor;import com.quasar.sika.design.server.common.auth.pojo.request.AuthRegisterRequest;import com.quasar.sika.design.server.common.captcha.pojo.request.CaptchaCheckRequest;import com.quasar.sika.design.server.common.mail.context.CheckMailCodeContext;import com.quasar.sika.design.server.common.mail.pojo.request.CheckMailRequest;import com.quasar.sika.design.server.common.shiro.util.SHA256Util;import com.sika.code.standard.base.pojo.context.BaseStandardContext;import com.sika.code.standard.base.pojo.executor.BaseStandardExecutor;import lombok.Data;import lombok.experimental.Accessors;/** * @author daiqi * @create 2021-01-09 18:02 */@Data@Accessors(chain = true)public class AuthRegisterContext extends BaseStandardContext {    private AuthRegisterRequest registerRequest;    private CheckMailRequest checkMailRequest;    protected CaptchaCheckRequest captchaCheckRequest;    private CheckMailCodeContext checkMailCodeContext;    private Boolean bindOauthUser;    @Override    public void initCustomer() {        checkMailCodeContext = new CheckMailCodeContext().setRequest(checkMailRequest);        registerRequest.setPassword(SHA256Util.sha256(registerRequest));    }    @Override    protected Class<? extends BaseStandardExecutor> buildExecutorClass() {        return AuthRegisterRequestExecutor.class;    }}

Executor领域执行者对象【按领域划分】

package com.quasar.sika.design.server.common.auth.executor;import cn.hutool.core.util.BooleanUtil;import com.quasar.sika.design.server.common.auth.context.AuthRegisterContext;import com.quasar.sika.design.server.common.auth.domain.AuthDomain;import com.quasar.sika.design.server.common.auth.pojo.request.AuthLoginRequest;import com.quasar.sika.design.server.common.auth.pojo.request.AuthRegisterRequest;import com.quasar.sika.design.server.common.auth.pojo.response.AuthResponse;import com.sika.code.basic.pojo.dto.ServiceResult;import com.sika.code.exception.BusinessException;import com.sika.code.standard.base.pojo.executor.BaseStandardExecutor;import lombok.Data;import lombok.experimental.Accessors;/** * @author daiqi * @create 2021-01-09 18:02 */@Data@Accessors(chain = true)public class AuthRegisterRequestExecutor extends BaseStandardExecutor<AuthRegisterContext> implements AuthDomain {    @Override    protected void executeBefore() {        verify();    }    protected void verify() {        // 图片验证码校验        captchaService().checkCaptchaVerifyCode(context.getCaptchaCheckRequest());        // 邮箱验证码校验        executorManager().execute(context.getCheckMailCodeContext());        // 校验用户名        AuthRegisterRequest registerRequest = context.getRegisterRequest();        authService().checkRegisterUsername(registerRequest);        // 校验邮箱        authService().checkRegisterEmail(registerRequest);        // 校验手机号        authService().checkRegisterPhone(registerRequest);    }    @Override    protected ServiceResult doExecute() {        AuthRegisterRequest registerRequest = context.getRegisterRequest();        boolean saveSuccess = userService().save(registerRequest);        if (BooleanUtil.isFalse(saveSuccess)) {            throw new BusinessException("保存失败,请校验注册参数");        }        return ServiceResult.newInstanceOfSucResult(AuthResponse.success(registerRequest));    }    @Override    protected void executeAfter() {        // 自动登录        AuthRegisterRequest registerRequest = context.getRegisterRequest();        AuthLoginRequest request = new AuthLoginRequest(registerRequest.getUsername(), registerRequest.getPassword());        request.setEncryptedPassword(true);        if (BooleanUtil.isTrue(context.getBindOauthUser())) {            authService().bindOauthUser(request);        } else {            authService().login(request);        }        // 移除缓存        captchaService().removeCaptchaVerifyCode(context.getCaptchaCheckRequest());        mailService().removeMailCode(context.getCheckMailRequest());    }}

前端环境和依赖

  • node
  • yarn
  • webpack
  • eslint
  • @vue/cli ~3
  • Quasar - Quasar Of Vue 实现

请注意,我们强烈建议本项目使用 Yarn 包管理工具,这样可以与本项目演示站所加载完全相同的依赖版本 (yarn.lock) 。由于我们没有对依赖进行强制的版本控制,采用非 yarn 包管理进行引入时,可能由于 Pro 所依赖的库已经升级版本而引入了新版本所导致的问题。作者可能会由于时间问题无法及时排查而导致您采用本项目作为基项目而出现问题。

项目下载和运行

  • 拉取项目代码
git clone https://github.com/dq-open-cloud/quasar-sika-design.gitcd quasar-sika-design
  • 安装依赖
yarn install
  • 开发模式运行
quasar dev
  • 编译项目
quasar build
  • Lints and fixes files
yarn run lint

文档待完善

启动步骤

  • 找到QuasarSikaDesignServerApplication直接运行
  • 前端quasar-dev启动运行即可

其他说明

  • 关于 Issue 反馈 (重要!重要!重要!) 请在开 Issue 前,先阅读该内容:Issue / PR 编写建议

  • 项目使用的 quasar-cli, 请确保你所使用的 quasar-cli 是新版,并且已经学习 cli 官方文档使用教程

  • 关闭 Eslint (不推荐) 移除 package.jsoneslintConfig 整个节点代码, vue.config.js 下的 lintOnSave 值改为 false

  • 用于生产环境,请使用 release 版本代码,使用 master 代码出现的任何问题需要你自行解决

  • 后端提供的MysqlRedis环境属于线上测试环境,内测阶段请大家一定不要随意增删字段

浏览器兼容

  • Chrome for Android >= 87
  • Firefox for Android >= 83
  • Android >= 81
  • Chrome >= 77
  • Edge >= 84
  • Firefox >= 74
  • iOS >= 10.3
  • Opera >= 68
  • Safari >= 11
IE / EdgeIE / EdgeFirefoxFirefoxChromeChromeSafariSafariOperaOpera
IE10, Edgelast 2 versionslast 2 versionslast 2 versionslast 2 versions

Contributors

This project exists thanks to all the people who contribute.

Customize the configuration

See Configuring quasar.conf.js.


鲜花

握手

雷人

路过

鸡蛋
该文章已有0人参与评论

请发表评论

全部评论

专题导读
热门推荐
热门话题
阅读排行榜

扫描微信二维码

查看手机版网站

随时了解更新最新资讯

139-2527-9053

在线客服(服务时间 9:00~18:00)

在线QQ客服
地址:深圳市南山区西丽大学城创智工业园
电邮:jeky_zhao#qq.com
移动电话:139-2527-9053

Powered by 互联科技 X3.4© 2001-2213 极客世界.|Sitemap