Ruby 沙盒与集成脚本语言 [英] Ruby sandboxing vs. integrating a scripting language

查看:17
本文介绍了Ruby 沙盒与集成脚本语言的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我目前正在使用 Ruby 开发基于文本的游戏引擎,将应用程序分为/lib 中的 Ruby 代码和/data 中的 YAML 数据,这些数据在游戏需要时加载.我希望允许数据文件包含基本脚本,主要是在事件/观察者模型中.但是,我也希望用户能够生成和共享自定义场景,而不必担心脚本中嵌入的恶意代码.

I am currently working on a text-based game engine in Ruby, with the app separated into Ruby code in /lib and YAML data in /data, which is loaded when needed by the game. I want to allow the data files to contain basic scripts, mostly in an event/observer model. However, I also want users to be able to generate and share custom scenarios without having to worry about malicious code embedded in the script.

附录:我最初的计划是将用户创建的内容分为两种类型,模块"是纯数据(因此是安全的)和添加附加功能的插件(但显然是不安全).与桌面游戏类比,模块类似于已发布的冒险场景和内容,而插件则是包含附加规则和系统的规则手册.

Addendum: My original plan was to have user-created content separated into two types, "modules" which were data-only (and thus safe) and plugins which added additional functionality (but obviously were not safe). To make an analogy to tabletop gaming, modules would be like published adventure scenarios and content, and plugins would be rulebooks containing additional rules and systems.

示例脚本(当然语法可能会根据解决方案进行更改):

Sample script (syntax of course subject to change based on solution):

---
Location:
  observers:
    on_door_open: |
      monster = spawn_monster(:goblin);
      monster.add_item(random_item());
      monster.hostile = true;

从安全的角度来看,如果脚本是严格选择加入的,可能是通过包含一个带有少量 DSL 的 mixin,例如:

From a security standpoint, it would be ideal if scripting was strictly opt-in, probably through an included mixin with a little DSL, e.g.:

class Frog
  include Scriptable

  def jump; ... ; end # this can be called from a script
  allow_scripting :jump

  def ribbit; ... ; end # this cannot be called from a script
end

我查看了三个四个选项,但我不确定哪一个是最好的方法:

I've looked at three four options, but I'm not sure which is the best approach to take:

  1. 使用 Ruby 脚本,但在某种沙箱中.

  1. Use Ruby scripting, but in a sandbox of some kind.

优点:非常熟悉 Ruby,不需要粘合"代码或在语言之间集成对象的问题.

Pros: Very familiar with Ruby, no need for "glue" code or issues integrating objects between languages.

缺点:对安全问题或沙盒不是很熟悉,还没有找到任何适合的现成解决方案.

Cons: Not very familiar with security issues or sandboxing, haven't found any out-of-the-box solutions that seem to fit.

Implement 嵌入另一种脚本语言,例如路亚.

Implement Embed another scripting language, e.g. Lua.

优点: Ruby 和 Lua 是基于 C 的,因此绑定应该相当简单.Lua 是一种相当流行的语言,所以如果我以后遇到问题,可以获得帮助.安全,因为我没有专门绑定的任何功能都将无法从脚本中使用.

Pros: Ruby and Lua are C-based, so bindings should be reasonably simple. Lua is a reasonably popular language, so help available if I run into issues later. Secure, since any functionality I don't specifically bind will be unavailable from scripts.

缺点:现有的 Ruby-Lua 绑定似乎是单向的、陈旧的和维护不善的,或者两者兼而有之.将一种脚本语言嵌入另一种脚本语言中似乎有点狡猾.

Cons: Existing Ruby-Lua bindings seem to be one-way, old and poorly maintained, or both. Seems a mite dodgy to embed a scripting language inside another scripting language.

使用 Ruby 解释器实现自定义脚本语言.我一直在试验 Treetop,制作一个足以满足脚本的简单语法应该不会太难.

Implement a custom scripting language with Ruby interpreter. I've been experimenting with Treetop, and it shouldn't be too hard to make a simple grammar that would suffice for the scripts.

优点:无需嵌入另一种语言.只有我专门实现的功能可用于脚本.

Pros: No need to embed another language. Only functionality I've specifically implemented will be available to scripts.

缺点: 矫枉过正.不是建在这里"综合症.可能是一堆可怕的错误等着发生.

Cons: Overkill. "Not built here" syndrome. Probably horrible nest of bugs waiting to happen.

使用特定于领域的语言完全在 Ruby 中实现数据文件.

Implement the data files entirely in Ruby, using a domain-specific language.

优点:简单易行.

缺点:没有任何用户创建的数据是可信的.

Cons: No user-created data is trustable.

我也愿意接受我可能没有想到的不在该列表中的其他建议.安全实现嵌入在数据文件中的脚本的最佳解决方案是什么?

I am also open to other suggestions not on that list that I may not have thought of. What is the best solution to safely implement scripts embedded in data files?

编辑 2011 年 12 月 23 日: 添加了第四个选项与 DSL,在顶部添加了附录"以及其他想法/上下文.

Edit 2011年12月23日: Added fourth option with DSL, added "addendum" at top with additional thoughts/context.

推荐答案

您可以考虑使用 Shikashi gem,它允许您创建沙箱并定义单个对象上允许的方法调用的白名单.

You might consider using the Shikashi gem, which allows you to create sandboxes and define a whitelist of allowed method calls on individual objects.

这篇关于Ruby 沙盒与集成脚本语言的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆