全国特有的培训方式Youth私塾--Android班

by sundy 8/30/2010 11:30:00 AM
1. ---前言 :
程序员的心声:

为何没有针对刚刚工作的,经验少于两年的程序员的再提升和高薪就业培训 ?

为何没有针对让程序员成为共享软件作者的培训,帮助程序员去跟进新技术的过程获利 ,更好的激发对新技术的热情?

为何没有高品质的程序员圈子,将志趣相投的一帮程序员聚集在一起,大家相互交流技术,分享经验,提供资源?

为何周围遇不到真正的“高手”来带自己?

............

程序员最了解程序员的心声

Youth私塾帮助程序员解决自己想过而又困惑多年的问题 :

Youth私塾Android班的“工友”也即是学员,经过三个月的付出,将真正得到如下的帮助 :

a) 掌握Android开发及养成良好的Android开发习惯

b) 享有Android Market账号,并且上传自有作品,开始Shareware之路

c) 学会共享软件走向海外的真正方式,并且开始尝试,有望再过3个月,月入500美元以上 。

d) 加入成都Android开发联盟,成为联盟“工友”,享有私有聚会权及海外项目接包机会 。

e) 推荐更好的从事Android开发工作,并且保证薪水不低于4000/M(成都地区),其它地区当面沟通 。

f) 认识圈内的Android资源,并且积极的享受Android之路 。

g) 享受Youthdeal Android商城的Android手机,平板电脑,电纸书的购物会员卡 。

---讲师:

张老师:

7年自由职业者 ,电子商务及移动应用的观察者,实施者,隐士 。 12年开发,8年移动开发,7年电子商务经验 .8年IT项目管理经验 , 带领超过70人的技术团队规模。

优秀的讲师及团队培养者 。做过超过30起企业培训,培训企业覆盖中国移动,中国电信,中国邮政 , Ixonos , Teleca , NCS,白象集团 ,省委组织部, 等各种类型企业及政府单位 。 同时做了2年高职教育 ,培养学生人次超过1000人 。

使用语言:Perl , Python, Delphi ,php  ,c/c++ , C# , Java ,

目前常用领域:移动开发,.电子商务,企业大型应用软件构架研究 。

移动平台开发经验:Palm , BREW , Symbian , J2ME , NDSL , Android

周老师:

6年Linux开发经验,4年手机开发经验。精通Linux C/C++编程, Perl, Python.精通Symbian 手机应用开发。2年Android开发经验。

曾在Intel, Nokia工作,具有海外工作经验。著有《深入浅出Google Android》,多年的移动开发培训经验。包括为芬兰公司Planware做新员工Linux开发培训,为芬兰公司IXONOS的新入职员工做Symbian培训等等。

使用语言:Perl , Python ,c/c++ , java .

目前专注领域:移动通讯开发

移动平台开发经验:Palm , Symbain , Moto Linux ,Android

---开课时间:

9月23日 – 秋分 宜:祭祀,修墳,涂泥,餘事勿取

---上课时间:

晚班 - 周一到周五晚上,每天3小时 .

---上课周期:

3-4个月 (因为后期商业项目有可能延长时间,因此做出一个月的浮动)

---课程描述:

我的目的就是捏造(记住,是捏造)职业化,专业化,标准化的Android程序员,并且保证推荐成都税后4000/ 以上的再就业

采用迭代式教学 . 大部分课程不直接从理论入手 .而是从最直观的演示 和 工具入手讲解 . 然后再不断的重复理论的应用 . 技能课是每课必练  . 同时在培训过程中要和讲师一起引导性完成两个商业项目的开发 . 直接累计两个完整和标准项目经验 . 同时在我们实际开发中,再不断的强化和应用理论 . 这就是所谓的迭代开发 .

同时,我们的培训还包括职业素质的培训 ,协同开发能力 , 项目分析和设计能力以及共享软件的培训

培训完后,我们的预期值是让“工友”达到职业化,专业化,标准化 , 并且具备Android应用项目开发综合能力.推荐每月4000以上的再就业!

培训的另外一个特点是 :讲师具有丰富的项目经验和培养开发团队的经验 . 课程中拒绝空谈.大部分Case & Sample 都是来自我们的经验 .同时,我们也是另类的,因为我们的入学的朋友都要经过筛选,具备一定的开发基础和身体健康才能入学 !

玉不雕不成器 , 让我们一起努力吧 !

---培训费用及缴费方式:

可以先跟班旁听(当作试听课吧) , 免费听取3天讲课,然后决定是否报名 . 签署培训合同后一次性缴纳5000元培训费用 .(整个培训不会再另收其它额外费用,并且赠送我们撰写及出版书籍《深入浅出Google android》)

---课程一级大纲列表

您可以通过截图浏览 :

p1 p2 p3 p4

也可以从ISTG服务器(电信独享10M)上下载

download->课程一级大纲Android.xls (578.00 kb)

关于第二个文档,也可以看我这篇文章:

http://sundyzlh.spaces.live.com/blog/cns!959CEE80F298BEFA!387.entry

Youth私塾第一个班,.NET模式班 ,目前学员没有低于5000税后的

Youth私塾的第一个班:.NET模式班

.NET班的图片:http://sundyzlh.spaces.live.com/blog/cns!959CEE80F298BEFA!917.entry

---报名热线:

GoogleTalk : sundyzlh@gmail.com

MSN:sundyzlh@hotmail.com

Email:sundyzlh@hotmail.com

QQ:183683266

Mobile:15608071871

欢迎面谈:)

 

Currently rated 1.9 by 129 people

  • Currently 1.88372/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Education & Consultation | Java & OpenSource Domain

ISPOSTBACK in JSF

by sundy 12/9/2009 9:21:55 AM

Although this kind of mechanism is not necessary as it’s in other frameworks like asp.net, I’ve observed in many places where people are demanding such a feature to understand a postback in JSF. I still don’t belive this need is a good practice since developers should not need to care about http cycles and consider them in the development process, but in the end it seemed challenging to figure out a way. I thought the best place to check for the postback is a view handler. In JSF using the decorator design pattern you can change the default behavior of the view handler.

A view handler has several methods like creating, rendering and restoring the view. This reveals the answer actually, when create view is called than it is simply not a postback. Here is the custom view handler.

package extensions;
import java.io.IOException;
import java.util.Locale;
import java.util.Map;
import javax.faces.FacesException;
import javax.faces.application.ViewHandler;
import javax.faces.component.UIViewRoot;
import javax.faces.context.FacesContext;
public class CustomViewHandler extends ViewHandler {
protected ViewHandler baseViewHandler;
public CustomViewHandler(ViewHandler viewHandler) {
super();
this.baseViewHandler = viewHandler;
}
public Locale calculateLocale(FacesContext facesContext) {
return baseViewHandler.calculateLocale(facesContext);
}
public String calculateRenderKitId(FacesContext facesContext) {
return baseViewHandler.calculateRenderKitId(facesContext);
}
public UIViewRoot createView(FacesContext facesContext, String arg1) {
setPostback(facesContext, false);
return baseViewHandler.createView(facesContext, arg1);
}
public String getActionURL(FacesContext facesContext, String arg1) {
return baseViewHandler.getActionURL(facesContext, arg1);
}
public String getResourceURL(FacesContext facesContext, String arg1) {
return baseViewHandler.getResourceURL(facesContext, arg1);
}
public void renderView(FacesContext facesContext, UIViewRoot arg1) throws IOException, FacesException {
baseViewHandler.renderView(facesContext, arg1);
}
public UIViewRoot restoreView(FacesContext facesContext, String arg1) {
setPostback(facesContext, true);
return baseViewHandler.restoreView(facesContext, arg1);
}
public void writeState(FacesContext facesContext) throws IOException&nbs
p;{
baseViewHandler.writeState(facesContext);
}
public Map getRequestScope(FacesContext facesContext) {
return (Map)facesContext.getApplication().createValueBinding("#{requestScope}").getValue(facesContext);
}
public void setPostback(FacesContext facesContext, boolean value) {
getRequestScope(facesContext).put("ispostback", new Boolean(value));
}
}

To plug-in this view handler to the application following decleration goes into the faces-config.

<application>
   <view-handler>extensions.CustomViewHandler</view-handler>
</application>

In order to get the info set by the view handler, the following method can be used;

public boolean isPostback() {
FacesContext facesContext = FacesContext.getCurrentInstance();
Map requestScope = (Map)facesContext.getApplication().createValueBinding("#{requestScope}").getValue(facesContext);
boolean ispostback = ((Boolean)requestScope.get("ispostback")).booleanValue();
return ispostback;
}

Important: The view handler approach won’t work when the state saving is set to server because the views are cached in session and create view is not called. I guess a better alternative to the viewhandler is hacking the navigation handler. I don’t think same issue will occur when a navigation handler is used to check for a postback

Currently rated 1.0 by 4 people

  • Currently 1/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain

I just do some development on Android . now show the installing process!

by sundy 8/12/2009 2:56:47 AM

Installing the Android SDK

This page describes how to install the Android SDK and set up your development environment. If you haven't downloaded the SDK, you can do so from the Download page. Once you've downloaded the SDK, return here.

If you encounter any problems during installation, see the Installation Notes at the bottom of this page.

Upgrading?

If you have already developed applications using an earlier version of the SDK, please read Upgrading the SDK, instead.

Preparing for Installation

Before you begin, take a moment to confirm that your development machine meets the System Requirements.

If you will be developing on Eclipse with the Android Development Tools (ADT) Plugin — the recommended path if you are new to Android — make sure that you have a suitable version of Eclipse installed on your computer (3.3 or newer). If you need to install Eclipse, you can download it from this location:

http://www.eclipse.org/downloads/

A Java or RCP version of Eclipse is recommended.

Installing the SDK

After downloading the SDK, unpack the .zip archive to a suitable location on your machine. By default, the SDK files are unpacked into a directory named android_sdk_<platform>_<release>. The directory contains a local copy of the documentation (accessible by opening documentation.html in your browser) and the subdirectories tools/, add-ons/, platforms/, and others. Inside each subdirectory of platforms/ you'll find samples/, which includes code samples that are specific to each version of the platform.

Make a note of the name and location of the unpacked SDK directory on your system — you will need to refer to the SDK directory later, when setting up the Android plugin or when using the SDK tools.

Optionally, you may want to add the location of the SDK's primary tools directory to your system PATH. The primary tools/ directory is located at the root of the SDK folder. Adding tools to your path lets you run Android Debug Bridge (adb) and the other command line tools without needing to supply the full path to the tools directory.

  • On Linux, edit your ~/.bash_profile or ~/.bashrc file. Look for a line that sets the PATH environment variable and add the full path to the tools/ directory to it. If you don't see a line setting the path, you can add one:
      export PATH=${PATH}:<your_sdk_dir>/tools
  • On a Mac, look in your home directory for .bash_profile and proceed as for Linux. You can create the .bash_profile if you haven't already set one up on your machine.
  • On Windows, right-click on My Computer, and select Properties. Under the Advanced tab, hit the Environment Variables button, and in the dialog that comes up, double-click on Path (under System Variables). Add the full path to the tools/ directory to the path.

Note that, if you update your SDK in the future, you should remember to update your PATH settings to point to the new location, if different.

If you will be using the Eclipse IDE as your development environment, the next section describes how to install the Android Development Tools plugin and set up Eclipse. If you choose not to use Eclipse, you can develop Android applications in an IDE of your choice and then compile, debug and deploy using the tools included in the SDK (skip to Next Steps).

Installing the ADT Plugin for Eclipse

Android offers a custom plugin for the Eclipse IDE, called Android Development Tools (ADT), that is designed to give you a powerful, integrated environment in which to build Android applications. It extends the capabilites of Eclipse to let you quickly set up new Android projects, create an application UI, add components based on the Android Framework API, debug your applications using the Android SDK tools, and even export signed (or unsigned) APKs in order to distribute your application.

In general, using Eclipse with ADT is a highly recommended approach to Android development and is the fastest way to get started. (If you prefer to work in an IDE other than Eclipse, you do not need to install Eclipse or ADT, instead, you can directly use the SDK tools to build and debug your application.)

Once you have Eclipse installed, as described in Preparing for Installation, follow the steps below to download the ADT plugin and install it in your respective Eclipse environment.

Eclipse 3.3 (Europa)
Eclipse 3.4 (Ganymede)

  1. Start Eclipse, then select Help > Software Updates > Find and Install....
  2. In the dialog that appears, select Search for new features to install and click Next.
  3. Click New Remote Site.
  4. In the resulting dialog box, enter a name for the remote site (e.g. "Android Plugin") and enter the URL:
    https://dl-ssl.google.com/android/eclipse/

    If you have trouble aqcuiring the plugin, try using "http" in the URL, instead of "https" (https is preferred for security reasons).

    Click OK.

  5. You should now see the new site added to the search list (and checked). Click Finish.
  6. In the subsequent Search Results dialog box, select the checkbox for the "Android Plugin". This will select the nested tools: "Android DDMS" and "Android Development Tools". Click Next.
  7. Read and accept the license agreement, then click Next.
  8. On the following Installation window, click Finish.
  9. The ADT plugin is not digitally signed. Accept the installation anyway by clicking Install All.
  10. Restart Eclipse.
  1. Start Eclipse, then select Help > Software Updates....
  2. In the dialog that appears, click the Available Software tab.
  3. Click Add Site...
  4. Enter the Location:
    https://dl-ssl.google.com/android/eclipse/

    If you have trouble aqcuiring the plugin, try using "http" in the Location URL, instead of "https" (https is preferred for security reasons).

    Click OK.

  5. Back in the Available Software view, you should see the plugin listed by the URL, with "Developer Tools" nested within it. Select the checkbox next to Developer Tools and click Install...
  6. On the subsequent Install window, "Android DDMS" and "Android Development Tools" should both be checked. Click Next.
  7. Read and accept the license agreement, then click Finish.
  8. Restart Eclipse.

Now modify your Eclipse preferences to point to the Android SDK directory:

  1. Select Window > Preferences... to open the Preferences panel (Mac: Eclipse > Preferences).
  2. Select Android from the left panel.
  3. For the SDK Location in the main panel, click Browse... and locate your downloaded SDK directory.
  4. Click Apply, then OK.

Done! If you haven't encountered any problems, then you're ready to begin developing Android applications. See the Next Steps section for suggestions on how to start.

Troubleshooting ADT Installation

If you are having trouble downloading the ADT plugin after following the steps above, here are some suggestions:

  • If Eclipse can not find the remote update site containing the ADT plugin, try changing the remote site URL to use http, rather than https. That is, set the Location for the remote site to:
    http://dl-ssl.google.com/android/eclipse/
  • If you are behind a firewall (such as a corporate firewall), make sure that you have properly configured your proxy settings in Eclipse. In Eclipse 3.3/3.4, you can configure proxy information from the main Eclipse menu in Window (on Mac, Eclipse) > Preferences > General > Network Connections.

If you are still unable to use Eclipse to download the ADT plugin as a remote update site, you can download the ADT zip file to your local machine and manually install the it:

  1. Download the ADT zip file (do not unpack it).
  2. Follow steps 1 and 2 in the default install instructions (above).
  3. In Eclipse 3.3, click New Archive Site....
    In Eclipse 3.4, click Add Site..., then Archive...
  4. Browse and select the downloaded zip file.
  5. Follow the remaining procedures, above, starting from steps 5.

To update your plugin once you've installed using the zip file, you will have to follow these steps again instead of the default update instructions.

Other install errors

Note that there are features of ADT that require some optional Eclipse components (for example, WST). If you encounter an error when installing ADT, your Eclipse installion might not include these components. For information about how to quickly add the necessary components to your Eclipse installation, see the troubleshooting topic ADT Installation Error: "requires plug-in org.eclipse.wst.sse.ui".

For Linux users

If you encounter this error when installing the ADT Plugin for Eclipse:

An error occurred during provisioning.
Cannot connect to keystore.
JKS

...then your development machine lacks a suitable Java VM. Installing Sun Java 6 will resolve this issue and you can then reinstall the ADT Plugin.

Next Steps

Once you have completed installation, you are ready to begin developing applications. Here are a few ways you can get started:

Learn about Android

  • Take a look at the Dev Guide and the types of information it provides
  • Read an introduction to Android as a platform in What is Android?
  • Learn about the Android framework and how applications run on it in Application Fundamentals
  • Take a look at the Android framework API specification in the Reference tab

Explore the SDK

Explore some code

  • Set up a Hello World application (highly recommended, especially for Eclipse users)
  • Follow the Notepad Tutorial to build a full Android application
  • Create a new project for one of the other sample applications included in <sdk>/platforms/<platfrom>/samples, then compile and run it in your development environment

Visit the Android developer groups

  • Take a look at the Community tab to see a list of Android developers groups. In particular, you might want to look at the Android Developers group to get a sense for what the Android developer community is like.

Installation Notes

Ubuntu Linux Notes
  • If you need help installing and configuring Java on your development machine, you might find these resources helpful:
  • Here are the steps to install Java and Eclipse, prior to installing the Android SDK and ADT Plugin.
    1. If you are running a 64-bit distribution on your development machine, you need to install the ia32-libs package using apt-get::
      apt-get install ia32-libs
    2. Next, install Java:
      apt-get install sun-java6-bin
    3. The Ubuntu package manager does not currently offer an Eclipse 3.3 version for download, so we recommend that you download Eclipse from eclipse.org (http://www.eclipse.org/ downloads/). A Java or RCP version of Eclipse is recommended.
    4. Follow the steps given in previous sections to install the SDK and the ADT plugin.
Other Linux Notes
  • If JDK is already installed on your development computer, please take a moment to make sure that it meets the version requirements listed in the System Requirements. In particular, note that some Linux distributions may include JDK 1.4 or Gnu Compiler for Java, both of which are not supported for Android development.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain | Mobile & Wireless

Struts源码分析4:ActionForward

by sundy 8/7/2009 11:57:40 AM

前言:发现很多j2ee的程序员基础都差得不行 ,会用ssh的甚至都不知道为何要这样,以及如何设计的 。因此为大家简单的剖析一下Struts的设计 ,以资借鉴 。

ActionForward继承了下ForwardConfig,然后就写了6个构造函数……然后就没了 汗=。=!
有一句话没翻译出来,有看得懂的来帮个忙吧 :
NOTE - This class would have been deprecated and
replaced by org.apache.struts.config.ForwardConfig except for the fact that
it is part of the public API that existing applications are using.
下面是翻译后的源码。

package org.apache.struts.action;
import org.apache.struts.config.ForwardConfig;
/**
* 一个ActionForward为控制器类RequestProcessor指向了一个目的地,由控制器执行跳转。
* 但也可能作为Action中的行为,直接执行RequestDispatcher.forward或
* HttpServletResponse.sendRedirect方法。这个类的实例可以会根据需要被动态创建,
* 也可以被设定为与一个ActionMapping绑定,通过名字查找这个mapping实例的多个跳转目的地。

* 一个ActionForward包含以下几个基本属性,其他的附加属性可以根据需要由子类提供。

* contextRelative(上下文关系): path路径值必须被解释为上下文相关路径(context-relative)

* name : 用来查找相关的ActionMapping。
* <li><strong>name</strong> - Logical name by which this instance may be
* looked up in relationship to a particular ActionMapping. </li>
*
* path : 一个让控制器实现转发(forward)的,模型相关/上下文相关URI;或一个让控制器
* 实现重定向(redirected)的,绝对/相对URI。
*
* redirect : 当需要控制器以重定向的方法执行path时则设为true,否则为false
*
* 这个类继承了 ForwardConfig 类和 contextRelative属性
*
* 注意 :这个类不推荐使用,而应由ForwardConfig取代 ..后面的翻不出来了。
* NOTE - This class would have been deprecated and
* replaced by org.apache.struts.config.ForwardConfig except for the fact that
* it is part of the public API that existing applications are using.</p>
*          
*/
public class ActionForward extends ForwardConfig {
/**
     * 无参构造函数 - 以默认值实例化
*/
public ActionForward() {
this(null, false);
    }
/**
     * 构造函数 - 参数path</p>
     *
*/
public ActionForward(String path) {
this(path, false);
    }
/**
     * 构造函数 - 参数 path,redirect
*/
public ActionForward(String path, boolean redirect) {
super();
        setName(null);
        setPath(path);
        setRedirect(redirect);
    }
/**
     *构造函数 - 参数 name,path,redirect
*/
public ActionForward(String name, String path, boolean redirect) {
super();
        setName(name);
        setPath(path);
        setRedirect(redirect);
    }
/**
     * 构造函数 - 参数 name,path,redirect,module 模块前缀
*/
public ActionForward(String name, String path, boolean redirect,
        String module) {
super();
        setName(name);
        setPath(path);
        setRedirect(redirect);
        setModule(module);
    }
/**
     * 构造函数 - 用已有的ActionForward对象实例化。
*/
public ActionForward(ActionForward copyMe) {
this(copyMe.getName(), copyMe.getPath(), copyMe.getRedirect(),
            copyMe.getModule());
    }
}

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain

Struts源码分析3:ActionForm

by sundy 8/7/2009 11:56:30 AM

前言:发现很多j2ee的程序员基础都差得不行 ,会用ssh的甚至都不知道为何要这样,以及如何设计的 。因此为大家简单的剖析一下Struts的设计 ,以资借鉴 。

import org.apache.struts.upload.MultipartRequestHandler;
import javax.servlet.ServletRequest;
import javax.servlet.http.HttpServletRequest;
import java.io.Serializable;
/**
* 一个ActionForm是可以与一个或多个任意的ActionMapping关联的JavaBean。这个bean的里属性
* 在对应Action.execute方法调用前,由对应的request初始化。    
*
* 当这个bean的属性被赋值后,Action.execute方法调用之前,bean的validate方法
* 将被调用,这个方法用来校验用户提交的属性值。如果发现错误,就返回一个包含了这些错误内容的
* error信息。controller将返回至相应的输入表单。如果无错误,validate方法就返回null,
* 相应的Action.execute方法将被调用。

* 这个类必须被继承使用。子类要为所有会被公开(expose)的bean属性提供get和set方法,以及
* 重写一些public或protected方法以提供具体实现。

* 由于ActionForm是JavaBeans,所以根据JavaBeans的规范,子类也会实现Serializable(可序列
* 化)接口。为了使用ActionForm相关的introspection API ?,一些容器会要求一个Form对象满足
* 所有JavaBean规范。

*/
public abstract class ActionForm implements Serializable {
// ----------------------------------------------------- Instance Variables
/**
     * <p>The servlet instance to which we are attached.</p>
*/
protected transient ActionServlet servlet = null;
/**
     * MultipartRequestHandler
     * 这个form的多请求处理对象。        //transient表示该属性将不被序列化。
     *  //wzl注:该对象的作用大约是结合upload包里的类,实现文件的上传功能。
     *  //由于还没接触过,所以下面的相关方法不再翻译
*/
protected transient MultipartRequestHandler multipartRequestHandler;
// ------------------------------------------------------------- Properties
/**
     * @return The servlet instance to which we are attached.
*/
protected ActionServlet getServlet() {
return (this.servlet);
    }
/**
     * ActionServletWrapper
     * 将所属的控制器servlet以ActionServletWrapper对象返回。
     * //该对象也在servlet上提供了对MultipartRequestHandler的使用。
     * @return An instance of ActionServletWrapper
*/
public ActionServletWrapper getServletWrapper() {
return new ActionServletWrapper(getServlet());
    }
/**
     * <p>Return the <code>MultipartRequestHandler</code> for this form The
     * reasoning behind this is to give form bean developers control over the
     * lifecycle of their multipart requests through the use of the
     * <code>finish</code> and/or <code>rollback</code> methods of
     * <code>MultipartRequestHandler</code>.  This method will return
     * <code>null</code> if this form's enctype is not "multipart/form-data".
     * </p>
     * 
     * @return The {@link org.apache.struts.upload.MultipartRequestHandler}
     *         for this form.
     * @see org.apache.struts.upload.MultipartRequestHandler
*/
public MultipartRequestHandler getMultipartRequestHandler() {
return multipartRequestHandler;
    }
/**
     * 设定所属的servlet(若非空)实例。
     *
     * @param servlet The new controller servlet, if any
*/
public void setServlet(ActionServlet servlet) {
this.servlet = servlet;
// :FIXME: Should this be releasing resources?
    }
/**
     * <p>Set the Handler provided for use in dealing with file uploads.</p>
     *
     * @param multipartRequestHandler The Handler to use for fileuploads.
*/
public void setMultipartRequestHandler(
        MultipartRequestHandler multipartRequestHandler) {
this.multipartRequestHandler = multipartRequestHandler;
    }
// --------------------------------------------------------- Public Methods
/**
     *  //直接调用下面那个重载HTTP的。
*/
public void reset(ActionMapping mapping, ServletRequest request) {
try {
            reset(mapping, (HttpServletRequest) request);
        } catch (ClassCastException e) {
            ; // FIXME: Why would this ever happen except a null
        }
    }
/**
     * 用来重置bean中的属性。这个方法在属性被控制器赋值前调用。
     * 
     * 默认的方法体为空,实际中发现,唯一需要被重置的是声明到session中表单的checkboxs属性
     * 除此以外的属性,都会在域声明时被初始化。
     * 
     * 如果为了实现form能被多个请求取值而将其放到了session中,那么你必须非常注意那些被
     * 重置(reset)的值,如上面提到的,对于每一个输入表单内容的页面,必须将session范围中的
     * checkboxs提前重置为fales。这是因为只有当checkbox为fales时才表示客户没有提交该值。
     * 如果一个session中的checkbox没有被提前重置的话,他将永远不会为fales。
     * 
     * 这个方法不适合用来给"修改"类型的页面中的表单赋初始值(这应该在setup Action中)。你唯一需要
     * 关心的就是将checkbox的值改为fales。所以这个方法一般不用实现
     * 
     * @param mapping The mapping used to select this instance
     * @param request The servlet request we are processing
*/
public void reset(ActionMapping mapping, HttpServletRequest request) {
// Default implementation does nothing
    }
/**
     *  //直接调用下面那个重载HTTP的。
*/
public ActionErrors validate(ActionMapping mapping, ServletRequest request) {
try {
return (validate(mapping, (HttpServletRequest) request));
        } catch (ClassCastException e) {
return (null);
        }
    }
/**
     * 用来验证request中的属性值,并返回一个ActionErrors对象,它包含了验证中发现的错误信息。
     * 如果验证成功,则返回null 或一个无错误信息记录的ActionErrors对象。
     * 
     * 默认的执行体为空并返回null,子类中必须重写这个方法以提供需要的验证操作。
     * 
     * @param mapping The mapping used to select this instance
     * @param request The servlet request we are processing
     * @return 验证失败就返回错误信息; 验证成功则返回null或空的信息。
     *         
     * @see DynaActionForm
*/
public ActionErrors validate(ActionMapping mapping,
        HttpServletRequest request) {
return (null);
    }
}

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain

Struts源码分析2:org.apache.struts.action.ActionErrors

by sundy 8/7/2009 11:54:47 AM

前言:发现很多j2ee的程序员基础都差得不行 ,会用ssh的甚至都不知道为何要这样,以及如何设计的 。因此为大家简单的剖析一下Struts的设计 ,以资借鉴 。

ActionErrors的源代码:

package org.apache.struts.action; 
import java.io.Serializable;
/**
*  一个用来压缩 (encapsulates) 错误信息的类。错误信息来自ActionForm的validate()的方法。
*  验证错误可能与整个ActionForm bean相关,也可能只针对一个bean属性。
*
*
* 每个单独的错误由一个ActionMessager对象来描述。
* 一个ActionMessager包含一个massage key。
*and up to four placeholder arguments used for parametric substitution in the resulting message.
*等于用于在resulting message中进行参数替换的4个占位符(placeholder)属性。??

*
* IMPLEMENTATION (执行) NOTE:假定这些对象在创建和操作中都
* 在同一个线程中,因此不需要同步。
*
*/
public class ActionErrors extends ActionMessages implements Serializable {
// --------------------------------------------------------- Public Methods
/**
     *  构造方法:创建空的 ActionErrors对象。
*/
public ActionErrors() {
super();
    }
/**
     * 用给的的Messages 初始化创建 ActionErrors对象    
     * @param messages The messages to be initially added to this object. This
     *                 parameter can be null
*/
public ActionErrors(ActionErrors messages) {
super(messages);
    }
}

Currently rated 1.0 by 6 people

  • Currently 1/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain

Struts源码分析1:org.apache.struts.action.Action

by sundy 8/7/2009 11:53:32 AM

前言:发现很多j2ee的程序员基础都差得不行 ,会用ssh的甚至都不知道为何要这样,以及如何设计的 。因此为大家简单的剖析一下Struts的设计 ,以资借鉴 。

actoin中的方法 大多是针对 Messages,Errors,token的一些操作。

package org.apache.struts.action;
import org.apache.struts.Globals;
import org.apache.struts.config.ModuleConfig;
import org.apache.struts.util.MessageResources;
import org.apache.struts.util.ModuleUtils;
import org.apache.struts.util.RequestUtils;
import org.apache.struts.util.TokenProcessor;
import javax.servlet.ServletContext;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.util.Locale;
/**
*  Action必须以线程安全的方式编写,
* 因为controller会为同时存在的多个request共享一个实例。
* 所以编写时要注意:
*
* 实例和static变量不能存储与具体request相关的信息。
*
*  存取受保护的JavaBeans, session 变量等资源时,必须使用同步(synchronized)。

*
*  当一个Action实例被第一次创建时,controller会用一个非空参数
*(标识这个servlet实例和附属他的Action)调用 setServlet 。
*   当实例被关闭时,setServlet会被再次调用,用一个null
*   参数来清空这个Action的信息
*          
*/
public class Action {
/**
     * org.apache.struts.util.TokenProcessor类:令牌产生器,用于防止事务重复提交 
*/
private static TokenProcessor token = TokenProcessor.getInstance();
// NOTE: We can make the token  variable protected and remove Action's
// token methods or leave it private and allow the token methods to
// delegate(委托) their calls.
// ----------------------------------------------------- Instance Variables
/**
     * Action附属的servlet。
*/
protected transient ActionServlet servlet = null;
// ------------------------------------------------------------- Properties
public ActionServlet getServlet() {
return (this.servlet);
    }
/**
     * 设置Action附属的servlet,或释放所有资源(servlet=null)       
     * @param servlet The new controller servlet, if any
*/
public void setServlet(ActionServlet servlet) {
this.servlet = servlet;
// :FIXME: Is this suppose to release resources?
    }
// --------------------------------------------------------- Public Methods
/**
     *      非HTTP的execute方法,一般不用。
     * /
    public ActionForward execute(ActionMapping mapping, ActionForm form,
        ServletRequest request, ServletResponse response)
        throws Exception {
        try {
            return execute(mapping, form, (HttpServletRequest) request,
                (HttpServletResponse) response);
        } catch (ClassCastException e) {
            return null;
        }
    }
    /**
     * 处理 HTTP request, 创建相应的(corresponding)
     * HTTP response (或定向到其他创建response 的组件
     * ), 返回 { ActionForward} 实例 来通知control如何跳转。
     * 或当处理完成时返回null
     * 注:当请求发送到Action时就会自动执行这个execute方法,所以一般简单的Action就重写这个方法即可//by wzl.
     * @param mapping  The ActionMapping used to select this instance (用来选择这个实例??)
     * @param form     可选的 ActionForm bean 
     * @param request  The HTTP request 
     * @param response The HTTP response 
     * @return forward  通知 control 应该跳转的页面, 或null (当业务完成时)
     * @throws Exception if the application business logic throws an
     *                   exception
     * @since Struts 1.1
*/
public ActionForward execute(ActionMapping mapping, ActionForm form,
        HttpServletRequest request, HttpServletResponse response)
throws Exception {
return null;
    }
// ---------------------------------------------------- Protected Methods
/**
     * 为request添加 messages 
     * 在JSP用用 < html:messages> 标签使用 (if messages="true" is set),
     *  参数message 必须被初始化                                                          //org.apache.struts.action.ActionMessages 
     *  Otherwise, ensure that the request attribute is not set.???
     *
     * @param request  被添加message的request请求
     * @param messages ActionMessages 需要添加的message
     * @since Struts 1.2.1
*/
protected void addMessages(HttpServletRequest request,
        ActionMessages messages) {
if (messages == null) {
//  bad programmer! *slap*
return;
        }
// 取得request中的requestMessages, 没有就创建一个
        ActionMessages requestMessages =
            (ActionMessages) request.getAttribute(Globals.MESSAGE_KEY);   //"org.apache.struts.action.ACTION_MESSAGE";
if (requestMessages == null) {
            requestMessages = new ActionMessages();
        }
// messages加入到requestMessages
        requestMessages.add(messages);
// if still empty, just wipe it out from the request
if (requestMessages.isEmpty()) {
            request.removeAttribute(Globals.MESSAGE_KEY);
return;
        }
// Save the messages
        request.setAttribute(Globals.MESSAGE_KEY, requestMessages);
    }
/**
     * Adds the specified errors keys into the appropriate request attribute
     * for use by the &lt;html:errors&gt; tag, if any messages are required.
     * Initialize the attribute if it has not already been. Otherwise, ensure
     * that the request attribute is not set.
     *  注:基本与addMessages相同,只是这里的ActionMessages含的是错误信息,在页面用 <html:errors>使用。/by wzl
     * @param request The servlet request we are processing
     * @param errors  Errors object
     * @since Struts 1.2.1
*/
protected void addErrors(HttpServletRequest request, ActionMessages errors) {
if (errors == null) {
//  bad programmer! *slap*
return;
        }
// get any existing errors from the request, or make a new one
        ActionMessages requestErrors =
            (ActionMessages) request.getAttribute(Globals.ERROR_KEY);
if (requestErrors == null) {
            requestErrors = new ActionMessages();
        }
// add incoming errors
        requestErrors.add(errors);
// if still empty, just wipe it out from the request
if (requestErrors.isEmpty()) {
            request.removeAttribute(Globals.ERROR_KEY);
return;
        }
// Save the errors
        request.setAttribute(Globals.ERROR_KEY, requestErrors);
    }
/**
     * <p>Generate a new transaction token, to be used for enforcing a single
     * request for a particular transaction.</p>
     * 为需要处理特殊事务的request生成一个 事务token
     * @param request The request we are processing
     * @return The new transaction token.
*/
protected String generateToken(HttpServletRequest request) {
return token.generateToken(request);
    }
/**
     * Retrieves any existing errors placed in the request by previous
     * actions. This method could be called instead of creating a <code>new
     * ActionMessages()</code> at the beginning of an <code>Action</code>.
     * This will prevent saveErrors() from wiping out any existing Errors
     *
     * 获得被上一个Action设置的error信息,这个方法可用来
     *初始化一个ActionMessages。可以用来防止saveErrors()清空已存在的Errors。
     *
     * @param request The servlet request we are processing
     * @return the Errors that already exist in the request, or a new
     *         ActionMessages object if empty.
     * @since Struts 1.2.1
*/
protected ActionMessages getErrors(HttpServletRequest request) {
        ActionMessages errors =
            (ActionMessages) request.getAttribute(Globals.ERROR_KEY);
if (errors == null) {
            errors = new ActionMessages();
        }
return errors;
    }
/**
     * 返回用户当前选择的 Locale。  //java.util.Locale 对象表示了特定的地理、政治和文化地区。
     *
     * @param request The request we are processing
     * @return The user's currently selected Locale.
*/
protected Locale getLocale(HttpServletRequest request) {
return RequestUtils.getUserLocale(request, null);
    }
/**
     * 大体同getError(request)
     * <p> Retrieves any existing messages placed in the request by previous
     * actions. This method could be called instead of creating a <code>new
     * ActionMessages()</code> at the beginning of an <code>Action</code> This
     * will prevent saveMessages() from wiping out any existing Messages </p>
     * 
     * @param request The servlet request we are processing
     * @return the Messages that already exist in the request, or a new
     *         ActionMessages object if empty.
     * @since Struts 1.2.1
*/
protected ActionMessages getMessages(HttpServletRequest request) {
        ActionMessages messages =
            (ActionMessages) request.getAttribute(Globals.MESSAGE_KEY);
if (messages == null) {
            messages = new ActionMessages();
        }
return messages;
    }
/**
     * 为当前模型返回默认的MessageResources         ?? //org.apache.struts.util.MessageResources 
     *
     * @param request The servlet request we are processing
     * @return The default message resources for the current module.
     * @since Struts 1.1
*/
protected MessageResources getResources(HttpServletRequest request) {
return ((MessageResources) request.getAttribute(Globals.MESSAGES_KEY));
    }
/**
     * <p>Return the specified message resources for the current module.</p>
     * 根据key为当前module返回特定的MessageResources
     * 看不懂
     * @param request The servlet request we are processing
     * @param key     The key specified in the message-resources element for
     *                the requested bundle.
     * @return The specified message resource for the current module.
     * @since Struts 1.1
*/
protected MessageResources getResources(HttpServletRequest request,
        String key) {
// Identify the current module
        ServletContext context = getServlet().getServletContext();
        ModuleConfig moduleConfig =
            ModuleUtils.getInstance().getModuleConfig(request, context);
// Return the requested message resources instance
return (MessageResources) context.getAttribute(key
+ moduleConfig.getPrefix());
    }
/**
     * <p>Returns <code>true</code> if the current form's cancel button was
     * pressed. This method will check if the <code>Globals.CANCEL_KEY</code>
     * request attribute has been set, which normally occurs if the cancel
     * button generated by <strong>CancelTag</strong> was pressed by the user
     * in the current request. If <code>true</code>, validation performed by
     * an <strong>ActionForm</strong>'s <code>validate()</code> method will
     * have been skipped by the controller servlet.</p>
     *
     * 当form的cancel按键?被按下时返回true。该方法会检查 request的
     *  Globals.CANCEL_KEY属性。若为true,ActionForm中的validate()将被跳过。
     *
     * <p> Since Action 1.3.0, the mapping for a cancellable Action must also have
     * the new "cancellable" property set to true. If "cancellable" is not set, and
     * the magic Cancel token is found in the request, the standard Composable
     * Request Processor will throw an InvalidCancelException. </p>
     *
     * @param request The servlet request we are processing
     * @return <code>true</code> if the cancel button was pressed;
     *         <code>false</code> otherwise.
*/
protected boolean isCancelled(HttpServletRequest request) {
return (request.getAttribute(Globals.CANCEL_KEY) != null);
    }
/**
     * 在当前session中存有事务token时 返回true。当存在以下情况时返回false:
     * <ul>
     *
     *  request中无session
     * 
     * session中无事务token
     * <li>No transaction token included as a request parameter</li>
     * request中没有事务token属性。
     *
     * 存在是事务token属性与session中的不匹配。
     * </ul>
     *
     * @param request The servlet request we are processing
     * @return <code>true</code> if there is a transaction token and it is
     *         valid; <code>false</code> otherwise.
*/
protected boolean isTokenValid(HttpServletRequest request) {
return token.isTokenValid(request, false);
    }
/**
     * <p>Return <code>true</code> if there is a transaction token stored in
     * the user's current session, and the value submitted as a request
     * parameter with this action matches it. Returns <code>false</code> under
     * any of the following circumstances:</p>
     * 重写上一个方法,添加参数 reset 决定是否在确认后重置token
     * <ul>
     *
     * <li>No session associated with this request</li> <li>No transaction
     * token saved in the session</li>
     *
     * <li>No transaction token included as a request parameter</li>
     *
     * <li>The included transaction token value does not match the transaction
     * token in the user's session</li>
     * 
     * </ul>
     *
     * @param request The servlet request we are processing
     * @param reset   Should we reset the token after checking it?
     * @return <code>true</code> if there is a transaction token and it is
     *         valid; <code>false</code> otherwise.
*/
protected boolean isTokenValid(HttpServletRequest request, boolean reset) {
return token.isTokenValid(request, reset);
    }
/**
     * <p>Reset the saved transaction token in the user's session. This
     * indicates that transactional token checking will not be needed on the
     * next request that is submitted.</p>
     * 重置token
     * @param request The servlet request we are processing
*/
protected void resetToken(HttpServletRequest request) {
        token.resetToken(request);
    }
/**
     * <p>Save the specified error messages keys into the appropriate request
     * attribute for use by the &lt;html:errors&gt; tag, if any messages are
     * required. Otherwise, ensure that the request attribute is not
     * created.</p>
     * 重置并设置Errors。
     * @param request The servlet request we are processing
     * @param errors  Error messages object
     * @since Struts 1.2
*/
protected void saveErrors(HttpServletRequest request, ActionMessages errors) {
// Remove any error messages attribute if none are required
if ((errors == null) || errors.isEmpty()) {
            request.removeAttribute(Globals.ERROR_KEY);
return;
        }
// Save the error messages we need
        request.setAttribute(Globals.ERROR_KEY, errors);
    }
/**
     * <p>Save the specified messages keys into the appropriate request
     * attribute for use by the &lt;html:messages&gt; tag (if messages="true"
     * is set), if any messages are required. Otherwise, ensure that the
     * request attribute is not created.</p>
     * 重置并设置request中的Messages
     * @param request  The servlet request we are processing.
     * @param messages The messages to save. <code>null</code> or empty
     *                 messages removes any existing ActionMessages in the
     *                 request.
     * @since Struts 1.1
*/
protected void saveMessages(HttpServletRequest request,
        ActionMessages messages) {
// Remove any messages attribute if none are required
if ((messages == null) || messages.isEmpty()) {
            request.removeAttribute(Globals.MESSAGE_KEY);
return;
        }
// Save the messages we need
        request.setAttribute(Globals.MESSAGE_KEY, messages);
    }
/**
     * <p>Save the specified messages keys into the appropriate session
     * attribute for use by the &lt;html:messages&gt; tag (if messages="true"
     * is set), if any messages are required. Otherwise, ensure that the
     * session attribute is not created.</p>
     *  重置并设置session中的Messages
     * @param session  The session to save the messages in.
     * @param messages The messages to save. <code>null</code> or empty
     *                 messages removes any existing ActionMessages in the
     *                 session.
     * @since Struts 1.2
*/
protected void saveMessages(HttpSession session, ActionMessages messages) {
// Remove any messages attribute if none are required
if ((messages == null) || messages.isEmpty()) {
            session.removeAttribute(Globals.MESSAGE_KEY);
return;
        }
// Save the messages we need
        session.setAttribute(Globals.MESSAGE_KEY, messages);
    }
/**
     * <p>Save the specified error messages keys into the appropriate session
     * attribute for use by the &lt;html:messages&gt; tag (if
     * messages="false") or &lt;html:errors&gt;, if any error messages are
     * required. Otherwise, ensure that the session attribute is empty.</p>
     * 重置并设置session中的Errors
     * @param session The session to save the error messages in.
     * @param errors  The error messages to save. <code>null</code> or empty
     *                messages removes any existing error ActionMessages in
     *                the session.
     * @since Struts 1.3
*/
protected void saveErrors(HttpSession session, ActionMessages errors) {
// Remove the error attribute if none are required
if ((errors == null) || errors.isEmpty()) {
            session.removeAttribute(Globals.ERROR_KEY);
return;
        }
// Save the errors we need
        session.setAttribute(Globals.ERROR_KEY, errors);
    }
/**
     * <p>Save a new transaction token in the user's current session, creating
     * a new session if necessary.</p>
     * 
     * @param request The servlet request we are processing
*/
protected void saveToken(HttpServletRequest request) {
        token.saveToken(request);
    }
/**
     * <p>Set the user's currently selected <code>Locale</code> into their
     * <code>HttpSession</code>.</p>
     *
     * @param request The request we are processing
     * @param locale  The user's selected Locale to be set, or null to select
     *                the server's default Locale
*/
protected void setLocale(HttpServletRequest request, Locale locale) {
        HttpSession session = request.getSession();
if (locale == null) {
            locale = Locale.getDefault();
        }
        session.setAttribute(Globals.LOCALE_KEY, locale);
    }
}

Currently rated 4.5 by 2 people

  • Currently 4.5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain

开源协议简介

by sundy 7/12/2009 5:26:00 AM

除了大家比较熟悉的GPL协议之外,开源界还有很多许可证,如LGPL许可证、BSD许可证等,下面就来一一介绍。

LGPL许可证

LGPL许可证是LESSER GENERAL PUBLIC LICENSE的简写,也叫LIBRARY GENERAL PUBLIC LICENSE,中文译为“较宽松公共许可证”或者“函数库公共许可证”。该许可证适用于一些由自由软件基金会与其它决定使用此许可证的软件作者所特殊设计的软件软件包─比如函数库(即Library)。
LGPL许可证

LGPL许可证,也是自由软件联盟GNU开源软件许可证的一种,大部分的 GNU软件,包括一些函数库,是受到原来的 GPL许可证保护的。而LGPL许可证,适用于特殊设计的函数库,且与原来的通用公共许可证有很大的不同,给予了被许可人较为宽松的权利,所以叫“较宽松公共许可证”。在特定的函数库中使用它,以准许非自由的程序可以与这些函数库连结。
当一个程序与一个函数库连结,不论是静态连结或使用共享函数库,二者的结合可以合理地说是结合的作品,一个原来的函数库的衍生品。因此,原来的通用公共许可证只有在整个结合品满足其自由的标准时,才允许连结。较宽松通用公共许可则以更宽松的标准允许其它程序代码与本函数库连结。例如,在少数情况下,可能会有特殊的需要而鼓励大家尽可能广泛地使用特定的函数库,因而使它成为实际上的标准。为了达到此目标,必须允许非自由的程序使用此函数库。一个较常发生的情况是,一个自由的函数库与一个被广泛使用的非自由函数库做相同的工作,在此情况下,限制只有自由软件可以使用此自由函数库不会有多少好处,故我们使用了LGPL许可证。

在其他情况下,允许非自由程序使用特定的函数库,可以让更多的人们使用自由软件的大部分。例如,允许非自由程序使用GNU C函数库,可以让更多的人们使用整个GNU作业系统,以及它的变形,GNU/Linux操作系统。

尽管LGPL许可证对使用者的自由保护是较少的,但它却能确保与此函数库连结的程序的使用者拥有自由,而且具有使用修改过的函数库版本来执行该程序的必要方法。

MPL许可证

MPL是The Mozilla Public License的简写,是1998年初Netscape的 Mozilla小组为其开源软件项目设计的软件许可证。MPL许可证出现的最重要原因就是,Netscape公司认为GPL许可证没有很好地平衡开发者对源代码的需求和他们利用源代码获得的利益。同著名的GPL许可证和BSD许可证相比,MPL在许多权利与义务的约定方面与它们相同(因为都是符合OSIA认定的开源软件许可证)。但是,相比而言MPL还有以下几个显著的不同之处:
◆ MPL虽然要求对于经MPL许可证发布的源代码的修改也要以MPL许可证的方式再许可出来,以保证其他人可以在MPL的条款下共享源代码。但是,在MPL许可证中对“发布”的定义是“以源代码方式发布的文件”,这就意味着MPL允许一个企业在自己已有的源代码库上加一个接口,除了接口程序的源代码以MPL许可证的形式对外许可外,源代码库中的源代码就可以不用MPL许可证的方式强制对外许可。这些,就为借鉴别人的源代码用做自己商业软件开发的行为留了一个豁口。

◆ MPL许可证第三条第7款中允许被许可人将经过MPL许可证获得的源代码同自己其他类型的代码混合得到自己的软件程序。

◆ 对软件专利的态度,MPL许可证不像GPL许可证那样明确表示反对软件专利,但是却明确要求源代码的提供者不能提供已经受专利保护的源代码(除非他本人是专利权人,并书面向公众免费许可这些源代码),也不能在将这些源代码以开放源代码许可证形式许可后再去申请与这些源代码有关的专利。

◆ 对源代码的定义

而在MPL(1.1版本)许可证中,对源代码的定义是:“源代码指的是对作品进行修改最优先择取的形式,它包括:所有模块的所有源程序,加上有关的接口的定义,加上控制可执行作品的安装和编译的‘原本’(原文为‘Script’),或者不是与初始源代码显著不同的源代码就是被源代码贡献者选择的从公共领域可以得到的程序代码。”

◆ MPL许可证第3条有专门的一款是关于对源代码修改进行描述的规定,就是要求所有再发布者都得有一个专门的文件就对源代码程序修改的时间和修改的方式有描述。

BSD许可证

BSD许可证原先是用在加州大学柏克利分校发表的各个4.4BSD/4.4BSD-Lite版本上面(BSD是Berkly Software Distribution的简写)的,后来也就逐渐沿用下来。1979年加州大学伯克利分校发布了BSD Unix,被称为开放源代码的先驱,BSD许可证就是随着BSD Unix发展起来的。BSD许可证现在被Apache和BSD操作系统等开源软件所采纳。
相较于GPL许可证和MPL许可证的严格性,BSD许可证就宽松许多了,一样是只需要附上许可证的原文,不过比较有趣的是,它还要求所有进一步开发者将自己的版权资料放上去,所以拿到以BSD许可证发行的软件可能会遇到一个小状况,就是这些版权资料许可证占的空间比程序还大。

QPL许可证

QPL是The Qt Public License的简称,是挪威一家机构创设的。QPL许可证的基本要求是获得源代码、修改源代码,并可将修改从原始代码中分离出来;修改可以按照作者的意愿被组合到新版本中;二进制代码可以和原始代码同名,这一点对于动态连接库来说尤其重要;任何人都可以修正错误,这对于系统的发布者来说很关键;修改过的软件可以按照满足QPL许可证基本要求的任何开源软件许可证进行发布。
QNCL许可证

QNCL许可证是Qt Non Commercial License的简称,是QPL许可证的“兄弟版”,就像GPL许可证与LGPL许可证的关系一样,QNCL许可证比QPL许可证更严格一些。
在修改和发布方面的规定,QNCL许可证与QPL许可证是一样的,差异就在于软件的范围方面,或者说在连接方面。QNCL许可证规定“假如一个应用程序给你提供了一个入口,使你有权使用QNCL许可证下的软件的功能开发程序、重复使用程序的某一部分或其他软件的某一部分,那么对该应用程序的使用视为是使用QNCL许可证下的软件的行为,该应用程序应受到QNCL许可证的约束”。QNCL许可证比QPL许可证更严格之处在于,QNCL许可证像GPL许可证那样,完全禁止根据本许可证得到的开放源码软件与其他非系统库函数连接的软件以其他许可方式一起发布。

Jabber许可证

Jabber许可证的全称是Jabber Open Source License,由美国Jabber.Com, Inc.公司提供。Jabber许可证在源代码的复制、发行规定方面基本上和其他许可证没有什么特别,但有一些细节规定值得借鉴:
◆ 可以将通过该许可证获得的源代码及修改过的源代码与其他类型的不受该许可证约束的代码结合,以新产品的形式发布,只要其中经该许可证获得的源代码及修改过的源代码能以与该许可证的要求类似的、符合OSI认证的其他开源软件许可证的方式发布。

◆ 明确了需将源代码置于公众可以得到的状态的时间至少应为12个月。

◆ 第三方对法定权利的声明。假如使用者发现通过本许可证获得的源代码及应用程序接口中有一方拥有的知识产权,应单独在源码的发布时冠以“LEGAL”为抬头的声明,写明知识产权权利要求的细节,提请源代码的接受者知道自己获得了哪些知识产权的授权,让源码的接受者知道如何与知识产权权利人联系。

◆ 细化了该许可证终止的情形,包括不按该许可证的要求发布和使用源代码、发生专利侵权诉讼。

Common许可证

Common许可证的全称是Common Public License。在满足OSIA开源软件许可证认证标准的前提下,Common许可证还有一些细节性的规定值得参考:
◆ 明确了专利授权。一般的开源软件都明确源代码的版权人将自己的修改权、复制权等版权权利向公众许可,但保留署名权,而Common许可证在此基础上还明确假如源代码中含有专利权,源代码专利权人将复制、使用的专有权利向公众许可。

◆ 规定可以将源代码及修改过的源代码与其他类型的不受本许可证约束的代码结合,以新产品的形式发布,只要其中经该许可证获得的源代码及修改过的源代码能按该许可证的要求发布即可。

◆ 细化了该许可证终止的情形,包括发生专利侵权诉讼。

◆ 明确了一个独立承担责任的原则,就是假如按该许可证使用源代码的使用者将获得的源代码应用于商业使用,那么他就要对在商业应用中出现的由于使用该源代码程序而产生的侵权诉讼承担完全责任。这一条规定是比较特殊的,绝大多数开源软件许可证都不这么要求。

IBM许可证

IBM许可证的全称是IBM Public License。在满足OSIA开源软件许可证认证标准的前提下,IBM许可证还有如下一些细节性规定:
◆ 明确了专利授权。一般的开源软件都明确源代码的版权人将自己的修改权、复制权等版权权利向公众许可,但保留署名权,而IBM许可证在此基础上还明确假如源代码中含有专利权,源代码专利权人将复制、使用的专有权利向公众许可。

◆ 细化了该许可证终止的情形,包括不按该许可证的要求发布和使用源代码、发生专利侵权诉讼等。

◆ 像Common许可证一样,IBM许可证也明确了独立承担责任原则,即假如按该许可证使用源代码的使用者将获得的源代码应用于商业使用,那么他就要对在商业应用中出现的、由于使用该源代码程序而产生的侵权诉讼承担完全责任。

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Flash,SilverLight Coming | Internet Communion | Java & OpenSource Domain | Microsoft Domain

Here we go again ; why Mono doesn't suck

by sundy 7/3/2009 11:49:00 AM

Here we go again – why Mono doesn’t suck

This post is a repost for something I sent to Linux Today. Their original message was here, where they invited people who don’t think Mono causes AIDS to justify themselves. I replied here. This is a repost, for the benefit of assorted aggregators. Some context may be lost by not reading the original “invitation” first.

—————————————————–

I am a member of the Debian Mono Group, Debian CLI Applications Team, and Debian CLI Libraries Team. I’ve been working on packaging for the Mono stack and applications which make use of it in Ubuntu (and Debian) for just under a year. And, fully aware of the flame war, threats and personal attacks which will follow, I’m going to take you up on your “invitation”. I speak for myself here – not for the Debian project, nor Ubuntu, not for the Mono project, nor for my employer.

Your request was for “a calm presentation of why Mono is desirable, why it is not a threat, and why it should be included in Ubuntu by default”. I’ll answer these three questions individually, then offer a general comment on your post, as well as the wider “anti-Mono” movement. This message is GPG-signed to ensure it is published unedited. The message as-sent will be made available at http://retro.apebox.org/herewegoagain.txt to allow people to verify authenticity signatures themselves.

More...

Currently rated 1.3 by 4 people

  • Currently 1.25/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Java & OpenSource Domain | Microsoft Domain

The opinions expressed herein are my own personal opinions and do not represent my employer's view in anyway.
© Copyright 2007 - 2008 Design by Sundy Linghua-Zhang 蜀ICP备08108648号

About the author

Name of author Author name
Something about me and what I do.

E-mail me Send mail

Calendar

<<  May 2012  >>
MoTuWeThFrSaSu
30123456
78910111213
14151617181920
21222324252627
28293031123
45678910

View posts in large calendar

Recent comments

Authors

Disclaimer

The opinions expressed herein are my own personal opinions and do not represent my employer's view in anyway.

© Copyright 2012

Sign in