rubygem的小细节

我在linux上安装了rubygem以后, 发现一个问题,单独写的ruby文件无法以相对路径require gem上的包
比如
require 'something' 不行,必须以绝对路径 require '/usr/local....../something' 才可以
我查询了ruby的loadpath ("$:") ,发现这个路径并不在RUBY的loadpath中, 按道理说不能require是正确的

但是为什么在我的windows上面或者在rubyonrails程序中的就可以这样require了呢,经过一番google再加上自己多次试验,终于发现了其中的缘故

原来windowsXP下面有一个环境变量 RUBYOPT='rubygems' 而linux下面没有, 在linux下面加上RUBYOPT以后,发现可以工作, 进一步发现只要在require其他类以前先require 'rubygems' 程序也能自动识别gem包内的库, 看来,rubygems 对require函数作了手脚, 总结如下

RUBYOPT中'rubygems' 实际上引用的是 ubygems.rb这个文件,在ubygems.rb中再require 'rubygems' 相当于作了一个alias

在rubygems.rb中, 对Kernel模块作了如下调整
1增加了require_gem的指令,这个指令支持按照指定版本号require
2在文件末尾, require了 'custom_require'

在custom_require.rb中, 对require函数作了修改,代码如下

module Kernel 
  alias require__ require 
  
  
def require(path) 
    require__ path 
  rescue LoadError 
=> load_error 
    begin 
      @gempath_searcher 
||= Gem::GemPathSearcher.new 
      
if spec = @gempath_searcher.find(path) 
        Gem.activate(spec.name, true, 
"= #{spec.version}"
        require__ path 
      
else 
        
raise load_error 
      end 
    end 
  end 
end 


在上面的代码中, require函数被更新, 当不能从RUBY内部的loadpath中读取文件时, require会从gempath中查找, 这样require函数就能支持gem了

结论: 要使用gem中的包, 3个办法
1 使用RUBYOPT='rubygems'
2 先require 'rubygems' 或者 'ubygems'
3 使用require_gem

posted @   tech.cap  阅读(211)  评论(0编辑  收藏  举报
编辑推荐:
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
阅读排行:
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 地球OL攻略 —— 某应届生求职总结
· 提示词工程——AI应用必不可少的技术
· Open-Sora 2.0 重磅开源!
· 周边上新:园子的第一款马克杯温暖上架
点击右上角即可分享
微信分享提示