A focus on building crisp abstractions, having a good separation of concerns, having a balanced distribution of responsibilities, and a fierce drive toward simplicity. Those things are at the heart of both OO and building good architectures, with or without the use of services.
这是Grady Booch的原话。我想大师就是大师,人家一语就道出了OO和构建良好架构的核心。
谢谢大家!
今天我读到了一位朋友sudianbo84的邮件,照抄如下:
Dear Mr solol,
I am sorry to send this email to bother you due to my stupidity,however ,I really need your help .
Imitating the main() method provided by yours JNIRegistry Package , I wrote a program to modify
the Internet Explore's settings in the windows' Registry ; but with something wrong when I run my
program,I hope you can give me some help or advices! the following is the hints when my program runs
"com.ice.jni.registry.RegistryException: Registry API Error 5, 'access denied' - 'RegSetValueEx()'
at com.ice.jni.registry.RegistryKey.setValue(Native Method)
at org.solol.test.ssss.main(ssss.java:29)
com.ice.jni.registry.NoSuchValueException: RegQueryValueEx(), value='ProxyServer'
at com.ice.jni.registry.RegistryKey.getStringValue(Native Method)
at org.solol.test.ssss.main(ssss.java:47)
Press any key to continue..."
And this Is my program list:(I hope you can give me some help or advices! )
package org.solol.test;
import com.ice.jni.registry.NoSuchKeyException;
import com.ice.jni.registry.RegStringValue;
import com.ice.jni.registry.RegDWordValue;
import com.ice.jni.registry.Registry;
import com.ice.jni.registry.RegistryException;
import com.ice.jni.registry.RegistryKey;
import com.ice.jni.registry.RegistryValue;
/**
* @author solo L
*
*/
public class ssss {
/**
* @param args
*/
public static void main(String[] args) {
try {
RegistryKey IEsetting = Registry.HKEY_CURRENT_USER.openSubKey("Software").openSubKey("Microsoft").openSubKey("Windows").openSubKey("CurrentVersion").openSubKey("Internet Settings");
IEsetting.setValue("ProxyServer", new RegStringValue(IEsetting,"ProxyServer","127.0.0.1:8080"));
IEsetting.setValue(new RegDWordValue(IEsetting,"ProxyEnable", RegistryValue.REG_DWORD,1));
IEsetting.closeKey();
} catch (NoSuchKeyException e) {
e.printStackTrace();
} catch (RegistryException e) {
e.printStackTrace();
}
try {
RegistryKey IEsetting = Registry.HKEY_CURRENT_USER.openSubKey("Software").openSubKey("Microsoft").openSubKey("Windows").openSubKey("CurrentVersion").openSubKey("Internet Settings");
//RegistryKey IEsetting = software.openSubKey("SubKeyName");
RegistryValue proxyenable = IEsetting.getValue("ProxyEnable");
String proxyserver = IEsetting.getStringValue("ProxyServer");
System.out.println(proxyenable.toString());
System.out.println(proxyserver);
IEsetting.closeKey();
} catch (NoSuchKeyException e) {
e.printStackTrace();
} catch (RegistryException e) {
e.printStackTrace();
}
}
}
这是由于我在文章用Java操作Windows注册表中犯了一个错误。
出错内容为:
RegistryKey openSubKey(java.lang.String subkey) 打开该key的subkey,具有写权限。
应该为:
RegistryKey openSubKey(java.lang.String subkey) 打开该key的subkey,具有读权限。
我已经对文章进行了更新。
sudianbo84朋友要解决你的问题可以使用下面的代码:
RegistryKey currentVersion = Registry.HKEY_CURRENT_USER.openSubKey("Software").openSubKey("Microsoft").openSubKey("Windows").openSubKey("CurrentVersion");
RegistryKey inetSetting = currentVersion.openSubKey("Internet Settings",RegistryKey.ACCESS_WRITE);
inetSetting.setValue(new RegStringValue(inetSetting, "ProxyServer", "127.0.0.1:8080"));
inetSetting.setValue(new RegDWordValue(inetSetting, "ProxyEnable",RegistryValue.REG_DWORD, 1));
再次感谢大家!谢谢!
今天,眼睛接收文字的速度快过大脑好多倍。
如下的图片和两段文字源于IBM中国,可参见Architecture 新手入门。
之所以采取这种方式构建系统,是因为没有对它们进行很好的规划。它们通常由缺乏必备技能和资源的人匆忙地构建以满足即时之需,而没有考虑到长期成功所必需的质量。构建此类系统的团队要么是人员太少,要么就是人员太多,从而减弱而不是增强了最有才能的团队成员的影响。
从上图可以看出,在团队开始构建系统之前,必须进行体系结构设计。在构建系统时,需要由少数(或许就是一个)预言家来领导设计团队以避免此类大杂烩。该预言家的头脑中必须有一个全盘计划,而不是每一个具体细节,更多的是有关需要什么以及如何实现的总体思想。并由该预言家来负责系统的体系结构。在开始构建系统之前有了这样的预言家,并且已经有一个准备好的体系结构,就可以井然有序地构建一致、可理解的系统——在新需求出现时可由该团队或其他团队修改的系统。
我们不是上面所提到的预言家,至少目前不是,不过我们需要被一个这样的预言家领导。
PoolTcpEndpoint是Tomcat中的TCP Server。主要负责:
PoolTcpEndpoint代码可能不容易读懂,因为这里有两个并发模型的实现。一个是Leader Follower Worker模型,一个是Master Slave Worker模型。前者的线程管理由ThreadPool来完成的,而后者的线程管理是在PoolTcpEndpoint中完成的。两者共同使用在PoolTcpEndpoint中定义的接收Socket逻辑和调用ConnectionHandler逻辑。
PoolTcpEndpoint作为TCP Server只负责处理TCP连接。更加进一步的处理,如相关协议的解析等,由ProtocolHangler和Processor完成。最后由Adapter将处理代理给Container。
PoolTcpEndpoint是Tomcat的核心机构。
这个标题可能不是很确切。确切的说法应该是Commons Digester中的策略模式。
Commons Digester是Apache Jakarta的一个XML到Java Object的映射工具包。
Tomcat和Struts都使用这个工具包来处理XML配置文件。在Tomcat中并没有直接使用Digester的*.jar文件而是将Digester做了一些简化放到了org.apache.tomcat.util.digester包中。我们下面的讨论是基于org.apache.tomcat.util.digester包的,这也是我们使用这个标题的用意,但是这里的讨论也完全适用于Digester。
具体的结构图如下:
这里涉及到两个策略模式。Rules是一个策略,封装了选择Rule的逻辑,可以通过定制Rules来实现自定义匹配逻辑。Rule是另一个策略,这是显而易见,封装了某种操作。如果需要自定义Rule那么必须认真考虑相关堆栈的状态。通常的做法是谁改变谁负责恢复。
关于模式的相关问题可以参阅面向对象设计(Object-Oriented Design)。如果您对这里的内容感兴趣可以和我们联系!
今天的话题非常有趣!这和当初读Java VM规范中关于Class Loader部分时的感觉一样。如果需要可以将Java Class放到数据库中或网络上,等等,当然还可以想到更多 ... ,只是不放到文件系统中。如果没有需要就不要这么做,否则会很无聊。
该话题源于这里The Resources Component。
通常使用tomcat只需要把web应用程序拷贝到$CATALINA_HOME/webapps目录下,此时web应用程序是以文件的形式存在于文件系统之中。我们对此已经习以为常了,然而tomcat还允许使用其它的方式:
如果您要对相关web应用程序进行加密,这里也提供了一种可行的方法。例如可以将web应用中的每一个文件加密后压缩到一个zip文件中,也可以先将整个web应用置于zip文件中在对zip文件加密。
要完成上面描述的内容,需要自己实现javax.naming.directory.DirContext接口。在此之前可能需要仔细研究一下tomcat提供的一些实现,如FileDirContext和WARDirContext等。
这个话题中的内容是tomcat相关的,如果您不使用tomcat,那么您需要仔细查阅您的web服务器的文档。
最后,我们必须告诉大家:我们没有实现过上面描述的内容,因此也不知道将会遇到什么样的困难。这里只是描述一种可能。
在上一篇中我们谈到了Tomcat中的观察者模式,这里标题中的“二”并不表示我们要继续上一篇的相关内容,仅仅表示我们要讨论Tomcat中的另外一个观察者模式。
上一篇中的观察者模式用来报告生命周期事件(Lifecycle Event),这里的这个观察者模式用来报告容器事件(Container Event),这两者是完全不同的。
具体的结构图如下:
和上一篇相比这里和GoF的描述是完全一致的,由Subject参与者负责管理Observer参与者。不过这里也实现了复用,这种复用是通过继承完成的。所有的管理逻辑都在ContainerBase。
关于模式的相关问题可以参阅面向对象设计(Object-Oriented Design)。如果您对这里的内容感兴趣可以和我们联系!
观察者模式擅长进行对象生命周期的管理。
Tomcat需要对Server、Service、Engine、Host和Context等进行生命周期的管理。这种管理是通过Lifecycle(Subject)、LifecycleListener(Observer)和LifecycleEvent来实施的。
具体的结构图如下:
在GoF给出的观察者模式中要由Subject参与者负责管理Observer参与者,这里也不例外。只不过Subject参与者的管理职责被委托给了LifecycleSupport而由后者负责具体的实现。这样多种Subject可以复用LifecycleSupport。
关于模式的相关问题可以参阅面向对象设计(Object-Oriented Design)。如果您对这里的内容感兴趣可以和我们联系!
职责链模式在Tomcat中用来处理请求(Request)和响应(Response)。该模式出现在Tomcat的四个Container中,它们是:
下面我们给出具体的结构图:
值得注意的是,和GoF给出的职责链模式的描述相比,这里多出了一个参与者Pipeline,它主要负责整个职责链的管理。从客户的角度来讲,这是非常有益的,因为客户不必在自行维护整条职责链。如果有多种客户在使用相同的职责链这种益处就更加明显。
关于模式的相关问题可以参阅这里[ http://www.solol.org/technologic/ood/ ]。这里的内容还只是在有限的范围内发布,没有放到公共域中,因为绝大多数内容还没有完成。如果您对这里的内容感兴趣可以和我们联系!