Ruby 删除所有加载的定义和常量

Ruby 删除所有加载的定义和常量,ruby,Ruby,我有一个ruby脚本,它接受plugin1.rb并加载它。然后我将调用run,plugin1将完成它的任务 之后,我可能会决定加载plugin2.rb,然后调用run,让plugin2完成它的工作 这两个插件彼此无关,只是它为我提供了一个run方法来实际执行它们,但是它们可以根据自己的需要定义它们的类和常量 没有理由不存在类冲突之类的问题,所以我认为最好的办法是在插件运行完毕后进行清理 我应该如何编写ruby脚本,以便在它实际加载一个插件之前,它能够正确地清理上一个会话中的任何内容,从而为新脚本

我有一个ruby脚本,它接受plugin1.rb并加载它。然后我将调用
run
plugin1
将完成它的任务

之后,我可能会决定加载
plugin2.rb
,然后调用
run
,让
plugin2
完成它的工作

这两个插件彼此无关,只是它为我提供了一个
run
方法来实际执行它们,但是它们可以根据自己的需要定义它们的类和常量

没有理由不存在类冲突之类的问题,所以我认为最好的办法是在插件运行完毕后进行清理

我应该如何编写ruby脚本,以便在它实际加载一个插件之前,它能够正确地清理上一个会话中的任何内容,从而为新脚本做好准备

我想知道我需要移除什么样的东西,以及如何移除它们

更新

环顾四周,我可以得到一个使用
Object.constants
定义的常量列表,其中包括已加载的所有类和模块

所以我在想一些关于

# get start-up constants
initial_consts = Object.constants

# load a plugin
load "plugin1.rb"

# get new constants
new_consts = Object.constants - initial_consts

# run plugin
test = NewClass.new #defined in plugin
test.run

# clean-up new things
new_consts.each {|c| Object.send(:remove_const, c) }
这不会“还原”任何已更改的类,但我的设计阻止插件使用某些名称定义类或方法,因此这应该不是一个太大的问题。

不,不,不。这太糟糕了。首先,今天尝试编写代码,目标是明天接受完整的狗屎代码,这是错误的。您可以编写更容易理解、更聪明、更可扩展的代码,但不要被发现试图编写比下一个开发人员更聪明的代码

现在请回到绘图板上。忘记你所知道的关于“插件”的一切,忘记你所学到的关于PHP、C或其他动态性较差的语言的一切。你需要什么?你如何以一种今天有效,明天可以扩展的方式解决这些问题?做那件事,别再做什么该死的事了。您是要为所有类使用全局名称空间编写代码,还是要将它们封装在以库命名的模块中以防止出现这种情况


你可以使用各种工具来锁定环境,比如洁净室,但我认为你甚至不需要这些。我认为你真的需要停止为模棱两可的需求编写代码,而雄心勃勃的目标是处理各种可能性

我认为你不应该这样做。每个库都应该在某个具有不同名称的模块下定义类作为名称空间,这样就不会发生冲突。这就是为什么gem并不都倾向于互相攻击。每个插件的主要问题是,每个插件都在读取使用封送处理序列化的数据,但数据本身采用全局名称空间,因此当使用封送处理加载它们时,它们几乎假定所有类都在全局名称空间中。我可以从两个不同的文件中读取数据,它们的类名完全相同,但类层次结构、签名、实例变量和常量完全不同。每个插件都定义了正确读取正确数据的类。我无法控制输入的设计方式。