页面程序流程(v1.1.2)

页面程序流程

页面程序,指与页面相关的程序逻辑代码。

页面程序流程,指带有一定执行顺序的页面程序逻辑代码。


  • 页面的程序流程有哪些?
  • 页面的程序流程的执行顺序是怎样的?
try{
    if(Check)
    {
        会话期限 else { 记录操作 return }
        用户登录 else { 记录操作 return }
        功能权限 else { 记录操作 return }
        用户权限 else { 记录操作 return }
    }
    界面风格
    业务逻辑(Page_Load/界面操作事件)
    语言
    记录操作
} catch(e){
    记录错误
    显示错误
    复原窗口
}

  • 每个程序流程在页面打开事件中是否执行?
  • 每个程序流程在界面操作事件中是否执行?

页面打开事件,指页面打开时执行的逻辑程序,如WebForm的Page_Load、微信小程序的OnLoad

界面操作事件,指如按钮的点击事件、文本框的更改事件等

程序流程 页面打开事件 前后端分离

界面操作事件
WebForm

界面操作事件
会话期限 执行 执行 执行
用户登录 执行 执行 执行
功能权限 执行 执行 执行
用户权限 执行 执行 执行
界面风格 执行 不需要执行 实际上执行
业务逻辑 执行 执行 执行
语言 执行 可能执行 实际上执行
记录操作 执行 执行 执行
记录错误 执行 执行 执行
显示错误 执行 执行 执行
复原窗口 执行 执行 执行

前后端分离指类似安卓app、苹果app、微信小程序、Vue的开发模式,即前端通过ajax无刷新更新的方式加载数据。

WebForm指asp.net的aspx后缀的页面开发模式,即开发模式主要依赖于from,每个事件会把form里的所有数据通过form提交到后端。

会话期限与用户登录

【会话】与【用户】的关系:

  • 一个【会话】只能有一个【用户】,表示登录的用户,如果未登录用户,则【会话】中的【用户】相关信息为null。
  • 一个【用户】可以有多个【会话】,因为用户可以登录在多个设备上、多个浏览器上、多个使用环境上、以及浏览器的多个选项卡上。

登录用户的程序流程:

  1. 验证用户账号和密码是否正确
  2. 把【用户】的相关信息记录在【会话】中
  3. 当登录的【用户】已有登录在多个地方的【会话】,则提示用户是否退出该用户正在使用的其它地方的【会话】,并提醒该用户其它地方的使用者:“有其它地方已登录你的账号”。

在原框架中,同一个用户不能同时登录多个使用端、或多个浏览器、或多个浏览器上的选项卡。

在新框架中,不再做同时登录同一用户的限制。


主动登录用户的操作流程:

  1. 未登录情况下
  2. 打开管理界面(Main.aspx)
  3. 点击右上角登录按钮
  4. 弹出登录窗口
  5. 录入账号密码
  6. 点击登录
  7. 关闭登录窗口,并提示登录成功

在原框架中,未登录情况下,是不能直接打开主界面(Main.aspx)的,只能先打开登录界面(Login.aspx)。

在原框架中,登录入口有两种,分别在登录页面(Login.aspx)、主界面(Main.aspx)使用过程中要求重新登录时。

而在新框架中,取消了使用登录页面的入口(Login.aspx),保留了主界面的登录入口,这样做的好处是:

  • 有些功能可能不需要要求用户登录,这样在主界面未登录情况下直接打开即可。如:新闻公告、活动公告、节假日公告等
  • 统一登录界面的入口,使登录入口只保留一种入口。

打开功能时要求登录的操作流程:

  1. 未登录情况下
  2. 打开管理界面(Main.aspx)
  3. 点击菜单栏的功能菜单项
  4. 弹出指定功能的窗口与页面界面,如果该功能需要登录,则界面只显示布局界面,不显示数据。
  5. 如果该功能需要登录,再弹出一个登录用户的窗口。
  6. 录入账号密码
  7. 点击登录
  8. 关闭登录窗口,并提示登录成功
  9. 该功能界面重新加载数据

会话到期时要求登录的操作流程:

  1. 会话到期情况下
  2. 当打开页面或操作界面
  3. 如果打开页面的功能需要登录用户,则界面只显示布局界面,不显示数据;如果操作界面的功能需要登录用户,则保持操作前的界面和数据状态。
  4. 再弹出一个登录用户的窗口
  5. 录入账号密码
  6. 点击登录
  7. 关闭登录窗口,并提示登录成功
  8. 如果是打开页面要求登录的,则打开的页面重新加载数据;如果是操作界面要求登录的,不会自动重新操作,需要用户自行重新操作。

在原框架中,会话到期,会关闭打开中的界面、或操作中的界面,这样用户原来操作的其它过滤操作、打开操作、选项卡等操作,就需要重新打开页面,并重新操作一遍过滤、选项卡等操作。


保持会话状态:

  • IIS重启后,用户不应该要重新登录,如果用户正在操作中并提醒“系统中断操作失败”。
  • 操作系统重启后,用户不应该要重新登录,如果用户正在操作中并提醒“系统中断操作失败”。
  • 系统崩溃后,用户不应该要重新登录,如果用户正在操作中并提醒“系统中断操作失败”。

在原框架中,系统可能因为不确定的原因,导致系统不间断重启,导致用户经常需要重新登录。

程序设计应该多往程序有缺陷的情况下去考虑设计,有时程序很难做完美没有任何问题。


会话期限、用户登录与App.Page.Check属性的设置关系:

  • 如果Check的值为None,不检查会话期限、用户登录,即界面操作不需要用户登录。
  • 如果Check的值为All,需要检查会话期限、用户登录,即界面操作需要用户登录。

App.Page.Check属性的详细说明请看本文章节“App.Page.Check属性”

记录错误与显示错误

指页面程序流程中,程序出错了把错误信息记录下,并提示用户程序出错。

指页面程序流程中,程序出错时:

  1. 把错误信息记录下来。
  2. 另外弹出窗口,提示用户程序出错,不应该显示错误的详细信息,只需要显示错误信息记录的Id,以便于开发人员直接找到错误信息。
  3. 出错的页面应该保留出错前的样子,不应该关闭页面。

在原框架中,出错时只显示出错了,要自己去找这次错误对应的大概时间的那条错误记录。

在原框架中,出错时会显示错误的详细信息,会让普通用户去看一大串看不懂的详细信息,那是只有专业的开发人员才看懂,而且这样会提高用户的出错心理阴影。

在原框架中,如果出错了原页面会关闭,这样用户原来操作的其它过滤操作、打开操作、选项卡等操作,就需要重新打开页面,并重新操作一遍过滤、选项卡等操作。

记录操作

  • 记录哪个用户在什么时间点打开哪个页面。
  • 记录哪个用户在什么时间点在界面上操作了什么。
  • 记录操作有没有执行主业务逻辑的程序流程,如果执行那大概执到哪个流程中断了。

如果用户还没登录,也需要记录操作,这样可以了解用户没登录的情况下操作了什么,记录操作应该更全面,有助于调查操作信息更可靠。

如果客户没有购买功能,也需要记录操作,这样可以了解客户是否对某个功能感兴趣常常去点点看,了解客户的好奇行为信息,并且记录操作应该更全面,有助于调查操作信息更可靠。

如果用户没有打开页面的权限,也需要记录操作,记录操作应该更全面,有助于调查操作信息更可靠。

如果用户没有某项界面操作的权限,也需要记录操作,记录操作应该更全面,有助于调查操作信息更可靠。

功能权限与用户权限

功能未激活:

  1. 打开页面
  2. 如果页面的功能未激活,则关闭当前页面
  3. 提示用户功能未购买激活,或未来可考虑设计成显示购买界面。

打开页面时,功能未授权:

  1. 打开页面
  2. 如果用户没有功能的查看权限,则关闭当前页面
  3. 提示用户功能未授权。

操作界面时,功能未授权:

  1. 操作界面
  2. 如果用户有功能的操作权限,则取消执行界面操作的业务逻辑程序
  3. 提示用户功能未授权。

功能权限、用户权限、App.Page.Check属性、App.Page.FunctionId的设置关系:

  • 如果Check的值为None时,不检查功能权限、用户权限。
  • 如果Check的值为All时,需要检查功能权限、用户权限。

App.Page.Check属性的详细说明请看本文章节“App.Page.Check属性”

App.Page.FunctionId属性的详细说明请看本文章节“App.Page.FunctionId属性”

语言

语言,如指软件的英文版、繁体版、简体版等。


判断使用哪个语言的程序逻辑:

  1. 如果会话在有效期内,则读取会话记录中的语言数据。
  2. 如果读取会话记录中的语言数据为null,则读取会话记录中的语言数据。
  3. 如果会话已超时,则读取客户端记录中的语言数据。
  4. 如果读取客户端记录中的语言数据为null,则使用默认语言。
  5. 如果会话记录不存在,则读取客户端记录中的语言数据。
  6. 如果客户端记录不存在,则提示“刚刚开发人员调试初始化客户端,操作被取消了,请重新操作。”,并初始化客户端记录。

新框架语言与原框架语言的区别:

  • 语言程序流程是优先于主要业务逻辑的执行,如果业务逻辑中有动态控件的生成,那么优先执行的语言程序流程就无法涉及到动态控件的语言控制了。因此,新框架中,语言程序流程放在了主业务逻辑的后面执行。

界面风格

界面风格,如指软件的蓝色风格、黑色风格、白色风格等。


判断使用哪个界面风格的程序逻辑:

  1. 如果会话在有效期内,则读取会话记录中的界面风格数据。
  2. 如果读取会话记录中的界面风格数据为null,则读取会话记录中的界面风格数据。
  3. 如果会话已超时,则读取客户端记录中的界面风格数据。
  4. 如果读取客户端记录中的界面风格数据为null,则使用默认界面风格。
  5. 如果会话记录不存在,则读取客户端记录中的界面风格数据。
  6. 如果客户端记录不存在,则提示“刚刚开发人员调试初始化客户端,操作被取消了,请重新操作。”,并初始化客户端记录。

处理进度

  • 显示处理进度条时,用户还可以操作其它界面处理其它事情。
  • 可以同时处理多个事情,并显示多个处理进度条信息。
  • 用户通过进度条可以主动中断处理。
  • 用户可以看到公共处理进度信息,处定时的收集卡机数据的进度、自动化分析考勤的进度信息等。
  • 用户关闭浏览器后,不需要中断处理进度。
  • 用户重新登录后,如果处理进度还在进行,则可以继续看到处理进度条。
  • 用户可以看到其它用户的处理进度情况,以便了解服务器的繁忙情况。
  • 通过ProgressEntityService统一管理处理进度信息,有利于更好的实现管理处理进度功能。

新框架中,不再通过window.Progress = new Progress(……),来控制进度条信息,将统一使用ProgressEntityService代替。。

异步

  • 异步可以同时更新数据,而不必一条条更新语句按顺序执行。
  • 异步可以同时查数据,而不必一条条查询语句按顺序执行。
  • 异步可以在等待硬盘IO操作的同时,处理其它事情。
  • 异步不是多线程,多个异步操作同一个变量不存在数据计算偏差和线程安全问题,但多个线程操作同一个变量存在计算数据偏差和线程安全。
  • .aspx代码文件,需要在顶部的<%@Page %>中加上Async="true"设置,指示该页面允许使用异步。
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Test.aspx.cs" Inherits="Test" Async="true" %>
<html xmlns="http://www.w3.org/1999/xhtml">
<head id="Head1" runat="server">
    <title></title>
</head>
<body>
    <form id="form1" runat="server">
    </form>
</body>
</html>
  • .aspx.cs代码文件,所有逻辑代码需要写在RegisterAsyncTask里。
using System;
using System.Web.UI;

public partial class Test : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {
        RegisterAsyncTask(new PageAsyncTask(async () =>
        {
            //逻辑代码
        }));
    }

    protected void OnMyEvent()
    {
        RegisterAsyncTask(new PageAsyncTask(async () =>
        {
            //逻辑代码
        }));
    }

    protected override void OnPreRender(EventArgs e)
    {
        base.OnPreRender(e);

        RegisterAsyncTask(new PageAsyncTask(async () =>
        {
            //逻辑代码
        }));
    }
}

App.Page.ClientId属性

  • 表示当前使用端是哪个【客户端】Id。可以通过ClientId获取到【客户端】的地理位置、IP地址、网卡物理地址、使用语言、界面风格……等
  • ClientId的有效期是2小时。
  • 用户端在线状态时,每间隔1小时,由客户端自行刷新有效期。
  • ClientId使用时,不需要判断有效期是否在2小时内。
  • ClientId可由【客户端】自行创建,也可由【服务端】创建。
  • ClientId在有效期内时:
    • 重新打开浏览器时,保持ClientId
    • 刷新浏览器时,保持ClientId
    • 重启服务器时,保持ClientId
    • 使用时,保留ClientId
  • ClientId超过有效期时:
    • 重新打开浏览器时,重新创建ClientId
    • 刷新浏览器时,保持ClientId
    • 重启服务器时,保持ClientId
    • 使用时,保留ClientId
有效期状态 重新打开浏览器 刷新浏览器 重启服务器 使用时
在有效期内 保持 保持 保持 保持
超过有效期 重新创建 保持 保持 保持

App.Page.SessionId属性

  • 表示当前使用者的【会话】Id,可以通过SessionId获取到:登录用户Id、登录用户名、客户端Id、客户端信息……等
  • SessionId的有效期是2小时。
  • 用户端在线状态时,每间隔1小时,由客户端发送请求到服务端,自动刷新有效期。
  • SessionId使用时,需要判断有效期是否在2小时内。
  • SessionId由【服务端】创建。
  • SessionId在有效期内时:
    • 重新打开浏览器时,保持SessionId
    • 刷新浏览器时,保持SessionId
    • 重启服务器时,保持SessionId
    • 使用时,保持SessionId
  • SessionId超过有效期时:
    • 重新打开浏览器时,重新创建SessionId
    • 刷新浏览器时,重新创建SessionId
    • 重启服务器时,重新创建SessionId
    • 使用时,重新创建SessionId
有效期状态 重新打开浏览器 刷新浏览器 重启服务器 使用时
在有效期内 保持 保持 保持 保持
超过有效期 重新创建 重新创建 重新创建 重新创建

App.Page.FunctionId属性的使用说明

  • 表示该【页面】只属于一个【功能】
  • 如果App.Page.Check的值包含Function,并且FunctionId有值时,则页面会检查功能权限。
  • 如果App.Page.Check的值包含Function | UserSession,并且FunctionId有值时,则页面会检查功能权限和用户权限。
  • 如果App.Page.Check的值包含Function时,FunctionId必需要有值,否则会报错“FunctionId is required for checking”
  • 如果App.Page.Check的值不包含Function时,即使FunctionId有值,不会检查功能权限和用户权限。
检查项 Function SessionUser
功能权限 -
用户权限

一个【页面】也可以属于多个【功能】,就需要其它处理方法了,可以把Check设置None,自行实现检查逻辑,就可以实现多个【功能】的检查。

FunctionId相当于在原框架中的GetWindowId()方法,区别和优点:

  • 区别1:GetWindowId是一个方法,FunctionId是一个属性。
  • 区别2:GetWindowId方法的返回类型是整型,FunctionId的属性类型是一个分布式Id
  • 区别3:GetWindowId不为null时,需要检查功能权限和用户权限。FunctionId不为null时,不代表需要检查功能权限和用户权限。
  • 优点1:未来考虑多方合作商共同参与开发,如果功能Id采用数字可能会常常发生重复冲突,需要中心化集中维护功能Id。如果果采用分布式Id,各自合作商自行生成Id即可,互不干扰,去中心化各自维护功能Id。
  • 优点2:去中心化同样方便于公司内部开发人员使用,内部开发人员自行生成Id即可,互不干扰,去中心化各自维护功能Id。

代码示例:

public class MyPage : App.Page
{
    protected internal override Id<FunctionEntity> FunctionId => new Id<FunctionEntity>("60244fff6545947758630631"); 
}

App.Page.WindowId属性

  • 指窗口的id
  • 一个窗口会有一个访问地址(Src)
  • 一个窗口可以最大化、最小化
  • 一个窗口可以显示坐标
  • WindowId必需要有值,如果WindowId为null,则会报错提示“WindowId异常,需要联系软件工程师处理”。

App.Page.Check属性

  • Check的值为All时,表示页面是否需要检查:会话期限、用户登录、功能权限、用户权限
  • Check的值为Function时,表示页面只做功能权限检查
  • Check的值为Session时,表示页面只做会话期限检查
  • Check的值为SessionUser时:
    • 检查会话期限
    • 检查用户登录
  • Check的值为Function | SessionUser时:
    • 检查会话期限
    • 检查用户登录
    • 检查功能权限
    • 检查用户权限
  • Check的值为None时,表示页面不做检查。
  • Check的值可以为组合值,如:Function | Session
  • Check的默认值为None
  • 如果Check的值为Function时,App.Page.FunctionId必需要有值,否则会报错“FunctionId is required for checking”
检查项 Function Session SessionUser
会话期限 - -
用户登录 - -
功能权限 - -
用户权限 -

如果需要自行编写检查逻辑,则把Check设置为None。

.Net WebForm的内置接口

.Net WebForm的内置接口,指 .net自带的接口。

在新框架中,以下内置接口保持使用:

  • Page_Load和OnLoad,用于处理页面数据的加载。
  • IsPostBack,用于表示页面是否处于事件逻辑。(目前暂时使用,后续应该会改动,以更适合未来的前后端分离的开发模式)
  • 控件的事件方法,如:myBtn_OnClick(object sender, EventArgs e)
  • OnPreRender,用于设置控件的非持久状态的数据。
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,525评论 6 507
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,203评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,862评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,728评论 1 294
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,743评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,590评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,330评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,244评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,693评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,885评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,001评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,723评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,343评论 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,919评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,042评论 1 270
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,191评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,955评论 2 355

推荐阅读更多精彩内容