您好,欢迎来到12图资源库!分享精神,快乐你我!我们只是素材的搬运工!!
  • 首 页
  • 当前位置:首页 > 网站教程 > AJAX教程 >
    Nej代码开发规范
    时间:2017-06-13 15:27 来源: 作者: 浏览:收藏 挑错 推荐 打印

    一. 概述

    为了统一前端开发的代码风格,以便后续代码的管理和维护,在使用前端开发时请遵循本文档制定的规范编写代码。 本文档涉及的规范主要包含四个方面:注释规范、命名规范、“类”模型、控件规范,另外会简要的说明系统发布的情况。

    二. 注释规范

    良好的注释可以增加代码的可读性和可维护性

    1. 文件注释

    文件注释用来说明当前文件所实现内容,主要包括说明部分和作者部分。

    • 说明部分:描述文件实现的功能、模块或接口等,如有需要增加使用说明或者范例。
    • 作者部分:记录文件的开发者名称和联系方式,用以后续的维护或者交流沟通等。
    • 依赖部分:记录当前文件直接依赖的其他文件,便于工具构建依赖关系。

    注释范例如下图所示:

     /**
     * ------------------------------------------
     * 水平滑动器逻辑封装实现文件
     * @version  1.0
     * @author   genify(caijf@corp.netease.com)
     * ------------------------------------------
     */

    关于这部分,如果使用Eclipse做为开发工具的话可以将其做成一个模板,在新建JS文件时可自动生成。

    2. 接口注释

    接口注释用来描述当前定义的接口的功能及输入输出数据,主要包括说明部分、输入部分、输出部分。

    • 说明部分:说明当前接口的功能,如有需要可增加使用说明或者范例。
    • 输入部分:说明输入数据的类型及含义。
    • 输出部分:说明输出数据的类型及含义。

    注释范例如下图所示:

    /**
     * 控件重置
     * @param  {Object} _options 可选配置参数
     * @return {Void}
     */
    _proAbstract.__reset = function(_options){
        this.__supReset(_options);
        this.__doInitClass(_options.clazz);
        this._$appendTo(_options.parent);
    };

    关于这部分,如果使用Eclipse的Aptana插件,则在接口写好后直接输入“/**”然后回车会自动生成默认的注释。

    3. “类”注释

    “类”注释用来说明当前类的基本功能、继承关系及可接收初始输入数据,主要包括功能描述部分、继承关系部分、初始数据部分。关于这里的“类”可参阅JAVASCRIPT类模型部分的详细说明。

    • 功能描述部分:描述类所代表的对象及基本功能,如需要可增加使用说明或范例。
    • 继承关系部分:说明类的父类,以便于代码的回溯。
    • 初始数据部分:类对象在实例化时可接收这些数据做为初始信息。

    注释范例如下图所示:

    /**
     * 提示建议控件
     * @class   提示建议控件
     * @extends nej.ui._$$Abstract
     * @param  {Object} _options 可选配置参数,已处理参数列表如下
     *                           input     [Node|String] - 输入框节点或者ID
     *                           onselect  [Function]    - 选中触发事件
     *                           onchange  [Function]    - 输入内容变化触发事件
     */
    _p._$$Suggest = NEJ.C();
      _proSuggest = _p._$$Suggest._$extend(_p._$$Abstract);
      _supSuggest = _p._$$Suggest._$supro;

    三. 命名规范

    本部分的规范主要为项目发布时的压缩混淆做准备

    1. 命名空间

    • 规则:小写字母
    • 说明:系统的命名空间通过基础库中window.P接口增加,会以字符串的形式出现,在系统发布时不予混淆,因此选择命名空间时不易选用过于复杂的名称。

    注:基础库的接口命名空间采用单个大写字母,独立项目中不宜使用此命名空间的名称规则 范例:op.tsk, lv.sys

    var _  = NEJ.P,
        _o = NEJ.O,
        _e = _('nej.e'),
        _u = _('nej.u'),
        _t = _('nej.ut'),
        _p = _('nej.ui'),

    2. 私有属性/接口

    • 规则:“__”+描述,即增加前缀“__”(两个下划线),变量必须有var关键字定义
    • 说明:此类属性/接口仅会在当前对象或者子类内使用,对于其他对象不可见,在系统发布时会对此类变量做混淆,因此在选择名称时以便于理解为主。

    范例:如下例所示的__initNode等等

    /**
     * 初始化节点
     * @return {Void}
     */
    _proSuggest.__initNode = function(){
        this.__supInitNode();
        this.__sopt.body = this.__body;
    };

    3. 公共属性/接口

    • 规则:“_$”+描述,即增加前缀“_$”
    • 说明:此类属性或者接口可以为外部程序直接使用,系统发布时如果所有js统一发布则该类属性或者接口也会做混淆处理,因此在选择名称时以便于理解为主,名称首字母小写,遵循驼峰规则

    范例:如下例所示的_$getBody等

    /**
     * 取当前控件节点
     * @return {Node} 控件节点
     */
    _proAbstract._$getBody = function(){
        return this.__body;
    };

    4. “类”对象

    • 规则:“_$$”+描述,即增加前缀“_$$”
    • 说明:此类对象可在程序任何地方使用,系统发布时如果所有js统一发布则该类名称也会做混淆处理,因此在选择名称时以便于理解为主。

    范例:如下例所示的_$$Event等

    _p._$$Event = NEJ.C();
      _proEvent = _p._$$Event.prototype;

    5. 临时变量/参数

    • 规则:“_”+描述,即增加前缀“_”(单个下划线)
    • 说明:此类名称仅在当前接口使用,系统发布时做混淆处理,因此在选择名称时以便于理解为主。

    范例:如下例所示的_options,_instance等

    _p._$$Event._$allocate = function(_options){
        _options = _options||{};
        // check pool first
        var _instance = !!this.__pool
                        &&this.__pool.shift()
                        ||new this(_options);
        // reset instance, flag first
        _instance.__xxxx = !0;
        _instance.__reset(_options);
        return _instance;
    };

    四. “类”模型

    在Script中本身没有“类”的概念,在实际应用中我们在Script中引入“类”的概念主要出于以下几方面考虑:

    • 利用面向对象的优势
    • 控件之间的低耦合性
    • 代码的重用
    • 代码的管理维护

    对于JavaScript中“类”模型的实现有很多方式,通过不断的实践我们并结合公司内部的库,项目中采用“类”模型设计的请遵循以下规范。注:请按照以下顺序创建“类”

    1. “类”的定义

    “类”定义统一使用C接口,范例如下

    _p._$$Abstract = NEJ.C();

    2. “类”的继承

    通过1中定义的“类”会具备扩展接口,可以从其他“类”继承,范例如下

    _p._$$Abstract = NEJ.C();
      _proAbstract = _p._$$Abstract._$extend(_t._$$Event);

    3. “类”的初始化

    “类”的初始化接口统一为__init

    • 接受“类”的构造参数做为输入
    • 如果需要调用父类的this.__supInit();
    /**
     * 初始化
     * @return {Void}
     */
    _proAbstract.__init = function(){
        this.__supInit();
        _e._$dumpCSSText();
        this.__initXGui();
        this.__initNode();
    };

    4. “类”接口的实现

    根据“类”的需要实现其他接口,在子“类”的其他接口中如果需要掉父“类”的同名接口采用以下方式 子类实现的接口是__init,__initNode,__destory,__reset的方法,要调用父类的方法可以用 __supInit, __supInitNode, __supDestroy, __supReset 如初使化方法:

    /**
     * 控件重置
     * @param  {Object} _options 可选配置参数
     * @return {Void}
     */
    _proAbstract.__reset = function(_options){
        this.__supReset(_options);
        this.__doInitClass(_options.clazz);
        this._$appendTo(_options.parent);
    };

    如果不是上面的4类接口,假设需要调用setData的父类方法就需要如此写了

    /**
     * 加载中控件
     * @class  加载中控件
     * @param  {Object} _options 可选配置参数,已处理参数列表如下:
     */
    _p._$$Resize = NEJ.C();
    _proResize = _p._$$Resize._$extend(_ui._$$Abstract);
    _supResize = _p._$$Resize._$supro;
    /**
     * 设置数据
     */
    __proResize.__setData = function(){
      _supResize.__setData.apply(this,arguments);
    };

    五. 控件规范

    .

    六. 文件定义

    var f = function(){
    
    };
    define('{pro}js/item.js', ['{lib}ui/item/item.js', '{lib}util/template/tpl.js'], f);

    七. 代码规范

    1 常量

    常量用全部大写字母如

    var __SECONDS_IN_A_MINUTE = 60;

    枚举型对象名大写枚举量用小写

    var __SECONDS_TABLE = {
      minute: 60,
      hour: 60 * 60
      day: 60 * 60 * 24
    }

    2 空格

    数值操作符(如, +/-/*/% 等)两边留空; 赋值操作符/等价判断符两边留一空格; for 循环条件中, 分号后留一空格; 变量声明语句, 数组值, 对象值及函数参数值中的逗号后留一空格; 空行不要有空格; 行尾不要有空格; 逗号和冒号后一定要跟空格; 点号前后不要出现空格; 空对象和数组不需要填入空格; 函数名末尾和左括号之间不要出现空格

    var _arr = [1, 2, 3];

    3 缩进

    HTML和JS统一成一个tab 4个空格,一般eclipse的编辑工具都是一个tab,只是tab没有转成空格,把转成空格勾选上即可。 设置在 Window->Preferences->general->editors->text editors display tab width:4 勾选 Insert Spaces for tabs Show Print Margin Print Margin column:80 如相图:

    Nej代码开发规范

    4 代码一行限制

    一行最多为80个字符,超过80个字符需要在适合的地方换行缩进一个tab

    v._$addEvent(this.__accountTabList[i],'mousedown',
                    this.__onMouseDownStopOrRightClick._$bind(this,i));

    5 条件语句

    条件语句的写法:

    if(_isOK){
    
    } else {
    
    }

    6 数组,对象定义

    • 单行数组或对象定义

      var _arr = [1, 2, 3]; var _obj ={a: 1, b:2, c: 3}

    • 多行数组或对象定义,换行缩进一个tab:

       var _inset = {
         top: 10,
         right: 20,
         bottom: 15,
         left: 12
       }
       this.__rows =[
         '"Slartibartfast" <fjordmaster@magrathea.com>',
         '"Zaphod Beeblebrox" <theprez@universe.gov>',
         '"Ford Prefect" <ford@theguide.com>',
         '"Arthur Dent" <has.no.tea@gmail.com>',
         '"Marvin the Paranoid " <marv@googlemail.com>',
         'the.mice@magrathea.com'
       ]

    定义数组和对象,要用自面量:

    var _a = {};
    var _b =[];

    7 换行

    • if的判断语句超长时,要在适合的地方换行:

      if(_list[i].fid!=__subFolderId&&

       _list[i].fid!=__advFolderId&&
           _list[i].fid!=__garbageFolderId&&
           _list[i].fid!=__draftFolderId&&
           _list[i].fid!=__deletedFolderId){
            _usedList.push(_list[i]);//_list.splice(i,1);
        }
    • 函数参数,如果一个函数的参数很多,需要对参数进行对齐:

       __proCacheDB._$deleteMessages = function(_username,_ckey,
                                                 _messageIds,_tofid,_crossPages){

    8 匿名函数

    函数体需要重起一个

    _proEvent.__destroy = (function(){
        var _doRemoveEvent = function(_args,_key,_map){
            delete _map[_key];
            _v._$delEvent.apply(_v,_args);
        };
        return function(){
            this._$clearEvent();
            _u._$forIn(this.__events_dom,_doRemoveEvent);
        };
    })();

    9 三元操作符

    三元操作符的格式,以下三种应该都是可行的

    var _x = _a ? _b : _c;
    var _y = a ?
        _loginButSimpleOperandB : _longButSimpleOperandC;
    var _a = _a ?
             _loginButSimpleOperandB : 
             _longButSimpleOperandC; 

    10 事件命名

    添加节点事件的命名规则 on + 名词 + 动作 符合驼峰规则 如页面上有一个editBtn的按钮,要给这个按钮添加点击事件时,可以命名成onEditBtnClick,如果是鼠标悬停,onEditBtnMouseover等这样的一种命名规则 除了事件的命名外,其他的所有回调函数都以cb开头,如item里对模块的回调,cache对外面的回调等都以__cb开头 + 名词 + 动词

    11 Array遍历

    统一写法:

    for(var i = 0,l = _array.length; i<l; i++){
    }

    12 定义多个变量

    var定义多个变量时,如果某个变量初始化了,就另起一行,重新用一个var来定义余下的变量

    var _a, _b, _c = true;
    var _i, _b = false;
    var _e;
    (责任编辑:信息网)

    (责任编辑:12图资源库)