<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>liy_j</title>
    <link>https://ruby-china.org/liy_j</link>
    <description></description>
    <language>en-us</language>
    <item>
      <title>关于 Ruby 文档中 JSON 模块中方法的疑惑</title>
      <description>&lt;p&gt;在&lt;a href="http://ruby-doc.org" rel="nofollow" target="_blank"&gt;http://ruby-doc.org&lt;/a&gt;”中看 JSON 模块文档时，JSON 可以响应 Public Class Methods 方法和 Public Instance Methods 方法，按道理说只能响应 Public Class Methods 方法才对啊？
难道是我看文档的姿势有误？??
还望各位前辈答疑解惑。&lt;/p&gt;

&lt;p&gt;比如说：module 中类方法只有 module 自己才可以调用，而在模块中定义的实例方法，在包含模块的类的实例对象才可以调用；module 是不能响应自己的实例方法的。&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="k"&gt;module&lt;/span&gt; &lt;span class="nn"&gt;My&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nc"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_class_method&lt;/span&gt;
   &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_instance_method&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="no"&gt;My&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;respond_to?&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="ss"&gt;:my_class_method&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;#true&lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="no"&gt;My&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;respond_to?&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="ss"&gt;:my_instance_method&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;#false&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;如下图中 红色圈为 Public Class Methods 方法，荧蓝色为 Public Instance Methods 方法，按说 module JSON 是不能响应 Public Instance Methods 方法的啊
&lt;img src="https://l.ruby-china.com/photo/2015/433541e79e212288aad23973fa433b62.png" title="" alt=""&gt;&lt;/p&gt;</description>
      <author>liy_j</author>
      <pubDate>Thu, 10 Dec 2015 09:03:44 +0800</pubDate>
      <link>https://ruby-china.org/topics/28331</link>
      <guid>https://ruby-china.org/topics/28331</guid>
    </item>
    <item>
      <title>Ruby 中通过 AES-128-CBC 加密后密码和 Java 中通过 AES/CBC/PKCS5Padding 加密的密码不一致?</title>
      <description>&lt;p&gt;最近在调试一个加密和解密的接口，用 ruby 加密，然后用 java 解密，在用 java 解密时错误。然后调试中分别用 ruby 和 java 给数据加密，看是否一致，结果发现加密的结果也不一致，大神帮看看是什么原因&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="n"&gt;data&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"45b00417-f7ca-4f53-bced-c1743d85604"&lt;/span&gt;

&lt;span class="n"&gt;cipher&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;OpenSSL&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;Cipher&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;AES&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;128&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:CBC&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encrypt&lt;/span&gt;
&lt;span class="n"&gt;key&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"quck7295abvdefgh"&lt;/span&gt;
&lt;span class="n"&gt;iv&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"abcdefgh3762quck"&lt;/span&gt;

&lt;span class="n"&gt;encrypted&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;final&lt;/span&gt;
&lt;span class="no"&gt;Base64&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encode64&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;encrypted&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;使用相同的 key 来加密
ruby 加密后结果为：&lt;/p&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;双次加密后结果："EAhESILT2j/MSa1CykE7yqtX7N8XvPVzrzewJoELRuPj+rK8DeSuxROD/uOq\nLqhy\n"
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;java 加密后结果为：&lt;/p&gt;
&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;javax.crypto.Cipher&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;javax.crypto.spec.IvParameterSpec&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;javax.crypto.spec.SecretKeySpec&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;CipherUtil&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;

    &lt;span class="kd"&gt;private&lt;/span&gt; &lt;span class="kd"&gt;final&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="no"&gt;KEY&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"quck7295abvdefgh"&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getBytes&lt;/span&gt;&lt;span class="o"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;private&lt;/span&gt; &lt;span class="kd"&gt;final&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="no"&gt;IV&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"abcdefgh3762quck"&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getBytes&lt;/span&gt;&lt;span class="o"&gt;();&lt;/span&gt;

    &lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="nf"&gt;encryption&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="kd"&gt;throws&lt;/span&gt; &lt;span class="nc"&gt;Exception&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nf"&gt;cipherIV&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;ENCRYPT_MODE&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;

    &lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="nf"&gt;decryption&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="kd"&gt;throws&lt;/span&gt; &lt;span class="nc"&gt;Exception&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nf"&gt;cipherIV&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;DECRYPT_MODE&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;

    &lt;span class="kd"&gt;private&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="nf"&gt;cipherIV&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;int&lt;/span&gt; &lt;span class="n"&gt;mode&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="kd"&gt;throws&lt;/span&gt; &lt;span class="nc"&gt;Exception&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="nc"&gt;SecretKeySpec&lt;/span&gt; &lt;span class="n"&gt;sekey&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;SecretKeySpec&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;KEY&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"AES"&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="nc"&gt;Cipher&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;Cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getInstance&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"AES/CBC/PKCS5Padding"&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;init&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;mode&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sekey&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;IvParameterSpec&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;IV&lt;/span&gt;&lt;span class="o"&gt;));&lt;/span&gt;
        &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;decrypted&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;doFinal&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;decrypted&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;

    &lt;span class="kd"&gt;private&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="nf"&gt;cipher&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;int&lt;/span&gt; &lt;span class="n"&gt;mode&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="kd"&gt;throws&lt;/span&gt; &lt;span class="nc"&gt;Exception&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="nc"&gt;Cipher&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;Cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getInstance&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"AES/CBC/PKCS5Padding"&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;init&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;mode&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;SecretKeySpec&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;KEY&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"AES"&lt;/span&gt;&lt;span class="o"&gt;));&lt;/span&gt;
        &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;decrypted&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;cipher&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;doFinal&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;decrypted&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;

    &lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;void&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="kd"&gt;throws&lt;/span&gt; &lt;span class="nc"&gt;Exception&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="nc"&gt;String&lt;/span&gt; &lt;span class="n"&gt;str&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"45b00417-f7ca-4f53-bced-c1743d85604"&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
        &lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;encryption&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;str&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getBytes&lt;/span&gt;&lt;span class="o"&gt;());&lt;/span&gt;
        &lt;span class="nc"&gt;String&lt;/span&gt; &lt;span class="n"&gt;str1&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;String&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Base64&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;encodeToString&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;));&lt;/span&gt;
        &lt;span class="nc"&gt;System&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;out&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;println&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;str&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="nc"&gt;System&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;out&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;println&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;str1&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
        &lt;span class="nc"&gt;System&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;out&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;println&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;String&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;decryption&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Base64&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;decode&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;str1&lt;/span&gt;&lt;span class="o"&gt;))));&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;双次加密后：2TStMVj6tPz8m4o0hjSY/GwTfx4UXFfDti9yhiJ6fr2tQFQsfNDG4Mqb3wpNy6x1
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;还有就是，ruby 加密后所谓的标准填充模式是什么啊？&lt;/p&gt;</description>
      <author>liy_j</author>
      <pubDate>Fri, 29 May 2015 16:56:02 +0800</pubDate>
      <link>https://ruby-china.org/topics/25810</link>
      <guid>https://ruby-china.org/topics/25810</guid>
    </item>
    <item>
      <title>vim 命令行中能否运行 rails 命令啊？</title>
      <description>&lt;p&gt;最近在折腾 VIM，想把 vim 变成类似于 subline 这种 IDE 的形式。
各位大神，能不能在打开的 rails 工程中的 vim 命令行中运行 rails 命令，来生成文件或控制器之类的，还是说必须打开另外一个终端来进行 rails 命令的输入。例如：$rails generate controller Users(图片中最后用红线圈起来的行)&lt;/p&gt;

&lt;p&gt;&lt;img src="https://l.ruby-china.com/photo/2015/2c1124200850973f53d310bd4639f780.jpg" title="" alt=""&gt;&lt;/p&gt;</description>
      <author>liy_j</author>
      <pubDate>Tue, 03 Feb 2015 15:19:18 +0800</pubDate>
      <link>https://ruby-china.org/topics/24092</link>
      <guid>https://ruby-china.org/topics/24092</guid>
    </item>
    <item>
      <title>正确理解类变量</title>
      <description>&lt;p&gt;&lt;strong&gt;测试环境是 ruby1.8.7。ruby1.9，ruby2.0 版本不适用&lt;/strong&gt;
&lt;strong&gt;各位看官，请看回复中的用于 ruby1.9 和 2.0 的帖子&lt;/strong&gt;
&lt;strong&gt;NOTE:&lt;/strong&gt;类变量并不真正属于类，它们属于类体系结构，可以被类或类的实例所使用。（类变量必须被初始化）
&lt;strong&gt;场景一：&lt;/strong&gt;&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码a&lt;/span&gt;
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;                          
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
 &lt;span class="vc"&gt;@@v&lt;/span&gt;                             
&lt;span class="k"&gt;end&lt;/span&gt;                             
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 a 中，@@v = 1 定义于 main 对象的上下文，因此它属于 main 的类 Object，所以也属于 Object 的所有子类。类 MyClass 继承自 Object，因此也共享了这个类变量&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码b&lt;/span&gt;
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;                          
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
 &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;                            
&lt;span class="k"&gt;end&lt;/span&gt;     
&lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;2                        &lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 b 中，类 MyClass 修改了共享类变量@@v，因此 Object 中类变量值也被改变了。&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码c                    &lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
 &lt;span class="vc"&gt;@@v&lt;/span&gt;                            
&lt;span class="k"&gt;end&lt;/span&gt;      
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;                       
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 c 中，执行这个文件时，会报没有初始化类变量@@v 的错误，也就是说，在类 MyClass 的祖先链中未发现已定义的@@v，因此在类 MyClass 中开始定义@@v，并且必须被初始化&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码d                      &lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
 &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;                            
&lt;span class="k"&gt;end&lt;/span&gt;      
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;    
&lt;span class="no"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;class_variable_get&lt;/span&gt; &lt;span class="ss"&gt;:@@v&lt;/span&gt;   &lt;span class="c1"&gt;#=&amp;gt;1                &lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 d 是代码 c 的进化版本，由于在类 MyClass 的祖先链中未发现已定义的@@v，因此在类 MyClass 中定义的@@v = 2 属于该类及所有子类，且可以被该类的实例所使用。
代码 d 中在类下方定义了@@v=1，这里的@@v=1 属于 Object 可以被其子类共享，与 MyClass 中@@v 是两个不同的类变量。Object 中类变量@@v=1 不能被 MyClass 及其子类所共享。
从代码 d 中可以看到，MyClass 中@@v 的改变不会影响 Object 中类变量（因为 MyClass 中类变量不是共享于 Object 的类变量）。也可以通过 MyClass 的子类来验证&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码e &lt;/span&gt;
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;                    
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
  &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt; 
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_method&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@v&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;                           
&lt;span class="k"&gt;end&lt;/span&gt;      
&lt;span class="no"&gt;MyClass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_method&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; 2  &lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt;  &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 e 中，MyClass 中@@v 是共享于 Object 中类变量（@@v 定义于 Object）,因此 MyClass 中@@v 的改变会影响定义于 Object 中@@v 的值&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码f                    &lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
  &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt; 
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_method&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@v&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;                           
&lt;span class="k"&gt;end&lt;/span&gt;  
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;    
&lt;span class="no"&gt;MyClass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_method&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; 2  &lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt;  &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 f 中，MyClass 中@@v=2 与 Object 中@@v=1 是两个不同的类变量，不存在共享的关系，而是分别定义于不同的类中。因此@@v 的改变不会影响彼此&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   代码g                 &lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;                 
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_method&lt;/span&gt;
     &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@v&lt;/span&gt;
     &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;#修改共享类变量值&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;                           
&lt;span class="k"&gt;end&lt;/span&gt;  
&lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;    
&lt;span class="no"&gt;MyClass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_method&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; 1  &lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt;  &lt;span class="vc"&gt;@@v&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;代码 g 中，MyClass 的方法 my_method 中@@v 属于共享的类变量，共享于 Object 中的@@v，因此在 my_method 中修改@@v 的值会影响定义于 Object 中@@v 的值。（定义于方法中的代码，只有在方法调用时才执行）&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;场景二&lt;/strong&gt;&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#  f1.rb&lt;/span&gt;
&lt;span class="k"&gt;module&lt;/span&gt; &lt;span class="nn"&gt;M1&lt;/span&gt;
  &lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"M1"&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nc"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m1&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#  f2.rb&lt;/span&gt;
&lt;span class="k"&gt;module&lt;/span&gt; &lt;span class="nn"&gt;M2&lt;/span&gt;
  &lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"M2"&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nc"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m2&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   图1-1&lt;/span&gt;
&lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"object"&lt;/span&gt;
&lt;span class="nb"&gt;require&lt;/span&gt; &lt;span class="s2"&gt;"f1.rb"&lt;/span&gt;
&lt;span class="nb"&gt;require&lt;/span&gt; &lt;span class="s2"&gt;"f2.rb"&lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;
  &lt;span class="kp"&gt;include&lt;/span&gt; &lt;span class="no"&gt;M1&lt;/span&gt;
  &lt;span class="kp"&gt;include&lt;/span&gt; &lt;span class="no"&gt;M2&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_method&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="no"&gt;MyClass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_method&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "M2"&lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;"object"&lt;/span&gt;
&lt;span class="no"&gt;M1&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m1&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "M1"&lt;/span&gt;
&lt;span class="no"&gt;M2&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m2&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "M2"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="c1"&gt;#   图1-2&lt;/span&gt;
&lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"object"&lt;/span&gt;
&lt;span class="nb"&gt;require&lt;/span&gt; &lt;span class="s2"&gt;"f1.rb"&lt;/span&gt;
&lt;span class="nb"&gt;require&lt;/span&gt; &lt;span class="s2"&gt;"f2.rb"&lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;MyClass&lt;/span&gt;
  &lt;span class="kp"&gt;include&lt;/span&gt; &lt;span class="no"&gt;M1&lt;/span&gt;
  &lt;span class="kp"&gt;include&lt;/span&gt; &lt;span class="no"&gt;M2&lt;/span&gt;
  &lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"myclass"&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;my_method&lt;/span&gt;
    &lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="no"&gt;MyClass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;new&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;my_method&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "myclass"&lt;/span&gt;
&lt;span class="nb"&gt;p&lt;/span&gt; &lt;span class="vc"&gt;@@via&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt;"object"&lt;/span&gt;
&lt;span class="no"&gt;M1&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m1&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "M1"&lt;/span&gt;
&lt;span class="no"&gt;M2&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;m2&lt;/span&gt; &lt;span class="c1"&gt;#=&amp;gt; "myclass"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;图 1-1 和图 1-2 中分别在 M1、M2 和 Object 中定义了@@via，这三个@@via 是三个不同的类变量。Object 中定义的@@via 可以被其子类 MyTest 共享；M1 中定义的@@via 可以被 include 的类共享；M2 中定义的@@via 也可以被 include 的类共享；那么类 MyTest 中共享的@@via 应该是哪个类或模块中定义的@@via？
&lt;strong&gt;通过图 1-1 和图 1-2 的例子可以理解为：&lt;/strong&gt;
类也是按照祖先链的方向来查找定义@@via 的类或模块，修改共享@@via 的值则会影响首次查找到的定义@@via 的类或模块中@@via 的值。
若在类的祖先链上未查找到有定义@@via 的类或模块，则类中显示@@via 的地方所表示的意思为：在此处定义@@via 且必须初始化（非共享的类变量）&lt;/p&gt;</description>
      <author>liy_j</author>
      <pubDate>Wed, 07 Aug 2013 20:14:15 +0800</pubDate>
      <link>https://ruby-china.org/topics/13138</link>
      <guid>https://ruby-china.org/topics/13138</guid>
    </item>
  </channel>
</rss>
