Getting "jQuery is not defined" when using a library that depends on it

154 views Asked by At

I am trying to use the bootstrap input spinner in my scalajs app. But when I try to use it I am getting the error "jQuery is not defined", even though I have included it in my project. Can someone tell me what I am missing?

So if I define a build.sbt:

name := "repro"
version := "1.0"
scalaVersion := "2.12.8"                      

scalaJSUseMainModuleInitializer := true       
mainClass in Compile := Some("App")   
enablePlugins(ScalaJSPlugin)
enablePlugins(ScalaJSBundlerPlugin)

webpackBundlingMode := BundlingMode.LibraryOnly()

libraryDependencies ++= Seq(
"org.querki" %%% "jquery-facade" % "1.2"
)

npmDependencies in Compile ++= Seq(
    "bootstrap" -> "4.3.1",
    "jquery" -> "3.2.1",
    "bootstrap-input-spinner" -> "1.11.8",
)

And then try to use it in my app as follows:

@js.native

trait BootstrapInputSpinner extends JQuery {
def inputSpinner(options: js.Object = js.Dynamic.literal()): BootstrapInputSpinner = js.native
}

object BootstrapInputSpinner {
@JSImport("bootstrap-input-spinner", JSImport.Default)
@js.native
object Import extends BootstrapInputSpinner
val _import = Import  // explicitly import it

implicit def bisExtensions(query: JQuery): BootstrapInputSpinner = 

query.asInstanceOf[BootstrapInputSpinner]
}


object App {

  import BootstrapInputSpinner._

  def main(args: Array[String]): Unit = {
    $(dom.document.getElementById("spinner")).inputSpinner()
  }
}

My html file is defined as follows:

<!DOCTYPE html>
<html>
<head>
    <title>Test User interface</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1">
</head>
<body>

<div class="app-container" id="root">
    <input id="spinner" type="number"/>
</div>

<script src="repro-fastopt-library.js"></script>
<script src="repro-fastopt-loader.js"></script>
<script src="repro-fastopt.js"></script>

</body>
</html>

Note that if I don't refer to the bootstrap-input-spinner library and try to use jQuery on its own it works fine. For example there are no errors if I change my App object to:

object App {

//  import BootstrapInputSpinner._

  def main(args: Array[String]): Unit = {
    println($(dom.document.getElementById("spinner")))
  }
}

Also, I checked the -library.js file and it has the following code:

module.exports = {
  "require": (function(x1) {
    return {
      "jquery": __webpack_require__(2),
      "bootstrap-input-spinner": __webpack_require__(3)
    }[x1]
  })
}

Which tells me that jquery should be imported first?

1

There are 1 answers

9
Ion On

I could guess from looking at the code, that you might need to add jQuery script too, before the library script that depend on.

Side note: You must check the compatibility of the bootstrap version and the jquery it depends

<script
  src="https://code.jquery.com/jquery-3.4.1.min.js"
  integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
  crossorigin="anonymous"></script>
<script src="repro-fastopt-library.js"></script>
<script src="repro-fastopt-loader.js"></script>
<script src="repro-fastopt.js"></script>

Which of the scripts depend on jquery?

repro-fastopt-library or repro-fastopt-loader or repro-fastopt

It could be the import order when you bundle them.