在asp.net中创建动态表单c#

M.R*_*.R. 7 vb.net asp.net webforms web-applications dynamic

所以,我需要一些输入重构一个asp.net(c#)应用程序,它基本上是一个用于创建动态表单(任何表单)的框架.从高层的角度来看,有一个表格有表格,然后有一个表格,其中包含所有表格字段,两者之间是一对多.有一个验证表,其中每个字段可以有多种类型的验证,从表单字段表到验证表是一对多.

所以问题是这个应用程序已经作为所有客户端的所有可定制解决方案出售.所以,这个想法是他们想要的任何形式,我们可以使用数据库配置来构建它.问题是,这并不总是可行的,因为字段之间存在复杂的关系,而且表单本身之间存在复杂的关系.此外,只有一次代码库,这适用于多个客户端 - 所有客户端都是自己托管的.每个客户端都有非常特定的逻辑,它们在同一个代码库中是ALL,没有真正的分离.有时候将它设置为通用是太困难了,因此有些情况下它具有硬编码逻辑(如果formID = XXX则执行_).您还可以在每个表单中拥有嵌套表单,例如,一组字段.

通常,当一个客户端请求更改时,我们进行更改并将其部署到该客户端 - 但是然后另一个客户端请求不同的更改,我们进行更改并将其部署到该客户端,但是从早期客户端的更改中断它是一个令人头疼的尝试调试,因为一切都是动态的.我们无法回滚早期的更改,因为那时其他客户端将被搞砸.

它不是在真正的3层架构中完成的 - 它是一个引用数据库类的网站,以及一个类库.网站本身,类库中存在业务逻辑,数据库存储过程(验证在存储过程中完成).

我一直负责重新组织整个事情,这些是我的想法/问题:

  1. 我认为这通常是一个糟糕的模型,因为我听到其中一位开发人员说过的一件事是,任何客户都做出改变,我们应该部署给所有人 - 但如果我们说20个客户,这是不现实的 - 需要对一切进行回归测试,因为我们不知道影响......

  2. 总共有大约100种形式,它们之间有一些相似之处(不多).但我认为动态引擎可以解决所有表单请求的想法也不现实.客户提出了最奇怪的要求.例如,他们使用此引擎执行常规数据输入表单和搜索表单.

  3. 页面之间有很多保留状态,并且它都是使用会话变量完成的,这是好的,除了它没有被真正跟踪,因此来自同一用户的会话不断被覆盖,我认为会话应该被删除的.

  4. 我真的应该重写整件事吗?这个应用程序大约3岁,已经进行了大量的测试和事情,并且实施了严格的业务逻辑,所以我讨厌摆脱所有这些(joel的建议).但它真的是一堆sphagetti代码,一切都需要永远做,事情因为微小的变化而一直在破碎.

我一直在阅读Martin Fowlers"Refactoring"和Michael Feathers"使用遗留代码有效地工作" - 而且它们很好,但我觉得它们是针对一个'略微'更好的架构的应用程序编写的,它仍然是一个3-分层架构,并且存在"某种"逻辑相似性.

思考/输入任何人?

哦,还有"救命!"

Sim*_*sey 5

我有许多类似的应用程序用于构建我支持的动态表单。

有很多事情你可以做/不能做,在放弃 3 年的测试/开发之前,你应该认真思考一下。

我建议您考虑的是在您现有的基础上实现一个插件架构。表单的任何自定义代码都会放入插件中,并且该插件的名称与表单一起存储。当您生成表单时,会调用正确的插件来增强基本功能。这样您就可以将所有自定义代码移出现有库。它还应该意味着更少的破坏性更改,每个插件仅影响其附加的表单。

从那时起,重构核心引擎将很容易,因为它是所有客户端和表单的通用功能。


Str*_*ior 5

我当前的项目听起来与您描述的产品几乎完全相同。幸运的是,我从以前的产品中学到了大部分最难的课程,因此我能够从头开始我的当前项目。您可能应该通读我对这个问题的回答,其中描述了我的经历和我学到的教训。

要关注的主要事情是您正在构建产品的想法。如果您无法找到一种使用当前产品功能集实现特定功能的方法,您需要花一些额外的时间思考如何将这个自定义的一次性功能转变为一个可以使所有人受益的可配置功能(或在最少)您的客户。

所以:

  1. 如果您指的是能够创建一个完全可定制的表单,使特定于客户的代码几乎没有必要的模型,那么该模型是完全有效的,并且我有一个可维护的工作产品,它有真实的付费客户可以证明这一点。回归测试是针对特定功能和配置组合进行的,而不是针对特定的客户端实现。使这成为可能的关键部分是:
    1. 一个管理界面,可有效禁止有问题的配置选项组合。
    2. 一个规则引擎,允许系统中的某些操作调用可定制的触发器并导致其他操作发生。
    3. 一个集成框架,允许从各种来源提取数据并以可配置的方式推送到各种来源。
    4. 绝对必要时将自定义代码作为插件注入的选项。
  2. 是的,客户提出了奇怪的要求。建议替代解决方案通常是值得的,这些解决方案仍然可以解决客户的问题,同时仍然允许您的产品对其他客户来说是健壮的和可配置的。有时你只需要推回。其他时候你必须按照他们说的去做,但使用明智的架构实践来最小化这可能对其他客户端代码的影响。
  3. 尽量减少使用会话来跟踪状态。每个页面都应该有足够的信息来跟踪当前页面的状态。即使用户单击“返回”并开始执行其他操作,也需要保留的信息应该存储在数据库中。然而,我发现在会话中保留一种面包屑树,跟踪用户如何到达特定地点以及在他们完成后将他们带回哪里很有用。但是他们实际所在节点的 ID 当前需要逐页保留,并随每个请求发送回,因此当用户浏览不同选项卡中的不同页面时,不会发生奇怪的事情.
  4. 使用增量重构。完成后,您可能最终会重新编写整个内容两次,或者您可能永远不会真正“完成”重构。但与此同时,一切仍然有效,您将时常拥有新功能。通常,重写整个内容会花费您数倍的时间,因此不要试图一口气读完整个内容。