我总是怀疑创建包时,我想利用包限制访问,但同时我希望将类似的类分成包。 当您了解Java中的包不是分层的时候会出现问题:
首先,包似乎是 等级,但他们不是。 source
想象一下,我在foo.bar上定义了一个带有类的API,只有API客户端需要的类才被设置为public。然后我在foo.bar.pojos定义的API中有另外一个包含我需要的内部对象的包,这个类需要是公共的,因此可以通过foo.bar访问它们,但这意味着如果包,API客户端也可以访问它们foo.bar.pojos已导入。
应该遵循的共同政策是什么?
答案 0 :(得分:4)
我见过两种做法。
第一个包括将公共API和内部类分成两个不同的人工制品(罐子)。文档也是分开的,因此最终用户很容易区分内部和非内部。但它有时会让两个罐子,两个源树等等变得更复杂。
第二个包括提供一个罐子,但有一个很好的文档,可以知道什么是内部的,什么不是。文本文档可以解释如何使用API(从而避免讨论内部)。并且javadoc可以指定一个类供内部使用,因此可以进行更改。
答案 1 :(得分:2)
是的,Java包不能让您对依赖项进行足够的控制。解决这个问题的经典方法是将外部API放在一个包中,将内部实现类放在另一个包中,并依靠人们的良好意识来避免在后者上创建依赖关系。
使用Maven和OSGI,您可以使用其他机制来管理模块/软件包之间的依赖关系。对于OSGI,您可以显式声明某些包未导出,并且OSGI感知开发环境将阻止人们创建有害的依赖项。 Maven的模块支持较弱,但至少它控制了依赖循环。
最后,您可以使用自定义PMD规则来强制执行项目的模块化约定......就像有规则来阻止对Java的“com.sun。*”包树的依赖一样。
答案 2 :(得分:1)
这是一团糟。
仅使用Java本身提供的内容,您必须将所有内容放在同一个包中。你最终会得到一个包含大量类的单个(或几个)包,并且没有好的方法可以自己对它们进行分组(但至少这个问题不会泄漏到外面)。但是,大多数人并不这样做,因此,您(作为这些库之上的开发人员)公共类路径中充斥着您根本不需要看到的内容。
您可能喜欢OSGi,它拥有(并强制执行)bundle-private包的概念。那些不会出口到外面。