note5 id:3120602024

天极传媒:天极网全国分站
您现在的位置:
& &&LOTUS Note ID 剖析
LOTUS Note ID 剖析天极网 14:05
  本文详细描述了 note IDs,并且解释了 Domino or Notes 任务 (复制等)使用 note ID 的组件时有什么不同以及 API 程序怎么使用他们.
  note ID 包括如下部分:
  UNID (Universal Note ID) - 唯一地确定了文档(note), 不管它(note)是位于何处或所处何时.另一方面, 每个文档(note)的复本拥有相同的 UNID, 并且 UNID 不会因为文档的更改而变化.
  OID (Originator ID) - 确定文档(note)的特殊的修订版本,不管它(note)位于何处,也就是说,每个文档(note)的复本拥有相同的 OID, 但是当文档(note)更改时OID也会随之修改.
  GNID (Global Note ID) - 确定一个特殊数据库中的一个特殊文档(note),GNID 不会随文档(note)的改变而变化。一个文档(note)复本的GNID可能会不同,因为毕竟他们在数据库中的位置可能不同。
  NID (Note ID) - 确定给定数据库中的一个特殊的文档(note)。NID 不包含数据库的信息(只在数据库内定位有效:译者注),并且文档(note)修改时不会变化。
  IID (Instance ID) - 确定一个给定数据库中的一个文档(note)的特殊修订版本,IID 不包含数据库信息,文档(note)修改时,IID会变化。
  GIID (Global Instance ID) - 确定一个特殊数据库中的一个文档(note)的特殊修订版本. GIID 包含数据库信息。The GIID 文档(note)修改时,IID会变化。
  你可以从 Notes 用户界面可以检查 ID 的信息。在视图中选择一个文档并且打开它。然后选择菜单 文件 - 文档属性。Notes 显示“文档属性”信息框。在信息页,Notes 显示和这个文档相关联的数据信息,包括文档创建和修改的日期和时间以及note ID 信息。 note ID 信息显示成三行,包含关键字和16进制字符。对于一个典型的文档,通常是这个样子:
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  这三行包含所选文档 Originator ID (OID), Universal Note ID (UNID), Global Note ID (GID), 和 Note ID (NID) 。
  The Universal Note ID (UNID) and the Originator ID (OID)
  第一、二行组成了完整的 Originator ID, Originator ID 由 Universal Note ID (整个第一行)加上序列时间和序列号(第二行):
  Originator ID (OID) =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  Universal Note ID (UNID) =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  Sequence Time =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  ************************
  Sequence Number =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  Originator ID (或 Universal Note ID)的前两部分由文件号(File member)和文档号(note member)组成。第一行由 \"OF\" (\"Originator ID - File\"),紧跟16个16进制字符,然后是连字符 \"-\" ,然后是 \"ON\" (\"Originator ID - Note\"),后面又是16个16进制字符。 \"OF\" 后面连字符之前的16个16进制字符构成了OID的文件号(File member)。\"ON\" 后面连字符之前的16个16进制字符构成了OID的文档号(note member)。
  OID.File =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  OID.Note =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  在头文件 nsfdata.h 中包含了下面的定义 ORIGINATORID 数据结构和 UNIVERSALNOTEID 数据结构:
  typedef struct {
  DBID F /* Unique (random) number */
  /* (Even though this field called \"File,\" */
  /* it doesn\'t have anything to do with the file!) */
  TIMEDATE N /* Original Note Creation time/date */
  /* (THE ABOVE 2 FIELDS MUST BE FIRST - UNID */
  /* COPIED FROM HERE ASSUMED AT OFFSET 0) */
  DWORD S /* LOW ORDER: sequence number, 1 for first version */
  /* HIGH ORDER WORD: flags, as above */
  TIMEDATE SequenceT/* time/date when sequence number was bumped */
  } ORIGINATORID;
  #define OID ORIGINATORID
  typedef struct {
  DBID F /* Unique (random) number */
  /* (Even though this field is called \"File,\" */
  /* it doesn\'t have anything to do with the file!) */
  TIMEDATE N /* Original Note Creation time/date */
  } UNIVERSALNOTEID;
  #define UNID UNIVERSALNOTEID
  文档的 Originator ID (OID) 确定了同一个文档(note)的所有复本。OID 由两部分组成:Universal Note ID (UNID) 和序列号(sequence number)、序列时间( sequence time)。 UNID 唯一的确定了同一个文档(note)的所有场合的复本。序列号(sequence number )和序列时间( sequence time) 放在一起区别同一文档(note)的不同版本。
  Universal note ID (UNID) 确定了驻留在所有上的同一个文档(note)。然而,UNID 缺少直接访问一个给定数据库中的文档(note)的信息。UNID 用于从一个文档来(note)引用另一个指定的文档(note)。答复文档中的\"$REF\" (FIELD_LINK) 域包含了其父文档的 UNID , DocLinks(参见nsfdata.h中的 NOTELINK 数据结构)包含了链接文档(note)的 UNID ,和链接视图的 UNID 以及链接文档所在数据库的 ID (ViewLinks 包含了相同的信息,不同的是链接文档的那部分全部设为0, 而 DatabaseLinks 包含的信息是链接文档和链接视图的部分全部设为0) 。UNID 的重要特征是它能总是确定同一个文档(),不论它是否更新过。
  UNID, the OID, 和复制器( Replicator)
  Universal Note ID (Originator ID的第一部分) 唯一的确定了同一文档(note)的所有版本和复本。如果两个文档(note)具有相同的UNID则它们互为复本。因此,相同文档(note)的所有复本的不同版本都有相同的 UNID。这就导出一个必然的结论:一个数据库中不能含有两个具有相同UNID的文档(note)。如果复制器(replicator)发现同一个数据库中两个文档(note)具有相同的UNID,它就会产生一个错误消息写到日志里,并且不对文档进行复制。
  完整的 Originator ID, 从另一个方面唯一地确定了一个文档(note)的一个特殊版本。就是说,一个文档的相同版本的复本具有相同的OID。同时,一个文档(note)复本修改后,它就会有不同的OID。因为在文档(note)被编辑后, Domino 和 Notes 会增加序列号(sequence number)和序列时间(sequence)。 当文档(note)的一个复本保持不变,而另一个复本被编辑并修改,于是这两个复本具有相同的 UNID但是序列号(sequence number)和序列时间(sequence times)不同,因此OID也不同。
  Domino 复制器(replicator)使用UNID 来匹配数据库中的文档(note),例如:如果数据库A和数据库B进行复制,数据库A中有个文档含有特殊的UNID,但是数据库B中没有,于是复制器(replicator)在数据库B中创建一个该文档的复本拷贝。
  如果数据库A中包含一个文档(note)同时数据库B中有个文档(note)和它有相同的UNID,复制器(replicator)推断这两个文档(note)是同一个文档的两个复本。这种情况下,复制器(replicator)继续检查两个文档的序列号(sequence number )和序列时间(sequence time),然后复制器(replicator)推断是否是同一时间更新过需不需要复制。如果序列号(sequence number )或序列时间(sequence time)其中有一个或两个都不同,复制器必须决定哪一个是最近更新的哪一个比较旧一点。
  如果其中一个更新过,而另一个未更新过,这样第一个复本的序列号会比第二个复本的序列号大,复制器(replicator)根据这种情况使用第一个复本覆盖第二个复本,从而达到两个数据库同步的目的。
  复制冲突
  复制冲突(Replication conflicts)发生在同时编辑并保存同一个文档(note)。如果用户修改了数据库A中的一个文档复本,而另一个数据库B中的文档复本也被修改(所作修改都在上一次成功复制之后,下一次复制之前),于是两个文档复本具有相同的序列号()但是序列时间不同。这种情况下,复制器产生一个复制冲突,因为一个文档的两个复本在同一时期都进行了修改。(如果把一个文档的多个复本看成是同一个文档的话,这就表示同一个文档同时被修改。)
  复制器通过生成复制冲突文档处理这种复制冲突。序列时间较早的文档(document)被标志为冲突文档。两个数据库中将会具有两个文档,只不过序列时间较早的文档会成为序列时间较晚的文档的答复文档。
  复制器产生复制文档冲突,会在冲突文档前标志黑色菱形标记。复制器把序列时间较晚的文档拷贝到序列时间较早的文档所在的数据库中,并完整的保持它的 OID。 然后复制器把序列时间较早的文档转成一个新的文档生成一个截然不同的 OID 并给它增加一个特殊的条目 \"$Conflict\" (_CONFLICT_ITEM) 。 这个 $Conflict 条目会使文档在视图的左边显示一个黑色的菱形标记,表示它是一个冲突文档。 复制器也会给这个冲突文档增加一个$REF 条目使他变成答复文档,$REF 条目中含有其父文档(序列时间较晚)的UNID。
  注意: 冲突文档(黑色菱形标记文档)并不总是立刻出现在两个服务器上。当拥有序列时间较晚文档的服务器发起复制时,冲突文档不会立刻在复制完成后出现在这个服务器上,但是会出现在那个拥有序列时间较早文档的服务器上。这是因为复制器仅在拥有序列时间较早文档的服务器上产生复制冲突文档(黑色菱形标记)。
  特殊地,当服务器B初始发起复制,首先服务器B从服务器A拉(PULL),然后服务器A从服务器B拉(PULL)。当服务器B从服务器A拉动改变时,B看到了A上的冲突文档,发现B上的文档较新(序列时间较晚),所以不会把A上的冲突文档拉到B上。这样做的理由是因为B已经是最新的文档了,不需要再取得旧的文档了。然后 A 从B拉动改变,看到B上的文档较新,因此A把自己的较旧的文档变成复制冲突(黑色菱形),并把B上的较新的文档拷贝到A上。这就满足复制的需要:使数据库保持最新的同步。于是冲突文档(较晚的)不会出现在B上。下一次服务器B和服务器A进行复制时,冲突文档(较晚的)就会出现同时出现在两个服务器上达到同步的目的。
  The OID and the API
  API 程序使用 NSFNoteGetInfo 来获得 Originator ID 的不同构件,可以指定 _NOTE_OID 标志位,例如:
  ORIGINATORID NoteOID;
  * Get the OID from the note AFTER it has been updated
  NSFNoteGetInfo (hNote, _NOTE_OID, &NoteOID);
  NSFNoteUpdate 导致 Domino 和 Notes 改变正在更新的文档的序列号(sequence number)和序列时间(sequence time)。 因此, API 程序特别注意他们调用 NSFNoteUpdate 和 NSFNoteGetInfo 的顺序。
  特别的,使用 NSFNoteCreate 创建一个新文档(note)获得文档的句柄后,直到这个文档保存到数据库中(使用 NSFNoteUpdate),NSFNoteGetInfo 才能返回有效的 OID。但是,既然这时 UNID 已经被赋值,所以 API 程序能够使用 NSFNoteGetInfo 分析并返回新建文档的 UNID 。
  UNID.File
  OID的文件号(File member )包含了一个号码,依赖于 Domino 或 Notes 的不同版本。 Notes 2.1之前的版本中,文件号表示数据库文件创建的时间和日期。Notes 2.1 版本设置文件号(File member)跟用户有关的唯一标志符,一部分取自创建文档的用户的ID,一部分取自文档所在的数据库。Notes 3.0 及以后版本文档创建后把文件号(File member)设置成一个随机的号码。
  UNID.Note
  OID的文档号(Note member)是文档创建的时间。 (详细信息参见数据结构 TIMEDATE )
  Global Note ID (GNID) and NOTEID (NID)
  Global Note ID (GNID) 由两部分组成:数据库 ID 和文档ID(Note ID)。既然 GNID 确定数据库和数据库中的文档,所以它可以唯一的确定所有数据库中所有文档的所有复本。
  GNID 出现在 ID 信息的最后一行(使用 Design - Document Properties信息框)。第一部分对应数据结构 GLOBALNOTEID 的文件部分(File member),第二部分对应数据结构 GLOBALNOTEID的 NoteID 部分。
  Global Note ID (GNID) =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  Database ID (GNID.File) =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  Note ID (GNID.NoteID) =
  ID: OF36C29F-ON86FB94
  SD07B8FA-SN
  DB867287-NT
  第三行开始是字符 \"DB\" (表示 \"Data Base\"),紧跟16个16进制字符,然后是连字符,然后是 \"NT\" (\"NoTe\"),跟着是8个16进制字符。在\"DB\" 后连字符前的16个16进制字符构成了 GNID的文件号(File member), \"NT\" 后的8个16进制字符构成 Note ID 。
  Global Note ID (GNID)
  不象 OID,GNID 不能区别同一文档的不同版本,因为 NoteID 和包含文档的文件有关,所以文档复本的 GNID 很可能不同。
  Database ID (GNID的文件部分)包含了数据库的复本ID(replica ID),API 头文件 nsfdata.h 定义 DBID 数据结构为 TIMEDATE类型:
  #define DBID TIMEDATE
  这个 8-byte DBID 包含了数据库原始创建的 TIMEDATE。你可以验证GNID的文件号(File member),显示在 File - Document 属性对话框,将会和数据库的 Replica ID相同,它显示在 File - Database 属性信息框。因为一个特殊数据库中的所有复本都有相同的 DBID,所以一个数据库中的所有复本数据库中的所有文档都有相同的 GNID.File.
  typedef struct {
  DBID F /* Creation Date/Time of NSF where note was created */
  NOTEID NoteID; /* Note\'s RRV in this file */
  } GLOBALNOTEID;
  #define GNID GLOBALNOTEID
  Note ID (NID)
  note ID (NID) 确定数据库中的一个文档。NID 是文档(note)的记录重布置向量(Record Relocation Vector (RRV))的文件位置。一个 RRV 是一个 DWORD 型的偏移量。 因为 note ID 有时会被描述为 \"the Note\'s RRV in this file.\",所以常会导致错误的理解。事实上,note ID 对于 RRV来讲是在文件中的偏移量,表示文档记录的入口点。RRV 是一个基本的数据结构,而 note ID 则更加明确。在 Domino 和Notes 内部,除了文档之外的其他不同对象也都有相关的 RRV。
  typedef DWORD RRV;
  typedef DWORD NOTEID;
  在一个数据库文件中,note ID 保证不会改变,除非这个文档被删除。当文档被删除时,note ID中的RRV_DELETED 标志位被设置。
  #define RRV_DELETED 0xL /* indicates a deleted note */
  因为 note ID 在数据库文件中是明确的,其他数据库中的同一文档的复本拷贝很可能会有不同的 note ID。 INSTANCEID (IID) Instance ID 表示给定数据库中的文档对象的实例。每次文档(note)被修改,Domino 或 Notes 使用时间和日期标志 instance ID。Instance ID 由文档修改的 TIMEDATE 和 note ID组成。
  typedef struct {
  TIMEDATE N /* Note\'s MODIFICATION date/time */
  NOTEID NoteID; /* Note\'s RRV */
  } INSTANCEID;
  #define IID INSTANCEID
  文档修改的 TIMEDATE (数据结构IID中的 Note 部分)和OID的修订时间不是相同的概念。数据库视图使用文档(note)的 IID 修改时间 来决定什么时候显示未读文档标志。你可以使用NSFNoteGetInfo 并指定 _NOTE_MODIFIED 标志位来访问IID修改时间。 复制器使用OID的修订时间(Revision Time)来比较不同数据库中文档的复本。 可以使用NSFNoteGetInfo 并指定 _NOTE_OID 标志位来访问OID修订时间。
  IID的 NoteID 部分是和GNID的 NoteID部分值相同。
  NSFNoteUpdate 每次 NSF 文件更新时更新修改时间,这个修改时间(modification timedate)控制视图显示未读文档标记。
  一个API程序有几种方式得到 IID ,从GNID 中取得Note ID,NIFReadEntries 缓冲区或者 SEARCH_MATCH数据结构的ID的NoteID 部分 。从SEARCH_MATCH数据结构的ID的NoteID 部分,或者调用 NSFNoteGetInfo 并指定 _NOTE_MODIFIED标志位来获取修改时间
  GLOBALINSTANCEID (GIID)
  Global Instance ID 是跨数据库的文档(note)实例。它包含了 Instance ID 的相同的部分并且增加了 database ID作为文件号。带有最近修改时间的文档是最新( \"most recent\")实例。
  typedef struct {
  DBID F /* database Creation time/date */
  TIMEDATE N /* note Modification time/date */
  NOTEID NoteID; /* note ID in database */
  } GLOBALINSTANCEID;
  #define GIID GLOBALINSTANCEID
  API 程序能够初始化一个 GIID 数据结构给文档,通过调用 NSFDbIDGet 来获得文件号,调用 NSFNoteGetInfo并指定_NOTE_MODIFIED 来获得对应于修改时间的部分。
(作者:来自网络责任编辑:McLaren)
欢迎在新浪微博上关注我们
办公软件IT新闻整机domino 中 UniversalID 和NoteID的区别_百度知道
domino 中 UniversalID 和NoteID的区别
提问者采纳
长度不同UNID是32-character&nbsplength(16进制数)NoteID是8-character&nbsplength(字母+数字,并且文档(note)修改时不会变化,
不管它(note)是位于何处或所处何时UniversalID 也被称作unique ID 或者UNID
唯一地确定了文档(note)。还有你如果想通过unid得到文档。NID
不包含数据库的信息(只在数据库内定位有效,互为副本的两个文档NoteID是不同的.另一方面,
每个文档(note)的复本拥有相同的
UNID.NoteID
确定给定数据库中的一个特殊的文档(note):译者注).getdocumentbyunid(unid)如果你想通过notesID找到文档则要用db,如NT)共享同一个UNID的文档互为副本而NoteID我觉得象一个文档在数据库的地址,用方法db,
不会因为文档的更改而变化
来自团队:
其他类似问题
为您推荐:
domino的相关知识
等待您来回答
下载知道APP
随时随地咨询
出门在外也不愁评奇酷大神Note3:ID无边框+指纹识别2.0_网易手机
评奇酷大神Note3:ID无边框+指纹识别2.0
大神Note3这款机型在千元机中有很多地方表现比较平凡,但还是有自己的突出之处,过年了,到底给父母家人购买一款什么样的手机,大神Note3只不过是为大家增加了一个选择项,至于这些手机能不能吸引住消费者,还要等待市场来检验。
2015年刚过没多久,大家翘首以盼的农历新年也马上到来,回家过年免不了需要带一些东西回家孝敬父母,而手机似乎也成为很多用户的首选。对于父母而言,智能机的功能再多,也不会发挥出最大的效果来,父母最多的也只是想要学会怎么使用一些社交软件在平常能够与自己的孩子常联系,那么千元机已然成为送给父母的首选。由于千元机的品类众多,而很多人在挑选时也面临着选择困难症,奇酷大神系列在千元机里口碑还算不错,今天小编刚刚拿到奇酷大神Note3,给大家做一个简单的评测,看看这款千元机是否值得大家入手。外观:5.5英寸屏幕,ID无边框设计此次大神Note3采用的是5.5英寸的高清显示屏,分辨率为,由于售价在千元左右,所以成本采用的方面能省则省,720p的分辨率基本上是所有千元机的标配了,Note3采用的720片显示屏中规中矩,没有太多争议的地方,也没有太出彩的地方。就显示效果来言,色彩还原度还是不错的,画面的细节表现也比较出色,屏幕最高也足够日常的使用,智能调节亮度的功能也是与其他手机一样带有,屏幕的整体虽说没什么突出之处,但是在细节方面的把控也算是可圈可点。大神Note3采用的ID无边框设计,所谓的ID无边框就是把正面的黑色玻璃悬浮在手机的中框上面,在手机熄屏时营造出一种无边框的感。在手机待机的情况下,大神Note3的屏幕外观还是比较简洁精致的,不过并不是真正的无边框设计,所以在亮屏之后,还是能够看得到屏幕两边的黑框的,不过ID无边框的设计也让大神Note3的屏幕外观相比其他的千元机更突出一些。屏幕的上方是以听筒为中心,传感器与摄像头分别位于听筒的左右两侧,呼吸灯位于传感器左侧。触控键是实体触控键,在风格上,也延续了奇酷的风格并没有做太大的改变,从左向右依次为菜单键,Ho键,返回键,触控键没有背光。手机屏幕上下以白色为基调,整个手机边框采用塑料材质将屏幕涵盖其中,降低手机因为摔落时造成碎屏的概率。大神Note3后壳为可拆卸塑料后壳,在如今千元机都拼命奔向金属机身的今天,大神Note3使用的塑料材质或许会得到一些对金属机身审美用户的垂青。虽然是塑料机身,但是塑料机身的设计使的手机质感十足,并没有塑料材质带有拖沓的感觉。机身的上方为摄像头,在摄像头左右两侧分辨是感光灯与麦克风控,指纹识别器位于摄像头下方。拆开机身外壳可以看到手机背后的两个SIM卡卡槽,扬声器也位于机身背后。大神Note3支持双卡双待,并且支持扩展存储,支持Nano-SIM卡与Micro-SIM两种格式,可惜不支持电池拆卸功能,如果支持的话相信对于续航能力带来质的飞升。手机顶端是耳机插孔,下风则是充电插孔与麦克风收音孔。手机的实体按键分别布局与手机的左右两侧,机身左侧为音量“+”“-”两键,机身的右侧则是电源键,按键舒适程度适中。大神Note3整体的设计非常符合年轻人的风格,虽然没有金属机身作为卖点,但是纯白色的机身加上优秀的设计使得手机在主观上感觉并不会太廉价,简洁的设计对于中老年人来言也不会太过于花哨。
本文来源:网易手机
作者:金箍棒_庞邺
责任编辑:韩一冰_NT3945
跟贴热词:
文明上网,登录发贴
网友评论仅供其表达个人看法,并不表明网易立场。
加载更多新闻
热门产品:   
:        
:         
热门影院:
阅读下一篇
用微信扫描二维码
分享至好友和朋友圈认证,查勇超
您的位置: →
认证,查勇超
目录一:云笔记简介 ............................................................................................................................... 11. 背景及简述 .......................................................................................................................... 12. 开发环境 ............................................................................................................................. 13. 功能描述 ............................................................................................................................. 1二:需求分析 ................................................................................................................................... 7三:数据库设计 ............................................................................................................................... 71. 有哪些表 .............................................................................................................................. 72. 表的作用 .............................................................................................................................. 73. 表之间的关联 ...................................................................................................................... 74. 表之间的先后顺序 .............................................................................................................. 8四:E-R图与类 ............................................................................................................................... 9五:具体设计 ................................................................................................................................. 101. 登陆与注册 ........................................................................................................................ 102. 添加笔记本 ........................................................................................................................ 123. 添加笔记 ............................................................................................................................ 134. 编辑笔记 ............................................................................................................................ 155. 删除笔记本、笔记 ............................................................................................................ 166. 收藏与分享笔记 ................................................................................................................ 17六:遇到的一些问题 ..................................................................................................................... 19七:云笔记 ................................................... 20八: ......................................................... 22一:云笔记简介1.背景及简述之前达内学员的使用的tts6有了简单的笔记功能,并且提供了简单的笔记分享,但是由于笔记内容随着时间的推移越来越多,那个笔记使用的架构趋于传统业务处理模型,这样导致系统没有办法应付如此大规模的笔记数据,并且笔记的分享能力有限,也无法做到笔记的随时随地可用吗,于是开发出了功能更完善的云笔记。2.开发环境Linux3.功能描述笔记本 :添加、删除、更改名称点击全部笔记本右侧的“+”号,会出现填写笔记本名字的对话框填写笔记名字后,点击创建,笔记本创建成功双击想要修改的笔记本,修改“笔记本”名字。1当“笔记本”下不存在笔记内容时,单击想要删除的笔记本,会出现“X”号。点击“X”号,会提示是否删除笔记本,点击“是”,笔记本将不进入回收站,直接删除。笔记 :添加、删除、更改名称、修改笔记内容、分享、收藏点击相应笔记本,会在右侧显示该“笔记本”下的所有笔记,点击相应笔记右侧的“+”号,创建“笔记名字”,填写完毕,点击保存,笔记创建成功。2点击对应的“笔记”,会在内容栏出现“对应笔记”的内容, “添加”或“修改”笔记内容。编辑结束,点击保存,笔记保存成功;不点击保存不予保存。点击相应笔记,会出现笔记状态,有“分享按钮”时为未公开的笔记。3点击“分享按钮”,会将笔记变为分享状态(分享后的笔记不能取消分享),此时笔记分享成功。点击相应笔记,在笔记标题右侧有“X”按钮,点击“X”按钮,会提示“是否删除此笔记?”,点击“是”,笔记进入“回收站”。回收站 :恢复笔记、彻底删除笔记点击“回收站”,会在笔记栏列出已经删除的 “笔记”,点击想要恢复的 “笔记”,点击标题右侧的“恢复”按钮,会弹出提示框,提示想要恢复到哪个“笔记本”,选择笔记本,点击回复,即可恢复。4点击“回收站”,会在笔记栏列出已经删除的 “笔记”,点击想要彻底删除的 “笔记”,点击标题右侧的“垃圾箱”按钮,会弹出提示框,提示确定要彻底删除笔记吗,点击是,笔记彻底删除。活动 :查看、参与在搜索共享笔记栏中,输入想要搜索的共享笔记关键字,会在“笔记栏”查询出共享笔记中符合查询条件的所有笔记。选中想要收藏的笔记,会在内容栏出现笔记内容,点击内容栏右侧的“收藏”按钮,会弹出“选择收藏笔记本”对话框,选择相应的笔记本,并点击“确定”,笔记收藏成功,笔记收藏后为共享状态,并且可以在本地“编辑”和“保存”。56二:需求分析在简介中已经说到云笔记的由来,由来中包含了它的一些需求,而在功能描述中也说到各个模块的功能,所以,它的需求分析的基本就是那些,如果要说地详细一点,那就是各个功能的具体细节,这个在后面的内容会说到。需求基本完善,就开始数据库设计。三:数据库设计1.有哪些表根据需求分析可以得知,它可以登录,登录之后可以有相关俄一些操作,所以,要有的表为:用户表、笔记本表、笔记本类型表、笔记表、笔记状态表、笔记类型表、笔记活动表、活动表、活动状态表、分享表。2.表的作用用户表记录用户信息。在登录、注册、查看笔记本、笔记时会用到。笔记本表记录笔记本信息。对笔记本进行操作的时候会用到。笔记本类型表记录笔记本类型。笔记本有不同的类型,就是通过这个表的字段设置的。笔记表记录笔记信息。笔记状态表记录笔记状态。正常笔记和删除的笔记的状态是不一样的,状态表反映了笔记的状态。笔记类型表记录笔记类型。笔记有不同的类型,就是通过这个表的字段设置的。笔记活动表记录笔记中的活动信息,或者说活动中的笔记信息。活动表记录活动信息。活动也是一个主体,可以对它进行一些操作。活动状态表记录活动状态,还未开始、进行、失效....分享表记录分享信息。笔记可以分享。3.表之间的关联通过第一点和第二点的说明,可以看到表之间的关联如下:74.表之间的先后顺序用户表,活动表,分享表用户表,笔记本表,笔记本类型表,笔记本状态表用户表,笔记表,笔记状态表,笔记活动表活动表,活动状态表,笔记活动表分享表,共享笔记表表之间的联系就是这样,联系反映的是表的先后顺序,建表的时候其实可以不完全按照那个顺序,因为没有用外键,只是表之间的字段有相互使用关系,插入数据的时候最好按照表之间的顺序插入,避免出错。8四:E-R图与类E-R图:类:用户表对应用户类
User笔记本表对应笔记本类
Notebook 笔记本类型表对应笔记本类型类 NotebookType 笔记表对应笔记类
Note笔记状态表对应笔记状态类
NoteStatus 笔记类型表对应笔记类型类
NoteType 笔记活动类对应笔记活动类
NoteActivity 活动表对应活动类
Activity活动状态表对应活动类
ActivityStatus 分享表对应活动类
Share9五:具体设计每个模块各个功能的实现都是一个可以细说的部分。1.登陆与注册登录:输入用户名与密码,进行验证。如果用户名和密码正确,则登录成功。因为登录页面是静态页面,所以登录的JS写在文件中,在JS中处理逻辑。核心代码:Dao:/*** 通过@MapperScannerConfigurer扫描目录中的所有接口, 动态在Spring Context中生成实现.* 方法名称必须与Mapper.xml中保持一致.** @author Meng Fanliang*/@MyBatisRepositorypublic interface UserMybatisDao {// 根据用户名密码查询用户信息public User getUserByLoginNamePsd(Map&String, Object& params);// 根据用户名密码查询用户public void createUser(User user);// 根据用户id重置密码public void updatePassword(User user);// 根据登录名查询用户public User getUserByLoginName(String cnUserName);}SQL:&mapper namespace=&com.tarena.bigdata.cloudnote.dao.UserMybatisDao&&&!-- 通过用户名获取用户: 输出直接映射到对象, 列名和字段名要进行处理,如:cn_user_id列要&as cnUserId&以方便映射 --&&select id=&getUserByLoginName& parameterType=&String&resultType=&com.tarena.bigdata.cloudnote.entity.User&&selectcn_user_id as cnUserId,cn_user_name as cnUserName,cn_user_password as cnUserPassword,cn_user_token as cnUserToken,cn_user_desc as cnUserDescfrom cn_userwhere cn_user_name=#{cnUserName}&/select&&/mapper&Service:/**10* 用户管理业务类.* @author YHT*/@Component(&userService&)@Transactionalpublic class UserService {private static Logger logger = LoggerFactory.getLogger(UserService.class);@Resource(name = &userMybatisDao&)private UserMybatisDao userMybatisD/*** 用户名密码验证* @Title: getUserByLoginNamePsd* @Time:日 上午10:47:57 YHT* @return User*/public User getUserByLoginNamePsd(String loginName, String pwd) {Map&String, Object& param = new HashMap&String, Object&();//封装dao层参数
param.put(&cnUserName&, loginName);//登录名param.put(&cnUserPassword&, Md5Utils.md5(pwd));//MD5加密的密码
logger.debug(&验证用户[&+param+&]&);User nowUser =//用于封装返回值nowUser = userMybatisDao.getUserByLoginNamePsd(param);//通过用户名密码查询用户信息return nowU}/*** 根据用户名查询用户(登陆名检查重复)* @Title: findUserByLoginName* @Time:日 上午10:47:11 YHT* @return User*/public User findUserByLoginName(String loginName) {User nowUser = userMybatisDao.getUserByLoginName(loginName);//通过登录名查询用户信息return nowU}注册://追加注册按钮事件处理$(function(){$(&#regist_button&).click(function(){//获取数据11var username = $(&#regist_username&).val();var nickname = $(&#nickname&).val();var password = $(&#regist_password&).val();//TODO 检查数据格式//发送ajax请求$.ajax({url:&http://localhost:8080/noteserver/user/regist.form&,data:{&cn_user_name&:username,&cn_user_desc&:nickname,&cn_user_password&:password},dataType:&json&,type:&post&,success:function(result){if(result.status==&1&){//用户名被占用$(&#warning_1&).html(result.msg).show();}else if(result.status==&0&){//成功alert(&恭喜您,注册成功&);$(&#back&).click();//触发返回按钮的单击事件
}},error:function(){alert(&很遗憾,注册失败&);}});});});2.添加笔记本点击全部笔记本右侧的“+”号,会产生响应动作,在edit.html中有对应的JS代码,然后引入一个添加的页面,也可以点击取消。核心代码:页面脚本://加载笔记本列表loadBookList();//给添加笔记本按钮追加单击事件$(&#add_notebook&).click(showAddBookWindow);//特殊事件绑定(动态事件绑定)$(&#can&).on(&click&,&#cancel_addbook&,closePopWindow);//给添加笔记本窗口中的创建按钮追加单击事件$(&#can&).on(&click&,&#sure_addbook&,sureAddNoteBook);具体JS://创建笔记本12function sureAddNoteBook(){//获取笔记本名称信息var bookName = $(&#input_notebook&).val().trim();var userId = getCookie(&userId&);//检测格式if(bookName==&&){$(&#bookname_msg&).html(&&font color='red'&不能为空&/font&&);}//发送ajax请求$.ajax({url:&http://localhost:8080/noteserver/notebook/add.form&,
type:&post&,data:{&cn_user_id&:userId,&cn_notebook_name&:bookName},dataType:&json&,success:function(result){if(result.status==&1&){//名称重复$(&#bookname_msg&).html(&&fontcolor='red'&&+result.msg+&&/font&&);}else if(result.status==&0&){//成功//关闭添加窗口closePopWindow();//将添加笔记本追加到列表中var bookId = result.//将原有笔记本列表中的li选中状态取消$(&#book_list li a&).removeClass(&checked&);//生成一个笔记本列表的li元素var $book_li = $(&&li class='online'&&a class='checked'&&i class='fa fa-book' title='online' rel='tooltip-bottom'&&/i&&+bookName+&&/a&&/li&&);$book_li.data(&bookId&,bookId);//给book_li元素绑定一组值//给li绑定单击事件$book_li.click(loadNotesByBookId);//将$book_li添加到笔记本列表中$(&#book_list&).prepend($book_li);}}});};3.添加笔记13点击全部笔记右侧的“+”号,会产生响应动作,在edit.html中有对应的JS代码,然后引入一个添加的页面,也可以点击取消。页面脚本://给添加笔记按钮追加单击事件$(&#add_note&).click(showAddNoteWindow);//给添加笔记窗口的取消按钮绑定单击事件$(&#can&).on(&click&,&#cancel_addnote&,closePopWindow);//给添加笔记窗口的创建按钮绑定单击事件$(&#can&).on(&click&,&#sure_addnote&,sureAddNote);JS代码://创建笔记操作//创建笔记按钮的操作function sureAddNote(){//获取客户端需要传递的数据var userId = getCookie(&userId&);var bookId = $(&#book_list a[class='checked']&).parent().data(&bookId&);
var noteName = $(&#input_note&).val().trim();//TODO 检测名称格式//发送ajax请求$.ajax({url:&http://localhost:8080/noteserver/note/add.form&,type:&post&,data:{&cn_notebook_id&:bookId,&cn_user_id&:userId,&cn_note_title&:noteName},dataType:&json&,success:function(result){//回调函数处理if(result.status==&0&){//正确closePopWindow();//关闭窗口//获取笔记的IDvar noteId = result.//将创建的笔记本添加到列表中var li = &&;li+=&&li class='online'&&;li+=&&a&&;li+=& &i class='fa fa-file-text-o' title='online' rel='tooltip-bottom'&&/i&&+noteName+&&button type='button' class='btn btn-default btn-xs btn_position btn_slide_down'&&i class='fa fa-chevron-down'&&/i&&/button&&;li+=&&/a&&;li+=&&div class='note_menu' tabindex='-1'&&;li+=& &dl&&;li+=&
&dt&&button type='button' class='btn14btn-default btn-xs btn_move' title='移动至...'&&i class='fa fa-random'&&/i&&/button&&/dt&&;li+=&
&dt&&button type='button' class='btn btn-default btn-xs btn_share' title='分享'&&i class='fa fa-sitemap'&&/i&&/button&&/dt&&;li+=&
&dt&&button type='button' class='btn btn-default btn-xs btn_delete' title='删除'&&i class='fa fa-times'&&/i&&/button&&/dt&&;li+=& &/dl&&;li+=&&/div&&;li+=&&/li&&;$li = $(li);//将li字符串转成jQuery对象$li.data(&noteId&,noteId);$(&#note_list&).append($li);//将li添加到笔记的ul中
//将当前li设置成选中$(&#note_list a&).removeClass(&checked&);$(&#note_list li:last a&).addClass(&checked&);//将笔记标题设置到编辑窗口$(&#input_note_title&).val(noteName);//将编辑区的内容清空um.setContent(&&);}}});};4.编辑笔记//给保存笔记按钮绑定单击事件$(&#save_note&).click(saveAddNote);//创建笔记操作function saveAddNote(){//获取请求需要提交的数据var noteName = $(&#input_note_title&).val().trim();var noteId = $(&#note_list a[class='checked']&).parent().data(&noteId&);
var noteBody = um.getContent();//TODO 格式检查(是否为空)//发送Ajax请求$.ajax({url:&http://localhost:8080/noteserver/note/update.form&,type:&post&,data:{&cn_note_id&:noteId,&cn_note_title&:noteName,&cn_note_body&:noteBody},dataType:&json&,success:function(result){//回调处理15if(result.status==&0&){//判断标题是否发生改变var li_noteName = $(&#note_list a[class='checked']&).text().trim();if(!(noteName==li_noteName)){//将li中的笔记标题改变var s = & &i class='fa fa-file-text-o' title='online' rel='tooltip-bottom'&&/i&&+noteName+&&button type='button' class='btn btn-default btn-xs btn_position btn_slide_down'&&i class='fa fa-chevron-down'&&/i&&/button&&;$(&#note_list a[class='checked']&).html(s);}//提示保存成功alert(result.msg);//var msg = &&font color='red'&&+result.msg+&&/font&&;//$(&#input_note_title_msg&).html(msg).hide(5000);//提示
}}});};5.删除笔记本、笔记删除笔记://删除笔记$(&#note_list&).on(&click&,&.btn_delete&,deleteNote);//笔记删除操作function deleteNote(){//获取当前选中的笔记livar $li = $(&#note_list a[class='checked']&).parent();var noteId = $li.data(&noteId&);//获取笔记ID//发送ajax请求$.ajax({url:&http://localhost:8080/noteserver/note/delete.form&,type:&post&,data:{&noteId&:noteId},dataType:&json&,success:function(result){if(result.status==&0&){//删除成功//将笔记li删除$li.remove();//清空编辑区显示的笔记信息$(&#input_note_title&).val(&&);um.setContent(&&);alert(&删除成功&);}16}});};删除笔记本:也是在页面脚本中增加相应代码,在JS文件中具体响应。 收藏与分享笔记分享://笔记分享按钮处理$(&#note_list&).on(&click&,&.btn_share&,shareNote);//分享笔记操作function shareNote(){//获取笔记IDvar $li = $(&#note_list a[class='checked']&).parent();var noteId = $li.data(&noteId&);//获取笔记ID//发送Ajax请求$.ajax({url:&http://localhost:8080/noteserver/note/share.form&,
type:&post&,data:{&noteId&:noteId},dataType:&json&,success:function(result){if(result.status==&0&){alert(&分享成功&);}else{alert(&分享失败&);}}});};搜索://笔记搜索$(&#search_note&).keydown(searchNote);//搜索笔记//为了支持火狐浏览器必须加event参数,再使用function searchNote(event){var code = event.keyCif(code==13){//回车事件//获取要传递参数var title = $(&#search_note&).val().trim();//发送ajax$.ajax({url:&http://localhost:8080/noteserver/note/search.form&,
type:&post&,17 6.data:{&title&:title},dataType:&json&,success:function(result){if(result.status==&0&){$(&#pc_part_2&).hide();//隐藏笔记列表$(&#pc_part_6&).show();//显示搜索列表//清除笔记列表内容$(&#share_list&).empty();//循环生成笔记列表for(i=0;i&result.data.i++){var share = result.data[i];var noteId = _note_//获取笔记ID
var noteName = _note_//获取笔记标题var li = &&;li+=&&li class='online'&&;li+=&&a&&;li+=& &i class='fa fa-file-text-o' title='online' rel='tooltip-bottom'&&/i&&+noteName+&&button type='button' class='btn btn-default btn-xs btn_position btn_slide_down'&&i class='fa fa-chevron-down'&&/i&&/button&&;li+=&&/a&&;li+=&&div class='note_menu' tabindex='-1'&&;
li+=& &dl&&;//li+=&
&dt&&button type='button' class='btn btn-default btn-xs btn_move' title='移动至...'&&i class='fa fa-random'&&/i&&/button&&/dt&&;li+=& &/dl&&;li+=&&/div&&;li+=&&/li&&;$li = $(li);//将li字符串转成jQuery对象
$li.data(&noteId&,noteId);$(&#share_list&).append($li);//将li添加到笔记的ul中}}}});}};收藏:这个功能暂时还没写。18六:遇到的一些问题在整个开发过程中,还是遇到过很多问题的。登录与注册的时候:1.因为静态页面和样式是给定的,然后老师按照页面的按钮添加动作,进行验证的时候使用已有的样式,但我没按照老师的来,而是自己写验证效果,出了一点小问题,效果出不来。2.登录的逻辑中,service那边的数据返回没有写好,导致登录失败。3.注册时,密码是要加密存入数据库的,用的是Base64加密算法,在插入数据时先要处理密码,是调用util包下的MessageUtil的方法,所以方法之间要正确调用,但我写的时候,因为没有完全跟上老师,所以加密出错。对笔记本和笔记的操作:1.添加笔记本和笔记的逻辑写好后时候,页面的上的按钮不能响应.取消也失败。2.当成功添加一个笔记本或笔记的时候,它可以被选中,但当鼠标点击其他列表后再点击那个刚创建的,它就不能被选中了.3.最开始加载笔记本列表和笔记列表出错,未能成功加载。4.当前选中笔记的下拉菜单有时出不来。5.点击一个笔记,应该把笔记标题显示在编辑框的标题中,当时没有分析清楚字段,所以SQL语句出错。6.给分享不能正确响应.分享一次后,还能再分享.19七:云笔记总结使用框架:Spring+Mybatis+bootstrap页面特点:都是静态页面。事件处理特点:1.分层开发表现层--》html(js,ajax)控制层--》SpringMVC DispatcherServelt,Controller 业务层--》Service (JavaBean)数据访问层--》MyBatis MapperDao2.所有请求一律采用Ajax方式发出HTML一律采用Ajax方式发送请求提交数据,
服务器端Controller处理完毕返回JSON结果3.服务器返回的JSON格式必须为{&status&:0,
//处理状态,0表示成功,其他失败
&msg&:&消息&,
//反馈消息&data&:数据
//反馈的数据}事件处理流程:就拿登录说吧;1.实现UserMapperDao组件(Spring+MyBatis)
--编写实体类--编写SQL定义的XML--编写UserMapperDao接口--配置SqlSessionFactoryBean,MapperScannerConfigurar
--测试UserMapperDao2.实现UserService--编写UserService接口--编写UserService实现组件--配置UserService(组件扫描,注入Dao)--测试Service3.实现LoginController--编写LoginController实现类--配置Controller(组件扫描,注入Service)4.配置设计好的请求和处理流程--在web.xml配置DispatcherServlet--在applicationContext.xml开启mvc注解配置20&mvc:annotation-driven/&支持@RequestMapping,@ResponseBody等标记--添加jackson系列jar包,用于对象和json字符串转换log_in.html(ajax)--&/user/login.form)--&DispatcherServlet--&HandlerMapping--&LoginController.execute--&UserService.checkLogin--&UserMapperDao.findByName--&返回约定的JSON结果所以,一个响应事件先在Dao组件中编写好SQL语句,service中实现相应接口,controller中实现相应逻辑,在XML中配置请求。页面中添加响应方法,JS文件中具体响应,发送请求,处理请求,返回结果,处理结果,在页面显示。分层:分层思想在这个项目中非常明显,不仅体现在处理逻辑上,也体现在建包,建文件上。 建包:按照mvc模式建包,一个逻辑对应一个包。一个包下再有文件,也是按照逻辑来的。 建文件:1个实体的处理逻辑建建一个JS文件,一个实体的SQL语句建一个XML,简单明了,容易分析与管理。所有引入的页面都放在一个文件中。通过这个项目,我更加认识到分层的重要性。21八:心得这个项目的开发,带给我很多。1.开发之前必须做好需求分析,否则会给开发带来很多麻烦,会不断改表,改逻辑,拖慢进度,使开发混乱。2.需求分析后还要详细的设计。使每一个细节逻辑通畅,通俗易懂,可以实行。3.然后是建表,建表要按照需求分析来,该有什么字段,字段又代表什么,一定要清楚。4.开发过程,要分层,对于一个功能,要明确处理逻辑,每一步应该怎么做。5.每一步都要测试,成功后才进行下一步,如果之间没有任何测试,而是到最后测试,则项目99%是失败的。测试中,如果失败,一定要问题,不要拖,因为前后逻辑有衔接,上一步失败,下一步也不会成功。6.需要一定的页面和样式功底。7.开发时,要习惯打桩,要有良好心态。8.代码之间的契合有时你都想不到,要遵守规则,否则很可能出不来效果。22
认证,查勇超相关文章
《》由(在点网)整理提供,版权归原作者、原出处所有。
Copyright &
All Rights Reserved.

我要回帖

更多关于 notes 的文章

 

随机推荐