ruby-type-inference
project is a completely new approach to
tackle the problems of Ruby dynamic nature and provide more reliable
symbol resolution and type inference. It collects some run time data
to build type contracts for the methods.
Every time a method is being called, some arguments of particular types are being passed to it. Type Tracker collects all such argument combinations and then builds a special contract which satisfies all encountered argument type tuples.
The approach has its own pros and cons:
This implementation addresses the stated coverage problem by providing the possibility to merge any type contracts at any time.
For simple usage you need to install the Ruby Dynamic Code Insight plugin for RubyMine. Then this plugin will require the arg_scanner gem to be installed. See arg_scanner installation instruction if you have problems while installation.
After that, you will have the possibility to run your programs under type tracker:
Or you can run your programs in terminal via the rubymine-type-tracker
binary (But you have to keep your project opened
in RubyMine). E.g.:
rubymine-type-tracker bin/rails server
The rubymine-type-tracker
binary is included into the arg_scanner gem.
See FEATURES.md for understanding what benefits you will have after running your program under type tracker.
arg_scanner is a gem with a native extension to attach to ruby processes and trace and intercept all method calls to log type-wise data flow in runtime.
See arg_scanner
documentation for details on usage.
The type contract processor server listens for
incoming type data (from arg_scanner
) and processes it to a compact format.
The data stored may be used later for better code analysis and also can be shared with other users.
Code analysis clients (a RubyMine/IJ+Ruby plugin) use the contract data to provide features for the users such as code completion, better resolution, etc.
(todo) Signature server receives contracts anonymously from the users and provides a compiled contract collections for popular gems.
The arg_scanner
gem is used for collecting type information. It can be installed manually
to the target SDK and requires MRI Ruby at least 2.3.
There are two possibilities to use the type tracker: (I) using IJ/RubyMine plugin or (II) requiring it from Ruby code.
The easiest way to run the plugin (and the most convenient for its development) is running it with special gradle task against IJ Ultimate snapshot:
./gradlew ide-plugin:runIde
The task will compile the plugin, run IJ Ultimate with plugin "installed" in it. There is no need in running anything manually in that case.
If you want to try it with existing RubyMine instance, you should:
./gradlew ide-plugin:buildPlugin
File | Settings | Plugins | Install plugin from disk...
ide-plugin/build/distributions
and select.Note that due to API changes the plugin may be incompatible with older RM instances.
In order to collect the data for the script needs a contract server to be up and running; it could be run by running
./gradlew contract-creator:runServer --args path-to-db.mv.db
where path-to-db.mv.db
is path where type contracts will be stored (H2 database file).
Run the ruby script to be processed via arg-scanner
binary.
Use the data collected by the contract server.
Any kind of ideas, use cases, contributions and questions are very welcome as the project is just incubating. Please feel free to create issues for any sensible request.