Skip to content
This repository has been archived by the owner on Jan 10, 2024. It is now read-only.

Using jasmine-rails in an engine #102

Open
bryanl opened this issue Jan 27, 2014 · 5 comments
Open

Using jasmine-rails in an engine #102

bryanl opened this issue Jan 27, 2014 · 5 comments

Comments

@bryanl
Copy link

bryanl commented Jan 27, 2014

Any thoughts on configuring jasmine-rails for an engine? Out of the box, I'm running into a few issues that can be solved, but I don't progress if there are other thoughts.

@searls
Copy link
Member

searls commented Jan 28, 2014

Hey Bryan! I have never thought of this use so I'm afraid you're on your own unless someone else has considered it. 😦 -- I'll think on it.

Long shot: If you happen to be using an Engine as a way to extract a front-end portion of a Rails project, I'd instead recommend making a lineman app and integrating it with rails-lineman.

@tdg5
Copy link

tdg5 commented Jan 28, 2014

I was also trying this today and couldn't get it to work the way I wanted it to work, but I think that was more to do with a wrapper rake task I was trying to create simultaneously.

That said, I was able to get jasmine-rails to work in an engine against the Dummy test app. This wasn't quite what I wanted, so I didn't spend any time trying to make it elegant, but it would run.

I haven't been able to find a way to make it so mounting JasmineRails in the WrapperEngine also mounts JasmineRails in an IncludingApplication. However, if you mount JasmineRails in the IncludingApplication directly it seems to work. The problem here arises from WrapperEngine using isolate_namespace which causes the :jasmine_rails named route to be obscured. A more complex/configurable approach to detecting the JasmineRails path could allow more options for getting around this problem, but for now it seems that something must be done to make it so the expected named_route exists in IncludingApplication.

This means to get JasmineRails to run in the Dummy app of WrapperEngine, we need to change the Dummy app routes to something like the following:

# test/dummy/config/routes.rb
Rails.application.routes.draw do
  mount WrapperEngine::Engine => '/'
  mount JasmineRails::Engine => '/specs'
end

This assumes something like the following in wrapper_engine.gemspec:

Gem::Specification.new do |spec|
  spec.add_dependency 'jasmine-rails'
end

The last thing you might need is to make sure the WrapperEngine's Rakefile points to the dummy app Rakefile:

# in Rakefile
APP_RAKEFILE = File.expand_path('../test/dummy/Rakefile', __FILE__)
load 'rails/tasks/engine.rake'

If all of this is in place you should be able to run the rake task with rake app:spec:javascripts.

That's about as far as I got. Not sure if there are any hoops you have to jump through to configure jasmine.yml correctly. The code for loading jasmine.yml is here, so that'd be a good place to start. Once that works though, seems like you'd be good to go.

@bryanl
Copy link
Author

bryanl commented Jan 29, 2014

@tgd5 This is pretty much what I did to get it working.

@searls
Copy link
Member

searls commented Jan 29, 2014

Hmm. Glad you both found workarounds, but obviously I'd like to better serve others with this need. Without thinking really hard about it, is any of this stuff that jasmine-rails could do better?

@tdg5
Copy link

tdg5 commented Jan 29, 2014

I was digging into this some more this AM and I've started to think that including JasmineRails as part of an Engine isn't a good way to go. This thinking stems from an error in my previous comment that I've since updated. I'd previously suggested that you could do something like this in your wrapper_engine.gemspec:

Gem::Specification.new do |spec|
  spec.add_development_dependency 'jasmine-rails'
end

But that won't work.

If jasmine-rails is added via :add_development_dependency the IncludingApplication won't install the gem. To get the IncludingApplication to install jasmine-rails you'd have to use :add_dependency or :add_runtime_dependency instead of :add_development_dependency.

I don't think there is a way to do a Gemfile-like :require => false in a gemspec, which means that as soon as you add jasmine-rails as a runtime dependency, you're shipping it to production.

No offense intended to JasmineRails, I haven't seen any reason to be weary of it, but, IMHO, it is not code for production. Especially given that, as far as I'm aware, you don't have any control over it being loaded. Even if you take precautions to make sure the route isn't mounted, it still introduces unnecessary risks.

Maybe I'm being overcautious, but after running into God monkeypatch makes 10.megabytes == 10.kilobytes, I tend to be more cautious when it comes to shipping code to production that doesn't HAVE to be in production. Especially considering that God is code that IS intended for production (but apparently not intended to be required by your Rails app).

YMMV, but considering all that, JasmineRails not working as part of another engine is a non-issue for me.

I don't know what the stance of the project is on production use, but if production use is part of someone's use-case, or if you're making an engine for dev use, then I'd think you'd need to make the spec_runner url something that was configurable. If there was a configured value, JasmineRails would use that instead of looking for the :jasmine_rails named route. I'm not positive, but that might be the only code that would need to change to make the rest of it work with some minor configuration or a well placed require.

kurko added a commit to kurko/jasmine-rails that referenced this issue Feb 4, 2018
**Context**

I was able to get this gem to work with my engine by going
inside the `test_app` dir and running

`bundle exec rails spec:javascript`

So far so good. The problem is that I don't want to have to run
`cd spec/test_app` every time to run my Javascript tests. I want to run them
from the engine's grandparent directory so I can include it in my Rakefile for
the entire test suite. In other words, this is my dir tree:

```
~/engine/
~/engine/spec/javascripts/
~/engine/spec/test_app/spec/javascripts/support/jasmine.yml
```

`Rails.root` is always `~/engine/spec/test_app/`, regardless of whether
I'm in `~/engine/ or not.

**The problem**

Look at this line:

```rb
[paths].flatten.map { |path| Dir.glob path }.flatten.collect { |path| Rails.root.join(path) }
```

`Dir.glob path`, equivalent to `Dir.glob("spec/javascripts")` returns
`true` because `Dir.pwd` is `~/engine/`, therefore
`~/engine/spec/javascripts` exists.

However, the last `collect` has `Rails.root.join("spec_javascript)`,
which will map to `~/engine/spec/test_app/spec/javascripts`, but
there's nothing there (because my test files were configured to
`~/engine/spec/javascript`).

To "fix that, I put `../javascripts` in my yml's `spec_dir`, but no `Dir.glob`
just returns false because, in fact, `~/engine/../javascripts` doesn't exist.
So, the code is verifying one path and resolving to some other.

**The fix**

```patch
-      [paths].flatten.map { |path| Dir.glob path }.flatten.collect { |path| Rails.root.join(path) }
+      [paths].flatten.map { |path| Dir.glob(Rails.root.join(path)) }.flatten.collect { |path| Rails.root.join(path) }
```

This fix just makes it cohesive.

I suspect this is in a way connected with
testdouble#102 (to make it work with
engines).
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants