有没有相当于红宝石之地的捆绑器等的哈斯克尔土地。如果不是,那么如此结构化的项目将如何设计?



读者注意:耐心听我说。我保证有问题。


我有一个问题要解决,我想"哦,我要用Ruby来做。">

$ bundle gem problemsolver
create  problemsolver/Gemfile
create  problemsolver/Rakefile
create  problemsolver/.gitignore
create  problemsolver/problemsolver.gemspec
create  problemsolver/lib/problemsolver.rb
create  problemsolver/lib/problemsolver/version.rb
Initializating git repo in /tmp/harang/problemsolver

删除problemsolver/problemsolver.gemspecs.add_development_dependency "rspec"的注释,然后

$ bundle exec rspec --init
The --configure option no longer needs any arguments, so true was ignored.
create   spec/spec_helper.rb
create   .rspec

新的测试进入spec/并且必须在以_spec.rb结尾的文件中。例如,spec/version_spec.rb

describe 'Problemsolver' do
it 'should be at version 0.0.1' do
Problemsolver::VERSION.should == '0.0.1'
end
end

运行specs——忽略像guard这样的代码更改运行器——是微不足道的:

$ bundle exec rspec
.
Finished in 0.00021 seconds
1 example, 0 failures

你看不见它,但是这个信息很好地用彩色编码进行了快速的"我搞砸了吗?"扫描。它的优点是:

  • 设置是快速的,几乎没有大脑(虽然弄清楚调用哪些命令不是微不足道的)。
  • 标准化的源代码树布局减少了对新代码库的熟悉期,使协作更简单,并减少了在选择您已经离开一段时间的项目时的停顿时间。
  • 对工具的严重依赖通过社区分发最佳实践,大致以新项目创建的速度分发。

添加覆盖工具、代码监视器、检查器、行为测试工具和其他工具并不困难。


这与人们认为"哦,我将在Haskell中实现"的情况形成了不利的对比。

$ mkdir problemsolver
$ cd problemsolver/
$ cabal init
Package name [default "problemsolver"]? 
Package version [default "0.1"]? 0.0.1
Please choose a license:
1) GPL
2) GPL-2
3) GPL-3
4) LGPL
5) LGPL-2.1
6) LGPL-3
* 7) BSD3
8) MIT
9) PublicDomain
10) AllRightsReserved
11) OtherLicense
12) Other (specify)
Your choice [default "BSD3"]? 
Author name? Brian L. Troutwine
Maintainer email [default "brian@troutwine.us"]? 
Project homepage/repo URL? 
Project synopsis? Solves a problem.
Project category:
1) Codec
2) Concurrency
3) Control
4) Data
5) Database
6) Development
7) Distribution
8) Game
9) Graphics
10) Language
11) Math
12) Network
13) Sound
14) System
15) Testing
16) Text
17) Web
18) Other (specify)
Your choice? ProblemSolver
ProblemSolver is not a valid choice.
Your choice? 18
Please specify? ProblemSolver
What does the package build:
1) Library
2) Executable
Your choice? 2
Generating LICENSE...
Generating Setup.hs...
Generating y.cabal...
You may want to edit the .cabal file and add a Description field.

"太好了,"你想,"我被烦死了,我敢打赌所有最新的Haskell软件开发最佳实践都在我的磁盘上等着我。">

$ ls
LICENSE  problemsolver.cabal  Setup.hs

请允许我总结一下我的感受::(

生成的cabal文件甚至没有指定Main,更不用说用于设置基本项目的指令。不过,好吧。如果你在寻找正确的搜索关键字上花了一点时间,你会发现如何编写一个Haskell程序,除了:

  • 所有的Haq源代码被扔到根目录。
  • Haq的测试代码仅在Test.hs中,仅是QuickCheck,并且没有使用拆分文件测试继续项目的设施。
  • 所有这些都必须为每个新项目手工编写或复制。

查看真实世界Haskell的第11章,你会发现它甚至没有提到cabal,并且完全回避了项目布局的问题。Don Stewart在这里善意回答的所有资源都没有在上述任何一个中提到,而且我要注意的是,Stewart先生没有解释如何使用所引用的任何工具。

请注意,Haskell测试工作流中可接受的答案引用了一个项目,该项目已经足够移动,因此不是一个好的答案,但确实表示

因为cabal测试还不存在——我们有一个学生在为今年夏天的代码工作!——我们最好的机制是使用cabal的用户钩子机制。

嘿,好吧,秘社的文档!适当的部分确实有例子,但它们非常做作,但不会给人留下每个人都是自己的印象,祝你好运。

当然,总有一些测试框架看起来不错,但它的示例代码除了在wiki上看到的之外并没有提供任何东西,而且在某种意义上是不可扩展的,因为一旦我的程序变得越来越复杂,我就不得不开发将测试划分为可管理模块的方法。我甚至不确定HTF发生了什么,我同意沃尔科夫先生的评估。

。Jelvis对链接的HTF问题的评论引起了我的特别兴趣:Haskell工具链非常严重地受到小决策暴政的影响。实际上,我无法着手手头的任务——在Haskell中解决我的问题——因为我正忙于使我的环境正确。为什么这样不好:

  • 这是白费力气。除非我正在编写一个测试工具,否则我很少关心我的测试是如何被吞掉的,只关心从的位置。
  • 这很难学。似乎没有单一的资源来建立一个包含测试的项目,并且存在的各种资源足够多样化,以至于没有帮助。
  • 很难繁殖。有这么多活动的片段要安排,我每次都要做得不同。
  • 作为推论,它是特殊的。这意味着很难进行合作,也很难启动休眠项目。

这简直太臭了。

也许我错了。在Haskell领域,是否存在一些宣传不佳的工具或紧密开发的工具来做类似于Bundler+Rspec的事情?如果没有,有没有一个广告宣传不好的现代Haskell测试的典型例子,其中包含了Stewart先生提到的所有好东西?创建或演示的项目:

  • 应该按照约定和工具以良好定义的方式将测试代码与应用程序代码分开(在ruby领域,Rspec测试放在spec/中,Cucumber特性放在features/中),
  • 不应该要求最终用户编译和安装测试依赖
  • 应易于复制,最好不超过10分钟,
  • 应标准化或有标准化的希望。

我相信Haskell-land根本没有这样的东西,我错了吗?


Edit0:请注意,Ruby语言的社区并不是唯一适用的比较。保罗·R.正确地指出了配置胜过约定的强大潮流。其他语言以其他方式解决了获得可伸缩项目结构的问题:

  • C::这种语言是古老的,而且有很好的文档,因此您很难确定采用哪种有很好的文档的方法。没有这样的工具。
  • Java:: Configuration over convention:在编译器级别绑定到它。许多工具和非常良好的文档。
  • Scala:强大的工具支持。
  • Erlang::如果你知道你在寻找什么,它是值得尊敬的和松散的文档。如果您使用螺纹钢或以其他方式瞄准OTP,则可以说配置优于约定。

保罗·R。如果像C语言一样,有足够的文档来编译这样的东西,那么使用自定义模板的解决方案非常有效。这仍然会遇到我试图在帖子中明确指出的问题,但它是可行的。据我所知,Haskell最好的作品是《如何编写一个Haskell程序》,但它远远不如把一个孤身的童子军扔到树林里,手里拿着手电筒和一瓶水。

同样,静态类型很好,确实解决了许多需要显式测试的问题。如果它们是最终的解决方案,或者甚至是基本足够的解决方案,那么快照框架就不会经过如此彻底的测试。(可以说"Copy snap-core."是对我问题的回答。)

目前没有一种单一的方法来设置测试套件。希望人们能够对cabal test进行标准化,因为它是现成的。事实上,Haskell平台也提供了HUnitQuickCheck,因此设置测试不需要下载任何额外的依赖项。

你是正确的,一个旧的被接受的答案不提供关于cabal test的信息。我编辑了它,现在它做到了!您也可能是正确的,Haskell wiki上的链接页面(也是在cabal test可用之前编写的)没有提供有关当前测试最佳实践的信息。这是一个wiki,我鼓励大家来编辑它!请注意,该页确实提供了一个链接到另一个页面,该页面描述了如何构建更复杂的Haskell项目。

tldr;使用cabal test。我喜欢test-framework,如果你愿意,可以和cabal test集成。很抱歉,cabal test是一种新的,并不是我们所有的资源(通常是社区可编辑的)都已经更新到指向它并描述如何使用它。更新大量资源和创建教程是社区的工作。我们应该更好地推广过去几年引入Haskell生态系统的许多新工具。

这里有很多要点。首先,将约定优于配置与显式配置进行比较。在红宝石王国,前者往往更受青睐。根据我的经验,尽管它对于do- {blog|social-thing|gem|library}- In -5-min -screen - cast和快速实验非常有效,但它在实际项目(超过5分钟)中的价值要小得多,因为初始化时间很快就会摊平。此外,工具提供配置工具还有一个原因:有许多不同的需求和用法。所以我对您的cabal-init问题的建议是:制作您自己的模板文件。把你需要的东西放在存根上,有很好的注释,需要的时候就用它。

关于测试,ruby和haskell之间的环境非常不同。在ruby中,可以编写foo do { oh dear I am typing nonsense here },除了实际运行代码之外,没有其他方法可以捕获这些无意义的代码。所以自动化测试是绝对需要的。然而,在haskell领域,你的代码有一个很好的静态分析,加上一个非常合理的范式(纯函数式的非严格的),在使用它多年之后,我仍然惊讶地发现,要写一些没有意义的东西而不被编译器立即捕获是多么困难。我在工作中也使用ruby,实际上,我90%的测试都是手工的"静态检查"。

尽管如此,仍然存在错误设计或角落错误的空间,这就是快速检查存在的原因。它会自动地(是的,真的是自动地)发现角落错误,并帮助你发现设计错误。如果您需要手动检查,您仍然可以使用现有包之一编写单元测试。

所以我的结论是:如果你在haskell土地上遮荫红宝石光,不要惊讶地发现阴影无处不在。这里的情况非常不同,需要有经验才能掌握权力。这并不意味着一切都是完美的,实际上改进工具链是一个普遍表达的愿望。你提出的观点并没有什么问题,也不值得你用那么多词汇。先试后判

最新更新