0

I know the extname is rb is worked.

I know linux file command is worked to in some case.

But all not accurate enough to decide a file is a ruby scripts

EDIT:

What I want to do is: more accuretely amount the ruby lines I wrote with a bash shell scripts like followings:

find -name '*.rb' |xargs -n100 cat |grep -v '\s*#' |wc -l

but, in fact, I wrote some executable ruby scripts, and others, e.g. .rake, Gemfile Capfile jbuider etc ...

Thanks

zw963
  • 1,157
  • 15
  • 11
  • What do you mean by *more accurate*? Do you want to ensure that the file actually contains Ruby code or at least is a valid Ruby file? – spickermann Apr 07 '17 at 15:31
  • @spickermann, linux `file` command, make my so much ruby file recognized as `ASCII text` or `C++ source, ASCII text`, And `.rb` extension will ignore some special executable file and others. (e.g. .rake) – zw963 Apr 07 '17 at 15:33

2 Answers2

2

Use ruby -c. From the man page:

-c    Causes Ruby to check the syntax of the script and exit

This will tell you if the file is a valid Ruby script without executing it. If it is, it will print "Syntax OK" to STDOUT and exit with status code 0; otherwise it will print a syntax error to STDERR and exit with a nonzero code. (You can of course suppress the messages using I/O redirection, e.g. &>/dev/null.)

Of course, false positives are possible (the fact that a file is valid Ruby doesn't necessarily mean it was intended to be a Ruby script), but unlikely except with very short files.

Jordan Running
  • 102,619
  • 17
  • 182
  • 182
  • Cool! this is exactly what I want. though, for some special file, e.g. git packed object, ruby -c is not worked. e.g. ╰─ $ ruby -c ./.git/objects/pack/pack-ef0573228b2fa7437e0913240d5cd6e7eca853a9.pack Syntax OK , But this not a big deal, I could skip `.git` directory to avoid this. – zw963 Apr 07 '17 at 15:55
  • @zw963 That's interesting. I would use `ruby -c` in combination with `file` or another technique to [check if it's a binary file](http://stackoverflow.com/questions/567757/how-do-i-distinguish-between-binary-and-text-files). – Jordan Running Apr 07 '17 at 16:03
  • @Jordon, yes, I think I need to do like you suggestion too. because ``ruby -c ./app/assets/images/favicon.ico Syntax OK `` is a little confusing, the same case for `ttf` files, But if in combination with `file+grep` recognized as ` text$`, it worked like a charm – zw963 Apr 07 '17 at 16:17
  • We need skip `*.js` too, ```$ cat 1.js (function () {asdfsadfasdfsdafasdfasdfasdfasdfa}).call(this); $ ruby -c 1.js Syntax OK ``` – zw963 Apr 07 '17 at 16:28
  • Yep. Like I said, there will be false positives. – Jordan Running Apr 07 '17 at 16:35
  • Finally I use this answer resolve my problem, please see gist: https://gist.github.com/927c8d45137353dc68553782d004bfa1 – zw963 Apr 07 '17 at 18:15
0

What you want is impossible. For example, the following is a valid, and semantically identical program in at least Ruby, PHP, Scala, and Perl:

print("Hello");

It is also valid in Python, although semantically slightly different: it prints a newline (i.e. it prints the string "Hello\n") while the others don't (the others print "Hello" without a newline).

It is also at least syntactically valid in ECMAScript, and may be semantically equivalent assuming a suitable print function exists in the standard library.

It is probably valid in a lot more languages than that, some that I can think of are AmbientTalk, Atomy, CoffeeScript, Converge, Dart, Dylan, E, Elixir, Falcon, Fancy, Groovy, Hack, Io, Ioke, Julia, Lua, Monte, Neko, Pico, Pike, and Seph. It is also a valid fragment, although not a complete program, in at least Perl6, C, C++, Objective-C, Objective-C++, D, Java, C♯, Spec♯, Sing♯, M♯, Cω, X♯, Kotlin, Ceylon, Rust, and Rust.

There is no way of knowing whether this is a Ruby program except asking the person who wrote it.

Jörg W Mittag
  • 363,080
  • 75
  • 446
  • 653
  • If we could add a special comment, which told `file` or others tools, this is a ruby scripts, it maybe help a lot. though, I don't know if this exist. – zw963 Apr 09 '17 at 17:06