瀏覽代碼

新增操作按钮分组下拉列表
新增拖拽上传文件功能
移除后台首页的新闻调用
优化后台修改管理员密码
修复在PHP7.3下的BUG

Karson 6 年之前
父節點
當前提交
6863ff05b4

+ 3 - 3
README.md

@@ -23,8 +23,8 @@ FastAdmin是一款基于ThinkPHP5+Bootstrap的极速后台开发框架。
 * 共用同一账号体系的Web端会员中心权限验证和API接口会员权限验证
 * 二级域名部署支持,同时域名支持绑定到插件
 * 多语言支持,服务端及客户端支持
-* 强大的第三方模块支持([CMS](https://www.fastadmin.net/store/cms.html)、[博客](https://www.fastadmin.net/store/blog.html)、[文档生成](https://www.fastadmin.net/store/docs.html)、[个人免签支付](https://www.fastadmin.net/store/pay.html))
-* 整合第三方短信接口(阿里云、创蓝短信)
+* 强大的第三方模块支持([CMS](https://www.fastadmin.net/store/cms.html)、[博客](https://www.fastadmin.net/store/blog.html)、[文档生成](https://www.fastadmin.net/store/docs.html))
+* 整合第三方短信接口(阿里云、腾讯云短信)
 * 无缝整合第三方云存储(七牛、阿里云OSS、又拍云)功能
 * 第三方富文本编辑器支持(Summernote、Tinymce、百度编辑器)
 * 第三方登录(QQ、微信、微博)整合
@@ -53,7 +53,7 @@ https://demo.fastadmin.net
 
 交流社区: https://forum.fastadmin.net
 
-QQ群: [636393962](https://jq.qq.com/?_wv=1027&k=487PNBb)(交流群①) [708784003](https://jq.qq.com/?_wv=1027&k=5ObjtwM)(交流群②) [696992864](https://jq.qq.com/?_wv=1027&k=5R2AB00)(高级群,邀请加入)
+QQ群: [636393962](https://jq.qq.com/?_wv=1027&k=487PNBb)(满) [708784003](https://jq.qq.com/?_wv=1027&k=5ObjtwM)(满) [964776039](https://jq.qq.com/?_wv=1027&k=59qjU2P)(3群)
 
 Email: (karsonzhang#163.com, 把#换成@)
 

+ 0 - 17
application/admin/view/common/header.html

@@ -28,23 +28,6 @@
                     <a href="__PUBLIC__" target="_blank"><i class="fa fa-home" style="font-size:14px;"></i></a>
                 </li>
 
-                <li class="dropdown notifications-menu hidden-xs">
-                    <a href="#" class="dropdown-toggle" data-toggle="dropdown">
-                        <i class="fa fa-bell-o"></i>
-                        <span class="label label-warning"></span>
-                    </a>
-                    <ul class="dropdown-menu">
-                        <li class="header">{:__('Latest news')}</li>
-                        <li>
-                            <!-- FastAdmin最新更新信息,你可以替换成你自己站点的信息,请注意修改public/assets/js/backend/index.js文件 -->
-                            <ul class="menu">
-
-                            </ul>
-                        </li>
-                        <li class="footer"><a href="#" target="_blank">{:__('View more')}</a></li>
-                    </ul>
-                </li>
-
                 <!-- 账号信息下拉框 -->
                 <li class="hidden-xs">
                     <a href="javascript:;" data-toggle="checkupdate" title="{:__('Check for updates')}">

+ 1 - 0
application/admin/view/dashboard/index.html

@@ -335,6 +335,7 @@
                     </div>
                 </div>
 
+                <!--如果需要删除最新新闻和最新发贴,删除HTML后还需要删除dashboard.js中的代码-->
                 <div class="row">
                     <div class="col-lg-4">
                         <div class="box box-danger">

+ 1 - 1
application/admin/view/general/profile/index.html

@@ -72,7 +72,7 @@
                         </div>
                         <div class="form-group">
                             <label for="password" class="control-label">{:__('Password')}:</label>
-                            <input type="text" class="form-control" id="password" placeholder="{:__('Leave password blank if dont want to change')}" autocomplete="new-password" name="row[password]" value=""/>
+                            <input type="password" class="form-control" id="password" placeholder="{:__('Leave password blank if dont want to change')}" autocomplete="new-password" name="row[password]" value="" data-rule="password"/>
                         </div>
                         <div class="form-group">
                             <button type="submit" class="btn btn-success">{:__('Submit')}</button>

+ 1 - 1
application/admin/view/index/login.html

@@ -81,7 +81,7 @@
                                     <div class="input-group-addon"><span class="glyphicon glyphicon-option-horizontal" aria-hidden="true"></span></div>
                                     <input type="text" name="captcha" class="form-control" placeholder="{:__('Captcha')}" data-rule="{:__('Captcha')}:required;length(4)" />
                                     <span class="input-group-addon" style="padding:0;border:none;cursor:pointer;">
-                                        <img src="{:rtrim('__PUBLIC__', '/')}/captcha" width="100" height="30" onclick="this.src = '{:rtrim('__PUBLIC__', '/')}/captcha?r=' + Math.random();"/>
+                                        <img src="{:rtrim('__PUBLIC__', '/')}/index.php/captcha" width="100" height="30" onclick="this.src = '{:rtrim('__PUBLIC__', '/')}/index.php/captcha?r=' + Math.random();"/>
                                     </span>
                                 </div>
                                 {/if}

+ 2 - 2
application/common/controller/Backend.php

@@ -315,7 +315,7 @@ class Backend extends Controller
                 case 'NOT BETWEEN':
                     $arr = array_slice(explode(',', $v), 0, 2);
                     if (stripos($v, ',') === false || !array_filter($arr))
-                        continue;
+                        continue 2;
                     //当出现一边为空时改变操作符
                     if ($arr[0] === '') {
                         $sym = $sym == 'BETWEEN' ? '<=' : '>';
@@ -331,7 +331,7 @@ class Backend extends Controller
                     $v = str_replace(' - ', ',', $v);
                     $arr = array_slice(explode(',', $v), 0, 2);
                     if (stripos($v, ',') === false || !array_filter($arr))
-                        continue;
+                        continue 2;
                     //当出现一边为空时改变操作符
                     if ($arr[0] === '') {
                         $sym = $sym == 'RANGE' ? '<=' : '>';

+ 0 - 16
public/assets/js/backend/index.js

@@ -52,21 +52,6 @@ define(['jquery', 'bootstrap', 'backend', 'addtabs', 'adminlte', 'form'], functi
                 Backend.api.addtabs($(this).data("url"));
             });
 
-            //读取FastAdmin的更新信息
-            $.ajax({
-                url: Config.fastadmin.api_url + '/news/index',
-                type: 'post',
-                dataType: 'jsonp',
-                success: function (ret) {
-                    $(".notifications-menu > a span").text(ret.new > 0 ? ret.new : '');
-                    $(".notifications-menu .footer a").attr("href", ret.url);
-                    $.each(ret.newslist, function (i, j) {
-                        var item = '<li><a href="' + j.url + '" target="_blank"><i class="' + j.icon + '"></i> ' + j.title + '</a></li>';
-                        $(item).appendTo($(".notifications-menu ul.menu"));
-                    });
-                }
-            });
-
             //读取首次登录推荐插件列表
             if (localStorage.getItem("fastep") == "installed") {
                 $.ajax({
@@ -203,7 +188,6 @@ define(['jquery', 'bootstrap', 'backend', 'addtabs', 'adminlte', 'form'], functi
                 }
             });
 
-
             var multiplenav = Config.fastadmin.multiplenav;
             var firstnav = $("#firstnav .nav-addtabs");
             var nav = multiplenav ? $("#secondnav .nav-addtabs") : firstnav;

+ 20 - 2
public/assets/js/require-backend.min.js

@@ -6021,6 +6021,7 @@ define('upload',['jquery', 'bootstrap', 'plupload', 'template'], function ($, un
                         container: $(this).parent().get(0), //取按钮的上级元素
                         flash_swf_url: '/assets/libs/plupload/js/Moxie.swf',
                         silverlight_xap_url: '/assets/libs/plupload/js/Moxie.xap',
+                        drop_element: [id, $(this).data("input-id")],
                         filters: {
                             max_file_size: maxsize,
                             mime_types: mimetype,
@@ -9930,8 +9931,9 @@ define('table',['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstr
                 type = typeof type === 'undefined' ? 'buttons' : type;
                 var options = table ? table.bootstrapTable('getOptions') : {};
                 var html = [];
-                var hidden, visible, disable, url, classname, icon, text, title, refresh, confirm, extend, click;
+                var hidden, visible, disable, url, classname, icon, text, title, refresh, confirm, extend, click, dropdown, link;
                 var fieldIndex = column.fieldIndex;
+                var dropdowns = {};
 
                 $.each(buttons, function (i, j) {
                     if (type === 'operate') {
@@ -9952,6 +9954,7 @@ define('table',['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstr
                         if (!visible) {
                             return true;
                         }
+                        dropdown = j.dropdown ? j.dropdown : '';
                         url = j.url ? j.url : '';
                         url = typeof url === 'function' ? url.call(table, row, j) : (url ? Fast.api.fixurl(Table.api.replaceurl(url, row, table)) : 'javascript:;');
                         classname = j.classname ? j.classname : 'btn-primary btn-' + name + 'one';
@@ -9965,9 +9968,24 @@ define('table',['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstr
                         if (disable) {
                             classname = classname + ' disabled';
                         }
-                        html.push('<a href="' + url + '" class="' + classname + '" ' + (confirm ? confirm + ' ' : '') + (refresh ? refresh + ' ' : '') + extend + ' title="' + title + '" data-table-id="' + (table ? table.attr("id") : '') + '" data-field-index="' + fieldIndex + '" data-row-index="' + index + '" data-button-index="' + i + '"><i class="' + icon + '"></i>' + (text ? ' ' + text : '') + '</a>');
+                        link = '<a href="' + url + '" class="' + classname + '" ' + (confirm ? confirm + ' ' : '') + (refresh ? refresh + ' ' : '') + extend + ' title="' + title + '" data-table-id="' + (table ? table.attr("id") : '') + '" data-field-index="' + fieldIndex + '" data-row-index="' + index + '" data-button-index="' + i + '"><i class="' + icon + '"></i>' + (text ? ' ' + text : '') + '</a>';
+                        if (dropdown) {
+                            if (typeof dropdowns[dropdown] == 'undefined') {
+                                dropdowns[dropdown] = [];
+                            }
+                            dropdowns[dropdown].push(link);
+                        } else {
+                            html.push(link);
+                        }
                     }
                 });
+                if (!$.isEmptyObject(dropdowns)) {
+                    var dropdownHtml = [];
+                    $.each(dropdowns, function (i, j) {
+                        dropdownHtml.push('<div class="btn-group"><button type="button" class="btn btn-primary dropdown-toggle btn-xs" data-toggle="dropdown">' + i + '</button><button type="button" class="btn btn-primary dropdown-toggle btn-xs" data-toggle="dropdown"><span class="caret"></span></button><ul class="dropdown-menu pull-right"><li>' + j.join('</li><li>') + '</li></ul></div>');
+                    });
+                    html.unshift(dropdownHtml);
+                }
                 return html.join(' ');
             },
             //替换URL中的数据

+ 19 - 2
public/assets/js/require-table.js

@@ -541,8 +541,9 @@ define(['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstrap-table
                 type = typeof type === 'undefined' ? 'buttons' : type;
                 var options = table ? table.bootstrapTable('getOptions') : {};
                 var html = [];
-                var hidden, visible, disable, url, classname, icon, text, title, refresh, confirm, extend, click;
+                var hidden, visible, disable, url, classname, icon, text, title, refresh, confirm, extend, click, dropdown, link;
                 var fieldIndex = column.fieldIndex;
+                var dropdowns = {};
 
                 $.each(buttons, function (i, j) {
                     if (type === 'operate') {
@@ -563,6 +564,7 @@ define(['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstrap-table
                         if (!visible) {
                             return true;
                         }
+                        dropdown = j.dropdown ? j.dropdown : '';
                         url = j.url ? j.url : '';
                         url = typeof url === 'function' ? url.call(table, row, j) : (url ? Fast.api.fixurl(Table.api.replaceurl(url, row, table)) : 'javascript:;');
                         classname = j.classname ? j.classname : 'btn-primary btn-' + name + 'one';
@@ -576,9 +578,24 @@ define(['jquery', 'bootstrap', 'moment', 'moment/locale/zh-cn', 'bootstrap-table
                         if (disable) {
                             classname = classname + ' disabled';
                         }
-                        html.push('<a href="' + url + '" class="' + classname + '" ' + (confirm ? confirm + ' ' : '') + (refresh ? refresh + ' ' : '') + extend + ' title="' + title + '" data-table-id="' + (table ? table.attr("id") : '') + '" data-field-index="' + fieldIndex + '" data-row-index="' + index + '" data-button-index="' + i + '"><i class="' + icon + '"></i>' + (text ? ' ' + text : '') + '</a>');
+                        link = '<a href="' + url + '" class="' + classname + '" ' + (confirm ? confirm + ' ' : '') + (refresh ? refresh + ' ' : '') + extend + ' title="' + title + '" data-table-id="' + (table ? table.attr("id") : '') + '" data-field-index="' + fieldIndex + '" data-row-index="' + index + '" data-button-index="' + i + '"><i class="' + icon + '"></i>' + (text ? ' ' + text : '') + '</a>';
+                        if (dropdown) {
+                            if (typeof dropdowns[dropdown] == 'undefined') {
+                                dropdowns[dropdown] = [];
+                            }
+                            dropdowns[dropdown].push(link);
+                        } else {
+                            html.push(link);
+                        }
                     }
                 });
+                if (!$.isEmptyObject(dropdowns)) {
+                    var dropdownHtml = [];
+                    $.each(dropdowns, function (i, j) {
+                        dropdownHtml.push('<div class="btn-group"><button type="button" class="btn btn-primary dropdown-toggle btn-xs" data-toggle="dropdown">' + i + '</button><button type="button" class="btn btn-primary dropdown-toggle btn-xs" data-toggle="dropdown"><span class="caret"></span></button><ul class="dropdown-menu pull-right"><li>' + j.join('</li><li>') + '</li></ul></div>');
+                    });
+                    html.unshift(dropdownHtml);
+                }
                 return html.join(' ');
             },
             //替换URL中的数据

+ 1 - 0
public/assets/js/require-upload.js

@@ -199,6 +199,7 @@ define(['jquery', 'bootstrap', 'plupload', 'template'], function ($, undefined,
                         container: $(this).parent().get(0), //取按钮的上级元素
                         flash_swf_url: '/assets/libs/plupload/js/Moxie.swf',
                         silverlight_xap_url: '/assets/libs/plupload/js/Moxie.xap',
+                        drop_element: [id, $(this).data("input-id")],
                         filters: {
                             max_file_size: maxsize,
                             mime_types: mimetype,

+ 2 - 2
public/install.php

@@ -122,8 +122,8 @@ if (isset($_SERVER['REQUEST_METHOD']) && $_SERVER['REQUEST_METHOD'] == 'POST') {
     } else if (strlen($adminUsername) < 3 || strlen($adminUsername) > 12) {
         echo "用户名请输入3~12位字符";
         exit;
-    } else if (strlen($adminPassword) < 6 || strlen($adminPassword) > 16) {
-        echo "密码请输入6~16位字符";
+    } else if (strlen($adminPassword) < 6 || strlen($adminPassword) > 16 || stripos($adminPassword, ' ') !== false) {
+        echo "密码请输入6~16位字符,不能包含空格";
         exit;
     }
     try {