stimulus-rails 0.7.2 → 1.0.3

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: a394227aa508c3626226dfc459efb1d264dcd310d90077d9f446605407f8f778
4
- data.tar.gz: 267e9e6e0429f0d2cb9a46befac52e319055e05f316ddf68f618cc4b59b2def8
3
+ metadata.gz: 79e7cd48f25a99d585cf5a257256a1d52d26d131e7cdb7a7de81135752e19ca3
4
+ data.tar.gz: bead4bdbef70c56d7343755884185eb399d93b0718f37b9988163a74aad9fe81
5
5
  SHA512:
6
- metadata.gz: 4ffd9d3864592dea0e364690f3d19dff2469b68e6318884c02e1af4ef110244fe193568003139b198df5a69da8e4194cd71bc96746ba004664460fc83a72908a
7
- data.tar.gz: c70a8be0745b25ac1de92456309ee11e74930c265ef6fb1cf5f9df0ae474beb295b5d06dd37f844b76d399b096424f0ebd41ea2598d21c2f69e7b55005001de2
6
+ metadata.gz: 83eb18cb343693c7535aa193fe16251b69a29196225c019672404ea02a45280296f6d5c2c163923e5fee4611ea12493d48040a9b1872f00d89cc0955e9677970
7
+ data.tar.gz: 4056db548e949647e7a7d66ba5e8759bb8e0a17f74f2fb4e8e23ddbb41d6d8eab5e729e430a07351554d893c756cc07cf0e15b71d236afb0bc0e23838f8b67df
data/README.md CHANGED
@@ -7,6 +7,10 @@ Stimulus for Rails makes it easy to use this modest framework with both import-m
7
7
 
8
8
  ## Installation
9
9
 
10
+ This gem is automatically configured for applications made with Rails 7+ (unless `--skip-hotwire` is passed to the generator). But if you're on Rails 6, you can install it with the installer or manually:
11
+
12
+ ### Installing with installer
13
+
10
14
  1. Add the `stimulus-rails` gem to your Gemfile: `gem 'stimulus-rails'`
11
15
  2. Run `./bin/bundle install`.
12
16
  3. Run `./bin/rails stimulus:install`
@@ -15,6 +19,89 @@ The installer will automatically detect whether you're using an [import map](htt
15
19
 
16
20
  The installer amends your JavaScript entry point at `app/javascript/application.js` to import the `app/javascript/controllers/index.js` file, which is responsible for setting up your Stimulus application and registering your controllers.
17
21
 
22
+ ### Installing manually
23
+
24
+ Note that we recommend running the installer as described above. But the following is helpful if you encounter errors while running the installer (e.g., if there are conflicts with existing files) or if you just like doing stuff manually. Follow the instructions for import map *or* JavaScript bundler, depending on your setup.
25
+
26
+ 1. Add the `stimulus-rails` gem to your Gemfile: `gem 'stimulus-rails'`
27
+ 2. Run `./bin/bundle install`.
28
+
29
+ #### With import map
30
+
31
+ 3. Create `app/javascript/controllers/index.js` and load your controllers like this:
32
+ ```javascript
33
+ import { application } from "controllers/application"
34
+
35
+ // Eager load all controllers defined in the import map under controllers/**/*_controller
36
+ import { eagerLoadControllersFrom } from "@hotwired/stimulus-loading"
37
+ eagerLoadControllersFrom("controllers", application)
38
+ ```
39
+
40
+ 4. Create `app/javascript/controllers/application.js` with the following content:
41
+ ```javascript
42
+ import { Application } from "@hotwired/stimulus"
43
+
44
+ const application = Application.start()
45
+
46
+ // Configure Stimulus development experience
47
+ application.debug = false
48
+ window.Stimulus = application
49
+
50
+ export { application }
51
+ ```
52
+
53
+ 5. Add the following line to `app/javascript/application.js` to import all your controllers:
54
+ ```javascript
55
+ import "controllers"
56
+ ```
57
+
58
+ 6. Finally, Pin Stimulus and controllers in `config/importmap.rb` by adding:
59
+ ```ruby
60
+ pin "@hotwired/stimulus", to: "stimulus.min.js", preload: true
61
+ pin "@hotwired/stimulus-loading", to: "stimulus-loading.js", preload: true
62
+ pin_all_from "app/javascript/controllers", under: "controllers"
63
+
64
+ ```
65
+
66
+ #### With JavaScript bundler
67
+
68
+ 3. Create `app/javascript/controllers/index.js` and load your controllers.
69
+
70
+ Make sure to change `HelloController` to an actual controller and repeat for every controller you have or use the command mentioned in the comments below:
71
+ ```javascript
72
+ // This file is auto-generated by ./bin/rails stimulus:manifest:update
73
+ // Run that command whenever you add a new controller or create them with
74
+ // ./bin/rails generate stimulus controllerName
75
+
76
+ import { application } from "./application"
77
+
78
+ import HelloController from "./hello_controller"
79
+ application.register("hello", HelloController)
80
+ ```
81
+
82
+ 4. Create `app/javascript/controllers/application.js` with the following content:
83
+ ```javascript
84
+ import { Application } from "@hotwired/stimulus"
85
+
86
+ const application = Application.start()
87
+
88
+ // Configure Stimulus development experience
89
+ application.debug = false
90
+ window.Stimulus = application
91
+
92
+ export { application }
93
+ ```
94
+
95
+ 5. Add the following line to `app/javascript/application.js` to import all your controllers:
96
+ ```javascript
97
+ import "controllers"
98
+ ```
99
+
100
+ 6. Finally, add the Stimulus package to yarn:
101
+ ```bash
102
+ yarn add @hotwired/stimulus
103
+ ```
104
+
18
105
 
19
106
  ## Usage with import map
20
107
 
@@ -19,7 +19,7 @@ function extractControllerNamesFrom(element) {
19
19
  function loadController(name) {
20
20
  import(controllerFilename(name))
21
21
  .then(module => registerController(name, module))
22
- .catch(error => console.log(`Failed to autoload controller: ${name}`, error))
22
+ .catch(error => console.error(`Failed to autoload controller: ${name}`, error))
23
23
  }
24
24
 
25
25
  function controllerFilename(name) {
@@ -21,7 +21,7 @@ function registerControllerFromPath(path, under, application) {
21
21
 
22
22
  import(path)
23
23
  .then(module => application.register(name, module.default))
24
- .catch(error => console.log(`Failed to register controller: ${name} (${path})`, error))
24
+ .catch(error => console.error(`Failed to register controller: ${name} (${path})`, error))
25
25
  }
26
26
 
27
27
  console.warn("stimulus-importmap-autoload.js has been deprecated in favor of stimulus-loading.js")
@@ -21,9 +21,11 @@ function registerControllerFromPath(path, under, application) {
21
21
  .replace(/\//g, "--")
22
22
  .replace(/_/g, "-")
23
23
 
24
- import(path)
25
- .then(module => registerController(name, module, application))
26
- .catch(error => console.debug(`Failed to register controller: ${name} (${path})`, error))
24
+ if (!(name in registeredControllers)) {
25
+ import(path)
26
+ .then(module => registerController(name, module, application))
27
+ .catch(error => console.error(`Failed to register controller: ${name} (${path})`, error))
28
+ }
27
29
  }
28
30
 
29
31
 
@@ -64,9 +66,11 @@ function extractControllerNamesFrom(element) {
64
66
  }
65
67
 
66
68
  function loadController(name, under, application) {
67
- import(controllerFilename(name, under))
68
- .then(module => registerController(name, module, application))
69
- .catch(error => console.debug(`Failed to autoload controller: ${name}`, error))
69
+ if (!(name in registeredControllers)) {
70
+ import(controllerFilename(name, under))
71
+ .then(module => registerController(name, module, application))
72
+ .catch(error => console.error(`Failed to autoload controller: ${name}`, error))
73
+ }
70
74
  }
71
75
 
72
76
  function controllerFilename(name, under) {
@@ -74,8 +78,6 @@ function controllerFilename(name, under) {
74
78
  }
75
79
 
76
80
  function registerController(name, module, application) {
77
- if (name in registeredControllers) return
78
-
79
81
  application.register(name, module.default)
80
82
  registeredControllers[name] = true
81
83
  }
@@ -1,9 +1,5 @@
1
1
  //= link ./stimulus-autoloader.js
2
2
  //= link ./stimulus-importmap-autoloader.js
3
3
  //= link ./stimulus-loading.js
4
-
5
- /*
6
- Stimulus 3.0.1
7
- Copyright © 2021 Basecamp, LLC
8
- */
9
4
  class e{constructor(e,t,r){this.eventTarget=e,this.eventName=t,this.eventOptions=r,this.unorderedBindings=new Set}connect(){this.eventTarget.addEventListener(this.eventName,this,this.eventOptions)}disconnect(){this.eventTarget.removeEventListener(this.eventName,this,this.eventOptions)}bindingConnected(e){this.unorderedBindings.add(e)}bindingDisconnected(e){this.unorderedBindings.delete(e)}handleEvent(e){const t=function(e){if("immediatePropagationStopped"in e)return e;{const{stopImmediatePropagation:t}=e;return Object.assign(e,{immediatePropagationStopped:!1,stopImmediatePropagation(){this.immediatePropagationStopped=!0,t.call(this)}})}}(e);for(const e of this.bindings){if(t.immediatePropagationStopped)break;e.handleEvent(t)}}get bindings(){return Array.from(this.unorderedBindings).sort(((e,t)=>{const r=e.index,s=t.index;return r<s?-1:r>s?1:0}))}}class t{constructor(e){this.application=e,this.eventListenerMaps=new Map,this.started=!1}start(){this.started||(this.started=!0,this.eventListeners.forEach((e=>e.connect())))}stop(){this.started&&(this.started=!1,this.eventListeners.forEach((e=>e.disconnect())))}get eventListeners(){return Array.from(this.eventListenerMaps.values()).reduce(((e,t)=>e.concat(Array.from(t.values()))),[])}bindingConnected(e){this.fetchEventListenerForBinding(e).bindingConnected(e)}bindingDisconnected(e){this.fetchEventListenerForBinding(e).bindingDisconnected(e)}handleError(e,t,r={}){this.application.handleError(e,`Error ${t}`,r)}fetchEventListenerForBinding(e){const{eventTarget:t,eventName:r,eventOptions:s}=e;return this.fetchEventListener(t,r,s)}fetchEventListener(e,t,r){const s=this.fetchEventListenerMapForEventTarget(e),n=this.cacheKey(t,r);let i=s.get(n);return i||(i=this.createEventListener(e,t,r),s.set(n,i)),i}createEventListener(t,r,s){const n=new e(t,r,s);return this.started&&n.connect(),n}fetchEventListenerMapForEventTarget(e){let t=this.eventListenerMaps.get(e);return t||(t=new Map,this.eventListenerMaps.set(e,t)),t}cacheKey(e,t){const r=[e];return Object.keys(t).sort().forEach((e=>{r.push(`${t[e]?"":"!"}${e}`)})),r.join(":")}}const r=/^((.+?)(@(window|document))?->)?(.+?)(#([^:]+?))(:(.+))?$/;function s(e){return"window"==e?window:"document"==e?document:void 0}function n(e){return e.replace(/(?:[_-])([a-z0-9])/g,((e,t)=>t.toUpperCase()))}function i(e){return e.charAt(0).toUpperCase()+e.slice(1)}function o(e){return e.replace(/([A-Z])/g,((e,t)=>`-${t.toLowerCase()}`))}const a={a:e=>"click",button:e=>"click",form:e=>"submit",details:e=>"toggle",input:e=>"submit"==e.getAttribute("type")?"click":"input",select:e=>"change",textarea:e=>"input"};function c(e){throw new Error(e)}function h(e){try{return JSON.parse(e)}catch(t){return e}}class l{constructor(e,t){this.context=e,this.action=t}get index(){return this.action.index}get eventTarget(){return this.action.eventTarget}get eventOptions(){return this.action.eventOptions}get identifier(){return this.context.identifier}handleEvent(e){this.willBeInvokedByEvent(e)&&this.invokeWithEvent(e)}get eventName(){return this.action.eventName}get method(){const e=this.controller[this.methodName];if("function"==typeof e)return e;throw new Error(`Action "${this.action}" references undefined method "${this.methodName}"`)}invokeWithEvent(e){const{target:t,currentTarget:r}=e;try{const{params:s}=this.action,n=Object.assign(e,{params:s});this.method.call(this.controller,n),this.context.logDebugActivity(this.methodName,{event:e,target:t,currentTarget:r,action:this.methodName})}catch(t){const{identifier:r,controller:s,element:n,index:i}=this,o={identifier:r,controller:s,element:n,index:i,event:e};this.context.handleError(t,`invoking action "${this.action}"`,o)}}willBeInvokedByEvent(e){const t=e.target;return this.element===t||(t instanceof Element&&this.element.contains(t)?this.scope.containsElement(t):this.scope.containsElement(this.action.element))}get controller(){return this.context.controller}get methodName(){return this.action.methodName}get element(){return this.scope.element}get scope(){return this.context.scope}}class u{constructor(e,t){this.mutationObserverInit={attributes:!0,childList:!0,subtree:!0},this.element=e,this.started=!1,this.delegate=t,this.elements=new Set,this.mutationObserver=new MutationObserver((e=>this.processMutations(e)))}start(){this.started||(this.started=!0,this.mutationObserver.observe(this.element,this.mutationObserverInit),this.refresh())}pause(e){this.started&&(this.mutationObserver.disconnect(),this.started=!1),e(),this.started||(this.mutationObserver.observe(this.element,this.mutationObserverInit),this.started=!0)}stop(){this.started&&(this.mutationObserver.takeRecords(),this.mutationObserver.disconnect(),this.started=!1)}refresh(){if(this.started){const e=new Set(this.matchElementsInTree());for(const t of Array.from(this.elements))e.has(t)||this.removeElement(t);for(const t of Array.from(e))this.addElement(t)}}processMutations(e){if(this.started)for(const t of e)this.processMutation(t)}processMutation(e){"attributes"==e.type?this.processAttributeChange(e.target,e.attributeName):"childList"==e.type&&(this.processRemovedNodes(e.removedNodes),this.processAddedNodes(e.addedNodes))}processAttributeChange(e,t){const r=e;this.elements.has(r)?this.delegate.elementAttributeChanged&&this.matchElement(r)?this.delegate.elementAttributeChanged(r,t):this.removeElement(r):this.matchElement(r)&&this.addElement(r)}processRemovedNodes(e){for(const t of Array.from(e)){const e=this.elementFromNode(t);e&&this.processTree(e,this.removeElement)}}processAddedNodes(e){for(const t of Array.from(e)){const e=this.elementFromNode(t);e&&this.elementIsActive(e)&&this.processTree(e,this.addElement)}}matchElement(e){return this.delegate.matchElement(e)}matchElementsInTree(e=this.element){return this.delegate.matchElementsInTree(e)}processTree(e,t){for(const r of this.matchElementsInTree(e))t.call(this,r)}elementFromNode(e){if(e.nodeType==Node.ELEMENT_NODE)return e}elementIsActive(e){return e.isConnected==this.element.isConnected&&this.element.contains(e)}addElement(e){this.elements.has(e)||this.elementIsActive(e)&&(this.elements.add(e),this.delegate.elementMatched&&this.delegate.elementMatched(e))}removeElement(e){this.elements.has(e)&&(this.elements.delete(e),this.delegate.elementUnmatched&&this.delegate.elementUnmatched(e))}}class d{constructor(e,t,r){this.attributeName=t,this.delegate=r,this.elementObserver=new u(e,this)}get element(){return this.elementObserver.element}get selector(){return`[${this.attributeName}]`}start(){this.elementObserver.start()}pause(e){this.elementObserver.pause(e)}stop(){this.elementObserver.stop()}refresh(){this.elementObserver.refresh()}get started(){return this.elementObserver.started}matchElement(e){return e.hasAttribute(this.attributeName)}matchElementsInTree(e){const t=this.matchElement(e)?[e]:[],r=Array.from(e.querySelectorAll(this.selector));return t.concat(r)}elementMatched(e){this.delegate.elementMatchedAttribute&&this.delegate.elementMatchedAttribute(e,this.attributeName)}elementUnmatched(e){this.delegate.elementUnmatchedAttribute&&this.delegate.elementUnmatchedAttribute(e,this.attributeName)}elementAttributeChanged(e,t){this.delegate.elementAttributeValueChanged&&this.attributeName==t&&this.delegate.elementAttributeValueChanged(e,t)}}class g{constructor(e,t){this.element=e,this.delegate=t,this.started=!1,this.stringMap=new Map,this.mutationObserver=new MutationObserver((e=>this.processMutations(e)))}start(){this.started||(this.started=!0,this.mutationObserver.observe(this.element,{attributes:!0,attributeOldValue:!0}),this.refresh())}stop(){this.started&&(this.mutationObserver.takeRecords(),this.mutationObserver.disconnect(),this.started=!1)}refresh(){if(this.started)for(const e of this.knownAttributeNames)this.refreshAttribute(e,null)}processMutations(e){if(this.started)for(const t of e)this.processMutation(t)}processMutation(e){const t=e.attributeName;t&&this.refreshAttribute(t,e.oldValue)}refreshAttribute(e,t){const r=this.delegate.getStringMapKeyForAttribute(e);if(null!=r){this.stringMap.has(e)||this.stringMapKeyAdded(r,e);const s=this.element.getAttribute(e);if(this.stringMap.get(e)!=s&&this.stringMapValueChanged(s,r,t),null==s){const t=this.stringMap.get(e);this.stringMap.delete(e),t&&this.stringMapKeyRemoved(r,e,t)}else this.stringMap.set(e,s)}}stringMapKeyAdded(e,t){this.delegate.stringMapKeyAdded&&this.delegate.stringMapKeyAdded(e,t)}stringMapValueChanged(e,t,r){this.delegate.stringMapValueChanged&&this.delegate.stringMapValueChanged(e,t,r)}stringMapKeyRemoved(e,t,r){this.delegate.stringMapKeyRemoved&&this.delegate.stringMapKeyRemoved(e,t,r)}get knownAttributeNames(){return Array.from(new Set(this.currentAttributeNames.concat(this.recordedAttributeNames)))}get currentAttributeNames(){return Array.from(this.element.attributes).map((e=>e.name))}get recordedAttributeNames(){return Array.from(this.stringMap.keys())}}function m(e,t,r){f(e,t).add(r)}function p(e,t,r){f(e,t).delete(r),b(e,t)}function f(e,t){let r=e.get(t);return r||(r=new Set,e.set(t,r)),r}function b(e,t){const r=e.get(t);null!=r&&0==r.size&&e.delete(t)}class v{constructor(){this.valuesByKey=new Map}get keys(){return Array.from(this.valuesByKey.keys())}get values(){return Array.from(this.valuesByKey.values()).reduce(((e,t)=>e.concat(Array.from(t))),[])}get size(){return Array.from(this.valuesByKey.values()).reduce(((e,t)=>e+t.size),0)}add(e,t){m(this.valuesByKey,e,t)}delete(e,t){p(this.valuesByKey,e,t)}has(e,t){const r=this.valuesByKey.get(e);return null!=r&&r.has(t)}hasKey(e){return this.valuesByKey.has(e)}hasValue(e){return Array.from(this.valuesByKey.values()).some((t=>t.has(e)))}getValuesForKey(e){const t=this.valuesByKey.get(e);return t?Array.from(t):[]}getKeysForValue(e){return Array.from(this.valuesByKey).filter((([t,r])=>r.has(e))).map((([e,t])=>e))}}class y extends v{constructor(){super(),this.keysByValue=new Map}get values(){return Array.from(this.keysByValue.keys())}add(e,t){super.add(e,t),m(this.keysByValue,t,e)}delete(e,t){super.delete(e,t),p(this.keysByValue,t,e)}hasValue(e){return this.keysByValue.has(e)}getKeysForValue(e){const t=this.keysByValue.get(e);return t?Array.from(t):[]}}class A{constructor(e,t,r){this.attributeObserver=new d(e,t,this),this.delegate=r,this.tokensByElement=new v}get started(){return this.attributeObserver.started}start(){this.attributeObserver.start()}pause(e){this.attributeObserver.pause(e)}stop(){this.attributeObserver.stop()}refresh(){this.attributeObserver.refresh()}get element(){return this.attributeObserver.element}get attributeName(){return this.attributeObserver.attributeName}elementMatchedAttribute(e){this.tokensMatched(this.readTokensForElement(e))}elementAttributeValueChanged(e){const[t,r]=this.refreshTokensForElement(e);this.tokensUnmatched(t),this.tokensMatched(r)}elementUnmatchedAttribute(e){this.tokensUnmatched(this.tokensByElement.getValuesForKey(e))}tokensMatched(e){e.forEach((e=>this.tokenMatched(e)))}tokensUnmatched(e){e.forEach((e=>this.tokenUnmatched(e)))}tokenMatched(e){this.delegate.tokenMatched(e),this.tokensByElement.add(e.element,e)}tokenUnmatched(e){this.delegate.tokenUnmatched(e),this.tokensByElement.delete(e.element,e)}refreshTokensForElement(e){const t=this.tokensByElement.getValuesForKey(e),r=this.readTokensForElement(e),s=function(e,t){const r=Math.max(e.length,t.length);return Array.from({length:r},((r,s)=>[e[s],t[s]]))}(t,r).findIndex((([e,t])=>{return s=t,!((r=e)&&s&&r.index==s.index&&r.content==s.content);var r,s}));return-1==s?[[],[]]:[t.slice(s),r.slice(s)]}readTokensForElement(e){const t=this.attributeName;return function(e,t,r){return e.trim().split(/\s+/).filter((e=>e.length)).map(((e,s)=>({element:t,attributeName:r,content:e,index:s})))}(e.getAttribute(t)||"",e,t)}}class E{constructor(e,t,r){this.tokenListObserver=new A(e,t,this),this.delegate=r,this.parseResultsByToken=new WeakMap,this.valuesByTokenByElement=new WeakMap}get started(){return this.tokenListObserver.started}start(){this.tokenListObserver.start()}stop(){this.tokenListObserver.stop()}refresh(){this.tokenListObserver.refresh()}get element(){return this.tokenListObserver.element}get attributeName(){return this.tokenListObserver.attributeName}tokenMatched(e){const{element:t}=e,{value:r}=this.fetchParseResultForToken(e);r&&(this.fetchValuesByTokenForElement(t).set(e,r),this.delegate.elementMatchedValue(t,r))}tokenUnmatched(e){const{element:t}=e,{value:r}=this.fetchParseResultForToken(e);r&&(this.fetchValuesByTokenForElement(t).delete(e),this.delegate.elementUnmatchedValue(t,r))}fetchParseResultForToken(e){let t=this.parseResultsByToken.get(e);return t||(t=this.parseToken(e),this.parseResultsByToken.set(e,t)),t}fetchValuesByTokenForElement(e){let t=this.valuesByTokenByElement.get(e);return t||(t=new Map,this.valuesByTokenByElement.set(e,t)),t}parseToken(e){try{return{value:this.delegate.parseValueForToken(e)}}catch(e){return{error:e}}}}class O{constructor(e,t){this.context=e,this.delegate=t,this.bindingsByAction=new Map}start(){this.valueListObserver||(this.valueListObserver=new E(this.element,this.actionAttribute,this),this.valueListObserver.start())}stop(){this.valueListObserver&&(this.valueListObserver.stop(),delete this.valueListObserver,this.disconnectAllActions())}get element(){return this.context.element}get identifier(){return this.context.identifier}get actionAttribute(){return this.schema.actionAttribute}get schema(){return this.context.schema}get bindings(){return Array.from(this.bindingsByAction.values())}connectAction(e){const t=new l(this.context,e);this.bindingsByAction.set(e,t),this.delegate.bindingConnected(t)}disconnectAction(e){const t=this.bindingsByAction.get(e);t&&(this.bindingsByAction.delete(e),this.delegate.bindingDisconnected(t))}disconnectAllActions(){this.bindings.forEach((e=>this.delegate.bindingDisconnected(e))),this.bindingsByAction.clear()}parseValueForToken(e){const t=class{constructor(e,t,r){this.element=e,this.index=t,this.eventTarget=r.eventTarget||e,this.eventName=r.eventName||function(e){const t=e.tagName.toLowerCase();if(t in a)return a[t](e)}(e)||c("missing event name"),this.eventOptions=r.eventOptions||{},this.identifier=r.identifier||c("missing identifier"),this.methodName=r.methodName||c("missing method name")}static forToken(e){return new this(e.element,e.index,function(e){const t=e.trim().match(r)||[];return{eventTarget:s(t[4]),eventName:t[2],eventOptions:t[9]?(n=t[9],n.split(":").reduce(((e,t)=>Object.assign(e,{[t.replace(/^!/,"")]:!/^!/.test(t)})),{})):{},identifier:t[5],methodName:t[7]};var n}(e.content))}toString(){const e=this.eventTargetName?`@${this.eventTargetName}`:"";return`${this.eventName}${e}->${this.identifier}#${this.methodName}`}get params(){return this.eventTarget instanceof Element?this.getParamsFromEventTargetAttributes(this.eventTarget):{}}getParamsFromEventTargetAttributes(e){const t={},r=new RegExp(`^data-${this.identifier}-(.+)-param$`);return Array.from(e.attributes).forEach((({name:e,value:s})=>{const i=e.match(r),o=i&&i[1];o&&Object.assign(t,{[n(o)]:h(s)})})),t}get eventTargetName(){return(e=this.eventTarget)==window?"window":e==document?"document":void 0;var e}}.forToken(e);if(t.identifier==this.identifier)return t}elementMatchedValue(e,t){this.connectAction(t)}elementUnmatchedValue(e,t){this.disconnectAction(t)}}class w{constructor(e,t){this.context=e,this.receiver=t,this.stringMapObserver=new g(this.element,this),this.valueDescriptorMap=this.controller.valueDescriptorMap,this.invokeChangedCallbacksForDefaultValues()}start(){this.stringMapObserver.start()}stop(){this.stringMapObserver.stop()}get element(){return this.context.element}get controller(){return this.context.controller}getStringMapKeyForAttribute(e){if(e in this.valueDescriptorMap)return this.valueDescriptorMap[e].name}stringMapKeyAdded(e,t){const r=this.valueDescriptorMap[t];this.hasValue(e)||this.invokeChangedCallback(e,r.writer(this.receiver[e]),r.writer(r.defaultValue))}stringMapValueChanged(e,t,r){const s=this.valueDescriptorNameMap[t];null!==e&&(null===r&&(r=s.writer(s.defaultValue)),this.invokeChangedCallback(t,e,r))}stringMapKeyRemoved(e,t,r){const s=this.valueDescriptorNameMap[e];this.hasValue(e)?this.invokeChangedCallback(e,s.writer(this.receiver[e]),r):this.invokeChangedCallback(e,s.writer(s.defaultValue),r)}invokeChangedCallbacksForDefaultValues(){for(const{key:e,name:t,defaultValue:r,writer:s}of this.valueDescriptors)null==r||this.controller.data.has(e)||this.invokeChangedCallback(t,s(r),void 0)}invokeChangedCallback(e,t,r){const s=`${e}Changed`,n=this.receiver[s];if("function"==typeof n){const s=this.valueDescriptorNameMap[e],i=s.reader(t);let o=r;r&&(o=s.reader(r)),n.call(this.receiver,i,o)}}get valueDescriptors(){const{valueDescriptorMap:e}=this;return Object.keys(e).map((t=>e[t]))}get valueDescriptorNameMap(){const e={};return Object.keys(this.valueDescriptorMap).forEach((t=>{const r=this.valueDescriptorMap[t];e[r.name]=r})),e}hasValue(e){const t=`has${i(this.valueDescriptorNameMap[e].name)}`;return this.receiver[t]}}class k{constructor(e,t){this.context=e,this.delegate=t,this.targetsByName=new v}start(){this.tokenListObserver||(this.tokenListObserver=new A(this.element,this.attributeName,this),this.tokenListObserver.start())}stop(){this.tokenListObserver&&(this.disconnectAllTargets(),this.tokenListObserver.stop(),delete this.tokenListObserver)}tokenMatched({element:e,content:t}){this.scope.containsElement(e)&&this.connectTarget(e,t)}tokenUnmatched({element:e,content:t}){this.disconnectTarget(e,t)}connectTarget(e,t){var r;this.targetsByName.has(t,e)||(this.targetsByName.add(t,e),null===(r=this.tokenListObserver)||void 0===r||r.pause((()=>this.delegate.targetConnected(e,t))))}disconnectTarget(e,t){var r;this.targetsByName.has(t,e)&&(this.targetsByName.delete(t,e),null===(r=this.tokenListObserver)||void 0===r||r.pause((()=>this.delegate.targetDisconnected(e,t))))}disconnectAllTargets(){for(const e of this.targetsByName.keys)for(const t of this.targetsByName.getValuesForKey(e))this.disconnectTarget(t,e)}get attributeName(){return`data-${this.context.identifier}-target`}get element(){return this.context.element}get scope(){return this.context.scope}}class M{constructor(e,t){this.logDebugActivity=(e,t={})=>{const{identifier:r,controller:s,element:n}=this;t=Object.assign({identifier:r,controller:s,element:n},t),this.application.logDebugActivity(this.identifier,e,t)},this.module=e,this.scope=t,this.controller=new e.controllerConstructor(this),this.bindingObserver=new O(this,this.dispatcher),this.valueObserver=new w(this,this.controller),this.targetObserver=new k(this,this);try{this.controller.initialize(),this.logDebugActivity("initialize")}catch(e){this.handleError(e,"initializing controller")}}connect(){this.bindingObserver.start(),this.valueObserver.start(),this.targetObserver.start();try{this.controller.connect(),this.logDebugActivity("connect")}catch(e){this.handleError(e,"connecting controller")}}disconnect(){try{this.controller.disconnect(),this.logDebugActivity("disconnect")}catch(e){this.handleError(e,"disconnecting controller")}this.targetObserver.stop(),this.valueObserver.stop(),this.bindingObserver.stop()}get application(){return this.module.application}get identifier(){return this.module.identifier}get schema(){return this.application.schema}get dispatcher(){return this.application.dispatcher}get element(){return this.scope.element}get parentElement(){return this.element.parentElement}handleError(e,t,r={}){const{identifier:s,controller:n,element:i}=this;r=Object.assign({identifier:s,controller:n,element:i},r),this.application.handleError(e,`Error ${t}`,r)}targetConnected(e,t){this.invokeControllerMethod(`${t}TargetConnected`,e)}targetDisconnected(e,t){this.invokeControllerMethod(`${t}TargetDisconnected`,e)}invokeControllerMethod(e,...t){const r=this.controller;"function"==typeof r[e]&&r[e](...t)}}function N(e,t){const r=T(e);return Array.from(r.reduce(((e,r)=>(function(e,t){const r=e[t];return Array.isArray(r)?r:[]}(r,t).forEach((t=>e.add(t))),e)),new Set))}function B(e,t){return T(e).reduce(((e,r)=>(e.push(...function(e,t){const r=e[t];return r?Object.keys(r).map((e=>[e,r[e]])):[]}(r,t)),e)),[])}function T(e){const t=[];for(;e;)t.push(e),e=Object.getPrototypeOf(e);return t.reverse()}function C(e){return function(e,t){const r=x(e),s=function(e,t){return F(t).reduce(((r,s)=>{const n=function(e,t,r){const s=Object.getOwnPropertyDescriptor(e,r);if(!s||!("value"in s)){const e=Object.getOwnPropertyDescriptor(t,r).value;return s&&(e.get=s.get||e.get,e.set=s.set||e.set),e}}(e,t,s);return n&&Object.assign(r,{[s]:n}),r}),{})}(e.prototype,t);return Object.defineProperties(r.prototype,s),r}(e,function(e){return N(e,"blessings").reduce(((t,r)=>{const s=r(e);for(const e in s){const r=t[e]||{};t[e]=Object.assign(r,s[e])}return t}),{})}(e))}const F="function"==typeof Object.getOwnPropertySymbols?e=>[...Object.getOwnPropertyNames(e),...Object.getOwnPropertySymbols(e)]:Object.getOwnPropertyNames,x=(()=>{function e(e){function t(){return Reflect.construct(e,arguments,new.target)}return t.prototype=Object.create(e.prototype,{constructor:{value:t}}),Reflect.setPrototypeOf(t,e),t}try{return function(){const t=e((function(){this.a.call(this)}));t.prototype.a=function(){},new t}(),e}catch(e){return e=>class extends e{}}})();class L{constructor(e,t){this.application=e,this.definition=function(e){return{identifier:e.identifier,controllerConstructor:C(e.controllerConstructor)}}(t),this.contextsByScope=new WeakMap,this.connectedContexts=new Set}get identifier(){return this.definition.identifier}get controllerConstructor(){return this.definition.controllerConstructor}get contexts(){return Array.from(this.connectedContexts)}connectContextForScope(e){const t=this.fetchContextForScope(e);this.connectedContexts.add(t),t.connect()}disconnectContextForScope(e){const t=this.contextsByScope.get(e);t&&(this.connectedContexts.delete(t),t.disconnect())}fetchContextForScope(e){let t=this.contextsByScope.get(e);return t||(t=new M(this,e),this.contextsByScope.set(e,t)),t}}class ${constructor(e){this.scope=e}has(e){return this.data.has(this.getDataKey(e))}get(e){return this.getAll(e)[0]}getAll(e){const t=this.data.get(this.getDataKey(e))||"";return t.match(/[^\s]+/g)||[]}getAttributeName(e){return this.data.getAttributeNameForKey(this.getDataKey(e))}getDataKey(e){return`${e}-class`}get data(){return this.scope.data}}class S{constructor(e){this.scope=e}get element(){return this.scope.element}get identifier(){return this.scope.identifier}get(e){const t=this.getAttributeNameForKey(e);return this.element.getAttribute(t)}set(e,t){const r=this.getAttributeNameForKey(e);return this.element.setAttribute(r,t),this.get(e)}has(e){const t=this.getAttributeNameForKey(e);return this.element.hasAttribute(t)}delete(e){if(this.has(e)){const t=this.getAttributeNameForKey(e);return this.element.removeAttribute(t),!0}return!1}getAttributeNameForKey(e){return`data-${this.identifier}-${o(e)}`}}class D{constructor(e){this.warnedKeysByObject=new WeakMap,this.logger=e}warn(e,t,r){let s=this.warnedKeysByObject.get(e);s||(s=new Set,this.warnedKeysByObject.set(e,s)),s.has(t)||(s.add(t),this.logger.warn(r,e))}}function V(e,t){return`[${e}~="${t}"]`}class K{constructor(e){this.scope=e}get element(){return this.scope.element}get identifier(){return this.scope.identifier}get schema(){return this.scope.schema}has(e){return null!=this.find(e)}find(...e){return e.reduce(((e,t)=>e||this.findTarget(t)||this.findLegacyTarget(t)),void 0)}findAll(...e){return e.reduce(((e,t)=>[...e,...this.findAllTargets(t),...this.findAllLegacyTargets(t)]),[])}findTarget(e){const t=this.getSelectorForTargetName(e);return this.scope.findElement(t)}findAllTargets(e){const t=this.getSelectorForTargetName(e);return this.scope.findAllElements(t)}getSelectorForTargetName(e){return V(this.schema.targetAttributeForScope(this.identifier),e)}findLegacyTarget(e){const t=this.getLegacySelectorForTargetName(e);return this.deprecate(this.scope.findElement(t),e)}findAllLegacyTargets(e){const t=this.getLegacySelectorForTargetName(e);return this.scope.findAllElements(t).map((t=>this.deprecate(t,e)))}getLegacySelectorForTargetName(e){const t=`${this.identifier}.${e}`;return V(this.schema.targetAttribute,t)}deprecate(e,t){if(e){const{identifier:r}=this,s=this.schema.targetAttribute,n=this.schema.targetAttributeForScope(r);this.guide.warn(e,`target:${t}`,`Please replace ${s}="${r}.${t}" with ${n}="${t}". The ${s} attribute is deprecated and will be removed in a future version of Stimulus.`)}return e}get guide(){return this.scope.guide}}class j{constructor(e,t,r,s){this.targets=new K(this),this.classes=new $(this),this.data=new S(this),this.containsElement=e=>e.closest(this.controllerSelector)===this.element,this.schema=e,this.element=t,this.identifier=r,this.guide=new D(s)}findElement(e){return this.element.matches(e)?this.element:this.queryElements(e).find(this.containsElement)}findAllElements(e){return[...this.element.matches(e)?[this.element]:[],...this.queryElements(e).filter(this.containsElement)]}queryElements(e){return Array.from(this.element.querySelectorAll(e))}get controllerSelector(){return V(this.schema.controllerAttribute,this.identifier)}}class I{constructor(e,t,r){this.element=e,this.schema=t,this.delegate=r,this.valueListObserver=new E(this.element,this.controllerAttribute,this),this.scopesByIdentifierByElement=new WeakMap,this.scopeReferenceCounts=new WeakMap}start(){this.valueListObserver.start()}stop(){this.valueListObserver.stop()}get controllerAttribute(){return this.schema.controllerAttribute}parseValueForToken(e){const{element:t,content:r}=e,s=this.fetchScopesByIdentifierForElement(t);let n=s.get(r);return n||(n=this.delegate.createScopeForElementAndIdentifier(t,r),s.set(r,n)),n}elementMatchedValue(e,t){const r=(this.scopeReferenceCounts.get(t)||0)+1;this.scopeReferenceCounts.set(t,r),1==r&&this.delegate.scopeConnected(t)}elementUnmatchedValue(e,t){const r=this.scopeReferenceCounts.get(t);r&&(this.scopeReferenceCounts.set(t,r-1),1==r&&this.delegate.scopeDisconnected(t))}fetchScopesByIdentifierForElement(e){let t=this.scopesByIdentifierByElement.get(e);return t||(t=new Map,this.scopesByIdentifierByElement.set(e,t)),t}}class R{constructor(e){this.application=e,this.scopeObserver=new I(this.element,this.schema,this),this.scopesByIdentifier=new v,this.modulesByIdentifier=new Map}get element(){return this.application.element}get schema(){return this.application.schema}get logger(){return this.application.logger}get controllerAttribute(){return this.schema.controllerAttribute}get modules(){return Array.from(this.modulesByIdentifier.values())}get contexts(){return this.modules.reduce(((e,t)=>e.concat(t.contexts)),[])}start(){this.scopeObserver.start()}stop(){this.scopeObserver.stop()}loadDefinition(e){this.unloadIdentifier(e.identifier);const t=new L(this.application,e);this.connectModule(t)}unloadIdentifier(e){const t=this.modulesByIdentifier.get(e);t&&this.disconnectModule(t)}getContextForElementAndIdentifier(e,t){const r=this.modulesByIdentifier.get(t);if(r)return r.contexts.find((t=>t.element==e))}handleError(e,t,r){this.application.handleError(e,t,r)}createScopeForElementAndIdentifier(e,t){return new j(this.schema,e,t,this.logger)}scopeConnected(e){this.scopesByIdentifier.add(e.identifier,e);const t=this.modulesByIdentifier.get(e.identifier);t&&t.connectContextForScope(e)}scopeDisconnected(e){this.scopesByIdentifier.delete(e.identifier,e);const t=this.modulesByIdentifier.get(e.identifier);t&&t.disconnectContextForScope(e)}connectModule(e){this.modulesByIdentifier.set(e.identifier,e);this.scopesByIdentifier.getValuesForKey(e.identifier).forEach((t=>e.connectContextForScope(t)))}disconnectModule(e){this.modulesByIdentifier.delete(e.identifier);this.scopesByIdentifier.getValuesForKey(e.identifier).forEach((t=>e.disconnectContextForScope(t)))}}const P={controllerAttribute:"data-controller",actionAttribute:"data-action",targetAttribute:"data-target",targetAttributeForScope:e=>`data-${e}-target`};class U{constructor(e=document.documentElement,r=P){this.logger=console,this.debug=!1,this.logDebugActivity=(e,t,r={})=>{this.debug&&this.logFormattedMessage(e,t,r)},this.element=e,this.schema=r,this.dispatcher=new t(this),this.router=new R(this)}static start(e,t){const r=new U(e,t);return r.start(),r}async start(){await new Promise((e=>{"loading"==document.readyState?document.addEventListener("DOMContentLoaded",(()=>e())):e()})),this.logDebugActivity("application","starting"),this.dispatcher.start(),this.router.start(),this.logDebugActivity("application","start")}stop(){this.logDebugActivity("application","stopping"),this.dispatcher.stop(),this.router.stop(),this.logDebugActivity("application","stop")}register(e,t){t.shouldLoad&&this.load({identifier:e,controllerConstructor:t})}load(e,...t){(Array.isArray(e)?e:[e,...t]).forEach((e=>this.router.loadDefinition(e)))}unload(e,...t){(Array.isArray(e)?e:[e,...t]).forEach((e=>this.router.unloadIdentifier(e)))}get controllers(){return this.router.contexts.map((e=>e.controller))}getControllerForElementAndIdentifier(e,t){const r=this.router.getContextForElementAndIdentifier(e,t);return r?r.controller:null}handleError(e,t,r){var s;this.logger.error("%s\n\n%o\n\n%o",t,e,r),null===(s=window.onerror)||void 0===s||s.call(window,t,"",0,0,e)}logFormattedMessage(e,t,r={}){r=Object.assign({application:this},r),this.logger.groupCollapsed(`${e} #${t}`),this.logger.log("details:",Object.assign({},r)),this.logger.groupEnd()}}function z([e,t]){return function(e,t){const r=`${o(e)}-value`,s=function(e){const t=function(e){const t=W(e.type);if(t){const r=q(e.default);if(t!==r)throw new Error(`Type "${t}" must match the type of the default value. Given default value: "${e.default}" as "${r}"`);return t}}(e),r=q(e),s=W(e),n=t||r||s;if(n)return n;throw new Error(`Unknown value type "${e}"`)}(t);return{type:s,key:r,name:n(r),get defaultValue(){return function(e){const t=W(e);if(t)return J[t];const r=e.default;return void 0!==r?r:e}(t)},get hasCustomDefaultValue(){return void 0!==q(t)},reader:_[s],writer:G[s]||G.default}}(e,t)}function W(e){switch(e){case Array:return"array";case Boolean:return"boolean";case Number:return"number";case Object:return"object";case String:return"string"}}function q(e){switch(typeof e){case"boolean":return"boolean";case"number":return"number";case"string":return"string"}return Array.isArray(e)?"array":"[object Object]"===Object.prototype.toString.call(e)?"object":void 0}const J={get array(){return[]},boolean:!1,number:0,get object(){return{}},string:""},_={array(e){const t=JSON.parse(e);if(!Array.isArray(t))throw new TypeError("Expected array");return t},boolean:e=>!("0"==e||"false"==e),number:e=>Number(e),object(e){const t=JSON.parse(e);if(null===t||"object"!=typeof t||Array.isArray(t))throw new TypeError("Expected object");return t},string:e=>e},G={default:function(e){return`${e}`},array:Z,object:Z};function Z(e){return JSON.stringify(e)}class H{constructor(e){this.context=e}static get shouldLoad(){return!0}get application(){return this.context.application}get scope(){return this.context.scope}get element(){return this.scope.element}get identifier(){return this.scope.identifier}get targets(){return this.scope.targets}get classes(){return this.scope.classes}get data(){return this.scope.data}initialize(){}connect(){}disconnect(){}dispatch(e,{target:t=this.element,detail:r={},prefix:s=this.identifier,bubbles:n=!0,cancelable:i=!0}={}){const o=new CustomEvent(s?`${s}:${e}`:e,{detail:r,bubbles:n,cancelable:i});return t.dispatchEvent(o),o}}H.blessings=[function(e){return N(e,"classes").reduce(((e,t)=>{return Object.assign(e,{[`${r=t}Class`]:{get(){const{classes:e}=this;if(e.has(r))return e.get(r);{const t=e.getAttributeName(r);throw new Error(`Missing attribute "${t}"`)}}},[`${r}Classes`]:{get(){return this.classes.getAll(r)}},[`has${i(r)}Class`]:{get(){return this.classes.has(r)}}});var r}),{})},function(e){return N(e,"targets").reduce(((e,t)=>{return Object.assign(e,{[`${r=t}Target`]:{get(){const e=this.targets.find(r);if(e)return e;throw new Error(`Missing target element "${r}" for "${this.identifier}" controller`)}},[`${r}Targets`]:{get(){return this.targets.findAll(r)}},[`has${i(r)}Target`]:{get(){return this.targets.has(r)}}});var r}),{})},function(e){const t=B(e,"values"),r={valueDescriptorMap:{get(){return t.reduce(((e,t)=>{const r=z(t),s=this.data.getAttributeNameForKey(r.key);return Object.assign(e,{[s]:r})}),{})}}};return t.reduce(((e,t)=>Object.assign(e,function(e){const t=z(e),{key:r,name:s,reader:n,writer:o}=t;return{[s]:{get(){const e=this.data.get(r);return null!==e?n(e):t.defaultValue},set(e){void 0===e?this.data.delete(r):this.data.set(r,o(e))}},[`has${i(s)}`]:{get(){return this.data.has(r)||t.hasCustomDefaultValue}}}}(t))),r)}],H.targets=[],H.values={};export{U as Application,d as AttributeObserver,M as Context,H as Controller,u as ElementObserver,y as IndexedMultimap,v as Multimap,g as StringMapObserver,A as TokenListObserver,E as ValueListObserver,m as add,P as defaultSchema,p as del,f as fetch,b as prune};
5
+ //# sourceMappingURL=stimulus.min.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stimulus.min.js","sources":["../src/core/event_listener.ts","../src/core/dispatcher.ts","../src/core/action_descriptor.ts","../src/core/string_helpers.ts","../src/core/action.ts","../src/core/binding.ts","../src/mutation-observers/element_observer.ts","../src/mutation-observers/attribute_observer.ts","../src/mutation-observers/string_map_observer.ts","../src/multimap/set_operations.ts","../src/multimap/multimap.ts","../src/multimap/indexed_multimap.ts","../src/mutation-observers/token_list_observer.ts","../src/mutation-observers/value_list_observer.ts","../src/core/binding_observer.ts","../src/core/value_observer.ts","../src/core/target_observer.ts","../src/core/context.ts","../src/core/inheritable_statics.ts","../src/core/blessing.ts","../src/core/module.ts","../src/core/definition.ts","../src/core/class_map.ts","../src/core/data_map.ts","../src/core/guide.ts","../src/core/selectors.ts","../src/core/target_set.ts","../src/core/scope.ts","../src/core/scope_observer.ts","../src/core/router.ts","../src/core/schema.ts","../src/core/application.ts","../src/core/value_properties.ts","../src/core/controller.ts","../src/core/class_properties.ts","../src/core/target_properties.ts"],"sourcesContent":["import { Binding } from \"./binding\"\n\nexport class EventListener implements EventListenerObject {\n readonly eventTarget: EventTarget\n readonly eventName: string\n readonly eventOptions: AddEventListenerOptions\n private unorderedBindings: Set<Binding>\n\n constructor(eventTarget: EventTarget, eventName: string, eventOptions: AddEventListenerOptions) {\n this.eventTarget = eventTarget\n this.eventName = eventName\n this.eventOptions = eventOptions\n this.unorderedBindings = new Set()\n }\n\n connect() {\n this.eventTarget.addEventListener(this.eventName, this, this.eventOptions)\n }\n\n disconnect() {\n this.eventTarget.removeEventListener(this.eventName, this, this.eventOptions)\n }\n\n // Binding observer delegate\n\n bindingConnected(binding: Binding) {\n this.unorderedBindings.add(binding)\n }\n\n bindingDisconnected(binding: Binding) {\n this.unorderedBindings.delete(binding)\n }\n\n handleEvent(event: Event) {\n // FIXME: Determine why TS won't recognize that the extended event has immediatePropagationStopped\n const extendedEvent = extendEvent(event) as any\n for (const binding of this.bindings) {\n if (extendedEvent.immediatePropagationStopped) {\n break\n } else {\n binding.handleEvent(extendedEvent)\n }\n }\n }\n\n get bindings(): Binding[] {\n return Array.from(this.unorderedBindings).sort((left, right) => {\n const leftIndex = left.index, rightIndex = right.index\n return leftIndex < rightIndex ? -1 : leftIndex > rightIndex ? 1 : 0\n })\n }\n\n}\n\nfunction extendEvent(event: Event) {\n if (\"immediatePropagationStopped\" in event) {\n return event\n } else {\n const { stopImmediatePropagation } = event\n return Object.assign(event, {\n immediatePropagationStopped: false,\n stopImmediatePropagation() {\n this.immediatePropagationStopped = true\n stopImmediatePropagation.call(this)\n }\n })\n }\n}\n","import { Application } from \"./application\"\nimport { Binding } from \"./binding\"\nimport { BindingObserverDelegate } from \"./binding_observer\"\nimport { EventListener } from \"./event_listener\"\n\nexport class Dispatcher implements BindingObserverDelegate {\n readonly application: Application\n private eventListenerMaps: Map<EventTarget, Map<string, EventListener>>\n private started: boolean\n\n constructor(application: Application) {\n this.application = application\n this.eventListenerMaps = new Map\n this.started = false\n }\n\n start() {\n if (!this.started) {\n this.started = true\n this.eventListeners.forEach(eventListener => eventListener.connect())\n }\n }\n\n stop() {\n if (this.started) {\n this.started = false\n this.eventListeners.forEach(eventListener => eventListener.disconnect())\n }\n }\n\n get eventListeners(): EventListener[] {\n return Array.from(this.eventListenerMaps.values())\n .reduce((listeners, map) => listeners.concat(Array.from(map.values())), [] as EventListener[])\n }\n\n // Binding observer delegate\n\n bindingConnected(binding: Binding) {\n this.fetchEventListenerForBinding(binding).bindingConnected(binding)\n }\n\n bindingDisconnected(binding: Binding) {\n this.fetchEventListenerForBinding(binding).bindingDisconnected(binding)\n }\n\n // Error handling\n\n handleError(error: Error, message: string, detail: object = {}) {\n this.application.handleError(error, `Error ${message}`, detail)\n }\n\n private fetchEventListenerForBinding(binding: Binding): EventListener {\n const { eventTarget, eventName, eventOptions } = binding\n return this.fetchEventListener(eventTarget, eventName, eventOptions)\n }\n\n private fetchEventListener(eventTarget: EventTarget, eventName: string, eventOptions: AddEventListenerOptions): EventListener {\n const eventListenerMap = this.fetchEventListenerMapForEventTarget(eventTarget)\n const cacheKey = this.cacheKey(eventName, eventOptions)\n let eventListener = eventListenerMap.get(cacheKey)\n if (!eventListener) {\n eventListener = this.createEventListener(eventTarget, eventName, eventOptions)\n eventListenerMap.set(cacheKey, eventListener)\n }\n return eventListener\n }\n\n private createEventListener(eventTarget: EventTarget, eventName: string, eventOptions: AddEventListenerOptions): EventListener {\n const eventListener = new EventListener(eventTarget, eventName, eventOptions)\n if (this.started) {\n eventListener.connect()\n }\n return eventListener\n }\n\n private fetchEventListenerMapForEventTarget(eventTarget: EventTarget): Map<string, EventListener> {\n let eventListenerMap = this.eventListenerMaps.get(eventTarget)\n if (!eventListenerMap) {\n eventListenerMap = new Map\n this.eventListenerMaps.set(eventTarget, eventListenerMap)\n }\n return eventListenerMap\n }\n\n private cacheKey(eventName: string, eventOptions: any): string {\n const parts = [ eventName ]\n Object.keys(eventOptions).sort().forEach(key => {\n parts.push(`${eventOptions[key] ? \"\" : \"!\"}${key}`)\n })\n return parts.join(\":\")\n }\n}\n","export interface ActionDescriptor {\n eventTarget: EventTarget\n eventOptions: AddEventListenerOptions\n eventName: string\n identifier: string\n methodName: string\n}\n\n// capture nos.: 12 23 4 43 1 5 56 7 768 9 98\nconst descriptorPattern = /^((.+?)(@(window|document))?->)?(.+?)(#([^:]+?))(:(.+))?$/\n\nexport function parseActionDescriptorString(descriptorString: string): Partial<ActionDescriptor> {\n const source = descriptorString.trim()\n const matches = source.match(descriptorPattern) || []\n return {\n eventTarget: parseEventTarget(matches[4]),\n eventName: matches[2],\n eventOptions: matches[9] ? parseEventOptions(matches[9]) : {},\n identifier: matches[5],\n methodName: matches[7]\n }\n}\n\nfunction parseEventTarget(eventTargetName: string): EventTarget | undefined {\n if (eventTargetName == \"window\") {\n return window\n } else if (eventTargetName == \"document\") {\n return document\n }\n}\n\nfunction parseEventOptions(eventOptions: string): AddEventListenerOptions {\n return eventOptions.split(\":\").reduce((options, token) =>\n Object.assign(options, { [token.replace(/^!/, \"\")]: !/^!/.test(token) })\n , {})\n}\n\nexport function stringifyEventTarget(eventTarget: EventTarget) {\n if (eventTarget == window) {\n return \"window\"\n } else if (eventTarget == document) {\n return \"document\"\n }\n}\n","export function camelize(value: string) {\n return value.replace(/(?:[_-])([a-z0-9])/g, (_, char) => char.toUpperCase())\n}\n\nexport function capitalize(value: string) {\n return value.charAt(0).toUpperCase() + value.slice(1)\n}\n\nexport function dasherize(value: string) {\n return value.replace(/([A-Z])/g, (_, char) => `-${char.toLowerCase()}`)\n}\n\nexport function tokenize(value: string) {\n return value.match(/[^\\s]+/g) || []\n}\n","import { ActionDescriptor, parseActionDescriptorString, stringifyEventTarget } from \"./action_descriptor\"\nimport { Token } from \"../mutation-observers\"\nimport { camelize } from \"./string_helpers\"\n\nexport class Action {\n readonly element: Element\n readonly index: number\n readonly eventTarget: EventTarget\n readonly eventName: string\n readonly eventOptions: AddEventListenerOptions\n readonly identifier: string\n readonly methodName: string\n\n static forToken(token: Token) {\n return new this(token.element, token.index, parseActionDescriptorString(token.content))\n }\n\n constructor(element: Element, index: number, descriptor: Partial<ActionDescriptor>) {\n this.element = element\n this.index = index\n this.eventTarget = descriptor.eventTarget || element\n this.eventName = descriptor.eventName || getDefaultEventNameForElement(element) || error(\"missing event name\")\n this.eventOptions = descriptor.eventOptions || {}\n this.identifier = descriptor.identifier || error(\"missing identifier\")\n this.methodName = descriptor.methodName || error(\"missing method name\")\n }\n\n toString() {\n const eventNameSuffix = this.eventTargetName ? `@${this.eventTargetName}` : \"\"\n return `${this.eventName}${eventNameSuffix}->${this.identifier}#${this.methodName}`\n }\n\n get params(): object {\n if (this.eventTarget instanceof Element) {\n return this.getParamsFromEventTargetAttributes(this.eventTarget)\n } else {\n return {}\n }\n }\n\n private getParamsFromEventTargetAttributes(eventTarget: Element): {[key: string]: any} {\n const params = {}\n const pattern = new RegExp(`^data-${this.identifier}-(.+)-param$`)\n const attributes = Array.from(eventTarget.attributes)\n\n attributes.forEach(({ name, value }: { name: string, value: string }) => {\n const match = name.match(pattern)\n const key = match && match[1]\n if (key) {\n Object.assign(params, { [camelize(key)]: typecast(value) })\n }\n })\n return params\n }\n\n private get eventTargetName() {\n return stringifyEventTarget(this.eventTarget)\n }\n}\n\nconst defaultEventNames: { [tagName: string]: (element: Element) => string } = {\n \"a\": e => \"click\",\n \"button\": e => \"click\",\n \"form\": e => \"submit\",\n \"details\": e => \"toggle\",\n \"input\": e => e.getAttribute(\"type\") == \"submit\" ? \"click\" : \"input\",\n \"select\": e => \"change\",\n \"textarea\": e => \"input\"\n}\n\nexport function getDefaultEventNameForElement(element: Element): string | undefined {\n const tagName = element.tagName.toLowerCase()\n if (tagName in defaultEventNames) {\n return defaultEventNames[tagName](element)\n }\n}\n\nfunction error(message: string): never {\n throw new Error(message)\n}\n\nfunction typecast(value: any): any {\n try {\n return JSON.parse(value)\n } catch (o_O) {\n return value\n }\n}\n\n","import { Action } from \"./action\"\nimport { ActionEvent } from \"./action_event\"\nimport { Context } from \"./context\"\nimport { Controller } from \"./controller\"\nimport { Scope } from \"./scope\"\n\nexport class Binding {\n readonly context: Context\n readonly action: Action\n\n constructor(context: Context, action: Action) {\n this.context = context\n this.action = action\n }\n\n get index(): number {\n return this.action.index\n }\n\n get eventTarget(): EventTarget {\n return this.action.eventTarget\n }\n\n get eventOptions(): AddEventListenerOptions {\n return this.action.eventOptions\n }\n\n get identifier(): string {\n return this.context.identifier\n }\n\n handleEvent(event: Event) {\n if (this.willBeInvokedByEvent(event)) {\n this.invokeWithEvent(event)\n }\n }\n\n get eventName(): string {\n return this.action.eventName\n }\n\n get method(): Function {\n const method = (this.controller as any)[this.methodName]\n if (typeof method == \"function\") {\n return method\n }\n throw new Error(`Action \"${this.action}\" references undefined method \"${this.methodName}\"`)\n }\n\n private invokeWithEvent(event: Event) {\n const { target, currentTarget } = event\n try {\n const { params } = this.action\n const actionEvent: ActionEvent = Object.assign(event, { params })\n this.method.call(this.controller, actionEvent)\n this.context.logDebugActivity(this.methodName, { event, target, currentTarget, action: this.methodName })\n } catch (error) {\n const { identifier, controller, element, index } = this\n const detail = { identifier, controller, element, index, event }\n this.context.handleError(error, `invoking action \"${this.action}\"`, detail)\n }\n }\n\n private willBeInvokedByEvent(event: Event): boolean {\n const eventTarget = event.target\n if (this.element === eventTarget) {\n return true\n } else if (eventTarget instanceof Element && this.element.contains(eventTarget)) {\n return this.scope.containsElement(eventTarget)\n } else {\n return this.scope.containsElement(this.action.element)\n }\n }\n\n private get controller(): Controller {\n return this.context.controller\n }\n\n private get methodName(): string {\n return this.action.methodName\n }\n\n private get element(): Element {\n return this.scope.element\n }\n\n private get scope(): Scope {\n return this.context.scope\n }\n}\n","export interface ElementObserverDelegate {\n matchElement(element: Element): boolean\n matchElementsInTree(tree: Element): Element[]\n\n elementMatched?(element: Element): void\n elementUnmatched?(element: Element): void\n elementAttributeChanged?(element: Element, attributeName: string): void\n}\n\nexport class ElementObserver {\n element: Element\n started: boolean\n private delegate: ElementObserverDelegate\n\n private elements: Set<Element>\n private mutationObserver: MutationObserver\n private mutationObserverInit = { attributes: true, childList: true, subtree: true }\n\n constructor(element: Element, delegate: ElementObserverDelegate) {\n this.element = element\n this.started = false\n this.delegate = delegate\n\n this.elements = new Set\n this.mutationObserver = new MutationObserver((mutations) => this.processMutations(mutations))\n }\n\n start() {\n if (!this.started) {\n this.started = true\n this.mutationObserver.observe(this.element, this.mutationObserverInit)\n this.refresh()\n }\n }\n\n pause(callback: () => void) {\n if (this.started) {\n this.mutationObserver.disconnect()\n this.started = false\n }\n\n callback()\n\n if (!this.started) {\n this.mutationObserver.observe(this.element, this.mutationObserverInit)\n this.started = true\n }\n }\n\n stop() {\n if (this.started) {\n this.mutationObserver.takeRecords()\n this.mutationObserver.disconnect()\n this.started = false\n }\n }\n\n refresh() {\n if (this.started) {\n const matches = new Set(this.matchElementsInTree())\n\n for (const element of Array.from(this.elements)) {\n if (!matches.has(element)) {\n this.removeElement(element)\n }\n }\n\n for (const element of Array.from(matches)) {\n this.addElement(element)\n }\n }\n }\n\n // Mutation record processing\n\n private processMutations(mutations: MutationRecord[]) {\n if (this.started) {\n for (const mutation of mutations) {\n this.processMutation(mutation)\n }\n }\n }\n\n private processMutation(mutation: MutationRecord) {\n if (mutation.type == \"attributes\") {\n this.processAttributeChange(mutation.target, mutation.attributeName!)\n } else if (mutation.type == \"childList\") {\n this.processRemovedNodes(mutation.removedNodes)\n this.processAddedNodes(mutation.addedNodes)\n }\n }\n\n private processAttributeChange(node: Node, attributeName: string) {\n const element = node as Element\n if (this.elements.has(element)) {\n if (this.delegate.elementAttributeChanged && this.matchElement(element)) {\n this.delegate.elementAttributeChanged(element, attributeName)\n } else {\n this.removeElement(element)\n }\n } else if (this.matchElement(element)) {\n this.addElement(element)\n }\n }\n\n private processRemovedNodes(nodes: NodeList) {\n for (const node of Array.from(nodes)) {\n const element = this.elementFromNode(node)\n if (element) {\n this.processTree(element, this.removeElement)\n }\n }\n }\n\n private processAddedNodes(nodes: NodeList) {\n for (const node of Array.from(nodes)) {\n const element = this.elementFromNode(node)\n if (element && this.elementIsActive(element)) {\n this.processTree(element, this.addElement)\n }\n }\n }\n\n // Element matching\n\n private matchElement(element: Element): boolean {\n return this.delegate.matchElement(element)\n }\n\n private matchElementsInTree(tree: Element = this.element): Element[] {\n return this.delegate.matchElementsInTree(tree)\n }\n\n private processTree(tree: Element, processor: (element: Element) => void) {\n for (const element of this.matchElementsInTree(tree)) {\n processor.call(this, element)\n }\n }\n\n private elementFromNode(node: Node): Element | undefined {\n if (node.nodeType == Node.ELEMENT_NODE) {\n return node as Element\n }\n }\n\n private elementIsActive(element: Element): boolean {\n if (element.isConnected != this.element.isConnected) {\n return false\n } else {\n return this.element.contains(element)\n }\n }\n\n // Element tracking\n\n private addElement(element: Element) {\n if (!this.elements.has(element)) {\n if (this.elementIsActive(element)) {\n this.elements.add(element)\n if (this.delegate.elementMatched) {\n this.delegate.elementMatched(element)\n }\n }\n }\n }\n\n private removeElement(element: Element) {\n if (this.elements.has(element)) {\n this.elements.delete(element)\n if (this.delegate.elementUnmatched) {\n this.delegate.elementUnmatched(element)\n }\n }\n }\n}\n","import { ElementObserver, ElementObserverDelegate } from \"./element_observer\"\n\nexport interface AttributeObserverDelegate {\n elementMatchedAttribute?(element: Element, attributeName: string): void\n elementAttributeValueChanged?(element: Element, attributeName: string): void\n elementUnmatchedAttribute?(element: Element, attributeName: string): void\n}\n\nexport class AttributeObserver implements ElementObserverDelegate {\n attributeName: string\n private delegate: AttributeObserverDelegate\n\n private elementObserver: ElementObserver\n\n constructor(element: Element, attributeName: string, delegate: AttributeObserverDelegate) {\n this.attributeName = attributeName\n this.delegate = delegate\n\n this.elementObserver = new ElementObserver(element, this)\n }\n\n get element(): Element {\n return this.elementObserver.element\n }\n\n get selector(): string {\n return `[${this.attributeName}]`\n }\n\n start() {\n this.elementObserver.start()\n }\n\n pause(callback: () => void) {\n this.elementObserver.pause(callback)\n }\n\n stop() {\n this.elementObserver.stop()\n }\n\n refresh() {\n this.elementObserver.refresh()\n }\n\n get started(): boolean {\n return this.elementObserver.started\n }\n\n // Element observer delegate\n\n matchElement(element: Element): boolean {\n return element.hasAttribute(this.attributeName)\n }\n\n matchElementsInTree(tree: Element): Element[] {\n const match = this.matchElement(tree) ? [tree] : []\n const matches = Array.from(tree.querySelectorAll(this.selector))\n return match.concat(matches)\n }\n\n elementMatched(element: Element) {\n if (this.delegate.elementMatchedAttribute) {\n this.delegate.elementMatchedAttribute(element, this.attributeName)\n }\n }\n\n elementUnmatched(element: Element) {\n if (this.delegate.elementUnmatchedAttribute) {\n this.delegate.elementUnmatchedAttribute(element, this.attributeName)\n }\n }\n\n elementAttributeChanged(element: Element, attributeName: string) {\n if (this.delegate.elementAttributeValueChanged && this.attributeName == attributeName) {\n this.delegate.elementAttributeValueChanged(element, attributeName)\n }\n }\n}\n","export interface StringMapObserverDelegate {\n getStringMapKeyForAttribute(attributeName: string): string | undefined\n stringMapKeyAdded?(key: string, attributeName: string): void\n stringMapValueChanged?(value: string | null, key: string, oldValue: string | null): void\n stringMapKeyRemoved?(key: string, attributeName: string, oldValue: string | null): void\n}\n\nexport class StringMapObserver {\n readonly element: Element\n readonly delegate: StringMapObserverDelegate\n private started: boolean\n private stringMap: Map<string, string>\n private mutationObserver: MutationObserver\n\n constructor(element: Element, delegate: StringMapObserverDelegate) {\n this.element = element\n this.delegate = delegate\n this.started = false\n this.stringMap = new Map\n this.mutationObserver = new MutationObserver(mutations => this.processMutations(mutations))\n }\n\n start() {\n if (!this.started) {\n this.started = true\n this.mutationObserver.observe(this.element, { attributes: true, attributeOldValue: true })\n this.refresh()\n }\n }\n\n stop() {\n if (this.started) {\n this.mutationObserver.takeRecords()\n this.mutationObserver.disconnect()\n this.started = false\n }\n }\n\n refresh() {\n if (this.started) {\n for (const attributeName of this.knownAttributeNames) {\n this.refreshAttribute(attributeName, null)\n }\n }\n }\n\n // Mutation record processing\n\n private processMutations(mutations: MutationRecord[]) {\n if (this.started) {\n for (const mutation of mutations) {\n this.processMutation(mutation)\n }\n }\n }\n\n private processMutation(mutation: MutationRecord) {\n const attributeName = mutation.attributeName\n if (attributeName) {\n this.refreshAttribute(attributeName, mutation.oldValue)\n }\n }\n\n // State tracking\n\n private refreshAttribute(attributeName: string, oldValue: string | null) {\n const key = this.delegate.getStringMapKeyForAttribute(attributeName)\n if (key != null) {\n if (!this.stringMap.has(attributeName)) {\n this.stringMapKeyAdded(key, attributeName)\n }\n\n const value = this.element.getAttribute(attributeName)\n if (this.stringMap.get(attributeName) != value) {\n this.stringMapValueChanged(value, key, oldValue)\n }\n\n if (value == null) {\n const oldValue = this.stringMap.get(attributeName)\n this.stringMap.delete(attributeName)\n if (oldValue) this.stringMapKeyRemoved(key, attributeName, oldValue)\n } else {\n this.stringMap.set(attributeName, value)\n }\n }\n }\n\n private stringMapKeyAdded(key: string, attributeName: string) {\n if (this.delegate.stringMapKeyAdded) {\n this.delegate.stringMapKeyAdded(key, attributeName)\n }\n }\n\n private stringMapValueChanged(value: string | null, key: string, oldValue: string | null) {\n if (this.delegate.stringMapValueChanged) {\n this.delegate.stringMapValueChanged(value, key, oldValue)\n }\n }\n\n private stringMapKeyRemoved(key: string, attributeName: string, oldValue: string | null) {\n if (this.delegate.stringMapKeyRemoved) {\n this.delegate.stringMapKeyRemoved(key, attributeName, oldValue)\n }\n }\n\n private get knownAttributeNames() {\n return Array.from(new Set(this.currentAttributeNames.concat(this.recordedAttributeNames)))\n }\n\n private get currentAttributeNames() {\n return Array.from(this.element.attributes).map(attribute => attribute.name)\n }\n\n private get recordedAttributeNames() {\n return Array.from(this.stringMap.keys())\n }\n}\n","export function add<K, V>(map: Map<K, Set<V>>, key: K, value: V) {\n fetch(map, key).add(value)\n}\n\nexport function del<K, V>(map: Map<K, Set<V>>, key: K, value: V) {\n fetch(map, key).delete(value)\n prune(map, key)\n}\n\nexport function fetch<K, V>(map: Map<K, Set<V>>, key: K): Set<V> {\n let values = map.get(key)\n if (!values) {\n values = new Set()\n map.set(key, values)\n }\n return values\n}\n\nexport function prune<K, V>(map: Map<K, Set<V>>, key: K) {\n const values = map.get(key)\n if (values != null && values.size == 0) {\n map.delete(key)\n }\n}\n","import { add, del } from \"./set_operations\"\n\nexport class Multimap<K, V> {\n private valuesByKey: Map<K, Set<V>>\n\n constructor() {\n this.valuesByKey = new Map<K, Set<V>>()\n }\n\n get keys() {\n return Array.from(this.valuesByKey.keys())\n }\n\n get values(): V[] {\n const sets = Array.from(this.valuesByKey.values())\n return sets.reduce((values, set) => values.concat(Array.from(set)), <V[]> [])\n }\n\n get size(): number {\n const sets = Array.from(this.valuesByKey.values())\n return sets.reduce((size, set) => size + set.size, 0)\n }\n\n add(key: K, value: V) {\n add(this.valuesByKey, key, value)\n }\n\n delete(key: K, value: V) {\n del(this.valuesByKey, key, value)\n }\n\n has(key: K, value: V): boolean {\n const values = this.valuesByKey.get(key)\n return values != null && values.has(value)\n }\n\n hasKey(key: K): boolean {\n return this.valuesByKey.has(key)\n }\n\n hasValue(value: V): boolean {\n const sets = Array.from(this.valuesByKey.values())\n return sets.some(set => set.has(value))\n }\n\n getValuesForKey(key: K): V[] {\n const values = this.valuesByKey.get(key)\n return values ? Array.from(values) : []\n }\n\n getKeysForValue(value: V): K[] {\n return Array.from(this.valuesByKey)\n .filter(([key, values]) => values.has(value))\n .map(([key, values]) => key)\n }\n}\n","import { Multimap } from \"./multimap\"\nimport { add, del } from \"./set_operations\"\n\nexport class IndexedMultimap<K, V> extends Multimap<K, V> {\n private keysByValue: Map<V, Set<K>>\n\n constructor() {\n super()\n this.keysByValue = new Map\n }\n\n get values(): V[] {\n return Array.from(this.keysByValue.keys())\n }\n\n add(key: K, value: V) {\n super.add(key, value)\n add(this.keysByValue, value, key)\n }\n\n delete(key: K, value: V) {\n super.delete(key, value)\n del(this.keysByValue, value, key)\n }\n\n hasValue(value: V): boolean {\n return this.keysByValue.has(value)\n }\n\n getKeysForValue(value: V): K[] {\n const set = this.keysByValue.get(value)\n return set ? Array.from(set) : []\n }\n}\n","import { AttributeObserver, AttributeObserverDelegate } from \"./attribute_observer\"\nimport { Multimap } from \"../multimap\"\n\nexport interface Token {\n element: Element\n attributeName: string\n index: number\n content: string\n}\n\nexport interface TokenListObserverDelegate {\n tokenMatched(token: Token): void\n tokenUnmatched(token: Token): void\n}\n\nexport class TokenListObserver implements AttributeObserverDelegate {\n private attributeObserver: AttributeObserver\n private delegate: TokenListObserverDelegate\n private tokensByElement: Multimap<Element, Token>\n\n constructor(element: Element, attributeName: string, delegate: TokenListObserverDelegate) {\n this.attributeObserver = new AttributeObserver(element, attributeName, this)\n this.delegate = delegate\n this.tokensByElement = new Multimap\n }\n\n get started(): boolean {\n return this.attributeObserver.started\n }\n\n start() {\n this.attributeObserver.start()\n }\n\n pause(callback: () => void) {\n this.attributeObserver.pause(callback)\n }\n\n stop() {\n this.attributeObserver.stop()\n }\n\n refresh() {\n this.attributeObserver.refresh()\n }\n\n get element(): Element {\n return this.attributeObserver.element\n }\n\n get attributeName(): string {\n return this.attributeObserver.attributeName\n }\n\n // Attribute observer delegate\n\n elementMatchedAttribute(element: Element) {\n this.tokensMatched(this.readTokensForElement(element))\n }\n\n elementAttributeValueChanged(element: Element) {\n const [unmatchedTokens, matchedTokens] = this.refreshTokensForElement(element)\n this.tokensUnmatched(unmatchedTokens)\n this.tokensMatched(matchedTokens)\n }\n\n elementUnmatchedAttribute(element: Element) {\n this.tokensUnmatched(this.tokensByElement.getValuesForKey(element))\n }\n\n private tokensMatched(tokens: Token[]) {\n tokens.forEach(token => this.tokenMatched(token))\n }\n\n private tokensUnmatched(tokens: Token[]) {\n tokens.forEach(token => this.tokenUnmatched(token))\n }\n\n private tokenMatched(token: Token) {\n this.delegate.tokenMatched(token)\n this.tokensByElement.add(token.element, token)\n }\n\n private tokenUnmatched(token: Token) {\n this.delegate.tokenUnmatched(token)\n this.tokensByElement.delete(token.element, token)\n }\n\n private refreshTokensForElement(element: Element): [Token[], Token[]] {\n const previousTokens = this.tokensByElement.getValuesForKey(element)\n const currentTokens = this.readTokensForElement(element)\n const firstDifferingIndex = zip(previousTokens, currentTokens)\n .findIndex(([previousToken, currentToken]) => !tokensAreEqual(previousToken, currentToken))\n\n if (firstDifferingIndex == -1) {\n return [[], []]\n } else {\n return [previousTokens.slice(firstDifferingIndex), currentTokens.slice(firstDifferingIndex)]\n }\n }\n\n private readTokensForElement(element: Element): Token[] {\n const attributeName = this.attributeName\n const tokenString = element.getAttribute(attributeName) || \"\"\n return parseTokenString(tokenString, element, attributeName)\n }\n}\n\nfunction parseTokenString(tokenString: string, element: Element, attributeName: string): Token[] {\n return tokenString.trim().split(/\\s+/).filter(content => content.length)\n .map((content, index) => ({ element, attributeName, content, index }))\n}\n\nfunction zip<L, R>(left: L[], right: R[]): [L | undefined, R | undefined][] {\n const length = Math.max(left.length, right.length)\n return Array.from({ length }, (_, index) => [left[index], right[index]] as [L, R])\n}\n\nfunction tokensAreEqual(left?: Token, right?: Token) {\n return left && right && left.index == right.index && left.content == right.content\n}\n","import { Token, TokenListObserver, TokenListObserverDelegate } from \"./token_list_observer\"\n\nexport interface ValueListObserverDelegate<T> {\n parseValueForToken(token: Token): T | undefined\n elementMatchedValue(element: Element, value: T): void\n elementUnmatchedValue(element: Element, value: T): void\n}\n\ninterface ParseResult<T> {\n value?: T\n error?: Error\n}\n\nexport class ValueListObserver<T> implements TokenListObserverDelegate {\n private tokenListObserver: TokenListObserver\n private delegate: ValueListObserverDelegate<T>\n private parseResultsByToken: WeakMap<Token, ParseResult<T>>\n private valuesByTokenByElement: WeakMap<Element, Map<Token, T>>\n\n constructor(element: Element, attributeName: string, delegate: ValueListObserverDelegate<T>) {\n this.tokenListObserver = new TokenListObserver(element, attributeName, this)\n this.delegate = delegate\n this.parseResultsByToken = new WeakMap\n this.valuesByTokenByElement = new WeakMap\n }\n\n get started(): boolean {\n return this.tokenListObserver.started\n }\n\n start() {\n this.tokenListObserver.start()\n }\n\n stop() {\n this.tokenListObserver.stop()\n }\n\n refresh() {\n this.tokenListObserver.refresh()\n }\n\n get element(): Element {\n return this.tokenListObserver.element\n }\n\n get attributeName(): string {\n return this.tokenListObserver.attributeName\n }\n\n tokenMatched(token: Token) {\n const { element } = token\n const { value } = this.fetchParseResultForToken(token)\n if (value) {\n this.fetchValuesByTokenForElement(element).set(token, value)\n this.delegate.elementMatchedValue(element, value)\n }\n }\n\n tokenUnmatched(token: Token) {\n const { element } = token\n const { value } = this.fetchParseResultForToken(token)\n if (value) {\n this.fetchValuesByTokenForElement(element).delete(token)\n this.delegate.elementUnmatchedValue(element, value)\n }\n }\n\n private fetchParseResultForToken(token: Token) {\n let parseResult = this.parseResultsByToken.get(token)\n if (!parseResult) {\n parseResult = this.parseToken(token)\n this.parseResultsByToken.set(token, parseResult)\n }\n return parseResult\n }\n\n private fetchValuesByTokenForElement(element: Element) {\n let valuesByToken = this.valuesByTokenByElement.get(element)\n if (!valuesByToken) {\n valuesByToken = new Map\n this.valuesByTokenByElement.set(element, valuesByToken)\n }\n return valuesByToken\n }\n\n private parseToken(token: Token): ParseResult<T> {\n try {\n const value = this.delegate.parseValueForToken(token)\n return { value }\n } catch (error) {\n return { error }\n }\n }\n}\n","import { Action } from \"./action\"\nimport { Binding } from \"./binding\"\nimport { Context } from \"./context\"\nimport { ErrorHandler } from \"./error_handler\"\nimport { Schema } from \"./schema\"\nimport { Token, ValueListObserver, ValueListObserverDelegate } from \"../mutation-observers\"\n\nexport interface BindingObserverDelegate extends ErrorHandler {\n bindingConnected(binding: Binding): void\n bindingDisconnected(binding: Binding): void\n}\n\nexport class BindingObserver implements ValueListObserverDelegate<Action> {\n readonly context: Context\n private delegate: BindingObserverDelegate\n private valueListObserver?: ValueListObserver<Action>\n private bindingsByAction: Map<Action, Binding>\n\n constructor(context: Context, delegate: BindingObserverDelegate) {\n this.context = context\n this.delegate = delegate\n this.bindingsByAction = new Map\n }\n\n start() {\n if (!this.valueListObserver) {\n this.valueListObserver = new ValueListObserver(this.element, this.actionAttribute, this)\n this.valueListObserver.start()\n }\n }\n\n stop() {\n if (this.valueListObserver) {\n this.valueListObserver.stop()\n delete this.valueListObserver\n this.disconnectAllActions()\n }\n }\n\n get element() {\n return this.context.element\n }\n\n get identifier() {\n return this.context.identifier\n }\n\n get actionAttribute() {\n return this.schema.actionAttribute\n }\n\n get schema(): Schema {\n return this.context.schema\n }\n\n get bindings(): Binding[] {\n return Array.from(this.bindingsByAction.values())\n }\n\n private connectAction(action: Action) {\n const binding = new Binding(this.context, action)\n this.bindingsByAction.set(action, binding)\n this.delegate.bindingConnected(binding)\n }\n\n private disconnectAction(action: Action) {\n const binding = this.bindingsByAction.get(action)\n if (binding) {\n this.bindingsByAction.delete(action)\n this.delegate.bindingDisconnected(binding)\n }\n }\n\n private disconnectAllActions() {\n this.bindings.forEach(binding => this.delegate.bindingDisconnected(binding))\n this.bindingsByAction.clear()\n }\n\n // Value observer delegate\n\n parseValueForToken(token: Token): Action | undefined {\n const action = Action.forToken(token)\n if (action.identifier == this.identifier) {\n return action\n }\n }\n\n elementMatchedValue(element: Element, action: Action) {\n this.connectAction(action)\n }\n\n elementUnmatchedValue(element: Element, action: Action) {\n this.disconnectAction(action)\n }\n}\n","import { Context } from \"./context\"\nimport { StringMapObserver, StringMapObserverDelegate } from \"../mutation-observers\"\nimport { ValueDescriptor } from \"./value_properties\"\nimport { capitalize } from \"./string_helpers\"\n\nexport class ValueObserver implements StringMapObserverDelegate {\n readonly context: Context\n readonly receiver: any\n private stringMapObserver: StringMapObserver\n private valueDescriptorMap: { [attributeName: string]: ValueDescriptor }\n\n constructor(context: Context, receiver: any) {\n this.context = context\n this.receiver = receiver\n this.stringMapObserver = new StringMapObserver(this.element, this)\n this.valueDescriptorMap = (this.controller as any).valueDescriptorMap\n this.invokeChangedCallbacksForDefaultValues()\n }\n\n start() {\n this.stringMapObserver.start()\n }\n\n stop() {\n this.stringMapObserver.stop()\n }\n\n get element() {\n return this.context.element\n }\n\n get controller() {\n return this.context.controller\n }\n\n // String map observer delegate\n\n getStringMapKeyForAttribute(attributeName: string) {\n if (attributeName in this.valueDescriptorMap) {\n return this.valueDescriptorMap[attributeName].name\n }\n }\n\n stringMapKeyAdded(key: string, attributeName: string) {\n const descriptor = this.valueDescriptorMap[attributeName]\n\n if (!this.hasValue(key)) {\n this.invokeChangedCallback(key, descriptor.writer(this.receiver[key]), descriptor.writer(descriptor.defaultValue))\n }\n }\n\n stringMapValueChanged(value: string, name: string, oldValue: string) {\n const descriptor = this.valueDescriptorNameMap[name]\n\n if (value === null) return\n\n if (oldValue === null) {\n oldValue = descriptor.writer(descriptor.defaultValue)\n }\n\n this.invokeChangedCallback(name, value, oldValue)\n }\n\n stringMapKeyRemoved(key: string, attributeName: string, oldValue: string) {\n const descriptor = this.valueDescriptorNameMap[key]\n\n if (this.hasValue(key)) {\n this.invokeChangedCallback(key, descriptor.writer(this.receiver[key]), oldValue)\n } else {\n this.invokeChangedCallback(key, descriptor.writer(descriptor.defaultValue), oldValue)\n }\n }\n\n private invokeChangedCallbacksForDefaultValues() {\n for (const { key, name, defaultValue, writer } of this.valueDescriptors) {\n if (defaultValue != undefined && !this.controller.data.has(key)) {\n this.invokeChangedCallback(name, writer(defaultValue), undefined)\n }\n }\n }\n\n private invokeChangedCallback(name: string, rawValue: string, rawOldValue: string | undefined) {\n const changedMethodName = `${name}Changed`\n const changedMethod = this.receiver[changedMethodName]\n\n if (typeof changedMethod == \"function\") {\n const descriptor = this.valueDescriptorNameMap[name]\n const value = descriptor.reader(rawValue)\n let oldValue = rawOldValue\n\n if (rawOldValue) {\n oldValue = descriptor.reader(rawOldValue)\n }\n\n changedMethod.call(this.receiver, value, oldValue)\n }\n }\n\n private get valueDescriptors() {\n const { valueDescriptorMap } = this\n return Object.keys(valueDescriptorMap).map(key => valueDescriptorMap[key])\n }\n\n private get valueDescriptorNameMap() {\n const descriptors: { [type: string]: ValueDescriptor } = {}\n\n Object.keys(this.valueDescriptorMap).forEach(key => {\n const descriptor = this.valueDescriptorMap[key]\n descriptors[descriptor.name] = descriptor\n })\n\n return descriptors\n }\n\n private hasValue(attributeName: string) {\n const descriptor = this.valueDescriptorNameMap[attributeName]\n const hasMethodName = `has${capitalize(descriptor.name)}`\n\n return this.receiver[hasMethodName]\n }\n}\n","import { Multimap } from \"../multimap\"\nimport { Token, TokenListObserver, TokenListObserverDelegate } from \"../mutation-observers\"\nimport { Context } from \"./context\"\n\nexport interface TargetObserverDelegate {\n targetConnected(element: Element, name: string): void\n targetDisconnected(element: Element, name: string): void\n}\n\nexport class TargetObserver implements TokenListObserverDelegate {\n readonly context: Context\n readonly delegate: TargetObserverDelegate\n readonly targetsByName: Multimap<string, Element>\n private tokenListObserver?: TokenListObserver\n\n constructor(context: Context, delegate: TargetObserverDelegate) {\n this.context = context\n this.delegate = delegate\n this.targetsByName = new Multimap\n }\n\n start() {\n if (!this.tokenListObserver) {\n this.tokenListObserver = new TokenListObserver(this.element, this.attributeName, this)\n this.tokenListObserver.start()\n }\n }\n\n stop() {\n if (this.tokenListObserver) {\n this.disconnectAllTargets()\n this.tokenListObserver.stop()\n delete this.tokenListObserver\n }\n }\n\n // Token list observer delegate\n\n tokenMatched({ element, content: name }: Token) {\n if (this.scope.containsElement(element)) {\n this.connectTarget(element, name)\n }\n }\n\n tokenUnmatched({ element, content: name }: Token) {\n this.disconnectTarget(element, name)\n }\n\n // Target management\n\n connectTarget(element: Element, name: string) {\n if (!this.targetsByName.has(name, element)) {\n this.targetsByName.add(name, element)\n this.tokenListObserver?.pause(() => this.delegate.targetConnected(element, name))\n }\n }\n\n disconnectTarget(element: Element, name: string) {\n if (this.targetsByName.has(name, element)) {\n this.targetsByName.delete(name, element)\n this.tokenListObserver?.pause(() => this.delegate.targetDisconnected(element, name))\n }\n }\n\n disconnectAllTargets() {\n for (const name of this.targetsByName.keys) {\n for (const element of this.targetsByName.getValuesForKey(name)) {\n this.disconnectTarget(element, name)\n }\n }\n }\n\n // Private\n\n private get attributeName() {\n return `data-${this.context.identifier}-target`\n }\n\n private get element() {\n return this.context.element\n }\n\n private get scope() {\n return this.context.scope\n }\n}\n","import { Application } from \"./application\"\nimport { BindingObserver } from \"./binding_observer\"\nimport { Controller } from \"./controller\"\nimport { Dispatcher } from \"./dispatcher\"\nimport { ErrorHandler } from \"./error_handler\"\nimport { Module } from \"./module\"\nimport { Schema } from \"./schema\"\nimport { Scope } from \"./scope\"\nimport { ValueObserver } from \"./value_observer\"\nimport { TargetObserver, TargetObserverDelegate } from \"./target_observer\"\n\nexport class Context implements ErrorHandler, TargetObserverDelegate {\n readonly module: Module\n readonly scope: Scope\n readonly controller: Controller\n private bindingObserver: BindingObserver\n private valueObserver: ValueObserver\n private targetObserver: TargetObserver\n\n constructor(module: Module, scope: Scope) {\n this.module = module\n this.scope = scope\n this.controller = new module.controllerConstructor(this)\n this.bindingObserver = new BindingObserver(this, this.dispatcher)\n this.valueObserver = new ValueObserver(this, this.controller)\n this.targetObserver = new TargetObserver(this, this)\n\n try {\n this.controller.initialize()\n this.logDebugActivity(\"initialize\")\n } catch (error) {\n this.handleError(error, \"initializing controller\")\n }\n }\n\n connect() {\n this.bindingObserver.start()\n this.valueObserver.start()\n this.targetObserver.start()\n\n try {\n this.controller.connect()\n this.logDebugActivity(\"connect\")\n } catch (error) {\n this.handleError(error, \"connecting controller\")\n }\n }\n\n disconnect() {\n try {\n this.controller.disconnect()\n this.logDebugActivity(\"disconnect\")\n } catch (error) {\n this.handleError(error, \"disconnecting controller\")\n }\n\n this.targetObserver.stop()\n this.valueObserver.stop()\n this.bindingObserver.stop()\n }\n\n get application(): Application {\n return this.module.application\n }\n\n get identifier(): string {\n return this.module.identifier\n }\n\n get schema(): Schema {\n return this.application.schema\n }\n\n get dispatcher(): Dispatcher {\n return this.application.dispatcher\n }\n\n get element(): Element {\n return this.scope.element\n }\n\n get parentElement(): Element | null {\n return this.element.parentElement\n }\n\n // Error handling\n\n handleError(error: Error, message: string, detail: object = {}) {\n const { identifier, controller, element } = this\n detail = Object.assign({ identifier, controller, element }, detail)\n this.application.handleError(error, `Error ${message}`, detail)\n }\n\n // Debug logging\n\n logDebugActivity = (functionName: string, detail: object = {}): void => {\n const { identifier, controller, element } = this\n detail = Object.assign({ identifier, controller, element }, detail)\n this.application.logDebugActivity(this.identifier, functionName, detail)\n }\n\n // Target observer delegate\n\n targetConnected(element: Element, name: string) {\n this.invokeControllerMethod(`${name}TargetConnected`, element)\n }\n\n targetDisconnected(element: Element, name: string) {\n this.invokeControllerMethod(`${name}TargetDisconnected`, element)\n }\n\n // Private\n\n invokeControllerMethod(methodName: string, ...args: any[]) {\n const controller: any = this.controller\n if (typeof controller[methodName] == \"function\") {\n controller[methodName](...args)\n }\n }\n}\n","import { Constructor } from \"./constructor\"\n\nexport function readInheritableStaticArrayValues<T, U = string>(constructor: Constructor<T>, propertyName: string) {\n const ancestors = getAncestorsForConstructor(constructor)\n return Array.from(ancestors.reduce((values, constructor) => {\n getOwnStaticArrayValues(constructor, propertyName).forEach(name => values.add(name))\n return values\n }, new Set as Set<U>))\n}\n\nexport function readInheritableStaticObjectPairs<T, U>(constructor: Constructor<T>, propertyName: string) {\n const ancestors = getAncestorsForConstructor(constructor)\n return ancestors.reduce((pairs, constructor) => {\n pairs.push(...getOwnStaticObjectPairs(constructor, propertyName) as any)\n return pairs\n }, [] as [string, U][])\n}\n\nfunction getAncestorsForConstructor<T>(constructor: Constructor<T>) {\n const ancestors: Constructor<{}>[] = []\n while (constructor) {\n ancestors.push(constructor)\n constructor = Object.getPrototypeOf(constructor)\n }\n return ancestors.reverse()\n}\n\nfunction getOwnStaticArrayValues<T>(constructor: Constructor<T>, propertyName: string) {\n const definition = (constructor as any)[propertyName]\n return Array.isArray(definition) ? definition : []\n}\n\nfunction getOwnStaticObjectPairs<T, U>(constructor: Constructor<T>, propertyName: string) {\n const definition = (constructor as any)[propertyName]\n return definition ? Object.keys(definition).map(key => [key, definition[key]] as [string, U]) : []\n}\n","import { Constructor } from \"./constructor\"\nimport { readInheritableStaticArrayValues } from \"./inheritable_statics\"\n\nexport type Blessing<T> = (constructor: Constructor<T>) => PropertyDescriptorMap\n\nexport interface Blessable<T> extends Constructor<T> {\n readonly blessings?: Blessing<T>[]\n}\n\nexport function bless<T>(constructor: Blessable<T>): Constructor<T> {\n return shadow(constructor, getBlessedProperties(constructor))\n}\n\nfunction shadow<T>(constructor: Constructor<T>, properties: PropertyDescriptorMap) {\n const shadowConstructor = extend(constructor)\n const shadowProperties = getShadowProperties(constructor.prototype, properties)\n Object.defineProperties(shadowConstructor.prototype, shadowProperties)\n return shadowConstructor\n}\n\nfunction getBlessedProperties<T>(constructor: Constructor<T>) {\n const blessings = readInheritableStaticArrayValues(constructor, \"blessings\") as Blessing<T>[]\n return blessings.reduce((blessedProperties, blessing) => {\n const properties = blessing(constructor)\n for (const key in properties) {\n const descriptor = blessedProperties[key] || {} as PropertyDescriptor\n blessedProperties[key] = Object.assign(descriptor, properties[key])\n }\n return blessedProperties\n }, {} as PropertyDescriptorMap)\n}\n\nfunction getShadowProperties<T>(prototype: any, properties: PropertyDescriptorMap) {\n return getOwnKeys(properties).reduce((shadowProperties, key) => {\n const descriptor = getShadowedDescriptor(prototype, properties, key)\n if (descriptor) {\n Object.assign(shadowProperties, { [key]: descriptor })\n }\n return shadowProperties\n }, {} as PropertyDescriptorMap)\n}\n\nfunction getShadowedDescriptor(prototype: any, properties: PropertyDescriptorMap, key: string | symbol) {\n const shadowingDescriptor = Object.getOwnPropertyDescriptor(prototype, key)\n const shadowedByValue = shadowingDescriptor && \"value\" in shadowingDescriptor\n if (!shadowedByValue) {\n const descriptor = Object.getOwnPropertyDescriptor(properties, key)!.value\n if (shadowingDescriptor) {\n descriptor.get = shadowingDescriptor.get || descriptor.get\n descriptor.set = shadowingDescriptor.set || descriptor.set\n }\n return descriptor\n }\n}\n\nconst getOwnKeys = (() => {\n if (typeof Object.getOwnPropertySymbols == \"function\") {\n return (object: any) => [\n ...Object.getOwnPropertyNames(object),\n ...Object.getOwnPropertySymbols(object)\n ]\n } else {\n return Object.getOwnPropertyNames\n }\n})()\n\nconst extend = (() => {\n function extendWithReflect<T extends Constructor<{}>>(constructor: T): T {\n function extended() {\n return Reflect.construct(constructor, arguments, new.target)\n }\n\n extended.prototype = Object.create(constructor.prototype, {\n constructor: { value: extended }\n })\n\n Reflect.setPrototypeOf(extended, constructor)\n return extended as any\n }\n\n function testReflectExtension() {\n const a = function(this: any) { this.a.call(this) } as any\n const b = extendWithReflect(a)\n b.prototype.a = function() {}\n return new b\n }\n\n try {\n testReflectExtension()\n return extendWithReflect\n } catch (error) {\n return <T extends Constructor<{}>>(constructor: T) => class extended extends constructor {}\n }\n})()\n","import { Application } from \"./application\"\nimport { Context } from \"./context\"\nimport { ControllerConstructor } from \"./controller\"\nimport { Definition, blessDefinition } from \"./definition\"\nimport { Scope } from \"./scope\"\n\nexport class Module {\n readonly application: Application\n readonly definition: Definition\n private contextsByScope: WeakMap<Scope, Context>\n private connectedContexts: Set<Context>\n\n constructor(application: Application, definition: Definition) {\n this.application = application\n this.definition = blessDefinition(definition)\n this.contextsByScope = new WeakMap\n this.connectedContexts = new Set\n }\n\n get identifier(): string {\n return this.definition.identifier\n }\n\n get controllerConstructor(): ControllerConstructor {\n return this.definition.controllerConstructor\n }\n\n get contexts(): Context[] {\n return Array.from(this.connectedContexts)\n }\n\n connectContextForScope(scope: Scope) {\n const context = this.fetchContextForScope(scope)\n this.connectedContexts.add(context)\n context.connect()\n }\n\n disconnectContextForScope(scope: Scope) {\n const context = this.contextsByScope.get(scope)\n if (context) {\n this.connectedContexts.delete(context)\n context.disconnect()\n }\n }\n\n private fetchContextForScope(scope: Scope): Context {\n let context = this.contextsByScope.get(scope)\n if (!context) {\n context = new Context(this, scope)\n this.contextsByScope.set(scope, context)\n }\n return context\n }\n}\n","import { bless } from \"./blessing\"\nimport { ControllerConstructor } from \"./controller\"\n\nexport interface Definition {\n identifier: string\n controllerConstructor: ControllerConstructor\n}\n\nexport function blessDefinition(definition: Definition): Definition {\n return {\n identifier: definition.identifier,\n controllerConstructor: bless(definition.controllerConstructor)\n }\n}\n","import { Scope } from \"./scope\"\nimport { tokenize } from \"./string_helpers\"\n\nexport class ClassMap {\n readonly scope: Scope\n\n constructor(scope: Scope) {\n this.scope = scope\n }\n\n has(name: string) {\n return this.data.has(this.getDataKey(name))\n }\n\n get(name: string): string | undefined {\n return this.getAll(name)[0]\n }\n\n getAll(name: string) {\n const tokenString = this.data.get(this.getDataKey(name)) || \"\"\n return tokenize(tokenString)\n }\n\n getAttributeName(name: string) {\n return this.data.getAttributeNameForKey(this.getDataKey(name))\n }\n\n getDataKey(name: string) {\n return `${name}-class`\n }\n\n get data() {\n return this.scope.data\n }\n}\n","import { Scope } from \"./scope\"\nimport { dasherize } from \"./string_helpers\"\n\nexport class DataMap {\n readonly scope: Scope\n\n constructor(scope: Scope) {\n this.scope = scope\n }\n\n get element(): Element {\n return this.scope.element\n }\n\n get identifier(): string {\n return this.scope.identifier\n }\n\n get(key: string): string | null {\n const name = this.getAttributeNameForKey(key)\n return this.element.getAttribute(name)\n }\n\n set(key: string, value: string): string | null {\n const name = this.getAttributeNameForKey(key)\n this.element.setAttribute(name, value)\n return this.get(key)\n }\n\n has(key: string): boolean {\n const name = this.getAttributeNameForKey(key)\n return this.element.hasAttribute(name)\n }\n\n delete(key: string): boolean {\n if (this.has(key)) {\n const name = this.getAttributeNameForKey(key)\n this.element.removeAttribute(name)\n return true\n } else {\n return false\n }\n }\n\n getAttributeNameForKey(key: string): string {\n return `data-${this.identifier}-${dasherize(key)}`\n }\n}\n","import { Logger } from \"./logger\"\n\nexport class Guide {\n readonly logger: Logger\n readonly warnedKeysByObject: WeakMap<any, Set<string>> = new WeakMap\n\n constructor(logger: Logger) {\n this.logger = logger\n }\n\n warn(object: any, key: string, message: string) {\n let warnedKeys: Set<string> | undefined = this.warnedKeysByObject.get(object)\n\n if (!warnedKeys) {\n warnedKeys = new Set\n this.warnedKeysByObject.set(object, warnedKeys)\n }\n\n if (!warnedKeys.has(key)) {\n warnedKeys.add(key)\n this.logger.warn(message, object)\n }\n }\n}\n","export function attributeValueContainsToken(attributeName: string, token: string) {\n return `[${attributeName}~=\"${token}\"]`\n}\n","import { Scope } from \"./scope\"\nimport { attributeValueContainsToken } from \"./selectors\"\n\nexport class TargetSet {\n readonly scope: Scope\n\n constructor(scope: Scope) {\n this.scope = scope\n }\n\n get element() {\n return this.scope.element\n }\n\n get identifier() {\n return this.scope.identifier\n }\n\n get schema() {\n return this.scope.schema\n }\n\n has(targetName: string) {\n return this.find(targetName) != null\n }\n\n find(...targetNames: string[]) {\n return targetNames.reduce((target, targetName) =>\n target\n || this.findTarget(targetName)\n || this.findLegacyTarget(targetName)\n , undefined as Element | undefined)\n }\n\n findAll(...targetNames: string[]) {\n return targetNames.reduce((targets, targetName) => [\n ...targets,\n ...this.findAllTargets(targetName),\n ...this.findAllLegacyTargets(targetName)\n ], [] as Element[])\n }\n\n private findTarget(targetName: string) {\n const selector = this.getSelectorForTargetName(targetName)\n return this.scope.findElement(selector)\n }\n\n private findAllTargets(targetName: string) {\n const selector = this.getSelectorForTargetName(targetName)\n return this.scope.findAllElements(selector)\n }\n\n private getSelectorForTargetName(targetName: string) {\n const attributeName = this.schema.targetAttributeForScope(this.identifier)\n return attributeValueContainsToken(attributeName, targetName)\n }\n\n private findLegacyTarget(targetName: string) {\n const selector = this.getLegacySelectorForTargetName(targetName)\n return this.deprecate(this.scope.findElement(selector), targetName)\n }\n\n private findAllLegacyTargets(targetName: string) {\n const selector = this.getLegacySelectorForTargetName(targetName)\n return this.scope.findAllElements(selector).map(element => this.deprecate(element, targetName))\n }\n\n private getLegacySelectorForTargetName(targetName: string) {\n const targetDescriptor = `${this.identifier}.${targetName}`\n return attributeValueContainsToken(this.schema.targetAttribute, targetDescriptor)\n }\n\n private deprecate<T>(element: T, targetName: string) {\n if (element) {\n const { identifier } = this\n const attributeName = this.schema.targetAttribute\n const revisedAttributeName = this.schema.targetAttributeForScope(identifier)\n this.guide.warn(element, `target:${targetName}`,\n `Please replace ${attributeName}=\"${identifier}.${targetName}\" with ${revisedAttributeName}=\"${targetName}\". ` +\n `The ${attributeName} attribute is deprecated and will be removed in a future version of Stimulus.`)\n }\n return element\n }\n\n private get guide() {\n return this.scope.guide\n }\n}\n","import { ClassMap } from \"./class_map\"\nimport { DataMap } from \"./data_map\"\nimport { Guide } from \"./guide\"\nimport { Logger } from \"./logger\"\nimport { Schema } from \"./schema\"\nimport { attributeValueContainsToken } from \"./selectors\"\nimport { TargetSet } from \"./target_set\"\n\nexport class Scope {\n readonly schema: Schema\n readonly element: Element\n readonly identifier: string\n readonly guide: Guide\n readonly targets = new TargetSet(this)\n readonly classes = new ClassMap(this)\n readonly data = new DataMap(this)\n\n constructor(schema: Schema, element: Element, identifier: string, logger: Logger) {\n this.schema = schema\n this.element = element\n this.identifier = identifier\n this.guide = new Guide(logger)\n }\n\n findElement(selector: string): Element | undefined {\n return this.element.matches(selector)\n ? this.element\n : this.queryElements(selector).find(this.containsElement)\n }\n\n findAllElements(selector: string): Element[] {\n return [\n ...this.element.matches(selector) ? [this.element] : [],\n ...this.queryElements(selector).filter(this.containsElement)\n ]\n }\n\n containsElement = (element: Element): boolean => {\n return element.closest(this.controllerSelector) === this.element\n }\n\n private queryElements(selector: string): Element[] {\n return Array.from(this.element.querySelectorAll(selector))\n }\n\n private get controllerSelector(): string {\n return attributeValueContainsToken(this.schema.controllerAttribute, this.identifier)\n }\n}\n","import { ErrorHandler } from \"./error_handler\"\nimport { Schema } from \"./schema\"\nimport { Scope } from \"./scope\"\nimport { Token, ValueListObserver, ValueListObserverDelegate } from \"../mutation-observers\"\n\nexport interface ScopeObserverDelegate extends ErrorHandler {\n createScopeForElementAndIdentifier(element: Element, identifier: string): Scope\n scopeConnected(scope: Scope): void\n scopeDisconnected(scope: Scope): void\n}\n\nexport class ScopeObserver implements ValueListObserverDelegate<Scope> {\n readonly element: Element\n readonly schema: Schema\n private delegate: ScopeObserverDelegate\n private valueListObserver: ValueListObserver<Scope>\n private scopesByIdentifierByElement: WeakMap<Element, Map<string, Scope>>\n private scopeReferenceCounts: WeakMap<Scope, number>\n\n constructor(element: Element, schema: Schema, delegate: ScopeObserverDelegate) {\n this.element = element\n this.schema = schema\n this.delegate = delegate\n this.valueListObserver = new ValueListObserver(this.element, this.controllerAttribute, this)\n this.scopesByIdentifierByElement = new WeakMap\n this.scopeReferenceCounts = new WeakMap\n }\n\n start() {\n this.valueListObserver.start()\n }\n\n stop() {\n this.valueListObserver.stop()\n }\n\n get controllerAttribute() {\n return this.schema.controllerAttribute\n }\n\n // Value observer delegate\n\n parseValueForToken(token: Token): Scope | undefined {\n const { element, content: identifier } = token\n const scopesByIdentifier = this.fetchScopesByIdentifierForElement(element)\n\n let scope = scopesByIdentifier.get(identifier)\n if (!scope) {\n scope = this.delegate.createScopeForElementAndIdentifier(element, identifier)\n scopesByIdentifier.set(identifier, scope)\n }\n\n return scope\n }\n\n elementMatchedValue(element: Element, value: Scope) {\n const referenceCount = (this.scopeReferenceCounts.get(value) || 0) + 1\n this.scopeReferenceCounts.set(value, referenceCount)\n if (referenceCount == 1) {\n this.delegate.scopeConnected(value)\n }\n }\n\n elementUnmatchedValue(element: Element, value: Scope) {\n const referenceCount = this.scopeReferenceCounts.get(value)\n if (referenceCount) {\n this.scopeReferenceCounts.set(value, referenceCount - 1)\n if (referenceCount == 1) {\n this.delegate.scopeDisconnected(value)\n }\n }\n }\n\n private fetchScopesByIdentifierForElement(element: Element) {\n let scopesByIdentifier = this.scopesByIdentifierByElement.get(element)\n if (!scopesByIdentifier) {\n scopesByIdentifier = new Map\n this.scopesByIdentifierByElement.set(element, scopesByIdentifier)\n }\n return scopesByIdentifier\n }\n}\n","import { Application } from \"./application\"\nimport { Context } from \"./context\"\nimport { Definition } from \"./definition\"\nimport { Module } from \"./module\"\nimport { Multimap } from \"../multimap\"\nimport { Scope } from \"./scope\"\nimport { ScopeObserver, ScopeObserverDelegate } from \"./scope_observer\"\n\nexport class Router implements ScopeObserverDelegate {\n readonly application: Application\n private scopeObserver: ScopeObserver\n private scopesByIdentifier: Multimap<string, Scope>\n private modulesByIdentifier: Map<string, Module>\n\n constructor(application: Application) {\n this.application = application\n this.scopeObserver = new ScopeObserver(this.element, this.schema, this)\n this.scopesByIdentifier = new Multimap\n this.modulesByIdentifier = new Map\n }\n\n get element() {\n return this.application.element\n }\n\n get schema() {\n return this.application.schema\n }\n\n get logger() {\n return this.application.logger\n }\n\n get controllerAttribute(): string {\n return this.schema.controllerAttribute\n }\n\n get modules() {\n return Array.from(this.modulesByIdentifier.values())\n }\n\n get contexts() {\n return this.modules.reduce((contexts, module) => contexts.concat(module.contexts), [] as Context[])\n }\n\n start() {\n this.scopeObserver.start()\n }\n\n stop() {\n this.scopeObserver.stop()\n }\n\n loadDefinition(definition: Definition) {\n this.unloadIdentifier(definition.identifier)\n const module = new Module(this.application, definition)\n this.connectModule(module)\n }\n\n unloadIdentifier(identifier: string) {\n const module = this.modulesByIdentifier.get(identifier)\n if (module) {\n this.disconnectModule(module)\n }\n }\n\n getContextForElementAndIdentifier(element: Element, identifier: string) {\n const module = this.modulesByIdentifier.get(identifier)\n if (module) {\n return module.contexts.find(context => context.element == element)\n }\n }\n\n // Error handler delegate\n\n handleError(error: Error, message: string, detail: any) {\n this.application.handleError(error, message, detail)\n }\n\n // Scope observer delegate\n\n createScopeForElementAndIdentifier(element: Element, identifier: string) {\n return new Scope(this.schema, element, identifier, this.logger)\n }\n\n scopeConnected(scope: Scope) {\n this.scopesByIdentifier.add(scope.identifier, scope)\n const module = this.modulesByIdentifier.get(scope.identifier)\n if (module) {\n module.connectContextForScope(scope)\n }\n }\n\n scopeDisconnected(scope: Scope) {\n this.scopesByIdentifier.delete(scope.identifier, scope)\n const module = this.modulesByIdentifier.get(scope.identifier)\n if (module) {\n module.disconnectContextForScope(scope)\n }\n }\n\n // Modules\n\n private connectModule(module: Module) {\n this.modulesByIdentifier.set(module.identifier, module)\n const scopes = this.scopesByIdentifier.getValuesForKey(module.identifier)\n scopes.forEach(scope => module.connectContextForScope(scope))\n }\n\n private disconnectModule(module: Module) {\n this.modulesByIdentifier.delete(module.identifier)\n const scopes = this.scopesByIdentifier.getValuesForKey(module.identifier)\n scopes.forEach(scope => module.disconnectContextForScope(scope))\n }\n}\n","export interface Schema {\n controllerAttribute: string\n actionAttribute: string\n targetAttribute: string\n targetAttributeForScope(identifier: string): string\n}\n\nexport const defaultSchema: Schema = {\n controllerAttribute: \"data-controller\",\n actionAttribute: \"data-action\",\n targetAttribute: \"data-target\",\n targetAttributeForScope: identifier => `data-${identifier}-target`\n}\n","import { Controller, ControllerConstructor } from \"./controller\"\nimport { Definition } from \"./definition\"\nimport { Dispatcher } from \"./dispatcher\"\nimport { ErrorHandler } from \"./error_handler\"\nimport { Logger } from \"./logger\"\nimport { Router } from \"./router\"\nimport { Schema, defaultSchema } from \"./schema\"\n\nexport class Application implements ErrorHandler {\n readonly element: Element\n readonly schema: Schema\n readonly dispatcher: Dispatcher\n readonly router: Router\n logger: Logger = console\n debug: boolean = false\n\n static start(element?: Element, schema?: Schema): Application {\n const application = new Application(element, schema)\n application.start()\n return application\n }\n\n constructor(element: Element = document.documentElement, schema: Schema = defaultSchema) {\n this.element = element\n this.schema = schema\n this.dispatcher = new Dispatcher(this)\n this.router = new Router(this)\n }\n\n async start() {\n await domReady()\n this.logDebugActivity(\"application\", \"starting\")\n this.dispatcher.start()\n this.router.start()\n this.logDebugActivity(\"application\", \"start\")\n }\n\n stop() {\n this.logDebugActivity(\"application\", \"stopping\")\n this.dispatcher.stop()\n this.router.stop()\n this.logDebugActivity(\"application\", \"stop\")\n }\n\n register(identifier: string, controllerConstructor: ControllerConstructor) {\n if ((controllerConstructor as any).shouldLoad) {\n this.load({ identifier, controllerConstructor })\n }\n }\n\n load(...definitions: Definition[]): void\n load(definitions: Definition[]): void\n load(head: Definition | Definition[], ...rest: Definition[]) {\n const definitions = Array.isArray(head) ? head : [head, ...rest]\n definitions.forEach(definition => this.router.loadDefinition(definition))\n }\n\n unload(...identifiers: string[]): void\n unload(identifiers: string[]): void\n unload(head: string | string[], ...rest: string[]) {\n const identifiers = Array.isArray(head) ? head : [head, ...rest]\n identifiers.forEach(identifier => this.router.unloadIdentifier(identifier))\n }\n\n // Controllers\n\n get controllers(): Controller[] {\n return this.router.contexts.map(context => context.controller)\n }\n\n getControllerForElementAndIdentifier(element: Element, identifier: string): Controller | null {\n const context = this.router.getContextForElementAndIdentifier(element, identifier)\n return context ? context.controller : null\n }\n\n // Error handling\n\n handleError(error: Error, message: string, detail: object) {\n this.logger.error(`%s\\n\\n%o\\n\\n%o`, message, error, detail)\n\n window.onerror?.(message, \"\", 0, 0, error)\n }\n\n // Debug logging\n\n logDebugActivity = (identifier: string, functionName: string, detail: object = {}): void => {\n if (this.debug) {\n this.logFormattedMessage(identifier, functionName, detail)\n }\n }\n\n private logFormattedMessage(identifier: string, functionName: string, detail: object = {}) {\n detail = Object.assign({ application: this }, detail)\n\n this.logger.groupCollapsed(`${identifier} #${functionName}`)\n this.logger.log(\"details:\", { ...detail })\n this.logger.groupEnd()\n }\n}\n\nfunction domReady() {\n return new Promise<void>(resolve => {\n if (document.readyState == \"loading\") {\n document.addEventListener(\"DOMContentLoaded\", () => resolve())\n } else {\n resolve()\n }\n })\n}\n","import { Constructor } from \"./constructor\"\nimport { Controller } from \"./controller\"\nimport { readInheritableStaticObjectPairs } from \"./inheritable_statics\"\nimport { camelize, capitalize, dasherize } from \"./string_helpers\"\n\nexport function ValuePropertiesBlessing<T>(constructor: Constructor<T>) {\n const valueDefinitionPairs = readInheritableStaticObjectPairs<T, ValueTypeDefinition>(constructor, \"values\")\n const propertyDescriptorMap: PropertyDescriptorMap = {\n valueDescriptorMap: {\n get(this: Controller) {\n return valueDefinitionPairs.reduce((result, valueDefinitionPair) => {\n const valueDescriptor = parseValueDefinitionPair(valueDefinitionPair)\n const attributeName = this.data.getAttributeNameForKey(valueDescriptor.key)\n return Object.assign(result, { [attributeName]: valueDescriptor })\n }, {} as ValueDescriptorMap)\n }\n }\n }\n\n return valueDefinitionPairs.reduce((properties, valueDefinitionPair) => {\n return Object.assign(properties, propertiesForValueDefinitionPair(valueDefinitionPair))\n }, propertyDescriptorMap)\n}\n\nexport function propertiesForValueDefinitionPair<T>(valueDefinitionPair: ValueDefinitionPair): PropertyDescriptorMap {\n const definition = parseValueDefinitionPair(valueDefinitionPair)\n const { key, name, reader: read, writer: write } = definition\n\n return {\n [name]: {\n get(this: Controller) {\n const value = this.data.get(key)\n if (value !== null) {\n return read(value)\n } else {\n return definition.defaultValue\n }\n },\n\n set(this: Controller, value: T | undefined) {\n if (value === undefined) {\n this.data.delete(key)\n } else {\n this.data.set(key, write(value))\n }\n }\n },\n\n [`has${capitalize(name)}`]: {\n get(this: Controller): boolean {\n return this.data.has(key) || definition.hasCustomDefaultValue\n }\n }\n }\n}\n\nexport type ValueDescriptor = {\n type: ValueType,\n key: string,\n name: string,\n defaultValue: ValueTypeDefault,\n hasCustomDefaultValue: boolean,\n reader: Reader,\n writer: Writer\n}\n\nexport type ValueDescriptorMap = { [attributeName: string]: ValueDescriptor }\n\nexport type ValueDefinitionMap = { [token: string]: ValueTypeDefinition }\n\nexport type ValueDefinitionPair = [string, ValueTypeDefinition]\n\nexport type ValueTypeConstant = typeof Array | typeof Boolean | typeof Number | typeof Object | typeof String\n\nexport type ValueTypeDefault = Array<any> | Boolean | Number | Object | String\n\nexport type ValueTypeObject = { type: ValueTypeConstant, default: ValueTypeDefault }\n\nexport type ValueTypeDefinition = ValueTypeConstant | ValueTypeDefault | ValueTypeObject\n\nexport type ValueType = \"array\" | \"boolean\" | \"number\" | \"object\" | \"string\"\n\nfunction parseValueDefinitionPair([token, typeDefinition]: ValueDefinitionPair): ValueDescriptor {\n return valueDescriptorForTokenAndTypeDefinition(token, typeDefinition)\n}\n\nfunction parseValueTypeConstant(constant: ValueTypeConstant) {\n switch (constant) {\n case Array: return \"array\"\n case Boolean: return \"boolean\"\n case Number: return \"number\"\n case Object: return \"object\"\n case String: return \"string\"\n }\n}\n\nfunction parseValueTypeDefault(defaultValue: ValueTypeDefault) {\n switch (typeof defaultValue) {\n case \"boolean\": return \"boolean\"\n case \"number\": return \"number\"\n case \"string\": return \"string\"\n }\n\n if (Array.isArray(defaultValue)) return \"array\"\n if (Object.prototype.toString.call(defaultValue) === \"[object Object]\") return \"object\"\n}\n\nfunction parseValueTypeObject(typeObject: ValueTypeObject) {\n const typeFromObject = parseValueTypeConstant(typeObject.type)\n\n if (typeFromObject) {\n const defaultValueType = parseValueTypeDefault(typeObject.default)\n\n if (typeFromObject !== defaultValueType) {\n throw new Error(`Type \"${typeFromObject}\" must match the type of the default value. Given default value: \"${typeObject.default}\" as \"${defaultValueType}\"`)\n }\n\n return typeFromObject\n }\n}\n\nfunction parseValueTypeDefinition(typeDefinition: ValueTypeDefinition): ValueType {\n const typeFromObject = parseValueTypeObject(typeDefinition as ValueTypeObject)\n const typeFromDefaultValue = parseValueTypeDefault(typeDefinition as ValueTypeDefault)\n const typeFromConstant = parseValueTypeConstant(typeDefinition as ValueTypeConstant)\n\n const type = typeFromObject || typeFromDefaultValue || typeFromConstant\n if (type) return type\n\n throw new Error(`Unknown value type \"${typeDefinition}\"`)\n}\n\nfunction defaultValueForDefinition(typeDefinition: ValueTypeDefinition): ValueTypeDefault {\n const constant = parseValueTypeConstant(typeDefinition as ValueTypeConstant)\n\n if (constant) return defaultValuesByType[constant]\n\n const defaultValue = (typeDefinition as ValueTypeObject).default\n if (defaultValue !== undefined) return defaultValue\n\n return typeDefinition\n}\n\nfunction valueDescriptorForTokenAndTypeDefinition(token: string, typeDefinition: ValueTypeDefinition) {\n const key = `${dasherize(token)}-value`\n const type = parseValueTypeDefinition(typeDefinition)\n return {\n type,\n key,\n name: camelize(key),\n get defaultValue() { return defaultValueForDefinition(typeDefinition) },\n get hasCustomDefaultValue() { return parseValueTypeDefault(typeDefinition) !== undefined },\n reader: readers[type],\n writer: writers[type] || writers.default\n }\n}\n\nconst defaultValuesByType = {\n get array() { return [] },\n boolean: false,\n number: 0,\n get object() { return {} },\n string: \"\"\n}\n\ntype Reader = (value: string) => any\n\nconst readers: { [type: string]: Reader } = {\n array(value: string): any[] {\n const array = JSON.parse(value)\n if (!Array.isArray(array)) {\n throw new TypeError(\"Expected array\")\n }\n return array\n },\n\n boolean(value: string): boolean {\n return !(value == \"0\" || String(value).toLowerCase() == \"false\")\n },\n\n number(value: string): number {\n return Number(value)\n },\n\n object(value: string): object {\n const object = JSON.parse(value)\n if (object === null || typeof object != \"object\" || Array.isArray(object)) {\n throw new TypeError(\"Expected object\")\n }\n return object\n },\n\n string(value: string): string {\n return value\n }\n}\n\ntype Writer = (value: any) => string\n\nconst writers: { [type: string]: Writer } = {\n default: writeString,\n array: writeJSON,\n object: writeJSON\n}\n\nfunction writeJSON(value: any) {\n return JSON.stringify(value)\n}\n\nfunction writeString(value: any) {\n return `${value}`\n}\n","import { ClassPropertiesBlessing } from \"./class_properties\"\nimport { Constructor } from \"./constructor\"\nimport { Context } from \"./context\"\nimport { TargetPropertiesBlessing } from \"./target_properties\"\nimport { ValuePropertiesBlessing, ValueDefinitionMap } from \"./value_properties\"\n\nexport type ControllerConstructor = Constructor<Controller>\n\nexport class Controller {\n static blessings = [ ClassPropertiesBlessing, TargetPropertiesBlessing, ValuePropertiesBlessing ]\n static targets: string[] = []\n static values: ValueDefinitionMap = {}\n\n static get shouldLoad() {\n return true\n }\n\n readonly context: Context\n\n constructor(context: Context) {\n this.context = context\n }\n\n get application() {\n return this.context.application\n }\n\n get scope() {\n return this.context.scope\n }\n\n get element() {\n return this.scope.element\n }\n\n get identifier() {\n return this.scope.identifier\n }\n\n get targets() {\n return this.scope.targets\n }\n\n get classes() {\n return this.scope.classes\n }\n\n get data() {\n return this.scope.data\n }\n\n initialize() {\n // Override in your subclass to set up initial controller state\n }\n\n connect() {\n // Override in your subclass to respond when the controller is connected to the DOM\n }\n\n disconnect() {\n // Override in your subclass to respond when the controller is disconnected from the DOM\n }\n\n dispatch(eventName: string, { target = this.element, detail = {}, prefix = this.identifier, bubbles = true, cancelable = true } = {}) {\n const type = prefix ? `${prefix}:${eventName}` : eventName\n const event = new CustomEvent(type, { detail, bubbles, cancelable })\n target.dispatchEvent(event)\n return event\n }\n}\n","import { Constructor } from \"./constructor\"\nimport { Controller } from \"./controller\"\nimport { readInheritableStaticArrayValues } from \"./inheritable_statics\"\nimport { capitalize } from \"./string_helpers\"\n\nexport function ClassPropertiesBlessing<T>(constructor: Constructor<T>) {\n const classes = readInheritableStaticArrayValues(constructor, \"classes\")\n return classes.reduce((properties, classDefinition) => {\n return Object.assign(properties, propertiesForClassDefinition(classDefinition))\n }, {} as PropertyDescriptorMap)\n}\n\nfunction propertiesForClassDefinition(key: string) {\n return {\n [`${key}Class`]: {\n get(this: Controller) {\n const { classes } = this\n if (classes.has(key)) {\n return classes.get(key)\n } else {\n const attribute = classes.getAttributeName(key)\n throw new Error(`Missing attribute \"${attribute}\"`)\n }\n }\n },\n\n [`${key}Classes`]: {\n get(this: Controller) {\n return this.classes.getAll(key)\n }\n },\n\n [`has${capitalize(key)}Class`]: {\n get(this: Controller) {\n return this.classes.has(key)\n }\n }\n }\n}\n","import { Constructor } from \"./constructor\"\nimport { Controller } from \"./controller\"\nimport { readInheritableStaticArrayValues } from \"./inheritable_statics\"\nimport { capitalize } from \"./string_helpers\"\n\nexport function TargetPropertiesBlessing<T>(constructor: Constructor<T>) {\n const targets = readInheritableStaticArrayValues(constructor, \"targets\")\n return targets.reduce((properties, targetDefinition) => {\n return Object.assign(properties, propertiesForTargetDefinition(targetDefinition))\n }, {} as PropertyDescriptorMap)\n}\n\nfunction propertiesForTargetDefinition(name: string) {\n return {\n [`${name}Target`]: {\n get(this: Controller) {\n const target = this.targets.find(name)\n if (target) {\n return target\n } else {\n throw new Error(`Missing target element \"${name}\" for \"${this.identifier}\" controller`)\n }\n }\n },\n\n [`${name}Targets`]: {\n get(this: Controller) {\n return this.targets.findAll(name)\n }\n },\n\n [`has${capitalize(name)}Target`]: {\n get(this: Controller) {\n return this.targets.has(name)\n }\n }\n }\n}\n"],"names":["EventListener","constructor","eventTarget","eventName","eventOptions","this","unorderedBindings","Set","connect","addEventListener","disconnect","removeEventListener","bindingConnected","binding","add","bindingDisconnected","delete","handleEvent","event","extendedEvent","stopImmediatePropagation","Object","assign","immediatePropagationStopped","call","extendEvent","bindings","Array","from","sort","left","right","leftIndex","index","rightIndex","Dispatcher","application","eventListenerMaps","Map","started","start","eventListeners","forEach","eventListener","stop","values","reduce","listeners","map","concat","fetchEventListenerForBinding","handleError","error","message","detail","fetchEventListener","eventListenerMap","fetchEventListenerMapForEventTarget","cacheKey","get","createEventListener","set","parts","keys","key","push","join","descriptorPattern","parseEventTarget","eventTargetName","window","document","camelize","value","replace","_","char","toUpperCase","capitalize","charAt","slice","dasherize","toLowerCase","defaultEventNames","a","e","button","form","details","input","getAttribute","select","textarea","Error","typecast","JSON","parse","o_O","Binding","context","action","identifier","willBeInvokedByEvent","invokeWithEvent","method","controller","methodName","target","currentTarget","params","actionEvent","logDebugActivity","element","Element","contains","scope","containsElement","ElementObserver","delegate","attributes","childList","subtree","elements","mutationObserver","MutationObserver","mutations","processMutations","observe","mutationObserverInit","refresh","pause","callback","takeRecords","matches","matchElementsInTree","has","removeElement","addElement","mutation","processMutation","type","processAttributeChange","attributeName","processRemovedNodes","removedNodes","processAddedNodes","addedNodes","node","elementAttributeChanged","matchElement","nodes","elementFromNode","processTree","elementIsActive","tree","processor","nodeType","Node","ELEMENT_NODE","isConnected","elementMatched","elementUnmatched","AttributeObserver","elementObserver","selector","hasAttribute","match","querySelectorAll","elementMatchedAttribute","elementUnmatchedAttribute","elementAttributeValueChanged","StringMapObserver","stringMap","attributeOldValue","knownAttributeNames","refreshAttribute","oldValue","getStringMapKeyForAttribute","stringMapKeyAdded","stringMapValueChanged","stringMapKeyRemoved","currentAttributeNames","recordedAttributeNames","attribute","name","fetch","del","prune","size","Multimap","valuesByKey","hasKey","hasValue","some","getValuesForKey","getKeysForValue","filter","IndexedMultimap","super","keysByValue","TokenListObserver","attributeObserver","tokensByElement","tokensMatched","readTokensForElement","unmatchedTokens","matchedTokens","refreshTokensForElement","tokensUnmatched","tokens","token","tokenMatched","tokenUnmatched","previousTokens","currentTokens","firstDifferingIndex","length","Math","max","zip","findIndex","previousToken","currentToken","content","tokenString","trim","split","parseTokenString","ValueListObserver","tokenListObserver","parseResultsByToken","WeakMap","valuesByTokenByElement","fetchParseResultForToken","fetchValuesByTokenForElement","elementMatchedValue","elementUnmatchedValue","parseResult","parseToken","valuesByToken","parseValueForToken","BindingObserver","bindingsByAction","valueListObserver","actionAttribute","disconnectAllActions","schema","connectAction","disconnectAction","clear","descriptor","tagName","getDefaultEventNameForElement","forToken","descriptorString","options","test","parseActionDescriptorString","toString","eventNameSuffix","getParamsFromEventTargetAttributes","pattern","RegExp","ValueObserver","receiver","stringMapObserver","valueDescriptorMap","invokeChangedCallbacksForDefaultValues","invokeChangedCallback","writer","defaultValue","valueDescriptorNameMap","valueDescriptors","undefined","data","rawValue","rawOldValue","changedMethodName","changedMethod","reader","descriptors","hasMethodName","TargetObserver","targetsByName","disconnectAllTargets","connectTarget","disconnectTarget","targetConnected","targetDisconnected","Context","module","functionName","controllerConstructor","bindingObserver","dispatcher","valueObserver","targetObserver","initialize","parentElement","invokeControllerMethod","args","readInheritableStaticArrayValues","propertyName","ancestors","getAncestorsForConstructor","definition","isArray","getOwnStaticArrayValues","readInheritableStaticObjectPairs","pairs","getOwnStaticObjectPairs","getPrototypeOf","reverse","bless","properties","shadowConstructor","extend","shadowProperties","prototype","getOwnKeys","shadowingDescriptor","getOwnPropertyDescriptor","getShadowedDescriptor","getShadowProperties","defineProperties","shadow","blessedProperties","blessing","getBlessedProperties","getOwnPropertySymbols","object","getOwnPropertyNames","extendWithReflect","extended","Reflect","construct","arguments","create","setPrototypeOf","b","testReflectExtension","Module","blessDefinition","contextsByScope","connectedContexts","contexts","connectContextForScope","fetchContextForScope","disconnectContextForScope","ClassMap","getDataKey","getAll","getAttributeName","getAttributeNameForKey","DataMap","setAttribute","removeAttribute","Guide","logger","warn","warnedKeys","warnedKeysByObject","attributeValueContainsToken","TargetSet","targetName","find","targetNames","findTarget","findLegacyTarget","findAll","targets","findAllTargets","findAllLegacyTargets","getSelectorForTargetName","findElement","findAllElements","targetAttributeForScope","getLegacySelectorForTargetName","deprecate","targetDescriptor","targetAttribute","revisedAttributeName","guide","Scope","closest","controllerSelector","queryElements","controllerAttribute","ScopeObserver","scopesByIdentifierByElement","scopeReferenceCounts","scopesByIdentifier","fetchScopesByIdentifierForElement","createScopeForElementAndIdentifier","referenceCount","scopeConnected","scopeDisconnected","Router","scopeObserver","modulesByIdentifier","modules","loadDefinition","unloadIdentifier","connectModule","disconnectModule","getContextForElementAndIdentifier","defaultSchema","Application","documentElement","console","debug","logFormattedMessage","router","Promise","resolve","readyState","register","shouldLoad","load","head","rest","unload","controllers","getControllerForElementAndIdentifier","onerror","groupCollapsed","log","groupEnd","parseValueDefinitionPair","typeDefinition","typeFromObject","typeObject","parseValueTypeConstant","defaultValueType","parseValueTypeDefault","default","parseValueTypeObject","typeFromDefaultValue","typeFromConstant","parseValueTypeDefinition","constant","defaultValuesByType","defaultValueForDefinition","hasCustomDefaultValue","readers","writers","valueDescriptorForTokenAndTypeDefinition","Boolean","Number","String","array","boolean","number","string","TypeError","writeJSON","stringify","Controller","classes","dispatch","prefix","bubbles","cancelable","CustomEvent","dispatchEvent","classDefinition","targetDefinition","valueDefinitionPairs","propertyDescriptorMap","result","valueDefinitionPair","valueDescriptor","read","write","propertiesForValueDefinitionPair"],"mappings":"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"}
@@ -4,13 +4,17 @@ class StimulusGenerator < Rails::Generators::NamedBase # :nodoc:
4
4
  source_root File.expand_path("templates", __dir__)
5
5
 
6
6
  def copy_view_files
7
- @attribute = stimulus_attribute_value(name)
8
- template "controller.js", "app/javascript/controllers/#{name}_controller.js"
9
- rails_command "stimulus:manifest:update" if Rails.root.join("package.json").exist?
7
+ @attribute = stimulus_attribute_value(controller_name)
8
+ template "controller.js", "app/javascript/controllers/#{controller_name}_controller.js"
9
+ rails_command "stimulus:manifest:update" unless Rails.root.join("config/importmap.rb").exist?
10
10
  end
11
11
 
12
12
  private
13
- def stimulus_attribute_value(name)
14
- name.gsub(/\//, "--").gsub("_", "-")
13
+ def controller_name
14
+ name.underscore.gsub(/_controller$/, "")
15
+ end
16
+
17
+ def stimulus_attribute_value(controller_name)
18
+ controller_name.gsub(/\//, "--").gsub("_", "-")
15
19
  end
16
20
  end
@@ -3,8 +3,7 @@ import { Application } from "@hotwired/stimulus"
3
3
  const application = Application.start()
4
4
 
5
5
  // Configure Stimulus development experience
6
- application.warnings = true
7
- application.debug = false
8
- window.Stimulus = application
6
+ application.debug = false
7
+ window.Stimulus = application
9
8
 
10
9
  export { application }
@@ -1,5 +1,6 @@
1
1
  // This file is auto-generated by ./bin/rails stimulus:manifest:update
2
- // Run that command whenever you add a new controller
2
+ // Run that command whenever you add a new controller or create them with
3
+ // ./bin/rails generate stimulus controllerName
3
4
 
4
5
  import { application } from "./application"
5
6
 
@@ -11,9 +11,12 @@ say "Import Stimulus controllers"
11
11
  append_to_file "app/javascript/application.js", %(import "controllers"\n)
12
12
 
13
13
  say "Pin Stimulus"
14
- append_to_file "config/importmap.rb" do <<-RUBY
15
- pin "@hotwired/stimulus", to: "stimulus.js", preload: true
16
- pin "@hotwired/stimulus-loading", to: "stimulus-loading.js", preload: true
17
- pin_all_from "app/javascript/controllers", under: "controllers"
18
- RUBY
19
- end
14
+ say %(Appending: pin "@hotwired/stimulus", to: "stimulus.min.js", preload: true")
15
+ append_to_file "config/importmap.rb", %(pin "@hotwired/stimulus", to: "stimulus.min.js", preload: true\n)
16
+
17
+ say %(Appending: pin "@hotwired/stimulus-loading", to: "stimulus-loading.js", preload: true)
18
+ append_to_file "config/importmap.rb", %(pin "@hotwired/stimulus-loading", to: "stimulus-loading.js", preload: true\n)
19
+
20
+ say "Pin all controllers"
21
+ say %(Appending: pin_all_from "app/javascript/controllers", under: "controllers")
22
+ append_to_file "config/importmap.rb", %(pin_all_from "app/javascript/controllers", under: "controllers"\n)
@@ -11,7 +11,7 @@ if (Rails.root.join("app/javascript/application.js")).exist?
11
11
  say "Import Stimulus controllers"
12
12
  append_to_file "app/javascript/application.js", %(import "./controllers"\n)
13
13
  else
14
- say %(You must import "./controllers" in your JavaScript entrypoint), :red
14
+ say %(Couldn't find "app/javascript/application.js".\nYou must import "./controllers" in your JavaScript entrypoint file), :red
15
15
  end
16
16
 
17
17
  say "Install Stimulus"
@@ -2,7 +2,7 @@ module Stimulus
2
2
  class Engine < ::Rails::Engine
3
3
  initializer "stimulus.assets" do
4
4
  if Rails.application.config.respond_to?(:assets)
5
- Rails.application.config.assets.precompile += %w( stimulus.js stimulus.min.js )
5
+ Rails.application.config.assets.precompile += %w( stimulus.js stimulus.min.js stimulus.min.js.map )
6
6
  end
7
7
  end
8
8
  end
@@ -1,3 +1,3 @@
1
1
  module Stimulus
2
- VERSION = "0.7.2"
2
+ VERSION = "1.0.3"
3
3
  end
@@ -37,7 +37,8 @@ namespace :stimulus do
37
37
 
38
38
  File.open(Rails.root.join("app/javascript/controllers/index.js"), "w+") do |index|
39
39
  index.puts "// This file is auto-generated by ./bin/rails stimulus:manifest:update"
40
- index.puts "// Run that command whenever you add a new controller"
40
+ index.puts "// Run that command whenever you add a new controller or create them with"
41
+ index.puts "// ./bin/rails generate stimulus controllerName"
41
42
  index.puts
42
43
  index.puts %(import { application } from "./application")
43
44
  index.puts manifest
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stimulus-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.7.2
4
+ version: 1.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sam Stephenson
@@ -10,10 +10,10 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2021-11-05 00:00:00.000000000 Z
13
+ date: 2022-02-19 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
- name: rails
16
+ name: railties
17
17
  requirement: !ruby/object:Gem::Requirement
18
18
  requirements:
19
19
  - - ">="
@@ -40,6 +40,7 @@ files:
40
40
  - app/assets/javascripts/stimulus-loading.js
41
41
  - app/assets/javascripts/stimulus.js
42
42
  - app/assets/javascripts/stimulus.min.js
43
+ - app/assets/javascripts/stimulus.min.js.map
43
44
  - lib/generators/stimulus/USAGE
44
45
  - lib/generators/stimulus/stimulus_generator.rb
45
46
  - lib/generators/stimulus/templates/controller.js.tt
@@ -75,7 +76,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
75
76
  - !ruby/object:Gem::Version
76
77
  version: '0'
77
78
  requirements: []
78
- rubygems_version: 3.2.22
79
+ rubygems_version: 3.2.32
79
80
  signing_key:
80
81
  specification_version: 4
81
82
  summary: A modest JavaScript framework for the HTML you already have.