struts 管理员功能模块

21.11  管理员功能模块

21.11.1  模块功能介绍

管理员功能模块主要包括以下功能。

管理员登录:用于登录系统。

添加管理员信息:用于添加管理员。

查看管理员列表:用于查询并显示系统中的全部管理员及其权限信息。

管理员权限设置:用于设置或修改管理员权限。

管理员删除:用于删除系统中的管理员信息及权限信息。

密码设置:用于管理员登录后修改自己的密码。

主要技术:继承了DispatchAction类,对管理员信息实现多业务操作。

21.11.2  创建管理员的Action实现类

Struts的核心在于它的Action,一般在 Action类中实现对页面的逻辑跳转工作。管理员功能模块的Action实现类继承了DispatchAction类(Action类的子类),实现多 业务的操作。在该类中首先需要在属性中实例化管理员模块的ManagerDao类(该类用于实现与数据库的交互)。管理员模块ManagerAction 实现类的关键代码如下。

例程21-16:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

package com.action;

import javax.servlet.http.*;

import org.apache.struts.action.*;

import com.actionForm.ManagerForm;

import org.apache.struts.actions.DispatchAction;

import com.dao.ManagerDao;

import com.ibatis.common.util.PaginatedList;

import java.util.List;

public class ManagerAction extends DispatchAction {

    private ManagerDao managerDao = new ManagerDao();

    ……  //此处省略了该类中的其他方法,这些方法将在后面的具体过程中给出

}

21.11.3  系统登录设计

系统登录模块是图书管理系统中最先使用的功能,是进 入系统的入口。在系统登录页面中,管理员可以通过输入正确的管理员账号和密码进入到系统,当用户没有输入管理员账号或密码时,系统会通过 JavaScript进行判断,并给予提示信息。系统登录模块的运行结果如图21.8所示。

图21.8  系统登录模块的运行结果

1.设计系统登录页面

系统登录页面主要用于收集管理员的输入信息及通过自定义的JavaScript函数验证输入信息是否为空,该页面涉及到的表单元素如表21.13所示。

表21.13                                           系统登录页面所涉及的表单元素

名    称

元 素 类 型

重 要 属 性

含    义

form

form

method="post"action="managerAction.do?method=checkManagerAction"onSubmit="returncheckEmpty(form)"

管理员登录表单

account

text

管理员名称

password

password

管理员密码

Submit2

submit

value=" 登录 "

【登录】按钮

Submit

reset

value=" 重置 "

【重置】按钮

编写自定义的JavaScript函数,用于判断管理员名称和密码是否为空,代码如下。

例程21-17:光盘/mr/21/wyBooks/src/web/js/validate.JS

function checkEmpty(form){

for(i=0;i<form.length;i++){

if(form.elements[i].value==""){

alert("表单信息不能为空");

return false;

}

}

}

2.管理员登录的Action实现类

在管理员登录页面的管理员名称和管理员密码文本框中 输入正确的管理员名称和密码后,单击“确定”按钮,网页会访问一个URL,这个URL是“manager Action.do? method= checkManagerAction”。从该URL地址中可以知道系统登录模块涉及到的method的参数值为 “checkManagerAction”,也就是当method=checkManagerAction时,会调用ManagerAction类验证管 理员身份的方法checkManagerAction(),该类继承了DispatchAction(extends DispatchAction),实现Struts中的多业务操作。验证管理员身份的方法checkManagerAction()的具体代码如下。

例程21-18:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

    public ActionForward checkManagerAction(ActionMapping mapping,

                                            ActionForm form,

                                            HttpServletRequest request,

                                            HttpServletResponse response) {

        ManagerForm managerForm = (ManagerForm) form;

        managerDao.getSqlMapClient();     //取得数据库的连接

        managerForm.setAccount(managerForm.getAccount());

        String password = managerForm.getPassword();

        ManagerForm managerform = managerDao.selectManager(managerForm);

        if (managerform == null || managerform.equals("")) {

            request.setAttribute("message", "您输入的管理员不存在!!!");

        } else if (!password.equals(managerform.getPassword())) {

            request.setAttribute("message", "您输入的密码不正确!!!");

        } else {

            request.setAttribute("account", managerform.getAccount());

            request.setAttribute("message", "您成功登录!!!");

            request.setAttribute("managerLevef", managerform.getManagerLevel());

        }

        return mapping.findForward("checkManager");

    }

3.struts-config.xml文件配置

在struts-config.xml文件中配置系统登录模块所涉及的<form-bean>元素,该元素用于指定管理员登录模块所使用的ActionForm。关键代码如下。

例程21-19:光盘/mr/21/wyBooks/web/WEB-INF/struts-config.xml

<form-bean name="managerForm" type="com.actionForm.ManagerForm"/>

在struts-config.xml文件中配置系统登录模块所涉及的<action>元素,该元素用于完成对页面的逻辑跳转工作。关键代码如下。

<action  name="managerForm" parameter="method" path="/managerAction" scope="request" type="com.action. ManagerAction" validate="true">

      <forward name="checkManager" path="/manager/resultManager.jsp"/>

</action>

在上面的代码中,parameter的属性设置为“method”后,当用户请求访问ManagerAction (继承了DispatchAction)时,应该提供method请求参数,例如:

http://localhost:8080/wyBooks/managerAction.do?method=checkManagerAction

以上method请求参数值为“checkManagerAction”,它指定了需要调用的业务方法,因此ManagerAction将调用相应的checkManagerAction()方法。

4.防止非法用户登录系统

从网站安全的角度考虑,仅仅上面介绍的系统登录页面 并不能有效的保证系统的安全,一旦系统主界面的地址被他人获得,就可以通过在地址栏中输入系统的主界面地址而直接进入到系统中。由于系统工具栏页面 topTwo.jsp几乎包含于整个系统的每个页面,所以笔者将验证用户是否登录的代码放置在该页中。验证用户是否登录的关键代码如下。

例程21-20:光盘/mr/21/wyBooks/web/topOne.jsp

if(session.getAttribute("account")==null||session.getAttribute("managerLevef")==null){

%>

<script language='javascript'>alert('您已经与服务器断开');window.location.href='index.jsp';</script>

<%}else{

//省略其他业务代码

<%}%>

在页面中包含系统工具栏页面topTwo.jsp的代码如下。

<jsp:include page="topTwo.jsp" flush="true"/>

这样,当系统调用每个页面时,都会判断session变量中manager是否存在,如果不存在,弹出脚本信息,单击【确定】按钮后将页面重定向到系统登录页面。

21.11.4  PaginatedList类实现分页显示管理员列表

主要技术:通过IBatis内置类PaginatedList,实现分页操作。

管理员登录后,选择“系统设置”/“管理员设置”菜 单项,进入到查看管理员列表页面,在该页面中,将列出系统中全部管理员及其权限信息,同时提供添加管理员信息、删除管理员信息,修改管理员权限的超链接以 及分页显示数据的功能。查看管理员列表页面的运行结果如图21.9所示。

图21.9  查看管理员列表页面运行结果

1.查看管理员列表第一页的操作

在实现系统导航菜单时,引用了JavaScript文件menu.JS,在该文件中是实现半透明背景菜单的全部JavaScript代码。打开该JS文件,可以找到如下所示的“管理员设置”菜单项的超链接代码。

<a href=managerAction.do?method=selectManagerAction>管理员设置</a>

从上面的URL地址中可以知道,查看管理员列表模块 涉及到的method的参数值为“selectManagerAction”,当method=selectManagerAction时,会调用 ManagerAction类中的selectManagerAction()方法。查看管理员列表selectManagerAction()方法的关 键代码如下。

例程21-21:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

    public ActionForward selectManagerAction(ActionMapping mapping,

                                              ActionForm form,

                                              HttpServletRequest request,

                                              HttpServletResponse response) {

        managerDao.getSqlMapClient();

        HttpSession session = request.getSession();

        PaginatedList list = managerDao.selectManagerList();

        /*调用ManagerDao类中的selectManagerList()方法,返回类型为PaginatedList*/

        session.setAttribute("list", list);

        /*将PaginatedList类的对象list的值保存到服务器端中的session*/

        request.setAttribute("list", (List) list);

        request.setAttribute("allList", managerDao.selectManager());

        /*调用ManagerDao类中的selectManager(),实现的是全部管理员的操作*/

        return mapping.findForward("selectManagerList");

    }

selectManagerAction()方法实现的是对管理员列表中第一页的操作。

2.查看管理员列表下一页的操作

当管理员在图21.9所示的页面中单击“下一页”的超链接时,实现查询管理员列表中的下一页记录。单击“下一页”超链接的代码如下。

<a href="managerAction.do?method=selectNextManagerAction&pageNumber=& lt;%=pageNumber+1%>&pageMax=<%=pageMax%>">下一页</a>

在上面的URL地址中,参数 pageNumber为当前的页数,参数pageMax为当前最大的页数。查看管理员下一页列表模块涉及到的method的参数值为 “selectNextManagerAction”,当method=selectNextManagerAction时,会调用 ManagerAction类中的select Next ManagerAction()方法。查看管理员下一页列表selectNextManagerAction()方法的关键代码 如下。

例程21-22:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

public ActionForward selectNextManagerAction(ActionMapping mapping,

                                                  ActionForm form,

                                                  HttpServletRequest request,

                                                  HttpServletResponse response) {

        managerDao.getSqlMapClient();

        HttpSession session=request.getSession();

        PaginatedList list =(PaginatedList)session.getAttribute("list");

        if (session.getAttribute("list")==null){

            request.setAttribute("message","您已经与服务器断开");

/*当从session中获取list对象为null,向页中传递message对象*/

            return mapping.findForward("failConnection");

        }

        list.nextPage();     /*通过PaginatedList类的对象list,获取下一页的纪录的操作*/

        request.setAttribute("list",(List)list);

        return mapping.findForward("selectManagerList");

    }

3.查看管理员列表上一页的操作

当管理员在图21.9所示的页面中单击“上一页”的超链接时,实现查询管理员列表中的上一页记录。单击“上一页”超链接的代码如下。

<a href="managerAction.do?method=selectPreviousManagerAction& pageNumber=<%=pageNumber-1%>&pageMax=<%=pageMax%>">上一 页</a>

从上面的URL地址中可以知道,查看管理员上一页列 表模块涉及到的method的参数值为“selectPreviousManagerAction”,当 method=selectPreviousManagerAction时,会调用ManagerAction类中的 selectPreviousManagerAction()方法。查看管理员上一页列表select PreviousManagerAction()方法的关键代码如下。

例程21-23:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

    public ActionForward selectPreviousManagerAction(ActionMapping mapping,

            ActionForm form,

            HttpServletRequest request,

            HttpServletResponse response) {

        managerDao.getSqlMapClient();

        HttpSession session = request.getSession();

        PaginatedList list = (PaginatedList) session.getAttribute("list");

        if (session.getAttribute("list") == null) {

            request.setAttribute("message", "您已经与服务器断开");

            return mapping.findForward("failConnection");

        }

        list.previousPage();   /*通过PaginatedList类的对象list,获取上一页的纪录的操作*/

        request.setAttribute("list",(List)list);

        return mapping.findForward("selectManagerList");

    }

4.struts-config.xml文件配置

从查看管理员列表第一页、下一页及上一页操作的代码 可以知道,在ActionMapping类对象mapping调用findForward()方法中的参数名称都是selectManagerList, 因此在struts-config.xml文件中,配置查看管理员列表所涉及的<forward>元素,代码如下。

    <forward name="selectManagerList" path="/manager/showManagerList.jsp"/>

5.查询管理员列表页

将ManagerAction实现类中的 selectManagerAction()方法、selectNextManagerAction()方法及 selectPreviousManagerAction()方法返回的查询结果显示在查看管理员列表页showManagerList.jsp中。显示 管理员列表showManagerList.jsp页的关键代码如下。

例程21-24:光盘/mr/21/wyBooks/web/manager/showManagerList.jsp

<%@ page import="java.util.List"%>

<%@ page import="com.actionForm.ManagerForm"%>

在showManagerList.jsp中首先通过request.getAttribute()方法获取查询结果并将其保存在List容器类中,再通过循环将管理员信息以列表的形式显示在页面中。关键代码如下。

<%

List list=(List)request.getAttribute("list");

int pageNumber=1;

if(request.getParameter("pageNumber")!=null){

pageNumber=Integer.parseInt(request.getParameter("pageNumber"));

}

int pageMax;

if(request.getParameter("pageMax")==null){

List allList=(List)request.getAttribute("allList");

pageMax=allList.size()/13;

if(allList.size()/13!=0){

pageMax=allList.size()/13+1;

}

}else{

pageMax=Integer.parseInt(request.getParameter("pageMax"));

}

%>

<body>

<table width="799" height="457" border="0" background="Images/operationTwo.jpg">

  <tr>

    <td valign="top" align="center">

      <br>

      <tablewidth="400" border="1"

        <tr>

          <td height="25">序号</td>

          <td>管理员</td>

          <td>级别</td>

          <td bgcolor="#83B9FF">操作</td>

        </tr>

循环显示管理员信息的关键代码如下。

        <%for(int i=0;i<list.size();i++){

          ManagerForm form=(ManagerForm)list.get(i);

          %>

        <tr align="center">

          <td height="25"><%=form.getId()%></td>

          <td><%=form.getAccount()%></td>

           <td><%=form.getManagerLevel()%></td>

          <td><%if(form.getAccount().equals("mr")){%>—— <%}else{%><a href="managerAction.do?method=updateLevefManagerAction&account=& lt;%=form.getAccount()%>">修改级别</a>&nbsp;&nbsp;<a href="managerAction.do?method=deleteManagerAction&account=& lt;%=form.getAccount()%>">删除信息</a><%}%></td>

        </tr>

        <%}%>

      </table>

在showManagerList.jsp页面中,判断单击“上一页”与“下一页”超链接的代码如下。

例程21-25:光盘/mr/21/wyBooks/web/manager/showManagerList.jsp

      <table width="400" border="0" cellpadding="0" cellspacing="0">

        <tr>

          <td width="240" height="32">&nbsp;<%=pageNumber%>/<%=pageMax%>页</td>

          <td width="160" align="right">

                <%if(pageNumber==1){%>

                <%}else if(pageNumber==2){%>

                <a href="managerAction.do?method=selectManagerAction">上一页</a>

                <%}else{%>

                <a href="managerAction.do?method=selectPreviousManagerAction& pageNumber=<%=pageNumber-1%>&pageMax=<%=pageMax%>">上一 页</a>

                <%}%>

  <%if(pageNumber!=pageMax){%>

  <a href="managerAction.do?method=selectNextManagerAction&pageNumber=& lt;%=pageNumber+1%>&pageMax=<%=pageMax%>">下一页</a>

  <%}%>

          </td>

        </tr>

      </table>

21.11.5  添加管理员信息

管理员登录后,选择“系统管理”/“添加管理员”菜单项,打开添加管理员信息页面。添加管理员信息页面的运行结果如图21.10所示。

图21.10  添加管理员页面的运行结果

1.添加管理员信息页面

添加管理员信息页面主要用于收集输入的管理员信息及通过自定义的JavaScript函数验证输入信息是否合法,该页面涉及到的表单元素如表21.14所示。

表21.14                                         添加管理员页面所涉及的表单元素

名    称

元 素 类 型

重 要 属 性

含    义

form

form

method="post" action="managerAction.do?method=insertManagerAction"  onSubmit="return checkEmpty(form)"

表单

account

text

管理员名称

password

password

管理员密码

radio

managerLevel

value="普通操作员" checked

普通操作员级别单选框

radio

managerLevel

value="高级操作员"

高级操作员级别单选框

Submit2

submit

value="添加操作员"

【添加操作员】按钮

back

button

value="返回操作" onClick=" javascript: history. go(-1);"

【返回操作】按钮

2.添加管理员的Action实现类

在添加管理员信息页面中,输入合法的管理员名称 及密码后,单击“添加操作员”按钮,网页会访问一个URL,这个URL是 “managerAction.do?method=insertManagerAction”。从该URL地址可以知道添加管理员信息模块涉及到的 action的参数值为“insertManagerAction”,也就是当method = insertManagerAction时,会调用ManagerAction类中的添加管理员信息的方法insertManagerAction(), 添加管理员信息insertManagerAction()方法的关键代码如下。

例程21-26:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

  public ActionForward insertManagerAction(ActionMapping mapping,

                                              ActionForm form,

                                              HttpServletRequest request,

                                              HttpServletResponse response) {

        ManagerForm managerForm = (ManagerForm) form;

        if (managerForm.getAccount() == null ||

            managerForm.getAccount().equals("")) {

            return mapping.findForward("insertManagerAction");

        } else {

                managerDao.getSqlMapClient();

                managerForm.setAccount(managerForm.getAccount());

                managerForm.setManagerLevel(managerForm.getManagerLevel());

                managerForm.setPassword(managerForm.getPassword());

                String message="添加管理员失败!!!"; 

              if(managerDao.insertManager(managerForm)) 

              {

                  message="添加管理员成功!!!";

              }

                request.setAttribute("result",message);

/*字段account为主键,当添加管理员的名称存在时,执行添加失败*/

            request.setAttribute("forwardPage", "firstPage.jsp");

            return mapping.findForward("showOperation");

        }

    }

3.struts-config.xml文件配置

在struts-config.xml文件中配置添加管理员信息所涉及的<forward>元素,代码如下。

      <forward name="showOperationManager" path="/manager/showOperationManager.jsp"/>

      <forward name="insertManagerAction" path="/manager/insertManager.jsp"/>

4.添加信息成功页面

笔者将添加管理员信息、设置管理员权限和管理员信息删除3个模块的操作成功页面用一个JSP文件实现,关键代码如下。

例程21-27:光盘/mr/21/wyBooks/src/web/ WEB-INF/ manager/ showOperation Manager.jsp

<%

if(request.getAttribute("result")==null){

%>

<script language='javascript'>alert('您修改的密码成功,请牢记您的新密码!!!');window.location.href='firstPage.jsp';</script>

<%}else{

String result=(String)request.getAttribute("result");

String method=(String)request.getAttribute("method");

%>

<script language='javascript'>alert('<%=result%>');window.location.href='<%=method%>';</script>

<%}%>

21.11.6  设置管理员权限

管理员登录后,选择“系统设置”/“管理员设置”菜单项,进入到查看管理员列表页面,在该页面中,单击想要设置权限的管理员信息后面的“修改级别”超链接,进入到“设置管理员权限”页面,设置该管理员的权限。设置管理员权限页面的运行结果如图21.11所示。

图21.11  设置管理员权限页面的运行结果

1.修改管理员权限页面

修改管理员权限信息页面主要用于修改管理员的级别,该页面涉及到的表单元素如表21.15所示。

表21.15                                     修改管理员权限页面所涉及的表单元素

名    称

元 素 类 型

重 要 属 性

含    义

form

form

method="post" action="managerAction.do?method=updateLevefManagerAction"

表单

account

hidden

value="<%=account%>"

隐藏管理员名称

password

hidden

value="<%=password%>"

隐藏管理员密码

radio

managerLevel

<%if(managerLevel.equals("普通管理员")){%>checked<%}%>

普通操作员级别单选框

radio

managerLevel

<%if(managerLevel.equals("高级管理员")){%>checked<%}%>

高级操作员级别单选框

Submit2

submit

value="修改级别"

【修改级别】按钮

back

button

value="返回操作" onClick="javascript:history.go(-1);"

【返回操作】按钮

2.设计设置管理员权限页面

在“查看管理员列表”页面中可以找到打开“修改级别”页面的超链接代码,代码如下。

<a href="managerAction.do?method=updateLevefManagerAction&account=wy9wy">修改级别</a>

从上面的URL地址中可以知道,设置管理员权限页面 所涉及到的method的参数值为“updateLevefManagerAction”,当 method=updateLevefManagerAction时,会调用查询指定管理员权限信息的方法 updateLevefManagerAction()。

在该方法中,笔者将查询管理员权限与修改管理员的权限都写在这个方法体中,通过判断从页面中取得密码是否为null,加以进行区分。

updateLevefManagerAction()的关键代码如下。

例程21-28:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

    public ActionForward updateLevefManagerAction(ActionMapping mapping,

                                                   ActionForm form,

                                                   HttpServletRequest request,

                                                   HttpServletResponse response) {

        ManagerForm managerForm = (ManagerForm) form;

        managerDao.getSqlMapClient();

        if (managerForm.getPassword() == null ||

            managerForm.getPassword().equals("")) {

        managerForm.setAccount(Chinese.toChinese(request.getParameter("account")));

            ManagerForm managerform = managerDao.selectManager(managerForm);

/*调用ManagerDao类中selectManager()实现管理员查询的操作*/

            request.setAttribute("account", managerform.getAccount());

            request.setAttribute("password", managerform.getPassword());

            request.setAttribute("managerLevel", managerform.getManagerLevel());

            return mapping.findForward("updateLevefManagerAction");

/*查询管理员权限后返回的mapping对象的值*/

        } else {

            managerForm.setAccount(managerForm.getAccount());

            managerForm.setPassword(managerForm.getPassword());

            managerForm.setManagerLevel(managerForm.getManagerLevel());

            request.setAttribute("result", "修改操作员级别成功!!!");

            request.setAttribute("method",

                                 "managerAction.do?method=selectManagerAction");

            managerDao.updateManager(managerForm);

/*调用ManagerDao类中updateManager()实现修改管理员信息的操作*/

            return mapping.findForward("showOperationManager");

/*修改管理员权限后返回的mapping对象的值*/

        }

    }

3.struts-config.xml文件配置

在struts-config.xml文件中配置设置管理员权限所涉及的<forward>元素,代码如下。

      <forward name="showOperationManager" path="/manager/showOperationManager.jsp"/>

      <forward name="updateLevefManagerAction" path="/manager/updateLevefManager.jsp"/>

4.管理员权限说明

在本例中主要存在以下3种管理权限的级别。

q    系统管理员

该权限的管理员拥有本系统中的全部功能,在管理员表tb_manager中,字段managerLevel的内容为“系统管理员”。系统管理员登录后,导航栏中的显示结果如图21.12所示。

图21.12  系统管理员登录导航栏显示结果

注意:系统管理员在本系统中是唯一的,它的账号和密码分别为:mr和mrsoft。

q    高级管理员

该权限的管理员拥有本系统中的图书设置、图书管理、图书销售、借阅管理及图表分析的功能,在管理员表tb_manager中,字段managerLevel的内容为“高级管理员”。高级管理员登录后,导航栏中的显示结果如图21.13所示。

图21.13  高级管理员登录导航栏显示结果

q    普通管理员

该权限的管理员拥有本系统中的图书销售、借阅管理及图表分析的功能,在管理员表tb_manager中,字段managerLevel的内容为“普通管理员”。普通管理员登录后,导航栏中的显示结果如图21.14所示。

图21.14  普通管理员登录导航栏显示结果

21.11.7  删除管理员信息

管理员登录后,选择“系统设置”/“管理员设置”菜单项,进入到查看管理员列表页面,在该页面中单击想要删除的管理员信息后面的“删除”超链接,该管理员信息被删除。

在“查看管理员列表”页面中,可以找到删除管理员信息的超链接代码,代码如下。

<a href="managerAction.do?method=deleteManagerAction&account=<%=form.getAccount()%>">删除信息</a>

从上面的URL地址中,可以知道删除管理员页所涉及 到的method的参数值为“deleteManagerAction”,当method=deleteManagerAction时,会调用 ManagerAction类中的删除管理员的方法deleteManagerAction(),删除管理员deleteManagerAction() 方法的关键代码如下。

例程21-29:光盘/mr/21/wyBooks/src/com/action/ManagerAction.java

public ActionForward deleteManagerAction(ActionMapping mapping,

                                              ActionForm form,

                                              HttpServletRequest request,

                                              HttpServletResponse response) {

        ManagerForm managerForm = (ManagerForm) form;

        managerDao.getSqlMapClient();

        managerForm.setAccount(request.getParameter("account"));

        managerDao.deleteManager(managerForm);

/*调用managerAction类中的deleteManager()删除数据库某一组数据*/

        request.setAttribute("result", "删除操作员成功!!!");

        request.setAttribute("method",

                             "managerAction.do?method=selectManagerAction");

        return mapping.findForward("showOperationManager");

    }

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值