Warning: error_log(/data/www/wwwroot/hmttv.cn/caches/error_log.php): failed to open stream: Permission denied in /data/www/wwwroot/hmttv.cn/phpcms/libs/functions/global.func.php on line 537 Warning: error_log(/data/www/wwwroot/hmttv.cn/caches/error_log.php): failed to open stream: Permission denied in /data/www/wwwroot/hmttv.cn/phpcms/libs/functions/global.func.php on line 537
先看數(shù)據(jù)庫(kù)的代碼:
-- 創(chuàng)建數(shù)據(jù)庫(kù)
create database musicdb
use musicdb
-- 創(chuàng)建表
-- 用戶(hù)表
create table [user](
uid int primary key identity(1,1),
name varchar(20) not null,
pwd varchar(20) not null,
[desc] varchar(50)
)
create table music(
mid int primary key identity(101,1),
musicName varchar(50) not null,
singer varchar(20) not null, --歌手
album varchar(20) not null, --專(zhuān)輯
timer varchar(20), --時(shí)長(zhǎng)
position varchar(100), --位置
)
select * from music
select * from [user]
然后vs2019 創(chuàng)建AspNet Web項(xiàng)目,添加Default.aspx
有一定基礎(chǔ)的同學(xué),應(yīng)該知道,AspNet 分兩部分,一部分是前臺(tái)界面,另一部分是后臺(tái)代碼,Aspnet使用了CodeBehind 代碼后置的技術(shù)
Default.aspx 前臺(tái)設(shè)計(jì)界面:
<div class="row">
<h3 class="text-center" style="color: orange">音樂(lè)庫(kù) 管理</h3>
</div>
<div class="row">
<asp:GridView ID="GridView1" runat="server" CssClass="table table-hover table-striped" AutoGenerateColumns="False" OnRowCommand="GridView1_RowCommand" OnRowDeleting="GridView1_RowDeleting" OnRowEditing="GridView1_RowEditing" DataKeyNames="mid" OnRowUpdating="GridView1_RowUpdating" OnRowCancelingEdit="GridView1_RowCancelingEdit">
<Columns>
<asp:BoundField DataField="mid" HeaderText="序號(hào)" />
<asp:BoundField DataField="musicName" HeaderText="歌曲名" />
<asp:BoundField DataField="singer" HeaderText="歌手" />
<asp:BoundField DataField="album" HeaderText="專(zhuān)輯" />
<asp:BoundField DataField="timer" HeaderText="時(shí)長(zhǎng)" />
<asp:BoundField DataField="position" HeaderText="存儲(chǔ)位置" />
<asp:TemplateField HeaderText="操作" ShowHeader="False">
<EditItemTemplate>
<asp:LinkButton ID="LinkButton1" runat="server" CausesValidation="True" CommandName="Update" Text="更新"></asp:LinkButton>
<asp:LinkButton ID="LinkButton2" runat="server" CausesValidation="False" CommandName="Cancel" Text="取消"></asp:LinkButton>
</EditItemTemplate>
<ItemTemplate>
<asp:LinkButton ID="LinkButton3" runat="server" CausesValidation="False" CommandName="Edit" Text="修改"></asp:LinkButton>
<asp:LinkButton ID="LinkButton1" runat="server" CausesValidation="False" CommandName="Delete" Text="刪除"></asp:LinkButton>
<a href="/add.aspx">插入</a>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
</div>
Default.aspx.cs 后臺(tái)代碼
public partial class _Default : Page
{
public string name = "";
protected void Page_Load(object sender, EventArgs e) // 首次加載
{
if (!IsPostBack) {
if (Session["userName"]==null)
{
Response.Redirect("~/login.aspx");
}
else
{
name = Session["userName"].ToString();
LoadMusic();
}
}
}
protected void GridView1_RowDeleting(object sender, GridViewDeleteEventArgs e)
{
string id = GridView1.Rows[e.RowIndex].Cells[0].Text;
string sql = $"delete from music where mid='{id}'";
if (DBHelper.Update(sql))
{
LoadMusic();
}
else {
Response.Write("<script>alert('刪除失敗!')</script>");
}
}
protected void GridView1_RowEditing(object sender, GridViewEditEventArgs e)
{
//string mid = e.CommandArgument.ToString();
name = Session["userName"].ToString();
GridView1.EditIndex = e.NewEditIndex;
LoadMusic();
}
private void LoadMusic()
{
this.GridView1.DataSource = DBHelper.Select("select * from music");
this.GridView1.DataBind();
}
protected void GridView1_RowUpdating(object sender, GridViewUpdateEventArgs e)
{
string id = this.GridView1.DataKeys[e.RowIndex].Value.ToString();
string name = ((TextBox)(GridView1.Rows[e.RowIndex].Cells[1].Controls[0])).Text;
string signer= ((TextBox)(GridView1.Rows[e.RowIndex].Cells[2].Controls[0])).Text;
string album= ((TextBox)(GridView1.Rows[e.RowIndex].Cells[3].Controls[0])).Text;
string timer= ((TextBox)(GridView1.Rows[e.RowIndex].Cells[4].Controls[0])).Text;
string p= ((TextBox)(GridView1.Rows[e.RowIndex].Cells[5].Controls[0])).Text;
string sql = $"update music set musicName='{name}',singer='{signer}',album='{album}',timer='{timer}',position='{p}' where mid='{id}'";
if (DBHelper.Update(sql)) {
Response.Write("<script>alert('修改成功!')</script>");
LoadMusic();
}
}
protected void GridView1_RowCancelingEdit(object sender, GridViewCancelEditEventArgs e)
{
name = Session["userName"].ToString();
GridView1.EditIndex = -1;
LoadMusic();
}
}
效果圖
以上就是首頁(yè)完成的顯示的功能,篇幅有限,需要源碼的朋友私聊我噢
千山萬(wàn)水總是情,打賞一元也是情
和老段一起終身學(xué)習(xí),我們一起做自己的CEO!
?有用嗎?對(duì)于學(xué)完Spring、SpringMVC、Mybatis還無(wú)從下手的同學(xué)來(lái)說(shuō)這是一個(gè)很好引子。對(duì)于正在學(xué)習(xí)同一個(gè)案例的同學(xué),可能解決一些問(wèn)題。對(duì)于需要這個(gè)案例的同學(xué)可以直接獲取。
??有什么?:xml配置文件編寫(xiě),引入一個(gè)簡(jiǎn)單的前端框架,使用MyBatis Generator逆向工程生成一些代碼,使用框架簡(jiǎn)單快速搭建一個(gè)頁(yè)面,好用的分頁(yè)工具PageHelper,簡(jiǎn)單的前后端分離,發(fā)送ajax請(qǐng)求,利用json傳遞數(shù)據(jù),增、刪、改、查的簡(jiǎn)單實(shí)現(xiàn)。
??簡(jiǎn)單嗎?內(nèi)容很簡(jiǎn)單,涉及Java代碼不多,但是對(duì)于新手來(lái)說(shuō),最困難的部分是各種環(huán)境搭建、配置文件、版本沖突,如果能夠根據(jù)錯(cuò)誤提示動(dòng)手解決,那就是一大進(jìn)步。
??怎么學(xué)?如果有時(shí)間可以在B站搜索:ssm整合crud,雷豐陽(yáng)講的。如果想看到每個(gè)功能的實(shí)現(xiàn)過(guò)程和源碼,可以在這里學(xué)習(xí),每個(gè)步驟都有注釋。也可以作為復(fù)習(xí)快速瀏覽。
前端格式校驗(yàn)、用戶(hù)名校驗(yàn)、后端校驗(yàn)、JSR303校驗(yàn),效果如圖
使用彈出模態(tài)框作為新增模塊,參考Bootstrap代碼
<!-- 為新增按鈕增加模態(tài)框 ,利用按鈕綁定單擊事件-->
<!-- Modal -->
<div class="modal fade" id="empAddModal" tabindex="-1" role="dialog"
aria-labelledby="myModalLabel">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal"
aria-label="Close">
<span aria-hidden="true">×</span>
</button>
<h4 class="modal-title" id="myModalLabel">員工添加</h4>
</div>
<div class="modal-body">
<!-- 添加表單 -->
<form class="form-horizontal" id="model-form">
<!-- 姓名 -->
<div class="form-group">
<label for="empName_add_input" class="col-sm-2 control-label">EmpName</label>
<div class="col-sm-10">
<input type="text" class="form-control" name="empName" id="empName_add_input"
placeholder="empName">
<!-- 用來(lái)顯示錯(cuò)誤提示 -->
<span class="help-block"></span>
</div>
</div>
<!-- 郵箱 -->
<div class="form-group">
<label for="email_add_input" class="col-sm-2 control-label">Email</label>
<div class="col-sm-10">
<input type="email" class="form-control" name="email" id="email_add_input"
placeholder="empName@123.com">
<!-- 用來(lái)顯示錯(cuò)誤提示 -->
<span class="help-block"></span>
</div>
</div>
<!-- 性別 -->
<div class="form-group">
<label class="col-sm-2 control-label">Gender</label>
<div class="col-sm-10">
<!-- 單選 -->
<label for="gender1_add_input"> <input type="radio"
name="gender" id="gender1_add_input"
name="gender" value="M" checked>
男
</label>
<label for="gender2_add_input"> <input type="radio"
name="gender" id="gender2_add_input"
name="gender" value="F">
女
</label>
</div>
</div>
<!-- 部門(mén)下拉框 -->
<div class="form-group">
<label class="col-sm-2 control-label">DeptName</label>
<div class="col-sm-10">
<!-- 部門(mén)下拉列表使用ajax查詢(xún)出來(lái)的動(dòng)態(tài)拼接,值為部門(mén)id -->
<select class="form-control" name="dId" id="deptName_add_select"></select>
</div>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">關(guān)閉</button>
<button type="button" class="btn btn-primary" id="emp_save_btn">保存</button>
</div>
</div>
</div>
</div>
//添加模態(tài)欄 $("#emp_add_modal_btn").click(function() {
//顯示模態(tài)框
$("#empAddModal").modal({
//模態(tài)框參數(shù),點(diǎn)擊背景不關(guān)閉
backdrop : "static"
});
});
//新增模態(tài)框 $("#emp_add_modal_btn").click(function() {
//添加模態(tài)欄之前將所表單信息清空,包括兩項(xiàng)驗(yàn)證的css樣式,顯示模態(tài)欄之后就是空的
//reset()方法是dom下的,使用[0]
$("#empAddModal form")[0].reset();
//清空輸入格式、重名校驗(yàn)的css樣式
reset_form("#empAddModal form");
//獲取所有部門(mén)信息
getDepts("#deptName_add_select");
//添加模態(tài)框,在模態(tài)框中需要所有部門(mén),所以需要查詢(xún)所有部門(mén)信息
$("#empAddModal").modal({
//模態(tài)框參數(shù),點(diǎn)擊背景不關(guān)閉
backdrop : "static"
});
});
//后面用
//新增模態(tài)框--清除表單數(shù)據(jù),樣式
function reset_form(ele) {
$(ele)[0].reset();
//該元素下所有css清除
$(ele).find("*").removeClass("has-error has-success");
//顯示警告信息部分清空
$(ele).find(".help-block").text("");
}
//新增模態(tài)框--請(qǐng)求所有部門(mén)信息 function getDepts(ele){
//---注意這里要清空---
$(ele).empty();
$.ajax({
url:"${PATH}/depts",
type:"GET",
success:function(result){
//console.log(result);
//動(dòng)態(tài)拼接
}
});
}
package com.ssm.controller;
import com.ssm.bean.Department;
import com.ssm.bean.Msg;
import com.ssm.service.DepartmentService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import java.util.List;
/**
* 部門(mén)信息
*/
@Controller
public class DepartmentController {
@Autowired
private DepartmentService departmentService;
/**
* 獲取所有部門(mén)信息
* @return
*/
@ResponseBody
@RequestMapping("/depts")
public Msg getDepts() {
List<Department> depts = departmentService.getDepts();
return Msg.success().add("depts", depts);
}
}
package com.ssm.service;
import com.ssm.bean.Department;
import com.ssm.dao.DepartmentMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
/**
* 部門(mén)信息
*/
@Service
public class DepartmentService {
@Autowired
DepartmentMapper departmentMapper;
/**
* 查詢(xún)所有部門(mén)
*/
public List<Department> getDepts(){
//方法本身可以添加查詢(xún)條件,如果為null代表查所有
List<Department> list = departmentMapper.selectByExample(null);
return list;
}
}
//新增模態(tài)框--請(qǐng)求所有部門(mén)信息 function getDepts(ele){
//---注意這里要清空---
$(ele).empty();
$.ajax({
url:"${PATH}/depts",
type:"GET",
success:function(result){
//console.log(result);
$.each(result.extend.depts,function(index,item){
//創(chuàng)建出option并添加到select中
var optionEle = $("<option></option>").append(item.deptName).attr("value",item.deptId);
optionEle.appendTo(ele);
});
}
});
}
效果
綁定保存按鈕
//------------------增刪改查都使用REST風(fēng)格------------------- //新增保存信息
$("#emp_save_btn").click(function(){
//1、模態(tài)框中填寫(xiě)的表單數(shù)據(jù)提交給服務(wù)器進(jìn)行保存
//2、發(fā)送ajax請(qǐng)求保存員工
$.ajax({
url:"${PATH}/saveemp",
type:"POST",
data:$("#empAddModal form").serialize(),
//.serialize()方法能將表單中數(shù)據(jù)序列化,直接發(fā)送給controll封裝成Bean
//console.log($("#empAddModal form").serialize());
//empName=Tom&email=Tom%40123.com&gender=M&dId=1
success:function(result){
//1.添加成功,關(guān)閉模態(tài)框
$("#empAddModal").modal("hide");
//2.來(lái)到最后一頁(yè),顯示插入的數(shù)據(jù),可以直接跳到一個(gè)很大的頁(yè)數(shù),因?yàn)? //合理性,所以不會(huì)超出,這里使用全局參數(shù),數(shù)據(jù)總條數(shù)
to_page(totalRecord+1);
}
});
EmployeeController
@ResponseBody @RequestMapping(value = "/saveemp",method = RequestMethod.POST)
public Msg saveEmp(Employee employee, BindingResult result) {
employeeService.saveEmp(employee);
return Msg.success();
}
EmployeeService
/**
* 保存emp員工,insert
* @param employee
*/
public void saveEmp(Employee employee) {
//這個(gè)是有選擇插入,insert()全插入,包括id
employeeMapper.insertSelective(employee);
}
一共有兩種驗(yàn)證方式 1.輸入框焦點(diǎn)單獨(dú)驗(yàn)證 2.提交按鈕總驗(yàn)證,為了不兩種方式的css樣式相互覆蓋,每種方式都驗(yàn)兩遍,格式在前,用戶(hù)名在后
(內(nèi)部Java格式驗(yàn)證)+ ajax用戶(hù)名驗(yàn)證(實(shí)現(xiàn)方法看下一小節(jié))
//1.(內(nèi)部Java格式驗(yàn)證)+ ajax用戶(hù)名驗(yàn)證 //新增保存信息--ajax用戶(hù)名校驗(yàn)
//由于在java內(nèi)又做了一次格式驗(yàn)證,所以這個(gè)方法相當(dāng)于即驗(yàn)證了格式,又驗(yàn)證了重名
$("#empName_add_input").blur(function () {
//發(fā)送ajax請(qǐng)求,驗(yàn)證用戶(hù)名是否可用
var empName = this.value;
$.ajax({
url: "${PATH}/checkname",
data: "empName=" + empName,
type: "POST",
success: function (result) {
console.log(result);
//獲取到返回值,Msg中的狀態(tài)碼
if (result.code == 2333) {
show_validate_msg("#empName_add_input", "success", "用戶(hù)名可用");
//因?yàn)槭褂昧藘煞N方式驗(yàn)證,格式和重名,會(huì)有css樣式?jīng)_突覆蓋,所以再加一次驗(yàn)證
//自定義屬性,或全局變量
//給添加按鈕添加自定義屬性,在提交時(shí)判斷是否通過(guò)兩項(xiàng)驗(yàn)證。
$("#emp_save_btn").attr("ajax-vl", "success");
} else if (result.code == 5555) {
show_validate_msg("#empName_add_input", "error", result.extend.msg);
$("#emp_save_btn").attr("ajax-vl", "error");
}
}
});
});
郵箱格式獨(dú)立校驗(yàn)
//2. 郵箱獨(dú)立驗(yàn)證 //新增保存信息--獨(dú)立郵箱格式驗(yàn)證
$("#email_add_input").blur(function () {
var email = $("#email_add_input").val();
var regEmail = /^([a-z0-9_\.-]+)@([\da-z\.-]+)\.([a-z\.]{2,6})$/;
if (!regEmail.test(email)) {
//alert("郵箱格式不正確");
show_validate_msg("#email_add_input", "error", "郵箱格式不正確");
//return false;
} else {
show_validate_msg("#email_add_input", "success", "");
}
//最后方法通過(guò)
//return true;
})
格式+用戶(hù)名驗(yàn)證+提交保存請(qǐng)求
//3. 格式+用戶(hù)名驗(yàn)證+提交保存請(qǐng)求,一共有兩種驗(yàn)證方式 1.輸入框焦點(diǎn)單獨(dú)驗(yàn)證 2.提交按鈕總驗(yàn)證, //為了不兩種方式的css樣式相互覆蓋,每種方式都驗(yàn)兩遍,格式在前,用戶(hù)名在后
//新增保存信息--請(qǐng)求
$("#emp_save_btn").click(function () {
//點(diǎn)擊就發(fā)送請(qǐng)求,保存使用POST請(qǐng)求
//1.先驗(yàn)證ajax重名校驗(yàn),防止用戶(hù)輸入重復(fù)用戶(hù)名之后,直接輸入正確的郵箱,點(diǎn)擊提交,重名的驗(yàn)證提示會(huì)被覆蓋
//ajax-vl是ajax重名校驗(yàn)之后添加的自定義屬性,用于表示提交按鈕是否可用
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//2.點(diǎn)擊保存按鈕請(qǐng)求之前完整驗(yàn)證一遍輸入格式
//JQuery格式總驗(yàn)證
if (!validate_add_form()) {
return false;
}
//3.重名驗(yàn)證
//ajax重名校驗(yàn)
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//1、模態(tài)框中填寫(xiě)的表單數(shù)據(jù)提交給服務(wù)器進(jìn)行保存
//2、發(fā)送ajax請(qǐng)求保存員工
$.ajax({
url: "${PATH}/saveemp",
type: "POST",
data: $("#empAddModal form").serialize(),
//.serialize()方法能將表單中數(shù)據(jù)序列化,直接發(fā)送給controll封裝成Bean
//console.log($("#empAddModal form").serialize());
//empName=Tom&email=Tom%40123.com&gender=M&dId=1
success: function (result) {
//1.添加成功,關(guān)閉模態(tài)框
$("#empAddModal").modal("hide");
//2.來(lái)到最后一頁(yè),顯示插入的數(shù)據(jù),可以直接跳到一個(gè)很大的頁(yè)數(shù),因?yàn)? //合理性,所以不會(huì)超出,這里使用全局參數(shù),參數(shù)值在上面分頁(yè)時(shí)獲取的,數(shù)據(jù)總條數(shù)+1保證不出現(xiàn)極端情況
to_page(totalRecord + 1);
}
});
});
請(qǐng)求按鈕JQuery格式總校驗(yàn)方法
//新增保存信息--請(qǐng)求按鈕JQuery格式總校驗(yàn)方法 function validate_add_form() {
console.log("validate_add_form()")
//1.拿到校驗(yàn)的數(shù)據(jù),使用正則表達(dá)式
//根據(jù)bootstrap提供的組件
//校驗(yàn)用戶(hù)名
var empName = $("#empName_add_input").val();
var regName = /(^[a-zA-Z0-9_-]{2,8}$)|(^[\u2E80-\u9FFF]{2,5})/;
if (!regName.test(empName)) {
//alert("用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合");
show_validate_msg("#empName_add_input", "error", "用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合");
return false;
} else {
show_validate_msg("#empName_add_input", "success", "");
}
//2、校驗(yàn)郵箱信息
var email = $("#email_add_input").val();
var regEmail = /^([a-z0-9_\.-]+)@([\da-z\.-]+)\.([a-z\.]{2,6})$/;
if (!regEmail.test(email)) {
//alert("郵箱格式不正確");
show_validate_msg("#email_add_input", "error", "郵箱格式不正確");
return false;
} else {
show_validate_msg("#email_add_input", "success", "");
}
//最后方法通過(guò)
return true;
}
添加樣式方法
//新增保存信息--添加css樣式 //show_validate_msg顯示校驗(yàn)狀態(tài),通過(guò)添加樣式,ele表示被選擇元素,status狀態(tài)
//用來(lái)判斷是用什么樣式,綠色、紅色,msg提示信息
function show_validate_msg(ele, status, msg) {
//判斷之前先清空之前樣式
$(ele).parent().removeClass("has-success has-error");
$(ele).next("span").text("");
if ("success" == status) {
$(ele).parent().addClass("has-success");
$(ele).next("span").text(msg)
} else if ("error" == status) {
$(ele).parent().addClass("has-error");
$(ele).next("span").text(msg)
}
}
如果添加相同的用戶(hù)名會(huì)造成混淆,所以在輸入用戶(hù)名之后立即進(jìn)行校驗(yàn)
發(fā)送ajax請(qǐng)求(與上一節(jié)相同)
$("#empName_add_input").blur(function () {
//發(fā)送ajax請(qǐng)求,驗(yàn)證用戶(hù)名是否可用
var empName = this.value;
$.ajax({
url: "${PATH}/checkname",
data: "empName=" + empName,
type: "POST",
success: function (result) {
console.log(result);
//獲取到返回值,Msg中的狀態(tài)碼
if (result.code == 2333) {
show_validate_msg("#empName_add_input", "success", "用戶(hù)名可用");
//因?yàn)槭褂昧藘煞N方式驗(yàn)證,格式和重名,會(huì)有css樣式?jīng)_突覆蓋,所以再加一次驗(yàn)證
//自定義屬性,或全局變量
//給添加按鈕添加自定義屬性,在提交時(shí)判斷是否通過(guò)兩項(xiàng)驗(yàn)證。
$("#emp_save_btn").attr("ajax-vl", "success");
} else if (result.code == 5555) {
show_validate_msg("#empName_add_input", "error", result.extend.msg);
$("#emp_save_btn").attr("ajax-vl", "error");
}
}
});
});
EmployeeController
/**
* 用戶(hù)名查重
* 前端校驗(yàn),在失去焦點(diǎn),保存之前都校驗(yàn)
* @param empName
* @return
*/
@ResponseBody
@RequestMapping("/checkname")
public Msg checkEmpName(@RequestParam("empName")String empName) {
//用戶(hù)名格式校驗(yàn)
String regx = "(^[a-zA-Z0-9_-]{2,8}$)|(^[\\u2E80-\\u9FFF]{2,5})";
if(!empName.matches(regx)){
return Msg.fail().add("msg", "用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合");
}
//返回查詢(xún)統(tǒng)計(jì)結(jié)果,true說(shuō)明沒(méi)有重名
boolean b = employeeService.checkEmpName(empName);
if(b) {
return Msg.success();
}else {
return Msg.fail().add("msg", "用戶(hù)名已存在");
}
}
EmployeeService
/**
* 查詢(xún)用戶(hù)是否存在
* 使用Example復(fù)雜查詢(xún)
*
* @param name
* @return
*/
public boolean checkEmpName(String name) {
//Example用法
EmployeeExample example = new EmployeeExample();
//創(chuàng)建查詢(xún)條件
EmployeeExample.Criteria criteria = example.createCriteria();
//我的理解:這一句相當(dāng)于添加了一個(gè)條件 where empName=name
criteria.andEmpNameEqualTo(name);
//統(tǒng)計(jì)查詢(xún)結(jié)構(gòu)
long count = employeeMapper.countByExample(example);
//返回true(0)說(shuō)明沒(méi)有重復(fù)用戶(hù)名
return count == 0;
}
前面是前端校驗(yàn),現(xiàn)在是后端校驗(yàn),針對(duì)Java
添加JSR303依賴(lài)
<!-- JSR303校驗(yàn) -->
<!-- https://mvnrepository.com/artifact/org.hibernate.validator/hibernate-validator -->
<dependency>
<groupId>org.hibernate.validator</groupId>
<artifactId>hibernate-validator</artifactId>
<version>6.1.0.Final</version>
</dependency>
在JavaBean上添加注解
public class Employee {
private Integer empId;
//JSR303自定義校驗(yàn)規(guī)則
@Pattern(regexp = "(^[a-zA-Z0-9_-]{2,8}$)|(^[\\u2E80-\\u9FFF]{2,5})", message = "用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合")
private String empName;
private String gender;
@Pattern(regexp = "^([a-z0-9_\\.-]+)@([\\da-z\\.-]+)\\.([a-z\\.]{2,6})$",message = "郵箱格式不正確")
private String email;
//...
在Controller方法中使用,在參數(shù)前添加注解,在參數(shù)后面添加結(jié)果參數(shù)
/**
* 新增,保存用戶(hù),并驗(yàn)證
*
* 添加JSR303校驗(yàn)
* @Valid表示校驗(yàn)下一個(gè)對(duì)象
* BindingResult緊跟被校驗(yàn)對(duì)象,接收結(jié)果
*
* @param employee
* @return
*/
@ResponseBody
@RequestMapping(value = "/saveemp",method = RequestMethod.POST)
public Msg saveEmp(@Valid Employee employee, BindingResult result) {
if(result.hasErrors()) {
//格式校驗(yàn)失敗,返回信息
Map<String ,Object> map = new HashMap<>();
List<FieldError> fieldErrors = result.getFieldErrors();
for(FieldError error : fieldErrors) {
System.out.println("錯(cuò)誤的字段名:" + error.getField());
System.out.println("錯(cuò)誤信息:" + error.getDefaultMessage());
//將錯(cuò)誤信息放到map中
map.put(error.getField(), error.getDefaultMessage());
}
return Msg.fail().add("errorFields", map);
}else if(!employeeService.checkEmpName(employee.getEmpName())){
//后端在保存的時(shí)候再次驗(yàn)證是否存在用戶(hù)名---有點(diǎn) 重復(fù)的感覺(jué)???
//因?yàn)槭窃谝黄鸾邮账藻e(cuò)誤信息一定要一樣,empName手動(dòng)寫(xiě)上
return Msg.fail().add("empName", "用戶(hù)名已存在");
}else {
employeeService.saveEmp(employee);
//不用這種:獲取總頁(yè)數(shù),用在新增完之后跳轉(zhuǎn)到最后一頁(yè),不過(guò)這樣就會(huì)多查一次數(shù)據(jù)庫(kù)
//PageInfo<Employee> pageInfo = employeeService.getPage(null);
//return Msg.success().add("pageInfo", pageInfo);
return Msg.success();
}
}
在index.jsp提交按鈕中處理返回結(jié)果
//3. 格式+用戶(hù)名驗(yàn)證+提交保存請(qǐng)求,一共有兩種驗(yàn)證方式 1.輸入框焦點(diǎn)單獨(dú)驗(yàn)證 2.提交按鈕總驗(yàn)證, //為了不兩種方式的css樣式相互覆蓋,每種方式都驗(yàn)兩遍,格式在前,用戶(hù)名在后
//新增保存信息--請(qǐng)求
$("#emp_save_btn").click(function () {
//點(diǎn)擊就發(fā)送請(qǐng)求,保存使用POST請(qǐng)求
//1.先驗(yàn)證ajax重名校驗(yàn),防止用戶(hù)輸入重復(fù)用戶(hù)名之后,直接輸入正確的郵箱,點(diǎn)擊提交,重名的驗(yàn)證提示會(huì)被覆蓋
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//2.點(diǎn)擊保存按鈕請(qǐng)求之前完整驗(yàn)證一遍輸入格式
console.log("JQuery格式總驗(yàn)證")
//方法一:JQuery格式總驗(yàn)證
if (!validate_add_form()) {
return false;
}
//3.重名驗(yàn)證
console.log("ajax重名校驗(yàn)")
//ajax重名校驗(yàn)
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//1、模態(tài)框中填寫(xiě)的表單數(shù)據(jù)提交給服務(wù)器進(jìn)行保存
//2、發(fā)送ajax請(qǐng)求保存員工
$.ajax({
url: "${PATH}/saveemp",
type: "POST",
data: $("#empAddModal form").serialize(),
//.serialize()方法能將表單中數(shù)據(jù)序列化,直接發(fā)送給controll封裝成Bean
//console.log($("#empAddModal form").serialize());
//empName=Tom&email=Tom%40123.com&gender=M&dId=1
success: function (result) {
//清除模態(tài)框和提示信息
$("#empAddModal form").find("*").removeClass("has-error has-success");
$("#empAddModal form").find(".help-block").text("");
//在這里判斷后端JSR303校驗(yàn)結(jié)果,最后一次!?。。。。。。?!真的
//前后端驗(yàn)證可以獨(dú)立運(yùn)行,注釋前端后端也能實(shí)現(xiàn)一樣效果
if(result.code == 2333){
//alert(result.msg);
//1.添加成功,關(guān)閉模態(tài)框
$("#empAddModal").modal("hide");
//2.來(lái)到最后一頁(yè),顯示插入的數(shù)據(jù),可以直接跳到一個(gè)很大的頁(yè)數(shù),因?yàn)? //合理性,所以不會(huì)超出,這里使用全局參數(shù),數(shù)據(jù)總條數(shù)+1保證不出現(xiàn)極端情況
to_page(totalRecord + 1);
}else{
//失敗,顯示信息,有幾個(gè)就顯示幾個(gè)
//undefined 就是沒(méi)找到這個(gè)錯(cuò)誤,說(shuō)明正確,可用alert(result.extend.errorFields.empName)驗(yàn)證
//用戶(hù)名格式
//alert(result.extend.errorFields.empName)
//用戶(hù)名格式和查重,因?yàn)椴橹氐膶傩愿袷胶透袷津?yàn)證不同,所以不能分開(kāi)
//result.extend.errorFields.empName 格式驗(yàn)證
//result.extend.empName 查重驗(yàn)證
if(undefined != result.extend.errorFields ){
//格式錯(cuò)誤
if(undefined != result.extend.errorFields.empName){
show_validate_msg("#empName_add_input","error",result.extend.errorFields.empName);
}
}else{
if(undefined != result.extend.empName){
//查重錯(cuò)誤
show_validate_msg("#empName_add_input","error",result.extend.empName);
}
}
//郵箱格式判斷
if(undefined != result.extend.errorFields){
if(undefined != result.extend.errorFields.email){
show_validate_msg("#email_add_input","error",result.extend.errorFields.email);
}
}
}
}
});
});
模態(tài)框
<!-- 為新增按鈕增加模態(tài)框 ,利用按鈕綁定單擊事件-->
<!-- Modal -->
<div class="modal fade" id="empAddModal" tabindex="-1" role="dialog"
aria-labelledby="myModalLabel">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal"
aria-label="Close">
<span aria-hidden="true">×</span>
</button>
<h4 class="modal-title" id="myModalLabel">員工添加</h4>
</div>
<div class="modal-body">
<!-- 添加表單 -->
<form class="form-horizontal" id="model-form">
<!-- 姓名 -->
<div class="form-group">
<label for="empName_add_input" class="col-sm-2 control-label">EmpName</label>
<div class="col-sm-10">
<input type="text" class="form-control" name="empName" id="empName_add_input"
placeholder="empName">
<!-- 用來(lái)顯示錯(cuò)誤提示 -->
<span class="help-block"></span>
</div>
</div>
<!-- 郵箱 -->
<div class="form-group">
<label for="email_add_input" class="col-sm-2 control-label">Email</label>
<div class="col-sm-10">
<input type="email" class="form-control" name="email" id="email_add_input"
placeholder="empName@123.com">
<!-- 用來(lái)顯示錯(cuò)誤提示 -->
<span class="help-block"></span>
</div>
</div>
<!-- 性別 -->
<div class="form-group">
<label class="col-sm-2 control-label">Gender</label>
<div class="col-sm-10">
<!-- 單選 -->
<label for="gender1_add_input"> <input type="radio"
name="gender" id="gender1_add_input"
name="gender" value="M" checked>
男
</label>
<label for="gender2_add_input"> <input type="radio"
name="gender" id="gender2_add_input"
name="gender" value="F">
女
</label>
</div>
</div>
<!-- 部門(mén)下拉框 -->
<div class="form-group">
<label class="col-sm-2 control-label">DeptName</label>
<div class="col-sm-10">
<!-- 部門(mén)下拉列表使用ajax查詢(xún)出來(lái)的動(dòng)態(tài)拼接,值為部門(mén)id -->
<select class="form-control" name="dId" id="deptName_add_select"></select>
</div>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">關(guān)閉</button>
<button type="button" class="btn btn-primary" id="emp_save_btn">保存</button>
</div>
</div>
</div>
</div>
請(qǐng)求和方法
<script type="text/javascript">
//------------------增刪改查都使用REST風(fēng)格-------------------
//1.(內(nèi)部Java格式驗(yàn)證)+ ajax用戶(hù)名驗(yàn)證
//新增保存信息--ajax用戶(hù)名校驗(yàn)
//由于在java內(nèi)又做了一次格式驗(yàn)證,所以這個(gè)方法相當(dāng)于即驗(yàn)證了格式,又驗(yàn)證了重名
$("#empName_add_input").blur(function () {
//發(fā)送ajax請(qǐng)求,驗(yàn)證用戶(hù)名是否可用
var empName = this.value;
$.ajax({
url: "${PATH}/checkname",
data: "empName=" + empName,
type: "POST",
success: function (result) {
console.log(result);
//獲取到返回值,Msg中的狀態(tài)碼
if (result.code == 2333) {
show_validate_msg("#empName_add_input", "success", "用戶(hù)名可用");
//因?yàn)槭褂昧藘煞N方式驗(yàn)證,格式和重名,會(huì)有css樣式?jīng)_突覆蓋,所以再加一次驗(yàn)證
//自定義屬性,或全局變量
//給添加按鈕添加自定義屬性,在提交時(shí)判斷是否通過(guò)兩項(xiàng)驗(yàn)證。
$("#emp_save_btn").attr("ajax-vl", "success");
} else if (result.code == 5555) {
show_validate_msg("#empName_add_input", "error", result.extend.msg);
$("#emp_save_btn").attr("ajax-vl", "error");
}
}
});
});
//2. 郵箱獨(dú)立驗(yàn)證
//新增保存信息--獨(dú)立郵箱格式驗(yàn)證
$("#email_add_input").blur(function () {
var email = $("#email_add_input").val();
var regEmail = /^([a-z0-9_\.-]+)@([\da-z\.-]+)\.([a-z\.]{2,6})$/;
if (!regEmail.test(email)) {
//alert("郵箱格式不正確");
show_validate_msg("#email_add_input", "error", "郵箱格式不正確");
//return false;
} else {
show_validate_msg("#email_add_input", "success", "");
}
//最后方法通過(guò)
//return true;
})
//3. 格式+用戶(hù)名驗(yàn)證+提交保存請(qǐng)求,一共有兩種驗(yàn)證方式 1.輸入框焦點(diǎn)單獨(dú)驗(yàn)證 2.提交按鈕總驗(yàn)證,
//為了不兩種方式的css樣式相互覆蓋,每種方式都驗(yàn)兩遍,格式在前,用戶(hù)名在后
//新增保存信息--請(qǐng)求
$("#emp_save_btn").click(function () {
//點(diǎn)擊就發(fā)送請(qǐng)求,保存使用POST請(qǐng)求
//1.先驗(yàn)證ajax重名校驗(yàn),防止用戶(hù)輸入重復(fù)用戶(hù)名之后,直接輸入正確的郵箱,點(diǎn)擊提交,重名的驗(yàn)證提示會(huì)被覆蓋
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//2.點(diǎn)擊保存按鈕請(qǐng)求之前完整驗(yàn)證一遍輸入格式
console.log("JQuery格式總驗(yàn)證")
//方法一:JQuery格式總驗(yàn)證
if (!validate_add_form()) {
return false;
}
//3.重名驗(yàn)證
console.log("ajax重名校驗(yàn)")
//ajax重名校驗(yàn)
if ($(this).attr("ajax-vl") == "error") {
return false;
}
//1、模態(tài)框中填寫(xiě)的表單數(shù)據(jù)提交給服務(wù)器進(jìn)行保存
//2、發(fā)送ajax請(qǐng)求保存員工
$.ajax({
url: "${PATH}/saveemp",
type: "POST",
data: $("#empAddModal form").serialize(),
//.serialize()方法能將表單中數(shù)據(jù)序列化,直接發(fā)送給controll封裝成Bean
//console.log($("#empAddModal form").serialize());
//empName=Tom&email=Tom%40123.com&gender=M&dId=1
success: function (result) {
//清除模態(tài)框和提示信息
$("#empAddModal form").find("*").removeClass("has-error has-success");
$("#empAddModal form").find(".help-block").text("");
//在這里判斷后端JSR303校驗(yàn)結(jié)果,最后一次!?。。。。。。?!真的
//前后端驗(yàn)證可以獨(dú)立運(yùn)行,注釋前端后端也能實(shí)現(xiàn)一樣效果
if(result.code == 2333){
//alert(result.msg);
//1.添加成功,關(guān)閉模態(tài)框
$("#empAddModal").modal("hide");
//2.來(lái)到最后一頁(yè),顯示插入的數(shù)據(jù),可以直接跳到一個(gè)很大的頁(yè)數(shù),因?yàn)? //合理性,所以不會(huì)超出,這里使用全局參數(shù),數(shù)據(jù)總條數(shù)+1保證不出現(xiàn)極端情況
to_page(totalRecord + 1);
}else{
//失敗,顯示信息,有幾個(gè)就顯示幾個(gè)
//undefined 就是沒(méi)找到這個(gè)錯(cuò)誤,說(shuō)明正確,可用alert(result.extend.errorFields.empName)驗(yàn)證
//用戶(hù)名格式
//alert(result.extend.errorFields.empName)
//用戶(hù)名格式和查重,因?yàn)椴橹氐膶傩愿袷胶透袷津?yàn)證不同,所以不能分開(kāi)
//result.extend.errorFields.empName 格式驗(yàn)證
//result.extend.empName 查重驗(yàn)證
if(undefined != result.extend.errorFields ){
//格式錯(cuò)誤
if(undefined != result.extend.errorFields.empName){
show_validate_msg("#empName_add_input","error",result.extend.errorFields.empName);
}
}else{
if(undefined != result.extend.empName){
//查重錯(cuò)誤
show_validate_msg("#empName_add_input","error",result.extend.empName);
}
}
//郵箱格式判斷
if(undefined != result.extend.errorFields){
if(undefined != result.extend.errorFields.email){
show_validate_msg("#email_add_input","error",result.extend.errorFields.email);
}
}
}
}
});
});
//新增保存信息--請(qǐng)求按鈕JQuery格式總校驗(yàn)方法
function validate_add_form() {
console.log("validate_add_form()")
//1.拿到校驗(yàn)的數(shù)據(jù),使用正則表達(dá)式
//根據(jù)bootstrap提供的組件
//校驗(yàn)用戶(hù)名
var empName = $("#empName_add_input").val();
var regName = /(^[a-zA-Z0-9_-]{2,8}$)|(^[\u2E80-\u9FFF]{2,5})/;
if (!regName.test(empName)) {
//alert("用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合");
show_validate_msg("#empName_add_input", "error", "用戶(hù)名可以是2-5位中文或者2-8位英文和數(shù)字的組合");
return false;
} else {
show_validate_msg("#empName_add_input", "success", "");
}
//2、校驗(yàn)郵箱信息
var email = $("#email_add_input").val();
var regEmail = /^([a-z0-9_\.-]+)@([\da-z\.-]+)\.([a-z\.]{2,6})$/;
if (!regEmail.test(email)) {
//alert("郵箱格式不正確");
show_validate_msg("#email_add_input", "error", "郵箱格式不正確");
return false;
} else {
show_validate_msg("#email_add_input", "success", "");
}
//最后方法通過(guò)
return true;
}
//新增保存信息--添加css樣式
//show_validate_msg顯示校驗(yàn)狀態(tài),通過(guò)添加樣式,ele表示被選擇元素,status狀態(tài)
//用來(lái)判斷是用什么樣式,綠色、紅色,msg提示信息
function show_validate_msg(ele, status, msg) {
//判斷之前先清空之前樣式
$(ele).parent().removeClass("has-success has-error");
$(ele).next("span").text("");
if ("success" == status) {
$(ele).parent().addClass("has-success");
$(ele).next("span").text(msg)
} else if ("error" == status) {
$(ele).parent().addClass("has-error");
$(ele).next("span").text(msg)
}
}
</script>
__EOF__
本文作者: 蔚然丶丶
本文鏈接: https://www.cnblogs.com/wei-ran/p/16131419.html
頁(yè)篡改是最為常見(jiàn)的一種黑客攻擊形式。網(wǎng)頁(yè)篡改是一種通過(guò)網(wǎng)頁(yè)應(yīng)用中的漏洞獲取權(quán)限,非法篡改Web應(yīng)用中的內(nèi)容、植入暗鏈、傳播惡意信息,危害社會(huì)安全并牟取暴利的網(wǎng)絡(luò)攻擊行為。
近些年來(lái),網(wǎng)頁(yè)篡改攻擊事件層出不窮,且具有以下四個(gè)特點(diǎn):篡改網(wǎng)站頁(yè)面?zhèn)鞑ニ俣瓤臁㈤喿x人群多;篡改頁(yè)面容易,預(yù)先檢查、實(shí)時(shí)防范、事后消除影響難;網(wǎng)絡(luò)環(huán)境復(fù)雜,追查責(zé)任難;攻擊工具簡(jiǎn)單,并且向智能化趨勢(shì)發(fā)展。
零時(shí)代:人工對(duì)比檢測(cè)
人工對(duì)比檢測(cè),其實(shí)就是一種專(zhuān)門(mén)指派網(wǎng)絡(luò)管理人員,人工監(jiān)控需要保護(hù)的網(wǎng)站,一旦發(fā)現(xiàn)被篡改,然后以人力對(duì)其修改還原的手段。嚴(yán)格說(shuō)來(lái),人工對(duì)比檢測(cè)不能算是一種網(wǎng)頁(yè)防篡改系統(tǒng)采用的技術(shù),而只能算是一種原始的應(yīng)對(duì)網(wǎng)頁(yè)被篡改的手段。但是其在網(wǎng)頁(yè)防篡改的技術(shù)發(fā)展歷程中存在一段相當(dāng)久的時(shí)間。
這種手段非常原始且效果不佳,且不說(shuō)人力成本較高,其最致命的缺陷在于人力監(jiān)控不能達(dá)到即時(shí)性,也就是不能在第一時(shí)間發(fā)現(xiàn)網(wǎng)頁(yè)被篡改,也不能在第一時(shí)間做出還原,當(dāng)管理人員發(fā)現(xiàn)網(wǎng)頁(yè)被篡改再做還原時(shí),被篡改的網(wǎng)頁(yè)已在互聯(lián)網(wǎng)存在了一段時(shí)間,可能已經(jīng)被一定數(shù)量的網(wǎng)民瀏覽,造成一定的負(fù)面影響。
第一代:時(shí)間輪詢(xún)技術(shù)
時(shí)間輪詢(xún)技術(shù),也稱(chēng)“外掛輪詢(xún)技術(shù)”。從這一代開(kāi)始,網(wǎng)頁(yè)防篡技術(shù)已經(jīng)擺脫了以人力檢測(cè)恢復(fù)為主體的原始手段,而是作為一種自動(dòng)化的技術(shù)形式出現(xiàn)。時(shí)間輪詢(xún)技術(shù)是利用一個(gè)網(wǎng)頁(yè)檢測(cè)程序,以輪詢(xún)方式讀出要監(jiān)控的網(wǎng)頁(yè),與真實(shí)網(wǎng)頁(yè)相比較后,進(jìn)行判斷網(wǎng)頁(yè)內(nèi)容的完整性,對(duì)于被篡改的網(wǎng)頁(yè)進(jìn)行報(bào)警和恢復(fù)。
采用時(shí)間輪詢(xún)式的網(wǎng)頁(yè)防篡改系統(tǒng),對(duì)每個(gè)網(wǎng)頁(yè)來(lái)說(shuō),輪詢(xún)掃描存在著時(shí)間間隔,一般為數(shù)十分鐘。所以,在這數(shù)十分鐘的間隔中,黑客可以攻擊系統(tǒng)并使訪問(wèn)者訪問(wèn)到被篡改的網(wǎng)頁(yè)。
此類(lèi)應(yīng)用在過(guò)去網(wǎng)頁(yè)訪問(wèn)量較少,具體網(wǎng)頁(yè)應(yīng)用較少的情況下適用,目前網(wǎng)站頁(yè)面通常少則上百頁(yè),檢測(cè)輪詢(xún)時(shí)間更長(zhǎng),且占用系統(tǒng)資源較大,該技術(shù)逐漸被淘汰。
第二代:事件觸發(fā)+核心內(nèi)嵌技術(shù)
將事件觸發(fā)技術(shù)與核心內(nèi)嵌技術(shù)兩種技術(shù)放在同一代來(lái)說(shuō),是因?yàn)檫@兩種網(wǎng)頁(yè)防篡改技術(shù)出現(xiàn)的時(shí)間差距不大,而且兩種技術(shù)常常被結(jié)合使用。
所謂核心內(nèi)嵌技術(shù),即密碼水印技術(shù),最初先將網(wǎng)頁(yè)內(nèi)容采取非對(duì)稱(chēng)加密存放,在外來(lái)訪問(wèn)請(qǐng)求時(shí)將經(jīng)過(guò)加密驗(yàn)證過(guò)的,進(jìn)行解密對(duì)外發(fā)布,若未經(jīng)過(guò)驗(yàn)證,則拒絕對(duì)外發(fā)布,調(diào)用備份網(wǎng)站文件進(jìn)行驗(yàn)證解密后對(duì)外發(fā)布。此種技術(shù)通常要結(jié)合事件觸發(fā)機(jī)制對(duì)文件的部分屬性進(jìn)行對(duì)比,如大小、頁(yè)面生成時(shí)間等做判斷,無(wú)法更準(zhǔn)確的進(jìn)行其它屬性的判斷。其最大的特點(diǎn)就是相對(duì)外掛輪詢(xún)技術(shù)安全性大大提高,但其美中不足是加密計(jì)算會(huì)占用大量服務(wù)器資源,系統(tǒng)反映較慢。
核心內(nèi)嵌技術(shù)避免了時(shí)間輪詢(xún)技術(shù)的輪詢(xún)間隔這個(gè)缺點(diǎn)。但是由于這種技術(shù)是對(duì)每個(gè)流出網(wǎng)頁(yè)都進(jìn)行完整檢查,占用巨大的系統(tǒng)資源,給服務(wù)器造成較大負(fù)載。而且,因?yàn)閷?duì)網(wǎng)頁(yè)正常發(fā)布流程作了更改,整個(gè)網(wǎng)站需要重新架構(gòu),增加新的發(fā)布服務(wù)器替代原先的服務(wù)器。
隨著IT技術(shù)發(fā)展以及網(wǎng)上各類(lèi)應(yīng)用的增多,對(duì)服務(wù)器的負(fù)載資源簡(jiǎn)直可以用“苛刻”來(lái)形容,任何占用服務(wù)器資源的部分都要淘汰,來(lái)確保網(wǎng)站的高效率訪問(wèn)和網(wǎng)頁(yè)防篡改技術(shù)追蹤率,如此一來(lái),內(nèi)嵌技術(shù)最終也被淘汰。
第三代:過(guò)濾驅(qū)動(dòng)+事件觸發(fā)技術(shù)
技術(shù)發(fā)展到二十一世紀(jì)初,第三代文件網(wǎng)頁(yè)防篡技術(shù):過(guò)濾驅(qū)動(dòng)+事件觸發(fā)技術(shù)應(yīng)運(yùn)而生。
文件過(guò)濾驅(qū)動(dòng)技術(shù)的最初應(yīng)用于保密系統(tǒng),作為文件保護(hù)技術(shù)和各類(lèi)審計(jì)技術(shù),甚至被應(yīng)用于“流氓軟件”。在網(wǎng)頁(yè)防篡改技術(shù)革新當(dāng)中,該技術(shù)找到了其發(fā)展的空間。與事件觸發(fā)技術(shù)結(jié)合,形成了第三代網(wǎng)頁(yè)防篡改保護(hù)技術(shù)。
其原理是將篡改監(jiān)測(cè)的核心程序,利用微軟文件底層驅(qū)動(dòng)技術(shù)應(yīng)用到Web服務(wù)器中,通過(guò)事件觸發(fā)方式,對(duì)文件夾的所有文件內(nèi)容,對(duì)照其底層文件屬性,經(jīng)過(guò)內(nèi)置散列快速算法,實(shí)時(shí)進(jìn)行監(jiān)測(cè)。若發(fā)現(xiàn)屬性變更,則通過(guò)非協(xié)議方式,將純文件安全拷貝,備份路徑文件夾內(nèi)容拷貝到監(jiān)測(cè)文件夾相應(yīng)文件位置,通過(guò)底層文件驅(qū)動(dòng)技術(shù),整個(gè)文件復(fù)制過(guò)程毫秒級(jí),使得公眾無(wú)法看到被篡改頁(yè)面,其運(yùn)行性能和檢測(cè)實(shí)時(shí)性都達(dá)到較高水準(zhǔn)。該頁(yè)面防篡改模塊采用Web服務(wù)器底層文件過(guò)濾驅(qū)動(dòng)級(jí)保護(hù)技術(shù),與操作系統(tǒng)緊密結(jié)合,所監(jiān)測(cè)的文件類(lèi)型不限,可以是一個(gè)html文件,也可以是一段動(dòng)態(tài)代碼,執(zhí)行準(zhǔn)確率較高。
這樣就不僅完全杜絕了輪詢(xún)掃描式頁(yè)面,防篡改軟件的掃描間隔中被篡改內(nèi)容被訪問(wèn)的可能,其所消耗的內(nèi)存和CPU占用率也遠(yuǎn)遠(yuǎn)低于文件輪詢(xún)掃描式或核心內(nèi)嵌式的同類(lèi)軟件??梢哉f(shuō)是一種簡(jiǎn)單、高效、安全性又極高的防篡改技術(shù)。
第四代:“五重防護(hù)”技術(shù)
目前,國(guó)內(nèi)專(zhuān)注于保密與非密領(lǐng)域的分級(jí)保護(hù)、等級(jí)保護(hù)、業(yè)務(wù)連續(xù)性安全和大數(shù)據(jù)安全產(chǎn)品解決方案與相關(guān)技術(shù)研究開(kāi)發(fā)的領(lǐng)軍企業(yè)——國(guó)聯(lián)易安更是基于“高效同步”、“安全傳輸”兩項(xiàng)技術(shù),研發(fā)出了具備獨(dú)特的“五重防護(hù)”新特性,支持網(wǎng)頁(yè)的全自動(dòng)發(fā)布、網(wǎng)頁(yè)監(jiān)控、報(bào)警和自動(dòng)恢復(fù),提供強(qiáng)大的網(wǎng)頁(yè)安全管理維護(hù)功能的網(wǎng)頁(yè)防篡改保護(hù)系統(tǒng)。
一重防護(hù):實(shí)時(shí)阻斷。系統(tǒng)能夠阻斷對(duì)受保護(hù)網(wǎng)頁(yè)的非法操作,此項(xiàng)技術(shù)有效地甄別合法進(jìn)程和非法進(jìn)程,阻斷非法進(jìn)程對(duì)網(wǎng)頁(yè)的篡改,將非法進(jìn)程直接阻斷。
二重防護(hù):事件觸發(fā)。系統(tǒng)具備觸發(fā)式檢驗(yàn)引擎,針對(duì)受保護(hù)的文件增刪改操作,一觸即發(fā),校驗(yàn)修改的合法性,瞬間清除被非法篡改的網(wǎng)頁(yè),實(shí)時(shí)恢復(fù)合法網(wǎng)頁(yè)。
三重防護(hù):核心內(nèi)嵌。系統(tǒng)內(nèi)嵌式篡改檢測(cè)引擎運(yùn)行于Web服務(wù)器內(nèi)部,與Web服務(wù)器無(wú)縫結(jié)合。系統(tǒng)檢測(cè)每一個(gè)Web請(qǐng)求訪問(wèn)頁(yè)面,進(jìn)行水印校驗(yàn),確保發(fā)送網(wǎng)頁(yè)的正確性。
四重防護(hù):主動(dòng)阻斷。當(dāng)網(wǎng)站受到持續(xù)性攻擊時(shí),系統(tǒng)會(huì)自動(dòng)啟動(dòng)積極防御機(jī)制,從根本上阻斷來(lái)自外部的攻擊。
五重防護(hù):木馬檢測(cè)與查殺。系統(tǒng)提供對(duì)被保護(hù)網(wǎng)頁(yè)是否已經(jīng)中木馬的檢測(cè)能力,如果已經(jīng)中木馬可以查殺清除。對(duì)未中木馬的網(wǎng)頁(yè),能提供防止掛木馬的防護(hù)能力。
結(jié)語(yǔ)
網(wǎng)頁(yè)防篡改主要有兩大功能:一是對(duì)攻擊事件進(jìn)行監(jiān)測(cè)與防護(hù),二是網(wǎng)頁(yè)被篡改后實(shí)現(xiàn)快速恢復(fù)。
網(wǎng)頁(yè)相當(dāng)于是一個(gè)組織機(jī)構(gòu)的臉面,如果發(fā)生了黑客惡意篡改網(wǎng)頁(yè),造成惡性事件,將對(duì)組織機(jī)構(gòu)形象造成嚴(yán)重負(fù)面影響。因此,無(wú)論在日常的網(wǎng)絡(luò)安全加固,還是在等保評(píng)測(cè)過(guò)程中,網(wǎng)頁(yè)防篡改防護(hù)均被提到重要高度,成為一個(gè)政府、企事業(yè)單位必須采購(gòu)的網(wǎng)絡(luò)安全產(chǎn)品。
值得一提的是,雖然Web防火墻WAF也能夠在日常的安全運(yùn)營(yíng)中發(fā)揮作用,但WAF不能替代網(wǎng)頁(yè)防篡改產(chǎn)品。因?yàn)橛泻诳陀刑嗟霓k法可以繞過(guò)WAF,造成網(wǎng)站被攻擊。惟有網(wǎng)頁(yè)防篡改產(chǎn)品才能真正防止網(wǎng)頁(yè)篡改惡性事件發(fā)生,或者在事后對(duì)網(wǎng)頁(yè)快速恢復(fù)。
關(guān)于國(guó)聯(lián)易安
北京國(guó)聯(lián)易安信息技術(shù)有限公司(原北京智恒聯(lián)盟科技有限公司)簡(jiǎn)稱(chēng)“國(guó)聯(lián)易安”,成立于2006年,擁有“國(guó)聯(lián)易安”和“智恒聯(lián)盟”兩個(gè)品牌,是國(guó)內(nèi)專(zhuān)注于保密與非密領(lǐng)域的分級(jí)保護(hù)、等級(jí)保護(hù)、業(yè)務(wù)連續(xù)性安全和大數(shù)據(jù)安全產(chǎn)品解決方案與相關(guān)技術(shù)研究開(kāi)發(fā)的領(lǐng)軍企業(yè)。公司多項(xiàng)安全技術(shù)補(bǔ)了國(guó)內(nèi)技術(shù)空白,并且在政府、金融、保密、電信運(yùn)營(yíng)商、軍隊(duì)軍工、大中型企業(yè)、能源、教育、醫(yī)療電商等領(lǐng)域得到廣泛應(yīng)用。
國(guó)聯(lián)易安除研發(fā)生產(chǎn)專(zhuān)業(yè)安全產(chǎn)品外,還為客戶(hù)提供全面的檢測(cè)與防護(hù)方案專(zhuān)家咨詢(xún)、源代碼安全評(píng)估、安全運(yùn)維值守、智能終端安全評(píng)估、安全滲透測(cè)試、專(zhuān)業(yè)安全培訓(xùn)等專(zhuān)業(yè)安全服務(wù)。
*請(qǐng)認(rèn)真填寫(xiě)需求信息,我們會(huì)在24小時(shí)內(nèi)與您取得聯(lián)系。