Ruby on Rails: Executing JAR - ruby-on-rails

Folks, i'm trying to execute a jar file inside RoR. Thanks to SO, I figured using IO::popen calls to execute a jar file.
Requirements:
- To login to site: To let our company employees login. Its a Java library which does some magic and figures if the username/password is valid. Which I did using,
result = IO::popen("java -cp auth.jar com.name.auth.LDAPLookup " + params[:username] + " " + params[:password]).read
p result
output: ["Authorized", "email", "id"]
No input sanitizing done. This is risky. Anyone could type something up in username/password and that will be executed in the server.
I'm not sure how to do this. One option I want to try is to use fork() or Process APIs to launch "java" and pass arguments. Couldn't figure out however. Any other thoughts?

Aside from the issue you mention, this sounds pretty painful in terms of performance (you're waiting around for the JVM to start up on every request, after all).
Two solutions jump out at me:
Look what the library does, and see if you really need to call out to Java for this; in particular, if it's just a question of making a lookup in an LDAP directory with a set of canned parameters, there are plenty of gems for that
If you must make use of Java classes from Ruby, strongly consider using JRuby, which will let you call the Java class in question directly, with neither the overhead of restarting the JVM on each call, nor the risk which comes with trying to correctly escape your arguments from Ruby to the shell to the JVM, and back.

Related

require os, Am i missing somehting?

I come from C-family "mainstream" langages and i'm currently giving a try in Lua .
I made a simple code that check for a user entry and try to open an URL (built with user entry) in the default browser.
Saw the command os.execute("start "URL") that failed, saying that "os is undefined".
Well, seemed to be logical. I then researched the reason and discovered the "require" key word (which seems to act as a LoadLibrary or kind).
This is where I'm lost !
All forums says "yeah yeah just add require os and it will do". But it actually fail !
I obviously suspect that i am missing a "file" or path pointing at that "os" description. And that it's so obvious nobody found useful enough to explain or ask for it.
Can someone explain me what does require, in details ? Which file am i supposed to add (if i really need to ?).
If someone also have an online lesson to advise me, i'll accept it with pleasure. I feel like i'm missing a lot of basics and that's really not a "try to step-up" friendly langage
The standard Lua environment has os available without using require, so you must be using a non-standard Lua environment.
When Lua is embedded into different software, access to libraries like os is usually removed, as it is a security risk. (For example, if you allowed full access to the os library to anyone using Lua on a webserver, it would mean that anyone could run random shell commands on that server.)
If your Lua environment has been altered in this way, then there is a good chance that you will never be able to use the os library whatever you do.

execute lua string as lua code

I want to share lua modules with coworkers. In order to get the latest version of shared modules I want to store and fetch them with a web server.
My questions is:
Is it possible to load lua code directly from http request or string?
I want to achieve something like that :
module = [[
local sharedModule = {}
function sharedModule.greet(name) print("hello " .. name) end
return sharedModule
]]
greeter = require (module)
greeter.greet("john")
Maybe this is not the right thing to do. Is there a better approach than this one?
There's a whole section in Programming in Lua devoted to that. Your needs will be directly fulfilled with loadstring in Lua 5.1 and older, or load in Lua 5.2 and newer.
I would carefully verify the code you're actually executing, though. At the very least, version it (running a wrong version would most probably end up in all sorts of problems, if the code being run depends on the environment being in a certain state). Optimally checksum and sign the code, and verify the signature before doing anything. If your environment isn't protected, this is essentially a huge backdoor opening.
You could also use rings library to isolate the code you're running within the Lua environment itself. It might not be airtight security-wise, but should at least prevent the received code from crashing your application if/when it goes awry.

Generate dependencies for Lua?

I have a lua project with lua files specified in multiple directories all under the same root folder with some dependencies.
Occasionally I run into issues where when a table is being loaded at load time I get a nil exception as the table is referencing a not yet initialised table, like:
Customer =
{
Type = CustomerTypes.Friendly
}
Which causes a nil exception for CustomerTypes as CustomerTypes.lua has not yet loaded.
My current solution is to simply have a global function call in these lua files to load the dependency scripts.
What I would like to do is pre-process my lua files to find all dependencies and at run time load them in that order without needing function calls or special syntax in my lua files to determine this (i.e. the pre-processor will procedurally work out dependencies).
Is this something which can be realistically achieved? Are there other solutions out there? (I've come across some but not sure if they're worth pursuing).
As usual with lua there are about 230891239122 ways to solve this. I'll name 3 off the top of my head but I bet I could illustrate at least 101 of them and publish a coffee table book.
First of all, it must be said that the notion of 'dependencies' here is strictly up to your application. Lua has no sense of it. So this isn't anything like overcoming a deficiency in lua, it's simply you creating a scripting environment in your application that makes you comfortable, and that's what lua's all about.
Now, it seems to me you've jumped to a conclusion that preprocessing is required to solve the given problem. I don't think that's warranted. I feel somewhat comfortable saying a more conventional approach to solving the problem would be to make a __newindex metamethod globally which handles the "CustomerTypes doesnt exist yet" situation by referencing a list of scripts which have been scanned out of the filesystem initially for one called CustomerTypes.lua and running that.
But maybe you have some good reason for wanting it done strictly as preprocessing. In your case, I would start by considering 'dependencies' to be any name which is a script found in your scripts filesystem. Then scan each script to look for the names of dependencies using the definitions/list you just created, and prepend a load(dependency) command to each of those scripts.
Since the concept of "runtime" or "preprocessing" is somewhat ambiguous in this context, you might mean at script-compile-time. You could use the LuaMacros token filters system to effect a macro which replaces CustomerTypes with require("CustomerTypes.lua") or something to that effect after having discovered that CustomerTypes is a legal dependency name.

Progress ABL How to Test for WEBSPEED in the PRE-PROCESSOR

I want to conditionally compile some blocks of code depending on type of client i'm running in. this is fine for batch and tty as i can use the {&BATCH-MODE} but how to test for when the code is being compiled in webspeed agent? eg. {&IF} not {&SOMETHING} EQ "YES" {&THEN}
{&ANALYSE-SUSPEND}
foo
bar
{&ANALYSE-RESUME}
{&ENDIF}
it would be helpful if this did not rely on defines auto generated by the architect in .w's etc but that would be a nice to have not essential.
Compile time isn't run time. If the program can be run different ways (as a part of a of webpage using webspeed, as a part of a batch and as a part of some other kind of client etc) you're most likely better of evaluating this in run time instead.
You can identify in what environment you're running:
SESSION:CLIENT-TYPE
This will identify your type of client.
DISPLAY SESSION:CLIENT-TYPE.
Type of client Attribute value
-------------------------------- -----------------------
ProVision standard ABL client 4GLCLIENT
WebClient WEBCLIENT
AppServer agent APPSERVER
WebSpeed agent WEBSPEED
Pacific Application Server agent MULTI-SESSION-AGENT
Other special-purpose clients Unknown value (?)
Documentation
Using VST
If you have at least one database connected
_Connect-ClientType tells you what kind of client this particular connection is:
Value Client
-------- ---------------------
ABL ABL client
SQLC SQL client
WTA Webspeed agent
APSV AppServer agent
SQFC SQL Federated client
Example:
FIND FIRST _myconnection NO-LOCK.
FIND FIRST _connect NO-LOCK WHERE _connect._connect-usr = _myconnection._MyConn-userid.
DISPLAY _connect._Connect-ClientType.
Based on OS
Perhaps you run different OS:es?
DISPLAY OPSYS.
Other ways
There's a number of other ways of doing this, including perhaps looking at PROPATH, Working directory etc.
Try to stick with a solution that won't change over the course of time because of Progress upgrades, new OS:es, new directory structures etc.
IMHO there is no such preprocessor variable out of the box.
But you could create your own include file and include that in the code that's relevant. You need two versions of that file, one says
&GLOBAL-DEFINE WebSpeed WebSpeed
and the other
&GLOBAL-DEFINE NoWebSpeed NoWebSpeed
And then configure your compile sessions so that they find exactly one of the files in propath.
But as you will agree, this is probably dangerous as the result will heavily rely on the proper PROPATH used during compilation. I'd rather attempt to use a runtime condition instead.
What are you trying to achieve in detail?
finally figured it out this morning {&webstream} and {&out} are not defined in in normal sessions so i can just test for that. runtime is not an issue in my case i just want to compile the code in all cases. in this shop dont ask me why but every single piece of code is session compiled. poor cpu but there u go. i could be defensive and add some logic with session:Client-type for bells and whistles you're right. if not can-do then boogie :)

Will "system()" call in Ruby wait until it finishes?

I'm new to ruby on rails. I want to call a system command to analyze an uploaded file in my Rails application. Something as follows:
after_save :analyse #post processing call
def analyse
command = "./c_executable " + Rails.root.to_s + "/output_csv_file"
system(command)
if FileTest.exists?(Rails.root.to_s + "/output_csv_file")
parse_csv
end
end
It runs fine on my local machine, but for some reason the function "parse_csv" won't get called on the server(dreamhost). However, I manually call the c_executable system command on the server and it outputs the csv file without a problem. Could anyone tell me what might be causing the problem here? I was thinking the system call takes some time to finish on the server. If that's the case, I'm wondering if there is a way to tell rails to wait until the system() call finishes execution. Thanks in advance!
The system call should block until the command inside is finished. It is possible that the file is not being created as you intended which might preclude that part of your app from running.
You might want to use a different way of constructing your path to be sure you're getting it right:
csv_path = File.expand_path('output_csv_file', Rails.root)
unless (system('./c_executable', csv_path))
# Could't execute system command for some reason.
end
if (File.exists?(csv_path))
# ...
end
When making system calls it's generally a good idea to specify the full path to the executable as your application PATH may be different from what you expect.
My first guess is that it's a permissions error. Do you know what user the web/app server is running as and see if it has the correct permissions to both read/execute the command and write the output file.
I'll answer my own question now. After spending several days of testing and googling, it turns out that dreamhost doesn't allow these kind of non built-in system calls. I'll have to change my hosting service.

Resources