Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Problem using 'lein trampoline' with cljsbuild #204

Open
deg opened this issue May 20, 2013 · 41 comments
Open

Problem using 'lein trampoline' with cljsbuild #204

deg opened this issue May 20, 2013 · 41 comments

Comments

@deg
Copy link

deg commented May 20, 2013

There seems to be a conflict using 'lein trampoline' when my project includes ':hooks [leiningen.cljsbuild]' in the top-level map in project.clj. Operations as simple as 'lein trampoline run' silently exit, with no error message, while 'lein run' works fine.

This bug-report is still half-baked. I'm sending what I've found so far, in the hope that someone will shout back "known bug" or "don't do that", but I can certainly give more detail if this is a real issue I've hit.

What I do know so far:

  • My project is based on https://github.com/magomimmo/modern-cljs. I believe (but have not 100% tested) that everything I'm saying here applies to that project too.
  • I've seen the problem in lein-cljsbuild 0.3.0 and 0.3.2. I've not tested other versions.
  • When I moved the ':hooks [leiningen.cljsbuild]' line into a :dev profile, the problem seems to go away. Even 'lein with-profile dev trampoline run' works. (Previously, I had the hook in the top-level map in my projects.clj).
@emezeske
Copy link
Owner

Hrm... That is weird, especially the :dev profile part.

This is probably a dumb question, but are you using the very latest version of Leiningen?

I'm trying to think of some way to determine whether the bug is in lein-cljsbuild or Leiningen itself. The only idea I've come up with is to run some other plugin with :hooks under lein trampoline, and see if it fails the same way or not.

@deg
Copy link
Author

deg commented May 21, 2013

(smacks self on side of head).

Looks like I’m running Leiningen 2.0.0, and the latest is 2.1.3. For some reason, I had thought that Leiningen or my config would do an auto version check.

I’ll upgrade Leiningen and test again. I should have an answer within an hour or two.

Assuming that the issue remains, I’ll try your idea of testing with another plugin. I’m still pretty new to this; do you suggest any plugin in particular?

David

From: Evan Mezeske [mailto:notifications@github.com]
Sent: Tuesday, May 21, 2013 8:31 AM
To: emezeske/lein-cljsbuild
Cc: David Goldfarb
Subject: Re: [lein-cljsbuild] Problem using 'lein trampoline' with cljsbuild (#204)

Hrm... That is weird, especially the :dev profile part.

This is probably a dumb question, but are you using the very latest version of Leiningen?

I'm trying to think of some way to determine whether the bug is in lein-cljsbuild or Leiningen itself. The only idea I've come up with is to run some other plugin with :hooks under lein trampoline, and see if it fails the same way or not.


Reply to this email directly or view it on GitHubhttps://github.com//issues/204#issuecomment-18190075.

@deg
Copy link
Author

deg commented May 21, 2013

Ok, some updates…

  1. I’ve upgraded to Leiningen 2.1.3. No change in behavior. (Side question: the first time I did ‘lein upgrade’, it took me only up to 2.1.2. I had to run it again to get to 2.1.3. Known behavior, or clue to some other weirdness?)
  2. My comment about the :dev profile was a red herring; ignore it. (My carelessness, trying to test and file a bug report late at night. I had a ‘:cljsbuild { .. :builds { .. :dev { …}}}’ section in my projects.clj map, and I stuck the line inside there, where it was obviously ineffective.
  3. I’ve verified that I can duplicate the problem in the latest version of https://github.com/magomimmo/modern-cljs; much cleaner than the messy playground of my current project.

So, revised bug report:

  • In the modern-cljs project, ‘lein trampoline ring server-headless’ works.
  • But, if you uncomment ‘:hooks [leiningen.cljsbuild]’ in its project.clj, than the trampoline run fails silently. This is in Leiningen 2.1.3.

Thanks,
David

@emezeske
Copy link
Owner

Thanks for the detailed updates! I will try to debug further sometime soon. Unfortunately it may have to wait until a weekend.

(Regarding your lein upgrade sidenote -- I have no idea, very weird!)

@xavi
Copy link

xavi commented Jun 6, 2013

I have the same problem, i.e. "trampoline" doesn't work with ":hooks [leiningen.cljsbuild]'". I think it's the same problem reported in technomancy/leiningen#956 . Could it be that the latest versions of Leiningen fixed the 30 seconds hang that prompted the explicit exit hack ( d836402 )? If so, maybe just removing the hack fixes the issue?

@ccfontes
Copy link

Please try a working fork that removes the exit hack and therefore allows use of trampoline: [ccfontes/lein-cljsbuild "0.3.2-no-exit"]
Hopefully this hack would be removed from the main repo.

@xavi
Copy link

xavi commented Jun 19, 2013

I don't know if it breaks something else, but I can confirm that ccfontes fork fixes the issue with trampoline. I also hope to see this in lein-cljsbuild main repo soon.

Thanks Carlos!

@ccfontes
Copy link

@xavi that's great, thanks! Your links helped me out on this one too.

As stated at d836402 - "Without an explicit exit, the in-project subprocess seems to just hang for around 30 seconds before exiting. I don't fully understand why...", but rumored as comment to that commit to be already fixed at technomancy/leiningen@4f2bc32, was my reason to remove the exit hack.
As more people give feedback about this fork, we will know if it is fixed in leiningen or not.

@ccfontes
Copy link

It happened here that, when deploying to heroku, the process hanged at Compiling ClojureScript for some minutes, but then completed the compilation and proceeded to other tasks.

-----> Deleting 6 files matching .slugignore patterns.
-----> Clojure (Leiningen 2) app detected
-----> Installing OpenJDK 1.6...done
-----> Using cached Leiningen 2.2.0
       Writing: lein script
-----> Building with Leiningen
       Found bin/build; running it instead of default lein invocation.
       Running: bin/build
       Compiling ClojureScript.

hanged, but resumed after some minutes..

       Compiling "target/cljsbuild-main.js" from ["src-cljs"]...
       Successfully compiled "target/cljsbuild-main.js" in 244.567180446 seconds.
       Compiling ClojureScript.
-----> Discovering process types
       Procfile declares types -> web

-----> Compiled slug size: 134.7MB
-----> Launching... done, v92
-----> Deploy hooks scheduled, check output in your logs

@ccfontes
Copy link

timed out one time:

> lein repl
Compiling ClojureScript.
Compiling "target/cljsbuild-main.js" from ["src-cljs"]...
Successfully compiled "target/cljsbuild-main.js" in 26.958402 seconds.
REPL server launch timed out.

but next try it didn't.

@ccfontes
Copy link

new record: Successfully compiled "target/cljsbuild-main.js" in 312.549677798 seconds.

@ccfontes
Copy link

For those using trampoline because of the exceeded memory quota on heroku there is the following alternative:
using the uberjar branch of heroku-buildpack-clojure#uberjar . It solved not only boot timeouts but also memory issues, so there's no need to use the fork [ccfontes/lein-cljsbuild "0.3.2-no-exit"] anymore for that purpose. It seems heroku will be using this method in the future. There are some recent closed issues in heroku-buildpack-clojure#uberjar explaining part of the process.
I'd be glad to help anyone who wants to try it.

@jeluard
Copy link
Contributor

jeluard commented Jul 17, 2013

I also hit this issue. @ccfontes fork apparently fixes it. Any plan to merge it?

@cemerick
Copy link
Collaborator

@jeluard I haven't repro'd yet, but would look at a pull request if it were offered.

@jeluard
Copy link
Contributor

jeluard commented Aug 29, 2013

I just tried to reproduce and now get an exception when running lein run trampoline (with hook defined): java.io.FileNotFoundException: Could not locate cljsbuild/compiler__init.class or cljsbuild/compiler.clj on classpath. Do you have some public project that I could test?

This is with leinigen 2.3.2 (not sure what else changed).

The previous behaviour was to exit after the line Compiling ClojureScript.. Quite similar to what happens when running lein cljsbuild once and no change is detected (which I think is confusing too).

@cemerick
Copy link
Collaborator

I can't point at a sample project, haven't seen the problem myself (though I only just saw this issue 10 minutes ago and I generally don't use trampoline). That said, hooks and trampoline often don't mix well.

General Q: why are people using trampoline when using cljsbuild?

@jeluard
Copy link
Contributor

jeluard commented Aug 29, 2013

I can't point at a sample project

I was referring to a project that works for you so that I can check it does work for me and try to reproduce the issue.

why are people using trampoline when using cljsbuild?

It's mostly for convenience. I use trampoline when I want to run something close to production environment. It's simpler if I can do this without having to change my project.clj (as I have cljsbuild hook defined).

@xavi
Copy link

xavi commented Aug 29, 2013

@cemerick I was using trampoline with cljsbuild (through hooks) when deploying to Heroku because at the time Heroku docs were recommending the use of trampoline, and OTOH I didn't want to put the compiled ClojureScript files in the repo (I think they don't belong there in the same way as .class files are not put in the repo), so I used hooks to get ClojureScript compiled on deployment.

But recently Heroku changed the recommended way to deploy (as @technomancy mentioned, and Heroku updated docs already reflect). Since then I'm following those recommendations to deploy my projects, and this issue has become non-relevant for me.

@magomimmo
Copy link
Contributor

Here is a sample repository from which is possible to reproduce the issue:

https://github.com/magomimmo/modern-cljs.git

  1. Use case: :hooks [leiningen.cljsbuild]

    $ lein trampoline ring server-headless
    Compiling ClojureScript.
    Exception in thread "main" java.io.FileNotFoundException: Could not locate cljsbuild/compiler__init.class or cljsbuild/compiler.clj on classpath:
    at clojure.lang.RT.load(RT.java:443)
    at clojure.lang.RT.load(RT.java:411)
    at clojure.core$load$fn__5018.invoke(core.clj:5530)
    at clojure.core$load.doInvoke(core.clj:5529)
    at clojure.lang.RestFn.invoke(RestFn.java:408)
    at clojure.core$load_one.invoke(core.clj:5336)
    at clojure.core$load_lib$fn__4967.invoke(core.clj:5375)
    at clojure.core$load_lib.doInvoke(core.clj:5374)
    at clojure.lang.RestFn.applyTo(RestFn.java:142)
    at clojure.core$apply.invoke(core.clj:619)
    at clojure.core$load_libs.doInvoke(core.clj:5413)
    at clojure.lang.RestFn.applyTo(RestFn.java:137)
    at clojure.core$apply.invoke(core.clj:619)
    at clojure.core$require.doInvoke(core.clj:5496)
    at clojure.lang.RestFn.invoke(RestFn.java:436)
    at user$eval7.invoke(form-init4607419569722922037.clj:1)
    at clojure.lang.Compiler.eval(Compiler.java:6619)
    at clojure.lang.Compiler.eval(Compiler.java:6608)
    at clojure.lang.Compiler.load(Compiler.java:7064)
    at clojure.lang.Compiler.loadFile(Compiler.java:7020)
    at clojure.main$load_script.invoke(main.clj:294)
    at clojure.main$init_opt.invoke(main.clj:299)
    at clojure.main$initialize.invoke(main.clj:327)
    at clojure.main$null_opt.invoke(main.clj:362)
    at clojure.main$main.doInvoke(main.clj:440)
    at clojure.lang.RestFn.invoke(RestFn.java:421)
    at clojure.lang.Var.invoke(Var.java:419)
    at clojure.lang.AFn.applyToHelper(AFn.java:163)
    at clojure.lang.Var.applyTo(Var.java:532)
    at clojure.main.main(main.java:37)
  2. Use Case: no hooks

$ lein trampoline ring server-headless
2013-09-13 00:34:50.568:INFO:oejs.Server:jetty-7.6.8.v20121106
2013-09-13 00:34:50.604:INFO:oejs.AbstractConnector:Started SelectChannelConnector@0.0.0.0:3000
Started server on port 3000

Seems to be a classpath problem.

@levand
Copy link
Contributor

levand commented Jun 5, 2014

I just wanted to add that this issue also breaks the REPL in the Cursive Intellij plugin, which apparently is using lein trampoline. @cursiveclojure @cemerick

@cemerick
Copy link
Collaborator

cemerick commented Jun 5, 2014

Looking at this, it's not clear to me why cljsbuild isn't on the classpath (along with e.g. everything else I have in :dev that is on the classpath) when attempting to run a task via lein trampoline. :hooks is not really relevant, it just forces the issue by necessarily attempting to run the cljsbuild task within the scope of the trampoline.

Again, happy to look at a PR on this.

In the meantime: don't use trampoline, or chain the task explicitly, before the trampoline, e.g. lein do cljsbuild once, trampoline repl.

@cursive-ide
Copy link

why are people using trampoline when using cljsbuild?

Cursive uses the underlying trampoline mechanism to start all its REPLs. This is so that the REPL startup script can be created in the Cursive process without having to start another external JVM just to create the script. It does create a few problems due to trampoline use and also the fact that the JVM used to run Cursive may be different to the one used to run the REPL, so some config is sometimes incorrect. However it's nothing that can't be worked around so far, and the alternative would be very slow.

@realyze
Copy link

realyze commented Nov 24, 2014

Please note that this is also a problem when deploying to Heroku as they suggest to use trampoline.

@cemerick
Copy link
Collaborator

Looking back at this, I've since developed and deployed an application to heroku that uses cljsbuild without trampoline, with no problems. That's strictly FWIW, just by way of saying I've still not been able to repro.

This issue has been open ~18 months, but no PR has been offered. If someone could produce one and have at least one other person vouch for it, I'll be happy to merge, if only to make sure that @cursiveclojure doesn't continue to get bitten.

@ccfontes
Copy link

When I was cleaning my forks, I accidentally deleted the one where the fix was made, but the source is still in clojars. I think It was a trivial fix though.

That being said, I don't even remember anything about the issue anymore. Sorry :(

@cprice404
Copy link
Contributor

ran into this with @cursiveclojure today. :(

@gdanov
Copy link

gdanov commented Mar 17, 2015

me too. it seems to be one of the things getting in the way of having cursive + cljs repls play together

@conan
Copy link

conan commented Nov 17, 2015

This is preventing me from running REPLs in Cursive, sadly.
Windows 10, Intellij 15.0.1, Cursive 0.1.70

@mneise mneise added the Bug label Dec 4, 2015
@mneise mneise reopened this Dec 4, 2015
j0ni added a commit to j0ni/music-wall-clj that referenced this issue Feb 1, 2016
@cprice404
Copy link
Contributor

Doing battle with this bug again today. I think I've broken it down into two discrete issues.

The first has to do with the fact that this git repo actually produces two separate artifacts; the lein plugin artifact lein-cljsbuild (from the plugin directory), and another artifact called just cljsbuild (from the support directory).

The code in plugin/src/leiningen/cljsbuild/subproject.clj does some fairly magical stuff to add in a dependency on the cljsbuild artifact, but I don't think that's necessarily causing the problem.

I'm not sure that I understand exactly why, but the temporary script that lein generates for the trampoline execution includes this at the top:

    (require (quote cljsbuild.compiler)
             (quote cljsbuild.crossover)
             (quote cljsbuild.util))

And the classpath that lein launches that script with does not include any of the lein plugin artifacts, nor their dependencies, so cljsbuild is not on the classpath.

This is easy enough to remedy; just add [cljsbuild "1.1.2"] to the dev dependencies for your project. Doing that gets me past the Could not locate cljsbuild/compiler__init.class or cljsbuild/compiler.clj on classpath error.

Which brings us to the second issue, which is the one that @ccfontes mentioned above; in the happy path of the code in plugin/src/leiningen/cljsbuild.clj there is a line that calls System/exit after the cljs compilation has completed. When this happens it kills the trampolined repl session.

I can't find anything in the code that explains why that exit is necessary, and it doesn't seem like lein cljsbuild once runs any slower without it, and it doesn't cause any test failures... so I can file a PR to remove it.

If I do the two things above (add cljsbuild to my dev deps, and remove the exit call from cljsbuild.clj in the plugin), the trampoline REPL works fine for me both from the CLI and via @cursive-ide .

@cprice404
Copy link
Contributor

I filed a PR, and also deployed a fork with the fix to clojars:

https://clojars.org/cprice404/lein-cljsbuild/versions/1.1.2-noexit

@mneise
Copy link
Collaborator

mneise commented Feb 3, 2016

@cprice404 Awesome, thank you for digging into this! Will have a closer look at your PR and your findings in the next couple of days 😉

@cprice404
Copy link
Contributor

@mneise ping! just checking to see if this slipped through the cracks.

@mneise
Copy link
Collaborator

mneise commented Feb 19, 2016

@cprice404 Merged your PR for the System/exit #436, thank you! This definitely helps when chaining tasks with lein do.

Regarding the missing cljsbuild dependency, we already add it as a dependency to the project's dependencies before running eval-in-project, so there really should be no need for a user to include it again in their project's dependencies. I've also noticed that not every use of lein trampoline has cljsbuild missing on the classpath, for example lein trampoline do clean, cljsbuild once dev works fine for me. Therefore, I think that this might be a bug in leiningen and I've already created an issue for this (technomancy/leiningen#2095).

@cprice404
Copy link
Contributor

@mneise thanks! Adding cljsbuild as an explicit dependency in my dev profile is a sufficient workaround for now, but I've been digging in the lein source lately for other reasons, so maybe I'll take a peek at that bug you opened if I get a chance.

Any idea when you might do the next release? Looking forward to getting off of my fork :)

@mneise mneise reopened this Feb 19, 2016
@mneise
Copy link
Collaborator

mneise commented Feb 19, 2016

@cprice404 Will try to cut a release this weekend 😉

@cprice404
Copy link
Contributor

yay, thanks.

@cprice404
Copy link
Contributor

I presume this went into the 1.1.3 release? If so, thanks!

@mneise
Copy link
Collaborator

mneise commented Mar 8, 2016

@cprice404 Yes, just released it this morning. Let me know if you experience any issues 😉

@cprice404
Copy link
Contributor

will do, thanks again.

@cprice404
Copy link
Contributor

Upgraded our project to 1.1.3 today and it seems to be working fine. Thanks!

ggiraldez added a commit to instedd/planwise that referenced this issue Jun 2, 2016
There's an open issue with using cljsbuild with `lein trampoline`. See
emezeske/lein-cljsbuild#204
@maiq123
Copy link

maiq123 commented Jan 14, 2024

Hi is there any update on this? Or are we still using the same workaround of adding the dependency?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests