??xml version="1.0" encoding="utf-8" standalone="yes"?>亚洲超碰97人人做人人爱,91精品在线免费视频,97在线观看视频http://www.aygfsteel.com/RongHao/category/19517.html心有多大Q舞台就有多?/description>zh-cnThu, 05 Apr 2007 22:32:57 GMTThu, 05 Apr 2007 22:32:57 GMT60Jackrabbbit数据源改为jndihttp://www.aygfsteel.com/RongHao/archive/2007/04/05/108765.htmlronghaoronghaoThu, 05 Apr 2007 10:44:00 GMThttp://www.aygfsteel.com/RongHao/archive/2007/04/05/108765.htmlhttp://www.aygfsteel.com/RongHao/comments/108765.htmlhttp://www.aygfsteel.com/RongHao/archive/2007/04/05/108765.html#Feedback0http://www.aygfsteel.com/RongHao/comments/commentRss/108765.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/108765.html需要jackrabbit-core.jarQjackrabbit-api.jar, jackrabbit-jcr-commons.jar三个包来替代Q另外,其要求Lucene 的版本要2.0Q下了个2.1不行?br>然后是攚w|文件?br>原先的配|?br>
        <PersistenceManager class="org.apache.jackrabbit.core.state.db.SimpleDbPersistenceManager">
        
<param name="driver" value="com.newatlanta.jturbo.driver.Driver"/>
        
<param name="url" value="jdbc:JTurbo://192.168.0.2:1433/bizfocus50"/>
        
<param name="schema" value="mssql"/>
        
<param name="user" value="sa"/>
        
<param name="password" value="sa"/>
        
<param name="schemaObjectPrefix" value="${wsp.name}_"/>
        
<param name="externalBLOBs" value="false"/>
    
</PersistenceManager>

现在的配|:
    <PersistenceManager class="org.apache.jackrabbit.core.persistence.db.JNDIDatabasePersistenceManager">
      
<param name="dataSourceLocation" value="java:comp/env/jdbc/wfmsDataSource" />
      
<param name="schemaObjectPrefix" value="DEFAULT_" />
      
<param name="externalBLOBs" value="false" />
  
</PersistenceManager>

q有是Q不要仅仅修改你ȝ那个配置文gQ每个工作区间下的配|文仉要同时修改,却记却记啊!


ronghao 2007-04-05 18:44 发表评论
]]>
什么是JAVA内容仓库(Java Content RepositoryQ?4?http://www.aygfsteel.com/RongHao/archive/2007/01/28/96417.htmlronghaoronghaoSun, 28 Jan 2007 15:55:00 GMThttp://www.aygfsteel.com/RongHao/archive/2007/01/28/96417.htmlhttp://www.aygfsteel.com/RongHao/comments/96417.htmlhttp://www.aygfsteel.com/RongHao/archive/2007/01/28/96417.html#Feedback2http://www.aygfsteel.com/RongHao/comments/commentRss/96417.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/96417.html获得列表
在上一步中我们已经把数据保存到了内容仓库中Q那我们如何定数据实保存q去了呢QgetBlogList() q个Ҏ返回根节点下所有名为blogEntry.的子节点?br />
public ArrayList getBlogList() throws BlogApplicationException {
    Session session 
= JackrabbitPlugin.getSession();
    ArrayList blogEntryList 
= new ArrayList();
    Node rootNode 
= session.getRootNode();
    NodeIterator blogEntryNodeIterator 
= rootNode.getNodes();

    
while (blogEntryNodeIterator.hasNext()) {
        Node blogEntry 
= blogEntryNodeIterator.nextNode();
        
if (blogEntry.getName().equals("blogEntry"== false)
            
continue;
        String title 
= blogEntry.getProperty("title").getString();
        String blogContent 
= blogEntry.getProperty("blogContent").getString();
        Value creationTimeValue 
= (Value) blogEntry.getProperty(
                
"creationTime").getValue();
        String userName 
= blogEntry.getProperty("userName").getString();
        BlogEntryDTO blogEntryDTO 
= new BlogEntryDTO(userName, title,
                blogContent, creationTimeValue.getDate());
        blogEntryList.add(blogEntryDTO);
    }
    
return blogEntryList;
}

一旦你获得了根节点q个对象Q你可以通过调用getNodes()q个Ҏ来获取它所有的子节炏V如果这个节Ҏ有子节点Q将q回一个空的NodeIterator 对象。我们可以遍历这个NodeIterator 对象来获得名为blogEntry 的节炚w合,然后通过getProperty()Ҏ来获得节点上的属性,x们保存的真实数据。getProperty()Ҏq回Value对象的一个实例。因为存储数据类型的不同Q所以返回的Value对象实例是不同的。根据不同的数据cdQ你应该调用特定的方法来获取数据Q比如getString()来获取字W串Q而getDate()获得一个日期?br />
查找内容Q用XPath的方式)
JSR-170定义了两U方式来查找内容Q也可以理解为查找节点)。一U用XPath语法Q另一U用SQL语法。JSR-170要求Level 1必须实现XPath的方式,而SQL的方式则作ؓ一个可选的功能?br />
XPath原本是一U设计用来查找XML元素的语a。因为我们的workspace是树状的l构Q很像XML。所以XPath语法非常适合于在q里查找内容。下面的代码演示了通过作者名来查找节炏V?br />
Session session = JackrabbitPlugin.getSession();
    Workspace workSpace 
= session.getWorkspace();
    QueryManager queryManager 
= workSpace.getQueryManager();

    StringBuffer queryStr 
= new StringBuffer(
            
"//blogEntry[@"+PROP_BLOGAUTHOR +"= '");
    queryStr.append(userName);
    queryStr.append(
"']");
    Query query 
= queryManager.createQuery(queryStr.toString(),
            Query.XPATH);

    QueryResult queryResult 
= query.execute();

    NodeIterator queryResultNodeIterator 
= queryResult.getNodes();
    
while (queryResultNodeIterator.hasNext()) {

        Node blogEntry 
= queryResultNodeIterator.nextNode();
        String title 
= blogEntry.getProperty(PROP_TITLE).getString();
        String blogContent 
= blogEntry.getProperty(PROP_BLOGCONTENT).getString();
        Value creationTimeValue 
= (Value) blogEntry.getProperty(
                PROP_CREATIONTIME).getValue();
        BlogEntryDTO blogEntryDTO 
= new BlogEntryDTO(userName, title,
                blogContent, creationTimeValue.getDate());
        blogEntryList.add(blogEntryDTO);
    }

首先获得session 对象Q通过它获得它q接的workspaceQ然后就可以通过workspace获得q个workspace的QueryManager 。QueryManager 接口定义了很多用来查询的Ҏ。接下来我们要做的是创徏一条查询语句。我们这里这样写"http://blogEntry[@blogAuthor='<bloggerName>'"。这句话的意思是查找所有名为blogEntry Q含有blogAuthor 属性且属性gؓ<bloggerName>的节炏V具体可以看JSR-170规范?br />
通过queryManager's createQuery()Ҏ创徏一个查询对象,q个Ҏ需要两个参敎ͼ一个是我们的查询语句,另一个是查询的方式,q里使用XPath。获得这个Query 查询对象后,调用它的execute() Ҏ开始执行查询,q回一个QueryResult 对象。注意,查询的结果受到当前session的限Ӟ换句话说Q就是如果这个session没有权限查看一个特定的节点Q哪怕这个节Ҏx们查询的条gQ在我们的查询结果里也是看不到这个节点的。所有的查询数据来自于该workspace已经持久化的数据Q哪些已l改变但q没有通过session.save()(item.save())持久化到workspace的数据不在查询之列。获得QueryResult 对象后,我们可以通过调用getNodes()Ҏ来获得符合查询条件的节点的一个遍历?br />
剩下的两个未实现的方法是updateBlogEntry() ?removeBlogEntry()Q它们实现v来都很简单。我们把BOLG 标题作ؓ主键Q通过标题来获得相关的节点。在updateBlogEntry()Ҏ里,我们直接讑֮需要改变的属性;?removeBlogEntry()Ҏ里,我们获得目标节点后直接在节点上调用remove()Ҏ。最后别忘了一定要调用session.save()Ҏ把我们改变的数据持久化?br />
处理二进制内?/b>
对内容仓库来_处理二进制内Ҏ个很基本的要求,比如说图片。现在我们的CZE序容许l每个BLOG附加一张图片。下面分别是附加囄和获取图片的Ҏ?br />
public void attachFileToBlogEntry(String blogTitle,
  InputStream uploadInputStream) 
throws BlogApplicationException {
    Session session 
= JackrabbitPlugin.getSession();
    Node blogEntryNode 
= getBlogEntryNode(blogTitle, session);
    blogEntryNode.setProperty(PROP_ATTACHMENT, uploadInputStream);
    session.save();

}
public InputStream getAttachedFile(String blogTitle) throws BlogApplicationException {
    InputStream attachFileIS 
= null;
    Node blogEntryNode 
= getBlogEntryNode(blogTitle);
    Value attachFileValue 
= (Value) blogEntryNode.getProperty(PROP_ATTACHMENT).getValue();
    attachFileIS 
= attachFileValue.getStream();
  
return attachFileIS;
}

正如你看到的那样Q我们的代码在处理二q制内容和一般内定wq没有什么太大的区别。仅仅一点不同的是你要通过InputStream 对象来保存和获取二进制数据。在我们的配|文仉关于persistent manager会有一个externalBLOBs 属性。把q个属性设为true, 囄会保存在文仉Q相反则会保存在数据库的blob字段里?br />
ȝ
到这里,我们?JSR-170, Jackrabbit以及如何使用 JSR-170 API开发一个简单的应用E序都有了大概的了解。我们的讨论更多的在于基。相信大家一定会对内容仓库有个初步的认识?img src ="http://www.aygfsteel.com/RongHao/aggbug/96417.html" width = "1" height = "1" />

ronghao 2007-01-28 23:55 发表评论
]]>
什么是JAVA内容仓库(Java Content RepositoryQ?3)http://www.aygfsteel.com/RongHao/archive/2007/01/25/96065.htmlronghaoronghaoThu, 25 Jan 2007 15:12:00 GMThttp://www.aygfsteel.com/RongHao/archive/2007/01/25/96065.htmlhttp://www.aygfsteel.com/RongHao/comments/96065.htmlhttp://www.aygfsteel.com/RongHao/archive/2007/01/25/96065.html#Feedback0http://www.aygfsteel.com/RongHao/comments/commentRss/96065.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/96065.html开发我们的例子E序
jackrabbit已经配置好了Q现在让我们来创建我们的CZE序。这个例子程序将调用JCR-170 API。很昄Q我们需要做两g事情Q一个是作ؓ后台的对数据q行增删ҎQ持久层Q,另一个是开发相对应的UI界面QWEB 层)。首先,让我们定义一个DAO接口。这个接口BlogEntryDAO.java 如下Q?br />
public interface BlogEntryDAO {
    
public void insertBlogEntry(BlogEntryDTO blogEntryDTO)
        
throws BlogApplicationException;
    
public void updateBlogEntry(BlogEntryDTO blogEntryDTO)
        
throws BlogApplicationException;
    
public ArrayList getBlogList()
        
throws BlogApplicationException;
    
public BlogEntryDTO getBlogEntry(String blogTitle)
        
throws BlogApplicationException;
    
public void removeBlogEntry(String blogTitle)
        
throws BlogApplicationException;
    
public ArrayList searchBlogList(String userName)
        
throws BlogApplicationException;
    
public void attachFileToBlogEntry(String blogTitle, InputStream uploadInputStream)
        
throws BlogApplicationException;
    
public InputStream getAttachedFile(String blogTitle)
        
throws BlogApplicationException;
}

正如你看到的Q这个接口提供了增删Ҏ的方法,同时q提供了两个Ҏ来处理附件。接下来Q我们需要一个DTO对象用来在两个层之间传递数据?br />
public class BlogEntryDTO {

    
private String userName;
    
private String title;
    
private String blogContent;
    
private Calendar creationTime;

    
//Getter and setter methods for each of these properties        
}

q里我们仅仅讨论持久层?br />
q接jackrabbit
现在Q第一件事情是开发一个组Ӟ获得一个到jackrabbit内容仓库的连接。ؓ了简单,我们在E序启动的时候获得这个连接,然后在程序停止的时候释放这个连接。这里我们用了Struts Q所以我们需要开发一个PlugIn cR如下:
public class JackrabbitPlugin implements PlugIn{
    
public static Session session;
    
public void destroy() {
        session.logout();
    }
    
public void init(ActionServlet actionServlet, ModuleConfig moduleConfig) 
    
throws ServletException {
        
try {
            System.setProperty(
"org.apache.jackrabbit.repository.home",
                
"c:/temp/Blogging");
            Repository repository 
= new TransientRepository();
            session 
= repository.login(new SimpleCredentials("username",
                    
"password".toCharArray()));
        } 
catch (LoginException e) {
            
throw new ServletException(e);
        } 
catch (IOException e) {
            
throw new ServletException(e);
        } 
catch (RepositoryException e) {
            
throw new ServletException(e);            
        }
    }
    
public static Session getSession() {
        
return session;
    }
}

init()Ҏ会在程序启动的时候调用,destroy()会在程序停止的时候调用。我们在init()Ҏ里获得了到jackrabbit内容仓库的连接。看看代码,我们做的W一件事是设定了org.apache.jackrabbit.repository.homeq个pȝ属性,在上文章里提到Q这个属性是用来指向我们的内容仓库主目录。这里我们设定它为c:/temp/blogging。接下来Q我们创ZTransientRepository的一个实例。这是jackrabbit提供的类Q它提供了一个到内容仓库的代理。它在第一个session 打开的时候自动启动内容仓库,在最后一个session 关闭的时候自动关闭内容仓库?br />一旦我们获得了一个内容仓库对象,我们可以调用它的login() Ҏ来打开一个连接。login() Ҏ需要一个Credential 对象作ؓ参数。如果Credential 对象是NULLQjackrabbit会认为其他的机制做了q个验证Q比如JAASQ。login() Ҏq可以传入一个workspace名字作ؓ参数Q如果不传入q个参数Qjackrabbit会返回一个session对象指向默认的workspace。注意workspace和session是一对一的,即一个session仅对应一个workspace。(注:如果不传入Credential对象Q返回的session对workspace是只ȝQ?br />
增加内容
q接已经建立h了,下面让我们实现BlogEntryDAOq个接口。第一个我们想实现的方法是插入数据 insertBlogEntry()
public void insertBlogEntry(BlogEntryDTO blogEntryDTO)
            
throws BlogApplicationException {
        Session session 
= JackrabbitPlugin.getSession();
        Node rootNode 
= session.getRootNode();
        Node blogEntry 
= rootNode.addNode("blogEntry");
        blogEntry.setProperty(
"title", blogEntryDTO.getTitle());
        blogEntry.setProperty(
"blogContent", blogEntryDTO.getBlogContent());
        blogEntry.setProperty(
"creationTime", blogEntryDTO.getCreationTime());
        blogEntry.setProperty(
"userName", blogEntryDTO.getUserName());            
        session.save();
}

首先获得session 对象Q即到内容仓库特定workspace的连接。然后,我们在这个session 对象上调用getRootNode() ҎQ获得这个workspace的根节点Q这个根节点的\径是Q?/"Q?一旦我们获得这个根节点Q我们就可以通过addNode()Ҏ在这个根节点下增加新的子节点。新节点的名字是blogEntry. 通过setProperty() Ҏ我们把数据存储到节点的property里。正如我们先前说明的Q真实的数据是存储在property元素里,property元素是叶子?br />注意session.save() q行代码。这个方法是必须调用的,q个Ҏ调用之前QQ?Node,Property的改变都被保存在q个session的一个时区域里Q其他的和该sessionq接到相同workspace的session都看不到q些改变。当q个Ҏ被调用ƈ被成功执行后Q这些Node,Property的改变才会被持久化到q个session兌的workspace里,同时所有与q个workspace兌的session才可见这些变化。相对应的,Session.refresh(false)会丢弃所有这些改变。item.save()和Item.refresh(false)作用怼Q只是媄响范围限定在单个Item上(注意Q包括它的子节点Q?img src ="http://www.aygfsteel.com/RongHao/aggbug/96065.html" width = "1" height = "1" />

ronghao 2007-01-25 23:12 发表评论
]]>
什么是JAVA内容仓库(Java Content RepositoryQ?2)http://www.aygfsteel.com/RongHao/archive/2007/01/23/95637.htmlronghaoronghaoTue, 23 Jan 2007 15:57:00 GMThttp://www.aygfsteel.com/RongHao/archive/2007/01/23/95637.htmlhttp://www.aygfsteel.com/RongHao/comments/95637.htmlhttp://www.aygfsteel.com/RongHao/archive/2007/01/23/95637.html#Feedback2http://www.aygfsteel.com/RongHao/comments/commentRss/95637.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/95637.html内容仓库模型
JSR-170 是这样定义内容仓库的Q内容仓库由一l?workspaceQ工作空_l成Q这些workspace通常应该包含怼的内宏V一个内容仓库有一个到多个 workspace。每个workspace都是一个树状结构,都有一个唯一的树根节点(root nodeQ。树上的itemQ元素)或者是个nodeQ节点)或者是个propertyQ属性)。每个node都可以有零个到多个子节点和零个到多个子属性。只有根节点没有父节点,其余所有的节点都有一个父节点。property 也必L一个父节点Q但它没有子节点或是子属性,property 是叶子元素。property是真正存储数据的元素?br />
下图描述了一个blog应用E序的内容仓库模型。每个root nodeQ根节点Q的子节炚w代表了一个blog实体。与q个blog实体有关的数据都存储?bolgEntry 节点的属性里Q其中一?blogAttachment property 存储了一个二q制囄文g?br />repositorymodel3.gif
Ҏ内容仓库实现的功能,JSR-170定义了三U别:
Level 1Q定义了一个只ȝ内容仓库。功能包括读取内容,内容导ZؓXML和查扑ֆ宏V?br />Level 2Q定义了可写的内容仓库。Level 2是Level 1的扩展,新增的功能包括往内容仓库里写入内容,和从XML导入数据C库?br />Advanced optionsQ定义实CU附加功能,版本控制、JTA、SQL查询、清晰的内容锁定和监视?br />
什么是Apache JackRabbitQ?/b>
Apache JackRabbit是一个开放源码的JSR-170 实现Q实CLevel 2Q但它还有许多扩展的功能。详l可以去它的官方|站?br />
下面我们军_用Apache JackRabbit来作为我们示例程序的内容仓库?br />
如何配置Apache JackRabbit
JackRabbit需要两个参数来配置一个内容仓库实例?br />1.内容仓库ȝ录:q个文g目录下通常包含了所有的内容Q搜索烦引,内部配置文g和其他持久化信息。它的结构看h会像下面q个样子Q?br />
   c:/temp
        
|
        
|--Blogging
                
|
                
|-repository
                
|       |
                
|       |-index
                
|       |-meta
                
|       |-namespaces
                
|       |-nodetypes             
                
|
                
|-version
                
|
                
|-workspace
                        
|
                        
|--default

  在上面的情况下,内容仓库ȝ录是c:/temp/Blogging.
2.内容仓库配置文gQ一个典型的配置文g如下Q?br />
<Repository>
 
<FileSystem class="org.apache.jackrabbit.core.fs.local.LocalFileSystem">
  
<param name="path" value="${rep.home}/repository"/>
 
</FileSystem>
 
<Security appName="Jackrabbit">
  
<AccessManager class="org.apache.jackrabbit.core.security.SimpleAccessManager"/>
  
<LoginModule class="org.apache.jackrabbit.core.security.SimpleLoginModule">
    
<param name="anonymousId" value="anonymous"/>
  
</LoginModule>
 
</Security>
 
<Workspaces rootPath="${rep.home}/workspaces" defaultWorkspace="default"/>
 
<Workspace name="${wsp.name}">
  
<FileSystem class="org.apache.jackrabbit.core.fs.local.LocalFileSystem">
   
<param name="path" value="${wsp.home}"/>
  
</FileSystem>
  
<PersistenceManager 
        
class="org.apache.jackrabbit.core.state.db.DerbyPersistenceManager">
   
<param name="url" value="jdbc:derby:${wsp.home}/db;create=true"/>
   
<param name="schemaObjectPrefix" value="${wsp.name}_"/>
  
</PersistenceManager>
  
<SearchIndex class="org.apache.jackrabbit.core.query.lucene.SearchIndex">
   
<param name="path" value="${wsp.home}/index"/>
  
</SearchIndex>
 
</Workspace>
 
<Versioning rootPath="${rep.home}/version">
  
<FileSystem class="org.apache.jackrabbit.core.fs.local.LocalFileSystem">
   
<param name="path" value="${rep.home}/version" />
  
</FileSystem>
  
<PersistenceManager 
        
class="org.apache.jackrabbit.core.state.db.DerbyPersistenceManager">
   
<param name="url" value="jdbc:derby:${rep.home}/version/db;create=true"/>
   
<param name="schemaObjectPrefix" value="version_"/>
  
</PersistenceManager>
  
</Versioning>
  
<SearchIndex class="org.apache.jackrabbit.core.query.lucene.SearchIndex">
   
<param name="path" value="${rep.home}/repository/index"/>
  
</SearchIndex>
</Repository>

 
  在这个配|文仉Q?lt;Repository>元素是根元素Q它包含了下面这些元素:
  aQ?lt;FileSystem>: 该元素配|了内容仓库的全局数据存储位置Q这些全局数据包括已注册的命名I间Q定制的节点cd{等。  ?    JackRabbit 提供了几U选择Q一U是像上面例子里配置的存储在本地文g里,LocalFileSystem. 如果你想把它们存储在数据库里Q你可以使用 DbFileSystem.
  bQ?lt;Security>:内容仓库的安全配|,它有两个子元素:<AccessManager>?lt;LoginModule>?lt;AccessManager>配置的类用来判断用户有没有权限来对特定数据执行特定的操作?br />  cQ?lt;Workspaces>:q个元素的配|对所有的workspace都通用。它的rootPath 属性是所有workspace文g夹的根目录,在我们的例子里它是c:/temp/Blogging/WorkspaceQdefaultWorkspace 属性则包含了workspace的默认名?br />  dQ?lt;Workspace>:q个元素是所有workspace的默认配|模ѝ去每个workspace文g夹下你都会发C个workspace.xml文gQ这个文件和q个元素的配|一模一栗三个子元素Q?lt;FileSystem>Q和q个workspace相关数据的存储位|;<PersistenceManager> Q这个workspace内容节点存储{略Q?lt;SearchIndex>Q可选,全文索?br />  eQ?lt;Versioning>:配置一个版本相关的对象。其实JackRabbit也是把它作ؓ节点来处理的?br />
q两个参数可以通过两种方式讄Q一U是在仓库实例创建时直接传到Jackrabbit里去Q一U是间接的通过讄JNDI object factory?br />你可以设|org.apache.jackrabbit.repository.home q个pȝ属性的值来指定你的内容仓库ȝ录;也可以设|?br />org.apache.jackrabbit.repository.conf q个pȝ属性的值来指定你的内容仓库配置文grepository.xml。如果你不设定这两个
参数QJackrabbit会把当前目录作ؓ内容仓库ȝ录,同时Q它有一个默认的内容仓库配置文g?img src ="http://www.aygfsteel.com/RongHao/aggbug/95637.html" width = "1" height = "1" />

ronghao 2007-01-23 23:57 发表评论
]]>
什么是JAVA内容仓库(Java Content RepositoryQ?1)http://www.aygfsteel.com/RongHao/archive/2007/01/23/95547.htmlronghaoronghaoTue, 23 Jan 2007 07:13:00 GMThttp://www.aygfsteel.com/RongHao/archive/2007/01/23/95547.htmlhttp://www.aygfsteel.com/RongHao/comments/95547.htmlhttp://www.aygfsteel.com/RongHao/archive/2007/01/23/95547.html#Feedback1http://www.aygfsteel.com/RongHao/comments/commentRss/95547.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/95547.htmlJSR-170把自己定义ؓ一个能与内容仓库互相访问的Q独立的Q标准的方式。同时它也对内容仓库做出了自q定义Q它认ؓ内容仓库是一个高U的信息理pȝQ该pȝ是是传统的数据仓库的扩展Q它提供了诸如版本控制、全文检索,讉K控制Q内容分cR访问控制、内容事件监视等内容服务?br />
Java Content Repository  APIQJSR-170Q试囑־立一套标准的API去访问内容仓库。如果你对内容管理系l(CMSQ不熟悉的话Q你一定会对内容仓库是什么感到疑惑。你可以q样ȝ解,把内容仓库理解ؓ一个用来存储文本和二进制数据(囄Qword文档QPDF{等Q的数据存储应用E序。一个显著的特点是你不用兛_你真正的数据到底存储在什么地方,是关pL据库Q是文gpȝQ还是XMLQ不仅仅是数据的存储和读取,大多数的内容仓库q提供了更加高的功能,例如讉K控制Q查找,版本控制Q锁定内容等{?br />
一D|间以来市Z出现了各个厂家开发的不同的CMSpȝQ这些系l都建立在他们各自的内容仓库之上?br />问题出现了,每个CMS开发商都提供了他们自己的API来访问内容仓库。这对应用程序的开发者带来了困扰Q因Z们要学习不同的开发商提供的APIQ同Ӟ他们的代码也与这些特定的API产生了绑定?br />
JSR-170正是册一问题而出现的Q它提供了一套标准的API来访问Q何数据仓库。通过JSR-170Q你开发代码只需要引?javax.jcr.* q些cd接口。它适用于Q何兼容JSR-170规范的内容仓库?br />
我们通过一个例子来逐步了解JSR-170?br />
Z么需?Java Content Repository API

随着各个厂家各自的内容仓库实现数量的增长Qh们越来越需要一l通用的编E接口来使用q些内容仓库Q这是JSR-170所要做的东ѝ它提供一l通用的编E接口来q接内容仓库。你可以把JSR-170理解为和JDBCcM的APIQ这样你可以不依赖Q何具体的内容仓库实现来开发你的程序。你可以直接使用支持JSR-170的内容仓库;或者如果一些厂家的内容仓库不支持JSR-170则可以通过q些厂家提供的JSR-170驱动来完成从JSR-170与厂家特定的内容仓库的{换?br />
下面q张图描qC使用JSR-170开发的应用pȝ的结构。在该系l运行的时候,它可以操作内容仓?Q?Q?中的L一个。在q些内容仓库当中Q只?是直接支持JSR-170的,剩下的两个都需要JSR-170驱动来和应用pȝ交互。注意:你的应用pȝ完全不用兛_你的数据是如何存储的?可能使用了关pL据库来存储,?使用了文件系l,至于上,它甚x前卫的用了XML?br />
repositorymodel1.gif

JSR-170 API对不同的人员提供了不同的好处?br />
●对于开发者无需了解厂家的仓库特定的APIQ只要兼容JSR-170可以通过JSR-170讉K其仓库?br />●对于用CMS的公司则无需p资金用于在不同种cCMS的内容仓库之间进行{换?br />●对于CMS厂家Q无需自己开发内容仓库,而专注于开发CMS应用?img src ="http://www.aygfsteel.com/RongHao/aggbug/95547.html" width = "1" height = "1" />

ronghao 2007-01-23 15:13 发表评论
]]>
使用freemarkerlcms生成静态htmlhttp://www.aygfsteel.com/RongHao/archive/2006/11/27/83858.htmlronghaoronghaoMon, 27 Nov 2006 10:51:00 GMThttp://www.aygfsteel.com/RongHao/archive/2006/11/27/83858.htmlhttp://www.aygfsteel.com/RongHao/comments/83858.htmlhttp://www.aygfsteel.com/RongHao/archive/2006/11/27/83858.html#Feedback3http://www.aygfsteel.com/RongHao/comments/commentRss/83858.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/83858.html考虑一个内容节点Content,其中节点有个pagecontent的属性,q个属性用来存储用户在后台输入的内容,
内容+模板=昄Q这里是Q?br />内容+模板-->昄静态html
内容用FCK来编辑,模板也同LFCK~辑Q这里用freemarker无疑是一个好的选择。这里是个最单的例子?br />首先定义一个最单的模板content.ftl
<html>
$
{content}
</html>
然后是把内容填充进去:
 Configuration cfg = new Configuration();
 
//模板存储的目?/span>
 cfg.setDirectoryForTemplateLoading(Path.getTemplateDirectory());
 
//默认
 cfg.setObjectWrapper(new DefaultObjectWrapper());
//填充数据        
Map root = new HashMap();
root.put(
"content", c.getPageContent());
     Template temp 
= cfg.getTemplate("content.ftl");
//发布日期
String date=c.getActivedate();
String filename 
= c.getId()+".html";
//创徏目录
Path.createFold(Path.getWebCmsHtmlDirPath(),date);
Writer out 
= new OutputStreamWriter(new FileOutputStream(Path.getWebCmsHtmlDirPath()+"/"+date+"/"+filename));
temp.process(root, out);
out.flush();
其实是q么单!对html的管理就很容易了Q基本的FILE操作

ronghao 2006-11-27 18:51 发表评论
]]>
开始开发EQShttp://www.aygfsteel.com/RongHao/archive/2006/11/16/81638.htmlronghaoronghaoThu, 16 Nov 2006 14:55:00 GMThttp://www.aygfsteel.com/RongHao/archive/2006/11/16/81638.htmlhttp://www.aygfsteel.com/RongHao/comments/81638.htmlhttp://www.aygfsteel.com/RongHao/archive/2006/11/16/81638.html#Feedback6http://www.aygfsteel.com/RongHao/comments/commentRss/81638.htmlhttp://www.aygfsteel.com/RongHao/services/trackbacks/81638.html1.很多CMS都包括了发布模板、显C模板,q里不用考虑QCMS仅仅是内容管理,负责内容存储Q至于展玎ͼ那是门户事情Q内容和展现分开QCMS作ؓ门户数据源的一个选择Q?br />2.一个完整的CMSq不是作Z个所谓的栏目信息Q它q必d括对各种文g的保存.Ҏ个^台的文g和附件进行统一理
3.版本理
4.全文?br />5.权限理Q具体到每一个节点的配置Q不仅仅是在CMS内部Q用户通过门户看到的信息也是要l过权限qoQ内|门P
6.一套可扩展的组l用h口(目前是直接用q_内部的组l用P考虑到CMS来的独立性,q个也是必要的)
7.文g的webdav支持
大概是q些了,已初步完成了对jcr的封装和架构Q感到spring有劲使不上,呵呵Q?br />CMS信息发布需?br />信息分两U:未发布的和发布的
1、未发布的信息可以进行增删改查、版本管理、上传和下蝲附g
2、将未发布的信息发布Q信息的状态将|ؓ发布状态同时结合模板生成静态HTML
3、发布的信息本n会增加一个对静态HTNL联接的属性,在后台即可以寚w态HTMLq行览
4、发布的信息依旧可以q行内容修改和版本恢复,q样会将生成的静态HTML删除然后再重新生?br />5、发布的信息可以删除Q信息进入回收站Q静态HTML同时被删?br />6、从回收站恢复信息,信息重新发布Q生成静态HTML
7、通过栏目的设|来军_信息的发布是直接发布q是通过工作发?img src ="http://www.aygfsteel.com/RongHao/aggbug/81638.html" width = "1" height = "1" />

ronghao 2006-11-16 22:55 发表评论
]]>
վ֩ģ壺 | | ³ƶ| | | | żҿ| | | Dz| ɳ| | | ɽ| ɽ| | | | ɽ| ͼ| Ӫ| | | | | ݳ| Ͽ| ں| Ī| | Ϫ| | ۶| | | | | Դ| | | |