algoliasearch - Version 1.4.0

Version Notes

- NEW: The design of the instant search is now responsive and mobile friendly
- NEW: Add the possibility to autocomplete on an attribute like brands, manufacturer, ...
- NEW: Handling of customer groups
- NEW: Add the possibility to do `partialUpdates` instead of `addObjects` to allow external sources to patch the records
- UPDATED: Handle empty query
- FIX: IE8 & IE9 compatibility issues
- FIX: Ability to use the extension if the magento instance is hosted in a subdir
- FIX: Add missing translations in the template
- FIX: Fixed a bug occurring while concatenating/minifying the JavaScript code

Download this release

Release Info

Developer Algolia Team
Extension algoliasearch
Version 1.4.0
Comparing to
See all releases


Code changes from version 1.3.5 to 1.4.0

app/code/community/Algolia/Algoliasearch/Block/System/Config/Form/Field/Additionalsections.php ADDED
@@ -0,0 +1,66 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+
3
+ /**
4
+ * Algolia custom sort order field
5
+ */
6
+ class Algolia_Algoliasearch_Block_System_Config_Form_Field_Additionalsections extends Mage_Adminhtml_Block_System_Config_Form_Field_Array_Abstract
7
+ {
8
+ protected $selectFields = array();
9
+
10
+ protected function getRenderer($columnId) {
11
+ if (!array_key_exists($columnId, $this->selectFields) || !$this->selectFields[$columnId])
12
+ {
13
+ $aOptions = array();
14
+
15
+ $selectField = Mage::app()->getLayout()->createBlock('algoliasearch/system_config_form_field_select')->setIsRenderToJsTemplate(true);
16
+
17
+ $config = Mage::helper('algoliasearch/config');
18
+
19
+ switch($columnId) {
20
+ case 'attribute': // Populate the attribute column with a list of searchable attributes
21
+
22
+ $attributes = $config->getFacets();
23
+
24
+ foreach ($attributes as $attribute) {
25
+ $aOptions[$attribute['attribute']] = $attribute['label'] ? $attribute['label'] : $attribute['attribute'];
26
+ }
27
+
28
+ $selectField->setExtraParams('style="width:130px;"');
29
+
30
+ break;
31
+ default:
32
+ throw new Exception('Unknown attribute id ' . $columnId);
33
+ }
34
+
35
+ $selectField->setOptions($aOptions);
36
+ $this->selectFields[$columnId] = $selectField;
37
+ }
38
+ return $this->selectFields[$columnId];
39
+ }
40
+
41
+ public function __construct()
42
+ {
43
+ $this->addColumn('attribute', array(
44
+ 'label' => Mage::helper('adminhtml')->__('Attribute'),
45
+ 'renderer'=> $this->getRenderer('attribute'),
46
+ ));
47
+
48
+ $this->addColumn('label', array(
49
+ 'label' => Mage::helper('adminhtml')->__('Label'),
50
+ 'style' => 'width: 100px;'
51
+ ));
52
+
53
+ $this->_addAfter = false;
54
+ $this->_addButtonLabel = Mage::helper('adminhtml')->__('Add Attribute');
55
+ parent::__construct();
56
+ }
57
+
58
+ protected function _prepareArrayRow(Varien_Object $row)
59
+ {
60
+ $row->setData(
61
+ 'option_extra_attr_' . $this->getRenderer('attribute')->calcOptionHash(
62
+ $row->getAttribute()),
63
+ 'selected="selected"'
64
+ );
65
+ }
66
+ }
app/code/community/Algolia/Algoliasearch/Block/System/Config/Form/Field/Facets.php CHANGED
@@ -32,6 +32,7 @@ class Algolia_Algoliasearch_Block_System_Config_Form_Field_Facets extends Mage_A
32
  'conjunctive' => 'Conjunctive',
33
  'disjunctive' => 'Disjunctive',
34
  'slider' => 'Slider',
 
35
  'other' => 'Other ->'
36
  );
37
 
32
  'conjunctive' => 'Conjunctive',
33
  'disjunctive' => 'Disjunctive',
34
  'slider' => 'Slider',
35
+ 'hierarchical' => 'Hierarchical (for categories only)',
36
  'other' => 'Other ->'
37
  );
38
 
app/code/community/Algolia/Algoliasearch/Helper/Algoliahelper.php CHANGED
@@ -2,28 +2,28 @@
2
 
3
  if (class_exists('AlgoliaSearch\Client', false) == false)
4
  {
5
- require_once 'AlgoliaSearch/Version.php';
6
- require_once 'AlgoliaSearch/AlgoliaException.php';
7
- require_once 'AlgoliaSearch/ClientContext.php';
8
- require_once 'AlgoliaSearch/Client.php';
9
- require_once 'AlgoliaSearch/Index.php';
10
  }
11
 
12
  class Algolia_Algoliasearch_Helper_Algoliahelper extends Mage_Core_Helper_Abstract
13
  {
14
  protected $client;
 
15
 
16
  public function __construct()
17
  {
 
18
  $this->resetCredentialsFromConfig();
19
  }
20
 
21
  public function resetCredentialsFromConfig()
22
  {
23
- $config = Mage::helper('algoliasearch/config');
24
-
25
- if ($config->getApplicationID() && $config->getAPIKey())
26
- $this->client = new \AlgoliaSearch\Client($config->getApplicationID(), $config->getAPIKey());
27
  }
28
 
29
  public function getIndex($name)
@@ -89,10 +89,58 @@ class Algolia_Algoliasearch_Helper_Algoliahelper extends Mage_Core_Helper_Abstra
89
  return $onlineSettings;
90
  }
91
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
92
  public function addObjects($objects, $index_name)
93
  {
 
 
94
  $index = $this->getIndex($index_name);
95
 
96
- $index->addObjects($objects);
 
 
 
97
  }
98
  }
2
 
3
  if (class_exists('AlgoliaSearch\Client', false) == false)
4
  {
5
+ require_once Mage::getBaseDir('lib').'/AlgoliaSearch/Version.php';
6
+ require_once Mage::getBaseDir('lib').'/AlgoliaSearch/AlgoliaException.php';
7
+ require_once Mage::getBaseDir('lib').'/AlgoliaSearch/ClientContext.php';
8
+ require_once Mage::getBaseDir('lib').'/AlgoliaSearch/Client.php';
9
+ require_once Mage::getBaseDir('lib').'/AlgoliaSearch/Index.php';
10
  }
11
 
12
  class Algolia_Algoliasearch_Helper_Algoliahelper extends Mage_Core_Helper_Abstract
13
  {
14
  protected $client;
15
+ private $config;
16
 
17
  public function __construct()
18
  {
19
+ $this->config = Mage::helper('algoliasearch/config');
20
  $this->resetCredentialsFromConfig();
21
  }
22
 
23
  public function resetCredentialsFromConfig()
24
  {
25
+ if ($this->config->getApplicationID() && $this->config->getAPIKey())
26
+ $this->client = new \AlgoliaSearch\Client($this->config->getApplicationID(), $this->config->getAPIKey());
 
 
27
  }
28
 
29
  public function getIndex($name)
89
  return $onlineSettings;
90
  }
91
 
92
+ public function handleTooBigRecords(&$objects, $index_name)
93
+ {
94
+ $long_attributes = array('description', 'short_description', 'meta_description', 'content');
95
+
96
+ $good_size = true;
97
+
98
+ $ids = array();
99
+
100
+ foreach ($objects as $key => &$object)
101
+ {
102
+ $size = mb_strlen(json_encode($object));
103
+
104
+ if ($size > 20000)
105
+ {
106
+ foreach ($long_attributes as $attribute)
107
+ {
108
+ if (isset($object[$attribute]))
109
+ {
110
+ unset($object[$attribute]);
111
+ $ids[$index_name.' objectID('.$object['objectID'].')'] = true;
112
+ $good_size = false;
113
+ }
114
+
115
+ }
116
+
117
+ $size = mb_strlen(json_encode($object));
118
+
119
+ if ($size > 20000)
120
+ {
121
+ unset($objects[$key]);
122
+ }
123
+ }
124
+ }
125
+
126
+ if (count($objects) <= 0)
127
+ return;
128
+
129
+ if ($good_size === false)
130
+ {
131
+ Mage::getSingleton('adminhtml/session')->addError('Algolia reindexing : You have some records ('.implode(',', array_keys($ids)).') that are too big. They have either been truncated or skipped');
132
+ }
133
+ }
134
+
135
  public function addObjects($objects, $index_name)
136
  {
137
+ $this->handleTooBigRecords($objects, $index_name);
138
+
139
  $index = $this->getIndex($index_name);
140
 
141
+ if ($this->config->isPartialUpdateEnabled())
142
+ $index->partialUpdateObjects($objects);
143
+ else
144
+ $index->addObjects($objects);
145
  }
146
  }
app/code/community/Algolia/Algoliasearch/Helper/Config.php CHANGED
@@ -17,6 +17,8 @@ class Algolia_Algoliasearch_Helper_Config extends Mage_Core_Helper_Abstract
17
  const XML_PATH_FACETS = 'algoliasearch/instant/facets';
18
  const XML_PATH_SORTING_INDICES = 'algoliasearch/instant/sorts';
19
 
 
 
20
  const XML_PATH_PRODUCT_ATTRIBUTES = 'algoliasearch/products/product_additional_attributes';
21
  const XML_PATH_PRODUCT_CUSTOM_RANKING = 'algoliasearch/products/custom_ranking_product_attributes';
22
  const XML_PATH_RESULTS_LIMIT = 'algoliasearch/products/results_limit';
@@ -45,6 +47,35 @@ class Algolia_Algoliasearch_Helper_Config extends Mage_Core_Helper_Abstract
45
  const XML_PATH_IS_ACTIVE = 'algoliasearch/queue/active';
46
  const XML_PATH_NUMBER_OF_ELEMENT_BY_PAGE = 'algoliasearch/queue/number_of_element_by_page';
47
  const XML_PATH_NUMBER_OF_JOB_TO_RUN = 'algoliasearch/queue/number_of_job_to_run';
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
48
 
49
  public function getNumberOfQuerySuggestions($storeId = null)
50
  {
@@ -167,8 +198,17 @@ class Algolia_Algoliasearch_Helper_Config extends Mage_Core_Helper_Abstract
167
 
168
  $attrs = unserialize(Mage::getStoreConfig(self::XML_PATH_SORTING_INDICES, $storeId));
169
 
 
 
 
 
 
 
 
 
 
170
  foreach ($attrs as &$attr)
171
- $attr['index_name'] = $product_helper->getIndexName($storeId).'_'.$attr['attribute'].'_'.$attr['sort'];
172
 
173
  if (is_array($attrs))
174
  return $attrs;
17
  const XML_PATH_FACETS = 'algoliasearch/instant/facets';
18
  const XML_PATH_SORTING_INDICES = 'algoliasearch/instant/sorts';
19
 
20
+ const XML_PATH_AUTOCOMPLETE_ADD_SECTIONS = 'algoliasearch/autocomplete/additional_sections';
21
+
22
  const XML_PATH_PRODUCT_ATTRIBUTES = 'algoliasearch/products/product_additional_attributes';
23
  const XML_PATH_PRODUCT_CUSTOM_RANKING = 'algoliasearch/products/custom_ranking_product_attributes';
24
  const XML_PATH_RESULTS_LIMIT = 'algoliasearch/products/results_limit';
47
  const XML_PATH_IS_ACTIVE = 'algoliasearch/queue/active';
48
  const XML_PATH_NUMBER_OF_ELEMENT_BY_PAGE = 'algoliasearch/queue/number_of_element_by_page';
49
  const XML_PATH_NUMBER_OF_JOB_TO_RUN = 'algoliasearch/queue/number_of_job_to_run';
50
+ const XML_PATH_NO_PROCESS = 'algoliasearch/queue/noprocess';
51
+
52
+ const XML_PATH_PARTIAL_UPDATES = 'algoliasearch/advanced/partial_update';
53
+ const XML_PATH_CUSTOMER_GROUPS_ENABLE = 'algoliasearch/advanced/customer_groups_enable';
54
+
55
+ public function noProcess($storeId = null)
56
+ {
57
+ return Mage::getStoreConfigFlag(self::XML_PATH_NO_PROCESS, $storeId);
58
+ }
59
+
60
+ public function isCustomerGroupsEnabled($storeId = null)
61
+ {
62
+ return Mage::getStoreConfigFlag(self::XML_PATH_CUSTOMER_GROUPS_ENABLE, $storeId);
63
+ }
64
+
65
+ public function isPartialUpdateEnabled($storeId = null)
66
+ {
67
+ return Mage::getStoreConfigFlag(self::XML_PATH_PARTIAL_UPDATES, $storeId);
68
+ }
69
+
70
+ public function getAutocompleteAdditionnalSections($storeId = null)
71
+ {
72
+ $attrs = unserialize(Mage::getStoreConfig(self::XML_PATH_AUTOCOMPLETE_ADD_SECTIONS, $storeId));
73
+
74
+ if (is_array($attrs))
75
+ return array_values($attrs);
76
+
77
+ return array();
78
+ }
79
 
80
  public function getNumberOfQuerySuggestions($storeId = null)
81
  {
198
 
199
  $attrs = unserialize(Mage::getStoreConfig(self::XML_PATH_SORTING_INDICES, $storeId));
200
 
201
+ $group_id = Mage::getSingleton('customer/session')->getCustomerGroupId();
202
+
203
+ $suffix_index_name = '';
204
+
205
+ if ($this->isCustomerGroupsEnabled($storeId))
206
+ {
207
+ $suffix_index_name = '_group_' . $group_id;
208
+ }
209
+
210
  foreach ($attrs as &$attr)
211
+ $attr['index_name'] = $product_helper->getIndexName($storeId).$suffix_index_name.'_'.$attr['attribute'].'_'.$attr['sort'];
212
 
213
  if (is_array($attrs))
214
  return $attrs;
app/code/community/Algolia/Algoliasearch/Helper/Data.php CHANGED
@@ -23,49 +23,82 @@ class Algolia_Algoliasearch_Helper_Data extends Mage_Core_Helper_Abstract
23
 
24
  public function __construct()
25
  {
26
- \AlgoliaSearch\Version::$custom_value = " Magento (1.3.5)";
27
 
28
- $this->algolia_helper = Mage::helper('algoliasearch/algoliahelper');
29
 
30
- $this->page_helper = Mage::helper('algoliasearch/entity_pagehelper');
31
- $this->category_helper = Mage::helper('algoliasearch/entity_categoryhelper');
32
- $this->product_helper = Mage::helper('algoliasearch/entity_producthelper');
33
- $this->suggestion_helper = Mage::helper('algoliasearch/entity_suggestionhelper');
 
34
 
35
- $this->config = Mage::helper('algoliasearch/config');
36
  }
37
 
38
  public function deleteProductsAndCategoriesStoreIndices($storeId = null)
39
  {
40
  $this->algolia_helper->deleteIndex($this->product_helper->getIndexName($storeId));
41
  $this->algolia_helper->deleteIndex($this->category_helper->getIndexName($storeId));
42
- }
43
 
44
- public function deletePagesStoreIndices($storeId = null)
45
- {
46
- $this->algolia_helper->deleteIndex($this->page_helper->getIndexName($storeId));
47
- }
 
 
 
 
48
 
49
- public function deleteSuggestionsStoreIndices($storeId = null)
50
- {
51
- $this->algolia_helper->deleteIndex($this->suggestion_helper->getIndexName($storeId));
52
  }
53
 
54
  public function saveConfigurationToAlgolia($storeId = null)
55
  {
56
  $this->algolia_helper->resetCredentialsFromConfig();
57
 
58
- $this->algolia_helper->setSettings($this->product_helper->getIndexName($storeId), $this->product_helper->getIndexSettings($storeId));
59
  $this->algolia_helper->setSettings($this->category_helper->getIndexName($storeId), $this->category_helper->getIndexSettings($storeId));
60
  $this->algolia_helper->setSettings($this->page_helper->getIndexName($storeId), $this->page_helper->getIndexSettings($storeId));
61
  $this->algolia_helper->setSettings($this->suggestion_helper->getIndexName($storeId), $this->suggestion_helper->getIndexSettings($storeId));
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
62
  }
63
 
64
  public function getSearchResult($query, $storeId)
65
  {
66
  $resultsLimit = $this->config->getResultsLimit($storeId);
67
 
68
- $answer = $this->algolia_helper->query($this->product_helper->getIndexName($storeId), $query, array(
 
 
 
 
 
 
 
 
 
 
 
 
69
  'hitsPerPage' => max(5, min($resultsLimit, 1000)), // retrieve all the hits (hard limit is 1000)
70
  'attributesToRetrieve' => 'objectID',
71
  'attributesToHighlight' => '',
@@ -95,6 +128,21 @@ class Algolia_Algoliasearch_Helper_Data extends Mage_Core_Helper_Abstract
95
  $index_name = $this->product_helper->getIndexName($store_id);
96
 
97
  $this->algolia_helper->deleteObjects($ids, $index_name);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
98
  }
99
  }
100
 
@@ -110,6 +158,25 @@ class Algolia_Algoliasearch_Helper_Data extends Mage_Core_Helper_Abstract
110
  }
111
  }
112
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
113
  public function rebuildStorePageIndex($storeId)
114
  {
115
  $index_name = $this->page_helper->getIndexName($storeId);
@@ -282,6 +349,23 @@ class Algolia_Algoliasearch_Helper_Data extends Mage_Core_Helper_Abstract
282
  unset($collection);
283
  }
284
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
285
  public function rebuildStoreProductIndexPage($storeId, $collectionDefault, $page, $pageSize)
286
  {
287
  set_time_limit(0);
@@ -294,20 +378,33 @@ class Algolia_Algoliasearch_Helper_Data extends Mage_Core_Helper_Abstract
294
 
295
  $index_name = $this->product_helper->getIndexName($storeId);
296
 
297
- $indexData = array();
298
 
299
- /** @var $product Mage_Catalog_Model_Product */
300
- foreach ($collection as $product)
 
 
 
 
 
 
 
 
 
 
 
301
  {
302
- $product->setStoreId($storeId);
 
 
303
 
304
- $json = $this->product_helper->getObject($product);
305
 
306
- array_push($indexData, $json);
307
- }
308
 
309
- if (count($indexData) > 0)
310
- $this->algolia_helper->addObjects($indexData, $index_name);
 
 
311
 
312
  unset($indexData);
313
 
23
 
24
  public function __construct()
25
  {
26
+ \AlgoliaSearch\Version::$custom_value = " Magento (1.4.0)";
27
 
28
+ $this->algolia_helper = Mage::helper('algoliasearch/algoliahelper');
29
 
30
+ $this->page_helper = Mage::helper('algoliasearch/entity_pagehelper');
31
+ $this->category_helper = Mage::helper('algoliasearch/entity_categoryhelper');
32
+ $this->product_helper = Mage::helper('algoliasearch/entity_producthelper');
33
+ $this->suggestion_helper = Mage::helper('algoliasearch/entity_suggestionhelper');
34
+ $this->additionalsections_helper = Mage::helper('algoliasearch/entity_additionalsectionshelper');
35
 
36
+ $this->config = Mage::helper('algoliasearch/config');
37
  }
38
 
39
  public function deleteProductsAndCategoriesStoreIndices($storeId = null)
40
  {
41
  $this->algolia_helper->deleteIndex($this->product_helper->getIndexName($storeId));
42
  $this->algolia_helper->deleteIndex($this->category_helper->getIndexName($storeId));
 
43
 
44
+ /**
45
+ * Handle deletetion for customer groups
46
+ */
47
+ if ($this->config->isCustomerGroupsEnabled($storeId))
48
+ {
49
+ foreach ($groups = Mage::getModel('customer/group')->getCollection() as $group)
50
+ {
51
+ $group_id = (int) $group->getData('customer_group_id');
52
 
53
+ $this->algolia_helper->deleteIndex($this->product_helper->getIndexName($storeId).'_group_'.$group_id);
54
+ }
55
+ }
56
  }
57
 
58
  public function saveConfigurationToAlgolia($storeId = null)
59
  {
60
  $this->algolia_helper->resetCredentialsFromConfig();
61
 
 
62
  $this->algolia_helper->setSettings($this->category_helper->getIndexName($storeId), $this->category_helper->getIndexSettings($storeId));
63
  $this->algolia_helper->setSettings($this->page_helper->getIndexName($storeId), $this->page_helper->getIndexSettings($storeId));
64
  $this->algolia_helper->setSettings($this->suggestion_helper->getIndexName($storeId), $this->suggestion_helper->getIndexSettings($storeId));
65
+
66
+ foreach ($this->config->getAutocompleteAdditionnalSections() as $section)
67
+ $this->algolia_helper->setSettings($this->additionalsections_helper->getIndexName($storeId).'_'.$section['attribute'], $this->additionalsections_helper->getIndexSettings($storeId));
68
+
69
+ $this->algolia_helper->setSettings($this->product_helper->getIndexName($storeId), $this->product_helper->getIndexSettings($storeId));
70
+
71
+ /**
72
+ * Handle deletetion for customer groups
73
+ */
74
+ if ($this->config->isCustomerGroupsEnabled($storeId))
75
+ {
76
+ foreach ($groups = Mage::getModel('customer/group')->getCollection() as $group)
77
+ {
78
+ $group_id = (int) $group->getData('customer_group_id');
79
+
80
+ $this->algolia_helper->setSettings($this->product_helper->getIndexName($storeId).'_group_'.$group_id, $this->product_helper->getIndexSettings($storeId, $group_id));
81
+ }
82
+ }
83
  }
84
 
85
  public function getSearchResult($query, $storeId)
86
  {
87
  $resultsLimit = $this->config->getResultsLimit($storeId);
88
 
89
+ $index_name = $this->product_helper->getIndexName($storeId);
90
+
91
+ /**
92
+ * Handle customer group
93
+ */
94
+ if ($this->config->isCustomerGroupsEnabled($storeId))
95
+ {
96
+ $group_id = Mage::getSingleton('customer/session')->getCustomerGroupId();
97
+
98
+ $index_name = $this->product_helper->getIndexName($storeId).'_group_'.$group_id;
99
+ }
100
+
101
+ $answer = $this->algolia_helper->query($index_name, $query, array(
102
  'hitsPerPage' => max(5, min($resultsLimit, 1000)), // retrieve all the hits (hard limit is 1000)
103
  'attributesToRetrieve' => 'objectID',
104
  'attributesToHighlight' => '',
128
  $index_name = $this->product_helper->getIndexName($store_id);
129
 
130
  $this->algolia_helper->deleteObjects($ids, $index_name);
131
+
132
+ /**
133
+ * Group Deleting
134
+ */
135
+ if ($this->config->isCustomerGroupsEnabled($store_id))
136
+ {
137
+ foreach ($groups = Mage::getModel('customer/group')->getCollection() as $group)
138
+ {
139
+ $group_id = (int) $group->getData('customer_group_id');
140
+
141
+ $index_name = $this->product_helper->getIndexName($store_id).'_group_'.$group_id;
142
+
143
+ $this->algolia_helper->deleteObjects($ids, $index_name);
144
+ }
145
+ }
146
  }
147
  }
148
 
158
  }
159
  }
160
 
161
+ public function rebuildStoreAdditionalSectionsIndex($storeId)
162
+ {
163
+ $additionnal_sections = $this->config->getAutocompleteAdditionnalSections();
164
+
165
+ foreach ($additionnal_sections as $section)
166
+ {
167
+ $index_name = $this->additionalsections_helper->getIndexName($storeId).'_'.$section['attribute'];
168
+
169
+ $attribute_values = $this->additionalsections_helper->getAttributeValues($storeId, $section);
170
+
171
+ foreach (array_chunk($attribute_values, 100) as $chunk)
172
+ $this->algolia_helper->addObjects($chunk, $index_name.'_tmp');
173
+
174
+ $this->algolia_helper->moveIndex($index_name.'_tmp', $index_name);
175
+
176
+ $this->algolia_helper->setSettings($index_name, $this->additionalsections_helper->getIndexSettings($storeId));
177
+ }
178
+ }
179
+
180
  public function rebuildStorePageIndex($storeId)
181
  {
182
  $index_name = $this->page_helper->getIndexName($storeId);
349
  unset($collection);
350
  }
351
 
352
+ private function getProductsRecords($storeId, $collection, $groupId = null)
353
+ {
354
+ $indexData = array();
355
+
356
+ /** @var $product Mage_Catalog_Model_Product */
357
+ foreach ($collection as $product)
358
+ {
359
+ $product->setStoreId($storeId);
360
+
361
+ $json = $this->product_helper->getObject($product, $groupId);
362
+
363
+ array_push($indexData, $json);
364
+ }
365
+
366
+ return $indexData;
367
+ }
368
+
369
  public function rebuildStoreProductIndexPage($storeId, $collectionDefault, $page, $pageSize)
370
  {
371
  set_time_limit(0);
378
 
379
  $index_name = $this->product_helper->getIndexName($storeId);
380
 
 
381
 
382
+ /**
383
+ * Normal Indexing
384
+ */
385
+ $indexData = $this->getProductsRecords($storeId, $collection, null);
386
+
387
+ if (count($indexData) > 0)
388
+ $this->algolia_helper->addObjects($indexData, $index_name);
389
+
390
+
391
+ /**
392
+ * Group Indexing
393
+ */
394
+ if ($this->config->isCustomerGroupsEnabled($storeId))
395
  {
396
+ foreach ($groups = Mage::getModel('customer/group')->getCollection() as $group)
397
+ {
398
+ $group_id = (int) $group->getData('customer_group_id');
399
 
400
+ $index_name = $this->product_helper->getIndexName($storeId).'_group_'.$group_id;
401
 
402
+ $indexData = $this->getProductsRecords($storeId, $collection, $group_id);
 
403
 
404
+ if (count($indexData) > 0)
405
+ $this->algolia_helper->addObjects($indexData, $index_name);
406
+ }
407
+ }
408
 
409
  unset($indexData);
410
 
app/code/community/Algolia/Algoliasearch/Helper/Entity/Additionalsectionshelper.php ADDED
@@ -0,0 +1,66 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+
3
+ class Algolia_Algoliasearch_Helper_Entity_Additionalsectionshelper extends Algolia_Algoliasearch_Helper_Entity_Helper
4
+ {
5
+ protected function getIndexNameSuffix()
6
+ {
7
+ return '_section';
8
+ }
9
+
10
+ public function getIndexSettings($storeId)
11
+ {
12
+ return array(
13
+ 'attributesToIndex' => array('value'),
14
+ );
15
+ }
16
+
17
+ public function getAttributeValues($storeId, $section)
18
+ {
19
+ $attributeCode = $section['attribute'];
20
+
21
+ $products = Mage::getResourceModel('catalog/product_collection')
22
+ ->addStoreFilter($storeId)
23
+ ->addAttributeToFilter('visibility', array('in' => Mage::getSingleton('catalog/product_visibility')->getVisibleInSearchIds()))
24
+ ->addAttributeToFilter($attributeCode, array('notnull' => true))
25
+ ->addAttributeToFilter($attributeCode, array('neq' => ''))
26
+ ->addAttributeToSelect($attributeCode);
27
+
28
+ $usedAttributeValues = array_unique($products->getColumnValues($attributeCode));
29
+
30
+ $attributeModel = Mage::getSingleton('eav/config')
31
+ ->getAttribute('catalog_product', $attributeCode)
32
+ ->setStoreId($storeId);
33
+
34
+ $values = $attributeModel->getSource()->getOptionText(
35
+ implode(',', $usedAttributeValues)
36
+ );
37
+
38
+ if (! $values || count($values) == 0)
39
+ {
40
+ $values = array_unique($products->getColumnValues($attributeCode));
41
+ }
42
+
43
+ if ($values && is_array($values) == false)
44
+ {
45
+ $values = array($values);
46
+ }
47
+
48
+ $values = array_map(function ($value) use ($section) {
49
+
50
+ $record = array(
51
+ 'objectID' => $value,
52
+ 'value' => $value
53
+ );
54
+
55
+ $transport = new Varien_Object($record);
56
+
57
+ Mage::dispatchEvent('algolia_additional_section_item_index_before', array('section' => $section, 'record' => $transport));
58
+
59
+ $record = $transport->getData();
60
+
61
+ return $record;
62
+ }, $values);
63
+
64
+ return $values;
65
+ }
66
+ }
app/code/community/Algolia/Algoliasearch/Helper/Entity/Producthelper.php CHANGED
@@ -11,7 +11,7 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
11
  return '_products';
12
  }
13
 
14
- public function getAllAttributes()
15
  {
16
  if (is_null(self::$_productAttributes))
17
  {
@@ -36,13 +36,18 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
36
 
37
  foreach ($productAttributes as $attributeCode)
38
  self::$_productAttributes[$attributeCode] = $config->getAttribute('catalog_category', $attributeCode)->getFrontendLabel();
39
-
40
- uksort(self::$_productAttributes, function ($a, $b) {
41
- return strcmp($a, $b);
42
- });
43
  }
44
 
45
- return self::$_productAttributes;
 
 
 
 
 
 
 
 
 
46
  }
47
 
48
  protected function isAttributeEnabled($additionalAttributes, $attr_name)
@@ -96,12 +101,22 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
96
  return $products;
97
  }
98
 
99
- public function getIndexSettings($storeId)
100
  {
101
  $attributesToIndex = array();
102
  $unretrievableAttributes = array();
103
  $attributesForFaceting = array();
104
 
 
 
 
 
 
 
 
 
 
 
105
  foreach ($this->config->getProductAdditionalAttributes($storeId) as $attribute)
106
  {
107
  if ($attribute['searchable'] == '1')
@@ -142,13 +157,11 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
142
  Mage::dispatchEvent('algolia_index_settings_prepare', array('store_id' => $storeId, 'index_settings' => $transport));
143
  $indexSettings = $transport->getData();
144
 
145
- $mergeSettings = $this->algolia_helper->mergeSettings($this->getIndexName($storeId), $indexSettings);
146
 
147
  /**
148
  * Handle Slaves
149
  */
150
-
151
-
152
  $sorting_indices = $this->config->getSortingIndices();
153
 
154
  if (count($sorting_indices) > 0)
@@ -156,15 +169,15 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
156
  $slaves = array();
157
 
158
  foreach ($sorting_indices as $values)
159
- $slaves[] = $this->getIndexName($storeId).'_'.$values['attribute'].'_'.$values['sort'];
160
 
161
- $this->algolia_helper->setSettings($this->getIndexName($storeId), array('slaves' => $slaves));
162
 
163
  foreach ($sorting_indices as $values)
164
  {
165
  $mergeSettings['ranking'] = array($values['sort'].'('.$values['attribute'].')', 'typo', 'geo', 'words', 'proximity', 'attribute', 'exact', 'custom');
166
 
167
- $this->algolia_helper->setSettings($this->getIndexName($storeId).'_'.$values['attribute'].'_'.$values['sort'], $mergeSettings);
168
  }
169
  }
170
 
@@ -173,7 +186,7 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
173
  return $mergeSettings;
174
  }
175
 
176
- public function getObject(Mage_Catalog_Model_Product $product)
177
  {
178
  $defaultData = array();
179
 
@@ -196,6 +209,22 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
196
 
197
  $special_price = $product->getFinalPrice();
198
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
199
  if ($special_price != $customData['price'])
200
  {
201
  $customData['special_price_from_date'] = strtotime($product->getSpecialFromDate());
@@ -246,10 +275,30 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
246
 
247
  $categories_with_path = array_intersect_key($categories_with_path, array_unique(array_map('serialize', $categories_with_path)));
248
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
249
  foreach ($categories_with_path as &$category)
250
  $category = implode(' /// ',$category);
251
 
252
- $customData['categories'] = array_values($categories_with_path);
253
 
254
  $customData['categories_without_path'] = $categories;
255
 
@@ -310,7 +359,6 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
310
  $customData['max_formated'] = Mage::helper('core')->formatPrice($max, false);
311
  $customData['min_with_tax_formated'] = Mage::helper('core')->formatPrice($min_with_tax, false);
312
  $customData['max_with_tax_formated'] = Mage::helper('core')->formatPrice($max_with_tax, false);
313
-
314
  }
315
 
316
  if (false === isset($defaultData['in_stock']))
@@ -378,6 +426,8 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
378
 
379
  if ($attribute_ressource)
380
  {
 
 
381
  if ($value === null)
382
  {
383
  /** Get values as array in children */
@@ -415,7 +465,10 @@ class Algolia_Algoliasearch_Helper_Entity_Producthelper extends Algolia_Algolias
415
  if ($value_text)
416
  $value = $value_text;
417
  else
 
 
418
  $value = $attribute_ressource->getFrontend()->getValue($product);
 
419
 
420
  if ($value)
421
  {
11
  return '_products';
12
  }
13
 
14
+ public function getAllAttributes($add_empty_row = false)
15
  {
16
  if (is_null(self::$_productAttributes))
17
  {
36
 
37
  foreach ($productAttributes as $attributeCode)
38
  self::$_productAttributes[$attributeCode] = $config->getAttribute('catalog_category', $attributeCode)->getFrontendLabel();
 
 
 
 
39
  }
40
 
41
+ $attributes = self::$_productAttributes;
42
+
43
+ if ($add_empty_row === true)
44
+ $attributes[''] = '';
45
+
46
+ uksort($attributes, function ($a, $b) {
47
+ return strcmp($a, $b);
48
+ });
49
+
50
+ return $attributes;
51
  }
52
 
53
  protected function isAttributeEnabled($additionalAttributes, $attr_name)
101
  return $products;
102
  }
103
 
104
+ public function getIndexSettings($storeId, $group_id = null)
105
  {
106
  $attributesToIndex = array();
107
  $unretrievableAttributes = array();
108
  $attributesForFaceting = array();
109
 
110
+ $suffix_index_name = '';
111
+
112
+ /**
113
+ * Handle grouping
114
+ */
115
+ if ($group_id !== null)
116
+ {
117
+ $suffix_index_name = '_group_'.$group_id;
118
+ }
119
+
120
  foreach ($this->config->getProductAdditionalAttributes($storeId) as $attribute)
121
  {
122
  if ($attribute['searchable'] == '1')
157
  Mage::dispatchEvent('algolia_index_settings_prepare', array('store_id' => $storeId, 'index_settings' => $transport));
158
  $indexSettings = $transport->getData();
159
 
160
+ $mergeSettings = $this->algolia_helper->mergeSettings($this->getIndexName($storeId).$suffix_index_name, $indexSettings);
161
 
162
  /**
163
  * Handle Slaves
164
  */
 
 
165
  $sorting_indices = $this->config->getSortingIndices();
166
 
167
  if (count($sorting_indices) > 0)
169
  $slaves = array();
170
 
171
  foreach ($sorting_indices as $values)
172
+ $slaves[] = $this->getIndexName($storeId).$suffix_index_name.'_'.$values['attribute'].'_'.$values['sort'];
173
 
174
+ $this->algolia_helper->setSettings($this->getIndexName($storeId).$suffix_index_name, array('slaves' => $slaves));
175
 
176
  foreach ($sorting_indices as $values)
177
  {
178
  $mergeSettings['ranking'] = array($values['sort'].'('.$values['attribute'].')', 'typo', 'geo', 'words', 'proximity', 'attribute', 'exact', 'custom');
179
 
180
+ $this->algolia_helper->setSettings($this->getIndexName($storeId).$suffix_index_name.'_'.$values['attribute'].'_'.$values['sort'], $mergeSettings);
181
  }
182
  }
183
 
186
  return $mergeSettings;
187
  }
188
 
189
+ public function getObject(Mage_Catalog_Model_Product $product, $group_id = null)
190
  {
191
  $defaultData = array();
192
 
209
 
210
  $special_price = $product->getFinalPrice();
211
 
212
+ /**
213
+ * Handle group price
214
+ */
215
+ if ($group_id !== null)
216
+ {
217
+ $discounted_price = Mage::getResourceModel('catalogrule/rule')->getRulePrice(
218
+ Mage::app()->getLocale()->storeTimeStamp($product->getStoreId()),
219
+ Mage::app()->getStore($product->getStoreId())->getWebsiteId(),
220
+ $group_id,
221
+ $product->getId());
222
+
223
+ if ($discounted_price !== false)
224
+ $special_price = $discounted_price;
225
+ }
226
+
227
+
228
  if ($special_price != $customData['price'])
229
  {
230
  $customData['special_price_from_date'] = strtotime($product->getSpecialFromDate());
275
 
276
  $categories_with_path = array_intersect_key($categories_with_path, array_unique(array_map('serialize', $categories_with_path)));
277
 
278
+ $categories_hierarchical = array();
279
+
280
+ $level_name = 'level';
281
+
282
+ foreach ($categories_with_path as $category)
283
+ {
284
+ for ($i = 0; $i < count($category); $i++)
285
+ {
286
+ if (isset($categories_hierarchical[$level_name.$i]) === false)
287
+ $categories_hierarchical[$level_name.$i] = array();
288
+
289
+ $categories_hierarchical[$level_name.$i][] = implode(' /// ', array_slice($category, 0, $i + 1));
290
+ }
291
+ }
292
+
293
+ foreach ($categories_hierarchical as &$level)
294
+ {
295
+ $level = array_unique($level);
296
+ }
297
+
298
  foreach ($categories_with_path as &$category)
299
  $category = implode(' /// ',$category);
300
 
301
+ $customData['categories'] = $categories_hierarchical;//array_values($categories_with_path);
302
 
303
  $customData['categories_without_path'] = $categories;
304
 
359
  $customData['max_formated'] = Mage::helper('core')->formatPrice($max, false);
360
  $customData['min_with_tax_formated'] = Mage::helper('core')->formatPrice($min_with_tax, false);
361
  $customData['max_with_tax_formated'] = Mage::helper('core')->formatPrice($max_with_tax, false);
 
362
  }
363
 
364
  if (false === isset($defaultData['in_stock']))
426
 
427
  if ($attribute_ressource)
428
  {
429
+ $attribute_ressource = $attribute_ressource->setStoreId($product->getStoreId());
430
+
431
  if ($value === null)
432
  {
433
  /** Get values as array in children */
465
  if ($value_text)
466
  $value = $value_text;
467
  else
468
+ {
469
+ $attribute_ressource = $attribute_ressource->setStoreId($product->getStoreId());
470
  $value = $attribute_ressource->getFrontend()->getValue($product);
471
+ }
472
 
473
  if ($value)
474
  {
app/code/community/Algolia/Algoliasearch/Model/Indexer/Algolia.php CHANGED
@@ -8,6 +8,8 @@ class Algolia_Algoliasearch_Model_Indexer_Algolia extends Mage_Index_Model_Index
8
  private $engine;
9
  private $config;
10
 
 
 
11
  public function __construct()
12
  {
13
  parent::__construct();
@@ -114,6 +116,16 @@ class Algolia_Algoliasearch_Model_Indexer_Algolia extends Mage_Index_Model_Index
114
  else
115
  {
116
  $event->addNewData('catalogsearch_update_product_id', $product->getId());
 
 
 
 
 
 
 
 
 
 
117
  }
118
 
119
  break;
@@ -330,16 +342,6 @@ class Algolia_Algoliasearch_Model_Indexer_Algolia extends Mage_Index_Model_Index
330
 
331
  $this->engine
332
  ->rebuildProductIndex(null, $productIds);
333
-
334
- /*
335
- * Change indexer status as need to reindex related categories to update product count.
336
- * It's low priority so no need to automatically reindex all related categories after deleting each product.
337
- * Do not reindex all if affected categories are given or product count is not indexed.
338
- */
339
- if ( ! isset($data['catalogsearch_update_category_id'])) {
340
- $process = $event->getProcess();
341
- $process->changeStatus(Mage_Index_Model_Process::STATUS_REQUIRE_REINDEX);
342
- }
343
  }
344
 
345
  /*
8
  private $engine;
9
  private $config;
10
 
11
+ public static $product_categories = array();
12
+
13
  public function __construct()
14
  {
15
  parent::__construct();
116
  else
117
  {
118
  $event->addNewData('catalogsearch_update_product_id', $product->getId());
119
+
120
+ if (isset(static::$product_categories[$product->getId()]))
121
+ {
122
+ $oldCategories = static::$product_categories[$product->getId()];
123
+ $newCategories = $product->getCategoryIds();
124
+
125
+ $diffCategories = array_merge(array_diff($oldCategories, $newCategories), array_diff($newCategories, $oldCategories));
126
+
127
+ $event->addNewData('catalogsearch_update_category_id', $diffCategories);
128
+ }
129
  }
130
 
131
  break;
342
 
343
  $this->engine
344
  ->rebuildProductIndex(null, $productIds);
 
 
 
 
 
 
 
 
 
 
345
  }
346
 
347
  /*
app/code/community/Algolia/Algoliasearch/Model/Indexer/Algoliaadditionalsections.php ADDED
@@ -0,0 +1,76 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+
3
+ class Algolia_Algoliasearch_Model_Indexer_Algoliaadditionalsections extends Mage_Index_Model_Indexer_Abstract
4
+ {
5
+ const EVENT_MATCH_RESULT_KEY = 'algoliasearch_match_result';
6
+
7
+ /** @var Algolia_Algoliasearch_Model_Resource_Engine */
8
+ private $engine;
9
+ private $config;
10
+
11
+ public function __construct()
12
+ {
13
+ parent::__construct();
14
+
15
+ $this->engine = new Algolia_Algoliasearch_Model_Resource_Engine();
16
+ $this->config = Mage::helper('algoliasearch/config');
17
+ }
18
+
19
+ protected $_matchedEntities = array();
20
+
21
+ protected function _getResource()
22
+ {
23
+ return Mage::getResourceSingleton('catalogsearch/indexer_fulltext');
24
+ }
25
+
26
+ public function getName()
27
+ {
28
+ return Mage::helper('algoliasearch')->__('Algolia Search Additional autocomplete sections');
29
+ }
30
+
31
+ public function getDescription()
32
+ {
33
+ return Mage::helper('algoliasearch')->__('Rebuild additional sections.
34
+ Please enable the queueing system to do it asynchronously (CRON) if you have a lot of products in System > Configuration > Algolia Search > Queue configuration');
35
+ }
36
+
37
+ public function matchEvent(Mage_Index_Model_Event $event)
38
+ {
39
+ return false;
40
+ }
41
+
42
+ protected function _registerEvent(Mage_Index_Model_Event $event)
43
+ {
44
+ return $this;
45
+ }
46
+
47
+ protected function _registerCatalogProductEvent(Mage_Index_Model_Event $event)
48
+ {
49
+ return $this;
50
+ }
51
+
52
+ protected function _registerCatalogCategoryEvent(Mage_Index_Model_Event $event)
53
+ {
54
+ return $this;
55
+ }
56
+
57
+ protected function _processEvent(Mage_Index_Model_Event $event)
58
+ {
59
+ }
60
+
61
+ /**
62
+ * Rebuild all index data
63
+ */
64
+ public function reindexAll()
65
+ {
66
+ if (! $this->config->getApplicationID() || ! $this->config->getAPIKey() || ! $this->config->getSearchOnlyAPIKey())
67
+ {
68
+ Mage::getSingleton('adminhtml/session')->addError('Algolia reindexing failed: You need to configure your Algolia credentials in System > Configuration > Algolia Search.');
69
+ return;
70
+ }
71
+
72
+ $this->engine->rebuildAdditionalSections();
73
+
74
+ return $this;
75
+ }
76
+ }
app/code/community/Algolia/Algoliasearch/Model/Observer.php CHANGED
@@ -45,25 +45,53 @@ class Algolia_Algoliasearch_Model_Observer
45
  return $this;
46
  }
47
 
48
- public function deleteProductsAndCategoriesStoreIndices(Varien_Object $event)
49
  {
50
- $storeId = $event->getStoreId();
 
51
 
52
- $this->helper->deleteProductsAndCategoriesStoreIndices($storeId);
53
  }
54
 
55
- public function deletePagesStoreIndices(Varien_Object $event)
56
  {
57
- $storeId = $event->getStoreId();
 
 
 
58
 
59
- $this->helper->deletePagesStoreIndices($storeId);
 
60
  }
61
 
62
- public function deleteSuggestionsStoreIndices(Varien_Object $event)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
63
  {
64
  $storeId = $event->getStoreId();
65
 
66
- $this->helper->deleteSuggestionsStoreIndices($storeId);
67
  }
68
 
69
  public function removeProducts(Varien_Object $event)
@@ -82,6 +110,13 @@ class Algolia_Algoliasearch_Model_Observer
82
  $this->helper->removeCategories($category_ids, $storeId);
83
  }
84
 
 
 
 
 
 
 
 
85
  public function rebuildPageIndex(Varien_Object $event)
86
  {
87
  $storeId = $event->getStoreId();
@@ -175,40 +210,4 @@ class Algolia_Algoliasearch_Model_Observer
175
 
176
  return $this;
177
  }
178
-
179
- /**
180
- * Catch request if it is a category page
181
- */
182
- public function controllerFrontInitBefore(Varien_Event_Observer $observer)
183
- {
184
- if ($this->config->replaceCategories() == false)
185
- return;
186
- if ($this->config->isInstantEnabled() == false)
187
- return;
188
-
189
- if (Mage::app()->getRequest()->getControllerName() == 'category' && Mage::app()->getRequest()->getParam('category') == null)
190
- {
191
- $category = Mage::registry('current_category');
192
-
193
- $category->getUrlInstance()->setStore(Mage::app()->getStore()->getStoreId());
194
-
195
- $path = '';
196
-
197
- foreach ($category->getPathIds() as $treeCategoryId) {
198
- if ($path != '') {
199
- $path .= ' /// ';
200
- }
201
-
202
- $path .= $this->product_helper->getCategoryName($treeCategoryId, Mage::app()->getStore()->getStoreId());
203
- }
204
-
205
- $indexName = $this->product_helper->getIndexName(Mage::app()->getStore()->getStoreId());
206
-
207
- $url = Mage::app()->getRequest()->getOriginalPathInfo().'?category=1#q=&page=0&refinements=%5B%7B%22categories%22%3A%5B%22'.$path.'%22%5D%7D%5D&numerics_refinements=%7B%7D&index_name=%22'.$indexName.'%22';
208
-
209
- header('Location: '.$url);
210
-
211
- die();
212
- }
213
- }
214
  }
45
  return $this;
46
  }
47
 
48
+ public function saveProduct(Varien_Event_Observer $observer)
49
  {
50
+ $product = $observer->getDataObject();
51
+ $product = Mage::getModel('catalog/product')->load($product->getId());
52
 
53
+ Algolia_Algoliasearch_Model_Indexer_Algolia::$product_categories[$product->getId()] = $product->getCategoryIds();
54
  }
55
 
56
+ private function updateStock($product_id)
57
  {
58
+ foreach (Mage::app()->getStores() as $storeId => $store)
59
+ {
60
+ if ( ! $store->getIsActive())
61
+ continue;
62
 
63
+ $this->helper->rebuildStoreProductIndex($storeId, array($product_id));
64
+ }
65
  }
66
 
67
+ public function catalogInventorySave(Varien_Event_Observer $observer)
68
+ {
69
+ $product = $observer->getItem();
70
+
71
+ $this->updateStock($product->getProductId());
72
+ }
73
+
74
+ public function quoteInventory(Varien_Event_Observer $observer)
75
+ {
76
+ $quote = $observer->getEvent()->getQuote();
77
+
78
+ foreach ($quote->getAllItems() as $product)
79
+ $this->updateStock($product->getProductId());
80
+ }
81
+
82
+ public function refundOrderInventory(Varien_Event_Observer $observer)
83
+ {
84
+ $creditmemo = $observer->getEvent()->getCreditmemo();
85
+
86
+ foreach ($creditmemo->getAllItems() as $product)
87
+ $this->updateStock($product->getProductId());
88
+ }
89
+
90
+ public function deleteProductsAndCategoriesStoreIndices(Varien_Object $event)
91
  {
92
  $storeId = $event->getStoreId();
93
 
94
+ $this->helper->deleteProductsAndCategoriesStoreIndices($storeId);
95
  }
96
 
97
  public function removeProducts(Varien_Object $event)
110
  $this->helper->removeCategories($category_ids, $storeId);
111
  }
112
 
113
+ public function rebuildAdditionalSectionsIndex(Varien_Object $event)
114
+ {
115
+ $storeId = $event->getStoreId();
116
+
117
+ $this->helper->rebuildStoreAdditionalSectionsIndex($storeId);
118
+ }
119
+
120
  public function rebuildPageIndex(Varien_Object $event)
121
  {
122
  $storeId = $event->getStoreId();
210
 
211
  return $this;
212
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
213
  }
app/code/community/Algolia/Algoliasearch/Model/Queue.php CHANGED
@@ -35,6 +35,9 @@ class Algolia_Algoliasearch_Model_Queue
35
  if ( ! $this->config->isQueueActive())
36
  return;
37
 
 
 
 
38
  $this->run($this->config->getNumberOfJobToRun());
39
  }
40
 
35
  if ( ! $this->config->isQueueActive())
36
  return;
37
 
38
+ if ($this->config->noProcess())
39
+ return;
40
+
41
  $this->run($this->config->getNumberOfJobToRun());
42
  }
43
 
app/code/community/Algolia/Algoliasearch/Model/Resource/Engine.php CHANGED
@@ -99,6 +99,14 @@ class Algolia_Algoliasearch_Model_Resource_Engine extends Mage_CatalogSearch_Mod
99
  }
100
  }
101
 
 
 
 
 
 
 
 
 
102
  public function rebuildSuggestions()
103
  {
104
  foreach (Mage::app()->getStores() as $store)
99
  }
100
  }
101
 
102
+ public function rebuildAdditionalSections()
103
+ {
104
+ foreach (Mage::app()->getStores() as $store)
105
+ {
106
+ $this->addToQueue('algoliasearch/observer', 'rebuildAdditionalSectionsIndex', array('store_id' => $store->getId()), $this->config->getQueueMaxRetries());
107
+ }
108
+ }
109
+
110
  public function rebuildSuggestions()
111
  {
112
  foreach (Mage::app()->getStores() as $store)
app/code/community/Algolia/Algoliasearch/Model/Resource/Fulltext/Collection.php CHANGED
@@ -7,19 +7,6 @@ class Algolia_Algoliasearch_Model_Resource_Fulltext_Collection extends Mage_Cata
7
  */
8
  public function addSearchFilter($query)
9
  {
10
- $config = Mage::helper('algoliasearch/config');
11
-
12
- if ($config->isInstantEnabled() && Mage::app()->getRequest()->getParam('instant') == null)
13
- {
14
- $product_helper = Mage::helper('algoliasearch/entity_producthelper');
15
-
16
- $url = Mage::getBaseUrl().'catalogsearch/result/?q='.$query.'&instant=1#q='.$query.'&page=0&refinements=%5B%5D&numerics_refinements=%7B%7D&index_name=%22'.$product_helper->getIndexName().'%22';
17
-
18
- header('Location: '.$url);
19
-
20
- die();
21
- }
22
-
23
  $data = Mage::helper('algoliasearch')->getSearchResult($query, Mage::app()->getStore()->getId());
24
 
25
  $sortedIds = array_reverse(array_keys($data));
7
  */
8
  public function addSearchFilter($query)
9
  {
 
 
 
 
 
 
 
 
 
 
 
 
 
10
  $data = Mage::helper('algoliasearch')->getSearchResult($query, Mage::app()->getStore()->getId());
11
 
12
  $sortedIds = array_reverse(array_keys($data));
app/code/community/Algolia/Algoliasearch/etc/config.xml CHANGED
@@ -72,14 +72,56 @@
72
  </algolia_search>
73
  </observers>
74
  </admin_system_config_changed_section_algoliasearch>
75
- <controller_action_layout_generate_blocks_before>
 
76
  <observers>
77
- <algolia_search>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
78
  <class>algoliasearch/observer</class>
79
- <method>controllerFrontInitBefore</method>
80
- </algolia_search >
81
  </observers>
82
- </controller_action_layout_generate_blocks_before>
83
  </events>
84
  <resources>
85
  <algoliasearch_setup>
@@ -99,6 +141,9 @@
99
  <search_indexer_suggest>
100
  <model>algoliasearch/indexer_algoliasuggestions</model>
101
  </search_indexer_suggest>
 
 
 
102
  </indexer>
103
  </index>
104
  </global>
@@ -132,15 +177,18 @@
132
  <instant>
133
  <replace_categories>1</replace_categories>
134
  <instant_selector>.main</instant_selector>
135
- <facets>a:2:{s:18:"_1432907948596_596";a:4:{s:9:"attribute";s:14:"price_with_tax";s:4:"type";s:6:"slider";s:10:"other_type";s:0:"";s:5:"label";s:5:"Price";}s:18:"_1432907963376_376";a:4:{s:9:"attribute";s:10:"categories";s:4:"type";s:11:"conjunctive";s:10:"other_type";s:0:"";s:5:"label";s:10:"Categories";}}</facets>
136
  <sorts>a:3:{s:18:"_1432908018844_844";a:3:{s:9:"attribute";s:14:"price_with_tax";s:4:"sort";s:3:"asc";s:5:"label";s:12:"Lowest price";}s:18:"_1432908022539_539";a:3:{s:9:"attribute";s:14:"price_with_tax";s:4:"sort";s:4:"desc";s:5:"label";s:13:"Highest price";}s:18:"_1433768597454_454";a:3:{s:9:"attribute";s:10:"created_at";s:4:"sort";s:4:"desc";s:5:"label";s:12:"Newest first";}}</sorts>
137
  </instant>
 
 
 
138
  <categories>
139
  <category_additional_attributes2>a:7:{s:18:"_1427960339954_954";a:4:{s:9:"attribute";s:4:"name";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427960354437_437";a:4:{s:9:"attribute";s:4:"path";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961004989_989";a:4:{s:9:"attribute";s:11:"description";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:9:"unordered";}s:18:"_1427961205511_511";a:4:{s:9:"attribute";s:10:"meta_title";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961216134_134";a:4:{s:9:"attribute";s:13:"meta_keywords";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961216916_916";a:4:{s:9:"attribute";s:16:"meta_description";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:9:"unordered";}s:18:"_1427977778338_338";a:4:{s:9:"attribute";s:13:"product_count";s:10:"searchable";s:1:"0";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}}</category_additional_attributes2>
140
  <custom_ranking_category_attributes>a:1:{s:18:"_1427961035192_192";a:2:{s:9:"attribute";s:13:"product_count";s:5:"order";s:4:"desc";}}</custom_ranking_category_attributes>
141
  </categories>
142
  <suggestions>
143
- <min_popularity>4</min_popularity>
144
  <min_number_of_results>2</min_number_of_results>
145
  </suggestions>
146
  <relevance>
@@ -161,7 +209,11 @@
161
  <retries>3</retries>
162
  <number_of_element_by_page>100</number_of_element_by_page>
163
  <number_of_job_to_run>300</number_of_job_to_run>
 
164
  </queue>
 
 
 
165
  </algoliasearch>
166
  </default>
167
  </config>
72
  </algolia_search>
73
  </observers>
74
  </admin_system_config_changed_section_algoliasearch>
75
+
76
+ <catalog_product_save_before>
77
  <observers>
78
+ <algolia_stockupdate>
79
+ <class>algoliasearch/observer</class>
80
+ <method>saveProduct</method>
81
+ </algolia_stockupdate>
82
+ </observers>
83
+ </catalog_product_save_before>
84
+
85
+ <cataloginventory_stock_item_save_commit_after>
86
+ <observers>
87
+ <algolia_stockupdate>
88
+ <class>algoliasearch/observer</class>
89
+ <method>catalogInventorySave</method>
90
+ </algolia_stockupdate>
91
+ </observers>
92
+ </cataloginventory_stock_item_save_commit_after>
93
+ <sales_model_service_quote_submit_before>
94
+ <observers>
95
+ <algolia_stockupdate>
96
+ <class>algoliasearch/observer</class>
97
+ <method>quoteInventory</method>
98
+ </algolia_stockupdate>
99
+ </observers>
100
+ </sales_model_service_quote_submit_before>
101
+ <sales_model_service_quote_submit_failure>
102
+ <observers>
103
+ <algolia_stockupdate>
104
+ <class>algoliasearch/observer</class>
105
+ <method>quoteInventory</method>
106
+ </algolia_stockupdate>
107
+ </observers>
108
+ </sales_model_service_quote_submit_failure>
109
+ <sales_order_item_cancel>
110
+ <observers>
111
+ <algolia_stockupdate>
112
+ <class>algoliasearch/observer</class>
113
+ <method>catalogInventorySave</method>
114
+ </algolia_stockupdate>
115
+ </observers>
116
+ </sales_order_item_cancel>
117
+ <sales_order_creditmemo_save_after>
118
+ <observers>
119
+ <algolia_stockupdate>
120
  <class>algoliasearch/observer</class>
121
+ <method>refundOrderInventory</method>
122
+ </algolia_stockupdate>
123
  </observers>
124
+ </sales_order_creditmemo_save_after>
125
  </events>
126
  <resources>
127
  <algoliasearch_setup>
141
  <search_indexer_suggest>
142
  <model>algoliasearch/indexer_algoliasuggestions</model>
143
  </search_indexer_suggest>
144
+ <search_indexer_addsections>
145
+ <model>algoliasearch/indexer_algoliaadditionalsections</model>
146
+ </search_indexer_addsections>
147
  </indexer>
148
  </index>
149
  </global>
177
  <instant>
178
  <replace_categories>1</replace_categories>
179
  <instant_selector>.main</instant_selector>
180
+ <facets>a:2:{s:18:"_1432907948596_596";a:4:{s:9:"attribute";s:14:"price_with_tax";s:4:"type";s:6:"slider";s:10:"other_type";s:0:"";s:5:"label";s:5:"Price";}s:18:"_1432907963376_376";a:4:{s:9:"attribute";s:10:"categories";s:4:"type";s:12:"hierarchical";s:10:"other_type";s:0:"";s:5:"label";s:10:"Categories";}}</facets>
181
  <sorts>a:3:{s:18:"_1432908018844_844";a:3:{s:9:"attribute";s:14:"price_with_tax";s:4:"sort";s:3:"asc";s:5:"label";s:12:"Lowest price";}s:18:"_1432908022539_539";a:3:{s:9:"attribute";s:14:"price_with_tax";s:4:"sort";s:4:"desc";s:5:"label";s:13:"Highest price";}s:18:"_1433768597454_454";a:3:{s:9:"attribute";s:10:"created_at";s:4:"sort";s:4:"desc";s:5:"label";s:12:"Newest first";}}</sorts>
182
  </instant>
183
+ <autocomplete>
184
+ <additional_sections></additional_sections>
185
+ </autocomplete>
186
  <categories>
187
  <category_additional_attributes2>a:7:{s:18:"_1427960339954_954";a:4:{s:9:"attribute";s:4:"name";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427960354437_437";a:4:{s:9:"attribute";s:4:"path";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961004989_989";a:4:{s:9:"attribute";s:11:"description";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:9:"unordered";}s:18:"_1427961205511_511";a:4:{s:9:"attribute";s:10:"meta_title";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961216134_134";a:4:{s:9:"attribute";s:13:"meta_keywords";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}s:18:"_1427961216916_916";a:4:{s:9:"attribute";s:16:"meta_description";s:10:"searchable";s:1:"1";s:11:"retrievable";s:1:"1";s:5:"order";s:9:"unordered";}s:18:"_1427977778338_338";a:4:{s:9:"attribute";s:13:"product_count";s:10:"searchable";s:1:"0";s:11:"retrievable";s:1:"1";s:5:"order";s:7:"ordered";}}</category_additional_attributes2>
188
  <custom_ranking_category_attributes>a:1:{s:18:"_1427961035192_192";a:2:{s:9:"attribute";s:13:"product_count";s:5:"order";s:4:"desc";}}</custom_ranking_category_attributes>
189
  </categories>
190
  <suggestions>
191
+ <min_popularity>100000</min_popularity>
192
  <min_number_of_results>2</min_number_of_results>
193
  </suggestions>
194
  <relevance>
209
  <retries>3</retries>
210
  <number_of_element_by_page>100</number_of_element_by_page>
211
  <number_of_job_to_run>300</number_of_job_to_run>
212
+ <noprocess>0</noprocess>
213
  </queue>
214
+ <advanced>
215
+ <partial_update>0</partial_update>
216
+ </advanced>
217
  </algoliasearch>
218
  </default>
219
  </config>
app/code/community/Algolia/Algoliasearch/etc/system.xml CHANGED
@@ -109,7 +109,7 @@
109
  </fields>
110
  </credentials>
111
  <products translate="label">
112
- <label>Product Search Configuration</label>
113
  <frontend_type>text</frontend_type>
114
  <sort_order>30</sort_order>
115
  <show_in_default>1</show_in_default>
@@ -149,7 +149,7 @@
149
  <comment>
150
  <![CDATA[
151
  Configure here the attributes that reflect the popularity of your product (number of orders, number of likes, number of views, ...).<br />
152
- <span style="color: #D83900">&#9888;</span> All attributes used here must be have been initially included in the Attributes configuration panel.
153
  ]]>
154
  </comment>
155
  </custom_ranking_product_attributes>
@@ -212,7 +212,7 @@
212
  </fields>
213
  </instant>
214
  <categories translate="label">
215
- <label>Category Search Configuration</label>
216
  <frontend_type>text</frontend_type>
217
  <sort_order>40</sort_order>
218
  <show_in_default>1</show_in_default>
@@ -252,14 +252,14 @@
252
  <comment>
253
  <![CDATA[
254
  Choose here the attributes that reflect the popularity of your categories (number of products, total number of sales of the category,etc.).<br />
255
- <span style="color: #D83900">&#9888;</span> All attributes used here must be have been included before in the Attributes chart.
256
  ]]>
257
  </comment>
258
  </custom_ranking_category_attributes>
259
  </fields>
260
  </categories>
261
  <pages>
262
- <label>Page Search Configuration</label>
263
  <frontend_type>text</frontend_type>
264
  <sort_order>45</sort_order>
265
  <show_in_default>1</show_in_default>
@@ -291,7 +291,7 @@
291
  </fields>
292
  </pages>
293
  <suggestions>
294
- <label>Query Suggestions Configuration</label>
295
  <frontend_type>text</frontend_type>
296
  <sort_order>46</sort_order>
297
  <show_in_default>1</show_in_default>
@@ -313,7 +313,7 @@
313
  <show_in_default>1</show_in_default>
314
  <show_in_website>1</show_in_website>
315
  <show_in_store>1</show_in_store>
316
- <comment>The min number of times a query has been performed in order to be suggested. Default value is 4.</comment>
317
  </min_popularity>
318
  <min_number_of_results translate="label comment">
319
  <label>Min number of products</label>
@@ -332,8 +332,35 @@
332
  </min_number_of_results>
333
  </fields>
334
  </suggestions>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
335
  <relevance translate="label">
336
- <label>Query Expansion Settings</label>
337
  <frontend_type>text</frontend_type>
338
  <expanded>1</expanded>
339
  <sort_order>50</sort_order>
@@ -359,7 +386,7 @@
359
  </fields>
360
  </relevance>
361
  <ui translate="label">
362
- <label>UI/UX</label>
363
  <frontend_type>text</frontend_type>
364
  <sort_order>60</sort_order>
365
  <show_in_default>1</show_in_default>
@@ -511,8 +538,58 @@
511
  <comment>Number of jobs to run each time the cron is run. Default value is 300.</comment>
512
  <depends><active>1</active></depends>
513
  </number_of_job_to_run>
 
 
 
 
 
 
 
 
 
 
 
514
  </fields>
515
  </queue>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
516
  </groups>
517
  </algoliasearch>
518
  </sections>
109
  </fields>
110
  </credentials>
111
  <products translate="label">
112
+ <label>Product Configuration</label>
113
  <frontend_type>text</frontend_type>
114
  <sort_order>30</sort_order>
115
  <show_in_default>1</show_in_default>
149
  <comment>
150
  <![CDATA[
151
  Configure here the attributes that reflect the popularity of your product (number of orders, number of likes, number of views, ...).<br />
152
+ <span style="color: #D83900">&#9888;</span> All attributes used here must have been initially included in the Attributes configuration panel.
153
  ]]>
154
  </comment>
155
  </custom_ranking_product_attributes>
212
  </fields>
213
  </instant>
214
  <categories translate="label">
215
+ <label>Category Autocomplete Configuration</label>
216
  <frontend_type>text</frontend_type>
217
  <sort_order>40</sort_order>
218
  <show_in_default>1</show_in_default>
252
  <comment>
253
  <![CDATA[
254
  Choose here the attributes that reflect the popularity of your categories (number of products, total number of sales of the category,etc.).<br />
255
+ <span style="color: #D83900">&#9888;</span> All attributes used here must have been included before in the Attributes chart.
256
  ]]>
257
  </comment>
258
  </custom_ranking_category_attributes>
259
  </fields>
260
  </categories>
261
  <pages>
262
+ <label>Page Autocomplete Configuration</label>
263
  <frontend_type>text</frontend_type>
264
  <sort_order>45</sort_order>
265
  <show_in_default>1</show_in_default>
291
  </fields>
292
  </pages>
293
  <suggestions>
294
+ <label>Query Suggestions Autocomplete Configuration</label>
295
  <frontend_type>text</frontend_type>
296
  <sort_order>46</sort_order>
297
  <show_in_default>1</show_in_default>
313
  <show_in_default>1</show_in_default>
314
  <show_in_website>1</show_in_website>
315
  <show_in_store>1</show_in_store>
316
+ <comment>The min number of times a query has been performed in order to be suggested. Default value is 100000.</comment>
317
  </min_popularity>
318
  <min_number_of_results translate="label comment">
319
  <label>Min number of products</label>
332
  </min_number_of_results>
333
  </fields>
334
  </suggestions>
335
+ <autocomplete>
336
+ <label>Additional Autocomplete Sections Configuration</label>
337
+ <frontend_type>text</frontend_type>
338
+ <sort_order>47</sort_order>
339
+ <show_in_default>1</show_in_default>
340
+ <show_in_website>1</show_in_website>
341
+ <show_in_store>1</show_in_store>
342
+ <expanded>1</expanded>
343
+ <fields>
344
+ <additional_sections>
345
+ <label>Additionnal Sections</label>
346
+ <frontend_model>algoliasearch/system_config_form_field_additionalsections</frontend_model>
347
+ <backend_model>adminhtml/system_config_backend_serialized_array</backend_model>
348
+ <sort_order>30</sort_order>
349
+ <show_in_default>1</show_in_default>
350
+ <show_in_website>1</show_in_website>
351
+ <show_in_store>1</show_in_store>
352
+ <depends><active>1</active></depends>
353
+ <comment>
354
+ <![CDATA[
355
+ Configure here the additional auto-completion menu sections you want include in the dropdown menu (Ex. Manufacturer).<br />
356
+ <span style="color: #D83900">&#9888;</span> All attributes used here must have been initially included in the <strong>Attributes Configuration</strong> panel and configured as a facet in the <strong>Instant Search Results Page Configuration</strong> panel to be able to refine on the specific attribute.
357
+ ]]>
358
+ </comment>
359
+ </additional_sections>
360
+ </fields>
361
+ </autocomplete>
362
  <relevance translate="label">
363
+ <label>Query Expansion Configuration</label>
364
  <frontend_type>text</frontend_type>
365
  <expanded>1</expanded>
366
  <sort_order>50</sort_order>
386
  </fields>
387
  </relevance>
388
  <ui translate="label">
389
+ <label>UI Configuration</label>
390
  <frontend_type>text</frontend_type>
391
  <sort_order>60</sort_order>
392
  <show_in_default>1</show_in_default>
538
  <comment>Number of jobs to run each time the cron is run. Default value is 300.</comment>
539
  <depends><active>1</active></depends>
540
  </number_of_job_to_run>
541
+ <noprocess>
542
+ <label>Disable indexing</label>
543
+ <frontend_type>select</frontend_type>
544
+ <source_model>adminhtml/system_config_source_yesno</source_model>
545
+ <sort_order>50</sort_order>
546
+ <show_in_default>1</show_in_default>
547
+ <show_in_website>1</show_in_website>
548
+ <show_in_store>1</show_in_store>
549
+ <comment>Job will stack onto the queue but no indexing will be done. Default value is false.</comment>
550
+ <depends><active>1</active></depends>
551
+ </noprocess>
552
  </fields>
553
  </queue>
554
+ <advanced translate="label">
555
+ <label>Advanced Configuration</label>
556
+ <expanded>0</expanded>
557
+ <frontend_type>text</frontend_type>
558
+ <sort_order>80</sort_order>
559
+ <show_in_default>1</show_in_default>
560
+ <show_in_website>1</show_in_website>
561
+ <show_in_store>1</show_in_store>
562
+ <fields>
563
+ <partial_update translate="label">
564
+ <label>Partial Updates</label>
565
+ <frontend_type>select</frontend_type>
566
+ <source_model>adminhtml/system_config_source_yesno</source_model>
567
+ <sort_order>10</sort_order>
568
+ <show_in_default>1</show_in_default>
569
+ <show_in_website>1</show_in_website>
570
+ <show_in_store>1</show_in_store>
571
+ <comment>
572
+ <![CDATA[
573
+ If enabled, all add/update operations will use <code>partialUpdateObjects</code> instead of <code>addObjects</code>. You should enable this option if you update some attributes of your records from an external source in addition to Magento to avoid any overriding.
574
+ ]]>
575
+ </comment>
576
+ </partial_update>
577
+ <customer_groups_enable translate="label">
578
+ <label>Customer Groups</label>
579
+ <frontend_type>select</frontend_type>
580
+ <source_model>adminhtml/system_config_source_yesno</source_model>
581
+ <sort_order>20</sort_order>
582
+ <show_in_default>1</show_in_default>
583
+ <show_in_website>1</show_in_website>
584
+ <show_in_store>1</show_in_store>
585
+ <comment>
586
+ <![CDATA[
587
+ If enabled, the extension will take into account your customer groups and display the price of the logged-in group instead of the default price.<br />Enabling this option creates an index per customer group.
588
+ ]]>
589
+ </comment>
590
+ </customer_groups_enable>
591
+ </fields>
592
+ </advanced>
593
  </groups>
594
  </algoliasearch>
595
  </sections>
app/design/frontend/base/default/template/algoliasearch/topsearch.phtml CHANGED
@@ -1,1370 +1,1679 @@
1
- <?php
2
- $config = Mage::helper('algoliasearch/config');
3
- $catalogSearchHelper = $this->helper('catalogsearch'); /** @var $catalogSearchHelper Mage_CatalogSearch_Helper_Data */
4
- $algoliaSearchHelper = $this->helper('algoliasearch'); /** @var $algoliaSearchHelper Algolia_Algoliasearch_Helper_Data */
5
- $product_helper = Mage::helper('algoliasearch/entity_producthelper');
6
- $isSearchPage = Mage::app()->getRequest()->getParam('instant') != null || Mage::app()->getRequest()->getParam('category') != null;
7
- $formKey = Mage::getSingleton('core/session')->getFormKey();
8
-
9
-
10
- if ($config->isInstantEnabled() && $isSearchPage) {
11
- // hide the instant-search selector ASAP to remove flickering. Will be re-displayed later with JS
12
- echo '<style>' . $config->getInstantSelector() . '{ display: none; }</style>';
13
- }
14
- ?>
15
-
16
- <!--
17
- //================================
18
- //
19
- // Search box
20
- //
21
- //================================
22
- -->
23
-
24
- <?php
25
-
26
- $types = array();
27
-
28
- if ($config->getNumberOfProductSuggestions() > 0)
29
- $types[] = $this->__('products');
30
-
31
- if ($config->getNumberOfCategorySuggestions() > 0)
32
- $types[] = $this->__('categories');
33
-
34
- if ($config->getNumberOfPageSuggestions() > 0)
35
- $types[] = $this->__('pages');
36
-
37
- $or = count($types) > 1 ? ' or ' : '';
38
-
39
- $placeholder = 'Search';
40
-
41
- if (count($types) > 0)
42
- {
43
- $placeholder = 'Search for ' . implode(', ', array_slice($types, 0, count($types) - 1)) . $or . $types[count($types) - 1];
44
- }
45
-
46
- $class = $isSearchPage ? 'search-page' : '';
47
-
48
- ?>
49
-
50
- <form id="search_mini_form" action="<?php echo $catalogSearchHelper->getResultUrl() ?>" method="get">
51
- <div id="algolia-searchbox" class="<?php echo $class; ?>">
52
- <label for="search"><?php echo $this->__('Search:') ?></label>
53
- <input id="search" type="text" name="<?php echo $catalogSearchHelper->getQueryParamName() ?>" class="input-text" autocomplete="off" spellcheck="false" autocorrect="off" autocapitalize="off" placeholder="<?php echo $placeholder; ?>" />
54
- <svg id="algolia-glass" xmlns="http://www.w3.org/2000/svg" class="magnifying-glass" width="24" height="24" viewBox="0 0 128 128" >
55
- <g transform="scale(4)">
56
- <path stroke-width="3" d="M19.5 19.582l9.438 9.438"></path>
57
- <circle stroke-width="3" cx="12" cy="12" r="10.5" fill="none"></circle>
58
- <path d="M23.646 20.354l-3.293 3.293c-.195.195-.195.512 0 .707l7.293 7.293c.195.195.512.195.707 0l3.293-3.293c.195-.195.195-.512 0-.707l-7.293-7.293c-.195-.195-.512-.195-.707 0z" ></path>
59
- </g>
60
- </svg>
61
- </div>
62
- </form>
63
-
64
- <!--
65
- //================================
66
- //
67
- // Multi-category Autocomplete
68
- //
69
- //================================
70
- -->
71
-
72
- <!-- Product hit template -->
73
- <script type="text/template" id="autocomplete_products_template">
74
- <a class="algoliasearch-autocomplete-hit" href="{{url}}">
75
- {{#thumbnail_url}}
76
- <div class="thumb"><img src="{{thumbnail_url}}" /></div>
77
- {{/thumbnail_url}}
78
- {{#price_with_tax}}
79
- <div class="algoliasearch-autocomplete-price">
80
- {{#special_price_with_tax}}
81
- <div class="after_special">
82
- {{special_price_with_tax_formated}}
83
- </div>
84
- {{/special_price_with_tax}}
85
- <div {{#special_price_with_tax}}class="before_special"{{/special_price_with_tax}}>
86
- {{price_with_tax_formated}}
87
- </div>
88
- </div>
89
- {{/price_with_tax}}
90
- <div class="info">
91
- {{{_highlightResult.name.value}}}
92
-
93
- {{#categories_without_path}}
94
- <div class="algoliasearch-autocomplete-category">
95
- in {{categories_without_path}}
96
- </div>
97
- {{/categories_without_path}}
98
- </div>
99
- <div class="clearfix"></div>
100
- </a>
101
- </script>
102
-
103
- <!-- Category hit template -->
104
- <script type="text/template" id="autocomplete_categories_template">
105
- <a class="algoliasearch-autocomplete-hit" href="{{url}}">
106
- {{#image_url}}
107
- <div class="thumb">
108
- <img src="{{image_url}}" />
109
- </div>
110
- {{/image_url}}
111
-
112
- {{#image_url}}
113
- <div class="info">
114
- {{/image_url}}
115
- {{^image_url}}
116
- <div class="info-without-thumb">
117
- {{{_highlightResult.path.value}}}
118
-
119
- {{#product_count}}
120
- <small>( {{product_count}} )</small>
121
- {{/product_count}}
122
-
123
- </div>
124
- <div class="clearfix"></div>
125
- {{/image_url}}
126
- </div>
127
- </a>
128
- </script>
129
-
130
- <!-- Page hit template -->
131
- <script type="text/template" id="autocomplete_pages_template">
132
- <a class="algoliasearch-autocomplete-hit" href="{{url}}">
133
- <div class="info-without-thumb">
134
- {{{_highlightResult.name.value}}}
135
- </div>
136
- <div class="clearfix"></div>
137
- </a>
138
- </script>
139
-
140
- <!-- Suggestion hit template -->
141
- <script type="text/template" id="autocomplete_suggestions_template">
142
- <a class="algoliasearch-autocomplete-hit" href="{{url}}">
143
- <div class="info-without-thumb">
144
- {{{_highlightResult.query.value}}}
145
-
146
- {{#category}}
147
- <span class="text-muted">in</span> <span class="category-tag">{{category}}</span>
148
- {{/category}}
149
- </div>
150
- <div class="clearfix"></div>
151
- </a>
152
- </script>
153
-
154
-
155
- <!--
156
- //================================
157
- //
158
- // Instant search results page
159
- //
160
- //================================
161
- -->
162
-
163
-
164
-
165
- <!-- Wrapping template -->
166
- <script type="text/template" id="instant_wrapper_template">
167
-
168
- <div id="algolia_instant_selector"<?php echo count($config->getFacets()) > 0 ? ' class="with-facets"' : '' ?>>
169
-
170
- <div id="algolia-left-container">
171
- <div id="instant-search-facets-container"></div>
172
- </div>
173
-
174
- <div id="algolia-right-container">
175
-
176
- {{#second_bar}}
177
- <div id="instant-search-bar-container">
178
- <div id="instant-search-box">
179
- <label for="instant-search-bar">
180
- Search :
181
- </label>
182
-
183
- <input value="<?php echo $catalogSearchHelper->getEscapedQueryText() ?>" placeholder="Search for products" id="instant-search-bar" type="text" autocomplete="off" spellcheck="false" autocorrect="off" autocapitalize="off" />
184
-
185
- <svg xmlns="http://www.w3.org/2000/svg" class="magnifying-glass" width="24" height="24" viewBox="0 0 128 128">
186
- <g transform="scale(4)">
187
- <path stroke-width="3" d="M19.5 19.582l9.438 9.438"></path>
188
- <circle stroke-width="3" cx="12" cy="12" r="10.5" fill="none"></circle>
189
- <path d="M23.646 20.354l-3.293 3.293c-.195.195-.195.512 0 .707l7.293 7.293c.195.195.512.195.707 0l3.293-3.293c.195-.195.195-.512 0-.707l-7.293-7.293c-.195-.195-.512-.195-.707 0z"></path>
190
- </g>
191
- </svg>
192
- </div>
193
- </div>
194
- {{/second_bar}}
195
-
196
- <div id="instant-search-results-container"></div>
197
- <div id="instant-search-pagination-container"></div>
198
- </div>
199
- </div>
200
- </script>
201
-
202
- <!-- Product hit template -->
203
- <script type="text/template" id="instant-content-template">
204
- <div class="hits">
205
- {{#hits.length}}
206
- <div class="infos">
207
- <div class="pull-left">
208
- {{nbHits}} result{{^nbHits_one}}s{{/nbHits_one}} found {{#query}}matching "<strong>{{query}}</strong>" {{/query}}in {{processingTimeMS}} ms
209
- </div>
210
- {{#sorting_indices.length}}
211
- <div class="pull-right">
212
- Order by
213
- <select id="index_to_use">
214
- <option {{#sortSelected}}{{relevance_index_name}}{{/sortSelected}} value="{{relevance_index_name}}">Relevance</option>
215
- {{#sorting_indices}}
216
- <option {{#sortSelected}}{{index_name}}{{/sortSelected}} value="{{index_name}}">{{label}}</option>
217
- {{/sorting_indices}}
218
- </select>
219
- </div>
220
- {{/sorting_indices.length}}
221
- <div class="clearfix"></div>
222
- </div>
223
- {{/hits.length}}
224
-
225
- {{#hits}}
226
- <div class="result-wrapper">
227
- <a href="{{url}}" class="result">
228
- <div class="result-content">
229
- <div class="result-thumbnail">
230
- {{#image_url}}
231
- <img src="{{{ image_url }}}" />
232
- {{/image_url}}
233
- {{^image_url}}
234
- <span class="no-image"></span>
235
- {{/image_url}}
236
- </div>
237
- <div class="result-sub-content">
238
- <h3 class="result-title text-ellipsis">
239
- {{{ _highlightResult.name.value }}}
240
- </h3>
241
- <div class="ratings">
242
- <div class="rating-box">
243
- <div class="rating" style="width:{{rating_summary}}%" width="148" height="148"></div>
244
- </div>
245
- </div>
246
- <div class="price">
247
- <div class="algoliasearch-autocomplete-price">
248
- <div>
249
- {{#special_price_with_tax}}
250
- <span class="after_special">
251
- {{special_price_with_tax_formated}}
252
- </span>
253
- {{/special_price_with_tax}}
254
-
255
- {{#special_price_with_tax}}
256
- <span class="before_special">
257
- {{/special_price_with_tax}}
258
-
259
- {{#price_with_tax}}{{price_with_tax_formated}}{{/price_with_tax}}
260
- {{^price_with_tax}}
261
- {{#min_with_tax_formated}}
262
- {{min_with_tax_formated}} - {{max_with_tax_formated}}
263
- {{/min_with_tax_formated}}
264
- {{^min_with_tax_formated}}-{{/min_with_tax_formated}}
265
- {{/price_with_tax}}
266
-
267
- {{#special_price_with_tax}}
268
- </span>
269
- {{/special_price_with_tax}}
270
-
271
-
272
- </div>
273
- </div>
274
- </div>
275
- <div class="result-description text-ellipsis">
276
- {{{ _highlightResult.description.value }}}
277
- </div>
278
-
279
- {{#isAddToCartEnabled}}
280
- {{#in_stock}}
281
- <form action="/checkout/cart/add/product/{{objectID}}" method="post">
282
- <input type="hidden" name="form_key" value="<?php echo $formKey; ?>" />
283
-
284
- <input type="hidden" name="qty" value="1">
285
-
286
- <button type="submit">Add to Cart</button>
287
- </form>
288
- {{/in_stock}}
289
- {{/isAddToCartEnabled}}
290
- </div>
291
- </div>
292
- <div class="clearfix"></div>
293
- </a>
294
- </div>
295
- {{/hits}}
296
- {{^hits.length}}
297
- <div class="no-results">
298
- No results found matching "<strong>{{query}}</strong>". <span class="button clear-button">Clear query and filters</span>
299
- </div>
300
- {{/hits.length}}
301
- <div class="clearfix"></div>
302
- </div>
303
- </script>
304
-
305
- <!-- Facet template -->
306
- <script type="text/template" id="instant-facets-template">
307
- <div class="facets">
308
- {{#facets}}
309
- {{#count}}
310
- <div class="facet">
311
- <div class="name">
312
- {{ facet_categorie_name }}
313
- </div>
314
- <div>
315
- {{#sub_facets}}
316
-
317
- {{#type.menu}}
318
- <div data-attribute="{{attribute}}" data-name="{{nameattr}}" data-type="menu" class="{{#checked}}checked {{/checked}}sub_facet menu">
319
- <input style="display: none;" data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
320
- {{name}}
321
- {{#print_count}}<span class="count">{{count}}</span>{{/print_count}}
322
- </div>
323
- {{/type.menu}}
324
-
325
- {{#type.conjunctive}}
326
- <div data-name="{{attribute}}" data-type="conjunctive" class="{{#checked}}checked {{/checked}}sub_facet conjunctive">
327
- <input style="display: none;" data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
328
- {{name}}
329
- {{#count}}<span class="count">{{count}}</span>{{/count}}
330
- </div>
331
- {{/type.conjunctive}}
332
-
333
- {{#type.slider}}
334
- <div class="algolia-slider algolia-slider-true" data-attribute="{{attribute}}" data-min="{{min}}" data-max="{{max}}"></div>
335
- <div class="algolia-slider-info">
336
- <div class="min" style="float: left;">{{current_min}}</div>
337
- <div class="max" style="float: right;">{{current_max}}</div>
338
- <div class="clearfix"></div>
339
- </div>
340
- {{/type.slider}}
341
-
342
- {{#type.disjunctive}}
343
- <div data-name="{{attribute}}" data-type="disjunctive" class="{{#checked}}checked {{/checked}}sub_facet disjunctive">
344
- <input data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
345
- {{name}}
346
- {{#count}}<span class="count">{{count}}</span>{{/count}}
347
- </div>
348
- {{/type.disjunctive}}
349
-
350
- {{/sub_facets}}
351
- </div>
352
- </div>
353
- {{/count}}
354
- {{/facets}}
355
- </div>
356
- </script>
357
-
358
- <!-- Pagination template -->
359
- <script type="text/template" id="instant-pagination-template">
360
- <div class="pagination-wrapper">
361
- <div class="text-center">
362
- <ul class="algolia-pagination">
363
- <a href="#" data-page="{{prev_page}}">
364
- <li {{^prev_page}}class="disabled"{{/prev_page}}>
365
- &laquo;
366
- </li>
367
- </a>
368
-
369
- {{#pages}}
370
- <a href="#" data-page="{{number}}">
371
- <li class="{{#current}}active{{/current}}{{#disabled}}disabled{{/disabled}}">
372
- {{ number }}
373
- </li>
374
- </a>
375
- {{/pages}}
376
- <a href="#" data-page="{{next_page}}">
377
- <li {{^next_page}}class="disabled"{{/next_page}}>
378
- &raquo;
379
- </li>
380
- </a>
381
- </ul>
382
- </div>
383
- </div>
384
- </script>
385
-
386
-
387
- <!--
388
- //================================
389
- //
390
- // JavaScript
391
- //
392
- //================================
393
- -->
394
-
395
-
396
- <script type="text/javascript">
397
- //<![CDATA[
398
-
399
- algoliaBundle.$(function($) {
400
- var algoliaConfig = {
401
- instant: {
402
- enabled: <?php echo $config->isInstantEnabled() ? "true" : "false"; ?>,
403
- selector: '<?php echo $config->getInstantSelector(); ?>',
404
- isAddToCartEnabled: <?php echo $config->isAddToCartEnable() ? "true" : "false"; ?>
405
- },
406
- autocomplete: {
407
- enabled: <?php echo $config->isAutoCompleteEnabled() ? "true" : "false"; ?>,
408
- selector: '#search',
409
- hitsPerPage: {
410
- products: <?php echo (int) $config->getNumberOfProductSuggestions() ?>,
411
- categories: <?php echo (int) $config->getNumberOfCategorySuggestions() ?>,
412
- pages: <?php echo (int) $config->getNumberOfPageSuggestions() ?>,
413
- suggestions: <?php echo (int) $config->getNumberOfQuerySuggestions() ?>
414
- },
415
- templates: {
416
- suggestions: algoliaBundle.Hogan.compile($('#autocomplete_suggestions_template').html()),
417
- products: algoliaBundle.Hogan.compile($('#autocomplete_products_template').html()),
418
- categories: algoliaBundle.Hogan.compile($('#autocomplete_categories_template').html()),
419
- pages: algoliaBundle.Hogan.compile($('#autocomplete_pages_template').html())
420
- },
421
- titles: {
422
- products: '<?php echo $this->__('Products'); ?>',
423
- categories: '<?php echo $this->__('Categories') ?>',
424
- pages: '<?php echo $this->__('Pages') ?>',
425
- suggestions: '<?php echo $this->__('Suggestions') ?>'
426
- }
427
- },
428
- applicationId: '<?php echo $config->getApplicationID() ?>',
429
- indexName: '<?php echo $product_helper->getBaseIndexName(); ?>',
430
- apiKey: '<?php echo $config->getSearchOnlyAPIKey() ?>',
431
- facets: <?php echo json_encode($config->getFacets()); ?>,
432
- hitsPerPage: <?php echo (int) $config->getNumberOfProductResults() ?>,
433
- sortingIndices: <?php echo json_encode(array_values($config->getSortingIndices())); ?>,
434
- isSearchPage: <?php echo $isSearchPage ? "true" : "false" ?>,
435
- removeBranding: <?php echo $config->isRemoveBranding() ? "true" : "false"; ?>
436
- };
437
-
438
- /*****************
439
- **
440
- ** INITIALIZATION
441
- **
442
- *****************/
443
-
444
- var algolia_client = algoliaBundle.algoliasearch(algoliaConfig.applicationId, algoliaConfig.apiKey);
445
-
446
- /**
447
- * Foreach Type decide if it need to have a conjunctive or dijunctive faceting
448
- * When you create a custom facet type you need to add it here.
449
- * Example : 'menu'
450
- */
451
- var conjunctive_facets = [];
452
- var disjunctive_facets = [];
453
-
454
- for (var i = 0; i < algoliaConfig.facets.length; i++)
455
- {
456
- if (algoliaConfig.facets[i].type == "conjunctive")
457
- conjunctive_facets.push(algoliaConfig.facets[i].attribute);
458
-
459
- if (algoliaConfig.facets[i].type == "disjunctive")
460
- disjunctive_facets.push(algoliaConfig.facets[i].attribute);
461
-
462
- if (algoliaConfig.facets[i].type == "slider")
463
- disjunctive_facets.push(algoliaConfig.facets[i].attribute);
464
-
465
- if (algoliaConfig.facets[i].type == "menu")
466
- disjunctive_facets.push(algoliaConfig.facets[i].attribute);
467
- }
468
-
469
- var helper = algoliaBundle.algoliasearchHelper(algolia_client, algoliaConfig.indexName + '_products', {
470
- facets: conjunctive_facets,
471
- disjunctiveFacets: disjunctive_facets,
472
- hitsPerPage: algoliaConfig.hitsPerPage
473
- });
474
-
475
- helper.setQuery('');
476
-
477
- /**
478
- * Helper functions
479
- */
480
- var history_timeout;
481
- var custom_facets_types = [];
482
-
483
- custom_facets_types["slider"] = function (helper, content, facet) {
484
- if (content.getFacetByName(facet.attribute) != undefined)
485
- {
486
- var min = content.getFacetByName(facet.attribute).stats.min;
487
- var max = content.getFacetByName(facet.attribute).stats.max;
488
-
489
- var current_min = helper.state.getNumericRefinement(facet.attribute, ">=");
490
- var current_max = helper.state.getNumericRefinement(facet.attribute, "<=");
491
-
492
- if (current_min == undefined)
493
- current_min = min;
494
-
495
- if (current_max == undefined)
496
- current_max = max;
497
-
498
- var params = {
499
- type: {},
500
- current_min: Math.floor(current_min),
501
- current_max: Math.ceil(current_max),
502
- count: min == max ? 0 : 1,
503
- min: Math.floor(min),
504
- max: Math.ceil(max)
505
- };
506
-
507
- params.type[facet.type] = true;
508
-
509
- return [params];
510
- }
511
-
512
- return [];
513
- };
514
-
515
- var updateUrl = function (push_state) {
516
-
517
- var refinements = [];
518
-
519
- /** Get refinements for conjunctive facets **/
520
- for (var refine in helper.state.facetsRefinements)
521
- {
522
- if (helper.state.facetsRefinements[refine])
523
- {
524
- var r = {};
525
-
526
- r[refine] = helper.state.facetsRefinements[refine];
527
-
528
- refinements.push(r);
529
- }
530
- }
531
-
532
- /** Get refinements for disjunctive facets **/
533
- for (var refine in helper.state.disjunctiveFacetsRefinements)
534
- {
535
- for (var i = 0; i < helper.state.disjunctiveFacetsRefinements[refine].length; i++)
536
- {
537
- var r = {};
538
-
539
- r[refine] = helper.state.disjunctiveFacetsRefinements[refine][i];
540
-
541
- refinements.push(r);
542
- }
543
- }
544
-
545
- var url = '#q=' + encodeURIComponent(helper.state.query) +
546
- '&page=' + helper.getCurrentPage() +
547
- '&refinements=' + encodeURIComponent(JSON.stringify(refinements)) +
548
- '&numerics_refinements=' + encodeURIComponent(JSON.stringify(helper.state.numericRefinements)) +
549
- '&index_name=' + encodeURIComponent(JSON.stringify(helper.getIndex()));
550
-
551
- /** If push_state is false wait for one second to push the state in history **/
552
- if (push_state)
553
- history.pushState(url, null, url);
554
- else
555
- {
556
- clearTimeout(history_timeout);
557
- history_timeout = setTimeout(function () {
558
- history.pushState(url, null, url);
559
- }, 1000);
560
- }
561
- };
562
-
563
- var getRefinementsFromUrl = function() {
564
-
565
- if (location.hash && location.hash.indexOf('#q=') === 0)
566
- {
567
- var params = location.hash.substring(3);
568
- var pageParamOffset = params.indexOf('&page=');
569
- var refinementsParamOffset = params.indexOf('&refinements=');
570
- var numericsRefinementsParamOffset = params.indexOf('&numerics_refinements=');
571
- var indexNameOffset = params.indexOf('&index_name=');
572
-
573
- var q = decodeURIComponent(params.substring(0, pageParamOffset));
574
- var page = parseInt(params.substring(pageParamOffset + '&page='.length, refinementsParamOffset));
575
- var refinements = JSON.parse(decodeURIComponent(params.substring(refinementsParamOffset + '&refinements='.length, numericsRefinementsParamOffset)));
576
- var numericsRefinements = JSON.parse(decodeURIComponent(params.substring(numericsRefinementsParamOffset + '&numerics_refinements='.length, indexNameOffset)));
577
- var indexName = JSON.parse(decodeURIComponent(params.substring(indexNameOffset + '&index_name='.length)));
578
-
579
- helper.setQuery(q);
580
-
581
- helper.clearRefinements();
582
-
583
- console.log(refinements);
584
-
585
- /** Set refinements from url data **/
586
- for (var i = 0; i < refinements.length; ++i) {
587
- for (var refine in refinements[i]) {
588
- for (var j = 0; j < refinements[i][refine].length; j++) {
589
- helper.toggleRefine(refine, refinements[i][refine][j]);
590
- }
591
- }
592
- }
593
-
594
- for (var key in numericsRefinements)
595
- for (var operator in numericsRefinements[key])
596
- helper.addNumericRefinement(key, operator, numericsRefinements[key][operator]);
597
-
598
- helper.setIndex(indexName).setCurrentPage(page);
599
-
600
- }
601
- helper.search();
602
- };
603
-
604
- var getFacets = function (content) {
605
-
606
- var facets = [];
607
-
608
- for (var i = 0; i < algoliaConfig.facets.length; i++)
609
- {
610
- var sub_facets = [];
611
-
612
- if (custom_facets_types[algoliaConfig.facets[i].type] != undefined)
613
- {
614
- try
615
- {
616
- var params = custom_facets_types[algoliaConfig.facets[i].type](helper, content, algoliaConfig.facets[i]);
617
-
618
- if (params)
619
- for (var k = 0; k < params.length; k++)
620
- sub_facets.push(params[k]);
621
- }
622
- catch(error)
623
- {
624
- throw("Bad facet function for '" + algoliaConfig.facets[i].type + "'");
625
- }
626
- }
627
- else
628
- {
629
- var content_facet = content.getFacetByName(algoliaConfig.facets[i].attribute);
630
-
631
- if (content_facet == undefined)
632
- continue;
633
-
634
- for (var key in content_facet.data)
635
- {
636
- var checked = helper.isRefined(algoliaConfig.facets[i].attribute, key);
637
-
638
- var nameattr = window.facetsLabels && window.facetsLabels[key] != undefined ? window.facetsLabels[key] : key;
639
- var explode = nameattr.split(' /// ');
640
- var name = explode[explode.length - 1];
641
-
642
- var params = {
643
- type: {},
644
- checked: checked,
645
- nameattr: nameattr,
646
- name: name,
647
- count: content_facet.data[key]
648
- };
649
-
650
- params.type[algoliaConfig.facets[i].type] = true;
651
-
652
- sub_facets.push(params);
653
- }
654
-
655
- sub_facets.sort(function sortByCheckedThenCount(f1, f2) {
656
- if (f1.checked !== f2.checked)
657
- return f1.checked ? -1 : 1;
658
-
659
- if (f2.count !== f1.count)
660
- return f2.count - f1.count;
661
-
662
- return f1.name.localeCompare(f2.name);
663
- });
664
-
665
- }
666
- facets.push({count: sub_facets.length, attribute: algoliaConfig.facets[i].attribute, facet_categorie_name: algoliaConfig.facets[i].label, sub_facets: sub_facets });
667
- }
668
-
669
- return facets;
670
- };
671
-
672
- var getPages = function (content) {
673
- var pages = [];
674
- if (content.page > 5)
675
- {
676
- pages.push({ current: false, number: 1 });
677
- pages.push({ current: false, number: '...', disabled: true });
678
- }
679
-
680
- for (var p = content.page - 5; p < content.page + 5; ++p)
681
- {
682
- if (p < 0 || p >= content.nbPages)
683
- continue;
684
-
685
- pages.push({ current: content.page == p, number: (p + 1) });
686
- }
687
- if (content.page + 5 < content.nbPages)
688
- {
689
- pages.push({ current: false, number: '...', disabled: true });
690
- pages.push({ current: false, number: content.nbPages });
691
- }
692
-
693
- return pages;
694
- };
695
-
696
- var sortSelected = function () {
697
- return function (val) {
698
- var template = algoliaBundle.Hogan.compile(val);
699
-
700
- var renderer = function(context) {
701
- return function(text) {
702
- return template.c.compile(text, template.options).render(context);
703
- };
704
- };
705
-
706
- var render = renderer(this);
707
-
708
- var index_name = render(val);
709
-
710
- if (index_name == helper.getIndex())
711
- return "selected";
712
- return "";
713
- }
714
- };
715
-
716
- var gotoPage = function(page) {
717
- helper.setCurrentPage(+page - 1);
718
- };
719
-
720
- var getDate = function () {
721
- return function (val) {
722
- var template = algoliaBundle.Hogan.compile(val);
723
-
724
- var renderer = function(context) {
725
- return function(text) {
726
- return template.c.compile(text, template.options).render(context);
727
- };
728
- };
729
-
730
- var render = renderer(this);
731
-
732
- var timestamp = render(val);
733
-
734
-
735
- var date = new Date(timestamp * 1000);
736
-
737
- var days = ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"];
738
- var months = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];
739
-
740
- var day = date.getDate();
741
-
742
- if (day == 1)
743
- day += "st";
744
- else if (day == 2)
745
- day += "nd";
746
- else if (day == 3)
747
- day += "rd";
748
- else
749
- day += "th";
750
-
751
- return days[date.getDay()] + ", " + months[date.getMonth()] + " " + day + ", " + date.getFullYear();
752
- }
753
- };
754
-
755
- /*****************
756
- **
757
- ** RENDERING HELPERS
758
- **
759
- *****************/
760
-
761
- function getHtmlForPagination(paginationTemplate, content, pages, facets) {
762
- var pagination_html = paginationTemplate.render({
763
- pages: pages,
764
- facets_count: facets.length,
765
- prev_page: (content.page > 0 ? content.page : false),
766
- next_page: (content.page + 1 < content.nbPages ? content.page + 2 : false)
767
- });
768
-
769
- return pagination_html;
770
- }
771
-
772
- function getHtmlForResults(resultsTemplate, content, facets) {
773
-
774
- var results_html = resultsTemplate.render({
775
- facets_count: facets.length,
776
- getDate: getDate,
777
- relevance_index_name: algoliaConfig.indexName + '_products',
778
- sorting_indices: algoliaConfig.sortingIndices,
779
- sortSelected: sortSelected,
780
- hits: content.hits,
781
- nbHits: content.nbHits,
782
- nbHits_zero: (content.nbHits === 0),
783
- nbHits_one: (content.nbHits === 1),
784
- nbHits_many: (content.nbHits > 1),
785
- query: helper.state.query,
786
- processingTimeMS: content.processingTimeMS,
787
- isAddToCartEnabled: algoliaConfig.instant.isAddToCartEnabled
788
- });
789
-
790
- return results_html;
791
- }
792
-
793
- function getHtmlForFacets(facetsTemplate, facets) {
794
-
795
- var facets_html = facetsTemplate.render({
796
- facets: facets,
797
- count: facets.length,
798
- getDate: getDate,
799
- relevance_index_name: algoliaConfig.indexName + '_products',
800
- sorting_indices: algoliaConfig.sortingIndices,
801
- sortSelected: sortSelected
802
- });
803
-
804
- return facets_html;
805
- }
806
-
807
- /*****************
808
- **
809
- ** AUTOCOMPLETION MENU
810
- **
811
- *****************/
812
-
813
- if (algoliaConfig.autocomplete.enabled)
814
- {
815
- var params = {};
816
-
817
- var hogan_objs = [];
818
-
819
- var indices = ['categories', 'products', 'pages'];
820
-
821
- if (algoliaConfig.autocomplete.hitsPerPage['suggestions'] > 0)
822
- {
823
- var suggestions_index = algolia_client.initIndex(algoliaConfig.indexName + "_suggestions");
824
- var products_index = algolia_client.initIndex(algoliaConfig.indexName + "_products");
825
-
826
- hogan_objs.push({
827
- displayKey: 'query',
828
- source: function (query, cb) {
829
- suggestions_index.search(query, {
830
- hitsPerPage: algoliaConfig.autocomplete.hitsPerPage['suggestions']
831
- }, function (err, content) {
832
- if (err)
833
- return;
834
-
835
- if (content.hits.length > 0) {
836
- products_index.search(content.hits[0].query, {
837
- facets: ['categories'],
838
- hitsPerPage: 0,
839
- typoTolerance: false,
840
- maxValuesPerFacet: 3
841
- }, function (err2, content2) {
842
-
843
- if (err2)
844
- {
845
- cb([]);
846
- return;
847
- }
848
-
849
- var hits = [];
850
-
851
- var categories = {};
852
-
853
- if (content2.facets.categories) {
854
-
855
- var obj = $.extend(true, {}, content.hits[0]);
856
- obj.category = '<?php echo $this->__('All departments') ?>';
857
- obj.url = '<?php echo Mage::getBaseUrl(); ?>catalogsearch/result/?q=' + obj.query;
858
- hits.push(obj);
859
-
860
- for (var key in content2.facets.categories) {
861
-
862
- var explode = key.split(' /// ');
863
- var nameattr = explode[0];
864
-
865
- categories[nameattr] = 1;
866
- }
867
-
868
- for (var key in categories)
869
- {
870
- var obj = $.extend(true, {}, content.hits[0]);
871
- obj.category = key;
872
- obj.url = '<?php echo Mage::getBaseUrl(); ?>?category=1#q=' + obj.query + '&page=0&refinements=%5B%7B%22categories%22%3A%5B%22' + obj.category + '%22%5D%7D%5D&numerics_refinements=%7B%7D&index_name=%22<?php echo $product_helper->getBaseIndexName(); ?>_products%22';
873
- hits.push(obj);
874
- }
875
- }
876
- else
877
- {
878
- var obj = $.extend(true, {}, content.hits[0]);
879
- obj.url = '<?php echo Mage::getBaseUrl(); ?>catalogsearch/result/?q=' + obj.query;
880
- hits.push(obj);
881
- }
882
-
883
- for (var k = 1; k < content.hits.length; k++)
884
- {
885
- var obj = $.extend(true, {}, content.hits[k]);
886
- obj.url = '<?php echo Mage::getBaseUrl(); ?>catalogsearch/result/?q=' + obj.query;
887
- hits.push(obj);
888
- }
889
-
890
-
891
- for (var k = 0; k < hits.length; k++)
892
- hits[k].query = content.query;
893
-
894
- cb(hits);
895
- });
896
- }
897
- else
898
- cb([]);
899
- });
900
- },
901
- templates: {
902
- suggestion: function (hit) {
903
- return algoliaConfig.autocomplete.templates['suggestions'].render(hit);
904
- }
905
- }
906
- });
907
- }
908
-
909
- for (var i = 0; i < indices.length; i++)
910
- {
911
- if (algoliaConfig.autocomplete.hitsPerPage[indices[i]] > 0)
912
- {
913
- var index = algolia_client.initIndex(algoliaConfig.indexName + "_" + indices[i]);
914
-
915
- hogan_objs.push({
916
- source: (function (index, i) {
917
- return function (query, cb) {
918
- index.search(query, {
919
- hitsPerPage: algoliaConfig.autocomplete.hitsPerPage[indices[i]]
920
- }, function (err, content) {
921
- if (err)
922
- {
923
- cb([]);
924
- return;
925
- }
926
-
927
- for (var k = 0; k < content.hits.length; k++)
928
- content.hits[k].query = content.query;
929
-
930
- cb(content.hits);
931
- });
932
- }
933
- })(index, i),
934
- displayKey: 'query',
935
- templates: {
936
- header: '<div class="category">' + algoliaConfig.autocomplete.titles[indices[i]] + '</div>',
937
- suggestion: (function (i) {
938
- return function (hit) {
939
- if (indices[i] == 'products')
940
- {
941
- var time = Math.floor(Date.now() / 1000);
942
-
943
- if ((hit.special_price_from_date != undefined && hit.special_price_from_date > time) ||
944
- (hit.special_price_to_date != undefined && hit.special_price_to_date < time))
945
- {
946
- delete hit.special_price_from_date;
947
- delete hit.special_price_to_date;
948
- delete hit.special_price;
949
- delete hit.special_price_with_tax;
950
- delete hit.special_price_formated;
951
- delete hit.special_price_with_tax_formated;
952
- }
953
-
954
- if (Array.isArray(hit.categories_without_path))
955
- hit.categories_without_path = hit.categories_without_path.join(', ');
956
-
957
- if (Array.isArray(hit._highlightResult.name)) {
958
- hit._highlightResult.name = hit._highlightResult.name[0];
959
- hit.displayKey = hit.name[0];
960
- }
961
-
962
- if (Array.isArray(hit.price))
963
- hit.price = hit.price[0];
964
-
965
- }
966
-
967
- if (indices[i] == 'categories')
968
- {
969
- hit.displayKey = hit.path;
970
- }
971
-
972
- hit.displayKey = hit.displayKey || hit.name;
973
-
974
- return algoliaConfig.autocomplete.templates[indices[i]].render(hit);
975
- }
976
- })(i)
977
- }
978
- });
979
- }
980
- }
981
-
982
- if (algoliaConfig.removeBranding === false)
983
- {
984
- hogan_objs.push({
985
- source: function findMatches(q, cb) {
986
- return cb(["algolia-branding"]);
987
- },
988
- displayKey: 'title',
989
- templates: {
990
- suggestion: function (hit) {
991
- return '<div class="footer_algolia"><a href="https://www.algolia.com/?utm_source=magento&utm_medium=link&utm_campaign=magento_autocompletion_menu" target="_blank"><img src="/skin/frontend/base/default/algoliasearch/algolia-logo.png" /></a></div>';
992
- }
993
- }
994
- });
995
- }
996
-
997
- $(algoliaConfig.autocomplete.selector).each(function (i) {
998
- var tt = $(this)
999
- .typeahead({hint: false}, hogan_objs)
1000
- .parent()
1001
- .attr('id', 'algolia-autocomplete-tt');
1002
-
1003
- $(this).on('typeahead:selected', function (e, item) {
1004
- autocomplete = false;
1005
- instant = false;
1006
- window.location.href = item.url;
1007
- });
1008
- });
1009
-
1010
- $("#algolia-glass").click(function () {
1011
- $(this).closest('form').submit();
1012
- });
1013
- }
1014
-
1015
- /*****************
1016
- **
1017
- ** INSTANT RESULTS PAGE SEARCH
1018
- **
1019
- *****************/
1020
-
1021
- if (algoliaConfig.instant.enabled && (<?php echo $isSearchPage ? "true" : "false"; ?> || ! algoliaConfig.autocomplete.enabled))
1022
- {
1023
- if ($(algoliaConfig.instant.selector).length !== 1)
1024
- throw '[Algolia] Invalid instant-search selector: ' + algoliaConfig.instant.selector;
1025
-
1026
- if ($(algoliaConfig.instant.selector).find(algoliaConfig.autocomplete.selector).length > 0)
1027
- throw '[Algolia] You can\'t have a search input matching "' + algoliaConfig.autocomplete.selector +
1028
- '" inside you instant selector "' + algoliaConfig.instant.selector + '"';
1029
-
1030
- var instant_selector = ! algoliaConfig.autocomplete.enabled ? "#search" : "#instant-search-bar";
1031
-
1032
- var wrapperTemplate = algoliaBundle.Hogan.compile($('#instant_wrapper_template').html());
1033
-
1034
- var initialized = false;
1035
-
1036
- var resultsTemplate = algoliaBundle.Hogan.compile($('#instant-content-template').html());
1037
- var facetsTemplate = algoliaBundle.Hogan.compile($('#instant-facets-template').html());
1038
- var paginationTemplate = algoliaBundle.Hogan.compile($('#instant-pagination-template').html());
1039
-
1040
-
1041
- function performQueries(push_state)
1042
- {
1043
- helper.search();
1044
-
1045
- updateUrl(push_state);
1046
- }
1047
-
1048
- function searchCallback(content)
1049
- {
1050
- if (initialized === false)
1051
- {
1052
- $(algoliaConfig.instant.selector).html(wrapperTemplate.render({ second_bar: algoliaConfig.autocomplete.enabled })).show();
1053
- initialized = true;
1054
- }
1055
- /**
1056
- * Modify results to be able to print it with Hogan
1057
- */
1058
- for (var i = 0; i < content.hits.length; ++i)
1059
- {
1060
- if (Array.isArray(content.hits[i].categories))
1061
- content.hits[i].categories = content.hits[i].categories.join(', ');
1062
-
1063
- if (Array.isArray(content.hits[i]._highlightResult.name))
1064
- content.hits[i]._highlightResult.name = content.hits[i]._highlightResult.name[0];
1065
-
1066
- if (Array.isArray(content.hits[i].price))
1067
- content.hits[i].price = content.hits[i].price[0];
1068
-
1069
- var time = Math.floor(Date.now() / 1000);
1070
-
1071
- if ((content.hits[i].special_price_from_date != undefined && content.hits[i].special_price_from_date > time) ||
1072
- (content.hits[i].special_price_to_date != undefined && content.hits[i].special_price_to_date < time))
1073
- {
1074
- delete content.hits[i].special_price_from_date;
1075
- delete content.hits[i].special_price_to_date;
1076
- delete content.hits[i].special_price;
1077
- delete content.hits[i].special_price_with_tax;
1078
- delete content.hits[i].special_price_formated;
1079
- delete content.hits[i].special_price_with_tax_formated;
1080
- }
1081
- }
1082
-
1083
- /**
1084
- * Generate HTML
1085
- */
1086
-
1087
- var instant_search_facets_container = $('#instant-search-facets-container');
1088
- var instant_search_results_container = $('#instant-search-results-container');
1089
- var instant_search_pagination_container = $('#instant-search-pagination-container');
1090
-
1091
- instant_search_facets_container.html('');
1092
- instant_search_results_container.html('');
1093
- instant_search_pagination_container.html('');
1094
-
1095
- var facets = [];
1096
- var pages = [];
1097
-
1098
- if (content.hits.length > 0)
1099
- {
1100
- facets = getFacets(content);
1101
- pages = getPages(content);
1102
-
1103
- instant_search_facets_container.html(getHtmlForFacets(facetsTemplate, facets));
1104
- }
1105
-
1106
- instant_search_results_container.html(getHtmlForResults(resultsTemplate, content, facets));
1107
-
1108
- if (content.hits.length > 0)
1109
- instant_search_pagination_container.html(getHtmlForPagination(paginationTemplate, content, pages, facets));
1110
-
1111
- updateSliderValues();
1112
-
1113
- var instant_search_bar = $(instant_selector);
1114
-
1115
- if (instant_search_bar.is(":focus") === false)
1116
- {
1117
- instant_search_bar.focus().val('');
1118
- instant_search_bar.val(helper.state.query);
1119
- }
1120
- }
1121
-
1122
- helper.on('result', searchCallback);
1123
-
1124
- /**
1125
- * Example of a custom facet type
1126
- */
1127
- custom_facets_types["menu"] = function (helper, content, facet) {
1128
-
1129
- var data = [];
1130
-
1131
- var all_count = 0;
1132
- var all_unchecked = true;
1133
-
1134
- var content_facet = content.getFacetByName(facet.attribute);
1135
-
1136
- if (content_facet == undefined)
1137
- return data;
1138
-
1139
- for (var key in content_facet.data)
1140
- {
1141
- var checked = helper.isRefined(facet.attribute, key);
1142
-
1143
- all_unchecked = all_unchecked && !checked;
1144
-
1145
- var name = window.facetsLabels && window.facetsLabels[key] != undefined ? window.facetsLabels[key] : key;
1146
- var explode = name.split(' /// ');
1147
- var nameattr = explode[explode.length - 1];
1148
-
1149
- var params = {
1150
- type: {},
1151
- checked: checked,
1152
- nameattr: nameattr,
1153
- name: name,
1154
- print_count: true,
1155
- count: content_facet.data[key]
1156
- };
1157
-
1158
- all_count += content_facet.data[key];
1159
-
1160
- params.type[facet.type] = true;
1161
-
1162
- data.push(params);
1163
- }
1164
-
1165
- var params = {
1166
- type: {},
1167
- checked: all_unchecked,
1168
- nameattr: 'all',
1169
- name: 'All',
1170
- print_count: false,
1171
- count: all_count
1172
- };
1173
-
1174
- params.type[facet.type] = true;
1175
-
1176
- data.unshift(params);
1177
-
1178
- return data;
1179
- };
1180
-
1181
- /**
1182
- * Handle click on menu custom facet
1183
- */
1184
- $("body").on("click", ".sub_facet.menu", function (e) {
1185
-
1186
- e.stopImmediatePropagation();
1187
-
1188
- if ($(this).attr("data-name") == "all")
1189
- helper.state.clearRefinements($(this).attr("data-attribute"));
1190
-
1191
- $(this).find("input[type='checkbox']").each(function (i) {
1192
- $(this).prop("checked", !$(this).prop("checked"));
1193
-
1194
- if (false == helper.isRefined($(this).attr("data-attribute"), $(this).attr("data-name")))
1195
- helper.state.clearRefinements($(this).attr("data-attribute"));
1196
-
1197
- if ($(this).attr("data-name") != "all")
1198
- helper.toggleRefine($(this).attr("data-attribute"), $(this).attr("data-name"));
1199
- });
1200
-
1201
- performQueries(true);
1202
- });
1203
-
1204
- /**
1205
- * Handle click on conjunctive and disjunctive facet
1206
- */
1207
- $("body").on("click", ".sub_facet", function () {
1208
-
1209
- $(this).find("input[type='checkbox']").each(function (i) {
1210
- $(this).prop("checked", !$(this).prop("checked"));
1211
-
1212
- helper.toggleRefine($(this).attr("data-attribute"), $(this).attr("data-name"));
1213
- });
1214
-
1215
- performQueries(true);
1216
- });
1217
-
1218
- /**
1219
- * Handle jquery-ui slider initialisation
1220
- */
1221
- $("body").on("slide", "", function (event, ui) {
1222
- updateSlideInfos(ui);
1223
- });
1224
-
1225
- /**
1226
- * Handle sort change
1227
- */
1228
- $("body").on("change", "#index_to_use", function () {
1229
- helper.setIndex($(this).val());
1230
-
1231
- helper.setCurrentPage(0);
1232
-
1233
- performQueries(true);
1234
- });
1235
-
1236
- /**
1237
- * Handle jquery-ui slide event
1238
- */
1239
- $("body").on("slidechange", ".algolia-slider-true", function (event, ui) {
1240
-
1241
- var slide_dom = $(ui.handle).closest(".algolia-slider");
1242
- var min = slide_dom.slider("values")[0];
1243
- var max = slide_dom.slider("values")[1];
1244
-
1245
- if (parseInt(slide_dom.slider("values")[0]) >= parseInt(slide_dom.attr("data-min")))
1246
- helper.addNumericRefinement(slide_dom.attr("data-attribute"), ">=", min);
1247
- if (parseInt(slide_dom.slider("values")[1]) <= parseInt(slide_dom.attr("data-max")))
1248
- helper.addNumericRefinement(slide_dom.attr("data-attribute"), "<=", max);
1249
-
1250
- if (parseInt(min) == parseInt(slide_dom.attr("data-min")))
1251
- helper.removeNumericRefinement(slide_dom.attr("data-attribute"), ">=");
1252
-
1253
- if (parseInt(max) == parseInt(slide_dom.attr("data-max")))
1254
- helper.removeNumericRefinement(slide_dom.attr("data-attribute"), "<=");
1255
-
1256
- updateSlideInfos(ui);
1257
- performQueries(true);
1258
- });
1259
-
1260
- /**
1261
- * Handle page change
1262
- */
1263
- $("body").on("click", ".algolia-pagination a", function (e) {
1264
- e.preventDefault();
1265
-
1266
- gotoPage($(this).attr("data-page"));
1267
- performQueries(true);
1268
-
1269
- $("body").scrollTop(0);
1270
-
1271
- return false;
1272
- });
1273
-
1274
- /** Handle input clearing **/
1275
- $('body').on('click', '.clear-button', function () {
1276
- $(instant_selector).val('').focus();
1277
- helper.clearRefinements().setQuery('');
1278
-
1279
- performQueries(true);
1280
- });
1281
-
1282
- /**
1283
- * Handle search
1284
- */
1285
-
1286
- $('body').on('keyup', instant_selector, function (e) {
1287
- e.preventDefault();
1288
-
1289
- helper.setQuery($(this).val());
1290
-
1291
- /* Uncomment to clear refinements on keyup */
1292
-
1293
- //helper.clearRefinements();
1294
-
1295
- performQueries(false);
1296
-
1297
- return false;
1298
- });
1299
-
1300
- function updateSliderValues()
1301
- {
1302
- $(".algolia-slider-true").each(function (i) {
1303
- var min = $(this).attr("data-min");
1304
- var max = $(this).attr("data-max");
1305
-
1306
- var new_min = helper.state.getNumericRefinement($(this).attr("data-attribute"), ">=");
1307
- var new_max = helper.state.getNumericRefinement($(this).attr("data-attribute"), "<=");
1308
-
1309
- if (new_min != undefined)
1310
- min = new_min;
1311
-
1312
- if (new_max != undefined)
1313
- max = new_max;
1314
-
1315
- $(this).slider({
1316
- min: parseInt($(this).attr("data-min")),
1317
- max: parseInt($(this).attr("data-max")),
1318
- range: true,
1319
- values: [min, max]
1320
- });
1321
- });
1322
- }
1323
-
1324
- function updateSlideInfos(ui)
1325
- {
1326
- var infos = $(ui.handle).closest(".algolia-slider").nextAll(".algolia-slider-info");
1327
-
1328
- infos.find(".min").html(ui.values[0]);
1329
- infos.find(".max").html(ui.values[1]);
1330
- }
1331
-
1332
- /**
1333
- * Initialization
1334
- */
1335
-
1336
- /** Clean input **/
1337
- $(algoliaConfig.autocomplete.selector).attr('autocomplete', 'off').attr('autocorrect', 'off').attr('spellcheck', 'false').attr('autocapitalize', 'off');
1338
-
1339
- if (<?php echo $isSearchPage ? "true" : "false"; ?> || location.hash.length > 1) {
1340
- getRefinementsFromUrl();
1341
- }
1342
-
1343
- window.addEventListener("popstate", function(e) {
1344
- getRefinementsFromUrl();
1345
- });
1346
-
1347
-
1348
- onfocus_css = {
1349
- 'opacity': '1',
1350
- 'fill': '#54A5CD',
1351
- 'stroke': '#54A5CD'
1352
- };
1353
-
1354
- onblur_css = {
1355
- 'opacity': '0.4',
1356
- 'fill': '#AAA',
1357
- 'stroke': '#AAA'
1358
- };
1359
-
1360
- $('#search').focus(function () {
1361
- $(this).parent().next().css(onfocus_css);
1362
- }).blur(function () {
1363
- $(this).parent().next().css(onblur_css);
1364
- }).parent().next().css(onblur_css);
1365
-
1366
- }
1367
- });
1368
-
1369
- //]]>
1370
- </script>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ $config = Mage::helper('algoliasearch/config');
3
+ $catalogSearchHelper = $this->helper('catalogsearch'); /** @var $catalogSearchHelper Mage_CatalogSearch_Helper_Data */
4
+ $algoliaSearchHelper = $this->helper('algoliasearch'); /** @var $algoliaSearchHelper Algolia_Algoliasearch_Helper_Data */
5
+ $product_helper = Mage::helper('algoliasearch/entity_producthelper');
6
+ $formKey = Mage::getSingleton('core/session')->getFormKey();
7
+
8
+ $base_url = Mage::getBaseUrl();
9
+
10
+ $isSearchPage = false;;
11
+ $hash_path = null;
12
+
13
+ $group_id = Mage::getSingleton('customer/session')->getCustomerGroupId();
14
+
15
+ $suffix_index_name = '';
16
+
17
+ if ($config->isCustomerGroupsEnabled(Mage::app()->getStore()->getStoreId()))
18
+ {
19
+ $suffix_index_name = '_group_' . $group_id;
20
+ }
21
+
22
+ /**
23
+ * Handle category replacement
24
+ */
25
+ if($config->isInstantEnabled() && $config->replaceCategories() && Mage::app()->getRequest()->getControllerName() == 'category')
26
+ {
27
+ $category = Mage::registry('current_category');
28
+
29
+ if ($category)
30
+ {
31
+ $category->getUrlInstance()->setStore(Mage::app()->getStore()->getStoreId());
32
+
33
+ $path = '';
34
+
35
+ foreach ($category->getPathIds() as $treeCategoryId) {
36
+ if ($path != '') {
37
+ $path .= ' /// ';
38
+ }
39
+
40
+ $path .= $product_helper->getCategoryName($treeCategoryId, Mage::app()->getStore()->getStoreId());
41
+ }
42
+
43
+ $indexName = $product_helper->getIndexName(Mage::app()->getStore()->getStoreId()).$suffix_index_name;
44
+ $category_url = $category->getUrl($category);
45
+ $hash_path = '#q=&page=0&refinements=%5B%7B%22categories%22%3A%5B%22'.$path.'%22%5D%7D%5D&numerics_refinements=%7B%7D&index_name=%22'.$indexName.'%22';
46
+
47
+ $isSearchPage = true;
48
+ }
49
+ }
50
+
51
+ /**
52
+ * Handle search
53
+ */
54
+ if ($config->isInstantEnabled())
55
+ {
56
+ $pageIdentifier = Mage::app()->getFrontController()->getAction()->getFullActionName();
57
+
58
+ if ($pageIdentifier === 'catalogsearch_result_index')
59
+ {
60
+ $query = Mage::app()->getRequest()->getParam('q');
61
+
62
+ if ($query == '__empty__')
63
+ $query = '';
64
+
65
+ $product_helper = Mage::helper('algoliasearch/entity_producthelper');
66
+
67
+ $hash_path = '#q='.$query.'&page=0&refinements=%5B%5D&numerics_refinements=%7B%7D&index_name=%22'.$product_helper->getIndexName().$suffix_index_name.'%22';
68
+
69
+ $refinement_key = Mage::app()->getRequest()->getParam('refinement_key');
70
+ $refinement_value = Mage::app()->getRequest()->getParam('refinement_value');
71
+
72
+ if ($refinement_key !== null)
73
+ {
74
+ $hash_path = '#q=&page=0&refinements=%5B%7B%22' . $refinement_key . '%22%3A%5B%22' . $refinement_value . '%22%5D%7D%5D&numerics_refinements=%7B%7D&index_name=%22' . $product_helper->getBaseIndexName() . '_products%22';
75
+ }
76
+
77
+ $isSearchPage = true;
78
+ }
79
+ }
80
+
81
+
82
+ if ($hash_path !== null)
83
+ {
84
+ echo '<script>if (window.location.hash.length <= 1) { window.location.hash = "'.$hash_path.'"; }</script>';
85
+ }
86
+
87
+
88
+
89
+ if ($base_url[strlen($base_url) - 1] == '/')
90
+ $base_url = substr($base_url, 0, strlen($base_url) - 1);
91
+
92
+ if ($config->isInstantEnabled() && $isSearchPage) {
93
+ // hide the instant-search selector ASAP to remove flickering. Will be re-displayed later with JS
94
+ echo '<style>' . $config->getInstantSelector() . '{ display: none; }</style>';
95
+
96
+
97
+ }
98
+ ?>
99
+
100
+ <!--
101
+ //================================
102
+ //
103
+ // Search box
104
+ //
105
+ //================================
106
+ -->
107
+
108
+ <?php
109
+
110
+ $types = array();
111
+
112
+ if ($config->getNumberOfProductSuggestions() > 0)
113
+ $types[] = $this->__('products');
114
+
115
+ if ($config->getNumberOfCategorySuggestions() > 0)
116
+ $types[] = $this->__('categories');
117
+
118
+ if ($config->getNumberOfPageSuggestions() > 0)
119
+ $types[] = $this->__('pages');
120
+
121
+ $or = count($types) > 1 ? ' '.$this->__('or').' ' : '';
122
+
123
+ $placeholder = $this->__('Search');
124
+
125
+ if (count($types) > 0)
126
+ {
127
+ $placeholder = $this->__('Search for'). ' ' . implode(', ', array_slice($types, 0, count($types) - 1)) . $or . $types[count($types) - 1];
128
+ }
129
+
130
+ $class = $isSearchPage ? 'search-page' : '';
131
+
132
+ ?>
133
+
134
+ <form id="search_mini_form" action="<?php echo $catalogSearchHelper->getResultUrl() ?>" method="get">
135
+ <div id="algolia-searchbox" class="<?php echo $class; ?>">
136
+ <label for="search"><?php echo $this->__('Search:') ?></label>
137
+ <input id="search" type="text" name="<?php echo $catalogSearchHelper->getQueryParamName() ?>" class="input-text" autocomplete="off" spellcheck="false" autocorrect="off" autocapitalize="off" placeholder="<?php echo $placeholder; ?>" />
138
+ <svg id="algolia-glass" xmlns="http://www.w3.org/2000/svg" class="magnifying-glass" width="24" height="24" viewBox="0 0 128 128" >
139
+ <g transform="scale(4)">
140
+ <path stroke-width="3" d="M19.5 19.582l9.438 9.438"></path>
141
+ <circle stroke-width="3" cx="12" cy="12" r="10.5" fill="none"></circle>
142
+ <path d="M23.646 20.354l-3.293 3.293c-.195.195-.195.512 0 .707l7.293 7.293c.195.195.512.195.707 0l3.293-3.293c.195-.195.195-.512 0-.707l-7.293-7.293c-.195-.195-.512-.195-.707 0z" ></path>
143
+ </g>
144
+ </svg>
145
+ </div>
146
+ </form>
147
+
148
+ <!--
149
+ //================================
150
+ //
151
+ // Multi-category Autocomplete
152
+ //
153
+ //================================
154
+ -->
155
+
156
+ <!-- Product hit template -->
157
+ <script type="text/template" id="autocomplete_products_template">
158
+ <a class="algoliasearch-autocomplete-hit" href="{{url}}">
159
+ {{#thumbnail_url}}
160
+ <div class="thumb"><img src="{{thumbnail_url}}" /></div>
161
+ {{/thumbnail_url}}
162
+ {{#price_with_tax}}
163
+ <div class="algoliasearch-autocomplete-price">
164
+ {{#special_price_with_tax}}
165
+ <div class="after_special">
166
+ {{special_price_with_tax_formated}}
167
+ </div>
168
+ {{/special_price_with_tax}}
169
+ <div {{#special_price_with_tax}}class="before_special"{{/special_price_with_tax}}>
170
+ {{price_with_tax_formated}}
171
+ </div>
172
+ </div>
173
+ {{/price_with_tax}}
174
+ <div class="info">
175
+ {{{_highlightResult.name.value}}}
176
+
177
+ {{#categories_without_path}}
178
+ <div class="algoliasearch-autocomplete-category">
179
+ <?php echo $this->__('in'); ?> {{categories_without_path}}
180
+ </div>
181
+ {{/categories_without_path}}
182
+ </div>
183
+ <div class="clearfix"></div>
184
+ </a>
185
+ </script>
186
+
187
+ <!-- Category hit template -->
188
+ <script type="text/template" id="autocomplete_categories_template">
189
+ <a class="algoliasearch-autocomplete-hit" href="{{url}}">
190
+ {{#image_url}}
191
+ <div class="thumb">
192
+ <img src="{{image_url}}" />
193
+ </div>
194
+ {{/image_url}}
195
+
196
+ {{#image_url}}
197
+ <div class="info">
198
+ {{/image_url}}
199
+ {{^image_url}}
200
+ <div class="info-without-thumb">
201
+ {{{_highlightResult.path.value}}}
202
+
203
+ {{#product_count}}
204
+ <small>( {{product_count}} )</small>
205
+ {{/product_count}}
206
+
207
+ </div>
208
+ <div class="clearfix"></div>
209
+ {{/image_url}}
210
+ </div>
211
+ </a>
212
+ </script>
213
+
214
+ <!-- Page hit template -->
215
+ <script type="text/template" id="autocomplete_pages_template">
216
+ <a class="algoliasearch-autocomplete-hit" href="{{url}}">
217
+ <div class="info-without-thumb">
218
+ {{{_highlightResult.name.value}}}
219
+ </div>
220
+ <div class="clearfix"></div>
221
+ </a>
222
+ </script>
223
+
224
+ <!-- Extra attribute hit template -->
225
+ <script type="text/template" id="autocomplete_extra_template">
226
+ <a class="algoliasearch-autocomplete-hit" href="{{url}}">
227
+ <div class="info-without-thumb">
228
+ {{{_highlightResult.value.value}}}
229
+ </div>
230
+ <div class="clearfix"></div>
231
+ </a>
232
+ </script>
233
+
234
+ <!-- Suggestion hit template -->
235
+ <script type="text/template" id="autocomplete_suggestions_template">
236
+ <a class="algoliasearch-autocomplete-hit" href="{{url}}">
237
+ <div class="info-without-thumb">
238
+ {{{_highlightResult.query.value}}}
239
+
240
+ {{#category}}
241
+ <span class="text-muted"><?php echo $this->__('in'); ?></span> <span class="category-tag">{{category}}</span>
242
+ {{/category}}
243
+ </div>
244
+ <div class="clearfix"></div>
245
+ </a>
246
+ </script>
247
+
248
+
249
+ <!--
250
+ //================================
251
+ //
252
+ // Instant search results page
253
+ //
254
+ //================================
255
+ -->
256
+
257
+
258
+
259
+ <!-- Wrapping template -->
260
+ <script type="text/template" id="instant_wrapper_template">
261
+
262
+ <div id="algolia_instant_selector"<?php echo count($config->getFacets()) > 0 ? ' class="with-facets"' : '' ?>>
263
+
264
+ <div class="row">
265
+ <div class="col-md-offset-3 col-md-9">
266
+ {{#second_bar}}
267
+ <div id="instant-search-bar-container">
268
+ <div id="instant-search-box">
269
+ <label for="instant-search-bar">
270
+ <?php echo $this->__('Search :'); ?>
271
+ </label>
272
+
273
+ <input value="<?php echo $catalogSearchHelper->getEscapedQueryText() ?>" placeholder="<?php echo $this->__('Search for products'); ?>" id="instant-search-bar" type="text" autocomplete="off" spellcheck="false" autocorrect="off" autocapitalize="off" />
274
+
275
+ <svg xmlns="http://www.w3.org/2000/svg" class="magnifying-glass" width="24" height="24" viewBox="0 0 128 128">
276
+ <g transform="scale(4)">
277
+ <path stroke-width="3" d="M19.5 19.582l9.438 9.438"></path>
278
+ <circle stroke-width="3" cx="12" cy="12" r="10.5" fill="none"></circle>
279
+ <path d="M23.646 20.354l-3.293 3.293c-.195.195-.195.512 0 .707l7.293 7.293c.195.195.512.195.707 0l3.293-3.293c.195-.195.195-.512 0-.707l-7.293-7.293c-.195-.195-.512-.195-.707 0z"></path>
280
+ </g>
281
+ </svg>
282
+ </div>
283
+ </div>
284
+ {{/second_bar}}
285
+ </div>
286
+ </div>
287
+
288
+ <div class="row">
289
+ <div class="col-md-3" id="algolia-left-container">
290
+ <div id="refine-toggle" class="visible-xs visible-sm">+ <?php echo $this->__('Refine'); ?></div>
291
+ <div class="hidden-xs hidden-sm" id="instant-search-facets-container"></div>
292
+ </div>
293
+
294
+ <div class="col-md-9" id="algolia-right-container">
295
+ <div id="instant-search-results-container"></div>
296
+ <div id="instant-search-pagination-container"></div>
297
+ </div>
298
+ </div>
299
+
300
+ </div>
301
+ </script>
302
+
303
+ <!-- Product hit template -->
304
+ <script type="text/template" id="instant-content-template">
305
+ <div class="hits">
306
+ {{#hits.length}}
307
+ <div class="infos">
308
+ <div class="pull-left">
309
+ {{nbHits}} <?php echo $this->__('result'); ?>{{^nbHits_one}}<?php echo $this->__('s'); ?>{{/nbHits_one}} <?php echo $this->__('found'); ?> {{#query}}<?php echo $this->__('matching'); ?> "<strong>{{query}}</strong>" {{/query}}<?php echo $this->__('in'); ?> {{processingTimeMS}} <?php echo $this->__('ms'); ?>
310
+ </div>
311
+ {{#sorting_indices.length}}
312
+ <div class="pull-right">
313
+ <?php echo $this->__('Order by'); ?>
314
+ <select id="index_to_use">
315
+ <option {{#sortSelected}}{{relevance_index_name}}{{/sortSelected}} value="{{relevance_index_name}}"><?php echo $this->__('Relevance'); ?></option>
316
+ {{#sorting_indices}}
317
+ <option {{#sortSelected}}{{index_name}}{{/sortSelected}} value="{{index_name}}">{{label}}</option>
318
+ {{/sorting_indices}}
319
+ </select>
320
+ </div>
321
+ {{/sorting_indices.length}}
322
+ <div class="clearfix"></div>
323
+ </div>
324
+ {{/hits.length}}
325
+
326
+ <div class="row">
327
+ {{#hits}}
328
+ <div class="col-md-4 col-sm-6">
329
+ <div class="result-wrapper">
330
+ <a href="{{url}}" class="result">
331
+ <div class="result-content">
332
+ <div class="result-thumbnail">
333
+ {{#image_url}}
334
+ <img src="{{{ image_url }}}" />
335
+ {{/image_url}}
336
+ {{^image_url}}
337
+ <span class="no-image"></span>
338
+ {{/image_url}}
339
+ </div>
340
+ <div class="result-sub-content">
341
+ <h3 class="result-title text-ellipsis">
342
+ {{{ _highlightResult.name.value }}}
343
+ </h3>
344
+ <div class="ratings">
345
+ <div class="rating-box">
346
+ <div class="rating" style="width:{{rating_summary}}%" width="148" height="148"></div>
347
+ </div>
348
+ </div>
349
+ <div class="price">
350
+ <div class="algoliasearch-autocomplete-price">
351
+ <div>
352
+ {{#special_price_with_tax}}
353
+ <span class="after_special">
354
+ {{special_price_with_tax_formated}}
355
+ </span>
356
+ {{/special_price_with_tax}}
357
+
358
+ {{#special_price_with_tax}}
359
+ <span class="before_special">
360
+ {{/special_price_with_tax}}
361
+
362
+ {{#price_with_tax}}{{price_with_tax_formated}}{{/price_with_tax}}
363
+ {{^price_with_tax}}
364
+ {{#min_with_tax_formated}}
365
+ {{min_with_tax_formated}} - {{max_with_tax_formated}}
366
+ {{/min_with_tax_formated}}
367
+ {{^min_with_tax_formated}}-{{/min_with_tax_formated}}
368
+ {{/price_with_tax}}
369
+
370
+ {{#special_price_with_tax}}
371
+ </span>
372
+ {{/special_price_with_tax}}
373
+
374
+
375
+ </div>
376
+ </div>
377
+ </div>
378
+ <div class="result-description text-ellipsis">
379
+ {{{ _highlightResult.description.value }}}
380
+ </div>
381
+
382
+ {{#isAddToCartEnabled}}
383
+ {{#in_stock}}
384
+
385
+ <form action="<?php echo $base_url; ?>/checkout/cart/add/product/{{objectID}}" method="post">
386
+ <input type="hidden" name="form_key" value="<?php echo $formKey; ?>" />
387
+
388
+ <input type="hidden" name="qty" value="1">
389
+
390
+ <button type="submit"><?php echo $this->__('Add to Cart'); ?></button>
391
+ </form>
392
+ {{/in_stock}}
393
+ {{/isAddToCartEnabled}}
394
+ </div>
395
+ </div>
396
+ <div class="clearfix"></div>
397
+ </a>
398
+ </div>
399
+ </div>
400
+ {{/hits}}
401
+ </div>
402
+
403
+ {{^hits.length}}
404
+ <div class="no-results">
405
+ <?php echo $this->__('No results found matching'); ?> "<strong>{{query}}</strong>". <span class="button clear-button"><?php echo $this->__('Clear query and filters'); ?></span>
406
+ </div>
407
+ {{/hits.length}}
408
+ <div class="clearfix"></div>
409
+ </div>
410
+ </script>
411
+
412
+ <script type="text/template" id="instant-facets-hierarchical-template">
413
+ {{#data}}
414
+ <div style="padding-left: 10px; padding-right: 0px;" class="hierarchical_facet">
415
+ <div data-name="{{attribute}}" data-path="{{path}}" data-type="hierarchical" class="{{#isRefined}}checked {{/isRefined}}sub_facet hierarchical">
416
+ <input style="display: none;" data-attribute="{{attribute}}" {{#isRefined}}checked{{/isRefined}} data-name="{{name}}" class="facet_value" type="checkbox" />
417
+ {{name}}
418
+ {{#count}}<span class="count">{{count}}</span>{{/count}}
419
+ </div>
420
+ {{>facet_hierarchical}}
421
+ </div>
422
+ {{/data}}
423
+ </script>
424
+
425
+ <!-- Facet template -->
426
+ <script type="text/template" id="instant-facets-template">
427
+ <div class="facets">
428
+ {{#facets}}
429
+ {{#count}}
430
+ <div class="facet">
431
+ <div class="name">
432
+ {{ facet_categorie_name }}
433
+ </div>
434
+ <div>
435
+ {{#sub_facets}}
436
+
437
+ {{#type.menu}}
438
+ <div data-attribute="{{attribute}}" data-name="{{nameattr}}" data-type="menu" class="{{#checked}}checked {{/checked}}sub_facet menu {{#empty}}empty{{/empty}}">
439
+ <input style="display: none;" data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
440
+ {{name}}
441
+ {{#print_count}}<span class="count">{{count}}</span>{{/print_count}}
442
+ </div>
443
+ {{/type.menu}}
444
+
445
+ {{#type.conjunctive}}
446
+ <div data-name="{{attribute}}" data-type="conjunctive" class="{{#checked}}checked {{/checked}}sub_facet conjunctive {{#empty}}empty{{/empty}}">
447
+ <input style="display: none;" data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
448
+ {{name}}
449
+ {{#count}}<span class="count">{{count}}</span>{{/count}}
450
+ </div>
451
+ {{/type.conjunctive}}
452
+
453
+ {{#type.slider}}
454
+ <div class="algolia-slider algolia-slider-true" data-attribute="{{attribute}}" data-min="{{min}}" data-max="{{max}}"></div>
455
+ <div class="algolia-slider-info">
456
+ <div class="min" style="float: left;">{{current_min}}</div>
457
+ <div class="max" style="float: right;">{{current_max}}</div>
458
+ <div class="clearfix"></div>
459
+ </div>
460
+ {{/type.slider}}
461
+
462
+ {{#type.disjunctive}}
463
+ <div data-name="{{attribute}}" data-type="disjunctive" class="{{#checked}}checked {{/checked}}sub_facet disjunctive {{#empty}}empty{{/empty}}">
464
+ <input data-attribute="{{attribute}}" {{#checked}}checked{{/checked}} data-name="{{nameattr}}" class="facet_value" type="checkbox" />
465
+ {{name}}
466
+ {{#count}}<span class="count">{{count}}</span>{{/count}}
467
+ </div>
468
+ {{/type.disjunctive}}
469
+
470
+ {{#type.hierarchical}}
471
+ <div style="margin-left: -10px;">
472
+ {{>facet_hierarchical}}
473
+ </div>
474
+ {{/type.hierarchical}}
475
+
476
+ {{/sub_facets}}
477
+ </div>
478
+ </div>
479
+ {{/count}}
480
+ {{/facets}}
481
+ </div>
482
+ </script>
483
+
484
+ <!-- Pagination template -->
485
+ <script type="text/template" id="instant-pagination-template">
486
+ <div class="pagination-wrapper">
487
+ <div class="text-center">
488
+ <ul class="algolia-pagination">
489
+ <a href="#" data-page="{{prev_page}}">
490
+ <li {{^prev_page}}class="disabled"{{/prev_page}}>
491
+ &laquo;
492
+ </li>
493
+ </a>
494
+
495
+ {{#pages}}
496
+ <a href="#" data-page="{{number}}">
497
+ <li class="{{#current}}active{{/current}}{{#disabled}}disabled{{/disabled}}">
498
+ {{ number }}
499
+ </li>
500
+ </a>
501
+ {{/pages}}
502
+ <a href="#" data-page="{{next_page}}">
503
+ <li {{^next_page}}class="disabled"{{/next_page}}>
504
+ &raquo;
505
+ </li>
506
+ </a>
507
+ </ul>
508
+ </div>
509
+ </div>
510
+ </script>
511
+
512
+
513
+ <!--
514
+ //================================
515
+ //
516
+ // JavaScript
517
+ //
518
+ //================================
519
+ -->
520
+
521
+
522
+ <script type="text/javascript">
523
+ //<![CDATA[
524
+
525
+ algoliaBundle.$(function($) {
526
+ var supportsHistory = window.history && window.history.pushState;
527
+
528
+ var algoliaConfig = {
529
+ instant: {
530
+ enabled: <?php echo $config->isInstantEnabled() ? "true" : "false"; ?>,
531
+ selector: '<?php echo $config->getInstantSelector(); ?>',
532
+ isAddToCartEnabled: <?php echo $config->isAddToCartEnable() ? "true" : "false"; ?>
533
+ },
534
+ autocomplete: {
535
+ enabled: <?php echo $config->isAutoCompleteEnabled() ? "true" : "false"; ?>,
536
+ selector: '#search',
537
+ hitsPerPage: {
538
+ products: <?php echo (int) $config->getNumberOfProductSuggestions() ?>,
539
+ categories: <?php echo (int) $config->getNumberOfCategorySuggestions() ?>,
540
+ pages: <?php echo (int) $config->getNumberOfPageSuggestions() ?>,
541
+ suggestions: <?php echo (int) $config->getNumberOfQuerySuggestions() ?>
542
+ },
543
+ templates: {
544
+ suggestions: algoliaBundle.Hogan.compile($('#autocomplete_suggestions_template').html()),
545
+ products: algoliaBundle.Hogan.compile($('#autocomplete_products_template').html()),
546
+ categories: algoliaBundle.Hogan.compile($('#autocomplete_categories_template').html()),
547
+ pages: algoliaBundle.Hogan.compile($('#autocomplete_pages_template').html()),
548
+ additionnalSection: algoliaBundle.Hogan.compile($('#autocomplete_extra_template').html()),
549
+ },
550
+ titles: {
551
+ products: '<?php echo $this->__('Products'); ?>',
552
+ categories: '<?php echo $this->__('Categories') ?>',
553
+ pages: '<?php echo $this->__('Pages') ?>',
554
+ suggestions: '<?php echo $this->__('Suggestions') ?>'
555
+ },
556
+ additionnalSection: <?php echo json_encode($config->getAutocompleteAdditionnalSections()); ?>
557
+ },
558
+ applicationId: '<?php echo $config->getApplicationID() ?>',
559
+ indexName: '<?php echo $product_helper->getBaseIndexName(); ?>',
560
+ suffixIndexName: '<?php echo $suffix_index_name; ?>',
561
+ apiKey: '<?php echo $config->getSearchOnlyAPIKey() ?>',
562
+ facets: <?php echo json_encode($config->getFacets()); ?>,
563
+ hitsPerPage: <?php echo (int) $config->getNumberOfProductResults() ?>,
564
+ sortingIndices: <?php echo json_encode(array_values($config->getSortingIndices())); ?>,
565
+ isSearchPage: <?php echo $isSearchPage ? "true" : "false" ?>,
566
+ removeBranding: <?php echo $config->isRemoveBranding() ? "true" : "false"; ?>
567
+ };
568
+
569
+
570
+ $('#search').closest('form').submit(function(e) {
571
+ var query = $('#search').val();
572
+
573
+ if (algoliaConfig.instant.enabled && query == '')
574
+ query = '__empty__';
575
+
576
+ var url = $(this).attr('action') + '?q=' + query;
577
+
578
+ window.location = url;
579
+
580
+ return false;
581
+ });
582
+
583
+ /*****************
584
+ **
585
+ ** INITIALIZATION
586
+ **
587
+ *****************/
588
+
589
+ var algolia_client = algoliaBundle.algoliasearch(algoliaConfig.applicationId, algoliaConfig.apiKey);
590
+
591
+ /**
592
+ * Foreach Type decide if it need to have a conjunctive or dijunctive faceting
593
+ * When you create a custom facet type you need to add it here.
594
+ * Example : 'menu'
595
+ */
596
+ var conjunctive_facets = [];
597
+ var hierarchical_facets = [];
598
+ var disjunctive_facets = [];
599
+ var disjunctive_facets_empty = [];
600
+
601
+ for (var i = 0; i < algoliaConfig.facets.length; i++)
602
+ {
603
+ /** Force categories to be hierarchical **/
604
+ if (algoliaConfig.facets[i].attribute == "categories")
605
+ algoliaConfig.facets[i].type = "hierarchical";
606
+
607
+ if (algoliaConfig.facets[i].type == "conjunctive")
608
+ conjunctive_facets.push(algoliaConfig.facets[i].attribute);
609
+
610
+ if (algoliaConfig.facets[i].type == "disjunctive")
611
+ {
612
+ disjunctive_facets.push(algoliaConfig.facets[i].attribute);
613
+ disjunctive_facets_empty.push(algoliaConfig.facets[i].attribute);
614
+ }
615
+
616
+ if (algoliaConfig.facets[i].type == "hierarchical")
617
+ {
618
+
619
+ var hierarchical_levels = [];
620
+
621
+ for (var l = 0; l < 10; l++)
622
+ hierarchical_levels.push('categories.level' + l.toString());
623
+
624
+ if (algoliaConfig.facets[i].attribute === 'categories')
625
+ hierarchical_facets.push({
626
+ name: algoliaConfig.facets[i].attribute,
627
+ attributes: hierarchical_levels,
628
+ separator: ' /// ',
629
+ alwaysGetRootLevel: true,
630
+ sortBy: ['name:asc']
631
+ });
632
+ else
633
+ disjunctive_facets.push(algoliaConfig.facets[i].attribute);
634
+ }
635
+
636
+ if (algoliaConfig.facets[i].type == "slider")
637
+ disjunctive_facets.push(algoliaConfig.facets[i].attribute);
638
+
639
+ if (algoliaConfig.facets[i].type == "menu")
640
+ {
641
+ disjunctive_facets.push(algoliaConfig.facets[i].attribute);
642
+ disjunctive_facets_empty.push(algoliaConfig.facets[i].attribute);
643
+ }
644
+ }
645
+
646
+ var helper = algoliaBundle.algoliasearchHelper(algolia_client, algoliaConfig.indexName + '_products' + algoliaConfig.suffixIndexName, {
647
+ facets: conjunctive_facets,
648
+ disjunctiveFacets: disjunctive_facets,
649
+ hierarchicalFacets: hierarchical_facets,
650
+ hitsPerPage: algoliaConfig.hitsPerPage
651
+ });
652
+
653
+ helper.setQuery('');
654
+
655
+ var helper_empty = algoliaBundle.algoliasearchHelper(algolia_client, algoliaConfig.indexName + '_products' + algoliaConfig.suffixIndexName, {
656
+ facets: conjunctive_facets,
657
+ disjunctiveFacets: disjunctive_facets_empty,
658
+ hierarchicalFacets: hierarchical_facets,
659
+ hitsPerPage: algoliaConfig.hitsPerPage
660
+ });
661
+
662
+ helper_empty.setQuery('');
663
+
664
+ /**
665
+ * Helper functions
666
+ */
667
+ var history_timeout;
668
+ var custom_facets_types = [];
669
+
670
+ custom_facets_types["slider"] = function (helper, content, facet) {
671
+ if (content.getFacetByName(facet.attribute) != undefined)
672
+ {
673
+ var min = content.getFacetByName(facet.attribute).stats.min;
674
+ var max = content.getFacetByName(facet.attribute).stats.max;
675
+
676
+ var current_min = helper.state.getNumericRefinement(facet.attribute, ">=");
677
+ var current_max = helper.state.getNumericRefinement(facet.attribute, "<=");
678
+
679
+ if (current_min == undefined)
680
+ current_min = min;
681
+
682
+ if (current_max == undefined)
683
+ current_max = max;
684
+
685
+ var params = {
686
+ type: {},
687
+ current_min: Math.floor(current_min),
688
+ current_max: Math.ceil(current_max),
689
+ count: min == max ? 0 : 1,
690
+ min: Math.floor(min),
691
+ max: Math.ceil(max)
692
+ };
693
+
694
+ params.type[facet.type] = true;
695
+
696
+ return [params];
697
+ }
698
+
699
+ return [];
700
+ };
701
+
702
+ var updateUrl = function (push_state) {
703
+
704
+ var refinements = [];
705
+
706
+ /** Get refinements for conjunctive facets **/
707
+ for (var refine in helper.state.facetsRefinements)
708
+ {
709
+ if (helper.state.facetsRefinements[refine])
710
+ {
711
+ var r = {};
712
+
713
+ r[refine] = helper.state.facetsRefinements[refine];
714
+
715
+ refinements.push(r);
716
+ }
717
+ }
718
+
719
+ /** Get refinements for disjunctive facets **/
720
+ for (var refine in helper.state.disjunctiveFacetsRefinements)
721
+ {
722
+ var r = {};
723
+
724
+ r[refine] = helper.state.disjunctiveFacetsRefinements[refine];
725
+
726
+ refinements.push(r);
727
+ }
728
+
729
+ /** Get refinements for hierarchical facets **/
730
+ for (var refine in helper.state.hierarchicalFacetsRefinements)
731
+ {
732
+ var r = {};
733
+
734
+ r[refine] = helper.state.hierarchicalFacetsRefinements[refine];
735
+
736
+ refinements.push(r);
737
+ }
738
+
739
+ var url = '#q=' + encodeURIComponent(helper.state.query) +
740
+ '&page=' + helper.getCurrentPage() +
741
+ '&refinements=' + encodeURIComponent(JSON.stringify(refinements)) +
742
+ '&numerics_refinements=' + encodeURIComponent(JSON.stringify(helper.state.numericRefinements)) +
743
+ '&index_name=' + encodeURIComponent(JSON.stringify(helper.getIndex()));
744
+
745
+ /** If we have pushState push_state is false wait for one second to push the state in history **/
746
+ if (push_state) {
747
+ updateBrowserUrlBar(url);
748
+ }
749
+ else
750
+ {
751
+ clearTimeout(history_timeout);
752
+ history_timeout = setTimeout(function() {
753
+ updateBrowserUrlBar(url)
754
+ }, 1000);
755
+ }
756
+ };
757
+
758
+ var getRefinementsFromUrl = function() {
759
+
760
+ if (location.hash && location.hash.indexOf('#q=') === 0)
761
+ {
762
+ var params = location.hash.substring(3);
763
+ var pageParamOffset = params.indexOf('&page=');
764
+ var refinementsParamOffset = params.indexOf('&refinements=');
765
+ var numericsRefinementsParamOffset = params.indexOf('&numerics_refinements=');
766
+ var indexNameOffset = params.indexOf('&index_name=');
767
+
768
+ var q = decodeURIComponent(params.substring(0, pageParamOffset));
769
+ var page = parseInt(params.substring(pageParamOffset + '&page='.length, refinementsParamOffset));
770
+ var refinements = JSON.parse(decodeURIComponent(params.substring(refinementsParamOffset + '&refinements='.length, numericsRefinementsParamOffset)));
771
+ var numericsRefinements = JSON.parse(decodeURIComponent(params.substring(numericsRefinementsParamOffset + '&numerics_refinements='.length, indexNameOffset)));
772
+ var indexName = JSON.parse(decodeURIComponent(params.substring(indexNameOffset + '&index_name='.length)));
773
+
774
+ helper.setQuery(q);
775
+
776
+ helper.clearRefinements();
777
+
778
+ /** Set refinements from url data **/
779
+ for (var i = 0; i < refinements.length; ++i) {
780
+ for (var refine in refinements[i]) {
781
+ for (var j = 0; j < refinements[i][refine].length; j++) {
782
+ helper.toggleRefine(refine, refinements[i][refine][j]);
783
+ }
784
+ }
785
+ }
786
+
787
+ for (var key in numericsRefinements)
788
+ for (var operator in numericsRefinements[key])
789
+ helper.addNumericRefinement(key, operator, numericsRefinements[key][operator]);
790
+
791
+ helper.setIndex(indexName).setCurrentPage(page);
792
+
793
+ }
794
+ helper.search();
795
+ };
796
+
797
+ var getFacets = function (content) {
798
+
799
+ var facets = [];
800
+
801
+ for (var i = 0; i < algoliaConfig.facets.length; i++)
802
+ {
803
+ var sub_facets = [];
804
+
805
+ if (custom_facets_types[algoliaConfig.facets[i].type] != undefined)
806
+ {
807
+ try
808
+ {
809
+ var params = custom_facets_types[algoliaConfig.facets[i].type](helper, content, algoliaConfig.facets[i]);
810
+
811
+ if (params)
812
+ for (var k = 0; k < params.length; k++)
813
+ sub_facets.push(params[k]);
814
+ }
815
+ catch(error)
816
+ {
817
+ console.log(error);
818
+ throw("Bad facet function for '" + algoliaConfig.facets[i].type + "'");
819
+ }
820
+ }
821
+ else
822
+ {
823
+ var content_facet = content.getFacetByName(algoliaConfig.facets[i].attribute);
824
+
825
+ if (content_facet == undefined)
826
+ continue;
827
+
828
+ for (var key in content_facet.data)
829
+ {
830
+ var checked = helper.isRefined(algoliaConfig.facets[i].attribute, key);
831
+
832
+ var nameattr = window.facetsLabels && window.facetsLabels[key] != undefined ? window.facetsLabels[key] : key;
833
+ var explode = nameattr.split(' /// ');
834
+ var name = explode[explode.length - 1];
835
+
836
+ var params = {
837
+ type: {},
838
+ checked: checked,
839
+ nameattr: nameattr,
840
+ name: name,
841
+ count: content_facet.data[key]
842
+ };
843
+
844
+ params.type[algoliaConfig.facets[i].type] = true;
845
+
846
+ sub_facets.push(params);
847
+ }
848
+
849
+ sub_facets.sort(function sortByCheckedThenCount(f1, f2) {
850
+ if (f1.checked !== f2.checked)
851
+ return f1.checked ? -1 : 1;
852
+
853
+ if (f2.count !== f1.count)
854
+ return f2.count - f1.count;
855
+
856
+ return f1.name.localeCompare(f2.name);
857
+ });
858
+
859
+ }
860
+
861
+ var label = algoliaConfig.facets[i].label !== "" ? algoliaConfig.facets[i].label : algoliaConfig.facets[i].attribute;
862
+
863
+ facets.push({count: sub_facets.length, attribute: algoliaConfig.facets[i].attribute, facet_categorie_name: label, sub_facets: sub_facets });
864
+ }
865
+
866
+ return facets;
867
+ };
868
+
869
+ var getPages = function (content) {
870
+ var pages = [];
871
+ if (content.page > 5)
872
+ {
873
+ pages.push({ current: false, number: 1 });
874
+ pages.push({ current: false, number: '...', disabled: true });
875
+ }
876
+
877
+ for (var p = content.page - 5; p < content.page + 5; ++p)
878
+ {
879
+ if (p < 0 || p >= content.nbPages)
880
+ continue;
881
+
882
+ pages.push({ current: content.page == p, number: (p + 1) });
883
+ }
884
+ if (content.page + 5 < content.nbPages)
885
+ {
886
+ pages.push({ current: false, number: '...', disabled: true });
887
+ pages.push({ current: false, number: content.nbPages });
888
+ }
889
+
890
+ return pages;
891
+ };
892
+
893
+ var sortSelected = function () {
894
+ return function (val) {
895
+ var template = algoliaBundle.Hogan.compile(val);
896
+
897
+ var renderer = function(context) {
898
+ return function(text) {
899
+ return template.c.compile(text, template.options).render(context);
900
+ };
901
+ };
902
+
903
+ var render = renderer(this);
904
+
905
+ var index_name = render(val);
906
+
907
+ if (index_name == helper.getIndex())
908
+ return "selected";
909
+ return "";
910
+ }
911
+ };
912
+
913
+ var gotoPage = function(page) {
914
+ helper.setCurrentPage(+page - 1);
915
+ };
916
+
917
+ var getDate = function () {
918
+ return function (val) {
919
+ var template = algoliaBundle.Hogan.compile(val);
920
+
921
+ var renderer = function(context) {
922
+ return function(text) {
923
+ return template.c.compile(text, template.options).render(context);
924
+ };
925
+ };
926
+
927
+ var render = renderer(this);
928
+
929
+ var timestamp = render(val);
930
+
931
+
932
+ var date = new Date(timestamp * 1000);
933
+
934
+ var days = ["<?php echo $this->__('Sunday'); ?>", "<?php echo $this->__('Monday'); ?>", "<?php echo $this->__('Tuesday'); ?>", "<?php echo $this->__('Wednesday'); ?>", "<?php echo $this->__('Thursday'); ?>", "<?php echo $this->__('Friday'); ?>", "<?php echo $this->__('Saturday'); ?>"];
935
+ var months = ["<?php echo $this->__('January'); ?>", "<?php echo $this->__('February'); ?>", "<?php echo $this->__('March'); ?>", "<?php echo $this->__('April'); ?>", "<?php echo $this->__('May'); ?>", "<?php echo $this->__('June'); ?>", "<?php echo $this->__('July'); ?>", "<?php echo $this->__('August'); ?>", "<?php echo $this->__('September'); ?>", "<?php echo $this->__('October'); ?>", "<?php echo $this->__('November'); ?>", "<?php echo $this->__('December'); ?>"];
936
+
937
+ var day = date.getDate();
938
+
939
+ if (day == 1)
940
+ day += "<?php echo $this->__('st'); ?>";
941
+ else if (day == 2)
942
+ day += "<?php echo $this->__('nd'); ?>";
943
+ else if (day == 3)
944
+ day += "<?php echo $this->__('rd'); ?>";
945
+ else
946
+ day += "<?php echo $this->__('th'); ?>";
947
+
948
+ return days[date.getDay()] + ", " + months[date.getMonth()] + " " + day + ", " + date.getFullYear();
949
+ }
950
+ };
951
+
952
+ /*****************
953
+ **
954
+ ** RENDERING HELPERS
955
+ **
956
+ *****************/
957
+
958
+ function getHtmlForPagination(paginationTemplate, content, pages, facets) {
959
+ var pagination_html = paginationTemplate.render({
960
+ pages: pages,
961
+ facets_count: facets.length,
962
+ prev_page: (content.page > 0 ? content.page : false),
963
+ next_page: (content.page + 1 < content.nbPages ? content.page + 2 : false)
964
+ });
965
+
966
+ return pagination_html;
967
+ }
968
+
969
+ function getHtmlForResults(resultsTemplate, content, facets) {
970
+
971
+ var results_html = resultsTemplate.render({
972
+ facets_count: facets.length,
973
+ getDate: getDate,
974
+ relevance_index_name: algoliaConfig.indexName + '_products',
975
+ sorting_indices: algoliaConfig.sortingIndices,
976
+ sortSelected: sortSelected,
977
+ hits: content.hits,
978
+ nbHits: content.nbHits,
979
+ nbHits_zero: (content.nbHits === 0),
980
+ nbHits_one: (content.nbHits === 1),
981
+ nbHits_many: (content.nbHits > 1),
982
+ query: helper.state.query,
983
+ processingTimeMS: content.processingTimeMS,
984
+ isAddToCartEnabled: algoliaConfig.instant.isAddToCartEnabled
985
+ });
986
+
987
+ return results_html;
988
+ }
989
+
990
+ function getHtmlForFacets(facetsTemplate, facets, empty) {
991
+
992
+ var facets_html = facetsTemplate.render({
993
+ facets: facets,
994
+ count: facets.length,
995
+ getDate: getDate,
996
+ relevance_index_name: algoliaConfig.indexName + '_products',
997
+ sorting_indices: algoliaConfig.sortingIndices,
998
+ sortSelected: sortSelected,
999
+ empty: empty
1000
+ }, {
1001
+ facet_hierarchical: facet_hierarchical
1002
+ });
1003
+
1004
+ return facets_html;
1005
+ }
1006
+
1007
+ /*****************
1008
+ **
1009
+ ** AUTOCOMPLETION MENU
1010
+ **
1011
+ *****************/
1012
+
1013
+ if (algoliaConfig.autocomplete.enabled)
1014
+ {
1015
+ var params = {};
1016
+
1017
+ var hogan_objs = [];
1018
+
1019
+ var indices = ['categories', 'products', 'pages'];
1020
+ var indices_with_suffix = ['categories', 'products' + algoliaConfig.suffixIndexName, 'pages'];
1021
+
1022
+ if (algoliaConfig.autocomplete.hitsPerPage['suggestions'] > 0)
1023
+ {
1024
+ var suggestions_index = algolia_client.initIndex(algoliaConfig.indexName + "_suggestions");
1025
+ var products_index = algolia_client.initIndex(algoliaConfig.indexName + "_products" + algoliaConfig.suffixIndexName);
1026
+
1027
+ hogan_objs.push({
1028
+ displayKey: 'query',
1029
+ source: function (query, cb) {
1030
+ suggestions_index.search(query, {
1031
+ hitsPerPage: algoliaConfig.autocomplete.hitsPerPage['suggestions']
1032
+ }, function (err, content) {
1033
+ if (err)
1034
+ return;
1035
+
1036
+ if (content.hits.length > 0) {
1037
+ products_index.search(content.hits[0].query, {
1038
+ facets: ['categories'],
1039
+ hitsPerPage: 0,
1040
+ typoTolerance: false,
1041
+ maxValuesPerFacet: 3
1042
+ }, function (err2, content2) {
1043
+
1044
+ if (err2)
1045
+ {
1046
+ cb([]);
1047
+ return;
1048
+ }
1049
+
1050
+ var hits = [];
1051
+
1052
+ var categories = {};
1053
+
1054
+ if (content2.facets.categories) {
1055
+
1056
+ var obj = $.extend(true, {}, content.hits[0]);
1057
+ obj.category = '<?php echo $this->__('All departments') ?>';
1058
+ obj.url = '<?php echo $base_url; ?>/catalogsearch/result/?q=' + obj.query;
1059
+ hits.push(obj);
1060
+
1061
+ for (var key in content2.facets.categories) {
1062
+
1063
+ var explode = key.split(' /// ');
1064
+ var nameattr = explode[0];
1065
+
1066
+ categories[nameattr] = 1;
1067
+ }
1068
+
1069
+ for (var key in categories)
1070
+ {
1071
+ var obj = $.extend(true, {}, content.hits[0]);
1072
+ obj.category = key;
1073
+ obj.url = '<?php echo $base_url; ?>?category=1#q=' + obj.query + '&page=0&refinements=%5B%7B%22categories%22%3A%5B%22' + obj.category + '%22%5D%7D%5D&numerics_refinements=%7B%7D&index_name=%22<?php echo $product_helper->getBaseIndexName(); ?>_products%22';
1074
+ hits.push(obj);
1075
+ }
1076
+ }
1077
+ else
1078
+ {
1079
+ var obj = $.extend(true, {}, content.hits[0]);
1080
+ obj.url = '<?php echo $base_url; ?>/catalogsearch/result/?q=' + obj.query;
1081
+ hits.push(obj);
1082
+ }
1083
+
1084
+ for (var k = 1; k < content.hits.length; k++)
1085
+ {
1086
+ var obj = $.extend(true, {}, content.hits[k]);
1087
+ obj.url = '<?php echo $base_url; ?>/catalogsearch/result/?q=' + obj.query;
1088
+ hits.push(obj);
1089
+ }
1090
+
1091
+
1092
+ for (var k = 0; k < hits.length; k++)
1093
+ hits[k].query = content.query;
1094
+
1095
+ cb(hits);
1096
+ });
1097
+ }
1098
+ else
1099
+ cb([]);
1100
+ });
1101
+ },
1102
+ templates: {
1103
+ suggestion: function (hit) {
1104
+ return algoliaConfig.autocomplete.templates['suggestions'].render(hit);
1105
+ }
1106
+ }
1107
+ });
1108
+ }
1109
+
1110
+ for (var i = 0; i < indices.length; i++)
1111
+ {
1112
+ if (algoliaConfig.autocomplete.hitsPerPage[indices[i]] > 0)
1113
+ {
1114
+ var index = algolia_client.initIndex(algoliaConfig.indexName + "_" + indices_with_suffix[i]);
1115
+
1116
+ hogan_objs.push({
1117
+ source: (function (index, i) {
1118
+ return function (query, cb) {
1119
+ index.search(query, {
1120
+ hitsPerPage: algoliaConfig.autocomplete.hitsPerPage[indices[i]]
1121
+ }, function (err, content) {
1122
+ if (err)
1123
+ {
1124
+ cb([]);
1125
+ return;
1126
+ }
1127
+
1128
+ for (var k = 0; k < content.hits.length; k++)
1129
+ content.hits[k].query = content.query;
1130
+
1131
+ cb(content.hits);
1132
+ });
1133
+ }
1134
+ })(index, i),
1135
+ displayKey: 'query',
1136
+ templates: {
1137
+ header: '<div class="category">' + algoliaConfig.autocomplete.titles[indices[i]] + '</div>',
1138
+ suggestion: (function (i) {
1139
+ return function (hit) {
1140
+ if (indices[i] == 'products')
1141
+ {
1142
+ var time = Math.floor(Date.now() / 1000);
1143
+
1144
+ if ((hit.special_price_from_date != undefined && (hit.special_price_from_date > time && hit.special_price_from_date !== '')) ||
1145
+ (hit.special_price_to_date != undefined && (hit.special_price_to_date < time && hit.special_price_to_date !== '')))
1146
+ {
1147
+ delete hit.special_price_from_date;
1148
+ delete hit.special_price_to_date;
1149
+ delete hit.special_price;
1150
+ delete hit.special_price_with_tax;
1151
+ delete hit.special_price_formated;
1152
+ delete hit.special_price_with_tax_formated;
1153
+ }
1154
+
1155
+ if (Array.isArray(hit.categories_without_path))
1156
+ hit.categories_without_path = hit.categories_without_path.join(', ');
1157
+
1158
+ if (Array.isArray(hit._highlightResult.name)) {
1159
+ hit._highlightResult.name = hit._highlightResult.name[0];
1160
+ hit.displayKey = hit.name[0];
1161
+ }
1162
+
1163
+ if (Array.isArray(hit.price))
1164
+ hit.price = hit.price[0];
1165
+
1166
+ }
1167
+
1168
+ if (indices[i] == 'categories')
1169
+ {
1170
+ hit.displayKey = hit.path;
1171
+ }
1172
+
1173
+ hit.displayKey = hit.displayKey || hit.name;
1174
+
1175
+ return algoliaConfig.autocomplete.templates[indices[i]].render(hit);
1176
+ }
1177
+ })(i)
1178
+ }
1179
+ });
1180
+ }
1181
+ }
1182
+
1183
+ for (var i = 0; i < algoliaConfig.autocomplete.additionnalSection.length; i++)
1184
+ {
1185
+ var index = algolia_client.initIndex(algoliaConfig.indexName + "_section_" + algoliaConfig.autocomplete.additionnalSection[i].attribute);
1186
+
1187
+ var label = algoliaConfig.autocomplete.additionnalSection[i].label !== "" ?
1188
+ algoliaConfig.autocomplete.additionnalSection[i].label : algoliaConfig.autocomplete.additionnalSection[i].attribute;
1189
+
1190
+ hogan_objs.push({
1191
+ source: (function (index, i) {
1192
+ return function (query, cb) {
1193
+ index.search(query, {
1194
+ hitsPerPage: algoliaConfig.autocomplete.additionnalSection[i].hitsPerPage
1195
+ }, function (err, content) {
1196
+ if (err)
1197
+ {
1198
+ cb([]);
1199
+ return;
1200
+ }
1201
+
1202
+ cb(content.hits);
1203
+ });
1204
+ }
1205
+ })(index, i),
1206
+ displayKey: 'value',
1207
+ templates: {
1208
+ header: '<div class="category">' + label + '</div>',
1209
+ suggestion: (function (i) {
1210
+ return function (hit) {
1211
+ hit.url = '<?php echo $base_url; ?>/catalogsearch/result/?q=' + hit.value + '&refinement_key=' + algoliaConfig.autocomplete.additionnalSection[i].attribute + "&refinement_value=" + hit.value;
1212
+
1213
+ return algoliaConfig.autocomplete.templates.additionnalSection.render(hit);
1214
+ }
1215
+ })(i)
1216
+ }
1217
+ });
1218
+ }
1219
+
1220
+ if (algoliaConfig.removeBranding === false)
1221
+ {
1222
+ hogan_objs.push({
1223
+ source: function findMatches(q, cb) {
1224
+ return cb(["algolia-branding"]);
1225
+ },
1226
+ displayKey: 'title',
1227
+ templates: {
1228
+ suggestion: function (hit) {
1229
+ return '<div class="footer_algolia"><a href="https://www.algolia.com/?utm_source=magento&utm_medium=link&utm_campaign=magento_autocompletion_menu" target="_blank"><img src="<?php echo $base_url; ?>/skin/frontend/base/default/algoliasearch/algolia-logo.png" /></a></div>';
1230
+ }
1231
+ }
1232
+ });
1233
+ }
1234
+
1235
+ $(algoliaConfig.autocomplete.selector).each(function (i) {
1236
+ var tt = $(this)
1237
+ .typeahead({hint: false}, hogan_objs)
1238
+ .parent()
1239
+ .attr('id', 'algolia-autocomplete-tt');
1240
+
1241
+ $(this).on('typeahead:selected', function (e, item) {
1242
+ autocomplete = false;
1243
+ instant = false;
1244
+ window.location.href = item.url;
1245
+ });
1246
+ });
1247
+
1248
+ $("#algolia-glass").click(function () {
1249
+ $(this).closest('form').submit();
1250
+ });
1251
+ }
1252
+
1253
+ /*****************
1254
+ **
1255
+ ** INSTANT RESULTS PAGE SEARCH
1256
+ **
1257
+ *****************/
1258
+
1259
+ if (algoliaConfig.instant.enabled && (<?php echo $isSearchPage ? "true" : "false"; ?> || ! algoliaConfig.autocomplete.enabled))
1260
+ {
1261
+ if ($(algoliaConfig.instant.selector).length !== 1)
1262
+ throw '[Algolia] Invalid instant-search selector: ' + algoliaConfig.instant.selector;
1263
+
1264
+ if ($(algoliaConfig.instant.selector).find(algoliaConfig.autocomplete.selector).length > 0)
1265
+ throw '[Algolia] You can\'t have a search input matching "' + algoliaConfig.autocomplete.selector +
1266
+ '" inside you instant selector "' + algoliaConfig.instant.selector + '"';
1267
+
1268
+ var instant_selector = ! algoliaConfig.autocomplete.enabled ? "#search" : "#instant-search-bar";
1269
+
1270
+ var wrapperTemplate = algoliaBundle.Hogan.compile($('#instant_wrapper_template').html());
1271
+
1272
+ var initialized = false;
1273
+
1274
+ var resultsTemplate = algoliaBundle.Hogan.compile($('#instant-content-template').html());
1275
+ var facetsTemplate = algoliaBundle.Hogan.compile($('#instant-facets-template').html());
1276
+ var paginationTemplate = algoliaBundle.Hogan.compile($('#instant-pagination-template').html());
1277
+ var facet_hierarchical = algoliaBundle.Hogan.compile($('#instant-facets-hierarchical-template').html());
1278
+
1279
+
1280
+ function performQueries(push_state)
1281
+ {
1282
+ helper.search();
1283
+
1284
+ updateUrl(push_state);
1285
+ }
1286
+
1287
+ function searchCallbackEmpty(content)
1288
+ {
1289
+ var instant_search_facets_container = $('#instant-search-facets-container');
1290
+
1291
+ var facets = getFacets(content);
1292
+
1293
+ instant_search_facets_container.html(getHtmlForFacets(facetsTemplate, facets, true));
1294
+ }
1295
+
1296
+ function searchCallback(content)
1297
+ {
1298
+ if (initialized === false)
1299
+ {
1300
+ $(algoliaConfig.instant.selector).html(wrapperTemplate.render({ second_bar: algoliaConfig.autocomplete.enabled })).show();
1301
+ initialized = true;
1302
+ }
1303
+ /**
1304
+ * Modify results to be able to print it with Hogan
1305
+ */
1306
+ for (var i = 0; i < content.hits.length; ++i)
1307
+ {
1308
+ if (Array.isArray(content.hits[i].categories))
1309
+ content.hits[i].categories = content.hits[i].categories.join(', ');
1310
+
1311
+ if (Array.isArray(content.hits[i]._highlightResult.name))
1312
+ content.hits[i]._highlightResult.name = content.hits[i]._highlightResult.name[0];
1313
+
1314
+ if (Array.isArray(content.hits[i].price))
1315
+ content.hits[i].price = content.hits[i].price[0];
1316
+
1317
+ var time = Math.floor(Date.now() / 1000);
1318
+
1319
+
1320
+ if ((content.hits[i].special_price_from_date != undefined && (content.hits[i].special_price_from_date > time && content.hits[i].special_price_from_date !== '')) ||
1321
+ (content.hits[i].special_price_to_date != undefined && (content.hits[i].special_price_to_date < time && content.hits[i].special_price_to_date !== '')))
1322
+ {
1323
+ delete content.hits[i].special_price_from_date;
1324
+ delete content.hits[i].special_price_to_date;
1325
+ delete content.hits[i].special_price;
1326
+ delete content.hits[i].special_price_with_tax;
1327
+ delete content.hits[i].special_price_formated;
1328
+ delete content.hits[i].special_price_with_tax_formated;
1329
+ }
1330
+ }
1331
+
1332
+ /**
1333
+ * Generate HTML
1334
+ */
1335
+
1336
+ var instant_search_facets_container = $('#instant-search-facets-container');
1337
+ var instant_search_results_container = $('#instant-search-results-container');
1338
+ var instant_search_pagination_container = $('#instant-search-pagination-container');
1339
+
1340
+ instant_search_pagination_container.html('');
1341
+
1342
+ var facets = [];
1343
+ var pages = [];
1344
+
1345
+ if (content.hits.length > 0)
1346
+ {
1347
+ facets = getFacets(content);
1348
+ pages = getPages(content);
1349
+
1350
+ instant_search_facets_container.html(getHtmlForFacets(facetsTemplate, facets, false));
1351
+ }
1352
+ else
1353
+ {
1354
+ helper_empty.search();
1355
+ }
1356
+
1357
+ instant_search_results_container.html(getHtmlForResults(resultsTemplate, content, facets));
1358
+
1359
+ if (content.hits.length > 0)
1360
+ instant_search_pagination_container.html(getHtmlForPagination(paginationTemplate, content, pages, facets));
1361
+
1362
+ updateSliderValues();
1363
+
1364
+ var instant_search_bar = $(instant_selector);
1365
+
1366
+ if (instant_search_bar.is(":focus") === false)
1367
+ {
1368
+ if ($(window).width() > 992) {
1369
+ instant_search_bar.focus().val('');
1370
+ }
1371
+ instant_search_bar.val(helper.state.query);
1372
+ }
1373
+ }
1374
+
1375
+ helper.on('result', searchCallback);
1376
+ helper_empty.on('result', searchCallbackEmpty);
1377
+
1378
+ custom_facets_types["hierarchical"] = function (helper, content, facet) {
1379
+ var data = [];
1380
+
1381
+ var content_facet = content.getFacetByName(facet.attribute);
1382
+
1383
+ content_facet.name = window.facetsLabels && window.facetsLabels[content_facet.name] != undefined ? window.facetsLabels[content_facet.name] : content_facet.name;
1384
+ content_facet.type = { hierarchical: true };
1385
+
1386
+ return [content_facet];
1387
+ };
1388
+
1389
+ /**
1390
+ * Example of a custom facet type
1391
+ */
1392
+ custom_facets_types["menu"] = function (helper, content, facet) {
1393
+
1394
+ var data = [];
1395
+
1396
+ var all_count = 0;
1397
+ var all_unchecked = true;
1398
+
1399
+ var content_facet = content.getFacetByName(facet.attribute);
1400
+
1401
+ if (content_facet == undefined)
1402
+ return data;
1403
+
1404
+ for (var key in content_facet.data)
1405
+ {
1406
+ var checked = helper.isRefined(facet.attribute, key);
1407
+
1408
+ all_unchecked = all_unchecked && !checked;
1409
+
1410
+ var name = window.facetsLabels && window.facetsLabels[key] != undefined ? window.facetsLabels[key] : key;
1411
+ var explode = name.split(' /// ');
1412
+ var nameattr = explode[explode.length - 1];
1413
+
1414
+ var params = {
1415
+ type: {},
1416
+ checked: checked,
1417
+ nameattr: nameattr,
1418
+ name: name,
1419
+ print_count: true,
1420
+ count: content_facet.data[key]
1421
+ };
1422
+
1423
+ all_count += content_facet.data[key];
1424
+
1425
+ params.type[facet.type] = true;
1426
+
1427
+ data.push(params);
1428
+ }
1429
+
1430
+ var params = {
1431
+ type: {},
1432
+ checked: all_unchecked,
1433
+ nameattr: 'all',
1434
+ name: 'All',
1435
+ print_count: false,
1436
+ count: all_count
1437
+ };
1438
+
1439
+ params.type[facet.type] = true;
1440
+
1441
+ data.unshift(params);
1442
+
1443
+ return data;
1444
+ };
1445
+
1446
+ /**
1447
+ * Handle click on menu custom facet
1448
+ */
1449
+ $("body").on("click", ".sub_facet.menu", function (e) {
1450
+
1451
+ e.stopImmediatePropagation();
1452
+
1453
+ if ($(this).hasClass("empty")) {
1454
+ helper.setQuery("");
1455
+ }
1456
+
1457
+ if ($(this).attr("data-name") == "all")
1458
+ helper.state.clearRefinements($(this).attr("data-attribute"));
1459
+
1460
+ $(this).find("input[type='checkbox']").each(function (i) {
1461
+ $(this).prop("checked", !$(this).prop("checked"));
1462
+
1463
+ if (false == helper.isRefined($(this).attr("data-attribute"), $(this).attr("data-name")))
1464
+ helper.state.clearRefinements($(this).attr("data-attribute"));
1465
+
1466
+ if ($(this).attr("data-name") != "all")
1467
+ helper.toggleRefine($(this).attr("data-attribute"), $(this).attr("data-name"));
1468
+ });
1469
+
1470
+ performQueries(true);
1471
+ });
1472
+
1473
+ /**
1474
+ * Handle click on hierarchical facet
1475
+ */
1476
+ $("body").on("click", ".sub_facet.hierarchical", function (e) {
1477
+
1478
+ e.stopImmediatePropagation();
1479
+
1480
+ if ($(this).hasClass("empty")) {
1481
+ helper.setQuery("");
1482
+ }
1483
+
1484
+ helper.toggleRefine($(this).attr("data-name"), $(this).attr('data-path'));
1485
+
1486
+ performQueries(true);
1487
+ });
1488
+
1489
+ /**
1490
+ * Handle click on conjunctive and disjunctive facet
1491
+ */
1492
+ $("body").on("click", ".sub_facet", function () {
1493
+
1494
+ if ($(this).hasClass("empty")) {
1495
+ helper.setQuery("");
1496
+ }
1497
+
1498
+ $(this).find("input[type='checkbox']").each(function (i) {
1499
+ $(this).prop("checked", !$(this).prop("checked"));
1500
+
1501
+ helper.toggleRefine($(this).attr("data-attribute"), $(this).attr("data-name"));
1502
+ });
1503
+
1504
+ performQueries(true);
1505
+ });
1506
+
1507
+ /**
1508
+ * Handle jquery-ui slider initialisation
1509
+ */
1510
+ $("body").on("slide", "", function (event, ui) {
1511
+ updateSlideInfos(ui);
1512
+ });
1513
+
1514
+ /**
1515
+ * Handle sort change
1516
+ */
1517
+ $("body").on("change", "#index_to_use", function () {
1518
+ helper.setIndex($(this).val());
1519
+
1520
+ helper.setCurrentPage(0);
1521
+
1522
+ performQueries(true);
1523
+ });
1524
+
1525
+ /**
1526
+ * Handle jquery-ui slide event
1527
+ */
1528
+ $("body").on("slidechange", ".algolia-slider-true", function (event, ui) {
1529
+
1530
+ var slide_dom = $(ui.handle).closest(".algolia-slider");
1531
+ var min = slide_dom.slider("values")[0];
1532
+ var max = slide_dom.slider("values")[1];
1533
+
1534
+ if (parseInt(slide_dom.slider("values")[0]) >= parseInt(slide_dom.attr("data-min")))
1535
+ helper.addNumericRefinement(slide_dom.attr("data-attribute"), ">=", min);
1536
+ if (parseInt(slide_dom.slider("values")[1]) <= parseInt(slide_dom.attr("data-max")))
1537
+ helper.addNumericRefinement(slide_dom.attr("data-attribute"), "<=", max);
1538
+
1539
+ if (parseInt(min) == parseInt(slide_dom.attr("data-min")))
1540
+ helper.removeNumericRefinement(slide_dom.attr("data-attribute"), ">=");
1541
+
1542
+ if (parseInt(max) == parseInt(slide_dom.attr("data-max")))
1543
+ helper.removeNumericRefinement(slide_dom.attr("data-attribute"), "<=");
1544
+
1545
+ updateSlideInfos(ui);
1546
+ performQueries(true);
1547
+ });
1548
+
1549
+ /**
1550
+ * Handle page change
1551
+ */
1552
+ $("body").on("click", ".algolia-pagination a", function (e) {
1553
+ e.preventDefault();
1554
+
1555
+ gotoPage($(this).attr("data-page"));
1556
+ performQueries(true);
1557
+
1558
+ $("body").scrollTop(0);
1559
+
1560
+ return false;
1561
+ });
1562
+
1563
+ /** Handle input clearing **/
1564
+ $('body').on('click', '.clear-button', function () {
1565
+ $(instant_selector).val('').focus();
1566
+ helper.clearRefinements().setQuery('');
1567
+
1568
+ performQueries(true);
1569
+ });
1570
+
1571
+ /** Handle small screen **/
1572
+ $('body').on('click', '#refine-toggle', function () {
1573
+ $('#instant-search-facets-container').toggleClass('hidden-sm').toggleClass('hidden-xs');
1574
+
1575
+ if ($(this).html()[0] === '+')
1576
+ $(this).html('- Refine');
1577
+ else
1578
+ $(this).html('+ Refine');
1579
+ });
1580
+
1581
+
1582
+ /**
1583
+ * Handle search
1584
+ */
1585
+
1586
+ $('body').on('keyup', instant_selector, function (e) {
1587
+ e.preventDefault();
1588
+
1589
+ helper.setQuery($(this).val());
1590
+
1591
+ /* Uncomment to clear refinements on keyup */
1592
+
1593
+ //helper.clearRefinements();
1594
+
1595
+ performQueries(false);
1596
+
1597
+ return false;
1598
+ });
1599
+
1600
+ function updateSliderValues()
1601
+ {
1602
+ $(".algolia-slider-true").each(function (i) {
1603
+ var min = $(this).attr("data-min");
1604
+ var max = $(this).attr("data-max");
1605
+
1606
+ var new_min = helper.state.getNumericRefinement($(this).attr("data-attribute"), ">=");
1607
+ var new_max = helper.state.getNumericRefinement($(this).attr("data-attribute"), "<=");
1608
+
1609
+ if (new_min != undefined)
1610
+ min = new_min;
1611
+
1612
+ if (new_max != undefined)
1613
+ max = new_max;
1614
+
1615
+ $(this).slider({
1616
+ min: parseInt($(this).attr("data-min")),
1617
+ max: parseInt($(this).attr("data-max")),
1618
+ range: true,
1619
+ values: [min, max]
1620
+ });
1621
+ });
1622
+ }
1623
+
1624
+ function updateSlideInfos(ui)
1625
+ {
1626
+ var infos = $(ui.handle).closest(".algolia-slider").nextAll(".algolia-slider-info");
1627
+
1628
+ infos.find(".min").html(ui.values[0]);
1629
+ infos.find(".max").html(ui.values[1]);
1630
+ }
1631
+
1632
+ function updateBrowserUrlBar(url) {
1633
+ if (supportsHistory) {
1634
+ history.pushState(url, null, url);
1635
+ } else {
1636
+ window.location.hash = url;
1637
+ }
1638
+ }
1639
+
1640
+ /**
1641
+ * Initialization
1642
+ */
1643
+
1644
+ /** Clean input **/
1645
+ $(algoliaConfig.autocomplete.selector).attr('autocomplete', 'off').attr('autocorrect', 'off').attr('spellcheck', 'false').attr('autocapitalize', 'off');
1646
+
1647
+ if (<?php echo $isSearchPage ? "true" : "false"; ?> || location.hash.length > 1) {
1648
+ getRefinementsFromUrl();
1649
+ }
1650
+
1651
+ if (supportsHistory) {
1652
+ window.addEventListener("popstate", getRefinementsFromUrl);
1653
+ } else {
1654
+ window.addEventListener("hashchange", getRefinementsFromUrl);
1655
+ }
1656
+
1657
+ onfocus_css = {
1658
+ 'opacity': '1',
1659
+ 'fill': '#54A5CD',
1660
+ 'stroke': '#54A5CD'
1661
+ };
1662
+
1663
+ onblur_css = {
1664
+ 'opacity': '0.4',
1665
+ 'fill': '#AAA',
1666
+ 'stroke': '#AAA'
1667
+ };
1668
+
1669
+ $('#search').focus(function () {
1670
+ $(this).parent().next().css(onfocus_css);
1671
+ }).blur(function () {
1672
+ $(this).parent().next().css(onblur_css);
1673
+ }).parent().next().css(onblur_css);
1674
+
1675
+ }
1676
+ });
1677
+
1678
+ //]]>
1679
+ </script>
js/algoliasearch/bundle.min.js CHANGED
@@ -1,22 +1,31409 @@
1
- (function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.algoliaBundle=f()}})(function(){var define,module,exports;return function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s}({1:[function(require,module,exports){module.exports={$:require("jquery"),Hogan:require("hogan.js"),algoliasearch:require("algoliasearch"),algoliasearchHelper:require("algoliasearch-helper")};require("jquery-ui/slider");var oldJQuery=window.jQuery;window.jQuery=module.exports.$;require("typeahead.js");window.jQuery=oldJQuery},{algoliasearch:187,"algoliasearch-helper":2,"hogan.js":201,jquery:207,"jquery-ui/slider":205,"typeahead.js":208}],2:[function(require,module,exports){"use strict";var AlgoliaSearchHelper=require("./src/algoliasearch.helper");var SearchParameters=require("./src/SearchParameters");var SearchResults=require("./src/SearchResults");function algoliasearchHelper(client,index,opts){return new AlgoliaSearchHelper(client,index,opts)}algoliasearchHelper.version="2.1.1";algoliasearchHelper.AlgoliaSearchHelper=AlgoliaSearchHelper;algoliasearchHelper.SearchParameters=SearchParameters;algoliasearchHelper.SearchResults=SearchResults;module.exports=algoliasearchHelper},{"./src/SearchParameters":120,"./src/SearchResults":121,"./src/algoliasearch.helper":122}],3:[function(require,module,exports){function compact(array){var index=-1,length=array?array.length:0,resIndex=-1,result=[];while(++index<length){var value=array[index];if(value){result[++resIndex]=value}}return result}module.exports=compact},{}],4:[function(require,module,exports){var baseIndexOf=require("../internal/baseIndexOf"),cacheIndexOf=require("../internal/cacheIndexOf"),createCache=require("../internal/createCache"),isArrayLike=require("../internal/isArrayLike"),restParam=require("../function/restParam");var intersection=restParam(function(arrays){var othLength=arrays.length,othIndex=othLength,caches=Array(length),indexOf=baseIndexOf,isCommon=true,result=[];while(othIndex--){var value=arrays[othIndex]=isArrayLike(value=arrays[othIndex])?value:[];caches[othIndex]=isCommon&&value.length>=120?createCache(othIndex&&value):null}var array=arrays[0],index=-1,length=array?array.length:0,seen=caches[0];outer:while(++index<length){value=array[index];if((seen?cacheIndexOf(seen,value):indexOf(result,value,0))<0){var othIndex=othLength;while(--othIndex){var cache=caches[othIndex];if((cache?cacheIndexOf(cache,value):indexOf(arrays[othIndex],value,0))<0){continue outer}}if(seen){seen.push(value)}result.push(value)}}return result});module.exports=intersection},{"../function/restParam":14,"../internal/baseIndexOf":37,"../internal/cacheIndexOf":54,"../internal/createCache":61,"../internal/isArrayLike":78}],5:[function(require,module,exports){function last(array){var length=array?array.length:0;return length?array[length-1]:undefined}module.exports=last},{}],6:[function(require,module,exports){var LazyWrapper=require("../internal/LazyWrapper"),LodashWrapper=require("../internal/LodashWrapper"),baseLodash=require("../internal/baseLodash"),isArray=require("../lang/isArray"),isObjectLike=require("../internal/isObjectLike"),wrapperClone=require("../internal/wrapperClone");var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function lodash(value){if(isObjectLike(value)&&!isArray(value)&&!(value instanceof LazyWrapper)){if(value instanceof LodashWrapper){return value}if(hasOwnProperty.call(value,"__chain__")&&hasOwnProperty.call(value,"__wrapped__")){return wrapperClone(value)}}return new LodashWrapper(value)}lodash.prototype=baseLodash.prototype;module.exports=lodash},{"../internal/LazyWrapper":15,"../internal/LodashWrapper":16,"../internal/baseLodash":42,"../internal/isObjectLike":84,"../internal/wrapperClone":98,"../lang/isArray":100}],7:[function(require,module,exports){var arrayFilter=require("../internal/arrayFilter"),baseCallback=require("../internal/baseCallback"),baseFilter=require("../internal/baseFilter"),isArray=require("../lang/isArray");function filter(collection,predicate,thisArg){var func=isArray(collection)?arrayFilter:baseFilter;predicate=baseCallback(predicate,thisArg,3);return func(collection,predicate)}module.exports=filter},{"../internal/arrayFilter":20,"../internal/baseCallback":25,"../internal/baseFilter":29,"../lang/isArray":100}],8:[function(require,module,exports){var baseEach=require("../internal/baseEach"),createFind=require("../internal/createFind");var find=createFind(baseEach);module.exports=find},{"../internal/baseEach":28,"../internal/createFind":63}],9:[function(require,module,exports){var arrayEach=require("../internal/arrayEach"),baseEach=require("../internal/baseEach"),createForEach=require("../internal/createForEach");var forEach=createForEach(arrayEach,baseEach);module.exports=forEach},{"../internal/arrayEach":19,"../internal/baseEach":28,"../internal/createForEach":64}],10:[function(require,module,exports){var arrayReduce=require("../internal/arrayReduce"),baseEach=require("../internal/baseEach"),createReduce=require("../internal/createReduce");var reduce=createReduce(arrayReduce,baseEach);module.exports=reduce},{"../internal/arrayReduce":22,"../internal/baseEach":28,"../internal/createReduce":67}],11:[function(require,module,exports){module.exports=require("../math/sum")},{"../math/sum":108}],12:[function(require,module,exports){var getNative=require("../internal/getNative");var nativeNow=getNative(Date,"now");var now=nativeNow||function(){return(new Date).getTime()};module.exports=now},{"../internal/getNative":76}],13:[function(require,module,exports){var createWrapper=require("../internal/createWrapper"),replaceHolders=require("../internal/replaceHolders"),restParam=require("./restParam");var BIND_FLAG=1,PARTIAL_FLAG=32;var bind=restParam(function(func,thisArg,partials){var bitmask=BIND_FLAG;if(partials.length){var holders=replaceHolders(partials,bind.placeholder);bitmask|=PARTIAL_FLAG}return createWrapper(func,bitmask,thisArg,partials,holders)});bind.placeholder={};module.exports=bind},{"../internal/createWrapper":68,"../internal/replaceHolders":92,"./restParam":14}],14:[function(require,module,exports){var FUNC_ERROR_TEXT="Expected a function";var nativeMax=Math.max;function restParam(func,start){if(typeof func!="function"){throw new TypeError(FUNC_ERROR_TEXT)}start=nativeMax(start===undefined?func.length-1:+start||0,0);return function(){var args=arguments,index=-1,length=nativeMax(args.length-start,0),rest=Array(length);while(++index<length){rest[index]=args[start+index]}switch(start){case 0:return func.call(this,rest);case 1:return func.call(this,args[0],rest);case 2:return func.call(this,args[0],args[1],rest)}var otherArgs=Array(start+1);index=-1;while(++index<start){otherArgs[index]=args[index]}otherArgs[start]=rest;return func.apply(this,otherArgs)}}module.exports=restParam},{}],15:[function(require,module,exports){var baseCreate=require("./baseCreate"),baseLodash=require("./baseLodash");var POSITIVE_INFINITY=Number.POSITIVE_INFINITY;function LazyWrapper(value){this.__wrapped__=value;this.__actions__=null;this.__dir__=1;this.__dropCount__=0;this.__filtered__=false;this.__iteratees__=null;this.__takeCount__=POSITIVE_INFINITY;this.__views__=null}LazyWrapper.prototype=baseCreate(baseLodash.prototype);LazyWrapper.prototype.constructor=LazyWrapper;module.exports=LazyWrapper},{"./baseCreate":26,"./baseLodash":42}],16:[function(require,module,exports){var baseCreate=require("./baseCreate"),baseLodash=require("./baseLodash");function LodashWrapper(value,chainAll,actions){this.__wrapped__=value;this.__actions__=actions||[];this.__chain__=!!chainAll}LodashWrapper.prototype=baseCreate(baseLodash.prototype);LodashWrapper.prototype.constructor=LodashWrapper;module.exports=LodashWrapper},{"./baseCreate":26,"./baseLodash":42}],17:[function(require,module,exports){(function(global){var cachePush=require("./cachePush"),getNative=require("./getNative");var Set=getNative(global,"Set");var nativeCreate=getNative(Object,"create");function SetCache(values){var length=values?values.length:0;this.data={hash:nativeCreate(null),set:new Set};while(length--){this.push(values[length])}}SetCache.prototype.push=cachePush;module.exports=SetCache}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./cachePush":55,"./getNative":76}],18:[function(require,module,exports){function arrayCopy(source,array){var index=-1,length=source.length;array||(array=Array(length));while(++index<length){array[index]=source[index]}return array}module.exports=arrayCopy},{}],19:[function(require,module,exports){function arrayEach(array,iteratee){var index=-1,length=array.length;while(++index<length){if(iteratee(array[index],index,array)===false){break}}return array}module.exports=arrayEach},{}],20:[function(require,module,exports){function arrayFilter(array,predicate){var index=-1,length=array.length,resIndex=-1,result=[];while(++index<length){var value=array[index];if(predicate(value,index,array)){result[++resIndex]=value}}return result}module.exports=arrayFilter},{}],21:[function(require,module,exports){function arrayMap(array,iteratee){var index=-1,length=array.length,result=Array(length);while(++index<length){result[index]=iteratee(array[index],index,array)}return result}module.exports=arrayMap},{}],22:[function(require,module,exports){function arrayReduce(array,iteratee,accumulator,initFromArray){var index=-1,length=array.length;if(initFromArray&&length){accumulator=array[++index]}while(++index<length){accumulator=iteratee(accumulator,array[index],index,array)}return accumulator}module.exports=arrayReduce},{}],23:[function(require,module,exports){function arraySome(array,predicate){var index=-1,length=array.length;while(++index<length){if(predicate(array[index],index,array)){return true}}return false}module.exports=arraySome},{}],24:[function(require,module,exports){function arraySum(array){var length=array.length,result=0;while(length--){result+=+array[length]||0}return result}module.exports=arraySum},{}],25:[function(require,module,exports){var baseMatches=require("./baseMatches"),baseMatchesProperty=require("./baseMatchesProperty"),bindCallback=require("./bindCallback"),identity=require("../utility/identity"),property=require("../utility/property");function baseCallback(func,thisArg,argCount){var type=typeof func;if(type=="function"){return thisArg===undefined?func:bindCallback(func,thisArg,argCount)}if(func==null){return identity}if(type=="object"){return baseMatches(func)}return thisArg===undefined?property(func):baseMatchesProperty(func,thisArg)}module.exports=baseCallback},{"../utility/identity":116,"../utility/property":118,"./baseMatches":43,"./baseMatchesProperty":44,"./bindCallback":53}],26:[function(require,module,exports){var isObject=require("../lang/isObject");var baseCreate=function(){function object(){}return function(prototype){if(isObject(prototype)){object.prototype=prototype;var result=new object;object.prototype=null}return result||{}}}();module.exports=baseCreate},{"../lang/isObject":104}],27:[function(require,module,exports){var baseIndexOf=require("./baseIndexOf"),cacheIndexOf=require("./cacheIndexOf"),createCache=require("./createCache");function baseDifference(array,values){var length=array?array.length:0,result=[];if(!length){return result}var index=-1,indexOf=baseIndexOf,isCommon=true,cache=isCommon&&values.length>=200?createCache(values):null,valuesLength=values.length;if(cache){indexOf=cacheIndexOf;isCommon=false;values=cache}outer:while(++index<length){var value=array[index];if(isCommon&&value===value){var valuesIndex=valuesLength;while(valuesIndex--){if(values[valuesIndex]===value){continue outer}}result.push(value)}else if(indexOf(values,value,0)<0){result.push(value)}}return result}module.exports=baseDifference},{"./baseIndexOf":37,"./cacheIndexOf":54,"./createCache":61}],28:[function(require,module,exports){var baseForOwn=require("./baseForOwn"),createBaseEach=require("./createBaseEach");var baseEach=createBaseEach(baseForOwn);module.exports=baseEach},{"./baseForOwn":35,"./createBaseEach":58}],29:[function(require,module,exports){var baseEach=require("./baseEach");function baseFilter(collection,predicate){var result=[];baseEach(collection,function(value,index,collection){if(predicate(value,index,collection)){result.push(value)}});return result}module.exports=baseFilter},{"./baseEach":28}],30:[function(require,module,exports){function baseFind(collection,predicate,eachFunc,retKey){var result;eachFunc(collection,function(value,key,collection){if(predicate(value,key,collection)){result=retKey?key:value;return false}});return result}module.exports=baseFind},{}],31:[function(require,module,exports){function baseFindIndex(array,predicate,fromRight){var length=array.length,index=fromRight?length:-1;while(fromRight?index--:++index<length){if(predicate(array[index],index,array)){return index}}return-1}module.exports=baseFindIndex},{}],32:[function(require,module,exports){var isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isArrayLike=require("./isArrayLike"),isObjectLike=require("./isObjectLike");function baseFlatten(array,isDeep,isStrict){var index=-1,length=array.length,resIndex=-1,result=[];while(++index<length){var value=array[index];if(isObjectLike(value)&&isArrayLike(value)&&(isStrict||isArray(value)||isArguments(value))){if(isDeep){value=baseFlatten(value,isDeep,isStrict)}var valIndex=-1,valLength=value.length;while(++valIndex<valLength){result[++resIndex]=value[valIndex]}}else if(!isStrict){result[++resIndex]=value}}return result}module.exports=baseFlatten},{"../lang/isArguments":99,"../lang/isArray":100,"./isArrayLike":78,"./isObjectLike":84}],33:[function(require,module,exports){var createBaseFor=require("./createBaseFor");var baseFor=createBaseFor();module.exports=baseFor},{"./createBaseFor":59}],34:[function(require,module,exports){var baseFor=require("./baseFor"),keysIn=require("../object/keysIn");function baseForIn(object,iteratee){return baseFor(object,iteratee,keysIn)}module.exports=baseForIn},{"../object/keysIn":110,"./baseFor":33}],35:[function(require,module,exports){var baseFor=require("./baseFor"),keys=require("../object/keys");function baseForOwn(object,iteratee){return baseFor(object,iteratee,keys)}module.exports=baseForOwn},{"../object/keys":109,"./baseFor":33}],36:[function(require,module,exports){var toObject=require("./toObject");function baseGet(object,path,pathKey){if(object==null){return}if(pathKey!==undefined&&pathKey in toObject(object)){path=[pathKey]}var index=0,length=path.length;while(object!=null&&index<length){object=object[path[index++]]}return index&&index==length?object:undefined}module.exports=baseGet},{"./toObject":96}],37:[function(require,module,exports){var indexOfNaN=require("./indexOfNaN");function baseIndexOf(array,value,fromIndex){if(value!==value){return indexOfNaN(array,fromIndex)}var index=fromIndex-1,length=array.length;while(++index<length){if(array[index]===value){return index}}return-1}module.exports=baseIndexOf},{"./indexOfNaN":77}],38:[function(require,module,exports){var baseIsEqualDeep=require("./baseIsEqualDeep"),isObject=require("../lang/isObject"),isObjectLike=require("./isObjectLike");function baseIsEqual(value,other,customizer,isLoose,stackA,stackB){if(value===other){return true}if(value==null||other==null||!isObject(value)&&!isObjectLike(other)){return value!==value&&other!==other}return baseIsEqualDeep(value,other,baseIsEqual,customizer,isLoose,stackA,stackB)}module.exports=baseIsEqual},{"../lang/isObject":104,"./baseIsEqualDeep":39,"./isObjectLike":84}],39:[function(require,module,exports){var equalArrays=require("./equalArrays"),equalByTag=require("./equalByTag"),equalObjects=require("./equalObjects"),isArray=require("../lang/isArray"),isTypedArray=require("../lang/isTypedArray");var argsTag="[object Arguments]",arrayTag="[object Array]",objectTag="[object Object]";var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;function baseIsEqualDeep(object,other,equalFunc,customizer,isLoose,stackA,stackB){var objIsArr=isArray(object),othIsArr=isArray(other),objTag=arrayTag,othTag=arrayTag;if(!objIsArr){objTag=objToString.call(object);if(objTag==argsTag){objTag=objectTag}else if(objTag!=objectTag){objIsArr=isTypedArray(object)}}if(!othIsArr){othTag=objToString.call(other);if(othTag==argsTag){othTag=objectTag}else if(othTag!=objectTag){othIsArr=isTypedArray(other)}}var objIsObj=objTag==objectTag,othIsObj=othTag==objectTag,isSameTag=objTag==othTag;if(isSameTag&&!(objIsArr||objIsObj)){return equalByTag(object,other,objTag)}if(!isLoose){var objIsWrapped=objIsObj&&hasOwnProperty.call(object,"__wrapped__"),othIsWrapped=othIsObj&&hasOwnProperty.call(other,"__wrapped__");if(objIsWrapped||othIsWrapped){return equalFunc(objIsWrapped?object.value():object,othIsWrapped?other.value():other,customizer,isLoose,stackA,stackB)}}if(!isSameTag){return false}stackA||(stackA=[]);stackB||(stackB=[]);var length=stackA.length;while(length--){if(stackA[length]==object){return stackB[length]==other}}stackA.push(object);stackB.push(other);var result=(objIsArr?equalArrays:equalObjects)(object,other,equalFunc,customizer,isLoose,stackA,stackB);stackA.pop();stackB.pop();return result}module.exports=baseIsEqualDeep},{"../lang/isArray":100,"../lang/isTypedArray":106,"./equalArrays":69,"./equalByTag":70,"./equalObjects":71}],40:[function(require,module,exports){function baseIsFunction(value){return typeof value=="function"||false}module.exports=baseIsFunction},{}],41:[function(require,module,exports){var baseIsEqual=require("./baseIsEqual"),toObject=require("./toObject");function baseIsMatch(object,matchData,customizer){var index=matchData.length,length=index,noCustomizer=!customizer;if(object==null){return!length}object=toObject(object);while(index--){var data=matchData[index];if(noCustomizer&&data[2]?data[1]!==object[data[0]]:!(data[0]in object)){return false}}while(++index<length){data=matchData[index];var key=data[0],objValue=object[key],srcValue=data[1];if(noCustomizer&&data[2]){if(objValue===undefined&&!(key in object)){return false}}else{var result=customizer?customizer(objValue,srcValue,key):undefined;if(!(result===undefined?baseIsEqual(srcValue,objValue,customizer,true):result)){return false}}}return true}module.exports=baseIsMatch},{"./baseIsEqual":38,"./toObject":96}],42:[function(require,module,exports){function baseLodash(){}module.exports=baseLodash},{}],43:[function(require,module,exports){var baseIsMatch=require("./baseIsMatch"),getMatchData=require("./getMatchData"),toObject=require("./toObject");function baseMatches(source){var matchData=getMatchData(source);if(matchData.length==1&&matchData[0][2]){var key=matchData[0][0],value=matchData[0][1];return function(object){if(object==null){return false}return object[key]===value&&(value!==undefined||key in toObject(object))}}return function(object){return baseIsMatch(object,matchData)}}module.exports=baseMatches},{"./baseIsMatch":41,"./getMatchData":75,"./toObject":96}],44:[function(require,module,exports){var baseGet=require("./baseGet"),baseIsEqual=require("./baseIsEqual"),baseSlice=require("./baseSlice"),isArray=require("../lang/isArray"),isKey=require("./isKey"),isStrictComparable=require("./isStrictComparable"),last=require("../array/last"),toObject=require("./toObject"),toPath=require("./toPath");function baseMatchesProperty(path,srcValue){var isArr=isArray(path),isCommon=isKey(path)&&isStrictComparable(srcValue),pathKey=path+"";path=toPath(path);return function(object){if(object==null){return false}var key=pathKey;object=toObject(object);if((isArr||!isCommon)&&!(key in object)){object=path.length==1?object:baseGet(object,baseSlice(path,0,-1));if(object==null){return false}key=last(path);object=toObject(object)}return object[key]===srcValue?srcValue!==undefined||key in object:baseIsEqual(srcValue,object[key],undefined,true)}}module.exports=baseMatchesProperty},{"../array/last":5,"../lang/isArray":100,"./baseGet":36,"./baseIsEqual":38,"./baseSlice":49,"./isKey":81,"./isStrictComparable":85,"./toObject":96,"./toPath":97}],45:[function(require,module,exports){function baseProperty(key){return function(object){return object==null?undefined:object[key]}}module.exports=baseProperty},{}],46:[function(require,module,exports){var baseGet=require("./baseGet"),toPath=require("./toPath");function basePropertyDeep(path){var pathKey=path+"";path=toPath(path);return function(object){return baseGet(object,path,pathKey)}}module.exports=basePropertyDeep},{"./baseGet":36,"./toPath":97}],47:[function(require,module,exports){function baseReduce(collection,iteratee,accumulator,initFromCollection,eachFunc){eachFunc(collection,function(value,index,collection){accumulator=initFromCollection?(initFromCollection=false,value):iteratee(accumulator,value,index,collection)});return accumulator}module.exports=baseReduce},{}],48:[function(require,module,exports){var identity=require("../utility/identity"),metaMap=require("./metaMap");var baseSetData=!metaMap?identity:function(func,data){metaMap.set(func,data);return func};module.exports=baseSetData},{"../utility/identity":116,"./metaMap":87}],49:[function(require,module,exports){function baseSlice(array,start,end){var index=-1,length=array.length;start=start==null?0:+start||0;if(start<0){start=-start>length?0:length+start}end=end===undefined||end>length?length:+end||0;if(end<0){end+=length}length=start>end?0:end-start>>>0;start>>>=0;var result=Array(length);while(++index<length){result[index]=array[index+start]}return result}module.exports=baseSlice},{}],50:[function(require,module,exports){var baseEach=require("./baseEach");function baseSum(collection,iteratee){var result=0;baseEach(collection,function(value,index,collection){result+=+iteratee(value,index,collection)||0});return result}module.exports=baseSum},{"./baseEach":28}],51:[function(require,module,exports){function baseToString(value){if(typeof value=="string"){return value}return value==null?"":value+""}module.exports=baseToString},{}],52:[function(require,module,exports){function baseValues(object,props){var index=-1,length=props.length,result=Array(length);while(++index<length){result[index]=object[props[index]]}return result}module.exports=baseValues},{}],53:[function(require,module,exports){var identity=require("../utility/identity");function bindCallback(func,thisArg,argCount){if(typeof func!="function"){return identity}if(thisArg===undefined){return func}switch(argCount){case 1:return function(value){return func.call(thisArg,value)};case 3:return function(value,index,collection){return func.call(thisArg,value,index,collection)};case 4:return function(accumulator,value,index,collection){return func.call(thisArg,accumulator,value,index,collection)};case 5:return function(value,other,key,object,source){return func.call(thisArg,value,other,key,object,source)}}return function(){return func.apply(thisArg,arguments)}}module.exports=bindCallback},{"../utility/identity":116}],54:[function(require,module,exports){var isObject=require("../lang/isObject");function cacheIndexOf(cache,value){var data=cache.data,result=typeof value=="string"||isObject(value)?data.set.has(value):data.hash[value];return result?0:-1}module.exports=cacheIndexOf},{"../lang/isObject":104}],55:[function(require,module,exports){var isObject=require("../lang/isObject");function cachePush(value){var data=this.data;if(typeof value=="string"||isObject(value)){data.set.add(value)}else{data.hash[value]=true}}module.exports=cachePush},{"../lang/isObject":104}],56:[function(require,module,exports){var nativeMax=Math.max;function composeArgs(args,partials,holders){var holdersLength=holders.length,argsIndex=-1,argsLength=nativeMax(args.length-holdersLength,0),leftIndex=-1,leftLength=partials.length,result=Array(argsLength+leftLength);while(++leftIndex<leftLength){result[leftIndex]=partials[leftIndex]}while(++argsIndex<holdersLength){result[holders[argsIndex]]=args[argsIndex]}while(argsLength--){result[leftIndex++]=args[argsIndex++]}return result}module.exports=composeArgs},{}],57:[function(require,module,exports){var nativeMax=Math.max;function composeArgsRight(args,partials,holders){var holdersIndex=-1,holdersLength=holders.length,argsIndex=-1,argsLength=nativeMax(args.length-holdersLength,0),rightIndex=-1,rightLength=partials.length,result=Array(argsLength+rightLength);while(++argsIndex<argsLength){result[argsIndex]=args[argsIndex]}var offset=argsIndex;while(++rightIndex<rightLength){result[offset+rightIndex]=partials[rightIndex]}while(++holdersIndex<holdersLength){result[offset+holders[holdersIndex]]=args[argsIndex++]}return result}module.exports=composeArgsRight},{}],58:[function(require,module,exports){var getLength=require("./getLength"),isLength=require("./isLength"),toObject=require("./toObject");function createBaseEach(eachFunc,fromRight){return function(collection,iteratee){var length=collection?getLength(collection):0;if(!isLength(length)){return eachFunc(collection,iteratee)}var index=fromRight?length:-1,iterable=toObject(collection);while(fromRight?index--:++index<length){if(iteratee(iterable[index],index,iterable)===false){break}}return collection}}module.exports=createBaseEach},{"./getLength":74,"./isLength":83,"./toObject":96}],59:[function(require,module,exports){var toObject=require("./toObject");function createBaseFor(fromRight){return function(object,iteratee,keysFunc){var iterable=toObject(object),props=keysFunc(object),length=props.length,index=fromRight?length:-1;while(fromRight?index--:++index<length){var key=props[index];if(iteratee(iterable[key],key,iterable)===false){break}}return object}}module.exports=createBaseFor},{"./toObject":96}],60:[function(require,module,exports){(function(global){var createCtorWrapper=require("./createCtorWrapper");function createBindWrapper(func,thisArg){var Ctor=createCtorWrapper(func);function wrapper(){var fn=this&&this!==global&&this instanceof wrapper?Ctor:func;return fn.apply(thisArg,arguments)}return wrapper}module.exports=createBindWrapper}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./createCtorWrapper":62}],61:[function(require,module,exports){(function(global){var SetCache=require("./SetCache"),constant=require("../utility/constant"),getNative=require("./getNative");var Set=getNative(global,"Set");var nativeCreate=getNative(Object,"create");var createCache=!(nativeCreate&&Set)?constant(null):function(values){return new SetCache(values)};module.exports=createCache}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"../utility/constant":115,"./SetCache":17,"./getNative":76}],62:[function(require,module,exports){var baseCreate=require("./baseCreate"),isObject=require("../lang/isObject");function createCtorWrapper(Ctor){return function(){var args=arguments;switch(args.length){case 0:return new Ctor;case 1:return new Ctor(args[0]);case 2:return new Ctor(args[0],args[1]);case 3:return new Ctor(args[0],args[1],args[2]);case 4:return new Ctor(args[0],args[1],args[2],args[3]);case 5:return new Ctor(args[0],args[1],args[2],args[3],args[4])}var thisBinding=baseCreate(Ctor.prototype),result=Ctor.apply(thisBinding,args);return isObject(result)?result:thisBinding}}module.exports=createCtorWrapper},{"../lang/isObject":104,"./baseCreate":26}],63:[function(require,module,exports){var baseCallback=require("./baseCallback"),baseFind=require("./baseFind"),baseFindIndex=require("./baseFindIndex"),isArray=require("../lang/isArray");function createFind(eachFunc,fromRight){return function(collection,predicate,thisArg){predicate=baseCallback(predicate,thisArg,3);if(isArray(collection)){var index=baseFindIndex(collection,predicate,fromRight);return index>-1?collection[index]:undefined}return baseFind(collection,predicate,eachFunc)}}module.exports=createFind},{"../lang/isArray":100,"./baseCallback":25,"./baseFind":30,"./baseFindIndex":31}],64:[function(require,module,exports){var bindCallback=require("./bindCallback"),isArray=require("../lang/isArray");function createForEach(arrayFunc,eachFunc){return function(collection,iteratee,thisArg){return typeof iteratee=="function"&&thisArg===undefined&&isArray(collection)?arrayFunc(collection,iteratee):eachFunc(collection,bindCallback(iteratee,thisArg,3))}}module.exports=createForEach},{"../lang/isArray":100,"./bindCallback":53}],65:[function(require,module,exports){(function(global){var arrayCopy=require("./arrayCopy"),composeArgs=require("./composeArgs"),composeArgsRight=require("./composeArgsRight"),createCtorWrapper=require("./createCtorWrapper"),isLaziable=require("./isLaziable"),reorder=require("./reorder"),replaceHolders=require("./replaceHolders"),setData=require("./setData");var BIND_FLAG=1,BIND_KEY_FLAG=2,CURRY_BOUND_FLAG=4,CURRY_FLAG=8,CURRY_RIGHT_FLAG=16,PARTIAL_FLAG=32,PARTIAL_RIGHT_FLAG=64,ARY_FLAG=128;var nativeMax=Math.max;function createHybridWrapper(func,bitmask,thisArg,partials,holders,partialsRight,holdersRight,argPos,ary,arity){var isAry=bitmask&ARY_FLAG,isBind=bitmask&BIND_FLAG,isBindKey=bitmask&BIND_KEY_FLAG,isCurry=bitmask&CURRY_FLAG,isCurryBound=bitmask&CURRY_BOUND_FLAG,isCurryRight=bitmask&CURRY_RIGHT_FLAG,Ctor=isBindKey?null:createCtorWrapper(func);function wrapper(){var length=arguments.length,index=length,args=Array(length);while(index--){args[index]=arguments[index]}if(partials){args=composeArgs(args,partials,holders)}if(partialsRight){args=composeArgsRight(args,partialsRight,holdersRight)}if(isCurry||isCurryRight){var placeholder=wrapper.placeholder,argsHolders=replaceHolders(args,placeholder);length-=argsHolders.length;if(length<arity){var newArgPos=argPos?arrayCopy(argPos):null,newArity=nativeMax(arity-length,0),newsHolders=isCurry?argsHolders:null,newHoldersRight=isCurry?null:argsHolders,newPartials=isCurry?args:null,newPartialsRight=isCurry?null:args;bitmask|=isCurry?PARTIAL_FLAG:PARTIAL_RIGHT_FLAG;bitmask&=~(isCurry?PARTIAL_RIGHT_FLAG:PARTIAL_FLAG);if(!isCurryBound){bitmask&=~(BIND_FLAG|BIND_KEY_FLAG)}var newData=[func,bitmask,thisArg,newPartials,newsHolders,newPartialsRight,newHoldersRight,newArgPos,ary,newArity],result=createHybridWrapper.apply(undefined,newData);if(isLaziable(func)){setData(result,newData)}result.placeholder=placeholder;return result}}var thisBinding=isBind?thisArg:this,fn=isBindKey?thisBinding[func]:func;if(argPos){args=reorder(args,argPos)}if(isAry&&ary<args.length){args.length=ary}if(this&&this!==global&&this instanceof wrapper){fn=Ctor||createCtorWrapper(func)}return fn.apply(thisBinding,args)}return wrapper}module.exports=createHybridWrapper}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./arrayCopy":18,"./composeArgs":56,"./composeArgsRight":57,"./createCtorWrapper":62,"./isLaziable":82,"./reorder":91,"./replaceHolders":92,"./setData":93}],66:[function(require,module,exports){(function(global){var createCtorWrapper=require("./createCtorWrapper");var BIND_FLAG=1;function createPartialWrapper(func,bitmask,thisArg,partials){var isBind=bitmask&BIND_FLAG,Ctor=createCtorWrapper(func);function wrapper(){var argsIndex=-1,argsLength=arguments.length,leftIndex=-1,leftLength=partials.length,args=Array(argsLength+leftLength);while(++leftIndex<leftLength){args[leftIndex]=partials[leftIndex];
 
 
 
 
 
 
2
 
3
- }while(argsLength--){args[leftIndex++]=arguments[++argsIndex]}var fn=this&&this!==global&&this instanceof wrapper?Ctor:func;return fn.apply(isBind?thisArg:this,args)}return wrapper}module.exports=createPartialWrapper}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./createCtorWrapper":62}],67:[function(require,module,exports){var baseCallback=require("./baseCallback"),baseReduce=require("./baseReduce"),isArray=require("../lang/isArray");function createReduce(arrayFunc,eachFunc){return function(collection,iteratee,accumulator,thisArg){var initFromArray=arguments.length<3;return typeof iteratee=="function"&&thisArg===undefined&&isArray(collection)?arrayFunc(collection,iteratee,accumulator,initFromArray):baseReduce(collection,baseCallback(iteratee,thisArg,4),accumulator,initFromArray,eachFunc)}}module.exports=createReduce},{"../lang/isArray":100,"./baseCallback":25,"./baseReduce":47}],68:[function(require,module,exports){var baseSetData=require("./baseSetData"),createBindWrapper=require("./createBindWrapper"),createHybridWrapper=require("./createHybridWrapper"),createPartialWrapper=require("./createPartialWrapper"),getData=require("./getData"),mergeData=require("./mergeData"),setData=require("./setData");var BIND_FLAG=1,BIND_KEY_FLAG=2,PARTIAL_FLAG=32,PARTIAL_RIGHT_FLAG=64;var FUNC_ERROR_TEXT="Expected a function";var nativeMax=Math.max;function createWrapper(func,bitmask,thisArg,partials,holders,argPos,ary,arity){var isBindKey=bitmask&BIND_KEY_FLAG;if(!isBindKey&&typeof func!="function"){throw new TypeError(FUNC_ERROR_TEXT)}var length=partials?partials.length:0;if(!length){bitmask&=~(PARTIAL_FLAG|PARTIAL_RIGHT_FLAG);partials=holders=null}length-=holders?holders.length:0;if(bitmask&PARTIAL_RIGHT_FLAG){var partialsRight=partials,holdersRight=holders;partials=holders=null}var data=isBindKey?null:getData(func),newData=[func,bitmask,thisArg,partials,holders,partialsRight,holdersRight,argPos,ary,arity];if(data){mergeData(newData,data);bitmask=newData[1];arity=newData[9]}newData[9]=arity==null?isBindKey?0:func.length:nativeMax(arity-length,0)||0;if(bitmask==BIND_FLAG){var result=createBindWrapper(newData[0],newData[2])}else if((bitmask==PARTIAL_FLAG||bitmask==(BIND_FLAG|PARTIAL_FLAG))&&!newData[4].length){result=createPartialWrapper.apply(undefined,newData)}else{result=createHybridWrapper.apply(undefined,newData)}var setter=data?baseSetData:setData;return setter(result,newData)}module.exports=createWrapper},{"./baseSetData":48,"./createBindWrapper":60,"./createHybridWrapper":65,"./createPartialWrapper":66,"./getData":72,"./mergeData":86,"./setData":93}],69:[function(require,module,exports){var arraySome=require("./arraySome");function equalArrays(array,other,equalFunc,customizer,isLoose,stackA,stackB){var index=-1,arrLength=array.length,othLength=other.length;if(arrLength!=othLength&&!(isLoose&&othLength>arrLength)){return false}while(++index<arrLength){var arrValue=array[index],othValue=other[index],result=customizer?customizer(isLoose?othValue:arrValue,isLoose?arrValue:othValue,index):undefined;if(result!==undefined){if(result){continue}return false}if(isLoose){if(!arraySome(other,function(othValue){return arrValue===othValue||equalFunc(arrValue,othValue,customizer,isLoose,stackA,stackB)})){return false}}else if(!(arrValue===othValue||equalFunc(arrValue,othValue,customizer,isLoose,stackA,stackB))){return false}}return true}module.exports=equalArrays},{"./arraySome":23}],70:[function(require,module,exports){var boolTag="[object Boolean]",dateTag="[object Date]",errorTag="[object Error]",numberTag="[object Number]",regexpTag="[object RegExp]",stringTag="[object String]";function equalByTag(object,other,tag){switch(tag){case boolTag:case dateTag:return+object==+other;case errorTag:return object.name==other.name&&object.message==other.message;case numberTag:return object!=+object?other!=+other:object==+other;case regexpTag:case stringTag:return object==other+""}return false}module.exports=equalByTag},{}],71:[function(require,module,exports){var keys=require("../object/keys");var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function equalObjects(object,other,equalFunc,customizer,isLoose,stackA,stackB){var objProps=keys(object),objLength=objProps.length,othProps=keys(other),othLength=othProps.length;if(objLength!=othLength&&!isLoose){return false}var index=objLength;while(index--){var key=objProps[index];if(!(isLoose?key in other:hasOwnProperty.call(other,key))){return false}}var skipCtor=isLoose;while(++index<objLength){key=objProps[index];var objValue=object[key],othValue=other[key],result=customizer?customizer(isLoose?othValue:objValue,isLoose?objValue:othValue,key):undefined;if(!(result===undefined?equalFunc(objValue,othValue,customizer,isLoose,stackA,stackB):result)){return false}skipCtor||(skipCtor=key=="constructor")}if(!skipCtor){var objCtor=object.constructor,othCtor=other.constructor;if(objCtor!=othCtor&&("constructor"in object&&"constructor"in other)&&!(typeof objCtor=="function"&&objCtor instanceof objCtor&&typeof othCtor=="function"&&othCtor instanceof othCtor)){return false}}return true}module.exports=equalObjects},{"../object/keys":109}],72:[function(require,module,exports){var metaMap=require("./metaMap"),noop=require("../utility/noop");var getData=!metaMap?noop:function(func){return metaMap.get(func)};module.exports=getData},{"../utility/noop":117,"./metaMap":87}],73:[function(require,module,exports){var realNames=require("./realNames");function getFuncName(func){var result=func.name,array=realNames[result],length=array?array.length:0;while(length--){var data=array[length],otherFunc=data.func;if(otherFunc==null||otherFunc==func){return data.name}}return result}module.exports=getFuncName},{"./realNames":90}],74:[function(require,module,exports){var baseProperty=require("./baseProperty");var getLength=baseProperty("length");module.exports=getLength},{"./baseProperty":45}],75:[function(require,module,exports){var isStrictComparable=require("./isStrictComparable"),pairs=require("../object/pairs");function getMatchData(object){var result=pairs(object),length=result.length;while(length--){result[length][2]=isStrictComparable(result[length][1])}return result}module.exports=getMatchData},{"../object/pairs":112,"./isStrictComparable":85}],76:[function(require,module,exports){var isNative=require("../lang/isNative");function getNative(object,key){var value=object==null?undefined:object[key];return isNative(value)?value:undefined}module.exports=getNative},{"../lang/isNative":103}],77:[function(require,module,exports){function indexOfNaN(array,fromIndex,fromRight){var length=array.length,index=fromIndex+(fromRight?0:-1);while(fromRight?index--:++index<length){var other=array[index];if(other!==other){return index}}return-1}module.exports=indexOfNaN},{}],78:[function(require,module,exports){var getLength=require("./getLength"),isLength=require("./isLength");function isArrayLike(value){return value!=null&&isLength(getLength(value))}module.exports=isArrayLike},{"./getLength":74,"./isLength":83}],79:[function(require,module,exports){var reIsUint=/^\d+$/;var MAX_SAFE_INTEGER=9007199254740991;function isIndex(value,length){value=typeof value=="number"||reIsUint.test(value)?+value:-1;length=length==null?MAX_SAFE_INTEGER:length;return value>-1&&value%1==0&&value<length}module.exports=isIndex},{}],80:[function(require,module,exports){var isArrayLike=require("./isArrayLike"),isIndex=require("./isIndex"),isObject=require("../lang/isObject");function isIterateeCall(value,index,object){if(!isObject(object)){return false}var type=typeof index;if(type=="number"?isArrayLike(object)&&isIndex(index,object.length):type=="string"&&index in object){var other=object[index];return value===value?value===other:other!==other}return false}module.exports=isIterateeCall},{"../lang/isObject":104,"./isArrayLike":78,"./isIndex":79}],81:[function(require,module,exports){var isArray=require("../lang/isArray"),toObject=require("./toObject");var reIsDeepProp=/\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\n\\]|\\.)*?\1)\]/,reIsPlainProp=/^\w*$/;function isKey(value,object){var type=typeof value;if(type=="string"&&reIsPlainProp.test(value)||type=="number"){return true}if(isArray(value)){return false}var result=!reIsDeepProp.test(value);return result||object!=null&&value in toObject(object)}module.exports=isKey},{"../lang/isArray":100,"./toObject":96}],82:[function(require,module,exports){var LazyWrapper=require("./LazyWrapper"),getData=require("./getData"),getFuncName=require("./getFuncName"),lodash=require("../chain/lodash");function isLaziable(func){var funcName=getFuncName(func);if(!(funcName in LazyWrapper.prototype)){return false}var other=lodash[funcName];if(func===other){return true}var data=getData(other);return!!data&&func===data[0]}module.exports=isLaziable},{"../chain/lodash":6,"./LazyWrapper":15,"./getData":72,"./getFuncName":73}],83:[function(require,module,exports){var MAX_SAFE_INTEGER=9007199254740991;function isLength(value){return typeof value=="number"&&value>-1&&value%1==0&&value<=MAX_SAFE_INTEGER}module.exports=isLength},{}],84:[function(require,module,exports){function isObjectLike(value){return!!value&&typeof value=="object"}module.exports=isObjectLike},{}],85:[function(require,module,exports){var isObject=require("../lang/isObject");function isStrictComparable(value){return value===value&&!isObject(value)}module.exports=isStrictComparable},{"../lang/isObject":104}],86:[function(require,module,exports){var arrayCopy=require("./arrayCopy"),composeArgs=require("./composeArgs"),composeArgsRight=require("./composeArgsRight"),replaceHolders=require("./replaceHolders");var BIND_FLAG=1,CURRY_BOUND_FLAG=4,CURRY_FLAG=8,ARY_FLAG=128,REARG_FLAG=256;var PLACEHOLDER="__lodash_placeholder__";var nativeMin=Math.min;function mergeData(data,source){var bitmask=data[1],srcBitmask=source[1],newBitmask=bitmask|srcBitmask,isCommon=newBitmask<ARY_FLAG;var isCombo=srcBitmask==ARY_FLAG&&bitmask==CURRY_FLAG||srcBitmask==ARY_FLAG&&bitmask==REARG_FLAG&&data[7].length<=source[8]||srcBitmask==(ARY_FLAG|REARG_FLAG)&&bitmask==CURRY_FLAG;if(!(isCommon||isCombo)){return data}if(srcBitmask&BIND_FLAG){data[2]=source[2];newBitmask|=bitmask&BIND_FLAG?0:CURRY_BOUND_FLAG}var value=source[3];if(value){var partials=data[3];data[3]=partials?composeArgs(partials,value,source[4]):arrayCopy(value);data[4]=partials?replaceHolders(data[3],PLACEHOLDER):arrayCopy(source[4])}value=source[5];if(value){partials=data[5];data[5]=partials?composeArgsRight(partials,value,source[6]):arrayCopy(value);data[6]=partials?replaceHolders(data[5],PLACEHOLDER):arrayCopy(source[6])}value=source[7];if(value){data[7]=arrayCopy(value)}if(srcBitmask&ARY_FLAG){data[8]=data[8]==null?source[8]:nativeMin(data[8],source[8])}if(data[9]==null){data[9]=source[9]}data[0]=source[0];data[1]=newBitmask;return data}module.exports=mergeData},{"./arrayCopy":18,"./composeArgs":56,"./composeArgsRight":57,"./replaceHolders":92}],87:[function(require,module,exports){(function(global){var getNative=require("./getNative");var WeakMap=getNative(global,"WeakMap");var metaMap=WeakMap&&new WeakMap;module.exports=metaMap}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./getNative":76}],88:[function(require,module,exports){var toObject=require("./toObject");function pickByArray(object,props){object=toObject(object);var index=-1,length=props.length,result={};while(++index<length){var key=props[index];if(key in object){result[key]=object[key]}}return result}module.exports=pickByArray},{"./toObject":96}],89:[function(require,module,exports){var baseForIn=require("./baseForIn");function pickByCallback(object,predicate){var result={};baseForIn(object,function(value,key,object){if(predicate(value,key,object)){result[key]=value}});return result}module.exports=pickByCallback},{"./baseForIn":34}],90:[function(require,module,exports){var realNames={};module.exports=realNames},{}],91:[function(require,module,exports){var arrayCopy=require("./arrayCopy"),isIndex=require("./isIndex");var nativeMin=Math.min;function reorder(array,indexes){var arrLength=array.length,length=nativeMin(indexes.length,arrLength),oldArray=arrayCopy(array);while(length--){var index=indexes[length];array[length]=isIndex(index,arrLength)?oldArray[index]:undefined}return array}module.exports=reorder},{"./arrayCopy":18,"./isIndex":79}],92:[function(require,module,exports){var PLACEHOLDER="__lodash_placeholder__";function replaceHolders(array,placeholder){var index=-1,length=array.length,resIndex=-1,result=[];while(++index<length){if(array[index]===placeholder){array[index]=PLACEHOLDER;result[++resIndex]=index}}return result}module.exports=replaceHolders},{}],93:[function(require,module,exports){var baseSetData=require("./baseSetData"),now=require("../date/now");var HOT_COUNT=150,HOT_SPAN=16;var setData=function(){var count=0,lastCalled=0;return function(key,value){var stamp=now(),remaining=HOT_SPAN-(stamp-lastCalled);lastCalled=stamp;if(remaining>0){if(++count>=HOT_COUNT){return key}}else{count=0}return baseSetData(key,value)}}();module.exports=setData},{"../date/now":12,"./baseSetData":48}],94:[function(require,module,exports){var isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isIndex=require("./isIndex"),isLength=require("./isLength"),keysIn=require("../object/keysIn");var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function shimKeys(object){var props=keysIn(object),propsLength=props.length,length=propsLength&&object.length;var allowIndexes=!!length&&isLength(length)&&(isArray(object)||isArguments(object));var index=-1,result=[];while(++index<propsLength){var key=props[index];if(allowIndexes&&isIndex(key,length)||hasOwnProperty.call(object,key)){result.push(key)}}return result}module.exports=shimKeys},{"../lang/isArguments":99,"../lang/isArray":100,"../object/keysIn":110,"./isIndex":79,"./isLength":83}],95:[function(require,module,exports){var isArrayLike=require("./isArrayLike"),isObject=require("../lang/isObject"),values=require("../object/values");function toIterable(value){if(value==null){return[]}if(!isArrayLike(value)){return values(value)}return isObject(value)?value:Object(value)}module.exports=toIterable},{"../lang/isObject":104,"../object/values":113,"./isArrayLike":78}],96:[function(require,module,exports){var isObject=require("../lang/isObject");function toObject(value){return isObject(value)?value:Object(value)}module.exports=toObject},{"../lang/isObject":104}],97:[function(require,module,exports){var baseToString=require("./baseToString"),isArray=require("../lang/isArray");var rePropName=/[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\n\\]|\\.)*?)\2)\]/g;var reEscapeChar=/\\(\\)?/g;function toPath(value){if(isArray(value)){return value}var result=[];baseToString(value).replace(rePropName,function(match,number,quote,string){result.push(quote?string.replace(reEscapeChar,"$1"):number||match)});return result}module.exports=toPath},{"../lang/isArray":100,"./baseToString":51}],98:[function(require,module,exports){var LazyWrapper=require("./LazyWrapper"),LodashWrapper=require("./LodashWrapper"),arrayCopy=require("./arrayCopy");function wrapperClone(wrapper){return wrapper instanceof LazyWrapper?wrapper.clone():new LodashWrapper(wrapper.__wrapped__,wrapper.__chain__,arrayCopy(wrapper.__actions__))}module.exports=wrapperClone},{"./LazyWrapper":15,"./LodashWrapper":16,"./arrayCopy":18}],99:[function(require,module,exports){var isArrayLike=require("../internal/isArrayLike"),isObjectLike=require("../internal/isObjectLike");var argsTag="[object Arguments]";var objectProto=Object.prototype;var objToString=objectProto.toString;function isArguments(value){return isObjectLike(value)&&isArrayLike(value)&&objToString.call(value)==argsTag}module.exports=isArguments},{"../internal/isArrayLike":78,"../internal/isObjectLike":84}],100:[function(require,module,exports){var getNative=require("../internal/getNative"),isLength=require("../internal/isLength"),isObjectLike=require("../internal/isObjectLike");var arrayTag="[object Array]";var objectProto=Object.prototype;var objToString=objectProto.toString;var nativeIsArray=getNative(Array,"isArray");var isArray=nativeIsArray||function(value){return isObjectLike(value)&&isLength(value.length)&&objToString.call(value)==arrayTag};module.exports=isArray},{"../internal/getNative":76,"../internal/isLength":83,"../internal/isObjectLike":84}],101:[function(require,module,exports){var isArguments=require("./isArguments"),isArray=require("./isArray"),isArrayLike=require("../internal/isArrayLike"),isFunction=require("./isFunction"),isObjectLike=require("../internal/isObjectLike"),isString=require("./isString"),keys=require("../object/keys");function isEmpty(value){if(value==null){return true}if(isArrayLike(value)&&(isArray(value)||isString(value)||isArguments(value)||isObjectLike(value)&&isFunction(value.splice))){return!value.length}return!keys(value).length}module.exports=isEmpty},{"../internal/isArrayLike":78,"../internal/isObjectLike":84,"../object/keys":109,"./isArguments":99,"./isArray":100,"./isFunction":102,"./isString":105}],102:[function(require,module,exports){(function(global){var baseIsFunction=require("../internal/baseIsFunction"),getNative=require("../internal/getNative");var funcTag="[object Function]";var objectProto=Object.prototype;var objToString=objectProto.toString;var Uint8Array=getNative(global,"Uint8Array");var isFunction=!(baseIsFunction(/x/)||Uint8Array&&!baseIsFunction(Uint8Array))?baseIsFunction:function(value){return objToString.call(value)==funcTag};module.exports=isFunction}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"../internal/baseIsFunction":40,"../internal/getNative":76}],103:[function(require,module,exports){var escapeRegExp=require("../string/escapeRegExp"),isObjectLike=require("../internal/isObjectLike");var funcTag="[object Function]";var reIsHostCtor=/^\[object .+?Constructor\]$/;var objectProto=Object.prototype;var fnToString=Function.prototype.toString;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;var reIsNative=RegExp("^"+escapeRegExp(fnToString.call(hasOwnProperty)).replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g,"$1.*?")+"$");function isNative(value){if(value==null){return false}if(objToString.call(value)==funcTag){return reIsNative.test(fnToString.call(value))}return isObjectLike(value)&&reIsHostCtor.test(value)}module.exports=isNative},{"../internal/isObjectLike":84,"../string/escapeRegExp":114}],104:[function(require,module,exports){function isObject(value){var type=typeof value;return!!value&&(type=="object"||type=="function")}module.exports=isObject},{}],105:[function(require,module,exports){var isObjectLike=require("../internal/isObjectLike");var stringTag="[object String]";var objectProto=Object.prototype;var objToString=objectProto.toString;function isString(value){return typeof value=="string"||isObjectLike(value)&&objToString.call(value)==stringTag}module.exports=isString},{"../internal/isObjectLike":84}],106:[function(require,module,exports){var isLength=require("../internal/isLength"),isObjectLike=require("../internal/isObjectLike");var argsTag="[object Arguments]",arrayTag="[object Array]",boolTag="[object Boolean]",dateTag="[object Date]",errorTag="[object Error]",funcTag="[object Function]",mapTag="[object Map]",numberTag="[object Number]",objectTag="[object Object]",regexpTag="[object RegExp]",setTag="[object Set]",stringTag="[object String]",weakMapTag="[object WeakMap]";var arrayBufferTag="[object ArrayBuffer]",float32Tag="[object Float32Array]",float64Tag="[object Float64Array]",int8Tag="[object Int8Array]",int16Tag="[object Int16Array]",int32Tag="[object Int32Array]",uint8Tag="[object Uint8Array]",uint8ClampedTag="[object Uint8ClampedArray]",uint16Tag="[object Uint16Array]",uint32Tag="[object Uint32Array]";var typedArrayTags={};typedArrayTags[float32Tag]=typedArrayTags[float64Tag]=typedArrayTags[int8Tag]=typedArrayTags[int16Tag]=typedArrayTags[int32Tag]=typedArrayTags[uint8Tag]=typedArrayTags[uint8ClampedTag]=typedArrayTags[uint16Tag]=typedArrayTags[uint32Tag]=true;typedArrayTags[argsTag]=typedArrayTags[arrayTag]=typedArrayTags[arrayBufferTag]=typedArrayTags[boolTag]=typedArrayTags[dateTag]=typedArrayTags[errorTag]=typedArrayTags[funcTag]=typedArrayTags[mapTag]=typedArrayTags[numberTag]=typedArrayTags[objectTag]=typedArrayTags[regexpTag]=typedArrayTags[setTag]=typedArrayTags[stringTag]=typedArrayTags[weakMapTag]=false;var objectProto=Object.prototype;var objToString=objectProto.toString;function isTypedArray(value){return isObjectLike(value)&&isLength(value.length)&&!!typedArrayTags[objToString.call(value)]}module.exports=isTypedArray},{"../internal/isLength":83,"../internal/isObjectLike":84}],107:[function(require,module,exports){function isUndefined(value){return value===undefined}module.exports=isUndefined},{}],108:[function(require,module,exports){var arraySum=require("../internal/arraySum"),baseCallback=require("../internal/baseCallback"),baseSum=require("../internal/baseSum"),isArray=require("../lang/isArray"),isIterateeCall=require("../internal/isIterateeCall"),toIterable=require("../internal/toIterable");function sum(collection,iteratee,thisArg){if(thisArg&&isIterateeCall(collection,iteratee,thisArg)){iteratee=null}var noIteratee=iteratee==null;iteratee=noIteratee?iteratee:baseCallback(iteratee,thisArg,3);return noIteratee?arraySum(isArray(collection)?collection:toIterable(collection)):baseSum(collection,iteratee)}module.exports=sum},{"../internal/arraySum":24,"../internal/baseCallback":25,"../internal/baseSum":50,"../internal/isIterateeCall":80,"../internal/toIterable":95,"../lang/isArray":100}],109:[function(require,module,exports){var getNative=require("../internal/getNative"),isArrayLike=require("../internal/isArrayLike"),isObject=require("../lang/isObject"),shimKeys=require("../internal/shimKeys");var nativeKeys=getNative(Object,"keys");var keys=!nativeKeys?shimKeys:function(object){var Ctor=object==null?null:object.constructor;if(typeof Ctor=="function"&&Ctor.prototype===object||typeof object!="function"&&isArrayLike(object)){return shimKeys(object)}return isObject(object)?nativeKeys(object):[]};module.exports=keys},{"../internal/getNative":76,"../internal/isArrayLike":78,"../internal/shimKeys":94,"../lang/isObject":104}],110:[function(require,module,exports){var isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isIndex=require("../internal/isIndex"),isLength=require("../internal/isLength"),isObject=require("../lang/isObject");var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function keysIn(object){if(object==null){return[]}if(!isObject(object)){object=Object(object)}var length=object.length;length=length&&isLength(length)&&(isArray(object)||isArguments(object))&&length||0;var Ctor=object.constructor,index=-1,isProto=typeof Ctor=="function"&&Ctor.prototype===object,result=Array(length),skipIndexes=length>0;while(++index<length){result[index]=index+""}for(var key in object){if(!(skipIndexes&&isIndex(key,length))&&!(key=="constructor"&&(isProto||!hasOwnProperty.call(object,key)))){result.push(key)}}return result}module.exports=keysIn},{"../internal/isIndex":79,"../internal/isLength":83,"../lang/isArguments":99,"../lang/isArray":100,"../lang/isObject":104}],111:[function(require,module,exports){var arrayMap=require("../internal/arrayMap"),baseDifference=require("../internal/baseDifference"),baseFlatten=require("../internal/baseFlatten"),bindCallback=require("../internal/bindCallback"),keysIn=require("./keysIn"),pickByArray=require("../internal/pickByArray"),pickByCallback=require("../internal/pickByCallback"),restParam=require("../function/restParam");var omit=restParam(function(object,props){if(object==null){return{}}if(typeof props[0]!="function"){var props=arrayMap(baseFlatten(props),String);return pickByArray(object,baseDifference(keysIn(object),props))}var predicate=bindCallback(props[0],props[1],3);return pickByCallback(object,function(value,key,object){return!predicate(value,key,object)})});module.exports=omit},{"../function/restParam":14,"../internal/arrayMap":21,"../internal/baseDifference":27,"../internal/baseFlatten":32,"../internal/bindCallback":53,"../internal/pickByArray":88,"../internal/pickByCallback":89,"./keysIn":110}],112:[function(require,module,exports){var keys=require("./keys"),toObject=require("../internal/toObject");function pairs(object){object=toObject(object);var index=-1,props=keys(object),length=props.length,result=Array(length);while(++index<length){var key=props[index];result[index]=[key,object[key]]}return result}module.exports=pairs},{"../internal/toObject":96,"./keys":109}],113:[function(require,module,exports){var baseValues=require("../internal/baseValues"),keys=require("./keys");function values(object){return baseValues(object,keys(object))}module.exports=values},{"../internal/baseValues":52,"./keys":109}],114:[function(require,module,exports){var baseToString=require("../internal/baseToString");var reRegExpChars=/[.*+?^${}()|[\]\/\\]/g,reHasRegExpChars=RegExp(reRegExpChars.source);function escapeRegExp(string){string=baseToString(string);return string&&reHasRegExpChars.test(string)?string.replace(reRegExpChars,"\\$&"):string}module.exports=escapeRegExp},{"../internal/baseToString":51}],115:[function(require,module,exports){function constant(value){return function(){return value}}module.exports=constant},{}],116:[function(require,module,exports){function identity(value){return value}module.exports=identity},{}],117:[function(require,module,exports){function noop(){}module.exports=noop},{}],118:[function(require,module,exports){var baseProperty=require("../internal/baseProperty"),basePropertyDeep=require("../internal/basePropertyDeep"),isKey=require("../internal/isKey");function property(path){return isKey(path)?baseProperty(path):basePropertyDeep(path)}module.exports=property},{"../internal/baseProperty":45,"../internal/basePropertyDeep":46,"../internal/isKey":81}],119:[function(require,module,exports){"use strict";var extend=require("../functions/extend");var isUndefined=require("lodash/lang/isUndefined");var isString=require("lodash/lang/isString");var isFunction=require("lodash/lang/isFunction");var isEmpty=require("lodash/lang/isEmpty");var reduce=require("lodash/collection/reduce");var filter=require("lodash/collection/filter");var omit=require("lodash/object/omit");var lib={addRefinement:function addRefinement(refinementList,attribute,value){if(lib.isRefined(refinementList,attribute,value)){return refinementList}var facetRefinement=!refinementList[attribute]?[value]:refinementList[attribute].concat(value);var mod={};mod[attribute]=facetRefinement;return extend({},refinementList,mod)},removeRefinement:function removeRefinement(refinementList,attribute,value){if(isUndefined(value)){return lib.clearRefinement(refinementList,attribute)}return lib.clearRefinement(refinementList,function(v,f){return attribute===f&&value===v})},toggleRefinement:function toggleRefinement(refinementList,attribute,value){if(isUndefined(value))throw new Error("toggleRefinement should be used with a value");if(lib.isRefined(refinementList,attribute,value)){return lib.removeRefinement(refinementList,attribute,value)}return lib.addRefinement(refinementList,attribute,value)},clearRefinement:function clearRefinement(refinementList,attribute,refinementType){if(isUndefined(attribute)){return{}}else if(isString(attribute)){return omit(refinementList,attribute)}else if(isFunction(attribute)){return reduce(refinementList,function(memo,values,key){var facetList=filter(values,function(value){return!attribute(value,key,refinementType)});if(!isEmpty(facetList))memo[key]=facetList;return memo},{})}},isRefined:function isRefined(refinementList,attribute,refinementValue){var containsRefinements=refinementList[attribute]&&refinementList[attribute].length>0;if(refinementValue===undefined){return containsRefinements}return containsRefinements&&refinementList[attribute].indexOf(refinementValue)!==-1}};module.exports=lib},{"../functions/extend":124,"lodash/collection/filter":7,"lodash/collection/reduce":10,"lodash/lang/isEmpty":101,"lodash/lang/isFunction":102,"lodash/lang/isString":105,"lodash/lang/isUndefined":107,"lodash/object/omit":111}],120:[function(require,module,exports){"use strict";var keys=require("lodash/object/keys");var intersection=require("lodash/array/intersection");var forEach=require("lodash/collection/forEach");var reduce=require("lodash/collection/reduce");var filter=require("lodash/collection/filter");var omit=require("lodash/object/omit");var isEmpty=require("lodash/lang/isEmpty");var isUndefined=require("lodash/lang/isUndefined");var isString=require("lodash/lang/isString");var isFunction=require("lodash/lang/isFunction");var extend=require("../functions/extend");var deepFreeze=require("../functions/deepFreeze");var RefinementList=require("./RefinementList");var SearchParameters=function(newParameters){var params=newParameters||{};this.query=params.query||"";this.facets=params.facets||[];this.disjunctiveFacets=params.disjunctiveFacets||[];this.facetsRefinements=params.facetsRefinements||{};this.facetsExcludes=params.facetsExcludes||{};this.disjunctiveFacetsRefinements=params.disjunctiveFacetsRefinements||{};this.numericRefinements=params.numericRefinements||{};this.tagRefinements=params.tagRefinements||[];this.tagFilters=params.tagFilters;this.hitsPerPage=params.hitsPerPage;this.maxValuesPerFacet=params.maxValuesPerFacet;this.page=params.page||0;this.queryType=params.queryType;this.typoTolerance=params.typoTolerance;this.minWordSizefor1Typo=params.minWordSizefor1Typo;this.minWordSizefor2Typos=params.minWordSizefor2Typos;this.allowTyposOnNumericTokens=params.allowTyposOnNumericTokens;this.ignorePlurals=params.ignorePlurals;this.restrictSearchableAttributes=params.restrictSearchableAttributes;this.advancedSyntax=params.advancedSyntax;this.analytics=params.analytics;this.analyticsTags=params.analyticsTags;this.synonyms=params.synonyms;this.replaceSynonymsInHighlight=params.replaceSynonymsInHighlight;this.optionalWords=params.optionalWords;this.removeWordsIfNoResults=params.removeWordsIfNoResults;this.attributesToRetrieve=params.attributesToRetrieve;this.attributesToHighlight=params.attributesToHighlight;this.attributesToSnippet=params.attributesToSnippet;this.getRankingInfo=params.getRankingInfo;this.distinct=params.distinct;this.aroundLatLng=params.aroundLatLng;this.aroundLatLngViaIP=params.aroundLatLngViaIP;this.aroundRadius=params.aroundRadius;this.aroundPrecision=params.aroundPrecision;this.insideBoundingBox=params.insideBoundingBox};SearchParameters.make=function makeSearchParameters(newParameters){var instance=new SearchParameters(newParameters);return deepFreeze(instance)};SearchParameters.validate=function(currentState,parameters){var params=parameters||{};var ks=keys(params);var unknownKeys=filter(ks,function(k){return!currentState.hasOwnProperty(k)});if(unknownKeys.length===1)return new Error("Property "+unknownKeys[0]+" is not defined on SearchParameters (see http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html )");if(unknownKeys.length>1)return new Error("Properties "+unknownKeys.join(" ")+" are not defined on SearchParameters (see http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html )");if(currentState.tagFilters&&params.tagRefinements&&params.tagRefinements.length>0){return new Error("[Tags] Can't switch from the managed tag API to the advanced API. It is probably an error, if it's really what you want, you should first clear the tags with clearTags method.")}if(currentState.tagRefinements.length>0&&params.tagFilters){return new Error("[Tags] Can't switch from the advanced tag API to the managed API. It is probably an error, if it's not, you should first clear the tags with clearTags method.");
 
 
 
4
 
5
- }return null};SearchParameters.prototype={constructor:SearchParameters,clearRefinements:function clearRefinements(attribute){return this.setQueryParameters({page:0,numericRefinements:this._clearNumericRefinements(attribute),facetsRefinements:RefinementList.clearRefinement(this.facetsRefinements,attribute,"conjunctiveFacet"),facetsExcludes:RefinementList.clearRefinement(this.facetsExcludes,attribute,"exclude"),disjunctiveFacetsRefinements:RefinementList.clearRefinement(this.disjunctiveFacetsRefinements,attribute,"disjunctiveFacet")})},clearTags:function clearTags(){if(this.tagFilters===undefined&&this.tagRefinements.length===0)return this;return this.setQueryParameters({page:0,tagFilters:undefined,tagRefinements:[]})},setQuery:function setQuery(newQuery){if(newQuery===this.query)return this;return this.setQueryParameters({query:newQuery,page:0})},setPage:function setPage(newPage){if(newPage===this.page)return this;return this.setQueryParameters({page:newPage})},setFacets:function setFacets(facets){return this.setQueryParameters({facets:facets})},setDisjunctiveFacets:function setDisjunctiveFacets(facets){return this.setQueryParameters({disjunctiveFacets:facets})},setHitsPerPage:function setHitsPerPage(n){if(this.hitsPerPage===n)return this;return this.setQueryParameters({hitsPerPage:n,page:0})},setTypoTolerance:function setTypoTolerance(typoTolerance){if(this.typoTolerance===typoTolerance)return this;return this.setQueryParameters({typoTolerance:typoTolerance,page:0})},addNumericRefinement:function(attribute,operator,value){if(this.isNumericRefined(attribute,operator,value))return this;var mod=extend({},this.numericRefinements);mod[attribute]=extend({},mod[attribute]);mod[attribute][operator]=value;return this.setQueryParameters({page:0,numericRefinements:mod})},getConjunctiveRefinements:function(facetName){return this.facetsRefinements[facetName]||[]},getDisjunctiveRefinements:function(facetName){return this.disjunctiveFacetsRefinements[facetName]||[]},getExcludeRefinements:function(facetName){return this.facetsExcludes[facetName]||[]},removeNumericRefinement:function(attribute,operator){if(!this.isNumericRefined(attribute,operator))return this;return this.setQueryParameters({page:0,numericRefinements:this._clearNumericRefinements(function(value,key){return key===attribute&&value.op===operator})})},getNumericRefinements:function(facetName){return this.numericRefinements[facetName]||[]},getNumericRefinement:function(attribute,operator){return this.numericRefinements[attribute]&&this.numericRefinements[attribute][operator]},_clearNumericRefinements:function _clearNumericRefinements(attribute){if(isUndefined(attribute)){return{}}else if(isString(attribute)){return omit(this.numericRefinements,attribute)}else if(isFunction(attribute)){return reduce(this.numericRefinements,function(memo,operators,key){var operatorList=omit(operators,function(value,operator){return attribute({val:value,op:operator},key,"numeric")});if(!isEmpty(operatorList))memo[key]=operatorList;return memo},{})}},addFacetRefinement:function addFacetRefinement(facet,value){if(RefinementList.isRefined(this.facetsRefinements,facet,value))return this;return this.setQueryParameters({page:0,facetsRefinements:RefinementList.addRefinement(this.facetsRefinements,facet,value)})},addExcludeRefinement:function addExcludeRefinement(facet,value){if(RefinementList.isRefined(this.facetsExcludes,facet,value))return this;return this.setQueryParameters({page:0,facetsExcludes:RefinementList.addRefinement(this.facetsExcludes,facet,value)})},addDisjunctiveFacetRefinement:function addDisjunctiveFacetRefinement(facet,value){if(RefinementList.isRefined(this.disjunctiveFacetsRefinements,facet,value))return this;return this.setQueryParameters({page:0,disjunctiveFacetsRefinements:RefinementList.addRefinement(this.disjunctiveFacetsRefinements,facet,value)})},addTagRefinement:function addTagRefinement(tag){if(this.isTagRefined(tag))return this;var modification={page:0,tagRefinements:this.tagRefinements.concat(tag)};return this.setQueryParameters(modification)},removeFacetRefinement:function removeFacetRefinement(facet,value){if(!RefinementList.isRefined(this.facetsRefinements,facet,value))return this;return this.setQueryParameters({page:0,facetsRefinements:RefinementList.removeRefinement(this.facetsRefinements,facet,value)})},removeExcludeRefinement:function removeExcludeRefinement(facet,value){if(!RefinementList.isRefined(this.facetsExcludes,facet,value))return this;return this.setQueryParameters({page:0,facetsExcludes:RefinementList.removeRefinement(this.facetsExcludes,facet,value)})},removeDisjunctiveFacetRefinement:function removeDisjunctiveFacetRefinement(facet,value){if(!RefinementList.isRefined(this.disjunctiveFacetsRefinements,facet,value))return this;return this.setQueryParameters({page:0,disjunctiveFacetsRefinements:RefinementList.removeRefinement(this.disjunctiveFacetsRefinements,facet,value)})},removeTagRefinement:function removeTagRefinement(tag){if(!this.isTagRefined(tag))return this;var modification={page:0,tagRefinements:filter(this.tagRefinements,function(t){return t!==tag})};return this.setQueryParameters(modification)},toggleFacetRefinement:function toggleFacetRefinement(facet,value){return this.setQueryParameters({page:0,facetsRefinements:RefinementList.toggleRefinement(this.facetsRefinements,facet,value)})},toggleExcludeFacetRefinement:function toggleExcludeFacetRefinement(facet,value){return this.setQueryParameters({page:0,facetsExcludes:RefinementList.toggleRefinement(this.facetsExcludes,facet,value)})},toggleDisjunctiveFacetRefinement:function toggleDisjunctiveFacetRefinement(facet,value){return this.setQueryParameters({page:0,disjunctiveFacetsRefinements:RefinementList.toggleRefinement(this.disjunctiveFacetsRefinements,facet,value)})},toggleTagRefinement:function toggleTagRefinement(tag){if(this.isTagRefined(tag)){return this.removeTagRefinement(tag)}else{return this.addTagRefinement(tag)}},isDisjunctiveFacet:function(facet){return this.disjunctiveFacets.indexOf(facet)>-1},isConjunctiveFacet:function(facet){return this.facets.indexOf(facet)>-1},isFacetRefined:function isFacetRefined(facet,value){return RefinementList.isRefined(this.facetsRefinements,facet,value)},isExcludeRefined:function isExcludeRefined(facet,value){return RefinementList.isRefined(this.facetsExcludes,facet,value)},isDisjunctiveFacetRefined:function isDisjunctiveFacetRefined(facet,value){return RefinementList.isRefined(this.disjunctiveFacetsRefinements,facet,value)},isNumericRefined:function isNumericRefined(attribute,operator,value){if(isUndefined(value)){return this.numericRefinements[attribute]&&!isUndefined(this.numericRefinements[attribute][operator])}return this.numericRefinements[attribute]&&!isUndefined(this.numericRefinements[attribute][operator])&&this.numericRefinements[attribute][operator]===value},isTagRefined:function isTagRefined(tag){return this.tagRefinements.indexOf(tag)!==-1},getRefinedDisjunctiveFacets:function getRefinedDisjunctiveFacets(){var disjunctiveNumericRefinedFacets=intersection(keys(this.numericRefinements),this.disjunctiveFacets);return keys(this.disjunctiveFacetsRefinements).concat(disjunctiveNumericRefinedFacets)},getUnrefinedDisjunctiveFacets:function(){var refinedFacets=this.getRefinedDisjunctiveFacets();return filter(this.disjunctiveFacets,function(f){return refinedFacets.indexOf(f)===-1})},managedParameters:["facets","disjunctiveFacets","facetsRefinements","facetsExcludes","disjunctiveFacetsRefinements","numericRefinements","tagRefinements"],getQueryParams:function getQueryParams(){var managedParameters=this.managedParameters;return reduce(this,function(memo,value,parameter,parameters){if(managedParameters.indexOf(parameter)===-1&&parameters[parameter]!==undefined){memo[parameter]=value}return memo},{})},getQueryParameter:function getQueryParameter(paramName){if(!this.hasOwnProperty(paramName))throw new Error("Parameter '"+paramName+"' is not an attribute of SearchParameters (http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html)");return this[paramName]},setQueryParameter:function setParameter(parameter,value){if(this[parameter]===value)return this;var modification={};modification[parameter]=value;return this.setQueryParameters(modification)},setQueryParameters:function setQueryParameters(params){var error=SearchParameters.validate(this,params);if(error){throw error}return this.mutateMe(function merge(newInstance){var ks=keys(params);forEach(ks,function(k){newInstance[k]=params[k]});return newInstance})},mutateMe:function mutateMe(fn){var newState=new this.constructor(this);fn(newState,this);return deepFreeze(newState)}};module.exports=SearchParameters},{"../functions/deepFreeze":123,"../functions/extend":124,"./RefinementList":119,"lodash/array/intersection":4,"lodash/collection/filter":7,"lodash/collection/forEach":9,"lodash/collection/reduce":10,"lodash/lang/isEmpty":101,"lodash/lang/isFunction":102,"lodash/lang/isString":105,"lodash/lang/isUndefined":107,"lodash/object/keys":109,"lodash/object/omit":111}],121:[function(require,module,exports){"use strict";var forEach=require("lodash/collection/forEach");var compact=require("lodash/array/compact");var sum=require("lodash/collection/sum");var find=require("lodash/collection/find");var extend=require("../functions/extend");function getIndices(obj){var indices={};forEach(obj,function(val,idx){indices[val]=idx});return indices}function assignFacetStats(dest,facetStats,key){if(facetStats&&facetStats[key]){dest.stats=facetStats[key]}}var SearchResults=function(state,algoliaResponse){var mainSubResponse=algoliaResponse.results[0];this.query=mainSubResponse.query;this.hits=mainSubResponse.hits;this.index=mainSubResponse.index;this.hitsPerPage=mainSubResponse.hitsPerPage;this.nbHits=mainSubResponse.nbHits;this.nbPages=mainSubResponse.nbPages;this.page=mainSubResponse.page;this.processingTimeMS=sum(algoliaResponse.results,"processingTimeMS");this.disjunctiveFacets=[];this.facets=[];var disjunctiveFacets=state.getRefinedDisjunctiveFacets();var facetsIndices=getIndices(state.facets);var disjunctiveFacetsIndices=getIndices(state.disjunctiveFacets);forEach(mainSubResponse.facets,function(facetValueObject,facetKey){var isFacetDisjunctive=state.disjunctiveFacets.indexOf(facetKey)!==-1;var position=isFacetDisjunctive?disjunctiveFacetsIndices[facetKey]:facetsIndices[facetKey];if(isFacetDisjunctive){this.disjunctiveFacets[position]={name:facetKey,data:facetValueObject,exhaustive:mainSubResponse.exhaustiveFacetsCount};assignFacetStats(this.disjunctiveFacets[position],mainSubResponse.facets_stats,facetKey)}else{this.facets[position]={name:facetKey,data:facetValueObject,exhaustive:mainSubResponse.exhaustiveFacetsCount};assignFacetStats(this.facets[position],mainSubResponse.facets_stats,facetKey)}},this);forEach(disjunctiveFacets,function(disjunctiveFacet,idx){var result=algoliaResponse.results[idx+1];forEach(result.facets,function(facetResults,dfacet){var position=disjunctiveFacetsIndices[dfacet];var dataFromMainRequest=mainSubResponse.facets&&mainSubResponse.facets[dfacet]||{};this.disjunctiveFacets[position]={name:dfacet,data:extend({},dataFromMainRequest,facetResults),exhaustive:result.exhaustiveFacetsCount};assignFacetStats(this.disjunctiveFacets[position],result.facets_stats,dfacet);if(state.disjunctiveFacetsRefinements[dfacet]){forEach(state.disjunctiveFacetsRefinements[dfacet],function(refinementValue){if(!this.disjunctiveFacets[position].data[refinementValue]&&state.disjunctiveFacetsRefinements[dfacet].indexOf(refinementValue)>-1){this.disjunctiveFacets[position].data[refinementValue]=0}},this)}},this)},this);forEach(state.facetsExcludes,function(excludes,facetName){var position=facetsIndices[facetName];this.facets[position]={name:facetName,data:mainSubResponse.facets[facetName],exhaustive:mainSubResponse.exhaustiveFacetsCount};forEach(excludes,function(facetValue){this.facets[position]=this.facets[position]||{name:facetName};this.facets[position].data=this.facets[position].data||{};this.facets[position].data[facetValue]=0},this)},this);this.facets=compact(this.facets);this.disjunctiveFacets=compact(this.disjunctiveFacets);this._state=state};SearchResults.prototype.getFacetByName=function(name){var isName=function(facet){return facet.name===name};var indexInFacets=find(this.facets,isName);return indexInFacets||find(this.disjunctiveFacets,isName)};module.exports=SearchResults},{"../functions/extend":124,"lodash/array/compact":3,"lodash/collection/find":8,"lodash/collection/forEach":9,"lodash/collection/sum":11}],122:[function(require,module,exports){"use strict";var SearchParameters=require("./SearchParameters");var SearchResults=require("./SearchResults");var extend=require("./functions/extend");var util=require("util");var events=require("events");var forEach=require("lodash/collection/forEach");var bind=require("lodash/function/bind");function AlgoliaSearchHelper(client,index,options){this.client=client;this.index=index;this.state=SearchParameters.make(options);this.lastResults=null;this._queryId=0;this._lastQueryIdReceived=-1}util.inherits(AlgoliaSearchHelper,events.EventEmitter);AlgoliaSearchHelper.prototype.search=function(){this._search();return this};AlgoliaSearchHelper.prototype.setQuery=function(q){this.state=this.state.setQuery(q);this._change();return this};AlgoliaSearchHelper.prototype.clearRefinements=function(name){this.state=this.state.clearRefinements(name);this._change();return this};AlgoliaSearchHelper.prototype.clearTags=function(){this.state=this.state.clearTags();this._change();return this};AlgoliaSearchHelper.prototype.addDisjunctiveRefine=function(facet,value){this.state=this.state.addDisjunctiveFacetRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.addNumericRefinement=function(attribute,operator,value){this.state=this.state.addNumericRefinement(attribute,operator,value);this._change();return this};AlgoliaSearchHelper.prototype.addRefine=function(facet,value){this.state=this.state.addFacetRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.addExclude=function(facet,value){this.state=this.state.addExcludeRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.addTag=function(tag){this.state=this.state.addTagRefinement(tag);this._change();return this};AlgoliaSearchHelper.prototype.removeNumericRefinement=function(attribute,operator,value){this.state=this.state.removeNumericRefinement(attribute,operator,value);this._change();return this};AlgoliaSearchHelper.prototype.removeDisjunctiveRefine=function(facet,value){this.state=this.state.removeDisjunctiveFacetRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.removeRefine=function(facet,value){this.state=this.state.removeFacetRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.removeExclude=function(facet,value){this.state=this.state.removeExcludeRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.removeTag=function(tag){this.state=this.state.removeTagRefinement(tag);this._change();return this};AlgoliaSearchHelper.prototype.toggleExclude=function(facet,value){this.state=this.state.toggleExcludeFacetRefinement(facet,value);this._change();return this};AlgoliaSearchHelper.prototype.toggleRefine=function(facet,value){if(this.state.isConjunctiveFacet(facet)){this.state=this.state.toggleFacetRefinement(facet,value)}else if(this.state.isDisjunctiveFacet(facet)){this.state=this.state.toggleDisjunctiveFacetRefinement(facet,value)}else{console.log("warning : you're trying to refine the undeclared facet '"+facet+"'; add it to the helper options 'facets' or 'disjunctiveFacets'");return this}this._change();return this};AlgoliaSearchHelper.prototype.toggleTag=function(tag){this.state=this.state.toggleTagRefinement(tag);this._change();return this};AlgoliaSearchHelper.prototype.nextPage=function(){return this.setCurrentPage(this.state.page+1)};AlgoliaSearchHelper.prototype.previousPage=function(){return this.setCurrentPage(this.state.page-1)};AlgoliaSearchHelper.prototype.setCurrentPage=function(page){if(page<0)throw new Error("Page requested below 0.");this.state=this.state.setPage(page);this._change();return this};AlgoliaSearchHelper.prototype.setIndex=function(name){this.index=name;this.setCurrentPage(0);return this};AlgoliaSearchHelper.prototype.setQueryParameter=function(parameter,value){var newState=this.state.setQueryParameter(parameter,value);if(this.state===newState)return this;this.state=newState;this._change();return this};AlgoliaSearchHelper.prototype.setState=function(newState){this.state=new SearchParameters(newState);this._change();return this};AlgoliaSearchHelper.prototype.overrideStateWithoutTriggeringChangeEvent=function(newState){this.state=new SearchParameters(newState);return this};AlgoliaSearchHelper.prototype.isRefined=function(facet,value){if(this.state.isConjunctiveFacet(facet)){return this.state.isFacetRefined(facet,value)}else if(this.state.isDisjunctiveFacet(facet)){return this.state.isDisjunctiveFacetRefined(facet,value)}return false};AlgoliaSearchHelper.prototype.hasRefinements=function(facet){return this.isRefined(facet)};AlgoliaSearchHelper.prototype.isExcluded=function(facet,value){return this.state.isExcludeRefined(facet,value)};AlgoliaSearchHelper.prototype.isDisjunctiveRefined=function(facet,value){return this.state.isDisjunctiveFacetRefined(facet,value)};AlgoliaSearchHelper.prototype.isTagRefined=function(tag){return this.state.isTagRefined(tag)};AlgoliaSearchHelper.prototype.getIndex=function(){return this.index};AlgoliaSearchHelper.prototype.getCurrentPage=function(){return this.state.page};AlgoliaSearchHelper.prototype.getTags=function(){return this.state.tagRefinements};AlgoliaSearchHelper.prototype.getQueryParameter=function(parameterName){return this.state.getQueryParameter(parameterName)};AlgoliaSearchHelper.prototype.getRefinements=function(facetName){var refinements=[];if(this.state.isConjunctiveFacet(facetName)){var conjRefinements=this.state.getConjunctiveRefinements(facetName);forEach(conjRefinements,function(r){refinements.push({value:r,type:"conjunctive"})})}else if(this.state.isDisjunctiveFacet(facetName)){var disjRefinements=this.state.getDisjunctiveRefinements(facetName);forEach(disjRefinements,function(r){refinements.push({value:r,type:"disjunctive"})})}var excludeRefinements=this.state.getExcludeRefinements(facetName);forEach(excludeRefinements,function(r){refinements.push({value:r,type:"exclude"})});var numericRefinements=this.state.getNumericRefinements(facetName);forEach(numericRefinements,function(value,operator){refinements.push({value:value,operator:operator,type:"numeric"})});return refinements};AlgoliaSearchHelper.prototype._search=function(){var state=this.state;var queries=[];queries.push({indexName:this.index,query:state.query,params:this._getHitsSearchParams()});forEach(state.getRefinedDisjunctiveFacets(),function(refinedFacet){queries.push({indexName:this.index,query:state.query,params:this._getDisjunctiveFacetSearchParams(refinedFacet)})},this);this.client.search(queries,bind(this._handleResponse,this,state,this._queryId++))};AlgoliaSearchHelper.prototype._handleResponse=function(state,queryId,err,content){if(queryId<this._lastQueryIdReceived){return}this._lastQueryIdReceived=queryId;if(err){this.emit("error",err);return}var formattedResponse=this.lastResults=new SearchResults(state,content);this.emit("result",formattedResponse,state)};AlgoliaSearchHelper.prototype._getHitsSearchParams=function(){var query=this.state.query;var facets=this.state.facets.concat(this.state.disjunctiveFacets);var facetFilters=this._getFacetFilters();var numericFilters=this._getNumericFilters();var tagFilters=this._getTagFilters();var additionalParams={facets:facets,tagFilters:tagFilters,distinct:this.state.distinct};if(!this.containsRefinement(query,facetFilters,numericFilters,tagFilters)){additionalParams.distinct=false}if(facetFilters.length>0){additionalParams.facetFilters=facetFilters}if(numericFilters.length>0){additionalParams.numericFilters=numericFilters}return extend(this.state.getQueryParams(),additionalParams)};AlgoliaSearchHelper.prototype._getDisjunctiveFacetSearchParams=function(facet){var query=this.state.query;var facetFilters=this._getFacetFilters(facet);var numericFilters=this._getNumericFilters(facet);var tagFilters=this._getTagFilters();var additionalParams={hitsPerPage:1,page:0,attributesToRetrieve:[],attributesToHighlight:[],attributesToSnippet:[],facets:facet,tagFilters:tagFilters,distinct:this.state.distinct};if(!this.containsRefinement(query,facetFilters,numericFilters,tagFilters)){additionalParams.distinct=false}if(numericFilters.length>0){additionalParams.numericFilters=numericFilters}if(facetFilters.length>0){additionalParams.facetFilters=facetFilters}return extend(this.state.getQueryParams(),additionalParams)};AlgoliaSearchHelper.prototype.containsRefinement=function(query,facetFilters,numericFilters,tagFilters){return query||facetFilters.length!==0||numericFilters.length!==0||tagFilters.length!==0};AlgoliaSearchHelper.prototype._getNumericFilters=function(facetName){var numericFilters=[];forEach(this.state.numericRefinements,function(operators,attribute){forEach(operators,function(value,operator){if(facetName!==attribute){numericFilters.push(attribute+operator+value)}})});return numericFilters};AlgoliaSearchHelper.prototype._getTagFilters=function(){if(this.state.tagFilters){return this.state.tagFilters}return this.state.tagRefinements.join(",")};AlgoliaSearchHelper.prototype._hasDisjunctiveRefinements=function(facet){return this.state.disjunctiveRefinements[facet]&&this.state.disjunctiveRefinements[facet].length>0};AlgoliaSearchHelper.prototype._getFacetFilters=function(facet){var facetFilters=[];forEach(this.state.facetsRefinements,function(facetValues,facetName){forEach(facetValues,function(facetValue){facetFilters.push(facetName+":"+facetValue)})});forEach(this.state.facetsExcludes,function(facetValues,facetName){forEach(facetValues,function(facetValue){facetFilters.push(facetName+":-"+facetValue)})});forEach(this.state.disjunctiveFacetsRefinements,function(facetValues,facetName){if(facetName===facet||!facetValues||facetValues.length===0)return;var orFilters=[];forEach(facetValues,function(facetValue){orFilters.push(facetName+":"+facetValue)});facetFilters.push(orFilters)});return facetFilters};AlgoliaSearchHelper.prototype._change=function(){this.emit("change",this.state,this.lastResults)};module.exports=AlgoliaSearchHelper},{"./SearchParameters":120,"./SearchResults":121,"./functions/extend":124,events:192,"lodash/collection/forEach":9,"lodash/function/bind":13,util:199}],123:[function(require,module,exports){"use strict";var isObject=require("lodash/lang/isObject");var forEach=require("lodash/collection/forEach");var deepFreeze=function(obj){if(!isObject(obj))return obj;forEach(obj,deepFreeze);if(!Object.isFrozen(obj)){Object.freeze(obj)}return obj};module.exports=deepFreeze},{"lodash/collection/forEach":9,"lodash/lang/isObject":104}],124:[function(require,module,exports){"use strict";module.exports=function extend(out){out=out||{};for(var i=1;i<arguments.length;i++){if(!arguments[i]){continue}for(var key in arguments[i]){if(arguments[i].hasOwnProperty(key)){out[key]=arguments[i][key]}}}return out}},{}],125:[function(require,module,exports){exports=module.exports=require("./debug");exports.log=log;exports.formatArgs=formatArgs;exports.save=save;exports.load=load;exports.useColors=useColors;exports.storage="undefined"!=typeof chrome&&"undefined"!=typeof chrome.storage?chrome.storage.local:localstorage();exports.colors=["lightseagreen","forestgreen","goldenrod","dodgerblue","darkorchid","crimson"];function useColors(){return"WebkitAppearance"in document.documentElement.style||window.console&&(console.firebug||console.exception&&console.table)||navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/)&&parseInt(RegExp.$1,10)>=31}exports.formatters.j=function(v){return JSON.stringify(v)};function formatArgs(){var args=arguments;var useColors=this.useColors;args[0]=(useColors?"%c":"")+this.namespace+(useColors?" %c":" ")+args[0]+(useColors?"%c ":" ")+"+"+exports.humanize(this.diff);if(!useColors)return args;var c="color: "+this.color;args=[args[0],c,"color: inherit"].concat(Array.prototype.slice.call(args,1));var index=0;var lastC=0;args[0].replace(/%[a-z%]/g,function(match){if("%%"===match)return;index++;if("%c"===match){lastC=index}});args.splice(lastC,0,c);return args}function log(){return"object"===typeof console&&console.log&&Function.prototype.apply.call(console.log,console,arguments)}function save(namespaces){try{if(null==namespaces){exports.storage.removeItem("debug")}else{exports.storage.debug=namespaces}}catch(e){}}function load(){var r;try{r=exports.storage.debug}catch(e){}return r}exports.enable(load());function localstorage(){try{return window.localStorage}catch(e){}}},{"./debug":126}],126:[function(require,module,exports){exports=module.exports=debug;exports.coerce=coerce;exports.disable=disable;exports.enable=enable;exports.enabled=enabled;exports.humanize=require("ms");exports.names=[];exports.skips=[];exports.formatters={};var prevColor=0;var prevTime;function selectColor(){return exports.colors[prevColor++%exports.colors.length]}function debug(namespace){function disabled(){}disabled.enabled=false;function enabled(){var self=enabled;var curr=+new Date;var ms=curr-(prevTime||curr);self.diff=ms;self.prev=prevTime;self.curr=curr;prevTime=curr;if(null==self.useColors)self.useColors=exports.useColors();if(null==self.color&&self.useColors)self.color=selectColor();var args=Array.prototype.slice.call(arguments);args[0]=exports.coerce(args[0]);if("string"!==typeof args[0]){args=["%o"].concat(args)}var index=0;args[0]=args[0].replace(/%([a-z%])/g,function(match,format){if(match==="%%")return match;index++;var formatter=exports.formatters[format];if("function"===typeof formatter){var val=args[index];match=formatter.call(self,val);args.splice(index,1);index--}return match});if("function"===typeof exports.formatArgs){args=exports.formatArgs.apply(self,args)}var logFn=enabled.log||exports.log||console.log.bind(console);logFn.apply(self,args)}enabled.enabled=true;var fn=exports.enabled(namespace)?enabled:disabled;fn.namespace=namespace;return fn}function enable(namespaces){exports.save(namespaces);var split=(namespaces||"").split(/[\s,]+/);var len=split.length;for(var i=0;i<len;i++){if(!split[i])continue;namespaces=split[i].replace(/\*/g,".*?");if(namespaces[0]==="-"){exports.skips.push(new RegExp("^"+namespaces.substr(1)+"$"))}else{exports.names.push(new RegExp("^"+namespaces+"$"))}}}function disable(){exports.enable("")}function enabled(name){var i,len;for(i=0,len=exports.skips.length;i<len;i++){if(exports.skips[i].test(name)){return false}}for(i=0,len=exports.names.length;i<len;i++){if(exports.names[i].test(name)){return true}}return false}function coerce(val){if(val instanceof Error)return val.stack||val.message;return val}},{ms:127}],127:[function(require,module,exports){var s=1e3;var m=s*60;var h=m*60;var d=h*24;var y=d*365.25;module.exports=function(val,options){options=options||{};if("string"==typeof val)return parse(val);return options["long"]?_long(val):_short(val)};function parse(str){str=""+str;if(str.length>1e4)return;var match=/^((?:\d+)?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|years?|yrs?|y)?$/i.exec(str);if(!match)return;var n=parseFloat(match[1]);var type=(match[2]||"ms").toLowerCase();switch(type){case"years":case"year":case"yrs":case"yr":case"y":return n*y;case"days":case"day":case"d":return n*d;case"hours":case"hour":case"hrs":case"hr":case"h":return n*h;case"minutes":case"minute":case"mins":case"min":case"m":return n*m;case"seconds":case"second":case"secs":case"sec":case"s":return n*s;case"milliseconds":case"millisecond":case"msecs":case"msec":case"ms":return n}}function _short(ms){if(ms>=d)return Math.round(ms/d)+"d";if(ms>=h)return Math.round(ms/h)+"h";if(ms>=m)return Math.round(ms/m)+"m";if(ms>=s)return Math.round(ms/s)+"s";return ms+"ms"}function _long(ms){return plural(ms,d,"day")||plural(ms,h,"hour")||plural(ms,m,"minute")||plural(ms,s,"second")||ms+" ms"}function plural(ms,n,name){if(ms<n)return;if(ms<n*1.5)return Math.floor(ms/n)+" "+name;return Math.ceil(ms/n)+" "+name+"s"}},{}],128:[function(require,module,exports){(function(process,global){(function(){"use strict";function lib$es6$promise$utils$$objectOrFunction(x){return typeof x==="function"||typeof x==="object"&&x!==null}function lib$es6$promise$utils$$isFunction(x){return typeof x==="function"}function lib$es6$promise$utils$$isMaybeThenable(x){return typeof x==="object"&&x!==null}var lib$es6$promise$utils$$_isArray;if(!Array.isArray){lib$es6$promise$utils$$_isArray=function(x){return Object.prototype.toString.call(x)==="[object Array]"}}else{lib$es6$promise$utils$$_isArray=Array.isArray}var lib$es6$promise$utils$$isArray=lib$es6$promise$utils$$_isArray;var lib$es6$promise$asap$$len=0;var lib$es6$promise$asap$$toString={}.toString;var lib$es6$promise$asap$$vertxNext;function lib$es6$promise$asap$$asap(callback,arg){lib$es6$promise$asap$$queue[lib$es6$promise$asap$$len]=callback;lib$es6$promise$asap$$queue[lib$es6$promise$asap$$len+1]=arg;lib$es6$promise$asap$$len+=2;if(lib$es6$promise$asap$$len===2){lib$es6$promise$asap$$scheduleFlush()}}var lib$es6$promise$asap$$default=lib$es6$promise$asap$$asap;var lib$es6$promise$asap$$browserWindow=typeof window!=="undefined"?window:undefined;var lib$es6$promise$asap$$browserGlobal=lib$es6$promise$asap$$browserWindow||{};var lib$es6$promise$asap$$BrowserMutationObserver=lib$es6$promise$asap$$browserGlobal.MutationObserver||lib$es6$promise$asap$$browserGlobal.WebKitMutationObserver;var lib$es6$promise$asap$$isNode=typeof process!=="undefined"&&{}.toString.call(process)==="[object process]";var lib$es6$promise$asap$$isWorker=typeof Uint8ClampedArray!=="undefined"&&typeof importScripts!=="undefined"&&typeof MessageChannel!=="undefined";function lib$es6$promise$asap$$useNextTick(){var nextTick=process.nextTick;var version=process.versions.node.match(/^(?:(\d+)\.)?(?:(\d+)\.)?(\*|\d+)$/);if(Array.isArray(version)&&version[1]==="0"&&version[2]==="10"){nextTick=setImmediate}return function(){nextTick(lib$es6$promise$asap$$flush)}}function lib$es6$promise$asap$$useVertxTimer(){return function(){lib$es6$promise$asap$$vertxNext(lib$es6$promise$asap$$flush)}}function lib$es6$promise$asap$$useMutationObserver(){var iterations=0;var observer=new lib$es6$promise$asap$$BrowserMutationObserver(lib$es6$promise$asap$$flush);var node=document.createTextNode("");observer.observe(node,{characterData:true});return function(){node.data=iterations=++iterations%2}}function lib$es6$promise$asap$$useMessageChannel(){var channel=new MessageChannel;channel.port1.onmessage=lib$es6$promise$asap$$flush;return function(){channel.port2.postMessage(0)}}function lib$es6$promise$asap$$useSetTimeout(){return function(){setTimeout(lib$es6$promise$asap$$flush,1)}}var lib$es6$promise$asap$$queue=new Array(1e3);function lib$es6$promise$asap$$flush(){for(var i=0;i<lib$es6$promise$asap$$len;i+=2){var callback=lib$es6$promise$asap$$queue[i];var arg=lib$es6$promise$asap$$queue[i+1];callback(arg);lib$es6$promise$asap$$queue[i]=undefined;lib$es6$promise$asap$$queue[i+1]=undefined}lib$es6$promise$asap$$len=0}function lib$es6$promise$asap$$attemptVertex(){try{var r=require;var vertx=r("vertx");lib$es6$promise$asap$$vertxNext=vertx.runOnLoop||vertx.runOnContext;return lib$es6$promise$asap$$useVertxTimer()}catch(e){return lib$es6$promise$asap$$useSetTimeout()}}var lib$es6$promise$asap$$scheduleFlush;if(lib$es6$promise$asap$$isNode){lib$es6$promise$asap$$scheduleFlush=lib$es6$promise$asap$$useNextTick()}else if(lib$es6$promise$asap$$BrowserMutationObserver){lib$es6$promise$asap$$scheduleFlush=lib$es6$promise$asap$$useMutationObserver();
 
 
 
 
 
 
 
6
 
7
- }else if(lib$es6$promise$asap$$isWorker){lib$es6$promise$asap$$scheduleFlush=lib$es6$promise$asap$$useMessageChannel()}else if(lib$es6$promise$asap$$browserWindow===undefined&&typeof require==="function"){lib$es6$promise$asap$$scheduleFlush=lib$es6$promise$asap$$attemptVertex()}else{lib$es6$promise$asap$$scheduleFlush=lib$es6$promise$asap$$useSetTimeout()}function lib$es6$promise$$internal$$noop(){}var lib$es6$promise$$internal$$PENDING=void 0;var lib$es6$promise$$internal$$FULFILLED=1;var lib$es6$promise$$internal$$REJECTED=2;var lib$es6$promise$$internal$$GET_THEN_ERROR=new lib$es6$promise$$internal$$ErrorObject;function lib$es6$promise$$internal$$selfFullfillment(){return new TypeError("You cannot resolve a promise with itself")}function lib$es6$promise$$internal$$cannotReturnOwn(){return new TypeError("A promises callback cannot return that same promise.")}function lib$es6$promise$$internal$$getThen(promise){try{return promise.then}catch(error){lib$es6$promise$$internal$$GET_THEN_ERROR.error=error;return lib$es6$promise$$internal$$GET_THEN_ERROR}}function lib$es6$promise$$internal$$tryThen(then,value,fulfillmentHandler,rejectionHandler){try{then.call(value,fulfillmentHandler,rejectionHandler)}catch(e){return e}}function lib$es6$promise$$internal$$handleForeignThenable(promise,thenable,then){lib$es6$promise$asap$$default(function(promise){var sealed=false;var error=lib$es6$promise$$internal$$tryThen(then,thenable,function(value){if(sealed){return}sealed=true;if(thenable!==value){lib$es6$promise$$internal$$resolve(promise,value)}else{lib$es6$promise$$internal$$fulfill(promise,value)}},function(reason){if(sealed){return}sealed=true;lib$es6$promise$$internal$$reject(promise,reason)},"Settle: "+(promise._label||" unknown promise"));if(!sealed&&error){sealed=true;lib$es6$promise$$internal$$reject(promise,error)}},promise)}function lib$es6$promise$$internal$$handleOwnThenable(promise,thenable){if(thenable._state===lib$es6$promise$$internal$$FULFILLED){lib$es6$promise$$internal$$fulfill(promise,thenable._result)}else if(thenable._state===lib$es6$promise$$internal$$REJECTED){lib$es6$promise$$internal$$reject(promise,thenable._result)}else{lib$es6$promise$$internal$$subscribe(thenable,undefined,function(value){lib$es6$promise$$internal$$resolve(promise,value)},function(reason){lib$es6$promise$$internal$$reject(promise,reason)})}}function lib$es6$promise$$internal$$handleMaybeThenable(promise,maybeThenable){if(maybeThenable.constructor===promise.constructor){lib$es6$promise$$internal$$handleOwnThenable(promise,maybeThenable)}else{var then=lib$es6$promise$$internal$$getThen(maybeThenable);if(then===lib$es6$promise$$internal$$GET_THEN_ERROR){lib$es6$promise$$internal$$reject(promise,lib$es6$promise$$internal$$GET_THEN_ERROR.error)}else if(then===undefined){lib$es6$promise$$internal$$fulfill(promise,maybeThenable)}else if(lib$es6$promise$utils$$isFunction(then)){lib$es6$promise$$internal$$handleForeignThenable(promise,maybeThenable,then)}else{lib$es6$promise$$internal$$fulfill(promise,maybeThenable)}}}function lib$es6$promise$$internal$$resolve(promise,value){if(promise===value){lib$es6$promise$$internal$$reject(promise,lib$es6$promise$$internal$$selfFullfillment())}else if(lib$es6$promise$utils$$objectOrFunction(value)){lib$es6$promise$$internal$$handleMaybeThenable(promise,value)}else{lib$es6$promise$$internal$$fulfill(promise,value)}}function lib$es6$promise$$internal$$publishRejection(promise){if(promise._onerror){promise._onerror(promise._result)}lib$es6$promise$$internal$$publish(promise)}function lib$es6$promise$$internal$$fulfill(promise,value){if(promise._state!==lib$es6$promise$$internal$$PENDING){return}promise._result=value;promise._state=lib$es6$promise$$internal$$FULFILLED;if(promise._subscribers.length!==0){lib$es6$promise$asap$$default(lib$es6$promise$$internal$$publish,promise)}}function lib$es6$promise$$internal$$reject(promise,reason){if(promise._state!==lib$es6$promise$$internal$$PENDING){return}promise._state=lib$es6$promise$$internal$$REJECTED;promise._result=reason;lib$es6$promise$asap$$default(lib$es6$promise$$internal$$publishRejection,promise)}function lib$es6$promise$$internal$$subscribe(parent,child,onFulfillment,onRejection){var subscribers=parent._subscribers;var length=subscribers.length;parent._onerror=null;subscribers[length]=child;subscribers[length+lib$es6$promise$$internal$$FULFILLED]=onFulfillment;subscribers[length+lib$es6$promise$$internal$$REJECTED]=onRejection;if(length===0&&parent._state){lib$es6$promise$asap$$default(lib$es6$promise$$internal$$publish,parent)}}function lib$es6$promise$$internal$$publish(promise){var subscribers=promise._subscribers;var settled=promise._state;if(subscribers.length===0){return}var child,callback,detail=promise._result;for(var i=0;i<subscribers.length;i+=3){child=subscribers[i];callback=subscribers[i+settled];if(child){lib$es6$promise$$internal$$invokeCallback(settled,child,callback,detail)}else{callback(detail)}}promise._subscribers.length=0}function lib$es6$promise$$internal$$ErrorObject(){this.error=null}var lib$es6$promise$$internal$$TRY_CATCH_ERROR=new lib$es6$promise$$internal$$ErrorObject;function lib$es6$promise$$internal$$tryCatch(callback,detail){try{return callback(detail)}catch(e){lib$es6$promise$$internal$$TRY_CATCH_ERROR.error=e;return lib$es6$promise$$internal$$TRY_CATCH_ERROR}}function lib$es6$promise$$internal$$invokeCallback(settled,promise,callback,detail){var hasCallback=lib$es6$promise$utils$$isFunction(callback),value,error,succeeded,failed;if(hasCallback){value=lib$es6$promise$$internal$$tryCatch(callback,detail);if(value===lib$es6$promise$$internal$$TRY_CATCH_ERROR){failed=true;error=value.error;value=null}else{succeeded=true}if(promise===value){lib$es6$promise$$internal$$reject(promise,lib$es6$promise$$internal$$cannotReturnOwn());return}}else{value=detail;succeeded=true}if(promise._state!==lib$es6$promise$$internal$$PENDING){}else if(hasCallback&&succeeded){lib$es6$promise$$internal$$resolve(promise,value)}else if(failed){lib$es6$promise$$internal$$reject(promise,error)}else if(settled===lib$es6$promise$$internal$$FULFILLED){lib$es6$promise$$internal$$fulfill(promise,value)}else if(settled===lib$es6$promise$$internal$$REJECTED){lib$es6$promise$$internal$$reject(promise,value)}}function lib$es6$promise$$internal$$initializePromise(promise,resolver){try{resolver(function resolvePromise(value){lib$es6$promise$$internal$$resolve(promise,value)},function rejectPromise(reason){lib$es6$promise$$internal$$reject(promise,reason)})}catch(e){lib$es6$promise$$internal$$reject(promise,e)}}function lib$es6$promise$enumerator$$Enumerator(Constructor,input){var enumerator=this;enumerator._instanceConstructor=Constructor;enumerator.promise=new Constructor(lib$es6$promise$$internal$$noop);if(enumerator._validateInput(input)){enumerator._input=input;enumerator.length=input.length;enumerator._remaining=input.length;enumerator._init();if(enumerator.length===0){lib$es6$promise$$internal$$fulfill(enumerator.promise,enumerator._result)}else{enumerator.length=enumerator.length||0;enumerator._enumerate();if(enumerator._remaining===0){lib$es6$promise$$internal$$fulfill(enumerator.promise,enumerator._result)}}}else{lib$es6$promise$$internal$$reject(enumerator.promise,enumerator._validationError())}}lib$es6$promise$enumerator$$Enumerator.prototype._validateInput=function(input){return lib$es6$promise$utils$$isArray(input)};lib$es6$promise$enumerator$$Enumerator.prototype._validationError=function(){return new Error("Array Methods must be provided an Array")};lib$es6$promise$enumerator$$Enumerator.prototype._init=function(){this._result=new Array(this.length)};var lib$es6$promise$enumerator$$default=lib$es6$promise$enumerator$$Enumerator;lib$es6$promise$enumerator$$Enumerator.prototype._enumerate=function(){var enumerator=this;var length=enumerator.length;var promise=enumerator.promise;var input=enumerator._input;for(var i=0;promise._state===lib$es6$promise$$internal$$PENDING&&i<length;i++){enumerator._eachEntry(input[i],i)}};lib$es6$promise$enumerator$$Enumerator.prototype._eachEntry=function(entry,i){var enumerator=this;var c=enumerator._instanceConstructor;if(lib$es6$promise$utils$$isMaybeThenable(entry)){if(entry.constructor===c&&entry._state!==lib$es6$promise$$internal$$PENDING){entry._onerror=null;enumerator._settledAt(entry._state,i,entry._result)}else{enumerator._willSettleAt(c.resolve(entry),i)}}else{enumerator._remaining--;enumerator._result[i]=entry}};lib$es6$promise$enumerator$$Enumerator.prototype._settledAt=function(state,i,value){var enumerator=this;var promise=enumerator.promise;if(promise._state===lib$es6$promise$$internal$$PENDING){enumerator._remaining--;if(state===lib$es6$promise$$internal$$REJECTED){lib$es6$promise$$internal$$reject(promise,value)}else{enumerator._result[i]=value}}if(enumerator._remaining===0){lib$es6$promise$$internal$$fulfill(promise,enumerator._result)}};lib$es6$promise$enumerator$$Enumerator.prototype._willSettleAt=function(promise,i){var enumerator=this;lib$es6$promise$$internal$$subscribe(promise,undefined,function(value){enumerator._settledAt(lib$es6$promise$$internal$$FULFILLED,i,value)},function(reason){enumerator._settledAt(lib$es6$promise$$internal$$REJECTED,i,reason)})};function lib$es6$promise$promise$all$$all(entries){return new lib$es6$promise$enumerator$$default(this,entries).promise}var lib$es6$promise$promise$all$$default=lib$es6$promise$promise$all$$all;function lib$es6$promise$promise$race$$race(entries){var Constructor=this;var promise=new Constructor(lib$es6$promise$$internal$$noop);if(!lib$es6$promise$utils$$isArray(entries)){lib$es6$promise$$internal$$reject(promise,new TypeError("You must pass an array to race."));return promise}var length=entries.length;function onFulfillment(value){lib$es6$promise$$internal$$resolve(promise,value)}function onRejection(reason){lib$es6$promise$$internal$$reject(promise,reason)}for(var i=0;promise._state===lib$es6$promise$$internal$$PENDING&&i<length;i++){lib$es6$promise$$internal$$subscribe(Constructor.resolve(entries[i]),undefined,onFulfillment,onRejection)}return promise}var lib$es6$promise$promise$race$$default=lib$es6$promise$promise$race$$race;function lib$es6$promise$promise$resolve$$resolve(object){var Constructor=this;if(object&&typeof object==="object"&&object.constructor===Constructor){return object}var promise=new Constructor(lib$es6$promise$$internal$$noop);lib$es6$promise$$internal$$resolve(promise,object);return promise}var lib$es6$promise$promise$resolve$$default=lib$es6$promise$promise$resolve$$resolve;function lib$es6$promise$promise$reject$$reject(reason){var Constructor=this;var promise=new Constructor(lib$es6$promise$$internal$$noop);lib$es6$promise$$internal$$reject(promise,reason);return promise}var lib$es6$promise$promise$reject$$default=lib$es6$promise$promise$reject$$reject;var lib$es6$promise$promise$$counter=0;function lib$es6$promise$promise$$needsResolver(){throw new TypeError("You must pass a resolver function as the first argument to the promise constructor")}function lib$es6$promise$promise$$needsNew(){throw new TypeError("Failed to construct 'Promise': Please use the 'new' operator, this object constructor cannot be called as a function.")}var lib$es6$promise$promise$$default=lib$es6$promise$promise$$Promise;function lib$es6$promise$promise$$Promise(resolver){this._id=lib$es6$promise$promise$$counter++;this._state=undefined;this._result=undefined;this._subscribers=[];if(lib$es6$promise$$internal$$noop!==resolver){if(!lib$es6$promise$utils$$isFunction(resolver)){lib$es6$promise$promise$$needsResolver()}if(!(this instanceof lib$es6$promise$promise$$Promise)){lib$es6$promise$promise$$needsNew()}lib$es6$promise$$internal$$initializePromise(this,resolver)}}lib$es6$promise$promise$$Promise.all=lib$es6$promise$promise$all$$default;lib$es6$promise$promise$$Promise.race=lib$es6$promise$promise$race$$default;lib$es6$promise$promise$$Promise.resolve=lib$es6$promise$promise$resolve$$default;lib$es6$promise$promise$$Promise.reject=lib$es6$promise$promise$reject$$default;lib$es6$promise$promise$$Promise.prototype={constructor:lib$es6$promise$promise$$Promise,then:function(onFulfillment,onRejection){var parent=this;var state=parent._state;if(state===lib$es6$promise$$internal$$FULFILLED&&!onFulfillment||state===lib$es6$promise$$internal$$REJECTED&&!onRejection){return this}var child=new this.constructor(lib$es6$promise$$internal$$noop);var result=parent._result;if(state){var callback=arguments[state-1];lib$es6$promise$asap$$default(function(){lib$es6$promise$$internal$$invokeCallback(state,child,callback,result)})}else{lib$es6$promise$$internal$$subscribe(parent,child,onFulfillment,onRejection)}return child},"catch":function(onRejection){return this.then(null,onRejection)}};function lib$es6$promise$polyfill$$polyfill(){var local;if(typeof global!=="undefined"){local=global}else if(typeof self!=="undefined"){local=self}else{try{local=Function("return this")()}catch(e){throw new Error("polyfill failed because global object is unavailable in this environment")}}var P=local.Promise;if(P&&Object.prototype.toString.call(P.resolve())==="[object Promise]"&&!P.cast){return}local.Promise=lib$es6$promise$promise$$default}var lib$es6$promise$polyfill$$default=lib$es6$promise$polyfill$$polyfill;var lib$es6$promise$umd$$ES6Promise={Promise:lib$es6$promise$promise$$default,polyfill:lib$es6$promise$polyfill$$default};if(typeof define==="function"&&define["amd"]){define(function(){return lib$es6$promise$umd$$ES6Promise})}else if(typeof module!=="undefined"&&module["exports"]){module["exports"]=lib$es6$promise$umd$$ES6Promise}else if(typeof this!=="undefined"){this["ES6Promise"]=lib$es6$promise$umd$$ES6Promise}lib$es6$promise$polyfill$$default()}).call(this)}).call(this,require("_process"),typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{_process:194}],129:[function(require,module,exports){if(typeof Object.create==="function"){module.exports=function inherits(ctor,superCtor){ctor.super_=superCtor;ctor.prototype=Object.create(superCtor.prototype,{constructor:{value:ctor,enumerable:false,writable:true,configurable:true}})}}else{module.exports=function inherits(ctor,superCtor){ctor.super_=superCtor;var TempCtor=function(){};TempCtor.prototype=superCtor.prototype;ctor.prototype=new TempCtor;ctor.prototype.constructor=ctor}}},{}],130:[function(require,module,exports){arguments[4][9][0].apply(exports,arguments)},{"../internal/arrayEach":133,"../internal/baseEach":137,"../internal/createForEach":151,dup:9}],131:[function(require,module,exports){arguments[4][14][0].apply(exports,arguments)},{dup:14}],132:[function(require,module,exports){arguments[4][18][0].apply(exports,arguments)},{dup:18}],133:[function(require,module,exports){arguments[4][19][0].apply(exports,arguments)},{dup:19}],134:[function(require,module,exports){var baseCopy=require("./baseCopy"),keys=require("../object/keys");function baseAssign(object,source){return source==null?object:baseCopy(source,keys(source),object)}module.exports=baseAssign},{"../object/keys":177,"./baseCopy":136}],135:[function(require,module,exports){var arrayCopy=require("./arrayCopy"),arrayEach=require("./arrayEach"),baseAssign=require("./baseAssign"),baseForOwn=require("./baseForOwn"),initCloneArray=require("./initCloneArray"),initCloneByTag=require("./initCloneByTag"),initCloneObject=require("./initCloneObject"),isArray=require("../lang/isArray"),isHostObject=require("./isHostObject"),isObject=require("../lang/isObject");var argsTag="[object Arguments]",arrayTag="[object Array]",boolTag="[object Boolean]",dateTag="[object Date]",errorTag="[object Error]",funcTag="[object Function]",mapTag="[object Map]",numberTag="[object Number]",objectTag="[object Object]",regexpTag="[object RegExp]",setTag="[object Set]",stringTag="[object String]",weakMapTag="[object WeakMap]";var arrayBufferTag="[object ArrayBuffer]",float32Tag="[object Float32Array]",float64Tag="[object Float64Array]",int8Tag="[object Int8Array]",int16Tag="[object Int16Array]",int32Tag="[object Int32Array]",uint8Tag="[object Uint8Array]",uint8ClampedTag="[object Uint8ClampedArray]",uint16Tag="[object Uint16Array]",uint32Tag="[object Uint32Array]";var cloneableTags={};cloneableTags[argsTag]=cloneableTags[arrayTag]=cloneableTags[arrayBufferTag]=cloneableTags[boolTag]=cloneableTags[dateTag]=cloneableTags[float32Tag]=cloneableTags[float64Tag]=cloneableTags[int8Tag]=cloneableTags[int16Tag]=cloneableTags[int32Tag]=cloneableTags[numberTag]=cloneableTags[objectTag]=cloneableTags[regexpTag]=cloneableTags[stringTag]=cloneableTags[uint8Tag]=cloneableTags[uint8ClampedTag]=cloneableTags[uint16Tag]=cloneableTags[uint32Tag]=true;cloneableTags[errorTag]=cloneableTags[funcTag]=cloneableTags[mapTag]=cloneableTags[setTag]=cloneableTags[weakMapTag]=false;var objectProto=Object.prototype;var objToString=objectProto.toString;function baseClone(value,isDeep,customizer,key,object,stackA,stackB){var result;if(customizer){result=object?customizer(value,key,object):customizer(value)}if(result!==undefined){return result}if(!isObject(value)){return value}var isArr=isArray(value);if(isArr){result=initCloneArray(value);if(!isDeep){return arrayCopy(value,result)}}else{var tag=objToString.call(value),isFunc=tag==funcTag;if(tag==objectTag||tag==argsTag||isFunc&&!object){if(isHostObject(value)){return object?value:{}}result=initCloneObject(isFunc?{}:value);if(!isDeep){return baseAssign(result,value)}}else{return cloneableTags[tag]?initCloneByTag(value,tag,isDeep):object?value:{}}}stackA||(stackA=[]);stackB||(stackB=[]);var length=stackA.length;while(length--){if(stackA[length]==value){return stackB[length]}}stackA.push(value);stackB.push(result);(isArr?arrayEach:baseForOwn)(value,function(subValue,key){result[key]=baseClone(subValue,isDeep,customizer,key,value,stackA,stackB)});return result}module.exports=baseClone},{"../lang/isArray":169,"../lang/isObject":172,"./arrayCopy":132,"./arrayEach":133,"./baseAssign":134,"./baseForOwn":140,"./initCloneArray":154,"./initCloneByTag":155,"./initCloneObject":156,"./isHostObject":158}],136:[function(require,module,exports){function baseCopy(source,props,object){object||(object={});var index=-1,length=props.length;while(++index<length){var key=props[index];object[key]=source[key]}return object}module.exports=baseCopy},{}],137:[function(require,module,exports){arguments[4][28][0].apply(exports,arguments)},{"./baseForOwn":140,"./createBaseEach":149,dup:28}],138:[function(require,module,exports){arguments[4][33][0].apply(exports,arguments)},{"./createBaseFor":150,dup:33}],139:[function(require,module,exports){arguments[4][34][0].apply(exports,arguments)},{"../object/keysIn":178,"./baseFor":138,dup:34}],140:[function(require,module,exports){arguments[4][35][0].apply(exports,arguments)},{"../object/keys":177,"./baseFor":138,dup:35}],141:[function(require,module,exports){arguments[4][40][0].apply(exports,arguments)},{dup:40}],142:[function(require,module,exports){var arrayEach=require("./arrayEach"),baseMergeDeep=require("./baseMergeDeep"),isArray=require("../lang/isArray"),isArrayLike=require("./isArrayLike"),isObject=require("../lang/isObject"),isObjectLike=require("./isObjectLike"),isTypedArray=require("../lang/isTypedArray"),keys=require("../object/keys");function baseMerge(object,source,customizer,stackA,stackB){if(!isObject(object)){return object}var isSrcArr=isArrayLike(source)&&(isArray(source)||isTypedArray(source)),props=isSrcArr?null:keys(source);arrayEach(props||source,function(srcValue,key){if(props){key=srcValue;srcValue=source[key]}if(isObjectLike(srcValue)){stackA||(stackA=[]);stackB||(stackB=[]);baseMergeDeep(object,source,key,baseMerge,customizer,stackA,stackB)}else{var value=object[key],result=customizer?customizer(value,srcValue,key,object,source):undefined,isCommon=result===undefined;if(isCommon){result=srcValue}if((result!==undefined||isSrcArr&&!(key in object))&&(isCommon||(result===result?result!==value:value===value))){object[key]=result}}});return object}module.exports=baseMerge},{"../lang/isArray":169,"../lang/isObject":172,"../lang/isTypedArray":175,"../object/keys":177,"./arrayEach":133,"./baseMergeDeep":143,"./isArrayLike":157,"./isObjectLike":162}],143:[function(require,module,exports){var arrayCopy=require("./arrayCopy"),isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isArrayLike=require("./isArrayLike"),isPlainObject=require("../lang/isPlainObject"),isTypedArray=require("../lang/isTypedArray"),toPlainObject=require("../lang/toPlainObject");function baseMergeDeep(object,source,key,mergeFunc,customizer,stackA,stackB){var length=stackA.length,srcValue=source[key];while(length--){if(stackA[length]==srcValue){object[key]=stackB[length];return}}var value=object[key],result=customizer?customizer(value,srcValue,key,object,source):undefined,isCommon=result===undefined;if(isCommon){result=srcValue;if(isArrayLike(srcValue)&&(isArray(srcValue)||isTypedArray(srcValue))){result=isArray(value)?value:isArrayLike(value)?arrayCopy(value):[]}else if(isPlainObject(srcValue)||isArguments(srcValue)){result=isArguments(value)?toPlainObject(value):isPlainObject(value)?value:{}}else{isCommon=false}}stackA.push(srcValue);stackB.push(result);if(isCommon){object[key]=mergeFunc(result,srcValue,customizer,stackA,stackB)}else if(result===result?result!==value:value===value){object[key]=result}}module.exports=baseMergeDeep},{"../lang/isArguments":168,"../lang/isArray":169,"../lang/isPlainObject":173,"../lang/isTypedArray":175,"../lang/toPlainObject":176,"./arrayCopy":132,"./isArrayLike":157}],144:[function(require,module,exports){var toObject=require("./toObject");function baseProperty(key){return function(object){return object==null?undefined:toObject(object)[key]}}module.exports=baseProperty},{"./toObject":165}],145:[function(require,module,exports){arguments[4][51][0].apply(exports,arguments)},{dup:51}],146:[function(require,module,exports){arguments[4][53][0].apply(exports,arguments)},{"../utility/identity":183,dup:53}],147:[function(require,module,exports){(function(global){var constant=require("../utility/constant"),getNative=require("./getNative");var ArrayBuffer=getNative(global,"ArrayBuffer"),bufferSlice=getNative(ArrayBuffer&&new ArrayBuffer(0),"slice"),floor=Math.floor,Uint8Array=getNative(global,"Uint8Array");var Float64Array=function(){try{var func=getNative(global,"Float64Array"),result=new func(new ArrayBuffer(10),0,1)&&func}catch(e){}return result||null}();var FLOAT64_BYTES_PER_ELEMENT=Float64Array?Float64Array.BYTES_PER_ELEMENT:0;function bufferClone(buffer){return bufferSlice.call(buffer,0)}if(!bufferSlice){bufferClone=!(ArrayBuffer&&Uint8Array)?constant(null):function(buffer){var byteLength=buffer.byteLength,floatLength=Float64Array?floor(byteLength/FLOAT64_BYTES_PER_ELEMENT):0,offset=floatLength*FLOAT64_BYTES_PER_ELEMENT,result=new ArrayBuffer(byteLength);if(floatLength){var view=new Float64Array(result,0,floatLength);view.set(new Float64Array(buffer,0,floatLength))}if(byteLength!=offset){view=new Uint8Array(result,offset);view.set(new Uint8Array(buffer,offset))}return result}}module.exports=bufferClone}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"../utility/constant":182,"./getNative":153}],148:[function(require,module,exports){var bindCallback=require("./bindCallback"),isIterateeCall=require("./isIterateeCall"),restParam=require("../function/restParam");function createAssigner(assigner){return restParam(function(object,sources){var index=-1,length=object==null?0:sources.length,customizer=length>2?sources[length-2]:undefined,guard=length>2?sources[2]:undefined,thisArg=length>1?sources[length-1]:undefined;if(typeof customizer=="function"){customizer=bindCallback(customizer,thisArg,5);length-=2}else{customizer=typeof thisArg=="function"?thisArg:undefined;length-=customizer?1:0}if(guard&&isIterateeCall(sources[0],sources[1],guard)){customizer=length<3?undefined:customizer;length=1}while(++index<length){var source=sources[index];if(source){assigner(object,source,customizer)}}return object})}module.exports=createAssigner},{"../function/restParam":131,"./bindCallback":146,"./isIterateeCall":160}],149:[function(require,module,exports){arguments[4][58][0].apply(exports,arguments)},{"./getLength":152,"./isLength":161,"./toObject":165,dup:58}],150:[function(require,module,exports){arguments[4][59][0].apply(exports,arguments)},{"./toObject":165,dup:59}],151:[function(require,module,exports){arguments[4][64][0].apply(exports,arguments)},{"../lang/isArray":169,"./bindCallback":146,dup:64}],152:[function(require,module,exports){arguments[4][74][0].apply(exports,arguments)},{"./baseProperty":144,dup:74}],153:[function(require,module,exports){arguments[4][76][0].apply(exports,arguments)},{"../lang/isNative":171,dup:76}],154:[function(require,module,exports){var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function initCloneArray(array){var length=array.length,result=new array.constructor(length);if(length&&typeof array[0]=="string"&&hasOwnProperty.call(array,"index")){result.index=array.index;result.input=array.input}return result}module.exports=initCloneArray},{}],155:[function(require,module,exports){(function(global){var bufferClone=require("./bufferClone");var boolTag="[object Boolean]",dateTag="[object Date]",numberTag="[object Number]",regexpTag="[object RegExp]",stringTag="[object String]";var arrayBufferTag="[object ArrayBuffer]",float32Tag="[object Float32Array]",float64Tag="[object Float64Array]",int8Tag="[object Int8Array]",int16Tag="[object Int16Array]",int32Tag="[object Int32Array]",uint8Tag="[object Uint8Array]",uint8ClampedTag="[object Uint8ClampedArray]",uint16Tag="[object Uint16Array]",uint32Tag="[object Uint32Array]";var reFlags=/\w*$/;var ctorByTag={};ctorByTag[float32Tag]=global.Float32Array;ctorByTag[float64Tag]=global.Float64Array;ctorByTag[int8Tag]=global.Int8Array;ctorByTag[int16Tag]=global.Int16Array;ctorByTag[int32Tag]=global.Int32Array;ctorByTag[uint8Tag]=global.Uint8Array;ctorByTag[uint8ClampedTag]=global.Uint8ClampedArray;ctorByTag[uint16Tag]=global.Uint16Array;ctorByTag[uint32Tag]=global.Uint32Array;function initCloneByTag(object,tag,isDeep){var Ctor=object.constructor;switch(tag){case arrayBufferTag:return bufferClone(object);case boolTag:case dateTag:return new Ctor(+object);case float32Tag:case float64Tag:case int8Tag:case int16Tag:case int32Tag:case uint8Tag:case uint8ClampedTag:case uint16Tag:case uint32Tag:if(Ctor instanceof Ctor){Ctor=ctorByTag[tag]}var buffer=object.buffer;return new Ctor(isDeep?bufferClone(buffer):buffer,object.byteOffset,object.length);case numberTag:case stringTag:return new Ctor(object);case regexpTag:var result=new Ctor(object.source,reFlags.exec(object));result.lastIndex=object.lastIndex}return result}module.exports=initCloneByTag}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./bufferClone":147}],156:[function(require,module,exports){function initCloneObject(object){var Ctor=object.constructor;if(!(typeof Ctor=="function"&&Ctor instanceof Ctor)){Ctor=Object}return new Ctor}module.exports=initCloneObject},{}],157:[function(require,module,exports){arguments[4][78][0].apply(exports,arguments)},{"./getLength":152,"./isLength":161,dup:78}],158:[function(require,module,exports){var isHostObject=function(){try{Object({toString:0}+"")}catch(e){return function(){return false}}return function(value){return typeof value.toString!="function"&&typeof(value+"")=="string"}}();module.exports=isHostObject},{}],159:[function(require,module,exports){arguments[4][79][0].apply(exports,arguments)},{dup:79}],160:[function(require,module,exports){arguments[4][80][0].apply(exports,arguments)},{"../lang/isObject":172,"./isArrayLike":157,"./isIndex":159,dup:80}],161:[function(require,module,exports){arguments[4][83][0].apply(exports,arguments)},{dup:83}],162:[function(require,module,exports){arguments[4][84][0].apply(exports,arguments)},{dup:84}],163:[function(require,module,exports){var baseForIn=require("./baseForIn"),isArguments=require("../lang/isArguments"),isHostObject=require("./isHostObject"),isObjectLike=require("./isObjectLike"),support=require("../support");var objectTag="[object Object]";var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;function shimIsPlainObject(value){var Ctor;if(!(isObjectLike(value)&&objToString.call(value)==objectTag&&!isHostObject(value))||!hasOwnProperty.call(value,"constructor")&&(Ctor=value.constructor,typeof Ctor=="function"&&!(Ctor instanceof Ctor))||!support.argsTag&&isArguments(value)){return false}var result;if(support.ownLast){baseForIn(value,function(subValue,key,object){result=hasOwnProperty.call(object,key);return false});return result!==false}baseForIn(value,function(subValue,key){result=key});return result===undefined||hasOwnProperty.call(value,result)}module.exports=shimIsPlainObject},{"../lang/isArguments":168,"../support":181,"./baseForIn":139,"./isHostObject":158,"./isObjectLike":162}],164:[function(require,module,exports){var isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isIndex=require("./isIndex"),isLength=require("./isLength"),isString=require("../lang/isString"),keysIn=require("../object/keysIn");var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;function shimKeys(object){var props=keysIn(object),propsLength=props.length,length=propsLength&&object.length;var allowIndexes=!!length&&isLength(length)&&(isArray(object)||isArguments(object)||isString(object));var index=-1,result=[];while(++index<propsLength){var key=props[index];if(allowIndexes&&isIndex(key,length)||hasOwnProperty.call(object,key)){result.push(key)}}return result}module.exports=shimKeys},{"../lang/isArguments":168,"../lang/isArray":169,"../lang/isString":174,"../object/keysIn":178,"./isIndex":159,"./isLength":161}],165:[function(require,module,exports){var isObject=require("../lang/isObject"),isString=require("../lang/isString"),support=require("../support");function toObject(value){if(support.unindexedChars&&isString(value)){var index=-1,length=value.length,result=Object(value);while(++index<length){result[index]=value.charAt(index)}return result}return isObject(value)?value:Object(value)}module.exports=toObject},{"../lang/isObject":172,"../lang/isString":174,"../support":181}],166:[function(require,module,exports){var baseClone=require("../internal/baseClone"),bindCallback=require("../internal/bindCallback"),isIterateeCall=require("../internal/isIterateeCall");function clone(value,isDeep,customizer,thisArg){if(isDeep&&typeof isDeep!="boolean"&&isIterateeCall(value,isDeep,customizer)){isDeep=false}else if(typeof isDeep=="function"){thisArg=customizer;customizer=isDeep;isDeep=false}return typeof customizer=="function"?baseClone(value,isDeep,bindCallback(customizer,thisArg,1)):baseClone(value,isDeep)}module.exports=clone},{"../internal/baseClone":135,"../internal/bindCallback":146,"../internal/isIterateeCall":160}],167:[function(require,module,exports){var baseClone=require("../internal/baseClone"),bindCallback=require("../internal/bindCallback");function cloneDeep(value,customizer,thisArg){return typeof customizer=="function"?baseClone(value,true,bindCallback(customizer,thisArg,1)):baseClone(value,true)}module.exports=cloneDeep},{"../internal/baseClone":135,"../internal/bindCallback":146}],168:[function(require,module,exports){var isArrayLike=require("../internal/isArrayLike"),isObjectLike=require("../internal/isObjectLike"),support=require("../support");var argsTag="[object Arguments]";var objectProto=Object.prototype;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;var propertyIsEnumerable=objectProto.propertyIsEnumerable;function isArguments(value){return isObjectLike(value)&&isArrayLike(value)&&objToString.call(value)==argsTag;
 
8
 
9
- }if(!support.argsTag){isArguments=function(value){return isObjectLike(value)&&isArrayLike(value)&&hasOwnProperty.call(value,"callee")&&!propertyIsEnumerable.call(value,"callee")}}module.exports=isArguments},{"../internal/isArrayLike":157,"../internal/isObjectLike":162,"../support":181}],169:[function(require,module,exports){arguments[4][100][0].apply(exports,arguments)},{"../internal/getNative":153,"../internal/isLength":161,"../internal/isObjectLike":162,dup:100}],170:[function(require,module,exports){arguments[4][102][0].apply(exports,arguments)},{"../internal/baseIsFunction":141,"../internal/getNative":153,dup:102}],171:[function(require,module,exports){var escapeRegExp=require("../string/escapeRegExp"),isHostObject=require("../internal/isHostObject"),isObjectLike=require("../internal/isObjectLike");var funcTag="[object Function]";var reIsHostCtor=/^\[object .+?Constructor\]$/;var objectProto=Object.prototype;var fnToString=Function.prototype.toString;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;var reIsNative=RegExp("^"+escapeRegExp(fnToString.call(hasOwnProperty)).replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g,"$1.*?")+"$");function isNative(value){if(value==null){return false}if(objToString.call(value)==funcTag){return reIsNative.test(fnToString.call(value))}return isObjectLike(value)&&(isHostObject(value)?reIsNative:reIsHostCtor).test(value)}module.exports=isNative},{"../internal/isHostObject":158,"../internal/isObjectLike":162,"../string/escapeRegExp":180}],172:[function(require,module,exports){arguments[4][104][0].apply(exports,arguments)},{dup:104}],173:[function(require,module,exports){var getNative=require("../internal/getNative"),isArguments=require("./isArguments"),shimIsPlainObject=require("../internal/shimIsPlainObject"),support=require("../support");var objectTag="[object Object]";var objectProto=Object.prototype;var objToString=objectProto.toString;var getPrototypeOf=getNative(Object,"getPrototypeOf");var isPlainObject=!getPrototypeOf?shimIsPlainObject:function(value){if(!(value&&objToString.call(value)==objectTag)||!support.argsTag&&isArguments(value)){return false}var valueOf=getNative(value,"valueOf"),objProto=valueOf&&(objProto=getPrototypeOf(valueOf))&&getPrototypeOf(objProto);return objProto?value==objProto||getPrototypeOf(value)==objProto:shimIsPlainObject(value)};module.exports=isPlainObject},{"../internal/getNative":153,"../internal/shimIsPlainObject":163,"../support":181,"./isArguments":168}],174:[function(require,module,exports){arguments[4][105][0].apply(exports,arguments)},{"../internal/isObjectLike":162,dup:105}],175:[function(require,module,exports){arguments[4][106][0].apply(exports,arguments)},{"../internal/isLength":161,"../internal/isObjectLike":162,dup:106}],176:[function(require,module,exports){var baseCopy=require("../internal/baseCopy"),keysIn=require("../object/keysIn");function toPlainObject(value){return baseCopy(value,keysIn(value))}module.exports=toPlainObject},{"../internal/baseCopy":136,"../object/keysIn":178}],177:[function(require,module,exports){var getNative=require("../internal/getNative"),isArrayLike=require("../internal/isArrayLike"),isObject=require("../lang/isObject"),shimKeys=require("../internal/shimKeys"),support=require("../support");var nativeKeys=getNative(Object,"keys");var keys=!nativeKeys?shimKeys:function(object){var Ctor=object==null?null:object.constructor;if(typeof Ctor=="function"&&Ctor.prototype===object||(typeof object=="function"?support.enumPrototypes:isArrayLike(object))){return shimKeys(object)}return isObject(object)?nativeKeys(object):[]};module.exports=keys},{"../internal/getNative":153,"../internal/isArrayLike":157,"../internal/shimKeys":164,"../lang/isObject":172,"../support":181}],178:[function(require,module,exports){var arrayEach=require("../internal/arrayEach"),isArguments=require("../lang/isArguments"),isArray=require("../lang/isArray"),isFunction=require("../lang/isFunction"),isIndex=require("../internal/isIndex"),isLength=require("../internal/isLength"),isObject=require("../lang/isObject"),isString=require("../lang/isString"),support=require("../support");var arrayTag="[object Array]",boolTag="[object Boolean]",dateTag="[object Date]",errorTag="[object Error]",funcTag="[object Function]",numberTag="[object Number]",objectTag="[object Object]",regexpTag="[object RegExp]",stringTag="[object String]";var shadowProps=["constructor","hasOwnProperty","isPrototypeOf","propertyIsEnumerable","toLocaleString","toString","valueOf"];var errorProto=Error.prototype,objectProto=Object.prototype,stringProto=String.prototype;var hasOwnProperty=objectProto.hasOwnProperty;var objToString=objectProto.toString;var nonEnumProps={};nonEnumProps[arrayTag]=nonEnumProps[dateTag]=nonEnumProps[numberTag]={constructor:true,toLocaleString:true,toString:true,valueOf:true};nonEnumProps[boolTag]=nonEnumProps[stringTag]={constructor:true,toString:true,valueOf:true};nonEnumProps[errorTag]=nonEnumProps[funcTag]=nonEnumProps[regexpTag]={constructor:true,toString:true};nonEnumProps[objectTag]={constructor:true};arrayEach(shadowProps,function(key){for(var tag in nonEnumProps){if(hasOwnProperty.call(nonEnumProps,tag)){var props=nonEnumProps[tag];props[key]=hasOwnProperty.call(props,key)}}});function keysIn(object){if(object==null){return[]}if(!isObject(object)){object=Object(object)}var length=object.length;length=length&&isLength(length)&&(isArray(object)||isArguments(object)||isString(object))&&length||0;var Ctor=object.constructor,index=-1,proto=isFunction(Ctor)&&Ctor.prototype||objectProto,isProto=proto===object,result=Array(length),skipIndexes=length>0,skipErrorProps=support.enumErrorProps&&(object===errorProto||object instanceof Error),skipProto=support.enumPrototypes&&isFunction(object);while(++index<length){result[index]=index+""}for(var key in object){if(!(skipProto&&key=="prototype")&&!(skipErrorProps&&(key=="message"||key=="name"))&&!(skipIndexes&&isIndex(key,length))&&!(key=="constructor"&&(isProto||!hasOwnProperty.call(object,key)))){result.push(key)}}if(support.nonEnumShadows&&object!==objectProto){var tag=object===stringProto?stringTag:object===errorProto?errorTag:objToString.call(object),nonEnums=nonEnumProps[tag]||nonEnumProps[objectTag];if(tag==objectTag){proto=objectProto}length=shadowProps.length;while(length--){key=shadowProps[length];var nonEnum=nonEnums[key];if(!(isProto&&nonEnum)&&(nonEnum?hasOwnProperty.call(object,key):object[key]!==proto[key])){result.push(key)}}}return result}module.exports=keysIn},{"../internal/arrayEach":133,"../internal/isIndex":159,"../internal/isLength":161,"../lang/isArguments":168,"../lang/isArray":169,"../lang/isFunction":170,"../lang/isObject":172,"../lang/isString":174,"../support":181}],179:[function(require,module,exports){var baseMerge=require("../internal/baseMerge"),createAssigner=require("../internal/createAssigner");var merge=createAssigner(baseMerge);module.exports=merge},{"../internal/baseMerge":142,"../internal/createAssigner":148}],180:[function(require,module,exports){arguments[4][114][0].apply(exports,arguments)},{"../internal/baseToString":145,dup:114}],181:[function(require,module,exports){(function(global){var argsTag="[object Arguments]",objectTag="[object Object]";var arrayProto=Array.prototype,errorProto=Error.prototype,objectProto=Object.prototype;var document=(document=global.window)?document.document:null;var objToString=objectProto.toString;var propertyIsEnumerable=objectProto.propertyIsEnumerable,splice=arrayProto.splice;var support={};(function(x){var Ctor=function(){this.x=x},object={0:x,length:x},props=[];Ctor.prototype={valueOf:x,y:x};for(var key in new Ctor){props.push(key)}support.argsTag=objToString.call(arguments)==argsTag;support.enumErrorProps=propertyIsEnumerable.call(errorProto,"message")||propertyIsEnumerable.call(errorProto,"name");support.enumPrototypes=propertyIsEnumerable.call(Ctor,"prototype");support.nodeTag=objToString.call(document)!=objectTag;support.nonEnumShadows=!/valueOf/.test(props);support.ownLast=props[0]!="x";support.spliceObjects=(splice.call(object,0,1),!object[0]);support.unindexedChars="x"[0]+Object("x")[0]!="xx";try{support.dom=document.createDocumentFragment().nodeType===11}catch(e){support.dom=false}})(1,0);module.exports=support}).call(this,typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{}],182:[function(require,module,exports){arguments[4][115][0].apply(exports,arguments)},{dup:115}],183:[function(require,module,exports){arguments[4][116][0].apply(exports,arguments)},{dup:116}],184:[function(require,module,exports){(function(process){module.exports=AlgoliaSearch;if(process.env.APP_ENV==="development"){require("debug").enable("algoliasearch*")}var errors=require("./errors");function AlgoliaSearch(applicationID,apiKey,opts){var debug=require("debug")("algoliasearch");var clone=require("lodash-compat/lang/clone");var isArray=require("lodash-compat/lang/isArray");var usage="Usage: algoliasearch(applicationID, apiKey, opts)";if(!applicationID){throw new errors.AlgoliaSearchError("Please provide an application ID. "+usage)}if(!apiKey){throw new errors.AlgoliaSearchError("Please provide an API key. "+usage)}this.applicationID=applicationID;this.apiKey=apiKey;var defaultHosts=[this.applicationID+"-1.algolianet.com",this.applicationID+"-2.algolianet.com",this.applicationID+"-3.algolianet.com"];this.hosts={read:[],write:[]};this.hostIndex={read:0,write:0};opts=opts||{};var protocol=opts.protocol||"https:";var timeout=opts.timeout===undefined?2e3:opts.timeout;if(!/:$/.test(protocol)){protocol=protocol+":"}if(opts.protocol!=="http:"&&opts.protocol!=="https:"){throw new errors.AlgoliaSearchError("protocol must be `http:` or `https:` (was `"+opts.protocol+"`)")}if(!opts.hosts){this.hosts.read=[this.applicationID+"-dsn.algolia.net"].concat(defaultHosts);this.hosts.write=[this.applicationID+".algolia.net"].concat(defaultHosts)}else{if(isArray(opts.hosts)){this.hosts.read=clone(opts.hosts);this.hosts.write=clone(opts.hosts)}else{this.hosts.read=clone(opts.hosts.read);this.hosts.write=clone(opts.hosts.write)}}this.hosts.read=map(this.hosts.read,prepareHost(protocol));this.hosts.write=map(this.hosts.write,prepareHost(protocol));this.requestTimeout=timeout;this.extraHeaders=[];this.cache={};this._ua=opts._ua;this._useCache=opts._useCache===undefined?true:opts._useCache;this._setTimeout=opts._setTimeout;debug("init done, %j",this)}AlgoliaSearch.prototype={deleteIndex:function(indexName,callback){return this._jsonRequest({method:"DELETE",url:"/1/indexes/"+encodeURIComponent(indexName),hostType:"write",callback:callback})},moveIndex:function(srcIndexName,dstIndexName,callback){var postObj={operation:"move",destination:dstIndexName};return this._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(srcIndexName)+"/operation",body:postObj,hostType:"write",callback:callback})},copyIndex:function(srcIndexName,dstIndexName,callback){var postObj={operation:"copy",destination:dstIndexName};return this._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(srcIndexName)+"/operation",body:postObj,hostType:"write",callback:callback})},getLogs:function(offset,length,callback){if(arguments.length===0||typeof offset==="function"){callback=offset;offset=0;length=10}else if(arguments.length===1||typeof length==="function"){callback=length;length=10}return this._jsonRequest({method:"GET",url:"/1/logs?offset="+offset+"&length="+length,hostType:"read",callback:callback})},listIndexes:function(page,callback){var params="";if(page===undefined||typeof page==="function"){callback=page}else{params="?page="+page}return this._jsonRequest({method:"GET",url:"/1/indexes"+params,hostType:"read",callback:callback})},initIndex:function(indexName){return new this.Index(this,indexName)},listUserKeys:function(callback){return this._jsonRequest({method:"GET",url:"/1/keys",hostType:"read",callback:callback})},getUserKeyACL:function(key,callback){return this._jsonRequest({method:"GET",url:"/1/keys/"+key,hostType:"read",callback:callback})},deleteUserKey:function(key,callback){return this._jsonRequest({method:"DELETE",url:"/1/keys/"+key,hostType:"write",callback:callback})},addUserKey:function(acls,params,callback){if(arguments.length===1||typeof params==="function"){callback=params;params=null}var postObj={acl:acls};if(params){postObj.validity=params.validity;postObj.maxQueriesPerIPPerHour=params.maxQueriesPerIPPerHour;postObj.maxHitsPerQuery=params.maxHitsPerQuery;postObj.indexes=params.indexes;postObj.description=params.description;if(params.queryParameters){postObj.queryParameters=this._getSearchParams(params.queryParameters,"")}postObj.referers=params.referers}return this._jsonRequest({method:"POST",url:"/1/keys",body:postObj,hostType:"write",callback:callback})},addUserKeyWithValidity:deprecate(function(acls,params,callback){return this.addUserKey(acls,params,callback)},deprecatedMessage("client.addUserKeyWithValidity()","client.addUserKey()")),updateUserKey:function(key,acls,params,callback){if(arguments.length===2||typeof params==="function"){callback=params;params=null}var putObj={acl:acls};if(params){putObj.validity=params.validity;putObj.maxQueriesPerIPPerHour=params.maxQueriesPerIPPerHour;putObj.maxHitsPerQuery=params.maxHitsPerQuery;putObj.indexes=params.indexes;putObj.description=params.description;if(params.queryParameters){putObj.queryParameters=this._getSearchParams(params.queryParameters,"")}putObj.referers=params.referers}return this._jsonRequest({method:"PUT",url:"/1/keys/"+key,body:putObj,hostType:"write",callback:callback})},setSecurityTags:function(tags){if(Object.prototype.toString.call(tags)==="[object Array]"){var strTags=[];for(var i=0;i<tags.length;++i){if(Object.prototype.toString.call(tags[i])==="[object Array]"){var oredTags=[];for(var j=0;j<tags[i].length;++j){oredTags.push(tags[i][j])}strTags.push("("+oredTags.join(",")+")")}else{strTags.push(tags[i])}}tags=strTags.join(",")}this.securityTags=tags},setUserToken:function(userToken){this.userToken=userToken},startQueriesBatch:deprecate(function(){this._batch=[]},deprecatedMessage("client.startQueriesBatch()","client.search()")),addQueryInBatch:deprecate(function(indexName,query,args){this._batch.push({indexName:indexName,query:query,params:args})},deprecatedMessage("client.addQueryInBatch()","client.search()")),clearCache:function(){this.cache={}},sendQueriesBatch:deprecate(function(callback){return this.search(this._batch,callback)},deprecatedMessage("client.sendQueriesBatch()","client.search()")),setRequestTimeout:function(milliseconds){if(milliseconds){this.requestTimeout=parseInt(milliseconds,10)}},search:function(queries,callback){var client=this;var postObj={requests:map(queries,function prepareRequest(query){var params="";if(query.query!==undefined){params+="query="+encodeURIComponent(query.query)}return{indexName:query.indexName,params:client._getSearchParams(query.params,params)}})};return this._jsonRequest({cache:this.cache,method:"POST",url:"/1/indexes/*/queries",body:postObj,hostType:"read",callback:callback})},batch:function(operations,callback){return this._jsonRequest({method:"POST",url:"/1/indexes/*/batch",body:{requests:operations},hostType:"write",callback:callback})},destroy:notImplemented,enableRateLimitForward:notImplemented,disableRateLimitForward:notImplemented,useSecuredAPIKey:notImplemented,disableSecuredAPIKey:notImplemented,generateSecuredApiKey:notImplemented,Index:function(algoliasearch,indexName){this.indexName=indexName;this.as=algoliasearch;this.typeAheadArgs=null;this.typeAheadValueOption=null;this.cache={}},setExtraHeader:function(name,value){this.extraHeaders.push({name:name.toLowerCase(),value:value})},_sendQueriesBatch:function(params,callback){return this._jsonRequest({cache:this.cache,method:"POST",url:"/1/indexes/*/queries",body:params,hostType:"read",fallback:{method:"GET",url:"/1/indexes/*",body:{params:function(){var reqParams="";for(var i=0;i<params.requests.length;++i){var q="/1/indexes/"+encodeURIComponent(params.requests[i].indexName)+"?"+params.requests[i].params;reqParams+=i+"="+encodeURIComponent(q)+"&"}return reqParams}()}},callback:callback})},_jsonRequest:function(opts){var requestDebug=require("debug")("algoliasearch:"+opts.url);var body;var cache=opts.cache;var client=this;var tries=0;var usingFallback=false;if(opts.body!==undefined){body=JSON.stringify(opts.body)}requestDebug("request start");function doRequest(requester,reqOpts){var cacheID;if(client._useCache){cacheID=opts.url}if(client._useCache&&body){cacheID+="_body_"+reqOpts.body}if(client._useCache&&cache&&cache[cacheID]!==undefined){requestDebug("serving response from cache");return client._promise.resolve(JSON.parse(JSON.stringify(cache[cacheID])))}if(tries>=client.hosts[opts.hostType].length||client.useFallback&&!usingFallback){if(!opts.fallback||!client._request.fallback||usingFallback){requestDebug("could not get any response");return client._promise.reject(new errors.AlgoliaSearchError("Cannot connect to the AlgoliaSearch API."+" Send an email to support@algolia.com to report and resolve the issue."+" Application id was: "+client.applicationID))}requestDebug("switching to fallback");tries=0;reqOpts.method=opts.fallback.method;reqOpts.url=opts.fallback.url;reqOpts.jsonBody=opts.fallback.body;if(reqOpts.jsonBody){reqOpts.body=JSON.stringify(reqOpts.jsonBody)}reqOpts.timeout=client.requestTimeout*(tries+1);client.hostIndex[opts.hostType]=0;usingFallback=true;return doRequest(client._request.fallback,reqOpts)}var url=client.hosts[opts.hostType][client.hostIndex[opts.hostType]]+reqOpts.url;var options={body:body,jsonBody:opts.body,method:reqOpts.method,headers:client._computeRequestHeaders(),timeout:reqOpts.timeout,debug:requestDebug};requestDebug("method: %s, url: %s, headers: %j, timeout: %d",options.method,url,options.headers,options.timeout);if(requester===client._request.fallback){requestDebug("using fallback")}return requester.call(client,url,options).then(success,tryFallback);function success(httpResponse){var status=httpResponse&&httpResponse.body&&httpResponse.body.message&&httpResponse.body.status||httpResponse.statusCode||httpResponse&&httpResponse.body&&200;requestDebug("received response: statusCode: %s, computed statusCode: %d, headers: %j",httpResponse.statusCode,status,httpResponse.headers);if(process.env.DEBUG&&process.env.DEBUG.indexOf("debugBody")!==-1){requestDebug("body: %j",httpResponse.body)}var ok=status===200||status===201;var retry=!ok&&Math.floor(status/100)!==4&&Math.floor(status/100)!==1;if(client._useCache&&ok&&cache){cache[cacheID]=httpResponse.body}if(ok){return httpResponse.body}if(retry){tries+=1;return retryRequest()}var unrecoverableError=new errors.AlgoliaSearchError(httpResponse.body&&httpResponse.body.message);return client._promise.reject(unrecoverableError)}function tryFallback(err){requestDebug("error: %s, stack: %s",err.message,err.stack);if(!(err instanceof errors.AlgoliaSearchError)){err=new errors.Unknown(err&&err.message,err)}tries+=1;if(err instanceof errors.Unknown||err instanceof errors.UnparsableJSON||!requester.fallback&&err instanceof errors.Network||tries>=client.hosts[opts.hostType].length&&(usingFallback||!opts.fallback||!client._request.fallback)){return client._promise.reject(err)}client.hostIndex[opts.hostType]=++client.hostIndex[opts.hostType]%client.hosts[opts.hostType].length;if(err instanceof errors.RequestTimeout){return retryRequest()}else if(client._request.fallback&&!client.useFallback){client.useFallback=true}return doRequest(requester,reqOpts)}function retryRequest(){client.hostIndex[opts.hostType]=++client.hostIndex[opts.hostType]%client.hosts[opts.hostType].length;reqOpts.timeout=client.requestTimeout*(tries+1);return doRequest(requester,reqOpts)}}var useFallback=client.useFallback&&opts.fallback;var requestOptions=useFallback?opts.fallback:opts;var promise=doRequest(useFallback?client._request.fallback:client._request,{url:requestOptions.url,method:requestOptions.method,body:body,jsonBody:opts.body,timeout:client.requestTimeout*(tries+1)});if(opts.callback){promise.then(function okCb(content){exitPromise(function(){opts.callback(null,content)},client._setTimeout||setTimeout)},function nookCb(err){exitPromise(function(){opts.callback(err)},client._setTimeout||setTimeout)})}else{return promise}},_getSearchParams:function(args,params){if(this._isUndefined(args)||args===null){return params}for(var key in args){if(key!==null&&args[key]!==undefined&&args.hasOwnProperty(key)){params+=params===""?"":"&";params+=key+"="+encodeURIComponent(Object.prototype.toString.call(args[key])==="[object Array]"?JSON.stringify(args[key]):args[key])}}return params},_isUndefined:function(obj){return obj===void 0},_computeRequestHeaders:function(){var forEach=require("lodash-compat/collection/forEach");var requestHeaders={"x-algolia-api-key":this.apiKey,"x-algolia-application-id":this.applicationID,"x-algolia-agent":this._ua};if(this.userToken){requestHeaders["x-algolia-usertoken"]=this.userToken}if(this.securityTags){requestHeaders["x-algolia-tagfilters"]=this.securityTags}if(this.extraHeaders){forEach(this.extraHeaders,function addToRequestHeaders(header){requestHeaders[header.name]=header.value})}return requestHeaders}};AlgoliaSearch.prototype.Index.prototype={clearCache:function(){this.cache={}},addObject:function(content,objectID,callback){var indexObj=this;if(arguments.length===1||typeof objectID==="function"){callback=objectID;objectID=undefined}return this.as._jsonRequest({method:objectID!==undefined?"PUT":"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+(objectID!==undefined?"/"+encodeURIComponent(objectID):""),body:content,hostType:"write",callback:callback})},addObjects:function(objects,callback){var indexObj=this;var postObj={requests:[]};for(var i=0;i<objects.length;++i){var request={action:"addObject",body:objects[i]};postObj.requests.push(request)}return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/batch",body:postObj,hostType:"write",callback:callback})},getObject:function(objectID,attrs,callback){var indexObj=this;if(arguments.length===1||typeof attrs==="function"){callback=attrs;attrs=undefined}var params="";if(attrs!==undefined){params="?attributes=";for(var i=0;i<attrs.length;++i){if(i!==0){params+=","}params+=attrs[i]}}return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/"+encodeURIComponent(objectID)+params,hostType:"read",callback:callback})},getObjects:function(objectIDs,attributesToRetrieve,callback){var indexObj=this;if(arguments.length===1||typeof attributesToRetrieve==="function"){callback=attributesToRetrieve;attributesToRetrieve=undefined}var body={requests:map(objectIDs,function prepareRequest(objectID){var request={indexName:indexObj.indexName,objectID:objectID};if(attributesToRetrieve){request.attributesToRetrieve=attributesToRetrieve.join(",")}return request})};return this.as._jsonRequest({method:"POST",url:"/1/indexes/*/objects",hostType:"read",body:body,callback:callback})},partialUpdateObject:function(partialObject,callback){var indexObj=this;return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/"+encodeURIComponent(partialObject.objectID)+"/partial",body:partialObject,hostType:"write",callback:callback})},partialUpdateObjects:function(objects,callback){var indexObj=this;var postObj={requests:[]};for(var i=0;i<objects.length;++i){var request={action:"partialUpdateObject",objectID:objects[i].objectID,body:objects[i]};postObj.requests.push(request)}return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/batch",body:postObj,hostType:"write",callback:callback})},saveObject:function(object,callback){var indexObj=this;return this.as._jsonRequest({method:"PUT",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/"+encodeURIComponent(object.objectID),body:object,hostType:"write",callback:callback})},saveObjects:function(objects,callback){var indexObj=this;var postObj={requests:[]};for(var i=0;i<objects.length;++i){var request={action:"updateObject",objectID:objects[i].objectID,body:objects[i]};postObj.requests.push(request)}return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/batch",body:postObj,hostType:"write",callback:callback})},deleteObject:function(objectID,callback){if(typeof objectID==="function"||typeof objectID!=="string"&&typeof objectID!=="number"){var err=new errors.AlgoliaSearchError("Cannot delete an object without an objectID");callback=objectID;if(typeof callback==="function"){return callback(err)}return this.as._promise.reject(err)}var indexObj=this;return this.as._jsonRequest({method:"DELETE",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/"+encodeURIComponent(objectID),hostType:"write",callback:callback})},deleteObjects:function(objectIDs,callback){var indexObj=this;var postObj={requests:map(objectIDs,function prepareRequest(objectID){return{action:"deleteObject",objectID:objectID,body:{objectID:objectID}}})};return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/batch",body:postObj,hostType:"write",callback:callback})},deleteByQuery:function(query,params,callback){var indexObj=this;var client=indexObj.as;if(arguments.length===1||typeof params==="function"){callback=params;params={}}params.attributesToRetrieve="objectID";params.hitsPerPage=1e3;this.clearCache();var promise=this.search(query,params).then(stopOrDelete);function stopOrDelete(searchContent){if(searchContent.nbHits===0){return searchContent}var objectIDs=map(searchContent.hits,function getObjectID(object){return object.objectID});return indexObj.deleteObjects(objectIDs).then(waitTask).then(deleteByQuery)}function waitTask(deleteObjectsContent){return indexObj.waitTask(deleteObjectsContent.taskID)}function deleteByQuery(){return indexObj.deleteByQuery(query,params)}if(!callback){return promise}promise.then(success,failure);function success(){exitPromise(function(){callback(null)},client._setTimeout||setTimeout)}function failure(err){exitPromise(function(){callback(err)},client._setTimeout||setTimeout)}},search:function(query,args,callback){if(typeof query==="function"&&typeof args==="object"||typeof callback==="object"){throw new errors.AlgoliaSearchError("index.search usage is index.search(query, params, cb)")}if(arguments.length===0||typeof query==="function"){callback=query;query=""}else if(arguments.length===1||typeof args==="function"){callback=args;args=undefined}if(typeof query==="object"&&query!==null){args=query;query=undefined}else if(query===undefined||query===null){query=""}var params="";if(query!==undefined){params+="query="+encodeURIComponent(query)}if(args!==undefined){params=this.as._getSearchParams(args,params)}return this._search(params,callback)},browse:function(query,queryParameters,callback){var merge=require("lodash-compat/object/merge");var indexObj=this;var page;var hitsPerPage;if(arguments.length===0||arguments.length===1&&typeof arguments[0]==="function"){page=0;callback=arguments[0];query=undefined}else if(typeof arguments[0]==="number"){page=arguments[0];if(typeof arguments[1]==="number"){hitsPerPage=arguments[1]}else if(typeof arguments[1]==="function"){callback=arguments[1];hitsPerPage=undefined}query=undefined;queryParameters=undefined}else if(typeof arguments[0]==="object"){if(typeof arguments[1]==="function"){callback=arguments[1]}queryParameters=arguments[0];query=undefined}else if(typeof arguments[0]==="string"&&typeof arguments[1]==="function"){callback=arguments[1];queryParameters=undefined}queryParameters=merge({},queryParameters||{},{page:page,hitsPerPage:hitsPerPage,query:query});var params=this.as._getSearchParams(queryParameters,"");return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/browse?"+params,hostType:"read",callback:callback})},browseFrom:function(cursor,callback){return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(this.indexName)+"/browse?cursor="+cursor,hostType:"read",callback:callback})},browseAll:function(query,queryParameters){if(typeof query==="object"){queryParameters=query;query=undefined}var merge=require("lodash-compat/object/merge");var IndexBrowser=require("./IndexBrowser");var browser=new IndexBrowser;var client=this.as;var index=this;var params=client._getSearchParams(merge({},queryParameters||{},{query:query}),"");browseLoop();function browseLoop(cursor){if(browser._stopped){return}var queryString;if(cursor!==undefined){queryString="cursor="+encodeURIComponent(cursor)}else{queryString=params}client._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(index.indexName)+"/browse?"+queryString,hostType:"read",callback:browseCallback})}function browseCallback(err,content){if(browser._stopped){return}if(err){browser._error(err);return}browser._result(content);if(content.cursor===undefined){browser._end();return}browseLoop(content.cursor)}return browser},ttAdapter:function(params){var self=this;return function(query,syncCb,asyncCb){var cb;if(typeof asyncCb==="function"){cb=asyncCb}else{cb=syncCb}self.search(query,params,function(err,content){if(err){cb(err);return}cb(content.hits)})}},waitTask:function(taskID,callback){var baseDelay=100;var maxDelay=5e3;var loop=0;var indexObj=this;var client=indexObj.as;var promise=retryLoop();function retryLoop(){return client._jsonRequest({method:"GET",hostType:"read",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/task/"+taskID}).then(function success(content){loop++;var delay=baseDelay*loop*loop;if(delay>maxDelay){delay=maxDelay}if(content.status!=="published"){return client._promise.delay(delay).then(function(){return retryLoop()})}return content})}if(!callback){return promise}promise.then(successCb,failureCb);function successCb(content){exitPromise(function(){callback(null,content)},client._setTimeout||setTimeout)}function failureCb(err){exitPromise(function(){callback(err)},client._setTimeout||setTimeout)}},clearIndex:function(callback){var indexObj=this;return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/clear",hostType:"write",callback:callback})},getSettings:function(callback){var indexObj=this;return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/settings",hostType:"read",callback:callback})},setSettings:function(settings,callback){var indexObj=this;return this.as._jsonRequest({method:"PUT",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/settings",hostType:"write",body:settings,callback:callback})},listUserKeys:function(callback){var indexObj=this;return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/keys",hostType:"read",callback:callback})},getUserKeyACL:function(key,callback){var indexObj=this;return this.as._jsonRequest({method:"GET",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/keys/"+key,hostType:"read",callback:callback})},deleteUserKey:function(key,callback){var indexObj=this;return this.as._jsonRequest({method:"DELETE",url:"/1/indexes/"+encodeURIComponent(indexObj.indexName)+"/keys/"+key,hostType:"write",callback:callback})},addUserKey:function(acls,params,callback){if(arguments.length===1||typeof params==="function"){callback=params;params=null}var postObj={acl:acls};if(params){postObj.validity=params.validity;postObj.maxQueriesPerIPPerHour=params.maxQueriesPerIPPerHour;postObj.maxHitsPerQuery=params.maxHitsPerQuery;postObj.description=params.description;if(params.queryParameters){postObj.queryParameters=this.as._getSearchParams(params.queryParameters,"")}postObj.referers=params.referers}return this.as._jsonRequest({method:"POST",url:"/1/indexes/"+encodeURIComponent(this.indexName)+"/keys",body:postObj,hostType:"write",
10
- callback:callback})},addUserKeyWithValidity:deprecate(function(acls,params,callback){return this.addUserKey(acls,params,callback)},deprecatedMessage("index.addUserKeyWithValidity()","index.addUserKey()")),updateUserKey:function(key,acls,params,callback){if(arguments.length===2||typeof params==="function"){callback=params;params=null}var putObj={acl:acls};if(params){putObj.validity=params.validity;putObj.maxQueriesPerIPPerHour=params.maxQueriesPerIPPerHour;putObj.maxHitsPerQuery=params.maxHitsPerQuery;putObj.description=params.description;if(params.queryParameters){putObj.queryParameters=this.as._getSearchParams(params.queryParameters,"")}putObj.referers=params.referers}return this.as._jsonRequest({method:"PUT",url:"/1/indexes/"+encodeURIComponent(this.indexName)+"/keys/"+key,body:putObj,hostType:"write",callback:callback})},_search:function(params,callback){return this.as._jsonRequest({cache:this.cache,method:"POST",url:"/1/indexes/"+encodeURIComponent(this.indexName)+"/query",body:{params:params},hostType:"read",fallback:{method:"GET",url:"/1/indexes/"+encodeURIComponent(this.indexName),body:{params:params}},callback:callback})},as:null,indexName:null,typeAheadArgs:null,typeAheadValueOption:null};function map(arr,fn){var ret=[];for(var i=0;i<arr.length;++i){ret.push(fn(arr[i],i))}return ret}function prepareHost(protocol){return function prepare(host){return protocol+"//"+host.toLowerCase()}}function notImplemented(){var message="Not implemented in this environment.\n"+"If you feel this is a mistake, write to support@algolia.com";throw new errors.AlgoliaSearchError(message)}function deprecatedMessage(previousUsage,newUsage){var githubAnchorLink=previousUsage.toLowerCase().replace(".","").replace("()","");return"algoliasearch: `"+previousUsage+"` was replaced by `"+newUsage+"`. Please see https://github.com/algolia/algoliasearch-client-js/wiki/Deprecated#"+githubAnchorLink}function exitPromise(fn,_setTimeout){_setTimeout(fn,0)}function deprecate(fn,message){var warned=false;function deprecated(){if(!warned){console.log(message);warned=true}return fn.apply(this,arguments)}return deprecated}}).call(this,require("_process"))},{"./IndexBrowser":185,"./errors":190,_process:194,debug:125,"lodash-compat/collection/forEach":130,"lodash-compat/lang/clone":166,"lodash-compat/lang/isArray":169,"lodash-compat/object/merge":179}],185:[function(require,module,exports){module.exports=IndexBrowser;var inherits=require("inherits");var EventEmitter=require("events").EventEmitter;function IndexBrowser(){}inherits(IndexBrowser,EventEmitter);IndexBrowser.prototype.stop=function(){this._stopped=true;this._clean()};IndexBrowser.prototype._end=function(){this.emit("end");this._clean()};IndexBrowser.prototype._error=function(err){this.emit("error",err);this._clean()};IndexBrowser.prototype._result=function(content){this.emit("result",content)};IndexBrowser.prototype._clean=function(){this.removeAllListeners("stop");this.removeAllListeners("end");this.removeAllListeners("error");this.removeAllListeners("result")}},{events:192,inherits:129}],186:[function(require,module,exports){module.exports=JSONPRequest;var errors=require("../errors");var JSONPCounter=0;function JSONPRequest(url,opts,cb){if(opts.method!=="GET"){cb(new Error("Method "+opts.method+" "+url+" is not supported by JSONP."));return}opts.debug("JSONP: start");var cbCalled=false;var timedOut=false;JSONPCounter+=1;var head=document.getElementsByTagName("head")[0];var script=document.createElement("script");var cbName="algoliaJSONP_"+JSONPCounter;var done=false;window[cbName]=function(data){try{delete window[cbName]}catch(e){window[cbName]=undefined}if(timedOut){return}cbCalled=true;clean();cb(null,{body:data})};url+="&callback="+cbName;if(opts.jsonBody&&opts.jsonBody.params){url+="&"+opts.jsonBody.params}var ontimeout=setTimeout(timeout,opts.timeout);script.onreadystatechange=readystatechange;script.onload=success;script.onerror=error;script.async=true;script.defer=true;script.src=url;head.appendChild(script);function success(){opts.debug("JSONP: success");if(done||timedOut){return}done=true;if(!cbCalled){opts.debug("JSONP: Fail. Script loaded but did not call the callback");clean();cb(new errors.JSONPScriptFail)}}function readystatechange(){if(this.readyState==="loaded"||this.readyState==="complete"){success()}}function clean(){clearTimeout(ontimeout);script.onload=null;script.onreadystatechange=null;script.onerror=null;head.removeChild(script);try{delete window[cbName];delete window[cbName+"_loaded"]}catch(e){window[cbName]=null;window[cbName+"_loaded"]=null}}function timeout(){opts.debug("JSONP: Script timeout");timedOut=true;clean();cb(new errors.RequestTimeout)}function error(){opts.debug("JSONP: Script error");if(done||timedOut){return}clean();cb(new errors.JSONPScriptError)}}},{"../errors":190}],187:[function(require,module,exports){module.exports=algoliasearch;var inherits=require("inherits");var Promise=window.Promise||require("es6-promise").Promise;var AlgoliaSearch=require("../../AlgoliaSearch");var errors=require("../../errors");var inlineHeaders=require("../inline-headers");var JSONPRequest=require("../JSONP-request");function algoliasearch(applicationID,apiKey,opts){var cloneDeep=require("lodash-compat/lang/cloneDeep");var getDocumentProtocol=require("../get-document-protocol");opts=cloneDeep(opts||{});if(opts.protocol===undefined){opts.protocol=getDocumentProtocol()}opts._ua=opts._ua||algoliasearch.ua;return new AlgoliaSearchBrowser(applicationID,apiKey,opts)}algoliasearch.version=require("../../version.json");algoliasearch.ua="Algolia for vanilla JavaScript "+algoliasearch.version;window.__algolia={debug:require("debug"),algoliasearch:algoliasearch};var support={hasXMLHttpRequest:"XMLHttpRequest"in window,hasXDomainRequest:"XDomainRequest"in window,cors:"withCredentials"in new XMLHttpRequest,timeout:"timeout"in new XMLHttpRequest};function AlgoliaSearchBrowser(){AlgoliaSearch.apply(this,arguments)}inherits(AlgoliaSearchBrowser,AlgoliaSearch);AlgoliaSearchBrowser.prototype._request=function(url,opts){return new Promise(function(resolve,reject){if(!support.cors&&!support.hasXDomainRequest){reject(new errors.Network("CORS not supported"));return}url=inlineHeaders(url,opts.headers);var body=opts.body;var req=support.cors?new XMLHttpRequest:new XDomainRequest;var ontimeout;var timedOut;if(req instanceof XMLHttpRequest){req.open(opts.method,url,true)}else{req.open(opts.method,url)}if(support.cors){if(body){if(opts.method==="POST"){req.setRequestHeader("content-type","application/x-www-form-urlencoded")}else{req.setRequestHeader("content-type","application/json")}}req.setRequestHeader("accept","application/json")}req.onprogress=function noop(){};req.onload=load;req.onerror=error;if(support.timeout){req.timeout=opts.timeout;req.ontimeout=timeout}else{ontimeout=setTimeout(timeout,opts.timeout)}req.send(body);function load(){if(timedOut){return}if(!support.timeout){clearTimeout(ontimeout)}var out;try{out={body:JSON.parse(req.responseText),statusCode:req.status,headers:req.getAllResponseHeaders&&req.getAllResponseHeaders()||{}}}catch(e){out=new errors.UnparsableJSON({more:req.responseText})}if(out instanceof errors.UnparsableJSON){reject(out)}else{resolve(out)}}function error(event){if(timedOut){return}if(!support.timeout){clearTimeout(ontimeout)}reject(new errors.Network({more:event}))}function timeout(){if(!support.timeout){timedOut=true;req.abort()}reject(new errors.RequestTimeout)}})};AlgoliaSearchBrowser.prototype._request.fallback=function(url,opts){url=inlineHeaders(url,opts.headers);return new Promise(function(resolve,reject){JSONPRequest(url,opts,function JSONPRequestDone(err,content){if(err){reject(err);return}resolve(content)})})};AlgoliaSearchBrowser.prototype._promise={reject:function(val){return Promise.reject(val)},resolve:function(val){return Promise.resolve(val)},delay:function(ms){return new Promise(function(resolve){setTimeout(resolve,ms)})}}},{"../../AlgoliaSearch":184,"../../errors":190,"../../version.json":191,"../JSONP-request":186,"../get-document-protocol":188,"../inline-headers":189,debug:125,"es6-promise":128,inherits:129,"lodash-compat/lang/cloneDeep":167}],188:[function(require,module,exports){module.exports=getDocumentProtocol;function getDocumentProtocol(){var protocol=window.document.location.protocol;if(protocol!=="http:"&&protocol!=="https:"){protocol="http:"}return protocol}},{}],189:[function(require,module,exports){module.exports=inlineHeaders;var querystring=require("querystring");function inlineHeaders(url,headers){if(/\?/.test(url)){url+="&"}else{url+="?"}return url+querystring.encode(headers)}},{querystring:197}],190:[function(require,module,exports){var inherits=require("inherits");function AlgoliaSearchError(message,extraProperties){var forEach=require("lodash-compat/collection/forEach");var error=this;if(typeof Error.captureStackTrace==="function"){Error.captureStackTrace(this,this.constructor)}else{error.stack=(new Error).stack||"Cannot get a stacktrace, browser is too old"}this.name=this.constructor.name;this.message=message||"Unknown error";if(extraProperties){forEach(extraProperties,function addToErrorObject(value,key){error[key]=value})}}inherits(AlgoliaSearchError,Error);function createCustomError(name,message){function AlgoliaSearchCustomError(){var args=Array.prototype.slice.call(arguments,0);if(typeof args[0]!=="string"){args.unshift(message)}AlgoliaSearchError.apply(this,args);this.name="AlgoliaSearch"+name+"Error"}inherits(AlgoliaSearchCustomError,AlgoliaSearchError);return AlgoliaSearchCustomError}module.exports={AlgoliaSearchError:AlgoliaSearchError,UnparsableJSON:createCustomError("UnparsableJSON","Could not parse the incoming response as JSON, see err.more for details"),RequestTimeout:createCustomError("RequestTimeout","Request timedout before getting a response"),Network:createCustomError("Network","Network issue, see err.more for details"),JSONPScriptFail:createCustomError("JSONPScriptFail","<script> was loaded but did not call our provided callback"),JSONPScriptError:createCustomError("JSONPScriptError","<script> unable to load due to an `error` event on it"),Unknown:createCustomError("Unknown","Unknown error occured")}},{inherits:129,"lodash-compat/collection/forEach":130}],191:[function(require,module,exports){module.exports="3.6.3"},{}],192:[function(require,module,exports){function EventEmitter(){this._events=this._events||{};this._maxListeners=this._maxListeners||undefined}module.exports=EventEmitter;EventEmitter.EventEmitter=EventEmitter;EventEmitter.prototype._events=undefined;EventEmitter.prototype._maxListeners=undefined;EventEmitter.defaultMaxListeners=10;EventEmitter.prototype.setMaxListeners=function(n){if(!isNumber(n)||n<0||isNaN(n))throw TypeError("n must be a positive number");this._maxListeners=n;return this};EventEmitter.prototype.emit=function(type){var er,handler,len,args,i,listeners;if(!this._events)this._events={};if(type==="error"){if(!this._events.error||isObject(this._events.error)&&!this._events.error.length){er=arguments[1];if(er instanceof Error){throw er}throw TypeError('Uncaught, unspecified "error" event.')}}handler=this._events[type];if(isUndefined(handler))return false;if(isFunction(handler)){switch(arguments.length){case 1:handler.call(this);break;case 2:handler.call(this,arguments[1]);break;case 3:handler.call(this,arguments[1],arguments[2]);break;default:len=arguments.length;args=new Array(len-1);for(i=1;i<len;i++)args[i-1]=arguments[i];handler.apply(this,args)}}else if(isObject(handler)){len=arguments.length;args=new Array(len-1);for(i=1;i<len;i++)args[i-1]=arguments[i];listeners=handler.slice();len=listeners.length;for(i=0;i<len;i++)listeners[i].apply(this,args)}return true};EventEmitter.prototype.addListener=function(type,listener){var m;if(!isFunction(listener))throw TypeError("listener must be a function");if(!this._events)this._events={};if(this._events.newListener)this.emit("newListener",type,isFunction(listener.listener)?listener.listener:listener);if(!this._events[type])this._events[type]=listener;else if(isObject(this._events[type]))this._events[type].push(listener);else this._events[type]=[this._events[type],listener];if(isObject(this._events[type])&&!this._events[type].warned){var m;if(!isUndefined(this._maxListeners)){m=this._maxListeners}else{m=EventEmitter.defaultMaxListeners}if(m&&m>0&&this._events[type].length>m){this._events[type].warned=true;console.error("(node) warning: possible EventEmitter memory "+"leak detected. %d listeners added. "+"Use emitter.setMaxListeners() to increase limit.",this._events[type].length);if(typeof console.trace==="function"){console.trace()}}}return this};EventEmitter.prototype.on=EventEmitter.prototype.addListener;EventEmitter.prototype.once=function(type,listener){if(!isFunction(listener))throw TypeError("listener must be a function");var fired=false;function g(){this.removeListener(type,g);if(!fired){fired=true;listener.apply(this,arguments)}}g.listener=listener;this.on(type,g);return this};EventEmitter.prototype.removeListener=function(type,listener){var list,position,length,i;if(!isFunction(listener))throw TypeError("listener must be a function");if(!this._events||!this._events[type])return this;list=this._events[type];length=list.length;position=-1;if(list===listener||isFunction(list.listener)&&list.listener===listener){delete this._events[type];if(this._events.removeListener)this.emit("removeListener",type,listener)}else if(isObject(list)){for(i=length;i-->0;){if(list[i]===listener||list[i].listener&&list[i].listener===listener){position=i;break}}if(position<0)return this;if(list.length===1){list.length=0;delete this._events[type]}else{list.splice(position,1)}if(this._events.removeListener)this.emit("removeListener",type,listener)}return this};EventEmitter.prototype.removeAllListeners=function(type){var key,listeners;if(!this._events)return this;if(!this._events.removeListener){if(arguments.length===0)this._events={};else if(this._events[type])delete this._events[type];return this}if(arguments.length===0){for(key in this._events){if(key==="removeListener")continue;this.removeAllListeners(key)}this.removeAllListeners("removeListener");this._events={};return this}listeners=this._events[type];if(isFunction(listeners)){this.removeListener(type,listeners)}else{while(listeners.length)this.removeListener(type,listeners[listeners.length-1])}delete this._events[type];return this};EventEmitter.prototype.listeners=function(type){var ret;if(!this._events||!this._events[type])ret=[];else if(isFunction(this._events[type]))ret=[this._events[type]];else ret=this._events[type].slice();return ret};EventEmitter.listenerCount=function(emitter,type){var ret;if(!emitter._events||!emitter._events[type])ret=0;else if(isFunction(emitter._events[type]))ret=1;else ret=emitter._events[type].length;return ret};function isFunction(arg){return typeof arg==="function"}function isNumber(arg){return typeof arg==="number"}function isObject(arg){return typeof arg==="object"&&arg!==null}function isUndefined(arg){return arg===void 0}},{}],193:[function(require,module,exports){arguments[4][129][0].apply(exports,arguments)},{dup:129}],194:[function(require,module,exports){var process=module.exports={};var queue=[];var draining=false;var currentQueue;var queueIndex=-1;function cleanUpNextTick(){draining=false;if(currentQueue.length){queue=currentQueue.concat(queue)}else{queueIndex=-1}if(queue.length){drainQueue()}}function drainQueue(){if(draining){return}var timeout=setTimeout(cleanUpNextTick);draining=true;var len=queue.length;while(len){currentQueue=queue;queue=[];while(++queueIndex<len){currentQueue[queueIndex].run()}queueIndex=-1;len=queue.length}currentQueue=null;draining=false;clearTimeout(timeout)}process.nextTick=function(fun){var args=new Array(arguments.length-1);if(arguments.length>1){for(var i=1;i<arguments.length;i++){args[i-1]=arguments[i]}}queue.push(new Item(fun,args));if(queue.length===1&&!draining){setTimeout(drainQueue,0)}};function Item(fun,array){this.fun=fun;this.array=array}Item.prototype.run=function(){this.fun.apply(null,this.array)};process.title="browser";process.browser=true;process.env={};process.argv=[];process.version="";process.versions={};function noop(){}process.on=noop;process.addListener=noop;process.once=noop;process.off=noop;process.removeListener=noop;process.removeAllListeners=noop;process.emit=noop;process.binding=function(name){throw new Error("process.binding is not supported")};process.cwd=function(){return"/"};process.chdir=function(dir){throw new Error("process.chdir is not supported")};process.umask=function(){return 0}},{}],195:[function(require,module,exports){"use strict";function hasOwnProperty(obj,prop){return Object.prototype.hasOwnProperty.call(obj,prop)}module.exports=function(qs,sep,eq,options){sep=sep||"&";eq=eq||"=";var obj={};if(typeof qs!=="string"||qs.length===0){return obj}var regexp=/\+/g;qs=qs.split(sep);var maxKeys=1e3;if(options&&typeof options.maxKeys==="number"){maxKeys=options.maxKeys}var len=qs.length;if(maxKeys>0&&len>maxKeys){len=maxKeys}for(var i=0;i<len;++i){var x=qs[i].replace(regexp,"%20"),idx=x.indexOf(eq),kstr,vstr,k,v;if(idx>=0){kstr=x.substr(0,idx);vstr=x.substr(idx+1)}else{kstr=x;vstr=""}k=decodeURIComponent(kstr);v=decodeURIComponent(vstr);if(!hasOwnProperty(obj,k)){obj[k]=v}else if(isArray(obj[k])){obj[k].push(v)}else{obj[k]=[obj[k],v]}}return obj};var isArray=Array.isArray||function(xs){return Object.prototype.toString.call(xs)==="[object Array]"}},{}],196:[function(require,module,exports){"use strict";var stringifyPrimitive=function(v){switch(typeof v){case"string":return v;case"boolean":return v?"true":"false";case"number":return isFinite(v)?v:"";default:return""}};module.exports=function(obj,sep,eq,name){sep=sep||"&";eq=eq||"=";if(obj===null){obj=undefined}if(typeof obj==="object"){return map(objectKeys(obj),function(k){var ks=encodeURIComponent(stringifyPrimitive(k))+eq;if(isArray(obj[k])){return map(obj[k],function(v){return ks+encodeURIComponent(stringifyPrimitive(v))}).join(sep)}else{return ks+encodeURIComponent(stringifyPrimitive(obj[k]))}}).join(sep)}if(!name)return"";return encodeURIComponent(stringifyPrimitive(name))+eq+encodeURIComponent(stringifyPrimitive(obj))};var isArray=Array.isArray||function(xs){return Object.prototype.toString.call(xs)==="[object Array]"};function map(xs,f){if(xs.map)return xs.map(f);var res=[];for(var i=0;i<xs.length;i++){res.push(f(xs[i],i))}return res}var objectKeys=Object.keys||function(obj){var res=[];for(var key in obj){if(Object.prototype.hasOwnProperty.call(obj,key))res.push(key)}return res}},{}],197:[function(require,module,exports){"use strict";exports.decode=exports.parse=require("./decode");exports.encode=exports.stringify=require("./encode")},{"./decode":195,"./encode":196}],198:[function(require,module,exports){module.exports=function isBuffer(arg){return arg&&typeof arg==="object"&&typeof arg.copy==="function"&&typeof arg.fill==="function"&&typeof arg.readUInt8==="function"}},{}],199:[function(require,module,exports){(function(process,global){var formatRegExp=/%[sdj%]/g;exports.format=function(f){if(!isString(f)){var objects=[];for(var i=0;i<arguments.length;i++){objects.push(inspect(arguments[i]))}return objects.join(" ")}var i=1;var args=arguments;var len=args.length;var str=String(f).replace(formatRegExp,function(x){if(x==="%%")return"%";if(i>=len)return x;switch(x){case"%s":return String(args[i++]);case"%d":return Number(args[i++]);case"%j":try{return JSON.stringify(args[i++])}catch(_){return"[Circular]"}default:return x}});for(var x=args[i];i<len;x=args[++i]){if(isNull(x)||!isObject(x)){str+=" "+x}else{str+=" "+inspect(x)}}return str};exports.deprecate=function(fn,msg){if(isUndefined(global.process)){return function(){return exports.deprecate(fn,msg).apply(this,arguments)}}if(process.noDeprecation===true){return fn}var warned=false;function deprecated(){if(!warned){if(process.throwDeprecation){throw new Error(msg)}else if(process.traceDeprecation){console.trace(msg)}else{console.error(msg)}warned=true}return fn.apply(this,arguments)}return deprecated};var debugs={};var debugEnviron;exports.debuglog=function(set){if(isUndefined(debugEnviron))debugEnviron=process.env.NODE_DEBUG||"";set=set.toUpperCase();if(!debugs[set]){if(new RegExp("\\b"+set+"\\b","i").test(debugEnviron)){var pid=process.pid;debugs[set]=function(){var msg=exports.format.apply(exports,arguments);console.error("%s %d: %s",set,pid,msg)}}else{debugs[set]=function(){}}}return debugs[set]};function inspect(obj,opts){var ctx={seen:[],stylize:stylizeNoColor};if(arguments.length>=3)ctx.depth=arguments[2];if(arguments.length>=4)ctx.colors=arguments[3];if(isBoolean(opts)){ctx.showHidden=opts}else if(opts){exports._extend(ctx,opts)}if(isUndefined(ctx.showHidden))ctx.showHidden=false;if(isUndefined(ctx.depth))ctx.depth=2;if(isUndefined(ctx.colors))ctx.colors=false;if(isUndefined(ctx.customInspect))ctx.customInspect=true;if(ctx.colors)ctx.stylize=stylizeWithColor;return formatValue(ctx,obj,ctx.depth)}exports.inspect=inspect;inspect.colors={bold:[1,22],italic:[3,23],underline:[4,24],inverse:[7,27],white:[37,39],grey:[90,39],black:[30,39],blue:[34,39],cyan:[36,39],green:[32,39],magenta:[35,39],red:[31,39],yellow:[33,39]};inspect.styles={special:"cyan",number:"yellow","boolean":"yellow",undefined:"grey","null":"bold",string:"green",date:"magenta",regexp:"red"};function stylizeWithColor(str,styleType){var style=inspect.styles[styleType];if(style){return"["+inspect.colors[style][0]+"m"+str+"["+inspect.colors[style][1]+"m"}else{return str}}function stylizeNoColor(str,styleType){return str}function arrayToHash(array){var hash={};array.forEach(function(val,idx){hash[val]=true});return hash}function formatValue(ctx,value,recurseTimes){if(ctx.customInspect&&value&&isFunction(value.inspect)&&value.inspect!==exports.inspect&&!(value.constructor&&value.constructor.prototype===value)){var ret=value.inspect(recurseTimes,ctx);if(!isString(ret)){ret=formatValue(ctx,ret,recurseTimes)}return ret}var primitive=formatPrimitive(ctx,value);if(primitive){return primitive}var keys=Object.keys(value);var visibleKeys=arrayToHash(keys);if(ctx.showHidden){keys=Object.getOwnPropertyNames(value)}if(isError(value)&&(keys.indexOf("message")>=0||keys.indexOf("description")>=0)){return formatError(value)}if(keys.length===0){if(isFunction(value)){var name=value.name?": "+value.name:"";return ctx.stylize("[Function"+name+"]","special")}if(isRegExp(value)){return ctx.stylize(RegExp.prototype.toString.call(value),"regexp")}if(isDate(value)){return ctx.stylize(Date.prototype.toString.call(value),"date")}if(isError(value)){return formatError(value)}}var base="",array=false,braces=["{","}"];if(isArray(value)){array=true;braces=["[","]"]}if(isFunction(value)){var n=value.name?": "+value.name:"";base=" [Function"+n+"]"}if(isRegExp(value)){base=" "+RegExp.prototype.toString.call(value)}if(isDate(value)){base=" "+Date.prototype.toUTCString.call(value)}if(isError(value)){base=" "+formatError(value)}if(keys.length===0&&(!array||value.length==0)){return braces[0]+base+braces[1]}if(recurseTimes<0){if(isRegExp(value)){return ctx.stylize(RegExp.prototype.toString.call(value),"regexp")}else{return ctx.stylize("[Object]","special")}}ctx.seen.push(value);var output;if(array){output=formatArray(ctx,value,recurseTimes,visibleKeys,keys)}else{output=keys.map(function(key){return formatProperty(ctx,value,recurseTimes,visibleKeys,key,array)})}ctx.seen.pop();return reduceToSingleString(output,base,braces)}function formatPrimitive(ctx,value){if(isUndefined(value))return ctx.stylize("undefined","undefined");if(isString(value)){var simple="'"+JSON.stringify(value).replace(/^"|"$/g,"").replace(/'/g,"\\'").replace(/\\"/g,'"')+"'";return ctx.stylize(simple,"string")}if(isNumber(value))return ctx.stylize(""+value,"number");if(isBoolean(value))return ctx.stylize(""+value,"boolean");if(isNull(value))return ctx.stylize("null","null")}function formatError(value){return"["+Error.prototype.toString.call(value)+"]"}function formatArray(ctx,value,recurseTimes,visibleKeys,keys){var output=[];for(var i=0,l=value.length;i<l;++i){if(hasOwnProperty(value,String(i))){output.push(formatProperty(ctx,value,recurseTimes,visibleKeys,String(i),true))}else{output.push("")}}keys.forEach(function(key){if(!key.match(/^\d+$/)){output.push(formatProperty(ctx,value,recurseTimes,visibleKeys,key,true))}});return output}function formatProperty(ctx,value,recurseTimes,visibleKeys,key,array){var name,str,desc;desc=Object.getOwnPropertyDescriptor(value,key)||{value:value[key]};if(desc.get){if(desc.set){str=ctx.stylize("[Getter/Setter]","special")}else{str=ctx.stylize("[Getter]","special")}}else{if(desc.set){str=ctx.stylize("[Setter]","special")}}if(!hasOwnProperty(visibleKeys,key)){name="["+key+"]"}if(!str){if(ctx.seen.indexOf(desc.value)<0){if(isNull(recurseTimes)){str=formatValue(ctx,desc.value,null)}else{str=formatValue(ctx,desc.value,recurseTimes-1)}if(str.indexOf("\n")>-1){if(array){str=str.split("\n").map(function(line){return" "+line}).join("\n").substr(2)}else{str="\n"+str.split("\n").map(function(line){return" "+line}).join("\n")}}}else{str=ctx.stylize("[Circular]","special")}}if(isUndefined(name)){if(array&&key.match(/^\d+$/)){return str}name=JSON.stringify(""+key);if(name.match(/^"([a-zA-Z_][a-zA-Z_0-9]*)"$/)){name=name.substr(1,name.length-2);name=ctx.stylize(name,"name")}else{name=name.replace(/'/g,"\\'").replace(/\\"/g,'"').replace(/(^"|"$)/g,"'");name=ctx.stylize(name,"string")}}return name+": "+str}function reduceToSingleString(output,base,braces){var numLinesEst=0;var length=output.reduce(function(prev,cur){numLinesEst++;if(cur.indexOf("\n")>=0)numLinesEst++;return prev+cur.replace(/\u001b\[\d\d?m/g,"").length+1},0);if(length>60){return braces[0]+(base===""?"":base+"\n ")+" "+output.join(",\n ")+" "+braces[1]}return braces[0]+base+" "+output.join(", ")+" "+braces[1]}function isArray(ar){return Array.isArray(ar)}exports.isArray=isArray;function isBoolean(arg){return typeof arg==="boolean"}exports.isBoolean=isBoolean;function isNull(arg){return arg===null}exports.isNull=isNull;function isNullOrUndefined(arg){return arg==null}exports.isNullOrUndefined=isNullOrUndefined;function isNumber(arg){return typeof arg==="number"}exports.isNumber=isNumber;function isString(arg){return typeof arg==="string"}exports.isString=isString;function isSymbol(arg){return typeof arg==="symbol"}exports.isSymbol=isSymbol;function isUndefined(arg){return arg===void 0}exports.isUndefined=isUndefined;function isRegExp(re){return isObject(re)&&objectToString(re)==="[object RegExp]"}exports.isRegExp=isRegExp;function isObject(arg){return typeof arg==="object"&&arg!==null}exports.isObject=isObject;function isDate(d){return isObject(d)&&objectToString(d)==="[object Date]"}exports.isDate=isDate;function isError(e){return isObject(e)&&(objectToString(e)==="[object Error]"||e instanceof Error)}exports.isError=isError;function isFunction(arg){return typeof arg==="function"}exports.isFunction=isFunction;function isPrimitive(arg){return arg===null||typeof arg==="boolean"||typeof arg==="number"||typeof arg==="string"||typeof arg==="symbol"||typeof arg==="undefined"}exports.isPrimitive=isPrimitive;exports.isBuffer=require("./support/isBuffer");function objectToString(o){return Object.prototype.toString.call(o)}function pad(n){return n<10?"0"+n.toString(10):n.toString(10)}var months=["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"];function timestamp(){var d=new Date;var time=[pad(d.getHours()),pad(d.getMinutes()),pad(d.getSeconds())].join(":");return[d.getDate(),months[d.getMonth()],time].join(" ")}exports.log=function(){console.log("%s - %s",timestamp(),exports.format.apply(exports,arguments))};exports.inherits=require("inherits");exports._extend=function(origin,add){if(!add||!isObject(add))return origin;var keys=Object.keys(add);var i=keys.length;while(i--){origin[keys[i]]=add[keys[i]]}return origin};function hasOwnProperty(obj,prop){return Object.prototype.hasOwnProperty.call(obj,prop)}}).call(this,require("_process"),typeof global!=="undefined"?global:typeof self!=="undefined"?self:typeof window!=="undefined"?window:{})},{"./support/isBuffer":198,_process:194,inherits:193}],200:[function(require,module,exports){(function(Hogan){var rIsWhitespace=/\S/,rQuot=/\"/g,rNewline=/\n/g,rCr=/\r/g,rSlash=/\\/g,rLineSep=/\u2028/,rParagraphSep=/\u2029/;Hogan.tags={"#":1,"^":2,"<":3,$:4,"/":5,"!":6,">":7,"=":8,_v:9,"{":10,"&":11,_t:12};Hogan.scan=function scan(text,delimiters){var len=text.length,IN_TEXT=0,IN_TAG_TYPE=1,IN_TAG=2,state=IN_TEXT,tagType=null,tag=null,buf="",tokens=[],seenTag=false,i=0,lineStart=0,otag="{{",ctag="}}";function addBuf(){if(buf.length>0){tokens.push({tag:"_t",text:new String(buf)});buf=""}}function lineIsWhitespace(){var isAllWhitespace=true;for(var j=lineStart;j<tokens.length;j++){isAllWhitespace=Hogan.tags[tokens[j].tag]<Hogan.tags["_v"]||tokens[j].tag=="_t"&&tokens[j].text.match(rIsWhitespace)===null;if(!isAllWhitespace){return false}}return isAllWhitespace}function filterLine(haveSeenTag,noNewLine){addBuf();if(haveSeenTag&&lineIsWhitespace()){for(var j=lineStart,next;j<tokens.length;j++){if(tokens[j].text){if((next=tokens[j+1])&&next.tag==">"){next.indent=tokens[j].text.toString()}tokens.splice(j,1)}}}else if(!noNewLine){tokens.push({tag:"\n"})}seenTag=false;lineStart=tokens.length}function changeDelimiters(text,index){var close="="+ctag,closeIndex=text.indexOf(close,index),delimiters=trim(text.substring(text.indexOf("=",index)+1,closeIndex)).split(" ");otag=delimiters[0];ctag=delimiters[delimiters.length-1];return closeIndex+close.length-1}if(delimiters){delimiters=delimiters.split(" ");otag=delimiters[0];ctag=delimiters[1]}for(i=0;i<len;i++){if(state==IN_TEXT){if(tagChange(otag,text,i)){--i;addBuf();state=IN_TAG_TYPE}else{if(text.charAt(i)=="\n"){filterLine(seenTag)}else{buf+=text.charAt(i)}}}else if(state==IN_TAG_TYPE){i+=otag.length-1;tag=Hogan.tags[text.charAt(i+1)];tagType=tag?text.charAt(i+1):"_v";if(tagType=="="){i=changeDelimiters(text,i);state=IN_TEXT}else{if(tag){i++}state=IN_TAG}seenTag=i}else{if(tagChange(ctag,text,i)){tokens.push({tag:tagType,n:trim(buf),otag:otag,ctag:ctag,i:tagType=="/"?seenTag-otag.length:i+ctag.length});buf="";i+=ctag.length-1;state=IN_TEXT;if(tagType=="{"){if(ctag=="}}"){i++}else{cleanTripleStache(tokens[tokens.length-1])}}}else{buf+=text.charAt(i)}}}filterLine(seenTag,true);return tokens};function cleanTripleStache(token){if(token.n.substr(token.n.length-1)==="}"){token.n=token.n.substring(0,token.n.length-1)}}function trim(s){if(s.trim){return s.trim()}return s.replace(/^\s*|\s*$/g,"")}function tagChange(tag,text,index){if(text.charAt(index)!=tag.charAt(0)){return false}for(var i=1,l=tag.length;i<l;i++){if(text.charAt(index+i)!=tag.charAt(i)){return false}}return true}var allowedInSuper={_t:true,"\n":true,$:true,"/":true};function buildTree(tokens,kind,stack,customTags){var instructions=[],opener=null,tail=null,token=null;tail=stack[stack.length-1];while(tokens.length>0){token=tokens.shift();if(tail&&tail.tag=="<"&&!(token.tag in allowedInSuper)){throw new Error("Illegal content in < super tag.")}if(Hogan.tags[token.tag]<=Hogan.tags["$"]||isOpener(token,customTags)){stack.push(token);token.nodes=buildTree(tokens,token.tag,stack,customTags)}else if(token.tag=="/"){if(stack.length===0){throw new Error("Closing tag without opener: /"+token.n)}opener=stack.pop();if(token.n!=opener.n&&!isCloser(token.n,opener.n,customTags)){throw new Error("Nesting error: "+opener.n+" vs. "+token.n)}opener.end=token.i;return instructions}else if(token.tag=="\n"){token.last=tokens.length==0||tokens[0].tag=="\n"}instructions.push(token)}if(stack.length>0){throw new Error("missing closing tag: "+stack.pop().n)}return instructions}function isOpener(token,tags){for(var i=0,l=tags.length;i<l;i++){if(tags[i].o==token.n){token.tag="#";return true}}}function isCloser(close,open,tags){for(var i=0,l=tags.length;i<l;i++){
11
- if(tags[i].c==close&&tags[i].o==open){return true}}}function stringifySubstitutions(obj){var items=[];for(var key in obj){items.push('"'+esc(key)+'": function(c,p,t,i) {'+obj[key]+"}")}return"{ "+items.join(",")+" }"}function stringifyPartials(codeObj){var partials=[];for(var key in codeObj.partials){partials.push('"'+esc(key)+'":{name:"'+esc(codeObj.partials[key].name)+'", '+stringifyPartials(codeObj.partials[key])+"}")}return"partials: {"+partials.join(",")+"}, subs: "+stringifySubstitutions(codeObj.subs)}Hogan.stringify=function(codeObj,text,options){return"{code: function (c,p,i) { "+Hogan.wrapMain(codeObj.code)+" },"+stringifyPartials(codeObj)+"}"};var serialNo=0;Hogan.generate=function(tree,text,options){serialNo=0;var context={code:"",subs:{},partials:{}};Hogan.walk(tree,context);if(options.asString){return this.stringify(context,text,options)}return this.makeTemplate(context,text,options)};Hogan.wrapMain=function(code){return'var t=this;t.b(i=i||"");'+code+"return t.fl();"};Hogan.template=Hogan.Template;Hogan.makeTemplate=function(codeObj,text,options){var template=this.makePartials(codeObj);template.code=new Function("c","p","i",this.wrapMain(codeObj.code));return new this.template(template,text,this,options)};Hogan.makePartials=function(codeObj){var key,template={subs:{},partials:codeObj.partials,name:codeObj.name};for(key in template.partials){template.partials[key]=this.makePartials(template.partials[key])}for(key in codeObj.subs){template.subs[key]=new Function("c","p","t","i",codeObj.subs[key])}return template};function esc(s){return s.replace(rSlash,"\\\\").replace(rQuot,'\\"').replace(rNewline,"\\n").replace(rCr,"\\r").replace(rLineSep,"\\u2028").replace(rParagraphSep,"\\u2029")}function chooseMethod(s){return~s.indexOf(".")?"d":"f"}function createPartial(node,context){var prefix="<"+(context.prefix||"");var sym=prefix+node.n+serialNo++;context.partials[sym]={name:node.n,partials:{}};context.code+='t.b(t.rp("'+esc(sym)+'",c,p,"'+(node.indent||"")+'"));';return sym}Hogan.codegen={"#":function(node,context){context.code+="if(t.s(t."+chooseMethod(node.n)+'("'+esc(node.n)+'",c,p,1),'+"c,p,0,"+node.i+","+node.end+',"'+node.otag+" "+node.ctag+'")){'+"t.rs(c,p,"+"function(c,p,t){";Hogan.walk(node.nodes,context);context.code+="});c.pop();}"},"^":function(node,context){context.code+="if(!t.s(t."+chooseMethod(node.n)+'("'+esc(node.n)+'",c,p,1),c,p,1,0,0,"")){';Hogan.walk(node.nodes,context);context.code+="};"},">":createPartial,"<":function(node,context){var ctx={partials:{},code:"",subs:{},inPartial:true};Hogan.walk(node.nodes,ctx);var template=context.partials[createPartial(node,context)];template.subs=ctx.subs;template.partials=ctx.partials},$:function(node,context){var ctx={subs:{},code:"",partials:context.partials,prefix:node.n};Hogan.walk(node.nodes,ctx);context.subs[node.n]=ctx.code;if(!context.inPartial){context.code+='t.sub("'+esc(node.n)+'",c,p,i);'}},"\n":function(node,context){context.code+=write('"\\n"'+(node.last?"":" + i"))},_v:function(node,context){context.code+="t.b(t.v(t."+chooseMethod(node.n)+'("'+esc(node.n)+'",c,p,0)));'},_t:function(node,context){context.code+=write('"'+esc(node.text)+'"')},"{":tripleStache,"&":tripleStache};function tripleStache(node,context){context.code+="t.b(t.t(t."+chooseMethod(node.n)+'("'+esc(node.n)+'",c,p,0)));'}function write(s){return"t.b("+s+");"}Hogan.walk=function(nodelist,context){var func;for(var i=0,l=nodelist.length;i<l;i++){func=Hogan.codegen[nodelist[i].tag];func&&func(nodelist[i],context)}return context};Hogan.parse=function(tokens,text,options){options=options||{};return buildTree(tokens,"",[],options.sectionTags||[])};Hogan.cache={};Hogan.cacheKey=function(text,options){return[text,!!options.asString,!!options.disableLambda,options.delimiters,!!options.modelGet].join("||")};Hogan.compile=function(text,options){options=options||{};var key=Hogan.cacheKey(text,options);var template=this.cache[key];if(template){var partials=template.partials;for(var name in partials){delete partials[name].instance}return template}template=this.generate(this.parse(this.scan(text,options.delimiters),text,options),text,options);return this.cache[key]=template}})(typeof exports!=="undefined"?exports:Hogan)},{}],201:[function(require,module,exports){var Hogan=require("./compiler");Hogan.Template=require("./template").Template;Hogan.template=Hogan.Template;module.exports=Hogan},{"./compiler":200,"./template":202}],202:[function(require,module,exports){var Hogan={};(function(Hogan){Hogan.Template=function(codeObj,text,compiler,options){codeObj=codeObj||{};this.r=codeObj.code||this.r;this.c=compiler;this.options=options||{};this.text=text||"";this.partials=codeObj.partials||{};this.subs=codeObj.subs||{};this.buf=""};Hogan.Template.prototype={r:function(context,partials,indent){return""},v:hoganEscape,t:coerceToString,render:function render(context,partials,indent){return this.ri([context],partials||{},indent)},ri:function(context,partials,indent){return this.r(context,partials,indent)},ep:function(symbol,partials){var partial=this.partials[symbol];var template=partials[partial.name];if(partial.instance&&partial.base==template){return partial.instance}if(typeof template=="string"){if(!this.c){throw new Error("No compiler available.")}template=this.c.compile(template,this.options)}if(!template){return null}this.partials[symbol].base=template;if(partial.subs){if(!partials.stackText)partials.stackText={};for(key in partial.subs){if(!partials.stackText[key]){partials.stackText[key]=this.activeSub!==undefined&&partials.stackText[this.activeSub]?partials.stackText[this.activeSub]:this.text}}template=createSpecializedPartial(template,partial.subs,partial.partials,this.stackSubs,this.stackPartials,partials.stackText)}this.partials[symbol].instance=template;return template},rp:function(symbol,context,partials,indent){var partial=this.ep(symbol,partials);if(!partial){return""}return partial.ri(context,partials,indent)},rs:function(context,partials,section){var tail=context[context.length-1];if(!isArray(tail)){section(context,partials,this);return}for(var i=0;i<tail.length;i++){context.push(tail[i]);section(context,partials,this);context.pop()}},s:function(val,ctx,partials,inverted,start,end,tags){var pass;if(isArray(val)&&val.length===0){return false}if(typeof val=="function"){val=this.ms(val,ctx,partials,inverted,start,end,tags)}pass=!!val;if(!inverted&&pass&&ctx){ctx.push(typeof val=="object"?val:ctx[ctx.length-1])}return pass},d:function(key,ctx,partials,returnFound){var found,names=key.split("."),val=this.f(names[0],ctx,partials,returnFound),doModelGet=this.options.modelGet,cx=null;if(key==="."&&isArray(ctx[ctx.length-2])){val=ctx[ctx.length-1]}else{for(var i=1;i<names.length;i++){found=findInScope(names[i],val,doModelGet);if(found!==undefined){cx=val;val=found}else{val=""}}}if(returnFound&&!val){return false}if(!returnFound&&typeof val=="function"){ctx.push(cx);val=this.mv(val,ctx,partials);ctx.pop()}return val},f:function(key,ctx,partials,returnFound){var val=false,v=null,found=false,doModelGet=this.options.modelGet;for(var i=ctx.length-1;i>=0;i--){v=ctx[i];val=findInScope(key,v,doModelGet);if(val!==undefined){found=true;break}}if(!found){return returnFound?false:""}if(!returnFound&&typeof val=="function"){val=this.mv(val,ctx,partials)}return val},ls:function(func,cx,partials,text,tags){var oldTags=this.options.delimiters;this.options.delimiters=tags;this.b(this.ct(coerceToString(func.call(cx,text)),cx,partials));this.options.delimiters=oldTags;return false},ct:function(text,cx,partials){if(this.options.disableLambda){throw new Error("Lambda features disabled.")}return this.c.compile(text,this.options).render(cx,partials)},b:function(s){this.buf+=s},fl:function(){var r=this.buf;this.buf="";return r},ms:function(func,ctx,partials,inverted,start,end,tags){var textSource,cx=ctx[ctx.length-1],result=func.call(cx);if(typeof result=="function"){if(inverted){return true}else{textSource=this.activeSub&&this.subsText&&this.subsText[this.activeSub]?this.subsText[this.activeSub]:this.text;return this.ls(result,cx,partials,textSource.substring(start,end),tags)}}return result},mv:function(func,ctx,partials){var cx=ctx[ctx.length-1];var result=func.call(cx);if(typeof result=="function"){return this.ct(coerceToString(result.call(cx)),cx,partials)}return result},sub:function(name,context,partials,indent){var f=this.subs[name];if(f){this.activeSub=name;f(context,partials,this,indent);this.activeSub=false}}};function findInScope(key,scope,doModelGet){var val;if(scope&&typeof scope=="object"){if(scope[key]!==undefined){val=scope[key]}else if(doModelGet&&scope.get&&typeof scope.get=="function"){val=scope.get(key)}}return val}function createSpecializedPartial(instance,subs,partials,stackSubs,stackPartials,stackText){function PartialTemplate(){}PartialTemplate.prototype=instance;function Substitutions(){}Substitutions.prototype=instance.subs;var key;var partial=new PartialTemplate;partial.subs=new Substitutions;partial.subsText={};partial.buf="";stackSubs=stackSubs||{};partial.stackSubs=stackSubs;partial.subsText=stackText;for(key in subs){if(!stackSubs[key])stackSubs[key]=subs[key]}for(key in stackSubs){partial.subs[key]=stackSubs[key]}stackPartials=stackPartials||{};partial.stackPartials=stackPartials;for(key in partials){if(!stackPartials[key])stackPartials[key]=partials[key]}for(key in stackPartials){partial.partials[key]=stackPartials[key]}return partial}var rAmp=/&/g,rLt=/</g,rGt=/>/g,rApos=/\'/g,rQuot=/\"/g,hChars=/[&<>\"\']/;function coerceToString(val){return String(val===null||val===undefined?"":val)}function hoganEscape(str){str=coerceToString(str);return hChars.test(str)?str.replace(rAmp,"&amp;").replace(rLt,"&lt;").replace(rGt,"&gt;").replace(rApos,"&#39;").replace(rQuot,"&quot;"):str}var isArray=Array.isArray||function(a){return Object.prototype.toString.call(a)==="[object Array]"}})(typeof exports!=="undefined"?exports:Hogan)},{}],203:[function(require,module,exports){var jQuery=require("jquery");(function($,undefined){var uuid=0,runiqueId=/^ui-id-\d+$/;$.ui=$.ui||{};$.extend($.ui,{version:"1.10.4",keyCode:{BACKSPACE:8,COMMA:188,DELETE:46,DOWN:40,END:35,ENTER:13,ESCAPE:27,HOME:36,LEFT:37,NUMPAD_ADD:107,NUMPAD_DECIMAL:110,NUMPAD_DIVIDE:111,NUMPAD_ENTER:108,NUMPAD_MULTIPLY:106,NUMPAD_SUBTRACT:109,PAGE_DOWN:34,PAGE_UP:33,PERIOD:190,RIGHT:39,SPACE:32,TAB:9,UP:38}});$.fn.extend({focus:function(orig){return function(delay,fn){return typeof delay==="number"?this.each(function(){var elem=this;setTimeout(function(){$(elem).focus();if(fn){fn.call(elem)}},delay)}):orig.apply(this,arguments)}}($.fn.focus),scrollParent:function(){var scrollParent;if($.ui.ie&&/(static|relative)/.test(this.css("position"))||/absolute/.test(this.css("position"))){scrollParent=this.parents().filter(function(){return/(relative|absolute|fixed)/.test($.css(this,"position"))&&/(auto|scroll)/.test($.css(this,"overflow")+$.css(this,"overflow-y")+$.css(this,"overflow-x"))}).eq(0)}else{scrollParent=this.parents().filter(function(){return/(auto|scroll)/.test($.css(this,"overflow")+$.css(this,"overflow-y")+$.css(this,"overflow-x"))}).eq(0)}return/fixed/.test(this.css("position"))||!scrollParent.length?$(document):scrollParent},zIndex:function(zIndex){if(zIndex!==undefined){return this.css("zIndex",zIndex)}if(this.length){var elem=$(this[0]),position,value;while(elem.length&&elem[0]!==document){position=elem.css("position");if(position==="absolute"||position==="relative"||position==="fixed"){value=parseInt(elem.css("zIndex"),10);if(!isNaN(value)&&value!==0){return value}}elem=elem.parent()}}return 0},uniqueId:function(){return this.each(function(){if(!this.id){this.id="ui-id-"+ ++uuid}})},removeUniqueId:function(){return this.each(function(){if(runiqueId.test(this.id)){$(this).removeAttr("id")}})}});function focusable(element,isTabIndexNotNaN){var map,mapName,img,nodeName=element.nodeName.toLowerCase();if("area"===nodeName){map=element.parentNode;mapName=map.name;if(!element.href||!mapName||map.nodeName.toLowerCase()!=="map"){return false}img=$("img[usemap=#"+mapName+"]")[0];return!!img&&visible(img)}return(/input|select|textarea|button|object/.test(nodeName)?!element.disabled:"a"===nodeName?element.href||isTabIndexNotNaN:isTabIndexNotNaN)&&visible(element)}function visible(element){return $.expr.filters.visible(element)&&!$(element).parents().addBack().filter(function(){return $.css(this,"visibility")==="hidden"}).length}$.extend($.expr[":"],{data:$.expr.createPseudo?$.expr.createPseudo(function(dataName){return function(elem){return!!$.data(elem,dataName)}}):function(elem,i,match){return!!$.data(elem,match[3])},focusable:function(element){return focusable(element,!isNaN($.attr(element,"tabindex")))},tabbable:function(element){var tabIndex=$.attr(element,"tabindex"),isTabIndexNaN=isNaN(tabIndex);return(isTabIndexNaN||tabIndex>=0)&&focusable(element,!isTabIndexNaN)}});if(!$("<a>").outerWidth(1).jquery){$.each(["Width","Height"],function(i,name){var side=name==="Width"?["Left","Right"]:["Top","Bottom"],type=name.toLowerCase(),orig={innerWidth:$.fn.innerWidth,innerHeight:$.fn.innerHeight,outerWidth:$.fn.outerWidth,outerHeight:$.fn.outerHeight};function reduce(elem,size,border,margin){$.each(side,function(){size-=parseFloat($.css(elem,"padding"+this))||0;if(border){size-=parseFloat($.css(elem,"border"+this+"Width"))||0}if(margin){size-=parseFloat($.css(elem,"margin"+this))||0}});return size}$.fn["inner"+name]=function(size){if(size===undefined){return orig["inner"+name].call(this)}return this.each(function(){$(this).css(type,reduce(this,size)+"px")})};$.fn["outer"+name]=function(size,margin){if(typeof size!=="number"){return orig["outer"+name].call(this,size)}return this.each(function(){$(this).css(type,reduce(this,size,true,margin)+"px")})}})}if(!$.fn.addBack){$.fn.addBack=function(selector){return this.add(selector==null?this.prevObject:this.prevObject.filter(selector))}}if($("<a>").data("a-b","a").removeData("a-b").data("a-b")){$.fn.removeData=function(removeData){return function(key){if(arguments.length){return removeData.call(this,$.camelCase(key))}else{return removeData.call(this)}}}($.fn.removeData)}$.ui.ie=!!/msie [\w.]+/.exec(navigator.userAgent.toLowerCase());$.support.selectstart="onselectstart"in document.createElement("div");$.fn.extend({disableSelection:function(){return this.bind(($.support.selectstart?"selectstart":"mousedown")+".ui-disableSelection",function(event){event.preventDefault()})},enableSelection:function(){return this.unbind(".ui-disableSelection")}});$.extend($.ui,{plugin:{add:function(module,option,set){var i,proto=$.ui[module].prototype;for(i in set){proto.plugins[i]=proto.plugins[i]||[];proto.plugins[i].push([option,set[i]])}},call:function(instance,name,args){var i,set=instance.plugins[name];if(!set||!instance.element[0].parentNode||instance.element[0].parentNode.nodeType===11){return}for(i=0;i<set.length;i++){if(instance.options[set[i][0]]){set[i][1].apply(instance.element,args)}}}},hasScroll:function(el,a){if($(el).css("overflow")==="hidden"){return false}var scroll=a&&a==="left"?"scrollLeft":"scrollTop",has=false;if(el[scroll]>0){return true}el[scroll]=1;has=el[scroll]>0;el[scroll]=0;return has}})})(jQuery)},{jquery:207}],204:[function(require,module,exports){var jQuery=require("jquery");require("./widget");(function($,undefined){var mouseHandled=false;$(document).mouseup(function(){mouseHandled=false});$.widget("ui.mouse",{version:"1.10.4",options:{cancel:"input,textarea,button,select,option",distance:1,delay:0},_mouseInit:function(){var that=this;this.element.bind("mousedown."+this.widgetName,function(event){return that._mouseDown(event)}).bind("click."+this.widgetName,function(event){if(true===$.data(event.target,that.widgetName+".preventClickEvent")){$.removeData(event.target,that.widgetName+".preventClickEvent");event.stopImmediatePropagation();return false}});this.started=false},_mouseDestroy:function(){this.element.unbind("."+this.widgetName);if(this._mouseMoveDelegate){$(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate)}},_mouseDown:function(event){if(mouseHandled){return}this._mouseStarted&&this._mouseUp(event);this._mouseDownEvent=event;var that=this,btnIsLeft=event.which===1,elIsCancel=typeof this.options.cancel==="string"&&event.target.nodeName?$(event.target).closest(this.options.cancel).length:false;if(!btnIsLeft||elIsCancel||!this._mouseCapture(event)){return true}this.mouseDelayMet=!this.options.delay;if(!this.mouseDelayMet){this._mouseDelayTimer=setTimeout(function(){that.mouseDelayMet=true},this.options.delay)}if(this._mouseDistanceMet(event)&&this._mouseDelayMet(event)){this._mouseStarted=this._mouseStart(event)!==false;if(!this._mouseStarted){event.preventDefault();return true}}if(true===$.data(event.target,this.widgetName+".preventClickEvent")){$.removeData(event.target,this.widgetName+".preventClickEvent")}this._mouseMoveDelegate=function(event){return that._mouseMove(event)};this._mouseUpDelegate=function(event){return that._mouseUp(event)};$(document).bind("mousemove."+this.widgetName,this._mouseMoveDelegate).bind("mouseup."+this.widgetName,this._mouseUpDelegate);event.preventDefault();mouseHandled=true;return true},_mouseMove:function(event){if($.ui.ie&&(!document.documentMode||document.documentMode<9)&&!event.button){return this._mouseUp(event)}if(this._mouseStarted){this._mouseDrag(event);return event.preventDefault()}if(this._mouseDistanceMet(event)&&this._mouseDelayMet(event)){this._mouseStarted=this._mouseStart(this._mouseDownEvent,event)!==false;this._mouseStarted?this._mouseDrag(event):this._mouseUp(event)}return!this._mouseStarted},_mouseUp:function(event){$(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate);if(this._mouseStarted){this._mouseStarted=false;if(event.target===this._mouseDownEvent.target){$.data(event.target,this.widgetName+".preventClickEvent",true)}this._mouseStop(event)}return false},_mouseDistanceMet:function(event){return Math.max(Math.abs(this._mouseDownEvent.pageX-event.pageX),Math.abs(this._mouseDownEvent.pageY-event.pageY))>=this.options.distance},_mouseDelayMet:function(){return this.mouseDelayMet},_mouseStart:function(){},_mouseDrag:function(){},_mouseStop:function(){},_mouseCapture:function(){return true}})})(jQuery)},{"./widget":206,jquery:207}],205:[function(require,module,exports){var jQuery=require("jquery");require("./core");require("./mouse");require("./widget");(function($,undefined){var numPages=5;$.widget("ui.slider",$.ui.mouse,{version:"1.10.4",widgetEventPrefix:"slide",options:{animate:false,distance:0,max:100,min:0,orientation:"horizontal",range:false,step:1,value:0,values:null,change:null,slide:null,start:null,stop:null},_create:function(){this._keySliding=false;this._mouseSliding=false;this._animateOff=true;this._handleIndex=null;this._detectOrientation();this._mouseInit();this.element.addClass("ui-slider"+" ui-slider-"+this.orientation+" ui-widget"+" ui-widget-content"+" ui-corner-all");this._refresh();this._setOption("disabled",this.options.disabled);this._animateOff=false},_refresh:function(){this._createRange();this._createHandles();this._setupEvents();this._refreshValue()},_createHandles:function(){var i,handleCount,options=this.options,existingHandles=this.element.find(".ui-slider-handle").addClass("ui-state-default ui-corner-all"),handle="<a class='ui-slider-handle ui-state-default ui-corner-all' href='#'></a>",handles=[];handleCount=options.values&&options.values.length||1;if(existingHandles.length>handleCount){existingHandles.slice(handleCount).remove();existingHandles=existingHandles.slice(0,handleCount)}for(i=existingHandles.length;i<handleCount;i++){handles.push(handle)}this.handles=existingHandles.add($(handles.join("")).appendTo(this.element));this.handle=this.handles.eq(0);this.handles.each(function(i){$(this).data("ui-slider-handle-index",i)})},_createRange:function(){var options=this.options,classes="";if(options.range){if(options.range===true){if(!options.values){options.values=[this._valueMin(),this._valueMin()]}else if(options.values.length&&options.values.length!==2){options.values=[options.values[0],options.values[0]]}else if($.isArray(options.values)){options.values=options.values.slice(0)}}if(!this.range||!this.range.length){this.range=$("<div></div>").appendTo(this.element);classes="ui-slider-range"+" ui-widget-header ui-corner-all"}else{this.range.removeClass("ui-slider-range-min ui-slider-range-max").css({left:"",bottom:""})}this.range.addClass(classes+(options.range==="min"||options.range==="max"?" ui-slider-range-"+options.range:""))}else{if(this.range){this.range.remove()}this.range=null}},_setupEvents:function(){var elements=this.handles.add(this.range).filter("a");this._off(elements);this._on(elements,this._handleEvents);this._hoverable(elements);this._focusable(elements)},_destroy:function(){this.handles.remove();if(this.range){this.range.remove()}this.element.removeClass("ui-slider"+" ui-slider-horizontal"+" ui-slider-vertical"+" ui-widget"+" ui-widget-content"+" ui-corner-all");this._mouseDestroy()},_mouseCapture:function(event){var position,normValue,distance,closestHandle,index,allowed,offset,mouseOverHandle,that=this,o=this.options;if(o.disabled){return false}this.elementSize={width:this.element.outerWidth(),height:this.element.outerHeight()};this.elementOffset=this.element.offset();position={x:event.pageX,y:event.pageY};normValue=this._normValueFromMouse(position);distance=this._valueMax()-this._valueMin()+1;this.handles.each(function(i){var thisDistance=Math.abs(normValue-that.values(i));if(distance>thisDistance||distance===thisDistance&&(i===that._lastChangedValue||that.values(i)===o.min)){distance=thisDistance;closestHandle=$(this);index=i}});allowed=this._start(event,index);if(allowed===false){return false}this._mouseSliding=true;this._handleIndex=index;closestHandle.addClass("ui-state-active").focus();offset=closestHandle.offset();mouseOverHandle=!$(event.target).parents().addBack().is(".ui-slider-handle");this._clickOffset=mouseOverHandle?{left:0,top:0}:{left:event.pageX-offset.left-closestHandle.width()/2,top:event.pageY-offset.top-closestHandle.height()/2-(parseInt(closestHandle.css("borderTopWidth"),10)||0)-(parseInt(closestHandle.css("borderBottomWidth"),10)||0)+(parseInt(closestHandle.css("marginTop"),10)||0)};if(!this.handles.hasClass("ui-state-hover")){this._slide(event,index,normValue)}this._animateOff=true;return true},_mouseStart:function(){return true},_mouseDrag:function(event){var position={x:event.pageX,y:event.pageY},normValue=this._normValueFromMouse(position);this._slide(event,this._handleIndex,normValue);return false},_mouseStop:function(event){this.handles.removeClass("ui-state-active");this._mouseSliding=false;this._stop(event,this._handleIndex);this._change(event,this._handleIndex);this._handleIndex=null;this._clickOffset=null;this._animateOff=false;return false},_detectOrientation:function(){this.orientation=this.options.orientation==="vertical"?"vertical":"horizontal"},_normValueFromMouse:function(position){var pixelTotal,pixelMouse,percentMouse,valueTotal,valueMouse;if(this.orientation==="horizontal"){pixelTotal=this.elementSize.width;pixelMouse=position.x-this.elementOffset.left-(this._clickOffset?this._clickOffset.left:0)}else{pixelTotal=this.elementSize.height;pixelMouse=position.y-this.elementOffset.top-(this._clickOffset?this._clickOffset.top:0)}percentMouse=pixelMouse/pixelTotal;if(percentMouse>1){percentMouse=1}if(percentMouse<0){percentMouse=0}if(this.orientation==="vertical"){percentMouse=1-percentMouse}valueTotal=this._valueMax()-this._valueMin();valueMouse=this._valueMin()+percentMouse*valueTotal;return this._trimAlignValue(valueMouse)},_start:function(event,index){var uiHash={handle:this.handles[index],value:this.value()};if(this.options.values&&this.options.values.length){uiHash.value=this.values(index);uiHash.values=this.values()}return this._trigger("start",event,uiHash)},_slide:function(event,index,newVal){var otherVal,newValues,allowed;if(this.options.values&&this.options.values.length){otherVal=this.values(index?0:1);if(this.options.values.length===2&&this.options.range===true&&(index===0&&newVal>otherVal||index===1&&newVal<otherVal)){newVal=otherVal}if(newVal!==this.values(index)){newValues=this.values();newValues[index]=newVal;allowed=this._trigger("slide",event,{handle:this.handles[index],value:newVal,values:newValues});otherVal=this.values(index?0:1);if(allowed!==false){this.values(index,newVal)}}}else{if(newVal!==this.value()){allowed=this._trigger("slide",event,{handle:this.handles[index],value:newVal});if(allowed!==false){this.value(newVal)}}}},_stop:function(event,index){var uiHash={handle:this.handles[index],value:this.value()};if(this.options.values&&this.options.values.length){uiHash.value=this.values(index);uiHash.values=this.values()}this._trigger("stop",event,uiHash)},_change:function(event,index){if(!this._keySliding&&!this._mouseSliding){var uiHash={handle:this.handles[index],value:this.value()};if(this.options.values&&this.options.values.length){uiHash.value=this.values(index);uiHash.values=this.values()}this._lastChangedValue=index;this._trigger("change",event,uiHash)}},value:function(newValue){if(arguments.length){this.options.value=this._trimAlignValue(newValue);this._refreshValue();this._change(null,0);return}return this._value()},values:function(index,newValue){var vals,newValues,i;if(arguments.length>1){this.options.values[index]=this._trimAlignValue(newValue);this._refreshValue();this._change(null,index);return}if(arguments.length){if($.isArray(arguments[0])){vals=this.options.values;newValues=arguments[0];for(i=0;i<vals.length;i+=1){vals[i]=this._trimAlignValue(newValues[i]);this._change(null,i)}this._refreshValue()}else{if(this.options.values&&this.options.values.length){return this._values(index)}else{return this.value()}}}else{return this._values()}},_setOption:function(key,value){var i,valsLength=0;if(key==="range"&&this.options.range===true){if(value==="min"){this.options.value=this._values(0);this.options.values=null}else if(value==="max"){this.options.value=this._values(this.options.values.length-1);this.options.values=null}}if($.isArray(this.options.values)){valsLength=this.options.values.length}$.Widget.prototype._setOption.apply(this,arguments);switch(key){case"orientation":this._detectOrientation();this.element.removeClass("ui-slider-horizontal ui-slider-vertical").addClass("ui-slider-"+this.orientation);this._refreshValue();break;case"value":this._animateOff=true;this._refreshValue();this._change(null,0);this._animateOff=false;break;case"values":this._animateOff=true;this._refreshValue();for(i=0;i<valsLength;i+=1){this._change(null,i)}this._animateOff=false;break;case"min":case"max":this._animateOff=true;this._refreshValue();this._animateOff=false;break;case"range":this._animateOff=true;this._refresh();this._animateOff=false;break}},_value:function(){var val=this.options.value;val=this._trimAlignValue(val);return val},_values:function(index){var val,vals,i;if(arguments.length){val=this.options.values[index];val=this._trimAlignValue(val);return val}else if(this.options.values&&this.options.values.length){vals=this.options.values.slice();for(i=0;i<vals.length;i+=1){vals[i]=this._trimAlignValue(vals[i])}return vals}else{return[]}},_trimAlignValue:function(val){if(val<=this._valueMin()){return this._valueMin()}if(val>=this._valueMax()){return this._valueMax()}var step=this.options.step>0?this.options.step:1,valModStep=(val-this._valueMin())%step,alignValue=val-valModStep;if(Math.abs(valModStep)*2>=step){alignValue+=valModStep>0?step:-step}return parseFloat(alignValue.toFixed(5))},_valueMin:function(){return this.options.min},_valueMax:function(){return this.options.max},_refreshValue:function(){var lastValPercent,valPercent,value,valueMin,valueMax,oRange=this.options.range,o=this.options,that=this,animate=!this._animateOff?o.animate:false,_set={};if(this.options.values&&this.options.values.length){this.handles.each(function(i){valPercent=(that.values(i)-that._valueMin())/(that._valueMax()-that._valueMin())*100;_set[that.orientation==="horizontal"?"left":"bottom"]=valPercent+"%";$(this).stop(1,1)[animate?"animate":"css"](_set,o.animate);if(that.options.range===true){if(that.orientation==="horizontal"){if(i===0){that.range.stop(1,1)[animate?"animate":"css"]({left:valPercent+"%"},o.animate)}if(i===1){that.range[animate?"animate":"css"]({width:valPercent-lastValPercent+"%"},{queue:false,duration:o.animate})}}else{if(i===0){that.range.stop(1,1)[animate?"animate":"css"]({bottom:valPercent+"%"},o.animate)}if(i===1){that.range[animate?"animate":"css"]({height:valPercent-lastValPercent+"%"},{queue:false,duration:o.animate})}}}lastValPercent=valPercent})}else{value=this.value();valueMin=this._valueMin();valueMax=this._valueMax();valPercent=valueMax!==valueMin?(value-valueMin)/(valueMax-valueMin)*100:0;_set[this.orientation==="horizontal"?"left":"bottom"]=valPercent+"%";this.handle.stop(1,1)[animate?"animate":"css"](_set,o.animate);if(oRange==="min"&&this.orientation==="horizontal"){this.range.stop(1,1)[animate?"animate":"css"]({width:valPercent+"%"},o.animate)}if(oRange==="max"&&this.orientation==="horizontal"){this.range[animate?"animate":"css"]({width:100-valPercent+"%"},{queue:false,duration:o.animate})}if(oRange==="min"&&this.orientation==="vertical"){this.range.stop(1,1)[animate?"animate":"css"]({height:valPercent+"%"},o.animate)}if(oRange==="max"&&this.orientation==="vertical"){this.range[animate?"animate":"css"]({height:100-valPercent+"%"},{queue:false,duration:o.animate})}}},_handleEvents:{keydown:function(event){var allowed,curVal,newVal,step,index=$(event.target).data("ui-slider-handle-index");switch(event.keyCode){case $.ui.keyCode.HOME:case $.ui.keyCode.END:case $.ui.keyCode.PAGE_UP:case $.ui.keyCode.PAGE_DOWN:case $.ui.keyCode.UP:case $.ui.keyCode.RIGHT:case $.ui.keyCode.DOWN:case $.ui.keyCode.LEFT:event.preventDefault();if(!this._keySliding){this._keySliding=true;$(event.target).addClass("ui-state-active");allowed=this._start(event,index);if(allowed===false){return}}break}step=this.options.step;if(this.options.values&&this.options.values.length){curVal=newVal=this.values(index)}else{curVal=newVal=this.value()}switch(event.keyCode){case $.ui.keyCode.HOME:newVal=this._valueMin();break;case $.ui.keyCode.END:newVal=this._valueMax();break;case $.ui.keyCode.PAGE_UP:newVal=this._trimAlignValue(curVal+(this._valueMax()-this._valueMin())/numPages);break;case $.ui.keyCode.PAGE_DOWN:newVal=this._trimAlignValue(curVal-(this._valueMax()-this._valueMin())/numPages);break;case $.ui.keyCode.UP:case $.ui.keyCode.RIGHT:if(curVal===this._valueMax()){return}newVal=this._trimAlignValue(curVal+step);break;case $.ui.keyCode.DOWN:case $.ui.keyCode.LEFT:if(curVal===this._valueMin()){return}newVal=this._trimAlignValue(curVal-step);break}this._slide(event,index,newVal)},click:function(event){event.preventDefault()},keyup:function(event){var index=$(event.target).data("ui-slider-handle-index");if(this._keySliding){this._keySliding=false;this._stop(event,index);this._change(event,index);$(event.target).removeClass("ui-state-active")}}}})})(jQuery)},{"./core":203,"./mouse":204,"./widget":206,jquery:207}],206:[function(require,module,exports){var jQuery=require("jquery");(function($,undefined){var uuid=0,slice=Array.prototype.slice,_cleanData=$.cleanData;$.cleanData=function(elems){for(var i=0,elem;(elem=elems[i])!=null;i++){try{$(elem).triggerHandler("remove")}catch(e){}}_cleanData(elems)};$.widget=function(name,base,prototype){var fullName,existingConstructor,constructor,basePrototype,proxiedPrototype={},namespace=name.split(".")[0];name=name.split(".")[1];fullName=namespace+"-"+name;if(!prototype){prototype=base;base=$.Widget}$.expr[":"][fullName.toLowerCase()]=function(elem){return!!$.data(elem,fullName)};$[namespace]=$[namespace]||{};existingConstructor=$[namespace][name];
12
 
13
- constructor=$[namespace][name]=function(options,element){if(!this._createWidget){return new constructor(options,element)}if(arguments.length){this._createWidget(options,element)}};$.extend(constructor,existingConstructor,{version:prototype.version,_proto:$.extend({},prototype),_childConstructors:[]});basePrototype=new base;basePrototype.options=$.widget.extend({},basePrototype.options);$.each(prototype,function(prop,value){if(!$.isFunction(value)){proxiedPrototype[prop]=value;return}proxiedPrototype[prop]=function(){var _super=function(){return base.prototype[prop].apply(this,arguments)},_superApply=function(args){return base.prototype[prop].apply(this,args)};return function(){var __super=this._super,__superApply=this._superApply,returnValue;this._super=_super;this._superApply=_superApply;returnValue=value.apply(this,arguments);this._super=__super;this._superApply=__superApply;return returnValue}}()});constructor.prototype=$.widget.extend(basePrototype,{widgetEventPrefix:existingConstructor?basePrototype.widgetEventPrefix||name:name},proxiedPrototype,{constructor:constructor,namespace:namespace,widgetName:name,widgetFullName:fullName});if(existingConstructor){$.each(existingConstructor._childConstructors,function(i,child){var childPrototype=child.prototype;$.widget(childPrototype.namespace+"."+childPrototype.widgetName,constructor,child._proto)});delete existingConstructor._childConstructors}else{base._childConstructors.push(constructor)}$.widget.bridge(name,constructor)};$.widget.extend=function(target){var input=slice.call(arguments,1),inputIndex=0,inputLength=input.length,key,value;for(;inputIndex<inputLength;inputIndex++){for(key in input[inputIndex]){value=input[inputIndex][key];if(input[inputIndex].hasOwnProperty(key)&&value!==undefined){if($.isPlainObject(value)){target[key]=$.isPlainObject(target[key])?$.widget.extend({},target[key],value):$.widget.extend({},value)}else{target[key]=value}}}}return target};$.widget.bridge=function(name,object){var fullName=object.prototype.widgetFullName||name;$.fn[name]=function(options){var isMethodCall=typeof options==="string",args=slice.call(arguments,1),returnValue=this;options=!isMethodCall&&args.length?$.widget.extend.apply(null,[options].concat(args)):options;if(isMethodCall){this.each(function(){var methodValue,instance=$.data(this,fullName);if(!instance){return $.error("cannot call methods on "+name+" prior to initialization; "+"attempted to call method '"+options+"'")}if(!$.isFunction(instance[options])||options.charAt(0)==="_"){return $.error("no such method '"+options+"' for "+name+" widget instance")}methodValue=instance[options].apply(instance,args);if(methodValue!==instance&&methodValue!==undefined){returnValue=methodValue&&methodValue.jquery?returnValue.pushStack(methodValue.get()):methodValue;return false}})}else{this.each(function(){var instance=$.data(this,fullName);if(instance){instance.option(options||{})._init()}else{$.data(this,fullName,new object(options,this))}})}return returnValue}};$.Widget=function(){};$.Widget._childConstructors=[];$.Widget.prototype={widgetName:"widget",widgetEventPrefix:"",defaultElement:"<div>",options:{disabled:false,create:null},_createWidget:function(options,element){element=$(element||this.defaultElement||this)[0];this.element=$(element);this.uuid=uuid++;this.eventNamespace="."+this.widgetName+this.uuid;this.options=$.widget.extend({},this.options,this._getCreateOptions(),options);this.bindings=$();this.hoverable=$();this.focusable=$();if(element!==this){$.data(element,this.widgetFullName,this);this._on(true,this.element,{remove:function(event){if(event.target===element){this.destroy()}}});this.document=$(element.style?element.ownerDocument:element.document||element);this.window=$(this.document[0].defaultView||this.document[0].parentWindow)}this._create();this._trigger("create",null,this._getCreateEventData());this._init()},_getCreateOptions:$.noop,_getCreateEventData:$.noop,_create:$.noop,_init:$.noop,destroy:function(){this._destroy();this.element.unbind(this.eventNamespace).removeData(this.widgetName).removeData(this.widgetFullName).removeData($.camelCase(this.widgetFullName));this.widget().unbind(this.eventNamespace).removeAttr("aria-disabled").removeClass(this.widgetFullName+"-disabled "+"ui-state-disabled");this.bindings.unbind(this.eventNamespace);this.hoverable.removeClass("ui-state-hover");this.focusable.removeClass("ui-state-focus")},_destroy:$.noop,widget:function(){return this.element},option:function(key,value){var options=key,parts,curOption,i;if(arguments.length===0){return $.widget.extend({},this.options)}if(typeof key==="string"){options={};parts=key.split(".");key=parts.shift();if(parts.length){curOption=options[key]=$.widget.extend({},this.options[key]);for(i=0;i<parts.length-1;i++){curOption[parts[i]]=curOption[parts[i]]||{};curOption=curOption[parts[i]]}key=parts.pop();if(arguments.length===1){return curOption[key]===undefined?null:curOption[key]}curOption[key]=value}else{if(arguments.length===1){return this.options[key]===undefined?null:this.options[key]}options[key]=value}}this._setOptions(options);return this},_setOptions:function(options){var key;for(key in options){this._setOption(key,options[key])}return this},_setOption:function(key,value){this.options[key]=value;if(key==="disabled"){this.widget().toggleClass(this.widgetFullName+"-disabled ui-state-disabled",!!value).attr("aria-disabled",value);this.hoverable.removeClass("ui-state-hover");this.focusable.removeClass("ui-state-focus")}return this},enable:function(){return this._setOption("disabled",false)},disable:function(){return this._setOption("disabled",true)},_on:function(suppressDisabledCheck,element,handlers){var delegateElement,instance=this;if(typeof suppressDisabledCheck!=="boolean"){handlers=element;element=suppressDisabledCheck;suppressDisabledCheck=false}if(!handlers){handlers=element;element=this.element;delegateElement=this.widget()}else{element=delegateElement=$(element);this.bindings=this.bindings.add(element)}$.each(handlers,function(event,handler){function handlerProxy(){if(!suppressDisabledCheck&&(instance.options.disabled===true||$(this).hasClass("ui-state-disabled"))){return}return(typeof handler==="string"?instance[handler]:handler).apply(instance,arguments)}if(typeof handler!=="string"){handlerProxy.guid=handler.guid=handler.guid||handlerProxy.guid||$.guid++}var match=event.match(/^(\w+)\s*(.*)$/),eventName=match[1]+instance.eventNamespace,selector=match[2];if(selector){delegateElement.delegate(selector,eventName,handlerProxy)}else{element.bind(eventName,handlerProxy)}})},_off:function(element,eventName){eventName=(eventName||"").split(" ").join(this.eventNamespace+" ")+this.eventNamespace;element.unbind(eventName).undelegate(eventName)},_delay:function(handler,delay){function handlerProxy(){return(typeof handler==="string"?instance[handler]:handler).apply(instance,arguments)}var instance=this;return setTimeout(handlerProxy,delay||0)},_hoverable:function(element){this.hoverable=this.hoverable.add(element);this._on(element,{mouseenter:function(event){$(event.currentTarget).addClass("ui-state-hover")},mouseleave:function(event){$(event.currentTarget).removeClass("ui-state-hover")}})},_focusable:function(element){this.focusable=this.focusable.add(element);this._on(element,{focusin:function(event){$(event.currentTarget).addClass("ui-state-focus")},focusout:function(event){$(event.currentTarget).removeClass("ui-state-focus")}})},_trigger:function(type,event,data){var prop,orig,callback=this.options[type];data=data||{};event=$.Event(event);event.type=(type===this.widgetEventPrefix?type:this.widgetEventPrefix+type).toLowerCase();event.target=this.element[0];orig=event.originalEvent;if(orig){for(prop in orig){if(!(prop in event)){event[prop]=orig[prop]}}}this.element.trigger(event,data);return!($.isFunction(callback)&&callback.apply(this.element[0],[event].concat(data))===false||event.isDefaultPrevented())}};$.each({show:"fadeIn",hide:"fadeOut"},function(method,defaultEffect){$.Widget.prototype["_"+method]=function(element,options,callback){if(typeof options==="string"){options={effect:options}}var hasOptions,effectName=!options?method:options===true||typeof options==="number"?defaultEffect:options.effect||defaultEffect;options=options||{};if(typeof options==="number"){options={duration:options}}hasOptions=!$.isEmptyObject(options);options.complete=callback;if(options.delay){element.delay(options.delay)}if(hasOptions&&$.effects&&$.effects.effect[effectName]){element[method](options)}else if(effectName!==method&&element[effectName]){element[effectName](options.duration,options.easing,callback)}else{element.queue(function(next){$(this)[method]();if(callback){callback.call(element[0])}next()})}}})})(jQuery)},{jquery:207}],207:[function(require,module,exports){(function(global,factory){if(typeof module==="object"&&typeof module.exports==="object"){module.exports=global.document?factory(global,true):function(w){if(!w.document){throw new Error("jQuery requires a window with a document")}return factory(w)}}else{factory(global)}})(typeof window!=="undefined"?window:this,function(window,noGlobal){var deletedIds=[];var slice=deletedIds.slice;var concat=deletedIds.concat;var push=deletedIds.push;var indexOf=deletedIds.indexOf;var class2type={};var toString=class2type.toString;var hasOwn=class2type.hasOwnProperty;var support={};var version="1.11.3",jQuery=function(selector,context){return new jQuery.fn.init(selector,context)},rtrim=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,rmsPrefix=/^-ms-/,rdashAlpha=/-([\da-z])/gi,fcamelCase=function(all,letter){return letter.toUpperCase()};jQuery.fn=jQuery.prototype={jquery:version,constructor:jQuery,selector:"",length:0,toArray:function(){return slice.call(this)},get:function(num){return num!=null?num<0?this[num+this.length]:this[num]:slice.call(this)},pushStack:function(elems){var ret=jQuery.merge(this.constructor(),elems);ret.prevObject=this;ret.context=this.context;return ret},each:function(callback,args){return jQuery.each(this,callback,args)},map:function(callback){return this.pushStack(jQuery.map(this,function(elem,i){return callback.call(elem,i,elem)}))},slice:function(){return this.pushStack(slice.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(i){var len=this.length,j=+i+(i<0?len:0);return this.pushStack(j>=0&&j<len?[this[j]]:[])},end:function(){return this.prevObject||this.constructor(null)},push:push,sort:deletedIds.sort,splice:deletedIds.splice};jQuery.extend=jQuery.fn.extend=function(){var src,copyIsArray,copy,name,options,clone,target=arguments[0]||{},i=1,length=arguments.length,deep=false;if(typeof target==="boolean"){deep=target;target=arguments[i]||{};i++}if(typeof target!=="object"&&!jQuery.isFunction(target)){target={}}if(i===length){target=this;i--}for(;i<length;i++){if((options=arguments[i])!=null){for(name in options){src=target[name];copy=options[name];if(target===copy){continue}if(deep&&copy&&(jQuery.isPlainObject(copy)||(copyIsArray=jQuery.isArray(copy)))){if(copyIsArray){copyIsArray=false;clone=src&&jQuery.isArray(src)?src:[]}else{clone=src&&jQuery.isPlainObject(src)?src:{}}target[name]=jQuery.extend(deep,clone,copy)}else if(copy!==undefined){target[name]=copy}}}}return target};jQuery.extend({expando:"jQuery"+(version+Math.random()).replace(/\D/g,""),isReady:true,error:function(msg){throw new Error(msg)},noop:function(){},isFunction:function(obj){return jQuery.type(obj)==="function"},isArray:Array.isArray||function(obj){return jQuery.type(obj)==="array"},isWindow:function(obj){return obj!=null&&obj==obj.window},isNumeric:function(obj){return!jQuery.isArray(obj)&&obj-parseFloat(obj)+1>=0},isEmptyObject:function(obj){var name;for(name in obj){return false}return true},isPlainObject:function(obj){var key;if(!obj||jQuery.type(obj)!=="object"||obj.nodeType||jQuery.isWindow(obj)){return false}try{if(obj.constructor&&!hasOwn.call(obj,"constructor")&&!hasOwn.call(obj.constructor.prototype,"isPrototypeOf")){return false}}catch(e){return false}if(support.ownLast){for(key in obj){return hasOwn.call(obj,key)}}for(key in obj){}return key===undefined||hasOwn.call(obj,key)},type:function(obj){if(obj==null){return obj+""}return typeof obj==="object"||typeof obj==="function"?class2type[toString.call(obj)]||"object":typeof obj},globalEval:function(data){if(data&&jQuery.trim(data)){(window.execScript||function(data){window["eval"].call(window,data)})(data)}},camelCase:function(string){return string.replace(rmsPrefix,"ms-").replace(rdashAlpha,fcamelCase)},nodeName:function(elem,name){return elem.nodeName&&elem.nodeName.toLowerCase()===name.toLowerCase()},each:function(obj,callback,args){var value,i=0,length=obj.length,isArray=isArraylike(obj);if(args){if(isArray){for(;i<length;i++){value=callback.apply(obj[i],args);if(value===false){break}}}else{for(i in obj){value=callback.apply(obj[i],args);if(value===false){break}}}}else{if(isArray){for(;i<length;i++){value=callback.call(obj[i],i,obj[i]);if(value===false){break}}}else{for(i in obj){value=callback.call(obj[i],i,obj[i]);if(value===false){break}}}}return obj},trim:function(text){return text==null?"":(text+"").replace(rtrim,"")},makeArray:function(arr,results){var ret=results||[];if(arr!=null){if(isArraylike(Object(arr))){jQuery.merge(ret,typeof arr==="string"?[arr]:arr)}else{push.call(ret,arr)}}return ret},inArray:function(elem,arr,i){var len;if(arr){if(indexOf){return indexOf.call(arr,elem,i)}len=arr.length;i=i?i<0?Math.max(0,len+i):i:0;for(;i<len;i++){if(i in arr&&arr[i]===elem){return i}}}return-1},merge:function(first,second){var len=+second.length,j=0,i=first.length;while(j<len){first[i++]=second[j++]}if(len!==len){while(second[j]!==undefined){first[i++]=second[j++]}}first.length=i;return first},grep:function(elems,callback,invert){var callbackInverse,matches=[],i=0,length=elems.length,callbackExpect=!invert;for(;i<length;i++){callbackInverse=!callback(elems[i],i);if(callbackInverse!==callbackExpect){matches.push(elems[i])}}return matches},map:function(elems,callback,arg){var value,i=0,length=elems.length,isArray=isArraylike(elems),ret=[];if(isArray){for(;i<length;i++){value=callback(elems[i],i,arg);if(value!=null){ret.push(value)}}}else{for(i in elems){value=callback(elems[i],i,arg);if(value!=null){ret.push(value)}}}return concat.apply([],ret)},guid:1,proxy:function(fn,context){var args,proxy,tmp;if(typeof context==="string"){tmp=fn[context];context=fn;fn=tmp}if(!jQuery.isFunction(fn)){return undefined}args=slice.call(arguments,2);proxy=function(){return fn.apply(context||this,args.concat(slice.call(arguments)))};proxy.guid=fn.guid=fn.guid||jQuery.guid++;return proxy},now:function(){return+new Date},support:support});jQuery.each("Boolean Number String Function Array Date RegExp Object Error".split(" "),function(i,name){class2type["[object "+name+"]"]=name.toLowerCase()});function isArraylike(obj){var length="length"in obj&&obj.length,type=jQuery.type(obj);if(type==="function"||jQuery.isWindow(obj)){return false}if(obj.nodeType===1&&length){return true}return type==="array"||length===0||typeof length==="number"&&length>0&&length-1 in obj}var Sizzle=function(window){var i,support,Expr,getText,isXML,tokenize,compile,select,outermostContext,sortInput,hasDuplicate,setDocument,document,docElem,documentIsHTML,rbuggyQSA,rbuggyMatches,matches,contains,expando="sizzle"+1*new Date,preferredDoc=window.document,dirruns=0,done=0,classCache=createCache(),tokenCache=createCache(),compilerCache=createCache(),sortOrder=function(a,b){if(a===b){hasDuplicate=true}return 0},MAX_NEGATIVE=1<<31,hasOwn={}.hasOwnProperty,arr=[],pop=arr.pop,push_native=arr.push,push=arr.push,slice=arr.slice,indexOf=function(list,elem){var i=0,len=list.length;for(;i<len;i++){if(list[i]===elem){return i}}return-1},booleans="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",whitespace="[\\x20\\t\\r\\n\\f]",characterEncoding="(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+",identifier=characterEncoding.replace("w","w#"),attributes="\\["+whitespace+"*("+characterEncoding+")(?:"+whitespace+"*([*^$|!~]?=)"+whitespace+"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|("+identifier+"))|)"+whitespace+"*\\]",pseudos=":("+characterEncoding+")(?:\\(("+"('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|"+"((?:\\\\.|[^\\\\()[\\]]|"+attributes+")*)|"+".*"+")\\)|)",rwhitespace=new RegExp(whitespace+"+","g"),rtrim=new RegExp("^"+whitespace+"+|((?:^|[^\\\\])(?:\\\\.)*)"+whitespace+"+$","g"),rcomma=new RegExp("^"+whitespace+"*,"+whitespace+"*"),rcombinators=new RegExp("^"+whitespace+"*([>+~]|"+whitespace+")"+whitespace+"*"),rattributeQuotes=new RegExp("="+whitespace+"*([^\\]'\"]*?)"+whitespace+"*\\]","g"),rpseudo=new RegExp(pseudos),ridentifier=new RegExp("^"+identifier+"$"),matchExpr={ID:new RegExp("^#("+characterEncoding+")"),CLASS:new RegExp("^\\.("+characterEncoding+")"),TAG:new RegExp("^("+characterEncoding.replace("w","w*")+")"),ATTR:new RegExp("^"+attributes),PSEUDO:new RegExp("^"+pseudos),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+whitespace+"*(even|odd|(([+-]|)(\\d*)n|)"+whitespace+"*(?:([+-]|)"+whitespace+"*(\\d+)|))"+whitespace+"*\\)|)","i"),bool:new RegExp("^(?:"+booleans+")$","i"),needsContext:new RegExp("^"+whitespace+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+whitespace+"*((?:-\\d)?\\d*)"+whitespace+"*\\)|)(?=[^-]|$)","i")},rinputs=/^(?:input|select|textarea|button)$/i,rheader=/^h\d$/i,rnative=/^[^{]+\{\s*\[native \w/,rquickExpr=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,rsibling=/[+~]/,rescape=/'|\\/g,runescape=new RegExp("\\\\([\\da-f]{1,6}"+whitespace+"?|("+whitespace+")|.)","ig"),funescape=function(_,escaped,escapedWhitespace){var high="0x"+escaped-65536;return high!==high||escapedWhitespace?escaped:high<0?String.fromCharCode(high+65536):String.fromCharCode(high>>10|55296,high&1023|56320)},unloadHandler=function(){setDocument()};try{push.apply(arr=slice.call(preferredDoc.childNodes),preferredDoc.childNodes);arr[preferredDoc.childNodes.length].nodeType}catch(e){push={apply:arr.length?function(target,els){push_native.apply(target,slice.call(els))}:function(target,els){var j=target.length,i=0;while(target[j++]=els[i++]){}target.length=j-1}}}function Sizzle(selector,context,results,seed){var match,elem,m,nodeType,i,groups,old,nid,newContext,newSelector;if((context?context.ownerDocument||context:preferredDoc)!==document){setDocument(context)}context=context||document;results=results||[];nodeType=context.nodeType;if(typeof selector!=="string"||!selector||nodeType!==1&&nodeType!==9&&nodeType!==11){return results}if(!seed&&documentIsHTML){if(nodeType!==11&&(match=rquickExpr.exec(selector))){if(m=match[1]){if(nodeType===9){elem=context.getElementById(m);if(elem&&elem.parentNode){if(elem.id===m){results.push(elem);return results}}else{return results}}else{if(context.ownerDocument&&(elem=context.ownerDocument.getElementById(m))&&contains(context,elem)&&elem.id===m){results.push(elem);return results}}}else if(match[2]){push.apply(results,context.getElementsByTagName(selector));return results}else if((m=match[3])&&support.getElementsByClassName){push.apply(results,context.getElementsByClassName(m));return results}}if(support.qsa&&(!rbuggyQSA||!rbuggyQSA.test(selector))){nid=old=expando;newContext=context;newSelector=nodeType!==1&&selector;if(nodeType===1&&context.nodeName.toLowerCase()!=="object"){groups=tokenize(selector);if(old=context.getAttribute("id")){nid=old.replace(rescape,"\\$&")}else{context.setAttribute("id",nid)}nid="[id='"+nid+"'] ";i=groups.length;while(i--){groups[i]=nid+toSelector(groups[i])}newContext=rsibling.test(selector)&&testContext(context.parentNode)||context;newSelector=groups.join(",")}if(newSelector){try{push.apply(results,newContext.querySelectorAll(newSelector));return results}catch(qsaError){}finally{if(!old){context.removeAttribute("id")}}}}}return select(selector.replace(rtrim,"$1"),context,results,seed)}function createCache(){var keys=[];function cache(key,value){if(keys.push(key+" ")>Expr.cacheLength){delete cache[keys.shift()]}return cache[key+" "]=value}return cache}function markFunction(fn){fn[expando]=true;return fn}function assert(fn){var div=document.createElement("div");try{return!!fn(div)}catch(e){return false}finally{if(div.parentNode){div.parentNode.removeChild(div)}div=null}}function addHandle(attrs,handler){var arr=attrs.split("|"),i=attrs.length;while(i--){Expr.attrHandle[arr[i]]=handler}}function siblingCheck(a,b){var cur=b&&a,diff=cur&&a.nodeType===1&&b.nodeType===1&&(~b.sourceIndex||MAX_NEGATIVE)-(~a.sourceIndex||MAX_NEGATIVE);if(diff){return diff}if(cur){while(cur=cur.nextSibling){if(cur===b){return-1}}}return a?1:-1}function createInputPseudo(type){return function(elem){var name=elem.nodeName.toLowerCase();return name==="input"&&elem.type===type}}function createButtonPseudo(type){return function(elem){var name=elem.nodeName.toLowerCase();return(name==="input"||name==="button")&&elem.type===type}}function createPositionalPseudo(fn){return markFunction(function(argument){argument=+argument;return markFunction(function(seed,matches){var j,matchIndexes=fn([],seed.length,argument),i=matchIndexes.length;while(i--){if(seed[j=matchIndexes[i]]){seed[j]=!(matches[j]=seed[j])}}})})}function testContext(context){return context&&typeof context.getElementsByTagName!=="undefined"&&context}support=Sizzle.support={};isXML=Sizzle.isXML=function(elem){var documentElement=elem&&(elem.ownerDocument||elem).documentElement;return documentElement?documentElement.nodeName!=="HTML":false};setDocument=Sizzle.setDocument=function(node){var hasCompare,parent,doc=node?node.ownerDocument||node:preferredDoc;if(doc===document||doc.nodeType!==9||!doc.documentElement){return document}document=doc;docElem=doc.documentElement;parent=doc.defaultView;if(parent&&parent!==parent.top){if(parent.addEventListener){parent.addEventListener("unload",unloadHandler,false)}else if(parent.attachEvent){parent.attachEvent("onunload",unloadHandler)}}documentIsHTML=!isXML(doc);support.attributes=assert(function(div){div.className="i";return!div.getAttribute("className")});support.getElementsByTagName=assert(function(div){div.appendChild(doc.createComment(""));return!div.getElementsByTagName("*").length});support.getElementsByClassName=rnative.test(doc.getElementsByClassName);support.getById=assert(function(div){docElem.appendChild(div).id=expando;return!doc.getElementsByName||!doc.getElementsByName(expando).length});if(support.getById){Expr.find["ID"]=function(id,context){if(typeof context.getElementById!=="undefined"&&documentIsHTML){var m=context.getElementById(id);return m&&m.parentNode?[m]:[]}};Expr.filter["ID"]=function(id){var attrId=id.replace(runescape,funescape);return function(elem){return elem.getAttribute("id")===attrId}}}else{delete Expr.find["ID"];Expr.filter["ID"]=function(id){var attrId=id.replace(runescape,funescape);return function(elem){var node=typeof elem.getAttributeNode!=="undefined"&&elem.getAttributeNode("id");return node&&node.value===attrId}}}Expr.find["TAG"]=support.getElementsByTagName?function(tag,context){if(typeof context.getElementsByTagName!=="undefined"){return context.getElementsByTagName(tag)}else if(support.qsa){return context.querySelectorAll(tag)}}:function(tag,context){var elem,tmp=[],i=0,results=context.getElementsByTagName(tag);if(tag==="*"){while(elem=results[i++]){if(elem.nodeType===1){tmp.push(elem)}}return tmp}return results};Expr.find["CLASS"]=support.getElementsByClassName&&function(className,context){if(documentIsHTML){return context.getElementsByClassName(className)}};rbuggyMatches=[];rbuggyQSA=[];if(support.qsa=rnative.test(doc.querySelectorAll)){assert(function(div){docElem.appendChild(div).innerHTML="<a id='"+expando+"'></a>"+"<select id='"+expando+"-\f]' msallowcapture=''>"+"<option selected=''></option></select>";if(div.querySelectorAll("[msallowcapture^='']").length){rbuggyQSA.push("[*^$]="+whitespace+"*(?:''|\"\")")}if(!div.querySelectorAll("[selected]").length){rbuggyQSA.push("\\["+whitespace+"*(?:value|"+booleans+")")}if(!div.querySelectorAll("[id~="+expando+"-]").length){rbuggyQSA.push("~=")}if(!div.querySelectorAll(":checked").length){rbuggyQSA.push(":checked")}if(!div.querySelectorAll("a#"+expando+"+*").length){rbuggyQSA.push(".#.+[+~]")}});assert(function(div){var input=doc.createElement("input");input.setAttribute("type","hidden");div.appendChild(input).setAttribute("name","D");if(div.querySelectorAll("[name=d]").length){rbuggyQSA.push("name"+whitespace+"*[*^$|!~]?=")}if(!div.querySelectorAll(":enabled").length){rbuggyQSA.push(":enabled",":disabled")}div.querySelectorAll("*,:x");rbuggyQSA.push(",.*:")})}if(support.matchesSelector=rnative.test(matches=docElem.matches||docElem.webkitMatchesSelector||docElem.mozMatchesSelector||docElem.oMatchesSelector||docElem.msMatchesSelector)){assert(function(div){support.disconnectedMatch=matches.call(div,"div");matches.call(div,"[s!='']:x");rbuggyMatches.push("!=",pseudos)})}rbuggyQSA=rbuggyQSA.length&&new RegExp(rbuggyQSA.join("|"));rbuggyMatches=rbuggyMatches.length&&new RegExp(rbuggyMatches.join("|"));hasCompare=rnative.test(docElem.compareDocumentPosition);contains=hasCompare||rnative.test(docElem.contains)?function(a,b){var adown=a.nodeType===9?a.documentElement:a,bup=b&&b.parentNode;return a===bup||!!(bup&&bup.nodeType===1&&(adown.contains?adown.contains(bup):a.compareDocumentPosition&&a.compareDocumentPosition(bup)&16))}:function(a,b){if(b){while(b=b.parentNode){if(b===a){return true}}}return false};sortOrder=hasCompare?function(a,b){if(a===b){hasDuplicate=true;return 0}var compare=!a.compareDocumentPosition-!b.compareDocumentPosition;if(compare){return compare}compare=(a.ownerDocument||a)===(b.ownerDocument||b)?a.compareDocumentPosition(b):1;if(compare&1||!support.sortDetached&&b.compareDocumentPosition(a)===compare){if(a===doc||a.ownerDocument===preferredDoc&&contains(preferredDoc,a)){return-1}if(b===doc||b.ownerDocument===preferredDoc&&contains(preferredDoc,b)){return 1}return sortInput?indexOf(sortInput,a)-indexOf(sortInput,b):0}return compare&4?-1:1}:function(a,b){if(a===b){hasDuplicate=true;return 0}var cur,i=0,aup=a.parentNode,bup=b.parentNode,ap=[a],bp=[b];if(!aup||!bup){return a===doc?-1:b===doc?1:aup?-1:bup?1:sortInput?indexOf(sortInput,a)-indexOf(sortInput,b):0}else if(aup===bup){return siblingCheck(a,b)}cur=a;while(cur=cur.parentNode){ap.unshift(cur)}cur=b;while(cur=cur.parentNode){bp.unshift(cur)}while(ap[i]===bp[i]){i++}return i?siblingCheck(ap[i],bp[i]):ap[i]===preferredDoc?-1:bp[i]===preferredDoc?1:0};return doc};Sizzle.matches=function(expr,elements){return Sizzle(expr,null,null,elements)};Sizzle.matchesSelector=function(elem,expr){if((elem.ownerDocument||elem)!==document){setDocument(elem)}expr=expr.replace(rattributeQuotes,"='$1']");if(support.matchesSelector&&documentIsHTML&&(!rbuggyMatches||!rbuggyMatches.test(expr))&&(!rbuggyQSA||!rbuggyQSA.test(expr))){try{var ret=matches.call(elem,expr);if(ret||support.disconnectedMatch||elem.document&&elem.document.nodeType!==11){return ret}}catch(e){}}return Sizzle(expr,document,null,[elem]).length>0};Sizzle.contains=function(context,elem){if((context.ownerDocument||context)!==document){setDocument(context)}return contains(context,elem)};Sizzle.attr=function(elem,name){if((elem.ownerDocument||elem)!==document){setDocument(elem)}var fn=Expr.attrHandle[name.toLowerCase()],val=fn&&hasOwn.call(Expr.attrHandle,name.toLowerCase())?fn(elem,name,!documentIsHTML):undefined;return val!==undefined?val:support.attributes||!documentIsHTML?elem.getAttribute(name):(val=elem.getAttributeNode(name))&&val.specified?val.value:null};Sizzle.error=function(msg){throw new Error("Syntax error, unrecognized expression: "+msg)};Sizzle.uniqueSort=function(results){var elem,duplicates=[],j=0,i=0;hasDuplicate=!support.detectDuplicates;sortInput=!support.sortStable&&results.slice(0);results.sort(sortOrder);if(hasDuplicate){while(elem=results[i++]){if(elem===results[i]){j=duplicates.push(i)}}while(j--){results.splice(duplicates[j],1)}}sortInput=null;return results};getText=Sizzle.getText=function(elem){var node,ret="",i=0,nodeType=elem.nodeType;if(!nodeType){while(node=elem[i++]){ret+=getText(node)}}else if(nodeType===1||nodeType===9||nodeType===11){if(typeof elem.textContent==="string"){return elem.textContent}else{for(elem=elem.firstChild;elem;elem=elem.nextSibling){ret+=getText(elem)}}}else if(nodeType===3||nodeType===4){return elem.nodeValue}return ret};Expr=Sizzle.selectors={cacheLength:50,createPseudo:markFunction,match:matchExpr,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:true}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:true},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(match){match[1]=match[1].replace(runescape,funescape);match[3]=(match[3]||match[4]||match[5]||"").replace(runescape,funescape);if(match[2]==="~="){match[3]=" "+match[3]+" "}return match.slice(0,4)},CHILD:function(match){match[1]=match[1].toLowerCase();if(match[1].slice(0,3)==="nth"){if(!match[3]){Sizzle.error(match[0])}match[4]=+(match[4]?match[5]+(match[6]||1):2*(match[3]==="even"||match[3]==="odd"));match[5]=+(match[7]+match[8]||match[3]==="odd")}else if(match[3]){Sizzle.error(match[0])}return match},PSEUDO:function(match){var excess,unquoted=!match[6]&&match[2];if(matchExpr["CHILD"].test(match[0])){return null}if(match[3]){match[2]=match[4]||match[5]||""}else if(unquoted&&rpseudo.test(unquoted)&&(excess=tokenize(unquoted,true))&&(excess=unquoted.indexOf(")",unquoted.length-excess)-unquoted.length)){match[0]=match[0].slice(0,excess);match[2]=unquoted.slice(0,excess)}return match.slice(0,3)}},filter:{TAG:function(nodeNameSelector){var nodeName=nodeNameSelector.replace(runescape,funescape).toLowerCase();return nodeNameSelector==="*"?function(){return true}:function(elem){return elem.nodeName&&elem.nodeName.toLowerCase()===nodeName}},CLASS:function(className){var pattern=classCache[className+" "];return pattern||(pattern=new RegExp("(^|"+whitespace+")"+className+"("+whitespace+"|$)"))&&classCache(className,function(elem){return pattern.test(typeof elem.className==="string"&&elem.className||typeof elem.getAttribute!=="undefined"&&elem.getAttribute("class")||"")})},ATTR:function(name,operator,check){return function(elem){var result=Sizzle.attr(elem,name);if(result==null){return operator==="!="}if(!operator){return true}result+="";return operator==="="?result===check:operator==="!="?result!==check:operator==="^="?check&&result.indexOf(check)===0:operator==="*="?check&&result.indexOf(check)>-1:operator==="$="?check&&result.slice(-check.length)===check:operator==="~="?(" "+result.replace(rwhitespace," ")+" ").indexOf(check)>-1:operator==="|="?result===check||result.slice(0,check.length+1)===check+"-":false}},CHILD:function(type,what,argument,first,last){var simple=type.slice(0,3)!=="nth",forward=type.slice(-4)!=="last",ofType=what==="of-type";return first===1&&last===0?function(elem){return!!elem.parentNode}:function(elem,context,xml){var cache,outerCache,node,diff,nodeIndex,start,dir=simple!==forward?"nextSibling":"previousSibling",parent=elem.parentNode,name=ofType&&elem.nodeName.toLowerCase(),useCache=!xml&&!ofType;if(parent){if(simple){while(dir){node=elem;while(node=node[dir]){if(ofType?node.nodeName.toLowerCase()===name:node.nodeType===1){return false}}start=dir=type==="only"&&!start&&"nextSibling"}return true}start=[forward?parent.firstChild:parent.lastChild];if(forward&&useCache){outerCache=parent[expando]||(parent[expando]={});cache=outerCache[type]||[];nodeIndex=cache[0]===dirruns&&cache[1];diff=cache[0]===dirruns&&cache[2];node=nodeIndex&&parent.childNodes[nodeIndex];while(node=++nodeIndex&&node&&node[dir]||(diff=nodeIndex=0)||start.pop()){if(node.nodeType===1&&++diff&&node===elem){outerCache[type]=[dirruns,nodeIndex,diff];break}}}else if(useCache&&(cache=(elem[expando]||(elem[expando]={}))[type])&&cache[0]===dirruns){diff=cache[1]}else{while(node=++nodeIndex&&node&&node[dir]||(diff=nodeIndex=0)||start.pop()){
14
- if((ofType?node.nodeName.toLowerCase()===name:node.nodeType===1)&&++diff){if(useCache){(node[expando]||(node[expando]={}))[type]=[dirruns,diff]}if(node===elem){break}}}}diff-=last;return diff===first||diff%first===0&&diff/first>=0}}},PSEUDO:function(pseudo,argument){var args,fn=Expr.pseudos[pseudo]||Expr.setFilters[pseudo.toLowerCase()]||Sizzle.error("unsupported pseudo: "+pseudo);if(fn[expando]){return fn(argument)}if(fn.length>1){args=[pseudo,pseudo,"",argument];return Expr.setFilters.hasOwnProperty(pseudo.toLowerCase())?markFunction(function(seed,matches){var idx,matched=fn(seed,argument),i=matched.length;while(i--){idx=indexOf(seed,matched[i]);seed[idx]=!(matches[idx]=matched[i])}}):function(elem){return fn(elem,0,args)}}return fn}},pseudos:{not:markFunction(function(selector){var input=[],results=[],matcher=compile(selector.replace(rtrim,"$1"));return matcher[expando]?markFunction(function(seed,matches,context,xml){var elem,unmatched=matcher(seed,null,xml,[]),i=seed.length;while(i--){if(elem=unmatched[i]){seed[i]=!(matches[i]=elem)}}}):function(elem,context,xml){input[0]=elem;matcher(input,null,xml,results);input[0]=null;return!results.pop()}}),has:markFunction(function(selector){return function(elem){return Sizzle(selector,elem).length>0}}),contains:markFunction(function(text){text=text.replace(runescape,funescape);return function(elem){return(elem.textContent||elem.innerText||getText(elem)).indexOf(text)>-1}}),lang:markFunction(function(lang){if(!ridentifier.test(lang||"")){Sizzle.error("unsupported lang: "+lang)}lang=lang.replace(runescape,funescape).toLowerCase();return function(elem){var elemLang;do{if(elemLang=documentIsHTML?elem.lang:elem.getAttribute("xml:lang")||elem.getAttribute("lang")){elemLang=elemLang.toLowerCase();return elemLang===lang||elemLang.indexOf(lang+"-")===0}}while((elem=elem.parentNode)&&elem.nodeType===1);return false}}),target:function(elem){var hash=window.location&&window.location.hash;return hash&&hash.slice(1)===elem.id},root:function(elem){return elem===docElem},focus:function(elem){return elem===document.activeElement&&(!document.hasFocus||document.hasFocus())&&!!(elem.type||elem.href||~elem.tabIndex)},enabled:function(elem){return elem.disabled===false},disabled:function(elem){return elem.disabled===true},checked:function(elem){var nodeName=elem.nodeName.toLowerCase();return nodeName==="input"&&!!elem.checked||nodeName==="option"&&!!elem.selected},selected:function(elem){if(elem.parentNode){elem.parentNode.selectedIndex}return elem.selected===true},empty:function(elem){for(elem=elem.firstChild;elem;elem=elem.nextSibling){if(elem.nodeType<6){return false}}return true},parent:function(elem){return!Expr.pseudos["empty"](elem)},header:function(elem){return rheader.test(elem.nodeName)},input:function(elem){return rinputs.test(elem.nodeName)},button:function(elem){var name=elem.nodeName.toLowerCase();return name==="input"&&elem.type==="button"||name==="button"},text:function(elem){var attr;return elem.nodeName.toLowerCase()==="input"&&elem.type==="text"&&((attr=elem.getAttribute("type"))==null||attr.toLowerCase()==="text")},first:createPositionalPseudo(function(){return[0]}),last:createPositionalPseudo(function(matchIndexes,length){return[length-1]}),eq:createPositionalPseudo(function(matchIndexes,length,argument){return[argument<0?argument+length:argument]}),even:createPositionalPseudo(function(matchIndexes,length){var i=0;for(;i<length;i+=2){matchIndexes.push(i)}return matchIndexes}),odd:createPositionalPseudo(function(matchIndexes,length){var i=1;for(;i<length;i+=2){matchIndexes.push(i)}return matchIndexes}),lt:createPositionalPseudo(function(matchIndexes,length,argument){var i=argument<0?argument+length:argument;for(;--i>=0;){matchIndexes.push(i)}return matchIndexes}),gt:createPositionalPseudo(function(matchIndexes,length,argument){var i=argument<0?argument+length:argument;for(;++i<length;){matchIndexes.push(i)}return matchIndexes})}};Expr.pseudos["nth"]=Expr.pseudos["eq"];for(i in{radio:true,checkbox:true,file:true,password:true,image:true}){Expr.pseudos[i]=createInputPseudo(i)}for(i in{submit:true,reset:true}){Expr.pseudos[i]=createButtonPseudo(i)}function setFilters(){}setFilters.prototype=Expr.filters=Expr.pseudos;Expr.setFilters=new setFilters;tokenize=Sizzle.tokenize=function(selector,parseOnly){var matched,match,tokens,type,soFar,groups,preFilters,cached=tokenCache[selector+" "];if(cached){return parseOnly?0:cached.slice(0)}soFar=selector;groups=[];preFilters=Expr.preFilter;while(soFar){if(!matched||(match=rcomma.exec(soFar))){if(match){soFar=soFar.slice(match[0].length)||soFar}groups.push(tokens=[])}matched=false;if(match=rcombinators.exec(soFar)){matched=match.shift();tokens.push({value:matched,type:match[0].replace(rtrim," ")});soFar=soFar.slice(matched.length)}for(type in Expr.filter){if((match=matchExpr[type].exec(soFar))&&(!preFilters[type]||(match=preFilters[type](match)))){matched=match.shift();tokens.push({value:matched,type:type,matches:match});soFar=soFar.slice(matched.length)}}if(!matched){break}}return parseOnly?soFar.length:soFar?Sizzle.error(selector):tokenCache(selector,groups).slice(0)};function toSelector(tokens){var i=0,len=tokens.length,selector="";for(;i<len;i++){selector+=tokens[i].value}return selector}function addCombinator(matcher,combinator,base){var dir=combinator.dir,checkNonElements=base&&dir==="parentNode",doneName=done++;return combinator.first?function(elem,context,xml){while(elem=elem[dir]){if(elem.nodeType===1||checkNonElements){return matcher(elem,context,xml)}}}:function(elem,context,xml){var oldCache,outerCache,newCache=[dirruns,doneName];if(xml){while(elem=elem[dir]){if(elem.nodeType===1||checkNonElements){if(matcher(elem,context,xml)){return true}}}}else{while(elem=elem[dir]){if(elem.nodeType===1||checkNonElements){outerCache=elem[expando]||(elem[expando]={});if((oldCache=outerCache[dir])&&oldCache[0]===dirruns&&oldCache[1]===doneName){return newCache[2]=oldCache[2]}else{outerCache[dir]=newCache;if(newCache[2]=matcher(elem,context,xml)){return true}}}}}}}function elementMatcher(matchers){return matchers.length>1?function(elem,context,xml){var i=matchers.length;while(i--){if(!matchers[i](elem,context,xml)){return false}}return true}:matchers[0]}function multipleContexts(selector,contexts,results){var i=0,len=contexts.length;for(;i<len;i++){Sizzle(selector,contexts[i],results)}return results}function condense(unmatched,map,filter,context,xml){var elem,newUnmatched=[],i=0,len=unmatched.length,mapped=map!=null;for(;i<len;i++){if(elem=unmatched[i]){if(!filter||filter(elem,context,xml)){newUnmatched.push(elem);if(mapped){map.push(i)}}}}return newUnmatched}function setMatcher(preFilter,selector,matcher,postFilter,postFinder,postSelector){if(postFilter&&!postFilter[expando]){postFilter=setMatcher(postFilter)}if(postFinder&&!postFinder[expando]){postFinder=setMatcher(postFinder,postSelector)}return markFunction(function(seed,results,context,xml){var temp,i,elem,preMap=[],postMap=[],preexisting=results.length,elems=seed||multipleContexts(selector||"*",context.nodeType?[context]:context,[]),matcherIn=preFilter&&(seed||!selector)?condense(elems,preMap,preFilter,context,xml):elems,matcherOut=matcher?postFinder||(seed?preFilter:preexisting||postFilter)?[]:results:matcherIn;if(matcher){matcher(matcherIn,matcherOut,context,xml)}if(postFilter){temp=condense(matcherOut,postMap);postFilter(temp,[],context,xml);i=temp.length;while(i--){if(elem=temp[i]){matcherOut[postMap[i]]=!(matcherIn[postMap[i]]=elem)}}}if(seed){if(postFinder||preFilter){if(postFinder){temp=[];i=matcherOut.length;while(i--){if(elem=matcherOut[i]){temp.push(matcherIn[i]=elem)}}postFinder(null,matcherOut=[],temp,xml)}i=matcherOut.length;while(i--){if((elem=matcherOut[i])&&(temp=postFinder?indexOf(seed,elem):preMap[i])>-1){seed[temp]=!(results[temp]=elem)}}}}else{matcherOut=condense(matcherOut===results?matcherOut.splice(preexisting,matcherOut.length):matcherOut);if(postFinder){postFinder(null,results,matcherOut,xml)}else{push.apply(results,matcherOut)}}})}function matcherFromTokens(tokens){var checkContext,matcher,j,len=tokens.length,leadingRelative=Expr.relative[tokens[0].type],implicitRelative=leadingRelative||Expr.relative[" "],i=leadingRelative?1:0,matchContext=addCombinator(function(elem){return elem===checkContext},implicitRelative,true),matchAnyContext=addCombinator(function(elem){return indexOf(checkContext,elem)>-1},implicitRelative,true),matchers=[function(elem,context,xml){var ret=!leadingRelative&&(xml||context!==outermostContext)||((checkContext=context).nodeType?matchContext(elem,context,xml):matchAnyContext(elem,context,xml));checkContext=null;return ret}];for(;i<len;i++){if(matcher=Expr.relative[tokens[i].type]){matchers=[addCombinator(elementMatcher(matchers),matcher)]}else{matcher=Expr.filter[tokens[i].type].apply(null,tokens[i].matches);if(matcher[expando]){j=++i;for(;j<len;j++){if(Expr.relative[tokens[j].type]){break}}return setMatcher(i>1&&elementMatcher(matchers),i>1&&toSelector(tokens.slice(0,i-1).concat({value:tokens[i-2].type===" "?"*":""})).replace(rtrim,"$1"),matcher,i<j&&matcherFromTokens(tokens.slice(i,j)),j<len&&matcherFromTokens(tokens=tokens.slice(j)),j<len&&toSelector(tokens))}matchers.push(matcher)}}return elementMatcher(matchers)}function matcherFromGroupMatchers(elementMatchers,setMatchers){var bySet=setMatchers.length>0,byElement=elementMatchers.length>0,superMatcher=function(seed,context,xml,results,outermost){var elem,j,matcher,matchedCount=0,i="0",unmatched=seed&&[],setMatched=[],contextBackup=outermostContext,elems=seed||byElement&&Expr.find["TAG"]("*",outermost),dirrunsUnique=dirruns+=contextBackup==null?1:Math.random()||.1,len=elems.length;if(outermost){outermostContext=context!==document&&context}for(;i!==len&&(elem=elems[i])!=null;i++){if(byElement&&elem){j=0;while(matcher=elementMatchers[j++]){if(matcher(elem,context,xml)){results.push(elem);break}}if(outermost){dirruns=dirrunsUnique}}if(bySet){if(elem=!matcher&&elem){matchedCount--}if(seed){unmatched.push(elem)}}}matchedCount+=i;if(bySet&&i!==matchedCount){j=0;while(matcher=setMatchers[j++]){matcher(unmatched,setMatched,context,xml)}if(seed){if(matchedCount>0){while(i--){if(!(unmatched[i]||setMatched[i])){setMatched[i]=pop.call(results)}}}setMatched=condense(setMatched)}push.apply(results,setMatched);if(outermost&&!seed&&setMatched.length>0&&matchedCount+setMatchers.length>1){Sizzle.uniqueSort(results)}}if(outermost){dirruns=dirrunsUnique;outermostContext=contextBackup}return unmatched};return bySet?markFunction(superMatcher):superMatcher}compile=Sizzle.compile=function(selector,match){var i,setMatchers=[],elementMatchers=[],cached=compilerCache[selector+" "];if(!cached){if(!match){match=tokenize(selector)}i=match.length;while(i--){cached=matcherFromTokens(match[i]);if(cached[expando]){setMatchers.push(cached)}else{elementMatchers.push(cached)}}cached=compilerCache(selector,matcherFromGroupMatchers(elementMatchers,setMatchers));cached.selector=selector}return cached};select=Sizzle.select=function(selector,context,results,seed){var i,tokens,token,type,find,compiled=typeof selector==="function"&&selector,match=!seed&&tokenize(selector=compiled.selector||selector);results=results||[];if(match.length===1){tokens=match[0]=match[0].slice(0);if(tokens.length>2&&(token=tokens[0]).type==="ID"&&support.getById&&context.nodeType===9&&documentIsHTML&&Expr.relative[tokens[1].type]){context=(Expr.find["ID"](token.matches[0].replace(runescape,funescape),context)||[])[0];if(!context){return results}else if(compiled){context=context.parentNode}selector=selector.slice(tokens.shift().value.length)}i=matchExpr["needsContext"].test(selector)?0:tokens.length;while(i--){token=tokens[i];if(Expr.relative[type=token.type]){break}if(find=Expr.find[type]){if(seed=find(token.matches[0].replace(runescape,funescape),rsibling.test(tokens[0].type)&&testContext(context.parentNode)||context)){tokens.splice(i,1);selector=seed.length&&toSelector(tokens);if(!selector){push.apply(results,seed);return results}break}}}}(compiled||compile(selector,match))(seed,context,!documentIsHTML,results,rsibling.test(selector)&&testContext(context.parentNode)||context);return results};support.sortStable=expando.split("").sort(sortOrder).join("")===expando;support.detectDuplicates=!!hasDuplicate;setDocument();support.sortDetached=assert(function(div1){return div1.compareDocumentPosition(document.createElement("div"))&1});if(!assert(function(div){div.innerHTML="<a href='#'></a>";return div.firstChild.getAttribute("href")==="#"})){addHandle("type|href|height|width",function(elem,name,isXML){if(!isXML){return elem.getAttribute(name,name.toLowerCase()==="type"?1:2)}})}if(!support.attributes||!assert(function(div){div.innerHTML="<input/>";div.firstChild.setAttribute("value","");return div.firstChild.getAttribute("value")===""})){addHandle("value",function(elem,name,isXML){if(!isXML&&elem.nodeName.toLowerCase()==="input"){return elem.defaultValue}})}if(!assert(function(div){return div.getAttribute("disabled")==null})){addHandle(booleans,function(elem,name,isXML){var val;if(!isXML){return elem[name]===true?name.toLowerCase():(val=elem.getAttributeNode(name))&&val.specified?val.value:null}})}return Sizzle}(window);jQuery.find=Sizzle;jQuery.expr=Sizzle.selectors;jQuery.expr[":"]=jQuery.expr.pseudos;jQuery.unique=Sizzle.uniqueSort;jQuery.text=Sizzle.getText;jQuery.isXMLDoc=Sizzle.isXML;jQuery.contains=Sizzle.contains;var rneedsContext=jQuery.expr.match.needsContext;var rsingleTag=/^<(\w+)\s*\/?>(?:<\/\1>|)$/;var risSimple=/^.[^:#\[\.,]*$/;function winnow(elements,qualifier,not){if(jQuery.isFunction(qualifier)){return jQuery.grep(elements,function(elem,i){return!!qualifier.call(elem,i,elem)!==not})}if(qualifier.nodeType){return jQuery.grep(elements,function(elem){return elem===qualifier!==not})}if(typeof qualifier==="string"){if(risSimple.test(qualifier)){return jQuery.filter(qualifier,elements,not)}qualifier=jQuery.filter(qualifier,elements)}return jQuery.grep(elements,function(elem){return jQuery.inArray(elem,qualifier)>=0!==not})}jQuery.filter=function(expr,elems,not){var elem=elems[0];if(not){expr=":not("+expr+")"}return elems.length===1&&elem.nodeType===1?jQuery.find.matchesSelector(elem,expr)?[elem]:[]:jQuery.find.matches(expr,jQuery.grep(elems,function(elem){return elem.nodeType===1}))};jQuery.fn.extend({find:function(selector){var i,ret=[],self=this,len=self.length;if(typeof selector!=="string"){return this.pushStack(jQuery(selector).filter(function(){for(i=0;i<len;i++){if(jQuery.contains(self[i],this)){return true}}}))}for(i=0;i<len;i++){jQuery.find(selector,self[i],ret)}ret=this.pushStack(len>1?jQuery.unique(ret):ret);ret.selector=this.selector?this.selector+" "+selector:selector;return ret},filter:function(selector){return this.pushStack(winnow(this,selector||[],false))},not:function(selector){return this.pushStack(winnow(this,selector||[],true))},is:function(selector){return!!winnow(this,typeof selector==="string"&&rneedsContext.test(selector)?jQuery(selector):selector||[],false).length}});var rootjQuery,document=window.document,rquickExpr=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]*))$/,init=jQuery.fn.init=function(selector,context){var match,elem;if(!selector){return this}if(typeof selector==="string"){if(selector.charAt(0)==="<"&&selector.charAt(selector.length-1)===">"&&selector.length>=3){match=[null,selector,null]}else{match=rquickExpr.exec(selector)}if(match&&(match[1]||!context)){if(match[1]){context=context instanceof jQuery?context[0]:context;jQuery.merge(this,jQuery.parseHTML(match[1],context&&context.nodeType?context.ownerDocument||context:document,true));if(rsingleTag.test(match[1])&&jQuery.isPlainObject(context)){for(match in context){if(jQuery.isFunction(this[match])){this[match](context[match])}else{this.attr(match,context[match])}}}return this}else{elem=document.getElementById(match[2]);if(elem&&elem.parentNode){if(elem.id!==match[2]){return rootjQuery.find(selector)}this.length=1;this[0]=elem}this.context=document;this.selector=selector;return this}}else if(!context||context.jquery){return(context||rootjQuery).find(selector)}else{return this.constructor(context).find(selector)}}else if(selector.nodeType){this.context=this[0]=selector;this.length=1;return this}else if(jQuery.isFunction(selector)){return typeof rootjQuery.ready!=="undefined"?rootjQuery.ready(selector):selector(jQuery)}if(selector.selector!==undefined){this.selector=selector.selector;this.context=selector.context}return jQuery.makeArray(selector,this)};init.prototype=jQuery.fn;rootjQuery=jQuery(document);var rparentsprev=/^(?:parents|prev(?:Until|All))/,guaranteedUnique={children:true,contents:true,next:true,prev:true};jQuery.extend({dir:function(elem,dir,until){var matched=[],cur=elem[dir];while(cur&&cur.nodeType!==9&&(until===undefined||cur.nodeType!==1||!jQuery(cur).is(until))){if(cur.nodeType===1){matched.push(cur)}cur=cur[dir]}return matched},sibling:function(n,elem){var r=[];for(;n;n=n.nextSibling){if(n.nodeType===1&&n!==elem){r.push(n)}}return r}});jQuery.fn.extend({has:function(target){var i,targets=jQuery(target,this),len=targets.length;return this.filter(function(){for(i=0;i<len;i++){if(jQuery.contains(this,targets[i])){return true}}})},closest:function(selectors,context){var cur,i=0,l=this.length,matched=[],pos=rneedsContext.test(selectors)||typeof selectors!=="string"?jQuery(selectors,context||this.context):0;for(;i<l;i++){for(cur=this[i];cur&&cur!==context;cur=cur.parentNode){if(cur.nodeType<11&&(pos?pos.index(cur)>-1:cur.nodeType===1&&jQuery.find.matchesSelector(cur,selectors))){matched.push(cur);break}}}return this.pushStack(matched.length>1?jQuery.unique(matched):matched)},index:function(elem){if(!elem){return this[0]&&this[0].parentNode?this.first().prevAll().length:-1}if(typeof elem==="string"){return jQuery.inArray(this[0],jQuery(elem))}return jQuery.inArray(elem.jquery?elem[0]:elem,this)},add:function(selector,context){return this.pushStack(jQuery.unique(jQuery.merge(this.get(),jQuery(selector,context))))},addBack:function(selector){return this.add(selector==null?this.prevObject:this.prevObject.filter(selector))}});function sibling(cur,dir){do{cur=cur[dir]}while(cur&&cur.nodeType!==1);return cur}jQuery.each({parent:function(elem){var parent=elem.parentNode;return parent&&parent.nodeType!==11?parent:null},parents:function(elem){return jQuery.dir(elem,"parentNode")},parentsUntil:function(elem,i,until){return jQuery.dir(elem,"parentNode",until)},next:function(elem){return sibling(elem,"nextSibling")},prev:function(elem){return sibling(elem,"previousSibling")},nextAll:function(elem){return jQuery.dir(elem,"nextSibling")},prevAll:function(elem){return jQuery.dir(elem,"previousSibling")},nextUntil:function(elem,i,until){return jQuery.dir(elem,"nextSibling",until)},prevUntil:function(elem,i,until){return jQuery.dir(elem,"previousSibling",until)},siblings:function(elem){return jQuery.sibling((elem.parentNode||{}).firstChild,elem)},children:function(elem){return jQuery.sibling(elem.firstChild)},contents:function(elem){return jQuery.nodeName(elem,"iframe")?elem.contentDocument||elem.contentWindow.document:jQuery.merge([],elem.childNodes)}},function(name,fn){jQuery.fn[name]=function(until,selector){var ret=jQuery.map(this,fn,until);if(name.slice(-5)!=="Until"){selector=until}if(selector&&typeof selector==="string"){ret=jQuery.filter(selector,ret)}if(this.length>1){if(!guaranteedUnique[name]){ret=jQuery.unique(ret)}if(rparentsprev.test(name)){ret=ret.reverse()}}return this.pushStack(ret)}});var rnotwhite=/\S+/g;var optionsCache={};function createOptions(options){var object=optionsCache[options]={};jQuery.each(options.match(rnotwhite)||[],function(_,flag){object[flag]=true});return object}jQuery.Callbacks=function(options){options=typeof options==="string"?optionsCache[options]||createOptions(options):jQuery.extend({},options);var firing,memory,fired,firingLength,firingIndex,firingStart,list=[],stack=!options.once&&[],fire=function(data){memory=options.memory&&data;fired=true;firingIndex=firingStart||0;firingStart=0;firingLength=list.length;firing=true;for(;list&&firingIndex<firingLength;firingIndex++){if(list[firingIndex].apply(data[0],data[1])===false&&options.stopOnFalse){memory=false;break}}firing=false;if(list){if(stack){if(stack.length){fire(stack.shift())}}else if(memory){list=[]}else{self.disable()}}},self={add:function(){if(list){var start=list.length;(function add(args){jQuery.each(args,function(_,arg){var type=jQuery.type(arg);if(type==="function"){if(!options.unique||!self.has(arg)){list.push(arg)}}else if(arg&&arg.length&&type!=="string"){add(arg)}})})(arguments);if(firing){firingLength=list.length}else if(memory){firingStart=start;fire(memory)}}return this},remove:function(){if(list){jQuery.each(arguments,function(_,arg){var index;while((index=jQuery.inArray(arg,list,index))>-1){list.splice(index,1);if(firing){if(index<=firingLength){firingLength--}if(index<=firingIndex){firingIndex--}}}})}return this},has:function(fn){return fn?jQuery.inArray(fn,list)>-1:!!(list&&list.length)},empty:function(){list=[];firingLength=0;return this},disable:function(){list=stack=memory=undefined;return this},disabled:function(){return!list},lock:function(){stack=undefined;if(!memory){self.disable()}return this},locked:function(){return!stack},fireWith:function(context,args){if(list&&(!fired||stack)){args=args||[];args=[context,args.slice?args.slice():args];if(firing){stack.push(args)}else{fire(args)}}return this},fire:function(){self.fireWith(this,arguments);return this},fired:function(){return!!fired}};return self};jQuery.extend({Deferred:function(func){var tuples=[["resolve","done",jQuery.Callbacks("once memory"),"resolved"],["reject","fail",jQuery.Callbacks("once memory"),"rejected"],["notify","progress",jQuery.Callbacks("memory")]],state="pending",promise={state:function(){return state},always:function(){deferred.done(arguments).fail(arguments);return this},then:function(){var fns=arguments;return jQuery.Deferred(function(newDefer){jQuery.each(tuples,function(i,tuple){var fn=jQuery.isFunction(fns[i])&&fns[i];deferred[tuple[1]](function(){var returned=fn&&fn.apply(this,arguments);if(returned&&jQuery.isFunction(returned.promise)){returned.promise().done(newDefer.resolve).fail(newDefer.reject).progress(newDefer.notify)}else{newDefer[tuple[0]+"With"](this===promise?newDefer.promise():this,fn?[returned]:arguments)}})});fns=null}).promise()},promise:function(obj){return obj!=null?jQuery.extend(obj,promise):promise}},deferred={};promise.pipe=promise.then;jQuery.each(tuples,function(i,tuple){var list=tuple[2],stateString=tuple[3];promise[tuple[1]]=list.add;if(stateString){list.add(function(){state=stateString},tuples[i^1][2].disable,tuples[2][2].lock)}deferred[tuple[0]]=function(){deferred[tuple[0]+"With"](this===deferred?promise:this,arguments);return this};deferred[tuple[0]+"With"]=list.fireWith});promise.promise(deferred);if(func){func.call(deferred,deferred)}return deferred},when:function(subordinate){var i=0,resolveValues=slice.call(arguments),length=resolveValues.length,remaining=length!==1||subordinate&&jQuery.isFunction(subordinate.promise)?length:0,deferred=remaining===1?subordinate:jQuery.Deferred(),updateFunc=function(i,contexts,values){return function(value){contexts[i]=this;values[i]=arguments.length>1?slice.call(arguments):value;if(values===progressValues){deferred.notifyWith(contexts,values)}else if(!--remaining){deferred.resolveWith(contexts,values)}}},progressValues,progressContexts,resolveContexts;if(length>1){progressValues=new Array(length);progressContexts=new Array(length);resolveContexts=new Array(length);for(;i<length;i++){if(resolveValues[i]&&jQuery.isFunction(resolveValues[i].promise)){resolveValues[i].promise().done(updateFunc(i,resolveContexts,resolveValues)).fail(deferred.reject).progress(updateFunc(i,progressContexts,progressValues))}else{--remaining}}}if(!remaining){deferred.resolveWith(resolveContexts,resolveValues)}return deferred.promise()}});var readyList;jQuery.fn.ready=function(fn){jQuery.ready.promise().done(fn);return this};jQuery.extend({isReady:false,readyWait:1,holdReady:function(hold){if(hold){jQuery.readyWait++}else{jQuery.ready(true)}},ready:function(wait){if(wait===true?--jQuery.readyWait:jQuery.isReady){return}if(!document.body){return setTimeout(jQuery.ready)}jQuery.isReady=true;if(wait!==true&&--jQuery.readyWait>0){return}readyList.resolveWith(document,[jQuery]);if(jQuery.fn.triggerHandler){jQuery(document).triggerHandler("ready");jQuery(document).off("ready")}}});function detach(){if(document.addEventListener){document.removeEventListener("DOMContentLoaded",completed,false);window.removeEventListener("load",completed,false)}else{document.detachEvent("onreadystatechange",completed);window.detachEvent("onload",completed)}}function completed(){if(document.addEventListener||event.type==="load"||document.readyState==="complete"){detach();jQuery.ready()}}jQuery.ready.promise=function(obj){if(!readyList){readyList=jQuery.Deferred();if(document.readyState==="complete"){setTimeout(jQuery.ready)}else if(document.addEventListener){document.addEventListener("DOMContentLoaded",completed,false);window.addEventListener("load",completed,false)}else{document.attachEvent("onreadystatechange",completed);window.attachEvent("onload",completed);var top=false;try{top=window.frameElement==null&&document.documentElement}catch(e){}if(top&&top.doScroll){(function doScrollCheck(){if(!jQuery.isReady){try{top.doScroll("left")}catch(e){return setTimeout(doScrollCheck,50)}detach();jQuery.ready()}})()}}}return readyList.promise(obj)};var strundefined=typeof undefined;var i;for(i in jQuery(support)){break}support.ownLast=i!=="0";support.inlineBlockNeedsLayout=false;jQuery(function(){var val,div,body,container;body=document.getElementsByTagName("body")[0];if(!body||!body.style){return}div=document.createElement("div");container=document.createElement("div");container.style.cssText="position:absolute;border:0;width:0;height:0;top:0;left:-9999px";body.appendChild(container).appendChild(div);if(typeof div.style.zoom!==strundefined){div.style.cssText="display:inline;margin:0;border:0;padding:1px;width:1px;zoom:1";support.inlineBlockNeedsLayout=val=div.offsetWidth===3;if(val){body.style.zoom=1}}body.removeChild(container)});(function(){var div=document.createElement("div");if(support.deleteExpando==null){support.deleteExpando=true;try{delete div.test}catch(e){support.deleteExpando=false}}div=null})();jQuery.acceptData=function(elem){var noData=jQuery.noData[(elem.nodeName+" ").toLowerCase()],nodeType=+elem.nodeType||1;return nodeType!==1&&nodeType!==9?false:!noData||noData!==true&&elem.getAttribute("classid")===noData};var rbrace=/^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,rmultiDash=/([A-Z])/g;function dataAttr(elem,key,data){if(data===undefined&&elem.nodeType===1){var name="data-"+key.replace(rmultiDash,"-$1").toLowerCase();data=elem.getAttribute(name);if(typeof data==="string"){try{data=data==="true"?true:data==="false"?false:data==="null"?null:+data+""===data?+data:rbrace.test(data)?jQuery.parseJSON(data):data}catch(e){}jQuery.data(elem,key,data)}else{data=undefined}}return data}function isEmptyDataObject(obj){var name;for(name in obj){if(name==="data"&&jQuery.isEmptyObject(obj[name])){continue}if(name!=="toJSON"){return false}}return true}function internalData(elem,name,data,pvt){if(!jQuery.acceptData(elem)){return}var ret,thisCache,internalKey=jQuery.expando,isNode=elem.nodeType,cache=isNode?jQuery.cache:elem,id=isNode?elem[internalKey]:elem[internalKey]&&internalKey;if((!id||!cache[id]||!pvt&&!cache[id].data)&&data===undefined&&typeof name==="string"){return}if(!id){if(isNode){id=elem[internalKey]=deletedIds.pop()||jQuery.guid++}else{id=internalKey}}if(!cache[id]){cache[id]=isNode?{}:{toJSON:jQuery.noop}}if(typeof name==="object"||typeof name==="function"){if(pvt){cache[id]=jQuery.extend(cache[id],name)}else{cache[id].data=jQuery.extend(cache[id].data,name)}}thisCache=cache[id];if(!pvt){if(!thisCache.data){thisCache.data={}}thisCache=thisCache.data}if(data!==undefined){thisCache[jQuery.camelCase(name)]=data}if(typeof name==="string"){ret=thisCache[name];if(ret==null){ret=thisCache[jQuery.camelCase(name)]}}else{ret=thisCache}return ret}function internalRemoveData(elem,name,pvt){if(!jQuery.acceptData(elem)){return}var thisCache,i,isNode=elem.nodeType,cache=isNode?jQuery.cache:elem,id=isNode?elem[jQuery.expando]:jQuery.expando;if(!cache[id]){return}if(name){thisCache=pvt?cache[id]:cache[id].data;if(thisCache){if(!jQuery.isArray(name)){if(name in thisCache){name=[name]}else{name=jQuery.camelCase(name);if(name in thisCache){name=[name]}else{name=name.split(" ")}}}else{name=name.concat(jQuery.map(name,jQuery.camelCase))}i=name.length;while(i--){delete thisCache[name[i]]}if(pvt?!isEmptyDataObject(thisCache):!jQuery.isEmptyObject(thisCache)){return}}}if(!pvt){delete cache[id].data;if(!isEmptyDataObject(cache[id])){return}}if(isNode){jQuery.cleanData([elem],true)}else if(support.deleteExpando||cache!=cache.window){delete cache[id]}else{cache[id]=null}}jQuery.extend({cache:{},noData:{"applet ":true,"embed ":true,"object ":"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"},hasData:function(elem){elem=elem.nodeType?jQuery.cache[elem[jQuery.expando]]:elem[jQuery.expando];return!!elem&&!isEmptyDataObject(elem)},data:function(elem,name,data){return internalData(elem,name,data)},removeData:function(elem,name){return internalRemoveData(elem,name)},_data:function(elem,name,data){return internalData(elem,name,data,true)},_removeData:function(elem,name){return internalRemoveData(elem,name,true)}});jQuery.fn.extend({data:function(key,value){var i,name,data,elem=this[0],attrs=elem&&elem.attributes;if(key===undefined){if(this.length){data=jQuery.data(elem);if(elem.nodeType===1&&!jQuery._data(elem,"parsedAttrs")){i=attrs.length;while(i--){if(attrs[i]){name=attrs[i].name;if(name.indexOf("data-")===0){name=jQuery.camelCase(name.slice(5));dataAttr(elem,name,data[name])}}}jQuery._data(elem,"parsedAttrs",true)}}return data}if(typeof key==="object"){return this.each(function(){jQuery.data(this,key)})}return arguments.length>1?this.each(function(){jQuery.data(this,key,value)}):elem?dataAttr(elem,key,jQuery.data(elem,key)):undefined},removeData:function(key){return this.each(function(){jQuery.removeData(this,key)})}});jQuery.extend({queue:function(elem,type,data){var queue;if(elem){type=(type||"fx")+"queue";queue=jQuery._data(elem,type);if(data){if(!queue||jQuery.isArray(data)){queue=jQuery._data(elem,type,jQuery.makeArray(data))}else{queue.push(data)}}return queue||[]}},dequeue:function(elem,type){type=type||"fx";var queue=jQuery.queue(elem,type),startLength=queue.length,fn=queue.shift(),hooks=jQuery._queueHooks(elem,type),next=function(){jQuery.dequeue(elem,type)};if(fn==="inprogress"){fn=queue.shift();startLength--}if(fn){if(type==="fx"){queue.unshift("inprogress")}delete hooks.stop;fn.call(elem,next,hooks)}if(!startLength&&hooks){hooks.empty.fire()}},_queueHooks:function(elem,type){var key=type+"queueHooks";return jQuery._data(elem,key)||jQuery._data(elem,key,{empty:jQuery.Callbacks("once memory").add(function(){jQuery._removeData(elem,type+"queue");jQuery._removeData(elem,key)})})}});jQuery.fn.extend({queue:function(type,data){var setter=2;if(typeof type!=="string"){data=type;type="fx";setter--}if(arguments.length<setter){return jQuery.queue(this[0],type)}return data===undefined?this:this.each(function(){var queue=jQuery.queue(this,type,data);jQuery._queueHooks(this,type);if(type==="fx"&&queue[0]!=="inprogress"){jQuery.dequeue(this,type)}})},dequeue:function(type){return this.each(function(){jQuery.dequeue(this,type)})},clearQueue:function(type){return this.queue(type||"fx",[])},promise:function(type,obj){var tmp,count=1,defer=jQuery.Deferred(),elements=this,i=this.length,resolve=function(){if(!--count){defer.resolveWith(elements,[elements])}};if(typeof type!=="string"){obj=type;type=undefined}type=type||"fx";while(i--){tmp=jQuery._data(elements[i],type+"queueHooks");
15
 
16
- if(tmp&&tmp.empty){count++;tmp.empty.add(resolve)}}resolve();return defer.promise(obj)}});var pnum=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source;var cssExpand=["Top","Right","Bottom","Left"];var isHidden=function(elem,el){elem=el||elem;return jQuery.css(elem,"display")==="none"||!jQuery.contains(elem.ownerDocument,elem)};var access=jQuery.access=function(elems,fn,key,value,chainable,emptyGet,raw){var i=0,length=elems.length,bulk=key==null;if(jQuery.type(key)==="object"){chainable=true;for(i in key){jQuery.access(elems,fn,i,key[i],true,emptyGet,raw)}}else if(value!==undefined){chainable=true;if(!jQuery.isFunction(value)){raw=true}if(bulk){if(raw){fn.call(elems,value);fn=null}else{bulk=fn;fn=function(elem,key,value){return bulk.call(jQuery(elem),value)}}}if(fn){for(;i<length;i++){fn(elems[i],key,raw?value:value.call(elems[i],i,fn(elems[i],key)))}}}return chainable?elems:bulk?fn.call(elems):length?fn(elems[0],key):emptyGet};var rcheckableType=/^(?:checkbox|radio)$/i;(function(){var input=document.createElement("input"),div=document.createElement("div"),fragment=document.createDocumentFragment();div.innerHTML=" <link/><table></table><a href='/a'>a</a><input type='checkbox'/>";support.leadingWhitespace=div.firstChild.nodeType===3;support.tbody=!div.getElementsByTagName("tbody").length;support.htmlSerialize=!!div.getElementsByTagName("link").length;support.html5Clone=document.createElement("nav").cloneNode(true).outerHTML!=="<:nav></:nav>";input.type="checkbox";input.checked=true;fragment.appendChild(input);support.appendChecked=input.checked;div.innerHTML="<textarea>x</textarea>";support.noCloneChecked=!!div.cloneNode(true).lastChild.defaultValue;fragment.appendChild(div);div.innerHTML="<input type='radio' checked='checked' name='t'/>";support.checkClone=div.cloneNode(true).cloneNode(true).lastChild.checked;support.noCloneEvent=true;if(div.attachEvent){div.attachEvent("onclick",function(){support.noCloneEvent=false});div.cloneNode(true).click()}if(support.deleteExpando==null){support.deleteExpando=true;try{delete div.test}catch(e){support.deleteExpando=false}}})();(function(){var i,eventName,div=document.createElement("div");for(i in{submit:true,change:true,focusin:true}){eventName="on"+i;if(!(support[i+"Bubbles"]=eventName in window)){div.setAttribute(eventName,"t");support[i+"Bubbles"]=div.attributes[eventName].expando===false}}div=null})();var rformElems=/^(?:input|select|textarea)$/i,rkeyEvent=/^key/,rmouseEvent=/^(?:mouse|pointer|contextmenu)|click/,rfocusMorph=/^(?:focusinfocus|focusoutblur)$/,rtypenamespace=/^([^.]*)(?:\.(.+)|)$/;function returnTrue(){return true}function returnFalse(){return false}function safeActiveElement(){try{return document.activeElement}catch(err){}}jQuery.event={global:{},add:function(elem,types,handler,data,selector){var tmp,events,t,handleObjIn,special,eventHandle,handleObj,handlers,type,namespaces,origType,elemData=jQuery._data(elem);if(!elemData){return}if(handler.handler){handleObjIn=handler;handler=handleObjIn.handler;selector=handleObjIn.selector}if(!handler.guid){handler.guid=jQuery.guid++}if(!(events=elemData.events)){events=elemData.events={}}if(!(eventHandle=elemData.handle)){eventHandle=elemData.handle=function(e){return typeof jQuery!==strundefined&&(!e||jQuery.event.triggered!==e.type)?jQuery.event.dispatch.apply(eventHandle.elem,arguments):undefined};eventHandle.elem=elem}types=(types||"").match(rnotwhite)||[""];t=types.length;while(t--){tmp=rtypenamespace.exec(types[t])||[];type=origType=tmp[1];namespaces=(tmp[2]||"").split(".").sort();if(!type){continue}special=jQuery.event.special[type]||{};type=(selector?special.delegateType:special.bindType)||type;special=jQuery.event.special[type]||{};handleObj=jQuery.extend({type:type,origType:origType,data:data,handler:handler,guid:handler.guid,selector:selector,needsContext:selector&&jQuery.expr.match.needsContext.test(selector),namespace:namespaces.join(".")},handleObjIn);if(!(handlers=events[type])){handlers=events[type]=[];handlers.delegateCount=0;if(!special.setup||special.setup.call(elem,data,namespaces,eventHandle)===false){if(elem.addEventListener){elem.addEventListener(type,eventHandle,false)}else if(elem.attachEvent){elem.attachEvent("on"+type,eventHandle)}}}if(special.add){special.add.call(elem,handleObj);if(!handleObj.handler.guid){handleObj.handler.guid=handler.guid}}if(selector){handlers.splice(handlers.delegateCount++,0,handleObj)}else{handlers.push(handleObj)}jQuery.event.global[type]=true}elem=null},remove:function(elem,types,handler,selector,mappedTypes){var j,handleObj,tmp,origCount,t,events,special,handlers,type,namespaces,origType,elemData=jQuery.hasData(elem)&&jQuery._data(elem);if(!elemData||!(events=elemData.events)){return}types=(types||"").match(rnotwhite)||[""];t=types.length;while(t--){tmp=rtypenamespace.exec(types[t])||[];type=origType=tmp[1];namespaces=(tmp[2]||"").split(".").sort();if(!type){for(type in events){jQuery.event.remove(elem,type+types[t],handler,selector,true)}continue}special=jQuery.event.special[type]||{};type=(selector?special.delegateType:special.bindType)||type;handlers=events[type]||[];tmp=tmp[2]&&new RegExp("(^|\\.)"+namespaces.join("\\.(?:.*\\.|)")+"(\\.|$)");origCount=j=handlers.length;while(j--){handleObj=handlers[j];if((mappedTypes||origType===handleObj.origType)&&(!handler||handler.guid===handleObj.guid)&&(!tmp||tmp.test(handleObj.namespace))&&(!selector||selector===handleObj.selector||selector==="**"&&handleObj.selector)){handlers.splice(j,1);if(handleObj.selector){handlers.delegateCount--}if(special.remove){special.remove.call(elem,handleObj)}}}if(origCount&&!handlers.length){if(!special.teardown||special.teardown.call(elem,namespaces,elemData.handle)===false){jQuery.removeEvent(elem,type,elemData.handle)}delete events[type]}}if(jQuery.isEmptyObject(events)){delete elemData.handle;jQuery._removeData(elem,"events")}},trigger:function(event,data,elem,onlyHandlers){var handle,ontype,cur,bubbleType,special,tmp,i,eventPath=[elem||document],type=hasOwn.call(event,"type")?event.type:event,namespaces=hasOwn.call(event,"namespace")?event.namespace.split("."):[];cur=tmp=elem=elem||document;if(elem.nodeType===3||elem.nodeType===8){return}if(rfocusMorph.test(type+jQuery.event.triggered)){return}if(type.indexOf(".")>=0){namespaces=type.split(".");type=namespaces.shift();namespaces.sort()}ontype=type.indexOf(":")<0&&"on"+type;event=event[jQuery.expando]?event:new jQuery.Event(type,typeof event==="object"&&event);event.isTrigger=onlyHandlers?2:3;event.namespace=namespaces.join(".");event.namespace_re=event.namespace?new RegExp("(^|\\.)"+namespaces.join("\\.(?:.*\\.|)")+"(\\.|$)"):null;event.result=undefined;if(!event.target){event.target=elem}data=data==null?[event]:jQuery.makeArray(data,[event]);special=jQuery.event.special[type]||{};if(!onlyHandlers&&special.trigger&&special.trigger.apply(elem,data)===false){return}if(!onlyHandlers&&!special.noBubble&&!jQuery.isWindow(elem)){bubbleType=special.delegateType||type;if(!rfocusMorph.test(bubbleType+type)){cur=cur.parentNode}for(;cur;cur=cur.parentNode){eventPath.push(cur);tmp=cur}if(tmp===(elem.ownerDocument||document)){eventPath.push(tmp.defaultView||tmp.parentWindow||window)}}i=0;while((cur=eventPath[i++])&&!event.isPropagationStopped()){event.type=i>1?bubbleType:special.bindType||type;handle=(jQuery._data(cur,"events")||{})[event.type]&&jQuery._data(cur,"handle");if(handle){handle.apply(cur,data)}handle=ontype&&cur[ontype];if(handle&&handle.apply&&jQuery.acceptData(cur)){event.result=handle.apply(cur,data);if(event.result===false){event.preventDefault()}}}event.type=type;if(!onlyHandlers&&!event.isDefaultPrevented()){if((!special._default||special._default.apply(eventPath.pop(),data)===false)&&jQuery.acceptData(elem)){if(ontype&&elem[type]&&!jQuery.isWindow(elem)){tmp=elem[ontype];if(tmp){elem[ontype]=null}jQuery.event.triggered=type;try{elem[type]()}catch(e){}jQuery.event.triggered=undefined;if(tmp){elem[ontype]=tmp}}}}return event.result},dispatch:function(event){event=jQuery.event.fix(event);var i,ret,handleObj,matched,j,handlerQueue=[],args=slice.call(arguments),handlers=(jQuery._data(this,"events")||{})[event.type]||[],special=jQuery.event.special[event.type]||{};args[0]=event;event.delegateTarget=this;if(special.preDispatch&&special.preDispatch.call(this,event)===false){return}handlerQueue=jQuery.event.handlers.call(this,event,handlers);i=0;while((matched=handlerQueue[i++])&&!event.isPropagationStopped()){event.currentTarget=matched.elem;j=0;while((handleObj=matched.handlers[j++])&&!event.isImmediatePropagationStopped()){if(!event.namespace_re||event.namespace_re.test(handleObj.namespace)){event.handleObj=handleObj;event.data=handleObj.data;ret=((jQuery.event.special[handleObj.origType]||{}).handle||handleObj.handler).apply(matched.elem,args);if(ret!==undefined){if((event.result=ret)===false){event.preventDefault();event.stopPropagation()}}}}}if(special.postDispatch){special.postDispatch.call(this,event)}return event.result},handlers:function(event,handlers){var sel,handleObj,matches,i,handlerQueue=[],delegateCount=handlers.delegateCount,cur=event.target;if(delegateCount&&cur.nodeType&&(!event.button||event.type!=="click")){for(;cur!=this;cur=cur.parentNode||this){if(cur.nodeType===1&&(cur.disabled!==true||event.type!=="click")){matches=[];for(i=0;i<delegateCount;i++){handleObj=handlers[i];sel=handleObj.selector+" ";if(matches[sel]===undefined){matches[sel]=handleObj.needsContext?jQuery(sel,this).index(cur)>=0:jQuery.find(sel,this,null,[cur]).length}if(matches[sel]){matches.push(handleObj)}}if(matches.length){handlerQueue.push({elem:cur,handlers:matches})}}}}if(delegateCount<handlers.length){handlerQueue.push({elem:this,handlers:handlers.slice(delegateCount)})}return handlerQueue},fix:function(event){if(event[jQuery.expando]){return event}var i,prop,copy,type=event.type,originalEvent=event,fixHook=this.fixHooks[type];if(!fixHook){this.fixHooks[type]=fixHook=rmouseEvent.test(type)?this.mouseHooks:rkeyEvent.test(type)?this.keyHooks:{}}copy=fixHook.props?this.props.concat(fixHook.props):this.props;event=new jQuery.Event(originalEvent);i=copy.length;while(i--){prop=copy[i];event[prop]=originalEvent[prop]}if(!event.target){event.target=originalEvent.srcElement||document}if(event.target.nodeType===3){event.target=event.target.parentNode}event.metaKey=!!event.metaKey;return fixHook.filter?fixHook.filter(event,originalEvent):event},props:"altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "),fixHooks:{},keyHooks:{props:"char charCode key keyCode".split(" "),filter:function(event,original){if(event.which==null){event.which=original.charCode!=null?original.charCode:original.keyCode}return event}},mouseHooks:{props:"button buttons clientX clientY fromElement offsetX offsetY pageX pageY screenX screenY toElement".split(" "),filter:function(event,original){var body,eventDoc,doc,button=original.button,fromElement=original.fromElement;if(event.pageX==null&&original.clientX!=null){eventDoc=event.target.ownerDocument||document;doc=eventDoc.documentElement;body=eventDoc.body;event.pageX=original.clientX+(doc&&doc.scrollLeft||body&&body.scrollLeft||0)-(doc&&doc.clientLeft||body&&body.clientLeft||0);event.pageY=original.clientY+(doc&&doc.scrollTop||body&&body.scrollTop||0)-(doc&&doc.clientTop||body&&body.clientTop||0)}if(!event.relatedTarget&&fromElement){event.relatedTarget=fromElement===event.target?original.toElement:fromElement}if(!event.which&&button!==undefined){event.which=button&1?1:button&2?3:button&4?2:0}return event}},special:{load:{noBubble:true},focus:{trigger:function(){if(this!==safeActiveElement()&&this.focus){try{this.focus();return false}catch(e){}}},delegateType:"focusin"},blur:{trigger:function(){if(this===safeActiveElement()&&this.blur){this.blur();return false}},delegateType:"focusout"},click:{trigger:function(){if(jQuery.nodeName(this,"input")&&this.type==="checkbox"&&this.click){this.click();return false}},_default:function(event){return jQuery.nodeName(event.target,"a")}},beforeunload:{postDispatch:function(event){if(event.result!==undefined&&event.originalEvent){event.originalEvent.returnValue=event.result}}}},simulate:function(type,elem,event,bubble){var e=jQuery.extend(new jQuery.Event,event,{type:type,isSimulated:true,originalEvent:{}});if(bubble){jQuery.event.trigger(e,null,elem)}else{jQuery.event.dispatch.call(elem,e)}if(e.isDefaultPrevented()){event.preventDefault()}}};jQuery.removeEvent=document.removeEventListener?function(elem,type,handle){if(elem.removeEventListener){elem.removeEventListener(type,handle,false)}}:function(elem,type,handle){var name="on"+type;if(elem.detachEvent){if(typeof elem[name]===strundefined){elem[name]=null}elem.detachEvent(name,handle)}};jQuery.Event=function(src,props){if(!(this instanceof jQuery.Event)){return new jQuery.Event(src,props)}if(src&&src.type){this.originalEvent=src;this.type=src.type;this.isDefaultPrevented=src.defaultPrevented||src.defaultPrevented===undefined&&src.returnValue===false?returnTrue:returnFalse}else{this.type=src}if(props){jQuery.extend(this,props)}this.timeStamp=src&&src.timeStamp||jQuery.now();this[jQuery.expando]=true};jQuery.Event.prototype={isDefaultPrevented:returnFalse,isPropagationStopped:returnFalse,isImmediatePropagationStopped:returnFalse,preventDefault:function(){var e=this.originalEvent;this.isDefaultPrevented=returnTrue;if(!e){return}if(e.preventDefault){e.preventDefault()}else{e.returnValue=false}},stopPropagation:function(){var e=this.originalEvent;this.isPropagationStopped=returnTrue;if(!e){return}if(e.stopPropagation){e.stopPropagation()}e.cancelBubble=true},stopImmediatePropagation:function(){var e=this.originalEvent;this.isImmediatePropagationStopped=returnTrue;if(e&&e.stopImmediatePropagation){e.stopImmediatePropagation()}this.stopPropagation()}};jQuery.each({mouseenter:"mouseover",mouseleave:"mouseout",pointerenter:"pointerover",pointerleave:"pointerout"},function(orig,fix){jQuery.event.special[orig]={delegateType:fix,bindType:fix,handle:function(event){var ret,target=this,related=event.relatedTarget,handleObj=event.handleObj;if(!related||related!==target&&!jQuery.contains(target,related)){event.type=handleObj.origType;ret=handleObj.handler.apply(this,arguments);event.type=fix}return ret}}});if(!support.submitBubbles){jQuery.event.special.submit={setup:function(){if(jQuery.nodeName(this,"form")){return false}jQuery.event.add(this,"click._submit keypress._submit",function(e){var elem=e.target,form=jQuery.nodeName(elem,"input")||jQuery.nodeName(elem,"button")?elem.form:undefined;if(form&&!jQuery._data(form,"submitBubbles")){jQuery.event.add(form,"submit._submit",function(event){event._submit_bubble=true});jQuery._data(form,"submitBubbles",true)}})},postDispatch:function(event){if(event._submit_bubble){delete event._submit_bubble;if(this.parentNode&&!event.isTrigger){jQuery.event.simulate("submit",this.parentNode,event,true)}}},teardown:function(){if(jQuery.nodeName(this,"form")){return false}jQuery.event.remove(this,"._submit")}}}if(!support.changeBubbles){jQuery.event.special.change={setup:function(){if(rformElems.test(this.nodeName)){if(this.type==="checkbox"||this.type==="radio"){jQuery.event.add(this,"propertychange._change",function(event){if(event.originalEvent.propertyName==="checked"){this._just_changed=true}});jQuery.event.add(this,"click._change",function(event){if(this._just_changed&&!event.isTrigger){this._just_changed=false}jQuery.event.simulate("change",this,event,true)})}return false}jQuery.event.add(this,"beforeactivate._change",function(e){var elem=e.target;if(rformElems.test(elem.nodeName)&&!jQuery._data(elem,"changeBubbles")){jQuery.event.add(elem,"change._change",function(event){if(this.parentNode&&!event.isSimulated&&!event.isTrigger){jQuery.event.simulate("change",this.parentNode,event,true)}});jQuery._data(elem,"changeBubbles",true)}})},handle:function(event){var elem=event.target;if(this!==elem||event.isSimulated||event.isTrigger||elem.type!=="radio"&&elem.type!=="checkbox"){return event.handleObj.handler.apply(this,arguments)}},teardown:function(){jQuery.event.remove(this,"._change");return!rformElems.test(this.nodeName)}}}if(!support.focusinBubbles){jQuery.each({focus:"focusin",blur:"focusout"},function(orig,fix){var handler=function(event){jQuery.event.simulate(fix,event.target,jQuery.event.fix(event),true)};jQuery.event.special[fix]={setup:function(){var doc=this.ownerDocument||this,attaches=jQuery._data(doc,fix);if(!attaches){doc.addEventListener(orig,handler,true)}jQuery._data(doc,fix,(attaches||0)+1)},teardown:function(){var doc=this.ownerDocument||this,attaches=jQuery._data(doc,fix)-1;if(!attaches){doc.removeEventListener(orig,handler,true);jQuery._removeData(doc,fix)}else{jQuery._data(doc,fix,attaches)}}}})}jQuery.fn.extend({on:function(types,selector,data,fn,one){var type,origFn;if(typeof types==="object"){if(typeof selector!=="string"){data=data||selector;selector=undefined}for(type in types){this.on(type,selector,data,types[type],one)}return this}if(data==null&&fn==null){fn=selector;data=selector=undefined}else if(fn==null){if(typeof selector==="string"){fn=data;data=undefined}else{fn=data;data=selector;selector=undefined}}if(fn===false){fn=returnFalse}else if(!fn){return this}if(one===1){origFn=fn;fn=function(event){jQuery().off(event);return origFn.apply(this,arguments)};fn.guid=origFn.guid||(origFn.guid=jQuery.guid++)}return this.each(function(){jQuery.event.add(this,types,fn,data,selector)})},one:function(types,selector,data,fn){return this.on(types,selector,data,fn,1)},off:function(types,selector,fn){var handleObj,type;if(types&&types.preventDefault&&types.handleObj){handleObj=types.handleObj;jQuery(types.delegateTarget).off(handleObj.namespace?handleObj.origType+"."+handleObj.namespace:handleObj.origType,handleObj.selector,handleObj.handler);return this}if(typeof types==="object"){for(type in types){this.off(type,selector,types[type])}return this}if(selector===false||typeof selector==="function"){fn=selector;selector=undefined}if(fn===false){fn=returnFalse}return this.each(function(){jQuery.event.remove(this,types,fn,selector)})},trigger:function(type,data){return this.each(function(){jQuery.event.trigger(type,data,this)})},triggerHandler:function(type,data){var elem=this[0];if(elem){return jQuery.event.trigger(type,data,elem,true)}}});function createSafeFragment(document){var list=nodeNames.split("|"),safeFrag=document.createDocumentFragment();if(safeFrag.createElement){while(list.length){safeFrag.createElement(list.pop())}}return safeFrag}var nodeNames="abbr|article|aside|audio|bdi|canvas|data|datalist|details|figcaption|figure|footer|"+"header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",rinlinejQuery=/ jQuery\d+="(?:null|\d+)"/g,rnoshimcache=new RegExp("<(?:"+nodeNames+")[\\s/>]","i"),rleadingWhitespace=/^\s+/,rxhtmlTag=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,rtagName=/<([\w:]+)/,rtbody=/<tbody/i,rhtml=/<|&#?\w+;/,rnoInnerhtml=/<(?:script|style|link)/i,rchecked=/checked\s*(?:[^=]|=\s*.checked.)/i,rscriptType=/^$|\/(?:java|ecma)script/i,rscriptTypeMasked=/^true\/(.*)/,rcleanScript=/^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g,wrapMap={option:[1,"<select multiple='multiple'>","</select>"],legend:[1,"<fieldset>","</fieldset>"],area:[1,"<map>","</map>"],param:[1,"<object>","</object>"],thead:[1,"<table>","</table>"],tr:[2,"<table><tbody>","</tbody></table>"],col:[2,"<table><tbody></tbody><colgroup>","</colgroup></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:support.htmlSerialize?[0,"",""]:[1,"X<div>","</div>"]},safeFragment=createSafeFragment(document),fragmentDiv=safeFragment.appendChild(document.createElement("div"));wrapMap.optgroup=wrapMap.option;wrapMap.tbody=wrapMap.tfoot=wrapMap.colgroup=wrapMap.caption=wrapMap.thead;wrapMap.th=wrapMap.td;function getAll(context,tag){var elems,elem,i=0,found=typeof context.getElementsByTagName!==strundefined?context.getElementsByTagName(tag||"*"):typeof context.querySelectorAll!==strundefined?context.querySelectorAll(tag||"*"):undefined;if(!found){for(found=[],elems=context.childNodes||context;(elem=elems[i])!=null;i++){if(!tag||jQuery.nodeName(elem,tag)){found.push(elem)}else{jQuery.merge(found,getAll(elem,tag))}}}return tag===undefined||tag&&jQuery.nodeName(context,tag)?jQuery.merge([context],found):found}function fixDefaultChecked(elem){if(rcheckableType.test(elem.type)){elem.defaultChecked=elem.checked}}function manipulationTarget(elem,content){return jQuery.nodeName(elem,"table")&&jQuery.nodeName(content.nodeType!==11?content:content.firstChild,"tr")?elem.getElementsByTagName("tbody")[0]||elem.appendChild(elem.ownerDocument.createElement("tbody")):elem}function disableScript(elem){elem.type=(jQuery.find.attr(elem,"type")!==null)+"/"+elem.type;return elem}function restoreScript(elem){var match=rscriptTypeMasked.exec(elem.type);if(match){elem.type=match[1]}else{elem.removeAttribute("type")}return elem}function setGlobalEval(elems,refElements){var elem,i=0;for(;(elem=elems[i])!=null;i++){jQuery._data(elem,"globalEval",!refElements||jQuery._data(refElements[i],"globalEval"))}}function cloneCopyEvent(src,dest){if(dest.nodeType!==1||!jQuery.hasData(src)){return}var type,i,l,oldData=jQuery._data(src),curData=jQuery._data(dest,oldData),events=oldData.events;if(events){delete curData.handle;curData.events={};for(type in events){for(i=0,l=events[type].length;i<l;i++){jQuery.event.add(dest,type,events[type][i])}}}if(curData.data){curData.data=jQuery.extend({},curData.data)}}function fixCloneNodeIssues(src,dest){var nodeName,e,data;if(dest.nodeType!==1){return}nodeName=dest.nodeName.toLowerCase();if(!support.noCloneEvent&&dest[jQuery.expando]){data=jQuery._data(dest);for(e in data.events){jQuery.removeEvent(dest,e,data.handle)}dest.removeAttribute(jQuery.expando)}if(nodeName==="script"&&dest.text!==src.text){disableScript(dest).text=src.text;restoreScript(dest)}else if(nodeName==="object"){if(dest.parentNode){dest.outerHTML=src.outerHTML}if(support.html5Clone&&(src.innerHTML&&!jQuery.trim(dest.innerHTML))){dest.innerHTML=src.innerHTML}}else if(nodeName==="input"&&rcheckableType.test(src.type)){dest.defaultChecked=dest.checked=src.checked;if(dest.value!==src.value){dest.value=src.value}}else if(nodeName==="option"){dest.defaultSelected=dest.selected=src.defaultSelected}else if(nodeName==="input"||nodeName==="textarea"){dest.defaultValue=src.defaultValue}}jQuery.extend({clone:function(elem,dataAndEvents,deepDataAndEvents){var destElements,node,clone,i,srcElements,inPage=jQuery.contains(elem.ownerDocument,elem);if(support.html5Clone||jQuery.isXMLDoc(elem)||!rnoshimcache.test("<"+elem.nodeName+">")){clone=elem.cloneNode(true)}else{fragmentDiv.innerHTML=elem.outerHTML;fragmentDiv.removeChild(clone=fragmentDiv.firstChild)}if((!support.noCloneEvent||!support.noCloneChecked)&&(elem.nodeType===1||elem.nodeType===11)&&!jQuery.isXMLDoc(elem)){destElements=getAll(clone);srcElements=getAll(elem);for(i=0;(node=srcElements[i])!=null;++i){if(destElements[i]){fixCloneNodeIssues(node,destElements[i])}}}if(dataAndEvents){if(deepDataAndEvents){srcElements=srcElements||getAll(elem);destElements=destElements||getAll(clone);for(i=0;(node=srcElements[i])!=null;i++){cloneCopyEvent(node,destElements[i])}}else{cloneCopyEvent(elem,clone)}}destElements=getAll(clone,"script");if(destElements.length>0){setGlobalEval(destElements,!inPage&&getAll(elem,"script"))}destElements=srcElements=node=null;return clone},buildFragment:function(elems,context,scripts,selection){var j,elem,contains,tmp,tag,tbody,wrap,l=elems.length,safe=createSafeFragment(context),nodes=[],i=0;for(;i<l;i++){elem=elems[i];if(elem||elem===0){if(jQuery.type(elem)==="object"){jQuery.merge(nodes,elem.nodeType?[elem]:elem)}else if(!rhtml.test(elem)){nodes.push(context.createTextNode(elem))}else{tmp=tmp||safe.appendChild(context.createElement("div"));tag=(rtagName.exec(elem)||["",""])[1].toLowerCase();wrap=wrapMap[tag]||wrapMap._default;tmp.innerHTML=wrap[1]+elem.replace(rxhtmlTag,"<$1></$2>")+wrap[2];j=wrap[0];while(j--){tmp=tmp.lastChild}if(!support.leadingWhitespace&&rleadingWhitespace.test(elem)){nodes.push(context.createTextNode(rleadingWhitespace.exec(elem)[0]))}if(!support.tbody){elem=tag==="table"&&!rtbody.test(elem)?tmp.firstChild:wrap[1]==="<table>"&&!rtbody.test(elem)?tmp:0;j=elem&&elem.childNodes.length;while(j--){if(jQuery.nodeName(tbody=elem.childNodes[j],"tbody")&&!tbody.childNodes.length){elem.removeChild(tbody)}}}jQuery.merge(nodes,tmp.childNodes);tmp.textContent="";while(tmp.firstChild){tmp.removeChild(tmp.firstChild)}tmp=safe.lastChild}}}if(tmp){safe.removeChild(tmp)}if(!support.appendChecked){jQuery.grep(getAll(nodes,"input"),fixDefaultChecked)}i=0;while(elem=nodes[i++]){if(selection&&jQuery.inArray(elem,selection)!==-1){continue}contains=jQuery.contains(elem.ownerDocument,elem);tmp=getAll(safe.appendChild(elem),"script");if(contains){setGlobalEval(tmp)}if(scripts){j=0;while(elem=tmp[j++]){if(rscriptType.test(elem.type||"")){scripts.push(elem)}}}}tmp=null;return safe},cleanData:function(elems,acceptData){var elem,type,id,data,i=0,internalKey=jQuery.expando,cache=jQuery.cache,deleteExpando=support.deleteExpando,special=jQuery.event.special;for(;(elem=elems[i])!=null;i++){if(acceptData||jQuery.acceptData(elem)){id=elem[internalKey];data=id&&cache[id];if(data){if(data.events){for(type in data.events){if(special[type]){jQuery.event.remove(elem,type)}else{jQuery.removeEvent(elem,type,data.handle)}}}if(cache[id]){delete cache[id];if(deleteExpando){delete elem[internalKey]}else if(typeof elem.removeAttribute!==strundefined){elem.removeAttribute(internalKey)}else{elem[internalKey]=null}deletedIds.push(id)}}}}}});jQuery.fn.extend({text:function(value){return access(this,function(value){return value===undefined?jQuery.text(this):this.empty().append((this[0]&&this[0].ownerDocument||document).createTextNode(value))},null,value,arguments.length)},append:function(){return this.domManip(arguments,function(elem){if(this.nodeType===1||this.nodeType===11||this.nodeType===9){var target=manipulationTarget(this,elem);target.appendChild(elem)}})},prepend:function(){return this.domManip(arguments,function(elem){if(this.nodeType===1||this.nodeType===11||this.nodeType===9){var target=manipulationTarget(this,elem);target.insertBefore(elem,target.firstChild)}})},before:function(){return this.domManip(arguments,function(elem){if(this.parentNode){this.parentNode.insertBefore(elem,this)}})},after:function(){return this.domManip(arguments,function(elem){if(this.parentNode){this.parentNode.insertBefore(elem,this.nextSibling)}})},remove:function(selector,keepData){var elem,elems=selector?jQuery.filter(selector,this):this,i=0;for(;(elem=elems[i])!=null;i++){if(!keepData&&elem.nodeType===1){jQuery.cleanData(getAll(elem))}if(elem.parentNode){if(keepData&&jQuery.contains(elem.ownerDocument,elem)){setGlobalEval(getAll(elem,"script"))}elem.parentNode.removeChild(elem)}}return this},empty:function(){var elem,i=0;for(;(elem=this[i])!=null;i++){if(elem.nodeType===1){jQuery.cleanData(getAll(elem,false))}while(elem.firstChild){elem.removeChild(elem.firstChild)}if(elem.options&&jQuery.nodeName(elem,"select")){elem.options.length=0}}return this},clone:function(dataAndEvents,deepDataAndEvents){dataAndEvents=dataAndEvents==null?false:dataAndEvents;deepDataAndEvents=deepDataAndEvents==null?dataAndEvents:deepDataAndEvents;return this.map(function(){return jQuery.clone(this,dataAndEvents,deepDataAndEvents)})},html:function(value){return access(this,function(value){var elem=this[0]||{},i=0,l=this.length;if(value===undefined){return elem.nodeType===1?elem.innerHTML.replace(rinlinejQuery,""):undefined}if(typeof value==="string"&&!rnoInnerhtml.test(value)&&(support.htmlSerialize||!rnoshimcache.test(value))&&(support.leadingWhitespace||!rleadingWhitespace.test(value))&&!wrapMap[(rtagName.exec(value)||["",""])[1].toLowerCase()]){value=value.replace(rxhtmlTag,"<$1></$2>");try{for(;i<l;i++){elem=this[i]||{};if(elem.nodeType===1){jQuery.cleanData(getAll(elem,false));elem.innerHTML=value}}elem=0}catch(e){}}if(elem){this.empty().append(value)}},null,value,arguments.length)},replaceWith:function(){var arg=arguments[0];this.domManip(arguments,function(elem){arg=this.parentNode;jQuery.cleanData(getAll(this));if(arg){arg.replaceChild(elem,this)}});return arg&&(arg.length||arg.nodeType)?this:this.remove()},detach:function(selector){return this.remove(selector,true)},domManip:function(args,callback){args=concat.apply([],args);var first,node,hasScripts,scripts,doc,fragment,i=0,l=this.length,set=this,iNoClone=l-1,value=args[0],isFunction=jQuery.isFunction(value);if(isFunction||l>1&&typeof value==="string"&&!support.checkClone&&rchecked.test(value)){return this.each(function(index){var self=set.eq(index);if(isFunction){args[0]=value.call(this,index,self.html())}self.domManip(args,callback)})}if(l){fragment=jQuery.buildFragment(args,this[0].ownerDocument,false,this);first=fragment.firstChild;if(fragment.childNodes.length===1){fragment=first}if(first){scripts=jQuery.map(getAll(fragment,"script"),disableScript);hasScripts=scripts.length;for(;i<l;i++){node=fragment;if(i!==iNoClone){node=jQuery.clone(node,true,true);if(hasScripts){jQuery.merge(scripts,getAll(node,"script"))}}callback.call(this[i],node,i)}if(hasScripts){doc=scripts[scripts.length-1].ownerDocument;jQuery.map(scripts,restoreScript);for(i=0;i<hasScripts;i++){node=scripts[i];if(rscriptType.test(node.type||"")&&!jQuery._data(node,"globalEval")&&jQuery.contains(doc,node)){if(node.src){if(jQuery._evalUrl){jQuery._evalUrl(node.src)}}else{jQuery.globalEval((node.text||node.textContent||node.innerHTML||"").replace(rcleanScript,""))}}}}fragment=first=null}}return this}});jQuery.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(name,original){jQuery.fn[name]=function(selector){var elems,i=0,ret=[],insert=jQuery(selector),last=insert.length-1;for(;i<=last;i++){elems=i===last?this:this.clone(true);jQuery(insert[i])[original](elems);push.apply(ret,elems.get())}return this.pushStack(ret)}});var iframe,elemdisplay={};function actualDisplay(name,doc){var style,elem=jQuery(doc.createElement(name)).appendTo(doc.body),display=window.getDefaultComputedStyle&&(style=window.getDefaultComputedStyle(elem[0]))?style.display:jQuery.css(elem[0],"display");elem.detach();return display}function defaultDisplay(nodeName){var doc=document,display=elemdisplay[nodeName];if(!display){display=actualDisplay(nodeName,doc);if(display==="none"||!display){iframe=(iframe||jQuery("<iframe frameborder='0' width='0' height='0'/>")).appendTo(doc.documentElement);doc=(iframe[0].contentWindow||iframe[0].contentDocument).document;doc.write();doc.close();display=actualDisplay(nodeName,doc);iframe.detach()}elemdisplay[nodeName]=display}return display}(function(){var shrinkWrapBlocksVal;support.shrinkWrapBlocks=function(){if(shrinkWrapBlocksVal!=null){return shrinkWrapBlocksVal}shrinkWrapBlocksVal=false;var div,body,container;body=document.getElementsByTagName("body")[0];if(!body||!body.style){return}div=document.createElement("div");container=document.createElement("div");container.style.cssText="position:absolute;border:0;width:0;height:0;top:0;left:-9999px";body.appendChild(container).appendChild(div);if(typeof div.style.zoom!==strundefined){div.style.cssText="-webkit-box-sizing:content-box;-moz-box-sizing:content-box;"+"box-sizing:content-box;display:block;margin:0;border:0;"+"padding:1px;width:1px;zoom:1";div.appendChild(document.createElement("div")).style.width="5px";shrinkWrapBlocksVal=div.offsetWidth!==3}body.removeChild(container);return shrinkWrapBlocksVal}})();var rmargin=/^margin/;var rnumnonpx=new RegExp("^("+pnum+")(?!px)[a-z%]+$","i");var getStyles,curCSS,rposition=/^(top|right|bottom|left)$/;if(window.getComputedStyle){getStyles=function(elem){if(elem.ownerDocument.defaultView.opener){return elem.ownerDocument.defaultView.getComputedStyle(elem,null);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
17
 
18
- }return window.getComputedStyle(elem,null)};curCSS=function(elem,name,computed){var width,minWidth,maxWidth,ret,style=elem.style;computed=computed||getStyles(elem);ret=computed?computed.getPropertyValue(name)||computed[name]:undefined;if(computed){if(ret===""&&!jQuery.contains(elem.ownerDocument,elem)){ret=jQuery.style(elem,name)}if(rnumnonpx.test(ret)&&rmargin.test(name)){width=style.width;minWidth=style.minWidth;maxWidth=style.maxWidth;style.minWidth=style.maxWidth=style.width=ret;ret=computed.width;style.width=width;style.minWidth=minWidth;style.maxWidth=maxWidth}}return ret===undefined?ret:ret+""}}else if(document.documentElement.currentStyle){getStyles=function(elem){return elem.currentStyle};curCSS=function(elem,name,computed){var left,rs,rsLeft,ret,style=elem.style;computed=computed||getStyles(elem);ret=computed?computed[name]:undefined;if(ret==null&&style&&style[name]){ret=style[name]}if(rnumnonpx.test(ret)&&!rposition.test(name)){left=style.left;rs=elem.runtimeStyle;rsLeft=rs&&rs.left;if(rsLeft){rs.left=elem.currentStyle.left}style.left=name==="fontSize"?"1em":ret;ret=style.pixelLeft+"px";style.left=left;if(rsLeft){rs.left=rsLeft}}return ret===undefined?ret:ret+""||"auto"}}function addGetHookIf(conditionFn,hookFn){return{get:function(){var condition=conditionFn();if(condition==null){return}if(condition){delete this.get;return}return(this.get=hookFn).apply(this,arguments)}}}(function(){var div,style,a,pixelPositionVal,boxSizingReliableVal,reliableHiddenOffsetsVal,reliableMarginRightVal;div=document.createElement("div");div.innerHTML=" <link/><table></table><a href='/a'>a</a><input type='checkbox'/>";a=div.getElementsByTagName("a")[0];style=a&&a.style;if(!style){return}style.cssText="float:left;opacity:.5";support.opacity=style.opacity==="0.5";support.cssFloat=!!style.cssFloat;div.style.backgroundClip="content-box";div.cloneNode(true).style.backgroundClip="";support.clearCloneStyle=div.style.backgroundClip==="content-box";support.boxSizing=style.boxSizing===""||style.MozBoxSizing===""||style.WebkitBoxSizing==="";jQuery.extend(support,{reliableHiddenOffsets:function(){if(reliableHiddenOffsetsVal==null){computeStyleTests()}return reliableHiddenOffsetsVal},boxSizingReliable:function(){if(boxSizingReliableVal==null){computeStyleTests()}return boxSizingReliableVal},pixelPosition:function(){if(pixelPositionVal==null){computeStyleTests()}return pixelPositionVal},reliableMarginRight:function(){if(reliableMarginRightVal==null){computeStyleTests()}return reliableMarginRightVal}});function computeStyleTests(){var div,body,container,contents;body=document.getElementsByTagName("body")[0];if(!body||!body.style){return}div=document.createElement("div");container=document.createElement("div");container.style.cssText="position:absolute;border:0;width:0;height:0;top:0;left:-9999px";body.appendChild(container).appendChild(div);div.style.cssText="-webkit-box-sizing:border-box;-moz-box-sizing:border-box;"+"box-sizing:border-box;display:block;margin-top:1%;top:1%;"+"border:1px;padding:1px;width:4px;position:absolute";pixelPositionVal=boxSizingReliableVal=false;reliableMarginRightVal=true;if(window.getComputedStyle){pixelPositionVal=(window.getComputedStyle(div,null)||{}).top!=="1%";boxSizingReliableVal=(window.getComputedStyle(div,null)||{width:"4px"}).width==="4px";contents=div.appendChild(document.createElement("div"));contents.style.cssText=div.style.cssText="-webkit-box-sizing:content-box;-moz-box-sizing:content-box;"+"box-sizing:content-box;display:block;margin:0;border:0;padding:0";contents.style.marginRight=contents.style.width="0";div.style.width="1px";reliableMarginRightVal=!parseFloat((window.getComputedStyle(contents,null)||{}).marginRight);div.removeChild(contents)}div.innerHTML="<table><tr><td></td><td>t</td></tr></table>";contents=div.getElementsByTagName("td");contents[0].style.cssText="margin:0;border:0;padding:0;display:none";reliableHiddenOffsetsVal=contents[0].offsetHeight===0;if(reliableHiddenOffsetsVal){contents[0].style.display="";contents[1].style.display="none";reliableHiddenOffsetsVal=contents[0].offsetHeight===0}body.removeChild(container)}})();jQuery.swap=function(elem,options,callback,args){var ret,name,old={};for(name in options){old[name]=elem.style[name];elem.style[name]=options[name]}ret=callback.apply(elem,args||[]);for(name in options){elem.style[name]=old[name]}return ret};var ralpha=/alpha\([^)]*\)/i,ropacity=/opacity\s*=\s*([^)]*)/,rdisplayswap=/^(none|table(?!-c[ea]).+)/,rnumsplit=new RegExp("^("+pnum+")(.*)$","i"),rrelNum=new RegExp("^([+-])=("+pnum+")","i"),cssShow={position:"absolute",visibility:"hidden",display:"block"},cssNormalTransform={letterSpacing:"0",fontWeight:"400"},cssPrefixes=["Webkit","O","Moz","ms"];function vendorPropName(style,name){if(name in style){return name}var capName=name.charAt(0).toUpperCase()+name.slice(1),origName=name,i=cssPrefixes.length;while(i--){name=cssPrefixes[i]+capName;if(name in style){return name}}return origName}function showHide(elements,show){var display,elem,hidden,values=[],index=0,length=elements.length;for(;index<length;index++){elem=elements[index];if(!elem.style){continue}values[index]=jQuery._data(elem,"olddisplay");display=elem.style.display;if(show){if(!values[index]&&display==="none"){elem.style.display=""}if(elem.style.display===""&&isHidden(elem)){values[index]=jQuery._data(elem,"olddisplay",defaultDisplay(elem.nodeName))}}else{hidden=isHidden(elem);if(display&&display!=="none"||!hidden){jQuery._data(elem,"olddisplay",hidden?display:jQuery.css(elem,"display"))}}}for(index=0;index<length;index++){elem=elements[index];if(!elem.style){continue}if(!show||elem.style.display==="none"||elem.style.display===""){elem.style.display=show?values[index]||"":"none"}}return elements}function setPositiveNumber(elem,value,subtract){var matches=rnumsplit.exec(value);return matches?Math.max(0,matches[1]-(subtract||0))+(matches[2]||"px"):value}function augmentWidthOrHeight(elem,name,extra,isBorderBox,styles){var i=extra===(isBorderBox?"border":"content")?4:name==="width"?1:0,val=0;for(;i<4;i+=2){if(extra==="margin"){val+=jQuery.css(elem,extra+cssExpand[i],true,styles)}if(isBorderBox){if(extra==="content"){val-=jQuery.css(elem,"padding"+cssExpand[i],true,styles)}if(extra!=="margin"){val-=jQuery.css(elem,"border"+cssExpand[i]+"Width",true,styles)}}else{val+=jQuery.css(elem,"padding"+cssExpand[i],true,styles);if(extra!=="padding"){val+=jQuery.css(elem,"border"+cssExpand[i]+"Width",true,styles)}}}return val}function getWidthOrHeight(elem,name,extra){var valueIsBorderBox=true,val=name==="width"?elem.offsetWidth:elem.offsetHeight,styles=getStyles(elem),isBorderBox=support.boxSizing&&jQuery.css(elem,"boxSizing",false,styles)==="border-box";if(val<=0||val==null){val=curCSS(elem,name,styles);if(val<0||val==null){val=elem.style[name]}if(rnumnonpx.test(val)){return val}valueIsBorderBox=isBorderBox&&(support.boxSizingReliable()||val===elem.style[name]);val=parseFloat(val)||0}return val+augmentWidthOrHeight(elem,name,extra||(isBorderBox?"border":"content"),valueIsBorderBox,styles)+"px"}jQuery.extend({cssHooks:{opacity:{get:function(elem,computed){if(computed){var ret=curCSS(elem,"opacity");return ret===""?"1":ret}}}},cssNumber:{columnCount:true,fillOpacity:true,flexGrow:true,flexShrink:true,fontWeight:true,lineHeight:true,opacity:true,order:true,orphans:true,widows:true,zIndex:true,zoom:true},cssProps:{"float":support.cssFloat?"cssFloat":"styleFloat"},style:function(elem,name,value,extra){if(!elem||elem.nodeType===3||elem.nodeType===8||!elem.style){return}var ret,type,hooks,origName=jQuery.camelCase(name),style=elem.style;name=jQuery.cssProps[origName]||(jQuery.cssProps[origName]=vendorPropName(style,origName));hooks=jQuery.cssHooks[name]||jQuery.cssHooks[origName];if(value!==undefined){type=typeof value;if(type==="string"&&(ret=rrelNum.exec(value))){value=(ret[1]+1)*ret[2]+parseFloat(jQuery.css(elem,name));type="number"}if(value==null||value!==value){return}if(type==="number"&&!jQuery.cssNumber[origName]){value+="px"}if(!support.clearCloneStyle&&value===""&&name.indexOf("background")===0){style[name]="inherit"}if(!hooks||!("set"in hooks)||(value=hooks.set(elem,value,extra))!==undefined){try{style[name]=value}catch(e){}}}else{if(hooks&&"get"in hooks&&(ret=hooks.get(elem,false,extra))!==undefined){return ret}return style[name]}},css:function(elem,name,extra,styles){var num,val,hooks,origName=jQuery.camelCase(name);name=jQuery.cssProps[origName]||(jQuery.cssProps[origName]=vendorPropName(elem.style,origName));hooks=jQuery.cssHooks[name]||jQuery.cssHooks[origName];if(hooks&&"get"in hooks){val=hooks.get(elem,true,extra)}if(val===undefined){val=curCSS(elem,name,styles)}if(val==="normal"&&name in cssNormalTransform){val=cssNormalTransform[name]}if(extra===""||extra){num=parseFloat(val);return extra===true||jQuery.isNumeric(num)?num||0:val}return val}});jQuery.each(["height","width"],function(i,name){jQuery.cssHooks[name]={get:function(elem,computed,extra){if(computed){return rdisplayswap.test(jQuery.css(elem,"display"))&&elem.offsetWidth===0?jQuery.swap(elem,cssShow,function(){return getWidthOrHeight(elem,name,extra)}):getWidthOrHeight(elem,name,extra)}},set:function(elem,value,extra){var styles=extra&&getStyles(elem);return setPositiveNumber(elem,value,extra?augmentWidthOrHeight(elem,name,extra,support.boxSizing&&jQuery.css(elem,"boxSizing",false,styles)==="border-box",styles):0)}}});if(!support.opacity){jQuery.cssHooks.opacity={get:function(elem,computed){return ropacity.test((computed&&elem.currentStyle?elem.currentStyle.filter:elem.style.filter)||"")?.01*parseFloat(RegExp.$1)+"":computed?"1":""},set:function(elem,value){var style=elem.style,currentStyle=elem.currentStyle,opacity=jQuery.isNumeric(value)?"alpha(opacity="+value*100+")":"",filter=currentStyle&&currentStyle.filter||style.filter||"";style.zoom=1;if((value>=1||value==="")&&jQuery.trim(filter.replace(ralpha,""))===""&&style.removeAttribute){style.removeAttribute("filter");if(value===""||currentStyle&&!currentStyle.filter){return}}style.filter=ralpha.test(filter)?filter.replace(ralpha,opacity):filter+" "+opacity}}}jQuery.cssHooks.marginRight=addGetHookIf(support.reliableMarginRight,function(elem,computed){if(computed){return jQuery.swap(elem,{display:"inline-block"},curCSS,[elem,"marginRight"])}});jQuery.each({margin:"",padding:"",border:"Width"},function(prefix,suffix){jQuery.cssHooks[prefix+suffix]={expand:function(value){var i=0,expanded={},parts=typeof value==="string"?value.split(" "):[value];for(;i<4;i++){expanded[prefix+cssExpand[i]+suffix]=parts[i]||parts[i-2]||parts[0]}return expanded}};if(!rmargin.test(prefix)){jQuery.cssHooks[prefix+suffix].set=setPositiveNumber}});jQuery.fn.extend({css:function(name,value){return access(this,function(elem,name,value){var styles,len,map={},i=0;if(jQuery.isArray(name)){styles=getStyles(elem);len=name.length;for(;i<len;i++){map[name[i]]=jQuery.css(elem,name[i],false,styles)}return map}return value!==undefined?jQuery.style(elem,name,value):jQuery.css(elem,name)},name,value,arguments.length>1)},show:function(){return showHide(this,true)},hide:function(){return showHide(this)},toggle:function(state){if(typeof state==="boolean"){return state?this.show():this.hide()}return this.each(function(){if(isHidden(this)){jQuery(this).show()}else{jQuery(this).hide()}})}});function Tween(elem,options,prop,end,easing){return new Tween.prototype.init(elem,options,prop,end,easing)}jQuery.Tween=Tween;Tween.prototype={constructor:Tween,init:function(elem,options,prop,end,easing,unit){this.elem=elem;this.prop=prop;this.easing=easing||"swing";this.options=options;this.start=this.now=this.cur();this.end=end;this.unit=unit||(jQuery.cssNumber[prop]?"":"px")},cur:function(){var hooks=Tween.propHooks[this.prop];return hooks&&hooks.get?hooks.get(this):Tween.propHooks._default.get(this)},run:function(percent){var eased,hooks=Tween.propHooks[this.prop];if(this.options.duration){this.pos=eased=jQuery.easing[this.easing](percent,this.options.duration*percent,0,1,this.options.duration)}else{this.pos=eased=percent}this.now=(this.end-this.start)*eased+this.start;if(this.options.step){this.options.step.call(this.elem,this.now,this)}if(hooks&&hooks.set){hooks.set(this)}else{Tween.propHooks._default.set(this)}return this}};Tween.prototype.init.prototype=Tween.prototype;Tween.propHooks={_default:{get:function(tween){var result;if(tween.elem[tween.prop]!=null&&(!tween.elem.style||tween.elem.style[tween.prop]==null)){return tween.elem[tween.prop]}result=jQuery.css(tween.elem,tween.prop,"");return!result||result==="auto"?0:result},set:function(tween){if(jQuery.fx.step[tween.prop]){jQuery.fx.step[tween.prop](tween)}else if(tween.elem.style&&(tween.elem.style[jQuery.cssProps[tween.prop]]!=null||jQuery.cssHooks[tween.prop])){jQuery.style(tween.elem,tween.prop,tween.now+tween.unit)}else{tween.elem[tween.prop]=tween.now}}}};Tween.propHooks.scrollTop=Tween.propHooks.scrollLeft={set:function(tween){if(tween.elem.nodeType&&tween.elem.parentNode){tween.elem[tween.prop]=tween.now}}};jQuery.easing={linear:function(p){return p},swing:function(p){return.5-Math.cos(p*Math.PI)/2}};jQuery.fx=Tween.prototype.init;jQuery.fx.step={};var fxNow,timerId,rfxtypes=/^(?:toggle|show|hide)$/,rfxnum=new RegExp("^(?:([+-])=|)("+pnum+")([a-z%]*)$","i"),rrun=/queueHooks$/,animationPrefilters=[defaultPrefilter],tweeners={"*":[function(prop,value){var tween=this.createTween(prop,value),target=tween.cur(),parts=rfxnum.exec(value),unit=parts&&parts[3]||(jQuery.cssNumber[prop]?"":"px"),start=(jQuery.cssNumber[prop]||unit!=="px"&&+target)&&rfxnum.exec(jQuery.css(tween.elem,prop)),scale=1,maxIterations=20;if(start&&start[3]!==unit){unit=unit||start[3];parts=parts||[];start=+target||1;do{scale=scale||".5";start=start/scale;jQuery.style(tween.elem,prop,start+unit)}while(scale!==(scale=tween.cur()/target)&&scale!==1&&--maxIterations)}if(parts){start=tween.start=+start||+target||0;tween.unit=unit;tween.end=parts[1]?start+(parts[1]+1)*parts[2]:+parts[2]}return tween}]};function createFxNow(){setTimeout(function(){fxNow=undefined});return fxNow=jQuery.now()}function genFx(type,includeWidth){var which,attrs={height:type},i=0;includeWidth=includeWidth?1:0;for(;i<4;i+=2-includeWidth){which=cssExpand[i];attrs["margin"+which]=attrs["padding"+which]=type}if(includeWidth){attrs.opacity=attrs.width=type}return attrs}function createTween(value,prop,animation){var tween,collection=(tweeners[prop]||[]).concat(tweeners["*"]),index=0,length=collection.length;for(;index<length;index++){if(tween=collection[index].call(animation,prop,value)){return tween}}}function defaultPrefilter(elem,props,opts){var prop,value,toggle,tween,hooks,oldfire,display,checkDisplay,anim=this,orig={},style=elem.style,hidden=elem.nodeType&&isHidden(elem),dataShow=jQuery._data(elem,"fxshow");if(!opts.queue){hooks=jQuery._queueHooks(elem,"fx");if(hooks.unqueued==null){hooks.unqueued=0;oldfire=hooks.empty.fire;hooks.empty.fire=function(){if(!hooks.unqueued){oldfire()}}}hooks.unqueued++;anim.always(function(){anim.always(function(){hooks.unqueued--;if(!jQuery.queue(elem,"fx").length){hooks.empty.fire()}})})}if(elem.nodeType===1&&("height"in props||"width"in props)){opts.overflow=[style.overflow,style.overflowX,style.overflowY];display=jQuery.css(elem,"display");checkDisplay=display==="none"?jQuery._data(elem,"olddisplay")||defaultDisplay(elem.nodeName):display;if(checkDisplay==="inline"&&jQuery.css(elem,"float")==="none"){if(!support.inlineBlockNeedsLayout||defaultDisplay(elem.nodeName)==="inline"){style.display="inline-block"}else{style.zoom=1}}}if(opts.overflow){style.overflow="hidden";if(!support.shrinkWrapBlocks()){anim.always(function(){style.overflow=opts.overflow[0];style.overflowX=opts.overflow[1];style.overflowY=opts.overflow[2]})}}for(prop in props){value=props[prop];if(rfxtypes.exec(value)){delete props[prop];toggle=toggle||value==="toggle";if(value===(hidden?"hide":"show")){if(value==="show"&&dataShow&&dataShow[prop]!==undefined){hidden=true}else{continue}}orig[prop]=dataShow&&dataShow[prop]||jQuery.style(elem,prop)}else{display=undefined}}if(!jQuery.isEmptyObject(orig)){if(dataShow){if("hidden"in dataShow){hidden=dataShow.hidden}}else{dataShow=jQuery._data(elem,"fxshow",{})}if(toggle){dataShow.hidden=!hidden}if(hidden){jQuery(elem).show()}else{anim.done(function(){jQuery(elem).hide()})}anim.done(function(){var prop;jQuery._removeData(elem,"fxshow");for(prop in orig){jQuery.style(elem,prop,orig[prop])}});for(prop in orig){tween=createTween(hidden?dataShow[prop]:0,prop,anim);if(!(prop in dataShow)){dataShow[prop]=tween.start;if(hidden){tween.end=tween.start;tween.start=prop==="width"||prop==="height"?1:0}}}}else if((display==="none"?defaultDisplay(elem.nodeName):display)==="inline"){style.display=display}}function propFilter(props,specialEasing){var index,name,easing,value,hooks;for(index in props){name=jQuery.camelCase(index);easing=specialEasing[name];value=props[index];if(jQuery.isArray(value)){easing=value[1];value=props[index]=value[0]}if(index!==name){props[name]=value;delete props[index]}hooks=jQuery.cssHooks[name];if(hooks&&"expand"in hooks){value=hooks.expand(value);delete props[name];for(index in value){if(!(index in props)){props[index]=value[index];specialEasing[index]=easing}}}else{specialEasing[name]=easing}}}function Animation(elem,properties,options){var result,stopped,index=0,length=animationPrefilters.length,deferred=jQuery.Deferred().always(function(){delete tick.elem}),tick=function(){if(stopped){return false}var currentTime=fxNow||createFxNow(),remaining=Math.max(0,animation.startTime+animation.duration-currentTime),temp=remaining/animation.duration||0,percent=1-temp,index=0,length=animation.tweens.length;for(;index<length;index++){animation.tweens[index].run(percent)}deferred.notifyWith(elem,[animation,percent,remaining]);if(percent<1&&length){return remaining}else{deferred.resolveWith(elem,[animation]);return false}},animation=deferred.promise({elem:elem,props:jQuery.extend({},properties),opts:jQuery.extend(true,{specialEasing:{}},options),originalProperties:properties,originalOptions:options,startTime:fxNow||createFxNow(),duration:options.duration,tweens:[],createTween:function(prop,end){var tween=jQuery.Tween(elem,animation.opts,prop,end,animation.opts.specialEasing[prop]||animation.opts.easing);animation.tweens.push(tween);return tween},stop:function(gotoEnd){var index=0,length=gotoEnd?animation.tweens.length:0;if(stopped){return this}stopped=true;for(;index<length;index++){animation.tweens[index].run(1)}if(gotoEnd){deferred.resolveWith(elem,[animation,gotoEnd])}else{deferred.rejectWith(elem,[animation,gotoEnd])}return this}}),props=animation.props;propFilter(props,animation.opts.specialEasing);for(;index<length;index++){result=animationPrefilters[index].call(animation,elem,props,animation.opts);if(result){return result}}jQuery.map(props,createTween,animation);if(jQuery.isFunction(animation.opts.start)){animation.opts.start.call(elem,animation)}jQuery.fx.timer(jQuery.extend(tick,{elem:elem,anim:animation,queue:animation.opts.queue}));return animation.progress(animation.opts.progress).done(animation.opts.done,animation.opts.complete).fail(animation.opts.fail).always(animation.opts.always)}jQuery.Animation=jQuery.extend(Animation,{tweener:function(props,callback){if(jQuery.isFunction(props)){callback=props;props=["*"]}else{props=props.split(" ")}var prop,index=0,length=props.length;for(;index<length;index++){prop=props[index];tweeners[prop]=tweeners[prop]||[];tweeners[prop].unshift(callback)}},prefilter:function(callback,prepend){if(prepend){animationPrefilters.unshift(callback)}else{animationPrefilters.push(callback)}}});jQuery.speed=function(speed,easing,fn){var opt=speed&&typeof speed==="object"?jQuery.extend({},speed):{complete:fn||!fn&&easing||jQuery.isFunction(speed)&&speed,duration:speed,easing:fn&&easing||easing&&!jQuery.isFunction(easing)&&easing};opt.duration=jQuery.fx.off?0:typeof opt.duration==="number"?opt.duration:opt.duration in jQuery.fx.speeds?jQuery.fx.speeds[opt.duration]:jQuery.fx.speeds._default;if(opt.queue==null||opt.queue===true){opt.queue="fx"}opt.old=opt.complete;opt.complete=function(){if(jQuery.isFunction(opt.old)){opt.old.call(this)}if(opt.queue){jQuery.dequeue(this,opt.queue)}};return opt};jQuery.fn.extend({fadeTo:function(speed,to,easing,callback){return this.filter(isHidden).css("opacity",0).show().end().animate({opacity:to},speed,easing,callback)},animate:function(prop,speed,easing,callback){var empty=jQuery.isEmptyObject(prop),optall=jQuery.speed(speed,easing,callback),doAnimation=function(){var anim=Animation(this,jQuery.extend({},prop),optall);if(empty||jQuery._data(this,"finish")){anim.stop(true)}};doAnimation.finish=doAnimation;return empty||optall.queue===false?this.each(doAnimation):this.queue(optall.queue,doAnimation)},stop:function(type,clearQueue,gotoEnd){var stopQueue=function(hooks){var stop=hooks.stop;delete hooks.stop;stop(gotoEnd)};if(typeof type!=="string"){gotoEnd=clearQueue;clearQueue=type;type=undefined}if(clearQueue&&type!==false){this.queue(type||"fx",[])}return this.each(function(){var dequeue=true,index=type!=null&&type+"queueHooks",timers=jQuery.timers,data=jQuery._data(this);if(index){if(data[index]&&data[index].stop){stopQueue(data[index])}}else{for(index in data){if(data[index]&&data[index].stop&&rrun.test(index)){stopQueue(data[index])}}}for(index=timers.length;index--;){if(timers[index].elem===this&&(type==null||timers[index].queue===type)){timers[index].anim.stop(gotoEnd);dequeue=false;timers.splice(index,1)}}if(dequeue||!gotoEnd){jQuery.dequeue(this,type)}})},finish:function(type){if(type!==false){type=type||"fx"}return this.each(function(){var index,data=jQuery._data(this),queue=data[type+"queue"],hooks=data[type+"queueHooks"],timers=jQuery.timers,length=queue?queue.length:0;data.finish=true;jQuery.queue(this,type,[]);if(hooks&&hooks.stop){hooks.stop.call(this,true)}for(index=timers.length;index--;){if(timers[index].elem===this&&timers[index].queue===type){timers[index].anim.stop(true);timers.splice(index,1)}}for(index=0;index<length;index++){if(queue[index]&&queue[index].finish){queue[index].finish.call(this)}}delete data.finish})}});jQuery.each(["toggle","show","hide"],function(i,name){var cssFn=jQuery.fn[name];jQuery.fn[name]=function(speed,easing,callback){return speed==null||typeof speed==="boolean"?cssFn.apply(this,arguments):this.animate(genFx(name,true),speed,easing,callback)}});jQuery.each({slideDown:genFx("show"),slideUp:genFx("hide"),slideToggle:genFx("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(name,props){jQuery.fn[name]=function(speed,easing,callback){return this.animate(props,speed,easing,callback)}});jQuery.timers=[];jQuery.fx.tick=function(){var timer,timers=jQuery.timers,i=0;fxNow=jQuery.now();for(;i<timers.length;i++){timer=timers[i];if(!timer()&&timers[i]===timer){timers.splice(i--,1)}}if(!timers.length){jQuery.fx.stop()}fxNow=undefined};jQuery.fx.timer=function(timer){jQuery.timers.push(timer);if(timer()){jQuery.fx.start()}else{jQuery.timers.pop()}};jQuery.fx.interval=13;jQuery.fx.start=function(){if(!timerId){timerId=setInterval(jQuery.fx.tick,jQuery.fx.interval)}};jQuery.fx.stop=function(){clearInterval(timerId);timerId=null};jQuery.fx.speeds={slow:600,fast:200,_default:400};jQuery.fn.delay=function(time,type){time=jQuery.fx?jQuery.fx.speeds[time]||time:time;type=type||"fx";return this.queue(type,function(next,hooks){var timeout=setTimeout(next,time);hooks.stop=function(){clearTimeout(timeout)}})};(function(){var input,div,select,a,opt;div=document.createElement("div");div.setAttribute("className","t");div.innerHTML=" <link/><table></table><a href='/a'>a</a><input type='checkbox'/>";a=div.getElementsByTagName("a")[0];select=document.createElement("select");opt=select.appendChild(document.createElement("option"));input=div.getElementsByTagName("input")[0];a.style.cssText="top:1px";support.getSetAttribute=div.className!=="t";support.style=/top/.test(a.getAttribute("style"));support.hrefNormalized=a.getAttribute("href")==="/a";support.checkOn=!!input.value;support.optSelected=opt.selected;support.enctype=!!document.createElement("form").enctype;select.disabled=true;support.optDisabled=!opt.disabled;input=document.createElement("input");input.setAttribute("value","");support.input=input.getAttribute("value")==="";input.value="t";input.setAttribute("type","radio");support.radioValue=input.value==="t"})();var rreturn=/\r/g;jQuery.fn.extend({val:function(value){var hooks,ret,isFunction,elem=this[0];if(!arguments.length){if(elem){hooks=jQuery.valHooks[elem.type]||jQuery.valHooks[elem.nodeName.toLowerCase()];if(hooks&&"get"in hooks&&(ret=hooks.get(elem,"value"))!==undefined){return ret}ret=elem.value;return typeof ret==="string"?ret.replace(rreturn,""):ret==null?"":ret}return}isFunction=jQuery.isFunction(value);return this.each(function(i){var val;if(this.nodeType!==1){return}if(isFunction){val=value.call(this,i,jQuery(this).val())}else{val=value}if(val==null){val=""}else if(typeof val==="number"){val+=""}else if(jQuery.isArray(val)){val=jQuery.map(val,function(value){return value==null?"":value+""})}hooks=jQuery.valHooks[this.type]||jQuery.valHooks[this.nodeName.toLowerCase()];if(!hooks||!("set"in hooks)||hooks.set(this,val,"value")===undefined){this.value=val}})}});jQuery.extend({valHooks:{option:{get:function(elem){var val=jQuery.find.attr(elem,"value");return val!=null?val:jQuery.trim(jQuery.text(elem))}},select:{get:function(elem){var value,option,options=elem.options,index=elem.selectedIndex,one=elem.type==="select-one"||index<0,values=one?null:[],max=one?index+1:options.length,i=index<0?max:one?index:0;for(;i<max;i++){option=options[i];if((option.selected||i===index)&&(support.optDisabled?!option.disabled:option.getAttribute("disabled")===null)&&(!option.parentNode.disabled||!jQuery.nodeName(option.parentNode,"optgroup"))){value=jQuery(option).val();if(one){return value}values.push(value)}}return values},set:function(elem,value){var optionSet,option,options=elem.options,values=jQuery.makeArray(value),i=options.length;while(i--){option=options[i];if(jQuery.inArray(jQuery.valHooks.option.get(option),values)>=0){try{option.selected=optionSet=true}catch(_){option.scrollHeight}}else{option.selected=false}}if(!optionSet){elem.selectedIndex=-1}return options}}}});jQuery.each(["radio","checkbox"],function(){jQuery.valHooks[this]={set:function(elem,value){if(jQuery.isArray(value)){return elem.checked=jQuery.inArray(jQuery(elem).val(),value)>=0}}};if(!support.checkOn){jQuery.valHooks[this].get=function(elem){return elem.getAttribute("value")===null?"on":elem.value}}});var nodeHook,boolHook,attrHandle=jQuery.expr.attrHandle,ruseDefault=/^(?:checked|selected)$/i,getSetAttribute=support.getSetAttribute,getSetInput=support.input;jQuery.fn.extend({attr:function(name,value){return access(this,jQuery.attr,name,value,arguments.length>1)},removeAttr:function(name){return this.each(function(){jQuery.removeAttr(this,name)})}});jQuery.extend({attr:function(elem,name,value){var hooks,ret,nType=elem.nodeType;if(!elem||nType===3||nType===8||nType===2){return}if(typeof elem.getAttribute===strundefined){return jQuery.prop(elem,name,value)}if(nType!==1||!jQuery.isXMLDoc(elem)){name=name.toLowerCase();hooks=jQuery.attrHooks[name]||(jQuery.expr.match.bool.test(name)?boolHook:nodeHook)}if(value!==undefined){if(value===null){jQuery.removeAttr(elem,name)}else if(hooks&&"set"in hooks&&(ret=hooks.set(elem,value,name))!==undefined){return ret}else{elem.setAttribute(name,value+"");return value}}else if(hooks&&"get"in hooks&&(ret=hooks.get(elem,name))!==null){return ret}else{ret=jQuery.find.attr(elem,name);return ret==null?undefined:ret}},removeAttr:function(elem,value){var name,propName,i=0,attrNames=value&&value.match(rnotwhite);if(attrNames&&elem.nodeType===1){while(name=attrNames[i++]){propName=jQuery.propFix[name]||name;if(jQuery.expr.match.bool.test(name)){if(getSetInput&&getSetAttribute||!ruseDefault.test(name)){elem[propName]=false}else{elem[jQuery.camelCase("default-"+name)]=elem[propName]=false}}else{jQuery.attr(elem,name,"")}elem.removeAttribute(getSetAttribute?name:propName)}}},attrHooks:{type:{set:function(elem,value){if(!support.radioValue&&value==="radio"&&jQuery.nodeName(elem,"input")){var val=elem.value;elem.setAttribute("type",value);if(val){elem.value=val}return value}}}}});boolHook={set:function(elem,value,name){if(value===false){jQuery.removeAttr(elem,name)}else if(getSetInput&&getSetAttribute||!ruseDefault.test(name)){elem.setAttribute(!getSetAttribute&&jQuery.propFix[name]||name,name)}else{elem[jQuery.camelCase("default-"+name)]=elem[name]=true}return name}};jQuery.each(jQuery.expr.match.bool.source.match(/\w+/g),function(i,name){var getter=attrHandle[name]||jQuery.find.attr;attrHandle[name]=getSetInput&&getSetAttribute||!ruseDefault.test(name)?function(elem,name,isXML){var ret,handle;if(!isXML){handle=attrHandle[name];attrHandle[name]=ret;ret=getter(elem,name,isXML)!=null?name.toLowerCase():null;attrHandle[name]=handle}return ret}:function(elem,name,isXML){if(!isXML){return elem[jQuery.camelCase("default-"+name)]?name.toLowerCase():null}}});if(!getSetInput||!getSetAttribute){jQuery.attrHooks.value={set:function(elem,value,name){if(jQuery.nodeName(elem,"input")){elem.defaultValue=value}else{return nodeHook&&nodeHook.set(elem,value,name)}}}}if(!getSetAttribute){nodeHook={set:function(elem,value,name){var ret=elem.getAttributeNode(name);if(!ret){elem.setAttributeNode(ret=elem.ownerDocument.createAttribute(name))}ret.value=value+="";if(name==="value"||value===elem.getAttribute(name)){return value}}};attrHandle.id=attrHandle.name=attrHandle.coords=function(elem,name,isXML){var ret;if(!isXML){return(ret=elem.getAttributeNode(name))&&ret.value!==""?ret.value:null}};jQuery.valHooks.button={get:function(elem,name){var ret=elem.getAttributeNode(name);if(ret&&ret.specified){return ret.value}},set:nodeHook.set};jQuery.attrHooks.contenteditable={set:function(elem,value,name){nodeHook.set(elem,value===""?false:value,name)}};jQuery.each(["width","height"],function(i,name){jQuery.attrHooks[name]={set:function(elem,value){if(value===""){elem.setAttribute(name,"auto");return value}}}})}if(!support.style){jQuery.attrHooks.style={get:function(elem){return elem.style.cssText||undefined},set:function(elem,value){return elem.style.cssText=value+""}}}var rfocusable=/^(?:input|select|textarea|button|object)$/i,rclickable=/^(?:a|area)$/i;jQuery.fn.extend({prop:function(name,value){return access(this,jQuery.prop,name,value,arguments.length>1)},removeProp:function(name){name=jQuery.propFix[name]||name;return this.each(function(){try{this[name]=undefined;delete this[name]}catch(e){}})}});jQuery.extend({propFix:{"for":"htmlFor","class":"className"},prop:function(elem,name,value){var ret,hooks,notxml,nType=elem.nodeType;if(!elem||nType===3||nType===8||nType===2){return}notxml=nType!==1||!jQuery.isXMLDoc(elem);if(notxml){name=jQuery.propFix[name]||name;hooks=jQuery.propHooks[name]}if(value!==undefined){return hooks&&"set"in hooks&&(ret=hooks.set(elem,value,name))!==undefined?ret:elem[name]=value}else{return hooks&&"get"in hooks&&(ret=hooks.get(elem,name))!==null?ret:elem[name]}},propHooks:{tabIndex:{get:function(elem){var tabindex=jQuery.find.attr(elem,"tabindex");return tabindex?parseInt(tabindex,10):rfocusable.test(elem.nodeName)||rclickable.test(elem.nodeName)&&elem.href?0:-1}}}});if(!support.hrefNormalized){jQuery.each(["href","src"],function(i,name){jQuery.propHooks[name]={get:function(elem){return elem.getAttribute(name,4)}}})}if(!support.optSelected){jQuery.propHooks.selected={get:function(elem){var parent=elem.parentNode;if(parent){parent.selectedIndex;if(parent.parentNode){parent.parentNode.selectedIndex}}return null}}}jQuery.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){jQuery.propFix[this.toLowerCase()]=this});if(!support.enctype){
19
- jQuery.propFix.enctype="encoding"}var rclass=/[\t\r\n\f]/g;jQuery.fn.extend({addClass:function(value){var classes,elem,cur,clazz,j,finalValue,i=0,len=this.length,proceed=typeof value==="string"&&value;if(jQuery.isFunction(value)){return this.each(function(j){jQuery(this).addClass(value.call(this,j,this.className))})}if(proceed){classes=(value||"").match(rnotwhite)||[];for(;i<len;i++){elem=this[i];cur=elem.nodeType===1&&(elem.className?(" "+elem.className+" ").replace(rclass," "):" ");if(cur){j=0;while(clazz=classes[j++]){if(cur.indexOf(" "+clazz+" ")<0){cur+=clazz+" "}}finalValue=jQuery.trim(cur);if(elem.className!==finalValue){elem.className=finalValue}}}}return this},removeClass:function(value){var classes,elem,cur,clazz,j,finalValue,i=0,len=this.length,proceed=arguments.length===0||typeof value==="string"&&value;if(jQuery.isFunction(value)){return this.each(function(j){jQuery(this).removeClass(value.call(this,j,this.className))})}if(proceed){classes=(value||"").match(rnotwhite)||[];for(;i<len;i++){elem=this[i];cur=elem.nodeType===1&&(elem.className?(" "+elem.className+" ").replace(rclass," "):"");if(cur){j=0;while(clazz=classes[j++]){while(cur.indexOf(" "+clazz+" ")>=0){cur=cur.replace(" "+clazz+" "," ")}}finalValue=value?jQuery.trim(cur):"";if(elem.className!==finalValue){elem.className=finalValue}}}}return this},toggleClass:function(value,stateVal){var type=typeof value;if(typeof stateVal==="boolean"&&type==="string"){return stateVal?this.addClass(value):this.removeClass(value)}if(jQuery.isFunction(value)){return this.each(function(i){jQuery(this).toggleClass(value.call(this,i,this.className,stateVal),stateVal)})}return this.each(function(){if(type==="string"){var className,i=0,self=jQuery(this),classNames=value.match(rnotwhite)||[];while(className=classNames[i++]){if(self.hasClass(className)){self.removeClass(className)}else{self.addClass(className)}}}else if(type===strundefined||type==="boolean"){if(this.className){jQuery._data(this,"__className__",this.className)}this.className=this.className||value===false?"":jQuery._data(this,"__className__")||""}})},hasClass:function(selector){var className=" "+selector+" ",i=0,l=this.length;for(;i<l;i++){if(this[i].nodeType===1&&(" "+this[i].className+" ").replace(rclass," ").indexOf(className)>=0){return true}}return false}});jQuery.each(("blur focus focusin focusout load resize scroll unload click dblclick "+"mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave "+"change select submit keydown keypress keyup error contextmenu").split(" "),function(i,name){jQuery.fn[name]=function(data,fn){return arguments.length>0?this.on(name,null,data,fn):this.trigger(name)}});jQuery.fn.extend({hover:function(fnOver,fnOut){return this.mouseenter(fnOver).mouseleave(fnOut||fnOver)},bind:function(types,data,fn){return this.on(types,null,data,fn)},unbind:function(types,fn){return this.off(types,null,fn)},delegate:function(selector,types,data,fn){return this.on(types,selector,data,fn)},undelegate:function(selector,types,fn){return arguments.length===1?this.off(selector,"**"):this.off(types,selector||"**",fn)}});var nonce=jQuery.now();var rquery=/\?/;var rvalidtokens=/(,)|(\[|{)|(}|])|"(?:[^"\\\r\n]|\\["\\\/bfnrt]|\\u[\da-fA-F]{4})*"\s*:?|true|false|null|-?(?!0\d)\d+(?:\.\d+|)(?:[eE][+-]?\d+|)/g;jQuery.parseJSON=function(data){if(window.JSON&&window.JSON.parse){return window.JSON.parse(data+"")}var requireNonComma,depth=null,str=jQuery.trim(data+"");return str&&!jQuery.trim(str.replace(rvalidtokens,function(token,comma,open,close){if(requireNonComma&&comma){depth=0}if(depth===0){return token}requireNonComma=open||comma;depth+=!close-!open;return""}))?Function("return "+str)():jQuery.error("Invalid JSON: "+data)};jQuery.parseXML=function(data){var xml,tmp;if(!data||typeof data!=="string"){return null}try{if(window.DOMParser){tmp=new DOMParser;xml=tmp.parseFromString(data,"text/xml")}else{xml=new ActiveXObject("Microsoft.XMLDOM");xml.async="false";xml.loadXML(data)}}catch(e){xml=undefined}if(!xml||!xml.documentElement||xml.getElementsByTagName("parsererror").length){jQuery.error("Invalid XML: "+data)}return xml};var ajaxLocParts,ajaxLocation,rhash=/#.*$/,rts=/([?&])_=[^&]*/,rheaders=/^(.*?):[ \t]*([^\r\n]*)\r?$/gm,rlocalProtocol=/^(?:about|app|app-storage|.+-extension|file|res|widget):$/,rnoContent=/^(?:GET|HEAD)$/,rprotocol=/^\/\//,rurl=/^([\w.+-]+:)(?:\/\/(?:[^\/?#]*@|)([^\/?#:]*)(?::(\d+)|)|)/,prefilters={},transports={},allTypes="*/".concat("*");try{ajaxLocation=location.href}catch(e){ajaxLocation=document.createElement("a");ajaxLocation.href="";ajaxLocation=ajaxLocation.href}ajaxLocParts=rurl.exec(ajaxLocation.toLowerCase())||[];function addToPrefiltersOrTransports(structure){return function(dataTypeExpression,func){if(typeof dataTypeExpression!=="string"){func=dataTypeExpression;dataTypeExpression="*"}var dataType,i=0,dataTypes=dataTypeExpression.toLowerCase().match(rnotwhite)||[];if(jQuery.isFunction(func)){while(dataType=dataTypes[i++]){if(dataType.charAt(0)==="+"){dataType=dataType.slice(1)||"*";(structure[dataType]=structure[dataType]||[]).unshift(func)}else{(structure[dataType]=structure[dataType]||[]).push(func)}}}}}function inspectPrefiltersOrTransports(structure,options,originalOptions,jqXHR){var inspected={},seekingTransport=structure===transports;function inspect(dataType){var selected;inspected[dataType]=true;jQuery.each(structure[dataType]||[],function(_,prefilterOrFactory){var dataTypeOrTransport=prefilterOrFactory(options,originalOptions,jqXHR);if(typeof dataTypeOrTransport==="string"&&!seekingTransport&&!inspected[dataTypeOrTransport]){options.dataTypes.unshift(dataTypeOrTransport);inspect(dataTypeOrTransport);return false}else if(seekingTransport){return!(selected=dataTypeOrTransport)}});return selected}return inspect(options.dataTypes[0])||!inspected["*"]&&inspect("*")}function ajaxExtend(target,src){var deep,key,flatOptions=jQuery.ajaxSettings.flatOptions||{};for(key in src){if(src[key]!==undefined){(flatOptions[key]?target:deep||(deep={}))[key]=src[key]}}if(deep){jQuery.extend(true,target,deep)}return target}function ajaxHandleResponses(s,jqXHR,responses){var firstDataType,ct,finalDataType,type,contents=s.contents,dataTypes=s.dataTypes;while(dataTypes[0]==="*"){dataTypes.shift();if(ct===undefined){ct=s.mimeType||jqXHR.getResponseHeader("Content-Type")}}if(ct){for(type in contents){if(contents[type]&&contents[type].test(ct)){dataTypes.unshift(type);break}}}if(dataTypes[0]in responses){finalDataType=dataTypes[0]}else{for(type in responses){if(!dataTypes[0]||s.converters[type+" "+dataTypes[0]]){finalDataType=type;break}if(!firstDataType){firstDataType=type}}finalDataType=finalDataType||firstDataType}if(finalDataType){if(finalDataType!==dataTypes[0]){dataTypes.unshift(finalDataType)}return responses[finalDataType]}}function ajaxConvert(s,response,jqXHR,isSuccess){var conv2,current,conv,tmp,prev,converters={},dataTypes=s.dataTypes.slice();if(dataTypes[1]){for(conv in s.converters){converters[conv.toLowerCase()]=s.converters[conv]}}current=dataTypes.shift();while(current){if(s.responseFields[current]){jqXHR[s.responseFields[current]]=response}if(!prev&&isSuccess&&s.dataFilter){response=s.dataFilter(response,s.dataType)}prev=current;current=dataTypes.shift();if(current){if(current==="*"){current=prev}else if(prev!=="*"&&prev!==current){conv=converters[prev+" "+current]||converters["* "+current];if(!conv){for(conv2 in converters){tmp=conv2.split(" ");if(tmp[1]===current){conv=converters[prev+" "+tmp[0]]||converters["* "+tmp[0]];if(conv){if(conv===true){conv=converters[conv2]}else if(converters[conv2]!==true){current=tmp[0];dataTypes.unshift(tmp[1])}break}}}}if(conv!==true){if(conv&&s["throws"]){response=conv(response)}else{try{response=conv(response)}catch(e){return{state:"parsererror",error:conv?e:"No conversion from "+prev+" to "+current}}}}}}}return{state:"success",data:response}}jQuery.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:ajaxLocation,type:"GET",isLocal:rlocalProtocol.test(ajaxLocParts[1]),global:true,processData:true,async:true,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":allTypes,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":true,"text json":jQuery.parseJSON,"text xml":jQuery.parseXML},flatOptions:{url:true,context:true}},ajaxSetup:function(target,settings){return settings?ajaxExtend(ajaxExtend(target,jQuery.ajaxSettings),settings):ajaxExtend(jQuery.ajaxSettings,target)},ajaxPrefilter:addToPrefiltersOrTransports(prefilters),ajaxTransport:addToPrefiltersOrTransports(transports),ajax:function(url,options){if(typeof url==="object"){options=url;url=undefined}options=options||{};var parts,i,cacheURL,responseHeadersString,timeoutTimer,fireGlobals,transport,responseHeaders,s=jQuery.ajaxSetup({},options),callbackContext=s.context||s,globalEventContext=s.context&&(callbackContext.nodeType||callbackContext.jquery)?jQuery(callbackContext):jQuery.event,deferred=jQuery.Deferred(),completeDeferred=jQuery.Callbacks("once memory"),statusCode=s.statusCode||{},requestHeaders={},requestHeadersNames={},state=0,strAbort="canceled",jqXHR={readyState:0,getResponseHeader:function(key){var match;if(state===2){if(!responseHeaders){responseHeaders={};while(match=rheaders.exec(responseHeadersString)){responseHeaders[match[1].toLowerCase()]=match[2]}}match=responseHeaders[key.toLowerCase()]}return match==null?null:match},getAllResponseHeaders:function(){return state===2?responseHeadersString:null},setRequestHeader:function(name,value){var lname=name.toLowerCase();if(!state){name=requestHeadersNames[lname]=requestHeadersNames[lname]||name;requestHeaders[name]=value}return this},overrideMimeType:function(type){if(!state){s.mimeType=type}return this},statusCode:function(map){var code;if(map){if(state<2){for(code in map){statusCode[code]=[statusCode[code],map[code]]}}else{jqXHR.always(map[jqXHR.status])}}return this},abort:function(statusText){var finalText=statusText||strAbort;if(transport){transport.abort(finalText)}done(0,finalText);return this}};deferred.promise(jqXHR).complete=completeDeferred.add;jqXHR.success=jqXHR.done;jqXHR.error=jqXHR.fail;s.url=((url||s.url||ajaxLocation)+"").replace(rhash,"").replace(rprotocol,ajaxLocParts[1]+"//");s.type=options.method||options.type||s.method||s.type;s.dataTypes=jQuery.trim(s.dataType||"*").toLowerCase().match(rnotwhite)||[""];if(s.crossDomain==null){parts=rurl.exec(s.url.toLowerCase());s.crossDomain=!!(parts&&(parts[1]!==ajaxLocParts[1]||parts[2]!==ajaxLocParts[2]||(parts[3]||(parts[1]==="http:"?"80":"443"))!==(ajaxLocParts[3]||(ajaxLocParts[1]==="http:"?"80":"443"))))}if(s.data&&s.processData&&typeof s.data!=="string"){s.data=jQuery.param(s.data,s.traditional)}inspectPrefiltersOrTransports(prefilters,s,options,jqXHR);if(state===2){return jqXHR}fireGlobals=jQuery.event&&s.global;if(fireGlobals&&jQuery.active++===0){jQuery.event.trigger("ajaxStart")}s.type=s.type.toUpperCase();s.hasContent=!rnoContent.test(s.type);cacheURL=s.url;if(!s.hasContent){if(s.data){cacheURL=s.url+=(rquery.test(cacheURL)?"&":"?")+s.data;delete s.data}if(s.cache===false){s.url=rts.test(cacheURL)?cacheURL.replace(rts,"$1_="+nonce++):cacheURL+(rquery.test(cacheURL)?"&":"?")+"_="+nonce++}}if(s.ifModified){if(jQuery.lastModified[cacheURL]){jqXHR.setRequestHeader("If-Modified-Since",jQuery.lastModified[cacheURL])}if(jQuery.etag[cacheURL]){jqXHR.setRequestHeader("If-None-Match",jQuery.etag[cacheURL])}}if(s.data&&s.hasContent&&s.contentType!==false||options.contentType){jqXHR.setRequestHeader("Content-Type",s.contentType)}jqXHR.setRequestHeader("Accept",s.dataTypes[0]&&s.accepts[s.dataTypes[0]]?s.accepts[s.dataTypes[0]]+(s.dataTypes[0]!=="*"?", "+allTypes+"; q=0.01":""):s.accepts["*"]);for(i in s.headers){jqXHR.setRequestHeader(i,s.headers[i])}if(s.beforeSend&&(s.beforeSend.call(callbackContext,jqXHR,s)===false||state===2)){return jqXHR.abort()}strAbort="abort";for(i in{success:1,error:1,complete:1}){jqXHR[i](s[i])}transport=inspectPrefiltersOrTransports(transports,s,options,jqXHR);if(!transport){done(-1,"No Transport")}else{jqXHR.readyState=1;if(fireGlobals){globalEventContext.trigger("ajaxSend",[jqXHR,s])}if(s.async&&s.timeout>0){timeoutTimer=setTimeout(function(){jqXHR.abort("timeout")},s.timeout)}try{state=1;transport.send(requestHeaders,done)}catch(e){if(state<2){done(-1,e)}else{throw e}}}function done(status,nativeStatusText,responses,headers){var isSuccess,success,error,response,modified,statusText=nativeStatusText;if(state===2){return}state=2;if(timeoutTimer){clearTimeout(timeoutTimer)}transport=undefined;responseHeadersString=headers||"";jqXHR.readyState=status>0?4:0;isSuccess=status>=200&&status<300||status===304;if(responses){response=ajaxHandleResponses(s,jqXHR,responses)}response=ajaxConvert(s,response,jqXHR,isSuccess);if(isSuccess){if(s.ifModified){modified=jqXHR.getResponseHeader("Last-Modified");if(modified){jQuery.lastModified[cacheURL]=modified}modified=jqXHR.getResponseHeader("etag");if(modified){jQuery.etag[cacheURL]=modified}}if(status===204||s.type==="HEAD"){statusText="nocontent"}else if(status===304){statusText="notmodified"}else{statusText=response.state;success=response.data;error=response.error;isSuccess=!error}}else{error=statusText;if(status||!statusText){statusText="error";if(status<0){status=0}}}jqXHR.status=status;jqXHR.statusText=(nativeStatusText||statusText)+"";if(isSuccess){deferred.resolveWith(callbackContext,[success,statusText,jqXHR])}else{deferred.rejectWith(callbackContext,[jqXHR,statusText,error])}jqXHR.statusCode(statusCode);statusCode=undefined;if(fireGlobals){globalEventContext.trigger(isSuccess?"ajaxSuccess":"ajaxError",[jqXHR,s,isSuccess?success:error])}completeDeferred.fireWith(callbackContext,[jqXHR,statusText]);if(fireGlobals){globalEventContext.trigger("ajaxComplete",[jqXHR,s]);if(!--jQuery.active){jQuery.event.trigger("ajaxStop")}}}return jqXHR},getJSON:function(url,data,callback){return jQuery.get(url,data,callback,"json")},getScript:function(url,callback){return jQuery.get(url,undefined,callback,"script")}});jQuery.each(["get","post"],function(i,method){jQuery[method]=function(url,data,callback,type){if(jQuery.isFunction(data)){type=type||callback;callback=data;data=undefined}return jQuery.ajax({url:url,type:method,dataType:type,data:data,success:callback})}});jQuery._evalUrl=function(url){return jQuery.ajax({url:url,type:"GET",dataType:"script",async:false,global:false,"throws":true})};jQuery.fn.extend({wrapAll:function(html){if(jQuery.isFunction(html)){return this.each(function(i){jQuery(this).wrapAll(html.call(this,i))})}if(this[0]){var wrap=jQuery(html,this[0].ownerDocument).eq(0).clone(true);if(this[0].parentNode){wrap.insertBefore(this[0])}wrap.map(function(){var elem=this;while(elem.firstChild&&elem.firstChild.nodeType===1){elem=elem.firstChild}return elem}).append(this)}return this},wrapInner:function(html){if(jQuery.isFunction(html)){return this.each(function(i){jQuery(this).wrapInner(html.call(this,i))})}return this.each(function(){var self=jQuery(this),contents=self.contents();if(contents.length){contents.wrapAll(html)}else{self.append(html)}})},wrap:function(html){var isFunction=jQuery.isFunction(html);return this.each(function(i){jQuery(this).wrapAll(isFunction?html.call(this,i):html)})},unwrap:function(){return this.parent().each(function(){if(!jQuery.nodeName(this,"body")){jQuery(this).replaceWith(this.childNodes)}}).end()}});jQuery.expr.filters.hidden=function(elem){return elem.offsetWidth<=0&&elem.offsetHeight<=0||!support.reliableHiddenOffsets()&&(elem.style&&elem.style.display||jQuery.css(elem,"display"))==="none"};jQuery.expr.filters.visible=function(elem){return!jQuery.expr.filters.hidden(elem)};var r20=/%20/g,rbracket=/\[\]$/,rCRLF=/\r?\n/g,rsubmitterTypes=/^(?:submit|button|image|reset|file)$/i,rsubmittable=/^(?:input|select|textarea|keygen)/i;function buildParams(prefix,obj,traditional,add){var name;if(jQuery.isArray(obj)){jQuery.each(obj,function(i,v){if(traditional||rbracket.test(prefix)){add(prefix,v)}else{buildParams(prefix+"["+(typeof v==="object"?i:"")+"]",v,traditional,add)}})}else if(!traditional&&jQuery.type(obj)==="object"){for(name in obj){buildParams(prefix+"["+name+"]",obj[name],traditional,add)}}else{add(prefix,obj)}}jQuery.param=function(a,traditional){var prefix,s=[],add=function(key,value){value=jQuery.isFunction(value)?value():value==null?"":value;s[s.length]=encodeURIComponent(key)+"="+encodeURIComponent(value)};if(traditional===undefined){traditional=jQuery.ajaxSettings&&jQuery.ajaxSettings.traditional}if(jQuery.isArray(a)||a.jquery&&!jQuery.isPlainObject(a)){jQuery.each(a,function(){add(this.name,this.value)})}else{for(prefix in a){buildParams(prefix,a[prefix],traditional,add)}}return s.join("&").replace(r20,"+")};jQuery.fn.extend({serialize:function(){return jQuery.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var elements=jQuery.prop(this,"elements");return elements?jQuery.makeArray(elements):this}).filter(function(){var type=this.type;return this.name&&!jQuery(this).is(":disabled")&&rsubmittable.test(this.nodeName)&&!rsubmitterTypes.test(type)&&(this.checked||!rcheckableType.test(type))}).map(function(i,elem){var val=jQuery(this).val();return val==null?null:jQuery.isArray(val)?jQuery.map(val,function(val){return{name:elem.name,value:val.replace(rCRLF,"\r\n")}}):{name:elem.name,value:val.replace(rCRLF,"\r\n")}}).get()}});jQuery.ajaxSettings.xhr=window.ActiveXObject!==undefined?function(){return!this.isLocal&&/^(get|post|head|put|delete|options)$/i.test(this.type)&&createStandardXHR()||createActiveXHR()}:createStandardXHR;var xhrId=0,xhrCallbacks={},xhrSupported=jQuery.ajaxSettings.xhr();if(window.attachEvent){window.attachEvent("onunload",function(){for(var key in xhrCallbacks){xhrCallbacks[key](undefined,true)}})}support.cors=!!xhrSupported&&"withCredentials"in xhrSupported;xhrSupported=support.ajax=!!xhrSupported;if(xhrSupported){jQuery.ajaxTransport(function(options){if(!options.crossDomain||support.cors){var callback;return{send:function(headers,complete){var i,xhr=options.xhr(),id=++xhrId;xhr.open(options.type,options.url,options.async,options.username,options.password);if(options.xhrFields){for(i in options.xhrFields){xhr[i]=options.xhrFields[i]}}if(options.mimeType&&xhr.overrideMimeType){xhr.overrideMimeType(options.mimeType)}if(!options.crossDomain&&!headers["X-Requested-With"]){headers["X-Requested-With"]="XMLHttpRequest"}for(i in headers){if(headers[i]!==undefined){xhr.setRequestHeader(i,headers[i]+"")}}xhr.send(options.hasContent&&options.data||null);callback=function(_,isAbort){var status,statusText,responses;if(callback&&(isAbort||xhr.readyState===4)){delete xhrCallbacks[id];callback=undefined;xhr.onreadystatechange=jQuery.noop;if(isAbort){if(xhr.readyState!==4){xhr.abort()}}else{responses={};status=xhr.status;if(typeof xhr.responseText==="string"){responses.text=xhr.responseText}try{statusText=xhr.statusText}catch(e){statusText=""}if(!status&&options.isLocal&&!options.crossDomain){status=responses.text?200:404}else if(status===1223){status=204}}}if(responses){complete(status,statusText,responses,xhr.getAllResponseHeaders())}};if(!options.async){callback()}else if(xhr.readyState===4){setTimeout(callback)}else{xhr.onreadystatechange=xhrCallbacks[id]=callback}},abort:function(){if(callback){callback(undefined,true)}}}}})}function createStandardXHR(){try{return new window.XMLHttpRequest}catch(e){}}function createActiveXHR(){try{return new window.ActiveXObject("Microsoft.XMLHTTP")}catch(e){}}jQuery.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/(?:java|ecma)script/},converters:{"text script":function(text){jQuery.globalEval(text);return text}}});jQuery.ajaxPrefilter("script",function(s){if(s.cache===undefined){s.cache=false}if(s.crossDomain){s.type="GET";s.global=false}});jQuery.ajaxTransport("script",function(s){if(s.crossDomain){var script,head=document.head||jQuery("head")[0]||document.documentElement;return{send:function(_,callback){script=document.createElement("script");script.async=true;if(s.scriptCharset){script.charset=s.scriptCharset}script.src=s.url;script.onload=script.onreadystatechange=function(_,isAbort){if(isAbort||!script.readyState||/loaded|complete/.test(script.readyState)){script.onload=script.onreadystatechange=null;if(script.parentNode){script.parentNode.removeChild(script)}script=null;if(!isAbort){callback(200,"success")}}};head.insertBefore(script,head.firstChild)},abort:function(){if(script){script.onload(undefined,true)}}}}});var oldCallbacks=[],rjsonp=/(=)\?(?=&|$)|\?\?/;jQuery.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var callback=oldCallbacks.pop()||jQuery.expando+"_"+nonce++;this[callback]=true;return callback}});jQuery.ajaxPrefilter("json jsonp",function(s,originalSettings,jqXHR){var callbackName,overwritten,responseContainer,jsonProp=s.jsonp!==false&&(rjsonp.test(s.url)?"url":typeof s.data==="string"&&!(s.contentType||"").indexOf("application/x-www-form-urlencoded")&&rjsonp.test(s.data)&&"data");if(jsonProp||s.dataTypes[0]==="jsonp"){callbackName=s.jsonpCallback=jQuery.isFunction(s.jsonpCallback)?s.jsonpCallback():s.jsonpCallback;if(jsonProp){s[jsonProp]=s[jsonProp].replace(rjsonp,"$1"+callbackName)}else if(s.jsonp!==false){s.url+=(rquery.test(s.url)?"&":"?")+s.jsonp+"="+callbackName}s.converters["script json"]=function(){if(!responseContainer){jQuery.error(callbackName+" was not called")}return responseContainer[0]};s.dataTypes[0]="json";overwritten=window[callbackName];window[callbackName]=function(){responseContainer=arguments};jqXHR.always(function(){window[callbackName]=overwritten;if(s[callbackName]){s.jsonpCallback=originalSettings.jsonpCallback;oldCallbacks.push(callbackName)}if(responseContainer&&jQuery.isFunction(overwritten)){overwritten(responseContainer[0])}responseContainer=overwritten=undefined});return"script"}});jQuery.parseHTML=function(data,context,keepScripts){if(!data||typeof data!=="string"){return null}if(typeof context==="boolean"){keepScripts=context;context=false}context=context||document;var parsed=rsingleTag.exec(data),scripts=!keepScripts&&[];if(parsed){return[context.createElement(parsed[1])]}parsed=jQuery.buildFragment([data],context,scripts);if(scripts&&scripts.length){jQuery(scripts).remove()}return jQuery.merge([],parsed.childNodes)};var _load=jQuery.fn.load;jQuery.fn.load=function(url,params,callback){if(typeof url!=="string"&&_load){return _load.apply(this,arguments)}var selector,response,type,self=this,off=url.indexOf(" ");if(off>=0){selector=jQuery.trim(url.slice(off,url.length));url=url.slice(0,off)}if(jQuery.isFunction(params)){callback=params;params=undefined}else if(params&&typeof params==="object"){type="POST"}if(self.length>0){jQuery.ajax({url:url,type:type,dataType:"html",data:params}).done(function(responseText){response=arguments;self.html(selector?jQuery("<div>").append(jQuery.parseHTML(responseText)).find(selector):responseText)}).complete(callback&&function(jqXHR,status){self.each(callback,response||[jqXHR.responseText,status,jqXHR])})}return this};jQuery.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(i,type){jQuery.fn[type]=function(fn){return this.on(type,fn)}});jQuery.expr.filters.animated=function(elem){return jQuery.grep(jQuery.timers,function(fn){return elem===fn.elem}).length};var docElem=window.document.documentElement;function getWindow(elem){return jQuery.isWindow(elem)?elem:elem.nodeType===9?elem.defaultView||elem.parentWindow:false}jQuery.offset={setOffset:function(elem,options,i){var curPosition,curLeft,curCSSTop,curTop,curOffset,curCSSLeft,calculatePosition,position=jQuery.css(elem,"position"),curElem=jQuery(elem),props={};if(position==="static"){elem.style.position="relative"}curOffset=curElem.offset();curCSSTop=jQuery.css(elem,"top");curCSSLeft=jQuery.css(elem,"left");calculatePosition=(position==="absolute"||position==="fixed")&&jQuery.inArray("auto",[curCSSTop,curCSSLeft])>-1;if(calculatePosition){curPosition=curElem.position();curTop=curPosition.top;curLeft=curPosition.left}else{curTop=parseFloat(curCSSTop)||0;curLeft=parseFloat(curCSSLeft)||0}if(jQuery.isFunction(options)){options=options.call(elem,i,curOffset)}if(options.top!=null){props.top=options.top-curOffset.top+curTop}if(options.left!=null){props.left=options.left-curOffset.left+curLeft}if("using"in options){options.using.call(elem,props)}else{curElem.css(props)}}};jQuery.fn.extend({offset:function(options){if(arguments.length){return options===undefined?this:this.each(function(i){jQuery.offset.setOffset(this,options,i)})}var docElem,win,box={top:0,left:0},elem=this[0],doc=elem&&elem.ownerDocument;if(!doc){return}docElem=doc.documentElement;if(!jQuery.contains(docElem,elem)){return box}if(typeof elem.getBoundingClientRect!==strundefined){box=elem.getBoundingClientRect()}win=getWindow(doc);return{top:box.top+(win.pageYOffset||docElem.scrollTop)-(docElem.clientTop||0),left:box.left+(win.pageXOffset||docElem.scrollLeft)-(docElem.clientLeft||0)}},position:function(){if(!this[0]){return}var offsetParent,offset,parentOffset={top:0,left:0},elem=this[0];if(jQuery.css(elem,"position")==="fixed"){offset=elem.getBoundingClientRect()}else{offsetParent=this.offsetParent();offset=this.offset();if(!jQuery.nodeName(offsetParent[0],"html")){parentOffset=offsetParent.offset()}parentOffset.top+=jQuery.css(offsetParent[0],"borderTopWidth",true);parentOffset.left+=jQuery.css(offsetParent[0],"borderLeftWidth",true)}return{top:offset.top-parentOffset.top-jQuery.css(elem,"marginTop",true),left:offset.left-parentOffset.left-jQuery.css(elem,"marginLeft",true)}},offsetParent:function(){return this.map(function(){var offsetParent=this.offsetParent||docElem;while(offsetParent&&(!jQuery.nodeName(offsetParent,"html")&&jQuery.css(offsetParent,"position")==="static")){offsetParent=offsetParent.offsetParent}return offsetParent||docElem})}});jQuery.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(method,prop){var top=/Y/.test(prop);jQuery.fn[method]=function(val){return access(this,function(elem,method,val){var win=getWindow(elem);if(val===undefined){return win?prop in win?win[prop]:win.document.documentElement[method]:elem[method]}if(win){win.scrollTo(!top?val:jQuery(win).scrollLeft(),top?val:jQuery(win).scrollTop())}else{elem[method]=val}},method,val,arguments.length,null)}});jQuery.each(["top","left"],function(i,prop){jQuery.cssHooks[prop]=addGetHookIf(support.pixelPosition,function(elem,computed){if(computed){computed=curCSS(elem,prop);return rnumnonpx.test(computed)?jQuery(elem).position()[prop]+"px":computed}})});jQuery.each({Height:"height",Width:"width"},function(name,type){jQuery.each({padding:"inner"+name,content:type,"":"outer"+name},function(defaultExtra,funcName){jQuery.fn[funcName]=function(margin,value){var chainable=arguments.length&&(defaultExtra||typeof margin!=="boolean"),extra=defaultExtra||(margin===true||value===true?"margin":"border");return access(this,function(elem,type,value){var doc;if(jQuery.isWindow(elem)){return elem.document.documentElement["client"+name]}if(elem.nodeType===9){doc=elem.documentElement;return Math.max(elem.body["scroll"+name],doc["scroll"+name],elem.body["offset"+name],doc["offset"+name],doc["client"+name])}return value===undefined?jQuery.css(elem,type,extra):jQuery.style(elem,type,value,extra)},type,chainable?margin:undefined,chainable,null)}})});jQuery.fn.size=function(){return this.length};jQuery.fn.andSelf=jQuery.fn.addBack;if(typeof define==="function"&&define.amd){define("jquery",[],function(){return jQuery})}var _jQuery=window.jQuery,_$=window.$;jQuery.noConflict=function(deep){if(window.$===jQuery){window.$=_$}if(deep&&window.jQuery===jQuery){window.jQuery=_jQuery}return jQuery};if(typeof noGlobal===strundefined){window.jQuery=window.$=jQuery}return jQuery})},{}],208:[function(require,module,exports){(function($){var _=function(){"use strict";return{isMsie:function(){return/(msie|trident)/i.test(navigator.userAgent)?navigator.userAgent.match(/(msie |rv:)(\d+(.\d+)?)/i)[2]:false},isBlankString:function(str){return!str||/^\s*$/.test(str)},escapeRegExChars:function(str){return str.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g,"\\$&")},isString:function(obj){return typeof obj==="string"},isNumber:function(obj){return typeof obj==="number"},isArray:$.isArray,isFunction:$.isFunction,isObject:$.isPlainObject,isUndefined:function(obj){return typeof obj==="undefined"},toStr:function toStr(s){return _.isUndefined(s)||s===null?"":s+""},bind:$.proxy,each:function(collection,cb){$.each(collection,reverseArgs);function reverseArgs(index,value){return cb(value,index)}},map:$.map,filter:$.grep,every:function(obj,test){var result=true;if(!obj){return result}$.each(obj,function(key,val){if(!(result=test.call(null,val,key,obj))){return false}});return!!result},some:function(obj,test){var result=false;if(!obj){return result}$.each(obj,function(key,val){if(result=test.call(null,val,key,obj)){return false}});return!!result},mixin:$.extend,getUniqueId:function(){var counter=0;return function(){return counter++}}(),templatify:function templatify(obj){return $.isFunction(obj)?obj:template;function template(){return String(obj)}},defer:function(fn){setTimeout(fn,0)},debounce:function(func,wait,immediate){var timeout,result;return function(){var context=this,args=arguments,later,callNow;later=function(){timeout=null;if(!immediate){result=func.apply(context,args)}};callNow=immediate&&!timeout;clearTimeout(timeout);timeout=setTimeout(later,wait);if(callNow){result=func.apply(context,args)}return result}},throttle:function(func,wait){var context,args,timeout,result,previous,later;previous=0;later=function(){previous=new Date;timeout=null;result=func.apply(context,args)};return function(){var now=new Date,remaining=wait-(now-previous);context=this;args=arguments;if(remaining<=0){clearTimeout(timeout);timeout=null;previous=now;result=func.apply(context,args)}else if(!timeout){timeout=setTimeout(later,remaining)}return result}},noop:function(){}}}();var VERSION="0.10.5";var tokenizers=function(){"use strict";return{nonword:nonword,whitespace:whitespace,obj:{nonword:getObjTokenizer(nonword),whitespace:getObjTokenizer(whitespace)}};function whitespace(str){str=_.toStr(str);return str?str.split(/\s+/):[]}function nonword(str){str=_.toStr(str);return str?str.split(/\W+/):[]}function getObjTokenizer(tokenizer){return function setKey(){var args=[].slice.call(arguments,0);return function tokenize(o){var tokens=[];_.each(args,function(k){tokens=tokens.concat(tokenizer(_.toStr(o[k])))});return tokens}}}}();var LruCache=function(){"use strict";function LruCache(maxSize){this.maxSize=_.isNumber(maxSize)?maxSize:100;this.reset();if(this.maxSize<=0){this.set=this.get=$.noop}}_.mixin(LruCache.prototype,{set:function set(key,val){var tailItem=this.list.tail,node;if(this.size>=this.maxSize){this.list.remove(tailItem);delete this.hash[tailItem.key]}if(node=this.hash[key]){node.val=val;this.list.moveToFront(node)}else{node=new Node(key,val);this.list.add(node);this.hash[key]=node;this.size++}},get:function get(key){var node=this.hash[key];if(node){this.list.moveToFront(node);return node.val}},reset:function reset(){this.size=0;this.hash={};this.list=new List}});function List(){this.head=this.tail=null}_.mixin(List.prototype,{add:function add(node){if(this.head){node.next=this.head;this.head.prev=node}this.head=node;this.tail=this.tail||node},remove:function remove(node){node.prev?node.prev.next=node.next:this.head=node.next;node.next?node.next.prev=node.prev:this.tail=node.prev},moveToFront:function(node){this.remove(node);this.add(node)}});function Node(key,val){this.key=key;this.val=val;this.prev=this.next=null}return LruCache}();var PersistentStorage=function(){
20
- "use strict";var ls,methods;try{ls=window.localStorage;ls.setItem("~~~","!");ls.removeItem("~~~")}catch(err){ls=null}function PersistentStorage(namespace){this.prefix=["__",namespace,"__"].join("");this.ttlKey="__ttl__";this.keyMatcher=new RegExp("^"+_.escapeRegExChars(this.prefix))}if(ls&&window.JSON){methods={_prefix:function(key){return this.prefix+key},_ttlKey:function(key){return this._prefix(key)+this.ttlKey},get:function(key){if(this.isExpired(key)){this.remove(key)}return decode(ls.getItem(this._prefix(key)))},set:function(key,val,ttl){if(_.isNumber(ttl)){ls.setItem(this._ttlKey(key),encode(now()+ttl))}else{ls.removeItem(this._ttlKey(key))}return ls.setItem(this._prefix(key),encode(val))},remove:function(key){ls.removeItem(this._ttlKey(key));ls.removeItem(this._prefix(key));return this},clear:function(){var i,key,keys=[],len=ls.length;for(i=0;i<len;i++){if((key=ls.key(i)).match(this.keyMatcher)){keys.push(key.replace(this.keyMatcher,""))}}for(i=keys.length;i--;){this.remove(keys[i])}return this},isExpired:function(key){var ttl=decode(ls.getItem(this._ttlKey(key)));return _.isNumber(ttl)&&now()>ttl?true:false}}}else{methods={get:_.noop,set:_.noop,remove:_.noop,clear:_.noop,isExpired:_.noop}}_.mixin(PersistentStorage.prototype,methods);return PersistentStorage;function now(){return(new Date).getTime()}function encode(val){return JSON.stringify(_.isUndefined(val)?null:val)}function decode(val){return JSON.parse(val)}}();var Transport=function(){"use strict";var pendingRequestsCount=0,pendingRequests={},maxPendingRequests=6,sharedCache=new LruCache(10);function Transport(o){o=o||{};this.cancelled=false;this.lastUrl=null;this._send=o.transport?callbackToDeferred(o.transport):$.ajax;this._get=o.rateLimiter?o.rateLimiter(this._get):this._get;this._cache=o.cache===false?new LruCache(0):sharedCache}Transport.setMaxPendingRequests=function setMaxPendingRequests(num){maxPendingRequests=num};Transport.resetCache=function resetCache(){sharedCache.reset()};_.mixin(Transport.prototype,{_get:function(url,o,cb){var that=this,jqXhr;if(this.cancelled||url!==this.lastUrl){return}if(jqXhr=pendingRequests[url]){jqXhr.done(done).fail(fail)}else if(pendingRequestsCount<maxPendingRequests){pendingRequestsCount++;pendingRequests[url]=this._send(url,o).done(done).fail(fail).always(always)}else{this.onDeckRequestArgs=[].slice.call(arguments,0)}function done(resp){cb&&cb(null,resp);that._cache.set(url,resp)}function fail(){cb&&cb(true)}function always(){pendingRequestsCount--;delete pendingRequests[url];if(that.onDeckRequestArgs){that._get.apply(that,that.onDeckRequestArgs);that.onDeckRequestArgs=null}}},get:function(url,o,cb){var resp;if(_.isFunction(o)){cb=o;o={}}this.cancelled=false;this.lastUrl=url;if(resp=this._cache.get(url)){_.defer(function(){cb&&cb(null,resp)})}else{this._get(url,o,cb)}return!!resp},cancel:function(){this.cancelled=true}});return Transport;function callbackToDeferred(fn){return function customSendWrapper(url,o){var deferred=$.Deferred();fn(url,o,onSuccess,onError);return deferred;function onSuccess(resp){_.defer(function(){deferred.resolve(resp)})}function onError(err){_.defer(function(){deferred.reject(err)})}}}}();var SearchIndex=function(){"use strict";function SearchIndex(o){o=o||{};if(!o.datumTokenizer||!o.queryTokenizer){$.error("datumTokenizer and queryTokenizer are both required")}this.datumTokenizer=o.datumTokenizer;this.queryTokenizer=o.queryTokenizer;this.reset()}_.mixin(SearchIndex.prototype,{bootstrap:function bootstrap(o){this.datums=o.datums;this.trie=o.trie},add:function(data){var that=this;data=_.isArray(data)?data:[data];_.each(data,function(datum){var id,tokens;id=that.datums.push(datum)-1;tokens=normalizeTokens(that.datumTokenizer(datum));_.each(tokens,function(token){var node,chars,ch;node=that.trie;chars=token.split("");while(ch=chars.shift()){node=node.children[ch]||(node.children[ch]=newNode());node.ids.push(id)}})})},get:function get(query){var that=this,tokens,matches;tokens=normalizeTokens(this.queryTokenizer(query));_.each(tokens,function(token){var node,chars,ch,ids;if(matches&&matches.length===0){return false}node=that.trie;chars=token.split("");while(node&&(ch=chars.shift())){node=node.children[ch]}if(node&&chars.length===0){ids=node.ids.slice(0);matches=matches?getIntersection(matches,ids):ids}else{matches=[];return false}});return matches?_.map(unique(matches),function(id){return that.datums[id]}):[]},reset:function reset(){this.datums=[];this.trie=newNode()},serialize:function serialize(){return{datums:this.datums,trie:this.trie}}});return SearchIndex;function normalizeTokens(tokens){tokens=_.filter(tokens,function(token){return!!token});tokens=_.map(tokens,function(token){return token.toLowerCase()});return tokens}function newNode(){return{ids:[],children:{}}}function unique(array){var seen={},uniques=[];for(var i=0,len=array.length;i<len;i++){if(!seen[array[i]]){seen[array[i]]=true;uniques.push(array[i])}}return uniques}function getIntersection(arrayA,arrayB){var ai=0,bi=0,intersection=[];arrayA=arrayA.sort(compare);arrayB=arrayB.sort(compare);var lenArrayA=arrayA.length,lenArrayB=arrayB.length;while(ai<lenArrayA&&bi<lenArrayB){if(arrayA[ai]<arrayB[bi]){ai++}else if(arrayA[ai]>arrayB[bi]){bi++}else{intersection.push(arrayA[ai]);ai++;bi++}}return intersection;function compare(a,b){return a-b}}}();var oParser=function(){"use strict";return{local:getLocal,prefetch:getPrefetch,remote:getRemote};function getLocal(o){return o.local||null}function getPrefetch(o){var prefetch,defaults;defaults={url:null,thumbprint:"",ttl:24*60*60*1e3,filter:null,ajax:{}};if(prefetch=o.prefetch||null){prefetch=_.isString(prefetch)?{url:prefetch}:prefetch;prefetch=_.mixin(defaults,prefetch);prefetch.thumbprint=VERSION+prefetch.thumbprint;prefetch.ajax.type=prefetch.ajax.type||"GET";prefetch.ajax.dataType=prefetch.ajax.dataType||"json";!prefetch.url&&$.error("prefetch requires url to be set")}return prefetch}function getRemote(o){var remote,defaults;defaults={url:null,cache:true,wildcard:"%QUERY",replace:null,rateLimitBy:"debounce",rateLimitWait:300,send:null,filter:null,ajax:{}};if(remote=o.remote||null){remote=_.isString(remote)?{url:remote}:remote;remote=_.mixin(defaults,remote);remote.rateLimiter=/^throttle$/i.test(remote.rateLimitBy)?byThrottle(remote.rateLimitWait):byDebounce(remote.rateLimitWait);remote.ajax.type=remote.ajax.type||"GET";remote.ajax.dataType=remote.ajax.dataType||"json";delete remote.rateLimitBy;delete remote.rateLimitWait;!remote.url&&$.error("remote requires url to be set")}return remote;function byDebounce(wait){return function(fn){return _.debounce(fn,wait)}}function byThrottle(wait){return function(fn){return _.throttle(fn,wait)}}}}();(function(root){"use strict";var old,keys;old=root.Bloodhound;keys={data:"data",protocol:"protocol",thumbprint:"thumbprint"};root.Bloodhound=Bloodhound;function Bloodhound(o){if(!o||!o.local&&!o.prefetch&&!o.remote){$.error("one of local, prefetch, or remote is required")}this.limit=o.limit||5;this.sorter=getSorter(o.sorter);this.dupDetector=o.dupDetector||ignoreDuplicates;this.local=oParser.local(o);this.prefetch=oParser.prefetch(o);this.remote=oParser.remote(o);this.cacheKey=this.prefetch?this.prefetch.cacheKey||this.prefetch.url:null;this.index=new SearchIndex({datumTokenizer:o.datumTokenizer,queryTokenizer:o.queryTokenizer});this.storage=this.cacheKey?new PersistentStorage(this.cacheKey):null}Bloodhound.noConflict=function noConflict(){root.Bloodhound=old;return Bloodhound};Bloodhound.tokenizers=tokenizers;_.mixin(Bloodhound.prototype,{_loadPrefetch:function loadPrefetch(o){var that=this,serialized,deferred;if(serialized=this._readFromStorage(o.thumbprint)){this.index.bootstrap(serialized);deferred=$.Deferred().resolve()}else{deferred=$.ajax(o.url,o.ajax).done(handlePrefetchResponse)}return deferred;function handlePrefetchResponse(resp){that.clear();that.add(o.filter?o.filter(resp):resp);that._saveToStorage(that.index.serialize(),o.thumbprint,o.ttl)}},_getFromRemote:function getFromRemote(query,cb){var that=this,url,uriEncodedQuery;if(!this.transport){return}query=query||"";uriEncodedQuery=encodeURIComponent(query);url=this.remote.replace?this.remote.replace(this.remote.url,query):this.remote.url.replace(this.remote.wildcard,uriEncodedQuery);return this.transport.get(url,this.remote.ajax,handleRemoteResponse);function handleRemoteResponse(err,resp){err?cb([]):cb(that.remote.filter?that.remote.filter(resp):resp)}},_cancelLastRemoteRequest:function cancelLastRemoteRequest(){this.transport&&this.transport.cancel()},_saveToStorage:function saveToStorage(data,thumbprint,ttl){if(this.storage){this.storage.set(keys.data,data,ttl);this.storage.set(keys.protocol,location.protocol,ttl);this.storage.set(keys.thumbprint,thumbprint,ttl)}},_readFromStorage:function readFromStorage(thumbprint){var stored={},isExpired;if(this.storage){stored.data=this.storage.get(keys.data);stored.protocol=this.storage.get(keys.protocol);stored.thumbprint=this.storage.get(keys.thumbprint)}isExpired=stored.thumbprint!==thumbprint||stored.protocol!==location.protocol;return stored.data&&!isExpired?stored.data:null},_initialize:function initialize(){var that=this,local=this.local,deferred;deferred=this.prefetch?this._loadPrefetch(this.prefetch):$.Deferred().resolve();local&&deferred.done(addLocalToIndex);this.transport=this.remote?new Transport(this.remote):null;return this.initPromise=deferred.promise();function addLocalToIndex(){that.add(_.isFunction(local)?local():local)}},initialize:function initialize(force){return!this.initPromise||force?this._initialize():this.initPromise},add:function add(data){this.index.add(data)},get:function get(query,cb){var that=this,matches=[],cacheHit=false;matches=this.index.get(query);matches=this.sorter(matches).slice(0,this.limit);matches.length<this.limit?cacheHit=this._getFromRemote(query,returnRemoteMatches):this._cancelLastRemoteRequest();if(!cacheHit){(matches.length>0||!this.transport)&&cb&&cb(matches)}function returnRemoteMatches(remoteMatches){var matchesWithBackfill=matches.slice(0);_.each(remoteMatches,function(remoteMatch){var isDuplicate;isDuplicate=_.some(matchesWithBackfill,function(match){return that.dupDetector(remoteMatch,match)});!isDuplicate&&matchesWithBackfill.push(remoteMatch);return matchesWithBackfill.length<that.limit});cb&&cb(that.sorter(matchesWithBackfill))}},clear:function clear(){this.index.reset()},clearPrefetchCache:function clearPrefetchCache(){this.storage&&this.storage.clear()},clearRemoteCache:function clearRemoteCache(){this.transport&&Transport.resetCache()},ttAdapter:function ttAdapter(){return _.bind(this.get,this)}});return Bloodhound;function getSorter(sortFn){return _.isFunction(sortFn)?sort:noSort;function sort(array){return array.sort(sortFn)}function noSort(array){return array}}function ignoreDuplicates(){return false}})(this);var html=function(){return{wrapper:'<span class="twitter-typeahead"></span>',dropdown:'<span class="tt-dropdown-menu"></span>',dataset:'<div class="tt-dataset-%CLASS%"></div>',suggestions:'<span class="tt-suggestions"></span>',suggestion:'<div class="tt-suggestion"></div>'}}();var css=function(){"use strict";var css={wrapper:{position:"relative",display:"inline-block"},hint:{position:"absolute",top:"0",left:"0",borderColor:"transparent",boxShadow:"none",opacity:"1"},input:{position:"relative",verticalAlign:"top",backgroundColor:"transparent"},inputWithNoHint:{position:"relative",verticalAlign:"top"},dropdown:{position:"absolute",top:"100%",left:"0",zIndex:"100",display:"none"},suggestions:{display:"block"},suggestion:{whiteSpace:"nowrap",cursor:"pointer"},suggestionChild:{whiteSpace:"normal"},ltr:{left:"0",right:"auto"},rtl:{left:"auto",right:" 0"}};if(_.isMsie()){_.mixin(css.input,{backgroundImage:"url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7)"})}if(_.isMsie()&&_.isMsie()<=7){_.mixin(css.input,{marginTop:"-1px"})}return css}();var EventBus=function(){"use strict";var namespace="typeahead:";function EventBus(o){if(!o||!o.el){$.error("EventBus initialized without el")}this.$el=$(o.el)}_.mixin(EventBus.prototype,{trigger:function(type){var args=[].slice.call(arguments,1);this.$el.trigger(namespace+type,args)}});return EventBus}();var EventEmitter=function(){"use strict";var splitter=/\s+/,nextTick=getNextTick();return{onSync:onSync,onAsync:onAsync,off:off,trigger:trigger};function on(method,types,cb,context){var type;if(!cb){return this}types=types.split(splitter);cb=context?bindContext(cb,context):cb;this._callbacks=this._callbacks||{};while(type=types.shift()){this._callbacks[type]=this._callbacks[type]||{sync:[],async:[]};this._callbacks[type][method].push(cb)}return this}function onAsync(types,cb,context){return on.call(this,"async",types,cb,context)}function onSync(types,cb,context){return on.call(this,"sync",types,cb,context)}function off(types){var type;if(!this._callbacks){return this}types=types.split(splitter);while(type=types.shift()){delete this._callbacks[type]}return this}function trigger(types){var type,callbacks,args,syncFlush,asyncFlush;if(!this._callbacks){return this}types=types.split(splitter);args=[].slice.call(arguments,1);while((type=types.shift())&&(callbacks=this._callbacks[type])){syncFlush=getFlush(callbacks.sync,this,[type].concat(args));asyncFlush=getFlush(callbacks.async,this,[type].concat(args));syncFlush()&&nextTick(asyncFlush)}return this}function getFlush(callbacks,context,args){return flush;function flush(){var cancelled;for(var i=0,len=callbacks.length;!cancelled&&i<len;i+=1){cancelled=callbacks[i].apply(context,args)===false}return!cancelled}}function getNextTick(){var nextTickFn;if(window.setImmediate){nextTickFn=function nextTickSetImmediate(fn){setImmediate(function(){fn()})}}else{nextTickFn=function nextTickSetTimeout(fn){setTimeout(function(){fn()},0)}}return nextTickFn}function bindContext(fn,context){return fn.bind?fn.bind(context):function(){fn.apply(context,[].slice.call(arguments,0))}}}();var highlight=function(doc){"use strict";var defaults={node:null,pattern:null,tagName:"strong",className:null,wordsOnly:false,caseSensitive:false};return function hightlight(o){var regex;o=_.mixin({},defaults,o);if(!o.node||!o.pattern){return}o.pattern=_.isArray(o.pattern)?o.pattern:[o.pattern];regex=getRegex(o.pattern,o.caseSensitive,o.wordsOnly);traverse(o.node,hightlightTextNode);function hightlightTextNode(textNode){var match,patternNode,wrapperNode;if(match=regex.exec(textNode.data)){wrapperNode=doc.createElement(o.tagName);o.className&&(wrapperNode.className=o.className);patternNode=textNode.splitText(match.index);patternNode.splitText(match[0].length);wrapperNode.appendChild(patternNode.cloneNode(true));textNode.parentNode.replaceChild(wrapperNode,patternNode)}return!!match}function traverse(el,hightlightTextNode){var childNode,TEXT_NODE_TYPE=3;for(var i=0;i<el.childNodes.length;i++){childNode=el.childNodes[i];if(childNode.nodeType===TEXT_NODE_TYPE){i+=hightlightTextNode(childNode)?1:0}else{traverse(childNode,hightlightTextNode)}}}};function getRegex(patterns,caseSensitive,wordsOnly){var escapedPatterns=[],regexStr;for(var i=0,len=patterns.length;i<len;i++){escapedPatterns.push(_.escapeRegExChars(patterns[i]))}regexStr=wordsOnly?"\\b("+escapedPatterns.join("|")+")\\b":"("+escapedPatterns.join("|")+")";return caseSensitive?new RegExp(regexStr):new RegExp(regexStr,"i")}}(window.document);var Input=function(){"use strict";var specialKeyCodeMap;specialKeyCodeMap={9:"tab",27:"esc",37:"left",39:"right",13:"enter",38:"up",40:"down"};function Input(o){var that=this,onBlur,onFocus,onKeydown,onInput;o=o||{};if(!o.input){$.error("input is missing")}onBlur=_.bind(this._onBlur,this);onFocus=_.bind(this._onFocus,this);onKeydown=_.bind(this._onKeydown,this);onInput=_.bind(this._onInput,this);this.$hint=$(o.hint);this.$input=$(o.input).on("blur.tt",onBlur).on("focus.tt",onFocus).on("keydown.tt",onKeydown);if(this.$hint.length===0){this.setHint=this.getHint=this.clearHint=this.clearHintIfInvalid=_.noop}if(!_.isMsie()){this.$input.on("input.tt",onInput)}else{this.$input.on("keydown.tt keypress.tt cut.tt paste.tt",function($e){if(specialKeyCodeMap[$e.which||$e.keyCode]){return}_.defer(_.bind(that._onInput,that,$e))})}this.query=this.$input.val();this.$overflowHelper=buildOverflowHelper(this.$input)}Input.normalizeQuery=function(str){return(str||"").replace(/^\s*/g,"").replace(/\s{2,}/g," ")};_.mixin(Input.prototype,EventEmitter,{_onBlur:function onBlur(){this.resetInputValue();this.trigger("blurred")},_onFocus:function onFocus(){this.trigger("focused")},_onKeydown:function onKeydown($e){var keyName=specialKeyCodeMap[$e.which||$e.keyCode];this._managePreventDefault(keyName,$e);if(keyName&&this._shouldTrigger(keyName,$e)){this.trigger(keyName+"Keyed",$e)}},_onInput:function onInput(){this._checkInputValue()},_managePreventDefault:function managePreventDefault(keyName,$e){var preventDefault,hintValue,inputValue;switch(keyName){case"tab":hintValue=this.getHint();inputValue=this.getInputValue();preventDefault=hintValue&&hintValue!==inputValue&&!withModifier($e);break;case"up":case"down":preventDefault=!withModifier($e);break;default:preventDefault=false}preventDefault&&$e.preventDefault()},_shouldTrigger:function shouldTrigger(keyName,$e){var trigger;switch(keyName){case"tab":trigger=!withModifier($e);break;default:trigger=true}return trigger},_checkInputValue:function checkInputValue(){var inputValue,areEquivalent,hasDifferentWhitespace;inputValue=this.getInputValue();areEquivalent=areQueriesEquivalent(inputValue,this.query);hasDifferentWhitespace=areEquivalent?this.query.length!==inputValue.length:false;this.query=inputValue;if(!areEquivalent){this.trigger("queryChanged",this.query)}else if(hasDifferentWhitespace){this.trigger("whitespaceChanged",this.query)}},focus:function focus(){this.$input.focus()},blur:function blur(){this.$input.blur()},getQuery:function getQuery(){return this.query},setQuery:function setQuery(query){this.query=query},getInputValue:function getInputValue(){return this.$input.val()},setInputValue:function setInputValue(value,silent){this.$input.val(value);silent?this.clearHint():this._checkInputValue()},resetInputValue:function resetInputValue(){this.setInputValue(this.query,true)},getHint:function getHint(){return this.$hint.val()},setHint:function setHint(value){this.$hint.val(value)},clearHint:function clearHint(){this.setHint("")},clearHintIfInvalid:function clearHintIfInvalid(){var val,hint,valIsPrefixOfHint,isValid;val=this.getInputValue();hint=this.getHint();valIsPrefixOfHint=val!==hint&&hint.indexOf(val)===0;isValid=val!==""&&valIsPrefixOfHint&&!this.hasOverflow();!isValid&&this.clearHint()},getLanguageDirection:function getLanguageDirection(){return(this.$input.css("direction")||"ltr").toLowerCase()},hasOverflow:function hasOverflow(){var constraint=this.$input.width()-2;this.$overflowHelper.text(this.getInputValue());return this.$overflowHelper.width()>=constraint},isCursorAtEnd:function(){var valueLength,selectionStart,range;valueLength=this.$input.val().length;selectionStart=this.$input[0].selectionStart;if(_.isNumber(selectionStart)){return selectionStart===valueLength}else if(document.selection){range=document.selection.createRange();range.moveStart("character",-valueLength);return valueLength===range.text.length}return true},destroy:function destroy(){this.$hint.off(".tt");this.$input.off(".tt");this.$hint=this.$input=this.$overflowHelper=null}});return Input;function buildOverflowHelper($input){return $('<pre aria-hidden="true"></pre>').css({position:"absolute",visibility:"hidden",whiteSpace:"pre",fontFamily:$input.css("font-family"),fontSize:$input.css("font-size"),fontStyle:$input.css("font-style"),fontVariant:$input.css("font-variant"),fontWeight:$input.css("font-weight"),wordSpacing:$input.css("word-spacing"),letterSpacing:$input.css("letter-spacing"),textIndent:$input.css("text-indent"),textRendering:$input.css("text-rendering"),textTransform:$input.css("text-transform")}).insertAfter($input)}function areQueriesEquivalent(a,b){return Input.normalizeQuery(a)===Input.normalizeQuery(b)}function withModifier($e){return $e.altKey||$e.ctrlKey||$e.metaKey||$e.shiftKey}}();var Dataset=function(){"use strict";var datasetKey="ttDataset",valueKey="ttValue",datumKey="ttDatum";function Dataset(o){o=o||{};o.templates=o.templates||{};if(!o.source){$.error("missing source")}if(o.name&&!isValidName(o.name)){$.error("invalid dataset name: "+o.name)}this.query=null;this.highlight=!!o.highlight;this.name=o.name||_.getUniqueId();this.source=o.source;this.displayFn=getDisplayFn(o.display||o.displayKey);this.templates=getTemplates(o.templates,this.displayFn);this.$el=$(html.dataset.replace("%CLASS%",this.name))}Dataset.extractDatasetName=function extractDatasetName(el){return $(el).data(datasetKey)};Dataset.extractValue=function extractDatum(el){return $(el).data(valueKey)};Dataset.extractDatum=function extractDatum(el){return $(el).data(datumKey)};_.mixin(Dataset.prototype,EventEmitter,{_render:function render(query,suggestions){if(!this.$el){return}var that=this,hasSuggestions;this.$el.empty();hasSuggestions=suggestions&&suggestions.length;if(!hasSuggestions&&this.templates.empty){this.$el.html(getEmptyHtml()).prepend(that.templates.header?getHeaderHtml():null).append(that.templates.footer?getFooterHtml():null)}else if(hasSuggestions){this.$el.html(getSuggestionsHtml()).prepend(that.templates.header?getHeaderHtml():null).append(that.templates.footer?getFooterHtml():null)}this.trigger("rendered");function getEmptyHtml(){return that.templates.empty({query:query,isEmpty:true})}function getSuggestionsHtml(){var $suggestions,nodes;$suggestions=$(html.suggestions).css(css.suggestions);nodes=_.map(suggestions,getSuggestionNode);$suggestions.append.apply($suggestions,nodes);that.highlight&&highlight({className:"tt-highlight",node:$suggestions[0],pattern:query});return $suggestions;function getSuggestionNode(suggestion){var $el;$el=$(html.suggestion).append(that.templates.suggestion(suggestion)).data(datasetKey,that.name).data(valueKey,that.displayFn(suggestion)).data(datumKey,suggestion);$el.children().each(function(){$(this).css(css.suggestionChild)});return $el}}function getHeaderHtml(){return that.templates.header({query:query,isEmpty:!hasSuggestions})}function getFooterHtml(){return that.templates.footer({query:query,isEmpty:!hasSuggestions})}},getRoot:function getRoot(){return this.$el},update:function update(query){var that=this;this.query=query;this.canceled=false;this.source(query,render);function render(suggestions){if(!that.canceled&&query===that.query){that._render(query,suggestions)}}},cancel:function cancel(){this.canceled=true},clear:function clear(){this.cancel();this.$el.empty();this.trigger("rendered")},isEmpty:function isEmpty(){return this.$el.is(":empty")},destroy:function destroy(){this.$el=null}});return Dataset;function getDisplayFn(display){display=display||"value";return _.isFunction(display)?display:displayFn;function displayFn(obj){return obj[display]}}function getTemplates(templates,displayFn){return{empty:templates.empty&&_.templatify(templates.empty),header:templates.header&&_.templatify(templates.header),footer:templates.footer&&_.templatify(templates.footer),suggestion:templates.suggestion||suggestionTemplate};function suggestionTemplate(context){return"<p>"+displayFn(context)+"</p>"}}function isValidName(str){return/^[_a-zA-Z0-9-]+$/.test(str)}}();var Dropdown=function(){"use strict";function Dropdown(o){var that=this,onSuggestionClick,onSuggestionMouseEnter,onSuggestionMouseLeave;o=o||{};if(!o.menu){$.error("menu is required")}this.isOpen=false;this.isEmpty=true;this.datasets=_.map(o.datasets,initializeDataset);onSuggestionClick=_.bind(this._onSuggestionClick,this);onSuggestionMouseEnter=_.bind(this._onSuggestionMouseEnter,this);onSuggestionMouseLeave=_.bind(this._onSuggestionMouseLeave,this);this.$menu=$(o.menu).on("click.tt",".tt-suggestion",onSuggestionClick).on("mouseenter.tt",".tt-suggestion",onSuggestionMouseEnter).on("mouseleave.tt",".tt-suggestion",onSuggestionMouseLeave);_.each(this.datasets,function(dataset){that.$menu.append(dataset.getRoot());dataset.onSync("rendered",that._onRendered,that)})}_.mixin(Dropdown.prototype,EventEmitter,{_onSuggestionClick:function onSuggestionClick($e){this.trigger("suggestionClicked",$($e.currentTarget))},_onSuggestionMouseEnter:function onSuggestionMouseEnter($e){this._removeCursor();this._setCursor($($e.currentTarget),true)},_onSuggestionMouseLeave:function onSuggestionMouseLeave(){this._removeCursor()},_onRendered:function onRendered(){this.isEmpty=_.every(this.datasets,isDatasetEmpty);this.isEmpty?this._hide():this.isOpen&&this._show();this.trigger("datasetRendered");function isDatasetEmpty(dataset){return dataset.isEmpty()}},_hide:function(){this.$menu.hide()},_show:function(){this.$menu.css("display","block")},_getSuggestions:function getSuggestions(){return this.$menu.find(".tt-suggestion")},_getCursor:function getCursor(){return this.$menu.find(".tt-cursor").first()},_setCursor:function setCursor($el,silent){$el.first().addClass("tt-cursor");!silent&&this.trigger("cursorMoved")},_removeCursor:function removeCursor(){this._getCursor().removeClass("tt-cursor")},_moveCursor:function moveCursor(increment){var $suggestions,$oldCursor,newCursorIndex,$newCursor;if(!this.isOpen){return}$oldCursor=this._getCursor();$suggestions=this._getSuggestions();this._removeCursor();newCursorIndex=$suggestions.index($oldCursor)+increment;newCursorIndex=(newCursorIndex+1)%($suggestions.length+1)-1;if(newCursorIndex===-1){this.trigger("cursorRemoved");return}else if(newCursorIndex<-1){newCursorIndex=$suggestions.length-1}this._setCursor($newCursor=$suggestions.eq(newCursorIndex));this._ensureVisible($newCursor)},_ensureVisible:function ensureVisible($el){var elTop,elBottom,menuScrollTop,menuHeight;elTop=$el.position().top;elBottom=elTop+$el.outerHeight(true);menuScrollTop=this.$menu.scrollTop();menuHeight=this.$menu.height()+parseInt(this.$menu.css("paddingTop"),10)+parseInt(this.$menu.css("paddingBottom"),10);if(elTop<0){this.$menu.scrollTop(menuScrollTop+elTop)}else if(menuHeight<elBottom){this.$menu.scrollTop(menuScrollTop+(elBottom-menuHeight))}},close:function close(){if(this.isOpen){this.isOpen=false;this._removeCursor();this._hide();this.trigger("closed")}},open:function open(){if(!this.isOpen){this.isOpen=true;!this.isEmpty&&this._show();this.trigger("opened")}},setLanguageDirection:function setLanguageDirection(dir){this.$menu.css(dir==="ltr"?css.ltr:css.rtl)},moveCursorUp:function moveCursorUp(){this._moveCursor(-1)},moveCursorDown:function moveCursorDown(){this._moveCursor(+1)},getDatumForSuggestion:function getDatumForSuggestion($el){var datum=null;if($el.length){datum={raw:Dataset.extractDatum($el),value:Dataset.extractValue($el),datasetName:Dataset.extractDatasetName($el)}}return datum},getDatumForCursor:function getDatumForCursor(){return this.getDatumForSuggestion(this._getCursor().first())},getDatumForTopSuggestion:function getDatumForTopSuggestion(){return this.getDatumForSuggestion(this._getSuggestions().first())},update:function update(query){_.each(this.datasets,updateDataset);function updateDataset(dataset){dataset.update(query)}},empty:function empty(){_.each(this.datasets,clearDataset);this.isEmpty=true;function clearDataset(dataset){dataset.clear()}},isVisible:function isVisible(){return this.isOpen&&!this.isEmpty},destroy:function destroy(){this.$menu.off(".tt");this.$menu=null;_.each(this.datasets,destroyDataset);function destroyDataset(dataset){dataset.destroy()}}});return Dropdown;function initializeDataset(oDataset){return new Dataset(oDataset)}}();var Typeahead=function(){"use strict";var attrsKey="ttAttrs";function Typeahead(o){var $menu,$input,$hint;o=o||{};if(!o.input){$.error("missing input")}this.isActivated=false;this.autoselect=!!o.autoselect;this.minLength=_.isNumber(o.minLength)?o.minLength:1;this.$node=buildDom(o.input,o.withHint);$menu=this.$node.find(".tt-dropdown-menu");$input=this.$node.find(".tt-input");$hint=this.$node.find(".tt-hint");$input.on("blur.tt",function($e){var active,isActive,hasActive;active=document.activeElement;isActive=$menu.is(active);hasActive=$menu.has(active).length>0;if(_.isMsie()&&(isActive||hasActive)){$e.preventDefault();$e.stopImmediatePropagation();_.defer(function(){$input.focus()})}});$menu.on("mousedown.tt",function($e){$e.preventDefault()});this.eventBus=o.eventBus||new EventBus({el:$input});this.dropdown=new Dropdown({menu:$menu,datasets:o.datasets}).onSync("suggestionClicked",this._onSuggestionClicked,this).onSync("cursorMoved",this._onCursorMoved,this).onSync("cursorRemoved",this._onCursorRemoved,this).onSync("opened",this._onOpened,this).onSync("closed",this._onClosed,this).onAsync("datasetRendered",this._onDatasetRendered,this);this.input=new Input({input:$input,hint:$hint}).onSync("focused",this._onFocused,this).onSync("blurred",this._onBlurred,this).onSync("enterKeyed",this._onEnterKeyed,this).onSync("tabKeyed",this._onTabKeyed,this).onSync("escKeyed",this._onEscKeyed,this).onSync("upKeyed",this._onUpKeyed,this).onSync("downKeyed",this._onDownKeyed,this).onSync("leftKeyed",this._onLeftKeyed,this).onSync("rightKeyed",this._onRightKeyed,this).onSync("queryChanged",this._onQueryChanged,this).onSync("whitespaceChanged",this._onWhitespaceChanged,this);this._setLanguageDirection()}_.mixin(Typeahead.prototype,{_onSuggestionClicked:function onSuggestionClicked(type,$el){var datum;if(datum=this.dropdown.getDatumForSuggestion($el)){this._select(datum)}},_onCursorMoved:function onCursorMoved(){var datum=this.dropdown.getDatumForCursor();this.input.setInputValue(datum.value,true);this.eventBus.trigger("cursorchanged",datum.raw,datum.datasetName)},_onCursorRemoved:function onCursorRemoved(){this.input.resetInputValue();this._updateHint()},_onDatasetRendered:function onDatasetRendered(){this._updateHint()},_onOpened:function onOpened(){this._updateHint();this.eventBus.trigger("opened")},_onClosed:function onClosed(){this.input.clearHint();this.eventBus.trigger("closed")},_onFocused:function onFocused(){this.isActivated=true;this.dropdown.open()},_onBlurred:function onBlurred(){this.isActivated=false;this.dropdown.empty();this.dropdown.close()},_onEnterKeyed:function onEnterKeyed(type,$e){var cursorDatum,topSuggestionDatum;cursorDatum=this.dropdown.getDatumForCursor();topSuggestionDatum=this.dropdown.getDatumForTopSuggestion();if(cursorDatum){this._select(cursorDatum);$e.preventDefault()}else if(this.autoselect&&topSuggestionDatum){this._select(topSuggestionDatum);$e.preventDefault()}},_onTabKeyed:function onTabKeyed(type,$e){var datum;if(datum=this.dropdown.getDatumForCursor()){this._select(datum);$e.preventDefault()}else{this._autocomplete(true)}},_onEscKeyed:function onEscKeyed(){this.dropdown.close();this.input.resetInputValue()},_onUpKeyed:function onUpKeyed(){var query=this.input.getQuery();this.dropdown.isEmpty&&query.length>=this.minLength?this.dropdown.update(query):this.dropdown.moveCursorUp();this.dropdown.open()},_onDownKeyed:function onDownKeyed(){var query=this.input.getQuery();this.dropdown.isEmpty&&query.length>=this.minLength?this.dropdown.update(query):this.dropdown.moveCursorDown();this.dropdown.open()},_onLeftKeyed:function onLeftKeyed(){this.dir==="rtl"&&this._autocomplete()},_onRightKeyed:function onRightKeyed(){this.dir==="ltr"&&this._autocomplete()},_onQueryChanged:function onQueryChanged(e,query){this.input.clearHintIfInvalid();query.length>=this.minLength?this.dropdown.update(query):this.dropdown.empty();this.dropdown.open();this._setLanguageDirection()},_onWhitespaceChanged:function onWhitespaceChanged(){this._updateHint();this.dropdown.open()},_setLanguageDirection:function setLanguageDirection(){var dir;if(this.dir!==(dir=this.input.getLanguageDirection())){this.dir=dir;this.$node.css("direction",dir);this.dropdown.setLanguageDirection(dir)}},_updateHint:function updateHint(){var datum,val,query,escapedQuery,frontMatchRegEx,match;
 
 
 
21
 
22
- datum=this.dropdown.getDatumForTopSuggestion();if(datum&&this.dropdown.isVisible()&&!this.input.hasOverflow()){val=this.input.getInputValue();query=Input.normalizeQuery(val);escapedQuery=_.escapeRegExChars(query);frontMatchRegEx=new RegExp("^(?:"+escapedQuery+")(.+$)","i");match=frontMatchRegEx.exec(datum.value);match?this.input.setHint(val+match[1]):this.input.clearHint()}else{this.input.clearHint()}},_autocomplete:function autocomplete(laxCursor){var hint,query,isCursorAtEnd,datum;hint=this.input.getHint();query=this.input.getQuery();isCursorAtEnd=laxCursor||this.input.isCursorAtEnd();if(hint&&query!==hint&&isCursorAtEnd){datum=this.dropdown.getDatumForTopSuggestion();datum&&this.input.setInputValue(datum.value);this.eventBus.trigger("autocompleted",datum.raw,datum.datasetName)}},_select:function select(datum){this.input.setQuery(datum.value);this.input.setInputValue(datum.value,true);this._setLanguageDirection();this.eventBus.trigger("selected",datum.raw,datum.datasetName);this.dropdown.close();_.defer(_.bind(this.dropdown.empty,this.dropdown))},open:function open(){this.dropdown.open()},close:function close(){this.dropdown.close()},setVal:function setVal(val){val=_.toStr(val);if(this.isActivated){this.input.setInputValue(val)}else{this.input.setQuery(val);this.input.setInputValue(val,true)}this._setLanguageDirection()},getVal:function getVal(){return this.input.getQuery()},destroy:function destroy(){this.input.destroy();this.dropdown.destroy();destroyDomStructure(this.$node);this.$node=null}});return Typeahead;function buildDom(input,withHint){var $input,$wrapper,$dropdown,$hint;$input=$(input);$wrapper=$(html.wrapper).css(css.wrapper);$dropdown=$(html.dropdown).css(css.dropdown);$hint=$input.clone().css(css.hint).css(getBackgroundStyles($input));$hint.val("").removeData().addClass("tt-hint").removeAttr("id name placeholder required").prop("readonly",true).attr({autocomplete:"off",spellcheck:"false",tabindex:-1});$input.data(attrsKey,{dir:$input.attr("dir"),autocomplete:$input.attr("autocomplete"),spellcheck:$input.attr("spellcheck"),style:$input.attr("style")});$input.addClass("tt-input").attr({autocomplete:"off",spellcheck:false}).css(withHint?css.input:css.inputWithNoHint);try{!$input.attr("dir")&&$input.attr("dir","auto")}catch(e){}return $input.wrap($wrapper).parent().prepend(withHint?$hint:null).append($dropdown)}function getBackgroundStyles($el){return{backgroundAttachment:$el.css("background-attachment"),backgroundClip:$el.css("background-clip"),backgroundColor:$el.css("background-color"),backgroundImage:$el.css("background-image"),backgroundOrigin:$el.css("background-origin"),backgroundPosition:$el.css("background-position"),backgroundRepeat:$el.css("background-repeat"),backgroundSize:$el.css("background-size")}}function destroyDomStructure($node){var $input=$node.find(".tt-input");_.each($input.data(attrsKey),function(val,key){_.isUndefined(val)?$input.removeAttr(key):$input.attr(key,val)});$input.detach().removeData(attrsKey).removeClass("tt-input").insertAfter($node);$node.remove()}}();(function(){"use strict";var old,typeaheadKey,methods;old=$.fn.typeahead;typeaheadKey="ttTypeahead";methods={initialize:function initialize(o,datasets){datasets=_.isArray(datasets)?datasets:[].slice.call(arguments,1);o=o||{};return this.each(attach);function attach(){var $input=$(this),eventBus,typeahead;_.each(datasets,function(d){d.highlight=!!o.highlight});typeahead=new Typeahead({input:$input,eventBus:eventBus=new EventBus({el:$input}),withHint:_.isUndefined(o.hint)?true:!!o.hint,minLength:o.minLength,autoselect:o.autoselect,datasets:datasets});$input.data(typeaheadKey,typeahead)}},open:function open(){return this.each(openTypeahead);function openTypeahead(){var $input=$(this),typeahead;if(typeahead=$input.data(typeaheadKey)){typeahead.open()}}},close:function close(){return this.each(closeTypeahead);function closeTypeahead(){var $input=$(this),typeahead;if(typeahead=$input.data(typeaheadKey)){typeahead.close()}}},val:function val(newVal){return!arguments.length?getVal(this.first()):this.each(setVal);function setVal(){var $input=$(this),typeahead;if(typeahead=$input.data(typeaheadKey)){typeahead.setVal(newVal)}}function getVal($input){var typeahead,query;if(typeahead=$input.data(typeaheadKey)){query=typeahead.getVal()}return query}},destroy:function destroy(){return this.each(unattach);function unattach(){var $input=$(this),typeahead;if(typeahead=$input.data(typeaheadKey)){typeahead.destroy();$input.removeData(typeaheadKey)}}}};$.fn.typeahead=function(method){var tts;if(methods[method]&&method!=="initialize"){tts=this.filter(function(){return!!$(this).data(typeaheadKey)});return methods[method].apply(tts,[].slice.call(arguments,1))}else{return methods.initialize.apply(this,arguments)}};$.fn.typeahead.noConflict=function noConflict(){$.fn.typeahead=old;return this}})()})(window.jQuery)},{}]},{},[1])(1)});
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ (function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.algoliaBundle = f()}})(function(){var define,module,exports;return (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
2
+ module.exports = {
3
+ $: require('jquery'),
4
+ Hogan: require('hogan.js'),
5
+ algoliasearch: require('algoliasearch'),
6
+ algoliasearchHelper: require('algoliasearch-helper')
7
+ };
8
 
9
+ require('jquery-ui/slider');
10
+ require('jquery-ui/sortable');
11
+ require('jquery-ui/draggable');
12
+ require('jquery-ui/mouse');
13
 
14
+ // Some jQuery plugins are not commonJS compatible and thus
15
+ // we cannot easily tell them to use our own jQuery instead of the global jQuery
16
+ // To solve this, we do a little trick.
17
+ var oldJQuery = window.jQuery;
18
+ window.jQuery = module.exports.$;
19
+ require('jquery-ui-touch-punch');
20
+ require('typeahead.js');
21
+ window.jQuery = oldJQuery;
22
 
23
+ },{"algoliasearch":213,"algoliasearch-helper":2,"hogan.js":228,"jquery":237,"jquery-ui-touch-punch":230,"jquery-ui/draggable":232,"jquery-ui/mouse":233,"jquery-ui/slider":234,"jquery-ui/sortable":235,"typeahead.js":238}],2:[function(require,module,exports){
24
+ 'use strict';
25
 
26
+ var AlgoliaSearchHelper = require('./src/algoliasearch.helper');
 
 
27
 
28
+ var SearchParameters = require('./src/SearchParameters');
29
+ var SearchResults = require('./src/SearchResults');
30
 
31
+ /**
32
+ * The algoliasearchHelper module contains everything needed to use the Algoliasearch
33
+ * Helper. It is a also a function that instanciate the helper.
34
+ * To use the helper, you also need the Algolia JS client v3.
35
+ * @example
36
+ * //using the UMD build
37
+ * var client = algoliasearch('latency', '6be0576ff61c053d5f9a3225e2a90f76');
38
+ * var helper = algoliasearchHelper(client, 'bestbuy', {
39
+ * facets: ['shipping'],
40
+ * disjunctiveFacets: ['category']
41
+ * });
42
+ * helper.on('result', function(result) {
43
+ * console.log(result);
44
+ * });
45
+ * helper.toggleRefine('Movies & TV Shows')
46
+ * .toggleRefine('Free shipping')
47
+ * .search();
48
+ * @module algoliasearchHelper
49
+ * @param {AlgoliaSearch} client an AlgoliaSearch client
50
+ * @param {string} index the index name to query
51
+ * @param {SearchParameters|object} opts an object defining the initial config of the search. It doesn't have to be a {SearchParameters}, just an object containing the properties you need from it.
52
+ * @return {AlgoliaSearchHelper}
53
+ */
54
+ function algoliasearchHelper(client, index, opts) {
55
+ return new AlgoliaSearchHelper(client, index, opts);
56
+ }
57
 
58
+ /**
59
+ * The version currently used
60
+ * @member module:algoliasearchHelper.version
61
+ * @type {number}
62
+ */
63
+ algoliasearchHelper.version = '2.1.2';
64
 
65
+ /**
66
+ * Constructor for the Helper.
67
+ * @member module:algoliasearchHelper.AlgoliaSearchHelper
68
+ * @type {AlgoliaSearchHelper}
69
+ */
70
+ algoliasearchHelper.AlgoliaSearchHelper = AlgoliaSearchHelper;
71
+
72
+ /**
73
+ * Constructor for the object containing all the parameters of the search.
74
+ * @member module:algoliasearchHelper.SearchParameters
75
+ * @type {SearchParameters}
76
+ */
77
+ algoliasearchHelper.SearchParameters = SearchParameters;
78
+
79
+ /**
80
+ * Constructor for the object containing the results of the search.
81
+ * @member module:algoliasearchHelper.SearchResults
82
+ * @type {SearchResults}
83
+ */
84
+ algoliasearchHelper.SearchResults = SearchResults;
85
+
86
+ module.exports = algoliasearchHelper;
87
+
88
+ },{"./src/SearchParameters":152,"./src/SearchResults":154,"./src/algoliasearch.helper":155}],3:[function(require,module,exports){
89
+ /**
90
+ * Creates an array with all falsey values removed. The values `false`, `null`,
91
+ * `0`, `""`, `undefined`, and `NaN` are falsey.
92
+ *
93
+ * @static
94
+ * @memberOf _
95
+ * @category Array
96
+ * @param {Array} array The array to compact.
97
+ * @returns {Array} Returns the new array of filtered values.
98
+ * @example
99
+ *
100
+ * _.compact([0, 1, false, 2, '', 3]);
101
+ * // => [1, 2, 3]
102
+ */
103
+ function compact(array) {
104
+ var index = -1,
105
+ length = array ? array.length : 0,
106
+ resIndex = -1,
107
+ result = [];
108
+
109
+ while (++index < length) {
110
+ var value = array[index];
111
+ if (value) {
112
+ result[++resIndex] = value;
113
+ }
114
+ }
115
+ return result;
116
+ }
117
+
118
+ module.exports = compact;
119
+
120
+ },{}],4:[function(require,module,exports){
121
+ var createFindIndex = require('../internal/createFindIndex');
122
+
123
+ /**
124
+ * This method is like `_.find` except that it returns the index of the first
125
+ * element `predicate` returns truthy for instead of the element itself.
126
+ *
127
+ * If a property name is provided for `predicate` the created `_.property`
128
+ * style callback returns the property value of the given element.
129
+ *
130
+ * If a value is also provided for `thisArg` the created `_.matchesProperty`
131
+ * style callback returns `true` for elements that have a matching property
132
+ * value, else `false`.
133
+ *
134
+ * If an object is provided for `predicate` the created `_.matches` style
135
+ * callback returns `true` for elements that have the properties of the given
136
+ * object, else `false`.
137
+ *
138
+ * @static
139
+ * @memberOf _
140
+ * @category Array
141
+ * @param {Array} array The array to search.
142
+ * @param {Function|Object|string} [predicate=_.identity] The function invoked
143
+ * per iteration.
144
+ * @param {*} [thisArg] The `this` binding of `predicate`.
145
+ * @returns {number} Returns the index of the found element, else `-1`.
146
+ * @example
147
+ *
148
+ * var users = [
149
+ * { 'user': 'barney', 'active': false },
150
+ * { 'user': 'fred', 'active': false },
151
+ * { 'user': 'pebbles', 'active': true }
152
+ * ];
153
+ *
154
+ * _.findIndex(users, function(chr) {
155
+ * return chr.user == 'barney';
156
+ * });
157
+ * // => 0
158
+ *
159
+ * // using the `_.matches` callback shorthand
160
+ * _.findIndex(users, { 'user': 'fred', 'active': false });
161
+ * // => 1
162
+ *
163
+ * // using the `_.matchesProperty` callback shorthand
164
+ * _.findIndex(users, 'active', false);
165
+ * // => 0
166
+ *
167
+ * // using the `_.property` callback shorthand
168
+ * _.findIndex(users, 'active');
169
+ * // => 2
170
+ */
171
+ var findIndex = createFindIndex();
172
+
173
+ module.exports = findIndex;
174
+
175
+ },{"../internal/createFindIndex":87}],5:[function(require,module,exports){
176
+ var baseIndexOf = require('../internal/baseIndexOf'),
177
+ binaryIndex = require('../internal/binaryIndex');
178
+
179
+ /* Native method references for those with the same name as other `lodash` methods. */
180
+ var nativeMax = Math.max;
181
+
182
+ /**
183
+ * Gets the index at which the first occurrence of `value` is found in `array`
184
+ * using [`SameValueZero`](http://ecma-international.org/ecma-262/6.0/#sec-samevaluezero)
185
+ * for equality comparisons. If `fromIndex` is negative, it is used as the offset
186
+ * from the end of `array`. If `array` is sorted providing `true` for `fromIndex`
187
+ * performs a faster binary search.
188
+ *
189
+ * @static
190
+ * @memberOf _
191
+ * @category Array
192
+ * @param {Array} array The array to search.
193
+ * @param {*} value The value to search for.
194
+ * @param {boolean|number} [fromIndex=0] The index to search from or `true`
195
+ * to perform a binary search on a sorted array.
196
+ * @returns {number} Returns the index of the matched value, else `-1`.
197
+ * @example
198
+ *
199
+ * _.indexOf([1, 2, 1, 2], 2);
200
+ * // => 1
201
+ *
202
+ * // using `fromIndex`
203
+ * _.indexOf([1, 2, 1, 2], 2, 2);
204
+ * // => 3
205
+ *
206
+ * // performing a binary search
207
+ * _.indexOf([1, 1, 2, 2], 2, true);
208
+ * // => 2
209
+ */
210
+ function indexOf(array, value, fromIndex) {
211
+ var length = array ? array.length : 0;
212
+ if (!length) {
213
+ return -1;
214
+ }
215
+ if (typeof fromIndex == 'number') {
216
+ fromIndex = fromIndex < 0 ? nativeMax(length + fromIndex, 0) : fromIndex;
217
+ } else if (fromIndex) {
218
+ var index = binaryIndex(array, value);
219
+ if (index < length &&
220
+ (value === value ? (value === array[index]) : (array[index] !== array[index]))) {
221
+ return index;
222
+ }
223
+ return -1;
224
+ }
225
+ return baseIndexOf(array, value, fromIndex || 0);
226
+ }
227
+
228
+ module.exports = indexOf;
229
+
230
+ },{"../internal/baseIndexOf":49,"../internal/binaryIndex":69}],6:[function(require,module,exports){
231
+ var baseIndexOf = require('../internal/baseIndexOf'),
232
+ cacheIndexOf = require('../internal/cacheIndexOf'),
233
+ createCache = require('../internal/createCache'),
234
+ isArrayLike = require('../internal/isArrayLike'),
235
+ restParam = require('../function/restParam');
236
+
237
+ /**
238
+ * Creates an array of unique values that are included in all of the provided
239
+ * arrays using [`SameValueZero`](http://ecma-international.org/ecma-262/6.0/#sec-samevaluezero)
240
+ * for equality comparisons.
241
+ *
242
+ * @static
243
+ * @memberOf _
244
+ * @category Array
245
+ * @param {...Array} [arrays] The arrays to inspect.
246
+ * @returns {Array} Returns the new array of shared values.
247
+ * @example
248
+ * _.intersection([1, 2], [4, 2], [2, 1]);
249
+ * // => [2]
250
+ */
251
+ var intersection = restParam(function(arrays) {
252
+ var othLength = arrays.length,
253
+ othIndex = othLength,
254
+ caches = Array(length),
255
+ indexOf = baseIndexOf,
256
+ isCommon = true,
257
+ result = [];
258
+
259
+ while (othIndex--) {
260
+ var value = arrays[othIndex] = isArrayLike(value = arrays[othIndex]) ? value : [];
261
+ caches[othIndex] = (isCommon && value.length >= 120) ? createCache(othIndex && value) : null;
262
+ }
263
+ var array = arrays[0],
264
+ index = -1,
265
+ length = array ? array.length : 0,
266
+ seen = caches[0];
267
+
268
+ outer:
269
+ while (++index < length) {
270
+ value = array[index];
271
+ if ((seen ? cacheIndexOf(seen, value) : indexOf(result, value, 0)) < 0) {
272
+ var othIndex = othLength;
273
+ while (--othIndex) {
274
+ var cache = caches[othIndex];
275
+ if ((cache ? cacheIndexOf(cache, value) : indexOf(arrays[othIndex], value, 0)) < 0) {
276
+ continue outer;
277
+ }
278
+ }
279
+ if (seen) {
280
+ seen.push(value);
281
+ }
282
+ result.push(value);
283
+ }
284
+ }
285
+ return result;
286
+ });
287
+
288
+ module.exports = intersection;
289
+
290
+ },{"../function/restParam":20,"../internal/baseIndexOf":49,"../internal/cacheIndexOf":72,"../internal/createCache":83,"../internal/isArrayLike":102}],7:[function(require,module,exports){
291
+ /**
292
+ * Gets the last element of `array`.
293
+ *
294
+ * @static
295
+ * @memberOf _
296
+ * @category Array
297
+ * @param {Array} array The array to query.
298
+ * @returns {*} Returns the last element of `array`.
299
+ * @example
300
+ *
301
+ * _.last([1, 2, 3]);
302
+ * // => 3
303
+ */
304
+ function last(array) {
305
+ var length = array ? array.length : 0;
306
+ return length ? array[length - 1] : undefined;
307
+ }
308
+
309
+ module.exports = last;
310
+
311
+ },{}],8:[function(require,module,exports){
312
+ var LazyWrapper = require('../internal/LazyWrapper'),
313
+ LodashWrapper = require('../internal/LodashWrapper'),
314
+ baseLodash = require('../internal/baseLodash'),
315
+ isArray = require('../lang/isArray'),
316
+ isObjectLike = require('../internal/isObjectLike'),
317
+ wrapperClone = require('../internal/wrapperClone');
318
+
319
+ /** Used for native method references. */
320
+ var objectProto = Object.prototype;
321
+
322
+ /** Used to check objects for own properties. */
323
+ var hasOwnProperty = objectProto.hasOwnProperty;
324
+
325
+ /**
326
+ * Creates a `lodash` object which wraps `value` to enable implicit chaining.
327
+ * Methods that operate on and return arrays, collections, and functions can
328
+ * be chained together. Methods that retrieve a single value or may return a
329
+ * primitive value will automatically end the chain returning the unwrapped
330
+ * value. Explicit chaining may be enabled using `_.chain`. The execution of
331
+ * chained methods is lazy, that is, execution is deferred until `_#value`
332
+ * is implicitly or explicitly called.
333
+ *
334
+ * Lazy evaluation allows several methods to support shortcut fusion. Shortcut
335
+ * fusion is an optimization strategy which merge iteratee calls; this can help
336
+ * to avoid the creation of intermediate data structures and greatly reduce the
337
+ * number of iteratee executions.
338
+ *
339
+ * Chaining is supported in custom builds as long as the `_#value` method is
340
+ * directly or indirectly included in the build.
341
+ *
342
+ * In addition to lodash methods, wrappers have `Array` and `String` methods.
343
+ *
344
+ * The wrapper `Array` methods are:
345
+ * `concat`, `join`, `pop`, `push`, `reverse`, `shift`, `slice`, `sort`,
346
+ * `splice`, and `unshift`
347
+ *
348
+ * The wrapper `String` methods are:
349
+ * `replace` and `split`
350
+ *
351
+ * The wrapper methods that support shortcut fusion are:
352
+ * `compact`, `drop`, `dropRight`, `dropRightWhile`, `dropWhile`, `filter`,
353
+ * `first`, `initial`, `last`, `map`, `pluck`, `reject`, `rest`, `reverse`,
354
+ * `slice`, `take`, `takeRight`, `takeRightWhile`, `takeWhile`, `toArray`,
355
+ * and `where`
356
+ *
357
+ * The chainable wrapper methods are:
358
+ * `after`, `ary`, `assign`, `at`, `before`, `bind`, `bindAll`, `bindKey`,
359
+ * `callback`, `chain`, `chunk`, `commit`, `compact`, `concat`, `constant`,
360
+ * `countBy`, `create`, `curry`, `debounce`, `defaults`, `defaultsDeep`,
361
+ * `defer`, `delay`, `difference`, `drop`, `dropRight`, `dropRightWhile`,
362
+ * `dropWhile`, `fill`, `filter`, `flatten`, `flattenDeep`, `flow`, `flowRight`,
363
+ * `forEach`, `forEachRight`, `forIn`, `forInRight`, `forOwn`, `forOwnRight`,
364
+ * `functions`, `groupBy`, `indexBy`, `initial`, `intersection`, `invert`,
365
+ * `invoke`, `keys`, `keysIn`, `map`, `mapKeys`, `mapValues`, `matches`,
366
+ * `matchesProperty`, `memoize`, `merge`, `method`, `methodOf`, `mixin`,
367
+ * `modArgs`, `negate`, `omit`, `once`, `pairs`, `partial`, `partialRight`,
368
+ * `partition`, `pick`, `plant`, `pluck`, `property`, `propertyOf`, `pull`,
369
+ * `pullAt`, `push`, `range`, `rearg`, `reject`, `remove`, `rest`, `restParam`,
370
+ * `reverse`, `set`, `shuffle`, `slice`, `sort`, `sortBy`, `sortByAll`,
371
+ * `sortByOrder`, `splice`, `spread`, `take`, `takeRight`, `takeRightWhile`,
372
+ * `takeWhile`, `tap`, `throttle`, `thru`, `times`, `toArray`, `toPlainObject`,
373
+ * `transform`, `union`, `uniq`, `unshift`, `unzip`, `unzipWith`, `values`,
374
+ * `valuesIn`, `where`, `without`, `wrap`, `xor`, `zip`, `zipObject`, `zipWith`
375
+ *
376
+ * The wrapper methods that are **not** chainable by default are:
377
+ * `add`, `attempt`, `camelCase`, `capitalize`, `ceil`, `clone`, `cloneDeep`,
378
+ * `deburr`, `endsWith`, `escape`, `escapeRegExp`, `every`, `find`, `findIndex`,
379
+ * `findKey`, `findLast`, `findLastIndex`, `findLastKey`, `findWhere`, `first`,
380
+ * `floor`, `get`, `gt`, `gte`, `has`, `identity`, `includes`, `indexOf`,
381
+ * `inRange`, `isArguments`, `isArray`, `isBoolean`, `isDate`, `isElement`,
382
+ * `isEmpty`, `isEqual`, `isError`, `isFinite` `isFunction`, `isMatch`,
383
+ * `isNative`, `isNaN`, `isNull`, `isNumber`, `isObject`, `isPlainObject`,
384
+ * `isRegExp`, `isString`, `isUndefined`, `isTypedArray`, `join`, `kebabCase`,
385
+ * `last`, `lastIndexOf`, `lt`, `lte`, `max`, `min`, `noConflict`, `noop`,
386
+ * `now`, `pad`, `padLeft`, `padRight`, `parseInt`, `pop`, `random`, `reduce`,
387
+ * `reduceRight`, `repeat`, `result`, `round`, `runInContext`, `shift`, `size`,
388
+ * `snakeCase`, `some`, `sortedIndex`, `sortedLastIndex`, `startCase`,
389
+ * `startsWith`, `sum`, `template`, `trim`, `trimLeft`, `trimRight`, `trunc`,
390
+ * `unescape`, `uniqueId`, `value`, and `words`
391
+ *
392
+ * The wrapper method `sample` will return a wrapped value when `n` is provided,
393
+ * otherwise an unwrapped value is returned.
394
+ *
395
+ * @name _
396
+ * @constructor
397
+ * @category Chain
398
+ * @param {*} value The value to wrap in a `lodash` instance.
399
+ * @returns {Object} Returns the new `lodash` wrapper instance.
400
+ * @example
401
+ *
402
+ * var wrapped = _([1, 2, 3]);
403
+ *
404
+ * // returns an unwrapped value
405
+ * wrapped.reduce(function(total, n) {
406
+ * return total + n;
407
+ * });
408
+ * // => 6
409
+ *
410
+ * // returns a wrapped value
411
+ * var squares = wrapped.map(function(n) {
412
+ * return n * n;
413
+ * });
414
+ *
415
+ * _.isArray(squares);
416
+ * // => false
417
+ *
418
+ * _.isArray(squares.value());
419
+ * // => true
420
+ */
421
+ function lodash(value) {
422
+ if (isObjectLike(value) && !isArray(value) && !(value instanceof LazyWrapper)) {
423
+ if (value instanceof LodashWrapper) {
424
+ return value;
425
+ }
426
+ if (hasOwnProperty.call(value, '__chain__') && hasOwnProperty.call(value, '__wrapped__')) {
427
+ return wrapperClone(value);
428
+ }
429
+ }
430
+ return new LodashWrapper(value);
431
+ }
432
+
433
+ // Ensure wrappers are instances of `baseLodash`.
434
+ lodash.prototype = baseLodash.prototype;
435
+
436
+ module.exports = lodash;
437
+
438
+ },{"../internal/LazyWrapper":21,"../internal/LodashWrapper":22,"../internal/baseLodash":53,"../internal/isObjectLike":108,"../internal/wrapperClone":125,"../lang/isArray":127}],9:[function(require,module,exports){
439
+ var arrayFilter = require('../internal/arrayFilter'),
440
+ baseCallback = require('../internal/baseCallback'),
441
+ baseFilter = require('../internal/baseFilter'),
442
+ isArray = require('../lang/isArray');
443
+
444
+ /**
445
+ * Iterates over elements of `collection`, returning an array of all elements
446
+ * `predicate` returns truthy for. The predicate is bound to `thisArg` and
447
+ * invoked with three arguments: (value, index|key, collection).
448
+ *
449
+ * If a property name is provided for `predicate` the created `_.property`
450
+ * style callback returns the property value of the given element.
451
+ *
452
+ * If a value is also provided for `thisArg` the created `_.matchesProperty`
453
+ * style callback returns `true` for elements that have a matching property
454
+ * value, else `false`.
455
+ *
456
+ * If an object is provided for `predicate` the created `_.matches` style
457
+ * callback returns `true` for elements that have the properties of the given
458
+ * object, else `false`.
459
+ *
460
+ * @static
461
+ * @memberOf _
462
+ * @alias select
463
+ * @category Collection
464
+ * @param {Array|Object|string} collection The collection to iterate over.
465
+ * @param {Function|Object|string} [predicate=_.identity] The function invoked
466
+ * per iteration.
467
+ * @param {*} [thisArg] The `this` binding of `predicate`.
468
+ * @returns {Array} Returns the new filtered array.
469
+ * @example
470
+ *
471
+ * _.filter([4, 5, 6], function(n) {
472
+ * return n % 2 == 0;
473
+ * });
474
+ * // => [4, 6]
475
+ *
476
+ * var users = [
477
+ * { 'user': 'barney', 'age': 36, 'active': true },
478
+ * { 'user': 'fred', 'age': 40, 'active': false }
479
+ * ];
480
+ *
481
+ * // using the `_.matches` callback shorthand
482
+ * _.pluck(_.filter(users, { 'age': 36, 'active': true }), 'user');
483
+ * // => ['barney']
484
+ *
485
+ * // using the `_.matchesProperty` callback shorthand
486
+ * _.pluck(_.filter(users, 'active', false), 'user');
487
+ * // => ['fred']
488
+ *
489
+ * // using the `_.property` callback shorthand
490
+ * _.pluck(_.filter(users, 'active'), 'user');
491
+ * // => ['barney']
492
+ */
493
+ function filter(collection, predicate, thisArg) {
494
+ var func = isArray(collection) ? arrayFilter : baseFilter;
495
+ predicate = baseCallback(predicate, thisArg, 3);
496
+ return func(collection, predicate);
497
+ }
498
+
499
+ module.exports = filter;
500
+
501
+ },{"../internal/arrayFilter":26,"../internal/baseCallback":35,"../internal/baseFilter":41,"../lang/isArray":127}],10:[function(require,module,exports){
502
+ var baseEach = require('../internal/baseEach'),
503
+ createFind = require('../internal/createFind');
504
+
505
+ /**
506
+ * Iterates over elements of `collection`, returning the first element
507
+ * `predicate` returns truthy for. The predicate is bound to `thisArg` and
508
+ * invoked with three arguments: (value, index|key, collection).
509
+ *
510
+ * If a property name is provided for `predicate` the created `_.property`
511
+ * style callback returns the property value of the given element.
512
+ *
513
+ * If a value is also provided for `thisArg` the created `_.matchesProperty`
514
+ * style callback returns `true` for elements that have a matching property
515
+ * value, else `false`.
516
+ *
517
+ * If an object is provided for `predicate` the created `_.matches` style
518
+ * callback returns `true` for elements that have the properties of the given
519
+ * object, else `false`.
520
+ *
521
+ * @static
522
+ * @memberOf _
523
+ * @alias detect
524
+ * @category Collection
525
+ * @param {Array|Object|string} collection The collection to search.
526
+ * @param {Function|Object|string} [predicate=_.identity] The function invoked
527
+ * per iteration.
528
+ * @param {*} [thisArg] The `this` binding of `predicate`.
529
+ * @returns {*} Returns the matched element, else `undefined`.
530
+ * @example
531
+ *
532
+ * var users = [
533
+ * { 'user': 'barney', 'age': 36, 'active': true },
534
+ * { 'user': 'fred', 'age': 40, 'active': false },
535
+ * { 'user': 'pebbles', 'age': 1, 'active': true }
536
+ * ];
537
+ *
538
+ * _.result(_.find(users, function(chr) {
539
+ * return chr.age < 40;
540
+ * }), 'user');
541
+ * // => 'barney'
542
+ *
543
+ * // using the `_.matches` callback shorthand
544
+ * _.result(_.find(users, { 'age': 1, 'active': true }), 'user');
545
+ * // => 'pebbles'
546
+ *
547
+ * // using the `_.matchesProperty` callback shorthand
548
+ * _.result(_.find(users, 'active', false), 'user');
549
+ * // => 'fred'
550
+ *
551
+ * // using the `_.property` callback shorthand
552
+ * _.result(_.find(users, 'active'), 'user');
553
+ * // => 'barney'
554
+ */
555
+ var find = createFind(baseEach);
556
+
557
+ module.exports = find;
558
+
559
+ },{"../internal/baseEach":40,"../internal/createFind":86}],11:[function(require,module,exports){
560
+ var arrayEach = require('../internal/arrayEach'),
561
+ baseEach = require('../internal/baseEach'),
562
+ createForEach = require('../internal/createForEach');
563
+
564
+ /**
565
+ * Iterates over elements of `collection` invoking `iteratee` for each element.
566
+ * The `iteratee` is bound to `thisArg` and invoked with three arguments:
567
+ * (value, index|key, collection). Iteratee functions may exit iteration early
568
+ * by explicitly returning `false`.
569
+ *
570
+ * **Note:** As with other "Collections" methods, objects with a "length" property
571
+ * are iterated like arrays. To avoid this behavior `_.forIn` or `_.forOwn`
572
+ * may be used for object iteration.
573
+ *
574
+ * @static
575
+ * @memberOf _
576
+ * @alias each
577
+ * @category Collection
578
+ * @param {Array|Object|string} collection The collection to iterate over.
579
+ * @param {Function} [iteratee=_.identity] The function invoked per iteration.
580
+ * @param {*} [thisArg] The `this` binding of `iteratee`.
581
+ * @returns {Array|Object|string} Returns `collection`.
582
+ * @example
583
+ *
584
+ * _([1, 2]).forEach(function(n) {
585
+ * console.log(n);
586
+ * }).value();
587
+ * // => logs each value from left to right and returns the array
588
+ *
589
+ * _.forEach({ 'a': 1, 'b': 2 }, function(n, key) {
590
+ * console.log(n, key);
591
+ * });
592
+ * // => logs each value-key pair and returns the object (iteration order is not guaranteed)
593
+ */
594
+ var forEach = createForEach(arrayEach, baseEach);
595
+
596
+ module.exports = forEach;
597
+
598
+ },{"../internal/arrayEach":25,"../internal/baseEach":40,"../internal/createForEach":88}],12:[function(require,module,exports){
599
+ var baseIndexOf = require('../internal/baseIndexOf'),
600
+ getLength = require('../internal/getLength'),
601
+ isArray = require('../lang/isArray'),
602
+ isIterateeCall = require('../internal/isIterateeCall'),
603
+ isLength = require('../internal/isLength'),
604
+ isString = require('../lang/isString'),
605
+ values = require('../object/values');
606
+
607
+ /* Native method references for those with the same name as other `lodash` methods. */
608
+ var nativeMax = Math.max;
609
+
610
+ /**
611
+ * Checks if `value` is in `collection` using
612
+ * [`SameValueZero`](http://ecma-international.org/ecma-262/6.0/#sec-samevaluezero)
613
+ * for equality comparisons. If `fromIndex` is negative, it is used as the offset
614
+ * from the end of `collection`.
615
+ *
616
+ * @static
617
+ * @memberOf _
618
+ * @alias contains, include
619
+ * @category Collection
620
+ * @param {Array|Object|string} collection The collection to search.
621
+ * @param {*} target The value to search for.
622
+ * @param {number} [fromIndex=0] The index to search from.
623
+ * @param- {Object} [guard] Enables use as a callback for functions like `_.reduce`.
624
+ * @returns {boolean} Returns `true` if a matching element is found, else `false`.
625
+ * @example
626
+ *
627
+ * _.includes([1, 2, 3], 1);
628
+ * // => true
629
+ *
630
+ * _.includes([1, 2, 3], 1, 2);
631
+ * // => false
632
+ *
633
+ * _.includes({ 'user': 'fred', 'age': 40 }, 'fred');
634
+ * // => true
635
+ *
636
+ * _.includes('pebbles', 'eb');
637
+ * // => true
638
+ */
639
+ function includes(collection, target, fromIndex, guard) {
640
+ var length = collection ? getLength(collection) : 0;
641
+ if (!isLength(length)) {
642
+ collection = values(collection);
643
+ length = collection.length;
644
+ }
645
+ if (typeof fromIndex != 'number' || (guard && isIterateeCall(target, fromIndex, guard))) {
646
+ fromIndex = 0;
647
+ } else {
648
+ fromIndex = fromIndex < 0 ? nativeMax(length + fromIndex, 0) : (fromIndex || 0);
649
+ }
650
+ return (typeof collection == 'string' || !isArray(collection) && isString(collection))
651
+ ? (fromIndex <= length && collection.indexOf(target, fromIndex) > -1)
652
+ : (!!length && baseIndexOf(collection, target, fromIndex) > -1);
653
+ }
654
+
655
+ module.exports = includes;
656
+
657
+ },{"../internal/baseIndexOf":49,"../internal/getLength":98,"../internal/isIterateeCall":104,"../internal/isLength":107,"../lang/isArray":127,"../lang/isString":133,"../object/values":146}],13:[function(require,module,exports){
658
+ var arrayMap = require('../internal/arrayMap'),
659
+ baseCallback = require('../internal/baseCallback'),
660
+ baseMap = require('../internal/baseMap'),
661
+ isArray = require('../lang/isArray');
662
+
663
+ /**
664
+ * Creates an array of values by running each element in `collection` through
665
+ * `iteratee`. The `iteratee` is bound to `thisArg` and invoked with three
666
+ * arguments: (value, index|key, collection).
667
+ *
668
+ * If a property name is provided for `iteratee` the created `_.property`
669
+ * style callback returns the property value of the given element.
670
+ *
671
+ * If a value is also provided for `thisArg` the created `_.matchesProperty`
672
+ * style callback returns `true` for elements that have a matching property
673
+ * value, else `false`.
674
+ *
675
+ * If an object is provided for `iteratee` the created `_.matches` style
676
+ * callback returns `true` for elements that have the properties of the given
677
+ * object, else `false`.
678
+ *
679
+ * Many lodash methods are guarded to work as iteratees for methods like
680
+ * `_.every`, `_.filter`, `_.map`, `_.mapValues`, `_.reject`, and `_.some`.
681
+ *
682
+ * The guarded methods are:
683
+ * `ary`, `callback`, `chunk`, `clone`, `create`, `curry`, `curryRight`,
684
+ * `drop`, `dropRight`, `every`, `fill`, `flatten`, `invert`, `max`, `min`,
685
+ * `parseInt`, `slice`, `sortBy`, `take`, `takeRight`, `template`, `trim`,
686
+ * `trimLeft`, `trimRight`, `trunc`, `random`, `range`, `sample`, `some`,
687
+ * `sum`, `uniq`, and `words`
688
+ *
689
+ * @static
690
+ * @memberOf _
691
+ * @alias collect
692
+ * @category Collection
693
+ * @param {Array|Object|string} collection The collection to iterate over.
694
+ * @param {Function|Object|string} [iteratee=_.identity] The function invoked
695
+ * per iteration.
696
+ * @param {*} [thisArg] The `this` binding of `iteratee`.
697
+ * @returns {Array} Returns the new mapped array.
698
+ * @example
699
+ *
700
+ * function timesThree(n) {
701
+ * return n * 3;
702
+ * }
703
+ *
704
+ * _.map([1, 2], timesThree);
705
+ * // => [3, 6]
706
+ *
707
+ * _.map({ 'a': 1, 'b': 2 }, timesThree);
708
+ * // => [3, 6] (iteration order is not guaranteed)
709
+ *
710
+ * var users = [
711
+ * { 'user': 'barney' },
712
+ * { 'user': 'fred' }
713
+ * ];
714
+ *
715
+ * // using the `_.property` callback shorthand
716
+ * _.map(users, 'user');
717
+ * // => ['barney', 'fred']
718
+ */
719
+ function map(collection, iteratee, thisArg) {
720
+ var func = isArray(collection) ? arrayMap : baseMap;
721
+ iteratee = baseCallback(iteratee, thisArg, 3);
722
+ return func(collection, iteratee);
723
+ }
724
+
725
+ module.exports = map;
726
+
727
+ },{"../internal/arrayMap":27,"../internal/baseCallback":35,"../internal/baseMap":54,"../lang/isArray":127}],14:[function(require,module,exports){
728
+ var map = require('./map'),
729
+ property = require('../utility/property');
730
+
731
+ /**
732
+ * Gets the property value of `path` from all elements in `collection`.
733
+ *
734
+ * @static
735
+ * @memberOf _
736
+ * @category Collection
737
+ * @param {Array|Object|string} collection The collection to iterate over.
738
+ * @param {Array|string} path The path of the property to pluck.
739
+ * @returns {Array} Returns the property values.
740
+ * @example
741
+ *
742
+ * var users = [
743
+ * { 'user': 'barney', 'age': 36 },
744
+ * { 'user': 'fred', 'age': 40 }
745
+ * ];
746
+ *
747
+ * _.pluck(users, 'user');
748
+ * // => ['barney', 'fred']
749
+ *
750
+ * var userIndex = _.indexBy(users, 'user');
751
+ * _.pluck(userIndex, 'age');
752
+ * // => [36, 40] (iteration order is not guaranteed)
753
+ */
754
+ function pluck(collection, path) {
755
+ return map(collection, property(path));
756
+ }
757
+
758
+ module.exports = pluck;
759
+
760
+ },{"../utility/property":150,"./map":13}],15:[function(require,module,exports){
761
+ var arrayReduce = require('../internal/arrayReduce'),
762
+ baseEach = require('../internal/baseEach'),
763
+ createReduce = require('../internal/createReduce');
764
+
765
+ /**
766
+ * Reduces `collection` to a value which is the accumulated result of running
767
+ * each element in `collection` through `iteratee`, where each successive
768
+ * invocation is supplied the return value of the previous. If `accumulator`
769
+ * is not provided the first element of `collection` is used as the initial
770
+ * value. The `iteratee` is bound to `thisArg` and invoked with four arguments:
771
+ * (accumulator, value, index|key, collection).
772
+ *
773
+ * Many lodash methods are guarded to work as iteratees for methods like
774
+ * `_.reduce`, `_.reduceRight`, and `_.transform`.
775
+ *
776
+ * The guarded methods are:
777
+ * `assign`, `defaults`, `defaultsDeep`, `includes`, `merge`, `sortByAll`,
778
+ * and `sortByOrder`
779
+ *
780
+ * @static
781
+ * @memberOf _
782
+ * @alias foldl, inject
783
+ * @category Collection
784
+ * @param {Array|Object|string} collection The collection to iterate over.
785
+ * @param {Function} [iteratee=_.identity] The function invoked per iteration.
786
+ * @param {*} [accumulator] The initial value.
787
+ * @param {*} [thisArg] The `this` binding of `iteratee`.
788
+ * @returns {*} Returns the accumulated value.
789
+ * @example
790
+ *
791
+ * _.reduce([1, 2], function(total, n) {
792
+ * return total + n;
793
+ * });
794
+ * // => 3
795
+ *
796
+ * _.reduce({ 'a': 1, 'b': 2 }, function(result, n, key) {
797
+ * result[key] = n * 3;
798
+ * return result;
799
+ * }, {});
800
+ * // => { 'a': 3, 'b': 6 } (iteration order is not guaranteed)
801
+ */
802
+ var reduce = createReduce(arrayReduce, baseEach);
803
+
804
+ module.exports = reduce;
805
+
806
+ },{"../internal/arrayReduce":29,"../internal/baseEach":40,"../internal/createReduce":91}],16:[function(require,module,exports){
807
+ var baseSortByOrder = require('../internal/baseSortByOrder'),
808
+ isArray = require('../lang/isArray'),
809
+ isIterateeCall = require('../internal/isIterateeCall');
810
+
811
+ /**
812
+ * This method is like `_.sortByAll` except that it allows specifying the
813
+ * sort orders of the iteratees to sort by. If `orders` is unspecified, all
814
+ * values are sorted in ascending order. Otherwise, a value is sorted in
815
+ * ascending order if its corresponding order is "asc", and descending if "desc".
816
+ *
817
+ * If a property name is provided for an iteratee the created `_.property`
818
+ * style callback returns the property value of the given element.
819
+ *
820
+ * If an object is provided for an iteratee the created `_.matches` style
821
+ * callback returns `true` for elements that have the properties of the given
822
+ * object, else `false`.
823
+ *
824
+ * @static
825
+ * @memberOf _
826
+ * @category Collection
827
+ * @param {Array|Object|string} collection The collection to iterate over.
828
+ * @param {Function[]|Object[]|string[]} iteratees The iteratees to sort by.
829
+ * @param {boolean[]} [orders] The sort orders of `iteratees`.
830
+ * @param- {Object} [guard] Enables use as a callback for functions like `_.reduce`.
831
+ * @returns {Array} Returns the new sorted array.
832
+ * @example
833
+ *
834
+ * var users = [
835
+ * { 'user': 'fred', 'age': 48 },
836
+ * { 'user': 'barney', 'age': 34 },
837
+ * { 'user': 'fred', 'age': 42 },
838
+ * { 'user': 'barney', 'age': 36 }
839
+ * ];
840
+ *
841
+ * // sort by `user` in ascending order and by `age` in descending order
842
+ * _.map(_.sortByOrder(users, ['user', 'age'], ['asc', 'desc']), _.values);
843
+ * // => [['barney', 36], ['barney', 34], ['fred', 48], ['fred', 42]]
844
+ */
845
+ function sortByOrder(collection, iteratees, orders, guard) {
846
+ if (collection == null) {
847
+ return [];
848
+ }
849
+ if (guard && isIterateeCall(iteratees, orders, guard)) {
850
+ orders = undefined;
851
+ }
852
+ if (!isArray(iteratees)) {
853
+ iteratees = iteratees == null ? [] : [iteratees];
854
+ }
855
+ if (!isArray(orders)) {
856
+ orders = orders == null ? [] : [orders];
857
+ }
858
+ return baseSortByOrder(collection, iteratees, orders);
859
+ }
860
+
861
+ module.exports = sortByOrder;
862
+
863
+ },{"../internal/baseSortByOrder":65,"../internal/isIterateeCall":104,"../lang/isArray":127}],17:[function(require,module,exports){
864
+ module.exports = require('../math/sum');
865
+
866
+ },{"../math/sum":137}],18:[function(require,module,exports){
867
+ var getNative = require('../internal/getNative');
868
+
869
+ /* Native method references for those with the same name as other `lodash` methods. */
870
+ var nativeNow = getNative(Date, 'now');
871
+
872
+ /**
873
+ * Gets the number of milliseconds that have elapsed since the Unix epoch
874
+ * (1 January 1970 00:00:00 UTC).
875
+ *
876
+ * @static
877
+ * @memberOf _
878
+ * @category Date
879
+ * @example
880
+ *
881
+ * _.defer(function(stamp) {
882
+ * console.log(_.now() - stamp);
883
+ * }, _.now());
884
+ * // => logs the number of milliseconds it took for the deferred function to be invoked
885
+ */
886
+ var now = nativeNow || function() {
887
+ return new Date().getTime();
888
+ };
889
+
890
+ module.exports = now;
891
+
892
+ },{"../internal/getNative":100}],19:[function(require,module,exports){
893
+ var createWrapper = require('../internal/createWrapper'),
894
+ replaceHolders = require('../internal/replaceHolders'),
895
+ restParam = require('./restParam');
896
+
897
+ /** Used to compose bitmasks for wrapper metadata. */
898
+ var BIND_FLAG = 1,
899
+ PARTIAL_FLAG = 32;
900
+
901
+ /**
902
+ * Creates a function that invokes `func` with the `this` binding of `thisArg`
903
+ * and prepends any additional `_.bind` arguments to those provided to the
904
+ * bound function.
905
+ *
906
+ * The `_.bind.placeholder` value, which defaults to `_` in monolithic builds,
907
+ * may be used as a placeholder for partially applied arguments.
908
+ *
909
+ * **Note:** Unlike native `Function#bind` this method does not set the "length"
910
+ * property of bound functions.
911
+ *
912
+ * @static
913
+ * @memberOf _
914
+ * @category Function
915
+ * @param {Function} func The function to bind.
916
+ * @param {*} thisArg The `this` binding of `func`.
917
+ * @param {...*} [partials] The arguments to be partially applied.
918
+ * @returns {Function} Returns the new bound function.
919
+ * @example
920
+ *
921
+ * var greet = function(greeting, punctuation) {
922
+ * return greeting + ' ' + this.user + punctuation;
923
+ * };
924
+ *
925
+ * var object = { 'user': 'fred' };
926
+ *
927
+ * var bound = _.bind(greet, object, 'hi');
928
+ * bound('!');
929
+ * // => 'hi fred!'
930
+ *
931
+ * // using placeholders
932
+ * var bound = _.bind(greet, object, _, '!');
933
+ * bound('hi');
934
+ * // => 'hi fred!'
935
+ */
936
+ var bind = restParam(function(func, thisArg, partials) {
937
+ var bitmask = BIND_FLAG;
938
+ if (partials.length) {
939
+ var holders = replaceHolders(partials, bind.placeholder);
940
+ bitmask |= PARTIAL_FLAG;
941
+ }
942
+ return createWrapper(func, bitmask, thisArg, partials, holders);
943
+ });
944
+
945
+ // Assign default placeholders.
946
+ bind.placeholder = {};
947
+
948
+ module.exports = bind;
949
+
950
+ },{"../internal/createWrapper":92,"../internal/replaceHolders":117,"./restParam":20}],20:[function(require,module,exports){
951
+ /** Used as the `TypeError` message for "Functions" methods. */
952
+ var FUNC_ERROR_TEXT = 'Expected a function';
953
+
954
+ /* Native method references for those with the same name as other `lodash` methods. */
955
+ var nativeMax = Math.max;
956
+
957
+ /**
958
+ * Creates a function that invokes `func` with the `this` binding of the
959
+ * created function and arguments from `start` and beyond provided as an array.
960
+ *
961
+ * **Note:** This method is based on the [rest parameter](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/rest_parameters).
962
+ *
963
+ * @static
964
+ * @memberOf _
965
+ * @category Function
966
+ * @param {Function} func The function to apply a rest parameter to.
967
+ * @param {number} [start=func.length-1] The start position of the rest parameter.
968
+ * @returns {Function} Returns the new function.
969
+ * @example
970
+ *
971
+ * var say = _.restParam(function(what, names) {
972
+ * return what + ' ' + _.initial(names).join(', ') +
973
+ * (_.size(names) > 1 ? ', & ' : '') + _.last(names);
974
+ * });
975
+ *
976
+ * say('hello', 'fred', 'barney', 'pebbles');
977
+ * // => 'hello fred, barney, & pebbles'
978
+ */
979
+ function restParam(func, start) {
980
+ if (typeof func != 'function') {
981
+ throw new TypeError(FUNC_ERROR_TEXT);
982
+ }
983
+ start = nativeMax(start === undefined ? (func.length - 1) : (+start || 0), 0);
984
+ return function() {
985
+ var args = arguments,
986
+ index = -1,
987
+ length = nativeMax(args.length - start, 0),
988
+ rest = Array(length);
989
+
990
+ while (++index < length) {
991
+ rest[index] = args[start + index];
992
+ }
993
+ switch (start) {
994
+ case 0: return func.call(this, rest);
995
+ case 1: return func.call(this, args[0], rest);
996
+ case 2: return func.call(this, args[0], args[1], rest);
997
+ }
998
+ var otherArgs = Array(start + 1);
999
+ index = -1;
1000
+ while (++index < start) {
1001
+ otherArgs[index] = args[index];
1002
+ }
1003
+ otherArgs[start] = rest;
1004
+ return func.apply(this, otherArgs);
1005
+ };
1006
+ }
1007
+
1008
+ module.exports = restParam;
1009
+
1010
+ },{}],21:[function(require,module,exports){
1011
+ var baseCreate = require('./baseCreate'),
1012
+ baseLodash = require('./baseLodash');
1013
+
1014
+ /** Used as references for `-Infinity` and `Infinity`. */
1015
+ var POSITIVE_INFINITY = Number.POSITIVE_INFINITY;
1016
+
1017
+ /**
1018
+ * Creates a lazy wrapper object which wraps `value` to enable lazy evaluation.
1019
+ *
1020
+ * @private
1021
+ * @param {*} value The value to wrap.
1022
+ */
1023
+ function LazyWrapper(value) {
1024
+ this.__wrapped__ = value;
1025
+ this.__actions__ = [];
1026
+ this.__dir__ = 1;
1027
+ this.__filtered__ = false;
1028
+ this.__iteratees__ = [];
1029
+ this.__takeCount__ = POSITIVE_INFINITY;
1030
+ this.__views__ = [];
1031
+ }
1032
+
1033
+ LazyWrapper.prototype = baseCreate(baseLodash.prototype);
1034
+ LazyWrapper.prototype.constructor = LazyWrapper;
1035
+
1036
+ module.exports = LazyWrapper;
1037
+
1038
+ },{"./baseCreate":38,"./baseLodash":53}],22:[function(require,module,exports){
1039
+ var baseCreate = require('./baseCreate'),
1040
+ baseLodash = require('./baseLodash');
1041
+
1042
+ /**
1043
+ * The base constructor for creating `lodash` wrapper objects.
1044
+ *
1045
+ * @private
1046
+ * @param {*} value The value to wrap.
1047
+ * @param {boolean} [chainAll] Enable chaining for all wrapper methods.
1048
+ * @param {Array} [actions=[]] Actions to peform to resolve the unwrapped value.
1049
+ */
1050
+ function LodashWrapper(value, chainAll, actions) {
1051
+ this.__wrapped__ = value;
1052
+ this.__actions__ = actions || [];
1053
+ this.__chain__ = !!chainAll;
1054
+ }
1055
+
1056
+ LodashWrapper.prototype = baseCreate(baseLodash.prototype);
1057
+ LodashWrapper.prototype.constructor = LodashWrapper;
1058
+
1059
+ module.exports = LodashWrapper;
1060
+
1061
+ },{"./baseCreate":38,"./baseLodash":53}],23:[function(require,module,exports){
1062
+ (function (global){
1063
+ var cachePush = require('./cachePush'),
1064
+ getNative = require('./getNative');
1065
+
1066
+ /** Native method references. */
1067
+ var Set = getNative(global, 'Set');
1068
+
1069
+ /* Native method references for those with the same name as other `lodash` methods. */
1070
+ var nativeCreate = getNative(Object, 'create');
1071
+
1072
+ /**
1073
+ *
1074
+ * Creates a cache object to store unique values.
1075
+ *
1076
+ * @private
1077
+ * @param {Array} [values] The values to cache.
1078
+ */
1079
+ function SetCache(values) {
1080
+ var length = values ? values.length : 0;
1081
+
1082
+ this.data = { 'hash': nativeCreate(null), 'set': new Set };
1083
+ while (length--) {
1084
+ this.push(values[length]);
1085
+ }
1086
+ }
1087
+
1088
+ // Add functions to the `Set` cache.
1089
+ SetCache.prototype.push = cachePush;
1090
+
1091
+ module.exports = SetCache;
1092
+
1093
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
1094
+ },{"./cachePush":73,"./getNative":100}],24:[function(require,module,exports){
1095
+ /**
1096
+ * Copies the values of `source` to `array`.
1097
+ *
1098
+ * @private
1099
+ * @param {Array} source The array to copy values from.
1100
+ * @param {Array} [array=[]] The array to copy values to.
1101
+ * @returns {Array} Returns `array`.
1102
+ */
1103
+ function arrayCopy(source, array) {
1104
+ var index = -1,
1105
+ length = source.length;
1106
+
1107
+ array || (array = Array(length));
1108
+ while (++index < length) {
1109
+ array[index] = source[index];
1110
+ }
1111
+ return array;
1112
+ }
1113
+
1114
+ module.exports = arrayCopy;
1115
+
1116
+ },{}],25:[function(require,module,exports){
1117
+ /**
1118
+ * A specialized version of `_.forEach` for arrays without support for callback
1119
+ * shorthands and `this` binding.
1120
+ *
1121
+ * @private
1122
+ * @param {Array} array The array to iterate over.
1123
+ * @param {Function} iteratee The function invoked per iteration.
1124
+ * @returns {Array} Returns `array`.
1125
+ */
1126
+ function arrayEach(array, iteratee) {
1127
+ var index = -1,
1128
+ length = array.length;
1129
+
1130
+ while (++index < length) {
1131
+ if (iteratee(array[index], index, array) === false) {
1132
+ break;
1133
+ }
1134
+ }
1135
+ return array;
1136
+ }
1137
+
1138
+ module.exports = arrayEach;
1139
+
1140
+ },{}],26:[function(require,module,exports){
1141
+ /**
1142
+ * A specialized version of `_.filter` for arrays without support for callback
1143
+ * shorthands and `this` binding.
1144
+ *
1145
+ * @private
1146
+ * @param {Array} array The array to iterate over.
1147
+ * @param {Function} predicate The function invoked per iteration.
1148
+ * @returns {Array} Returns the new filtered array.
1149
+ */
1150
+ function arrayFilter(array, predicate) {
1151
+ var index = -1,
1152
+ length = array.length,
1153
+ resIndex = -1,
1154
+ result = [];
1155
+
1156
+ while (++index < length) {
1157
+ var value = array[index];
1158
+ if (predicate(value, index, array)) {
1159
+ result[++resIndex] = value;
1160
+ }
1161
+ }
1162
+ return result;
1163
+ }
1164
+
1165
+ module.exports = arrayFilter;
1166
+
1167
+ },{}],27:[function(require,module,exports){
1168
+ /**
1169
+ * A specialized version of `_.map` for arrays without support for callback
1170
+ * shorthands and `this` binding.
1171
+ *
1172
+ * @private
1173
+ * @param {Array} array The array to iterate over.
1174
+ * @param {Function} iteratee The function invoked per iteration.
1175
+ * @returns {Array} Returns the new mapped array.
1176
+ */
1177
+ function arrayMap(array, iteratee) {
1178
+ var index = -1,
1179
+ length = array.length,
1180
+ result = Array(length);
1181
+
1182
+ while (++index < length) {
1183
+ result[index] = iteratee(array[index], index, array);
1184
+ }
1185
+ return result;
1186
+ }
1187
+
1188
+ module.exports = arrayMap;
1189
+
1190
+ },{}],28:[function(require,module,exports){
1191
+ /**
1192
+ * Appends the elements of `values` to `array`.
1193
+ *
1194
+ * @private
1195
+ * @param {Array} array The array to modify.
1196
+ * @param {Array} values The values to append.
1197
+ * @returns {Array} Returns `array`.
1198
+ */
1199
+ function arrayPush(array, values) {
1200
+ var index = -1,
1201
+ length = values.length,
1202
+ offset = array.length;
1203
+
1204
+ while (++index < length) {
1205
+ array[offset + index] = values[index];
1206
+ }
1207
+ return array;
1208
+ }
1209
+
1210
+ module.exports = arrayPush;
1211
+
1212
+ },{}],29:[function(require,module,exports){
1213
+ /**
1214
+ * A specialized version of `_.reduce` for arrays without support for callback
1215
+ * shorthands and `this` binding.
1216
+ *
1217
+ * @private
1218
+ * @param {Array} array The array to iterate over.
1219
+ * @param {Function} iteratee The function invoked per iteration.
1220
+ * @param {*} [accumulator] The initial value.
1221
+ * @param {boolean} [initFromArray] Specify using the first element of `array`
1222
+ * as the initial value.
1223
+ * @returns {*} Returns the accumulated value.
1224
+ */
1225
+ function arrayReduce(array, iteratee, accumulator, initFromArray) {
1226
+ var index = -1,
1227
+ length = array.length;
1228
+
1229
+ if (initFromArray && length) {
1230
+ accumulator = array[++index];
1231
+ }
1232
+ while (++index < length) {
1233
+ accumulator = iteratee(accumulator, array[index], index, array);
1234
+ }
1235
+ return accumulator;
1236
+ }
1237
+
1238
+ module.exports = arrayReduce;
1239
+
1240
+ },{}],30:[function(require,module,exports){
1241
+ /**
1242
+ * A specialized version of `_.some` for arrays without support for callback
1243
+ * shorthands and `this` binding.
1244
+ *
1245
+ * @private
1246
+ * @param {Array} array The array to iterate over.
1247
+ * @param {Function} predicate The function invoked per iteration.
1248
+ * @returns {boolean} Returns `true` if any element passes the predicate check,
1249
+ * else `false`.
1250
+ */
1251
+ function arraySome(array, predicate) {
1252
+ var index = -1,
1253
+ length = array.length;
1254
+
1255
+ while (++index < length) {
1256
+ if (predicate(array[index], index, array)) {
1257
+ return true;
1258
+ }
1259
+ }
1260
+ return false;
1261
+ }
1262
+
1263
+ module.exports = arraySome;
1264
+
1265
+ },{}],31:[function(require,module,exports){
1266
+ /**
1267
+ * A specialized version of `_.sum` for arrays without support for callback
1268
+ * shorthands and `this` binding..
1269
+ *
1270
+ * @private
1271
+ * @param {Array} array The array to iterate over.
1272
+ * @param {Function} iteratee The function invoked per iteration.
1273
+ * @returns {number} Returns the sum.
1274
+ */
1275
+ function arraySum(array, iteratee) {
1276
+ var length = array.length,
1277
+ result = 0;
1278
+
1279
+ while (length--) {
1280
+ result += +iteratee(array[length]) || 0;
1281
+ }
1282
+ return result;
1283
+ }
1284
+
1285
+ module.exports = arraySum;
1286
+
1287
+ },{}],32:[function(require,module,exports){
1288
+ /**
1289
+ * Used by `_.defaults` to customize its `_.assign` use.
1290
+ *
1291
+ * @private
1292
+ * @param {*} objectValue The destination object property value.
1293
+ * @param {*} sourceValue The source object property value.
1294
+ * @returns {*} Returns the value to assign to the destination object.
1295
+ */
1296
+ function assignDefaults(objectValue, sourceValue) {
1297
+ return objectValue === undefined ? sourceValue : objectValue;
1298
+ }
1299
+
1300
+ module.exports = assignDefaults;
1301
+
1302
+ },{}],33:[function(require,module,exports){
1303
+ var keys = require('../object/keys');
1304
+
1305
+ /**
1306
+ * A specialized version of `_.assign` for customizing assigned values without
1307
+ * support for argument juggling, multiple sources, and `this` binding `customizer`
1308
+ * functions.
1309
+ *
1310
+ * @private
1311
+ * @param {Object} object The destination object.
1312
+ * @param {Object} source The source object.
1313
+ * @param {Function} customizer The function to customize assigned values.
1314
+ * @returns {Object} Returns `object`.
1315
+ */
1316
+ function assignWith(object, source, customizer) {
1317
+ var index = -1,
1318
+ props = keys(source),
1319
+ length = props.length;
1320
+
1321
+ while (++index < length) {
1322
+ var key = props[index],
1323
+ value = object[key],
1324
+ result = customizer(value, source[key], key, object, source);
1325
+
1326
+ if ((result === result ? (result !== value) : (value === value)) ||
1327
+ (value === undefined && !(key in object))) {
1328
+ object[key] = result;
1329
+ }
1330
+ }
1331
+ return object;
1332
+ }
1333
+
1334
+ module.exports = assignWith;
1335
+
1336
+ },{"../object/keys":140}],34:[function(require,module,exports){
1337
+ var baseCopy = require('./baseCopy'),
1338
+ keys = require('../object/keys');
1339
+
1340
+ /**
1341
+ * The base implementation of `_.assign` without support for argument juggling,
1342
+ * multiple sources, and `customizer` functions.
1343
+ *
1344
+ * @private
1345
+ * @param {Object} object The destination object.
1346
+ * @param {Object} source The source object.
1347
+ * @returns {Object} Returns `object`.
1348
+ */
1349
+ function baseAssign(object, source) {
1350
+ return source == null
1351
+ ? object
1352
+ : baseCopy(source, keys(source), object);
1353
+ }
1354
+
1355
+ module.exports = baseAssign;
1356
+
1357
+ },{"../object/keys":140,"./baseCopy":37}],35:[function(require,module,exports){
1358
+ var baseMatches = require('./baseMatches'),
1359
+ baseMatchesProperty = require('./baseMatchesProperty'),
1360
+ bindCallback = require('./bindCallback'),
1361
+ identity = require('../utility/identity'),
1362
+ property = require('../utility/property');
1363
+
1364
+ /**
1365
+ * The base implementation of `_.callback` which supports specifying the
1366
+ * number of arguments to provide to `func`.
1367
+ *
1368
+ * @private
1369
+ * @param {*} [func=_.identity] The value to convert to a callback.
1370
+ * @param {*} [thisArg] The `this` binding of `func`.
1371
+ * @param {number} [argCount] The number of arguments to provide to `func`.
1372
+ * @returns {Function} Returns the callback.
1373
+ */
1374
+ function baseCallback(func, thisArg, argCount) {
1375
+ var type = typeof func;
1376
+ if (type == 'function') {
1377
+ return thisArg === undefined
1378
+ ? func
1379
+ : bindCallback(func, thisArg, argCount);
1380
+ }
1381
+ if (func == null) {
1382
+ return identity;
1383
+ }
1384
+ if (type == 'object') {
1385
+ return baseMatches(func);
1386
+ }
1387
+ return thisArg === undefined
1388
+ ? property(func)
1389
+ : baseMatchesProperty(func, thisArg);
1390
+ }
1391
+
1392
+ module.exports = baseCallback;
1393
+
1394
+ },{"../utility/identity":148,"../utility/property":150,"./baseMatches":55,"./baseMatchesProperty":56,"./bindCallback":71}],36:[function(require,module,exports){
1395
+ /**
1396
+ * The base implementation of `compareAscending` which compares values and
1397
+ * sorts them in ascending order without guaranteeing a stable sort.
1398
+ *
1399
+ * @private
1400
+ * @param {*} value The value to compare.
1401
+ * @param {*} other The other value to compare.
1402
+ * @returns {number} Returns the sort order indicator for `value`.
1403
+ */
1404
+ function baseCompareAscending(value, other) {
1405
+ if (value !== other) {
1406
+ var valIsNull = value === null,
1407
+ valIsUndef = value === undefined,
1408
+ valIsReflexive = value === value;
1409
+
1410
+ var othIsNull = other === null,
1411
+ othIsUndef = other === undefined,
1412
+ othIsReflexive = other === other;
1413
+
1414
+ if ((value > other && !othIsNull) || !valIsReflexive ||
1415
+ (valIsNull && !othIsUndef && othIsReflexive) ||
1416
+ (valIsUndef && othIsReflexive)) {
1417
+ return 1;
1418
+ }
1419
+ if ((value < other && !valIsNull) || !othIsReflexive ||
1420
+ (othIsNull && !valIsUndef && valIsReflexive) ||
1421
+ (othIsUndef && valIsReflexive)) {
1422
+ return -1;
1423
+ }
1424
+ }
1425
+ return 0;
1426
+ }
1427
+
1428
+ module.exports = baseCompareAscending;
1429
+
1430
+ },{}],37:[function(require,module,exports){
1431
+ /**
1432
+ * Copies properties of `source` to `object`.
1433
+ *
1434
+ * @private
1435
+ * @param {Object} source The object to copy properties from.
1436
+ * @param {Array} props The property names to copy.
1437
+ * @param {Object} [object={}] The object to copy properties to.
1438
+ * @returns {Object} Returns `object`.
1439
+ */
1440
+ function baseCopy(source, props, object) {
1441
+ object || (object = {});
1442
+
1443
+ var index = -1,
1444
+ length = props.length;
1445
+
1446
+ while (++index < length) {
1447
+ var key = props[index];
1448
+ object[key] = source[key];
1449
+ }
1450
+ return object;
1451
+ }
1452
+
1453
+ module.exports = baseCopy;
1454
+
1455
+ },{}],38:[function(require,module,exports){
1456
+ var isObject = require('../lang/isObject');
1457
+
1458
+ /**
1459
+ * The base implementation of `_.create` without support for assigning
1460
+ * properties to the created object.
1461
+ *
1462
+ * @private
1463
+ * @param {Object} prototype The object to inherit from.
1464
+ * @returns {Object} Returns the new object.
1465
+ */
1466
+ var baseCreate = (function() {
1467
+ function object() {}
1468
+ return function(prototype) {
1469
+ if (isObject(prototype)) {
1470
+ object.prototype = prototype;
1471
+ var result = new object;
1472
+ object.prototype = undefined;
1473
+ }
1474
+ return result || {};
1475
+ };
1476
+ }());
1477
+
1478
+ module.exports = baseCreate;
1479
+
1480
+ },{"../lang/isObject":131}],39:[function(require,module,exports){
1481
+ var baseIndexOf = require('./baseIndexOf'),
1482
+ cacheIndexOf = require('./cacheIndexOf'),
1483
+ createCache = require('./createCache');
1484
+
1485
+ /** Used as the size to enable large array optimizations. */
1486
+ var LARGE_ARRAY_SIZE = 200;
1487
+
1488
+ /**
1489
+ * The base implementation of `_.difference` which accepts a single array
1490
+ * of values to exclude.
1491
+ *
1492
+ * @private
1493
+ * @param {Array} array The array to inspect.
1494
+ * @param {Array} values The values to exclude.
1495
+ * @returns {Array} Returns the new array of filtered values.
1496
+ */
1497
+ function baseDifference(array, values) {
1498
+ var length = array ? array.length : 0,
1499
+ result = [];
1500
+
1501
+ if (!length) {
1502
+ return result;
1503
+ }
1504
+ var index = -1,
1505
+ indexOf = baseIndexOf,
1506
+ isCommon = true,
1507
+ cache = (isCommon && values.length >= LARGE_ARRAY_SIZE) ? createCache(values) : null,
1508
+ valuesLength = values.length;
1509
+
1510
+ if (cache) {
1511
+ indexOf = cacheIndexOf;
1512
+ isCommon = false;
1513
+ values = cache;
1514
+ }
1515
+ outer:
1516
+ while (++index < length) {
1517
+ var value = array[index];
1518
+
1519
+ if (isCommon && value === value) {
1520
+ var valuesIndex = valuesLength;
1521
+ while (valuesIndex--) {
1522
+ if (values[valuesIndex] === value) {
1523
+ continue outer;
1524
+ }
1525
+ }
1526
+ result.push(value);
1527
+ }
1528
+ else if (indexOf(values, value, 0) < 0) {
1529
+ result.push(value);
1530
+ }
1531
+ }
1532
+ return result;
1533
+ }
1534
+
1535
+ module.exports = baseDifference;
1536
+
1537
+ },{"./baseIndexOf":49,"./cacheIndexOf":72,"./createCache":83}],40:[function(require,module,exports){
1538
+ var baseForOwn = require('./baseForOwn'),
1539
+ createBaseEach = require('./createBaseEach');
1540
+
1541
+ /**
1542
+ * The base implementation of `_.forEach` without support for callback
1543
+ * shorthands and `this` binding.
1544
+ *
1545
+ * @private
1546
+ * @param {Array|Object|string} collection The collection to iterate over.
1547
+ * @param {Function} iteratee The function invoked per iteration.
1548
+ * @returns {Array|Object|string} Returns `collection`.
1549
+ */
1550
+ var baseEach = createBaseEach(baseForOwn);
1551
+
1552
+ module.exports = baseEach;
1553
+
1554
+ },{"./baseForOwn":47,"./createBaseEach":80}],41:[function(require,module,exports){
1555
+ var baseEach = require('./baseEach');
1556
+
1557
+ /**
1558
+ * The base implementation of `_.filter` without support for callback
1559
+ * shorthands and `this` binding.
1560
+ *
1561
+ * @private
1562
+ * @param {Array|Object|string} collection The collection to iterate over.
1563
+ * @param {Function} predicate The function invoked per iteration.
1564
+ * @returns {Array} Returns the new filtered array.
1565
+ */
1566
+ function baseFilter(collection, predicate) {
1567
+ var result = [];
1568
+ baseEach(collection, function(value, index, collection) {
1569
+ if (predicate(value, index, collection)) {
1570
+ result.push(value);
1571
+ }
1572
+ });
1573
+ return result;
1574
+ }
1575
+
1576
+ module.exports = baseFilter;
1577
+
1578
+ },{"./baseEach":40}],42:[function(require,module,exports){
1579
+ /**
1580
+ * The base implementation of `_.find`, `_.findLast`, `_.findKey`, and `_.findLastKey`,
1581
+ * without support for callback shorthands and `this` binding, which iterates
1582
+ * over `collection` using the provided `eachFunc`.
1583
+ *
1584
+ * @private
1585
+ * @param {Array|Object|string} collection The collection to search.
1586
+ * @param {Function} predicate The function invoked per iteration.
1587
+ * @param {Function} eachFunc The function to iterate over `collection`.
1588
+ * @param {boolean} [retKey] Specify returning the key of the found element
1589
+ * instead of the element itself.
1590
+ * @returns {*} Returns the found element or its key, else `undefined`.
1591
+ */
1592
+ function baseFind(collection, predicate, eachFunc, retKey) {
1593
+ var result;
1594
+ eachFunc(collection, function(value, key, collection) {
1595
+ if (predicate(value, key, collection)) {
1596
+ result = retKey ? key : value;
1597
+ return false;
1598
+ }
1599
+ });
1600
+ return result;
1601
+ }
1602
+
1603
+ module.exports = baseFind;
1604
+
1605
+ },{}],43:[function(require,module,exports){
1606
+ /**
1607
+ * The base implementation of `_.findIndex` and `_.findLastIndex` without
1608
+ * support for callback shorthands and `this` binding.
1609
+ *
1610
+ * @private
1611
+ * @param {Array} array The array to search.
1612
+ * @param {Function} predicate The function invoked per iteration.
1613
+ * @param {boolean} [fromRight] Specify iterating from right to left.
1614
+ * @returns {number} Returns the index of the matched value, else `-1`.
1615
+ */
1616
+ function baseFindIndex(array, predicate, fromRight) {
1617
+ var length = array.length,
1618
+ index = fromRight ? length : -1;
1619
+
1620
+ while ((fromRight ? index-- : ++index < length)) {
1621
+ if (predicate(array[index], index, array)) {
1622
+ return index;
1623
+ }
1624
+ }
1625
+ return -1;
1626
+ }
1627
+
1628
+ module.exports = baseFindIndex;
1629
+
1630
+ },{}],44:[function(require,module,exports){
1631
+ var arrayPush = require('./arrayPush'),
1632
+ isArguments = require('../lang/isArguments'),
1633
+ isArray = require('../lang/isArray'),
1634
+ isArrayLike = require('./isArrayLike'),
1635
+ isObjectLike = require('./isObjectLike');
1636
+
1637
+ /**
1638
+ * The base implementation of `_.flatten` with added support for restricting
1639
+ * flattening and specifying the start index.
1640
+ *
1641
+ * @private
1642
+ * @param {Array} array The array to flatten.
1643
+ * @param {boolean} [isDeep] Specify a deep flatten.
1644
+ * @param {boolean} [isStrict] Restrict flattening to arrays-like objects.
1645
+ * @param {Array} [result=[]] The initial result value.
1646
+ * @returns {Array} Returns the new flattened array.
1647
+ */
1648
+ function baseFlatten(array, isDeep, isStrict, result) {
1649
+ result || (result = []);
1650
+
1651
+ var index = -1,
1652
+ length = array.length;
1653
+
1654
+ while (++index < length) {
1655
+ var value = array[index];
1656
+ if (isObjectLike(value) && isArrayLike(value) &&
1657
+ (isStrict || isArray(value) || isArguments(value))) {
1658
+ if (isDeep) {
1659
+ // Recursively flatten arrays (susceptible to call stack limits).
1660
+ baseFlatten(value, isDeep, isStrict, result);
1661
+ } else {
1662
+ arrayPush(result, value);
1663
+ }
1664
+ } else if (!isStrict) {
1665
+ result[result.length] = value;
1666
+ }
1667
+ }
1668
+ return result;
1669
+ }
1670
+
1671
+ module.exports = baseFlatten;
1672
+
1673
+ },{"../lang/isArguments":126,"../lang/isArray":127,"./arrayPush":28,"./isArrayLike":102,"./isObjectLike":108}],45:[function(require,module,exports){
1674
+ var createBaseFor = require('./createBaseFor');
1675
+
1676
+ /**
1677
+ * The base implementation of `baseForIn` and `baseForOwn` which iterates
1678
+ * over `object` properties returned by `keysFunc` invoking `iteratee` for
1679
+ * each property. Iteratee functions may exit iteration early by explicitly
1680
+ * returning `false`.
1681
+ *
1682
+ * @private
1683
+ * @param {Object} object The object to iterate over.
1684
+ * @param {Function} iteratee The function invoked per iteration.
1685
+ * @param {Function} keysFunc The function to get the keys of `object`.
1686
+ * @returns {Object} Returns `object`.
1687
+ */
1688
+ var baseFor = createBaseFor();
1689
+
1690
+ module.exports = baseFor;
1691
+
1692
+ },{"./createBaseFor":81}],46:[function(require,module,exports){
1693
+ var baseFor = require('./baseFor'),
1694
+ keysIn = require('../object/keysIn');
1695
+
1696
+ /**
1697
+ * The base implementation of `_.forIn` without support for callback
1698
+ * shorthands and `this` binding.
1699
+ *
1700
+ * @private
1701
+ * @param {Object} object The object to iterate over.
1702
+ * @param {Function} iteratee The function invoked per iteration.
1703
+ * @returns {Object} Returns `object`.
1704
+ */
1705
+ function baseForIn(object, iteratee) {
1706
+ return baseFor(object, iteratee, keysIn);
1707
+ }
1708
+
1709
+ module.exports = baseForIn;
1710
+
1711
+ },{"../object/keysIn":141,"./baseFor":45}],47:[function(require,module,exports){
1712
+ var baseFor = require('./baseFor'),
1713
+ keys = require('../object/keys');
1714
+
1715
+ /**
1716
+ * The base implementation of `_.forOwn` without support for callback
1717
+ * shorthands and `this` binding.
1718
+ *
1719
+ * @private
1720
+ * @param {Object} object The object to iterate over.
1721
+ * @param {Function} iteratee The function invoked per iteration.
1722
+ * @returns {Object} Returns `object`.
1723
+ */
1724
+ function baseForOwn(object, iteratee) {
1725
+ return baseFor(object, iteratee, keys);
1726
+ }
1727
+
1728
+ module.exports = baseForOwn;
1729
+
1730
+ },{"../object/keys":140,"./baseFor":45}],48:[function(require,module,exports){
1731
+ var toObject = require('./toObject');
1732
+
1733
+ /**
1734
+ * The base implementation of `get` without support for string paths
1735
+ * and default values.
1736
+ *
1737
+ * @private
1738
+ * @param {Object} object The object to query.
1739
+ * @param {Array} path The path of the property to get.
1740
+ * @param {string} [pathKey] The key representation of path.
1741
+ * @returns {*} Returns the resolved value.
1742
+ */
1743
+ function baseGet(object, path, pathKey) {
1744
+ if (object == null) {
1745
+ return;
1746
+ }
1747
+ if (pathKey !== undefined && pathKey in toObject(object)) {
1748
+ path = [pathKey];
1749
+ }
1750
+ var index = 0,
1751
+ length = path.length;
1752
+
1753
+ while (object != null && index < length) {
1754
+ object = object[path[index++]];
1755
+ }
1756
+ return (index && index == length) ? object : undefined;
1757
+ }
1758
+
1759
+ module.exports = baseGet;
1760
+
1761
+ },{"./toObject":121}],49:[function(require,module,exports){
1762
+ var indexOfNaN = require('./indexOfNaN');
1763
+
1764
+ /**
1765
+ * The base implementation of `_.indexOf` without support for binary searches.
1766
+ *
1767
+ * @private
1768
+ * @param {Array} array The array to search.
1769
+ * @param {*} value The value to search for.
1770
+ * @param {number} fromIndex The index to search from.
1771
+ * @returns {number} Returns the index of the matched value, else `-1`.
1772
+ */
1773
+ function baseIndexOf(array, value, fromIndex) {
1774
+ if (value !== value) {
1775
+ return indexOfNaN(array, fromIndex);
1776
+ }
1777
+ var index = fromIndex - 1,
1778
+ length = array.length;
1779
+
1780
+ while (++index < length) {
1781
+ if (array[index] === value) {
1782
+ return index;
1783
+ }
1784
+ }
1785
+ return -1;
1786
+ }
1787
+
1788
+ module.exports = baseIndexOf;
1789
+
1790
+ },{"./indexOfNaN":101}],50:[function(require,module,exports){
1791
+ var baseIsEqualDeep = require('./baseIsEqualDeep'),
1792
+ isObject = require('../lang/isObject'),
1793
+ isObjectLike = require('./isObjectLike');
1794
+
1795
+ /**
1796
+ * The base implementation of `_.isEqual` without support for `this` binding
1797
+ * `customizer` functions.
1798
+ *
1799
+ * @private
1800
+ * @param {*} value The value to compare.
1801
+ * @param {*} other The other value to compare.
1802
+ * @param {Function} [customizer] The function to customize comparing values.
1803
+ * @param {boolean} [isLoose] Specify performing partial comparisons.
1804
+ * @param {Array} [stackA] Tracks traversed `value` objects.
1805
+ * @param {Array} [stackB] Tracks traversed `other` objects.
1806
+ * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
1807
+ */
1808
+ function baseIsEqual(value, other, customizer, isLoose, stackA, stackB) {
1809
+ if (value === other) {
1810
+ return true;
1811
+ }
1812
+ if (value == null || other == null || (!isObject(value) && !isObjectLike(other))) {
1813
+ return value !== value && other !== other;
1814
+ }
1815
+ return baseIsEqualDeep(value, other, baseIsEqual, customizer, isLoose, stackA, stackB);
1816
+ }
1817
+
1818
+ module.exports = baseIsEqual;
1819
+
1820
+ },{"../lang/isObject":131,"./baseIsEqualDeep":51,"./isObjectLike":108}],51:[function(require,module,exports){
1821
+ var equalArrays = require('./equalArrays'),
1822
+ equalByTag = require('./equalByTag'),
1823
+ equalObjects = require('./equalObjects'),
1824
+ isArray = require('../lang/isArray'),
1825
+ isTypedArray = require('../lang/isTypedArray');
1826
+
1827
+ /** `Object#toString` result references. */
1828
+ var argsTag = '[object Arguments]',
1829
+ arrayTag = '[object Array]',
1830
+ objectTag = '[object Object]';
1831
+
1832
+ /** Used for native method references. */
1833
+ var objectProto = Object.prototype;
1834
+
1835
+ /** Used to check objects for own properties. */
1836
+ var hasOwnProperty = objectProto.hasOwnProperty;
1837
+
1838
+ /**
1839
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
1840
+ * of values.
1841
+ */
1842
+ var objToString = objectProto.toString;
1843
+
1844
+ /**
1845
+ * A specialized version of `baseIsEqual` for arrays and objects which performs
1846
+ * deep comparisons and tracks traversed objects enabling objects with circular
1847
+ * references to be compared.
1848
+ *
1849
+ * @private
1850
+ * @param {Object} object The object to compare.
1851
+ * @param {Object} other The other object to compare.
1852
+ * @param {Function} equalFunc The function to determine equivalents of values.
1853
+ * @param {Function} [customizer] The function to customize comparing objects.
1854
+ * @param {boolean} [isLoose] Specify performing partial comparisons.
1855
+ * @param {Array} [stackA=[]] Tracks traversed `value` objects.
1856
+ * @param {Array} [stackB=[]] Tracks traversed `other` objects.
1857
+ * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
1858
+ */
1859
+ function baseIsEqualDeep(object, other, equalFunc, customizer, isLoose, stackA, stackB) {
1860
+ var objIsArr = isArray(object),
1861
+ othIsArr = isArray(other),
1862
+ objTag = arrayTag,
1863
+ othTag = arrayTag;
1864
+
1865
+ if (!objIsArr) {
1866
+ objTag = objToString.call(object);
1867
+ if (objTag == argsTag) {
1868
+ objTag = objectTag;
1869
+ } else if (objTag != objectTag) {
1870
+ objIsArr = isTypedArray(object);
1871
+ }
1872
+ }
1873
+ if (!othIsArr) {
1874
+ othTag = objToString.call(other);
1875
+ if (othTag == argsTag) {
1876
+ othTag = objectTag;
1877
+ } else if (othTag != objectTag) {
1878
+ othIsArr = isTypedArray(other);
1879
+ }
1880
+ }
1881
+ var objIsObj = objTag == objectTag,
1882
+ othIsObj = othTag == objectTag,
1883
+ isSameTag = objTag == othTag;
1884
+
1885
+ if (isSameTag && !(objIsArr || objIsObj)) {
1886
+ return equalByTag(object, other, objTag);
1887
+ }
1888
+ if (!isLoose) {
1889
+ var objIsWrapped = objIsObj && hasOwnProperty.call(object, '__wrapped__'),
1890
+ othIsWrapped = othIsObj && hasOwnProperty.call(other, '__wrapped__');
1891
+
1892
+ if (objIsWrapped || othIsWrapped) {
1893
+ return equalFunc(objIsWrapped ? object.value() : object, othIsWrapped ? other.value() : other, customizer, isLoose, stackA, stackB);
1894
+ }
1895
+ }
1896
+ if (!isSameTag) {
1897
+ return false;
1898
+ }
1899
+ // Assume cyclic values are equal.
1900
+ // For more information on detecting circular references see https://es5.github.io/#JO.
1901
+ stackA || (stackA = []);
1902
+ stackB || (stackB = []);
1903
+
1904
+ var length = stackA.length;
1905
+ while (length--) {
1906
+ if (stackA[length] == object) {
1907
+ return stackB[length] == other;
1908
+ }
1909
+ }
1910
+ // Add `object` and `other` to the stack of traversed objects.
1911
+ stackA.push(object);
1912
+ stackB.push(other);
1913
+
1914
+ var result = (objIsArr ? equalArrays : equalObjects)(object, other, equalFunc, customizer, isLoose, stackA, stackB);
1915
+
1916
+ stackA.pop();
1917
+ stackB.pop();
1918
+
1919
+ return result;
1920
+ }
1921
+
1922
+ module.exports = baseIsEqualDeep;
1923
+
1924
+ },{"../lang/isArray":127,"../lang/isTypedArray":134,"./equalArrays":93,"./equalByTag":94,"./equalObjects":95}],52:[function(require,module,exports){
1925
+ var baseIsEqual = require('./baseIsEqual'),
1926
+ toObject = require('./toObject');
1927
+
1928
+ /**
1929
+ * The base implementation of `_.isMatch` without support for callback
1930
+ * shorthands and `this` binding.
1931
+ *
1932
+ * @private
1933
+ * @param {Object} object The object to inspect.
1934
+ * @param {Array} matchData The propery names, values, and compare flags to match.
1935
+ * @param {Function} [customizer] The function to customize comparing objects.
1936
+ * @returns {boolean} Returns `true` if `object` is a match, else `false`.
1937
+ */
1938
+ function baseIsMatch(object, matchData, customizer) {
1939
+ var index = matchData.length,
1940
+ length = index,
1941
+ noCustomizer = !customizer;
1942
+
1943
+ if (object == null) {
1944
+ return !length;
1945
+ }
1946
+ object = toObject(object);
1947
+ while (index--) {
1948
+ var data = matchData[index];
1949
+ if ((noCustomizer && data[2])
1950
+ ? data[1] !== object[data[0]]
1951
+ : !(data[0] in object)
1952
+ ) {
1953
+ return false;
1954
+ }
1955
+ }
1956
+ while (++index < length) {
1957
+ data = matchData[index];
1958
+ var key = data[0],
1959
+ objValue = object[key],
1960
+ srcValue = data[1];
1961
+
1962
+ if (noCustomizer && data[2]) {
1963
+ if (objValue === undefined && !(key in object)) {
1964
+ return false;
1965
+ }
1966
+ } else {
1967
+ var result = customizer ? customizer(objValue, srcValue, key) : undefined;
1968
+ if (!(result === undefined ? baseIsEqual(srcValue, objValue, customizer, true) : result)) {
1969
+ return false;
1970
+ }
1971
+ }
1972
+ }
1973
+ return true;
1974
+ }
1975
+
1976
+ module.exports = baseIsMatch;
1977
+
1978
+ },{"./baseIsEqual":50,"./toObject":121}],53:[function(require,module,exports){
1979
+ /**
1980
+ * The function whose prototype all chaining wrappers inherit from.
1981
+ *
1982
+ * @private
1983
+ */
1984
+ function baseLodash() {
1985
+ // No operation performed.
1986
+ }
1987
+
1988
+ module.exports = baseLodash;
1989
+
1990
+ },{}],54:[function(require,module,exports){
1991
+ var baseEach = require('./baseEach'),
1992
+ isArrayLike = require('./isArrayLike');
1993
+
1994
+ /**
1995
+ * The base implementation of `_.map` without support for callback shorthands
1996
+ * and `this` binding.
1997
+ *
1998
+ * @private
1999
+ * @param {Array|Object|string} collection The collection to iterate over.
2000
+ * @param {Function} iteratee The function invoked per iteration.
2001
+ * @returns {Array} Returns the new mapped array.
2002
+ */
2003
+ function baseMap(collection, iteratee) {
2004
+ var index = -1,
2005
+ result = isArrayLike(collection) ? Array(collection.length) : [];
2006
+
2007
+ baseEach(collection, function(value, key, collection) {
2008
+ result[++index] = iteratee(value, key, collection);
2009
+ });
2010
+ return result;
2011
+ }
2012
+
2013
+ module.exports = baseMap;
2014
+
2015
+ },{"./baseEach":40,"./isArrayLike":102}],55:[function(require,module,exports){
2016
+ var baseIsMatch = require('./baseIsMatch'),
2017
+ getMatchData = require('./getMatchData'),
2018
+ toObject = require('./toObject');
2019
+
2020
+ /**
2021
+ * The base implementation of `_.matches` which does not clone `source`.
2022
+ *
2023
+ * @private
2024
+ * @param {Object} source The object of property values to match.
2025
+ * @returns {Function} Returns the new function.
2026
+ */
2027
+ function baseMatches(source) {
2028
+ var matchData = getMatchData(source);
2029
+ if (matchData.length == 1 && matchData[0][2]) {
2030
+ var key = matchData[0][0],
2031
+ value = matchData[0][1];
2032
+
2033
+ return function(object) {
2034
+ if (object == null) {
2035
+ return false;
2036
+ }
2037
+ return object[key] === value && (value !== undefined || (key in toObject(object)));
2038
+ };
2039
+ }
2040
+ return function(object) {
2041
+ return baseIsMatch(object, matchData);
2042
+ };
2043
+ }
2044
+
2045
+ module.exports = baseMatches;
2046
+
2047
+ },{"./baseIsMatch":52,"./getMatchData":99,"./toObject":121}],56:[function(require,module,exports){
2048
+ var baseGet = require('./baseGet'),
2049
+ baseIsEqual = require('./baseIsEqual'),
2050
+ baseSlice = require('./baseSlice'),
2051
+ isArray = require('../lang/isArray'),
2052
+ isKey = require('./isKey'),
2053
+ isStrictComparable = require('./isStrictComparable'),
2054
+ last = require('../array/last'),
2055
+ toObject = require('./toObject'),
2056
+ toPath = require('./toPath');
2057
+
2058
+ /**
2059
+ * The base implementation of `_.matchesProperty` which does not clone `srcValue`.
2060
+ *
2061
+ * @private
2062
+ * @param {string} path The path of the property to get.
2063
+ * @param {*} srcValue The value to compare.
2064
+ * @returns {Function} Returns the new function.
2065
+ */
2066
+ function baseMatchesProperty(path, srcValue) {
2067
+ var isArr = isArray(path),
2068
+ isCommon = isKey(path) && isStrictComparable(srcValue),
2069
+ pathKey = (path + '');
2070
+
2071
+ path = toPath(path);
2072
+ return function(object) {
2073
+ if (object == null) {
2074
+ return false;
2075
+ }
2076
+ var key = pathKey;
2077
+ object = toObject(object);
2078
+ if ((isArr || !isCommon) && !(key in object)) {
2079
+ object = path.length == 1 ? object : baseGet(object, baseSlice(path, 0, -1));
2080
+ if (object == null) {
2081
+ return false;
2082
+ }
2083
+ key = last(path);
2084
+ object = toObject(object);
2085
+ }
2086
+ return object[key] === srcValue
2087
+ ? (srcValue !== undefined || (key in object))
2088
+ : baseIsEqual(srcValue, object[key], undefined, true);
2089
+ };
2090
+ }
2091
+
2092
+ module.exports = baseMatchesProperty;
2093
+
2094
+ },{"../array/last":7,"../lang/isArray":127,"./baseGet":48,"./baseIsEqual":50,"./baseSlice":63,"./isKey":105,"./isStrictComparable":110,"./toObject":121,"./toPath":122}],57:[function(require,module,exports){
2095
+ var arrayEach = require('./arrayEach'),
2096
+ baseMergeDeep = require('./baseMergeDeep'),
2097
+ isArray = require('../lang/isArray'),
2098
+ isArrayLike = require('./isArrayLike'),
2099
+ isObject = require('../lang/isObject'),
2100
+ isObjectLike = require('./isObjectLike'),
2101
+ isTypedArray = require('../lang/isTypedArray'),
2102
+ keys = require('../object/keys');
2103
+
2104
+ /**
2105
+ * The base implementation of `_.merge` without support for argument juggling,
2106
+ * multiple sources, and `this` binding `customizer` functions.
2107
+ *
2108
+ * @private
2109
+ * @param {Object} object The destination object.
2110
+ * @param {Object} source The source object.
2111
+ * @param {Function} [customizer] The function to customize merged values.
2112
+ * @param {Array} [stackA=[]] Tracks traversed source objects.
2113
+ * @param {Array} [stackB=[]] Associates values with source counterparts.
2114
+ * @returns {Object} Returns `object`.
2115
+ */
2116
+ function baseMerge(object, source, customizer, stackA, stackB) {
2117
+ if (!isObject(object)) {
2118
+ return object;
2119
+ }
2120
+ var isSrcArr = isArrayLike(source) && (isArray(source) || isTypedArray(source)),
2121
+ props = isSrcArr ? undefined : keys(source);
2122
+
2123
+ arrayEach(props || source, function(srcValue, key) {
2124
+ if (props) {
2125
+ key = srcValue;
2126
+ srcValue = source[key];
2127
+ }
2128
+ if (isObjectLike(srcValue)) {
2129
+ stackA || (stackA = []);
2130
+ stackB || (stackB = []);
2131
+ baseMergeDeep(object, source, key, baseMerge, customizer, stackA, stackB);
2132
+ }
2133
+ else {
2134
+ var value = object[key],
2135
+ result = customizer ? customizer(value, srcValue, key, object, source) : undefined,
2136
+ isCommon = result === undefined;
2137
+
2138
+ if (isCommon) {
2139
+ result = srcValue;
2140
+ }
2141
+ if ((result !== undefined || (isSrcArr && !(key in object))) &&
2142
+ (isCommon || (result === result ? (result !== value) : (value === value)))) {
2143
+ object[key] = result;
2144
+ }
2145
+ }
2146
+ });
2147
+ return object;
2148
+ }
2149
+
2150
+ module.exports = baseMerge;
2151
+
2152
+ },{"../lang/isArray":127,"../lang/isObject":131,"../lang/isTypedArray":134,"../object/keys":140,"./arrayEach":25,"./baseMergeDeep":58,"./isArrayLike":102,"./isObjectLike":108}],58:[function(require,module,exports){
2153
+ var arrayCopy = require('./arrayCopy'),
2154
+ isArguments = require('../lang/isArguments'),
2155
+ isArray = require('../lang/isArray'),
2156
+ isArrayLike = require('./isArrayLike'),
2157
+ isPlainObject = require('../lang/isPlainObject'),
2158
+ isTypedArray = require('../lang/isTypedArray'),
2159
+ toPlainObject = require('../lang/toPlainObject');
2160
+
2161
+ /**
2162
+ * A specialized version of `baseMerge` for arrays and objects which performs
2163
+ * deep merges and tracks traversed objects enabling objects with circular
2164
+ * references to be merged.
2165
+ *
2166
+ * @private
2167
+ * @param {Object} object The destination object.
2168
+ * @param {Object} source The source object.
2169
+ * @param {string} key The key of the value to merge.
2170
+ * @param {Function} mergeFunc The function to merge values.
2171
+ * @param {Function} [customizer] The function to customize merged values.
2172
+ * @param {Array} [stackA=[]] Tracks traversed source objects.
2173
+ * @param {Array} [stackB=[]] Associates values with source counterparts.
2174
+ * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
2175
+ */
2176
+ function baseMergeDeep(object, source, key, mergeFunc, customizer, stackA, stackB) {
2177
+ var length = stackA.length,
2178
+ srcValue = source[key];
2179
+
2180
+ while (length--) {
2181
+ if (stackA[length] == srcValue) {
2182
+ object[key] = stackB[length];
2183
+ return;
2184
+ }
2185
+ }
2186
+ var value = object[key],
2187
+ result = customizer ? customizer(value, srcValue, key, object, source) : undefined,
2188
+ isCommon = result === undefined;
2189
+
2190
+ if (isCommon) {
2191
+ result = srcValue;
2192
+ if (isArrayLike(srcValue) && (isArray(srcValue) || isTypedArray(srcValue))) {
2193
+ result = isArray(value)
2194
+ ? value
2195
+ : (isArrayLike(value) ? arrayCopy(value) : []);
2196
+ }
2197
+ else if (isPlainObject(srcValue) || isArguments(srcValue)) {
2198
+ result = isArguments(value)
2199
+ ? toPlainObject(value)
2200
+ : (isPlainObject(value) ? value : {});
2201
+ }
2202
+ else {
2203
+ isCommon = false;
2204
+ }
2205
+ }
2206
+ // Add the source value to the stack of traversed objects and associate
2207
+ // it with its merged value.
2208
+ stackA.push(srcValue);
2209
+ stackB.push(result);
2210
+
2211
+ if (isCommon) {
2212
+ // Recursively merge objects and arrays (susceptible to call stack limits).
2213
+ object[key] = mergeFunc(result, srcValue, customizer, stackA, stackB);
2214
+ } else if (result === result ? (result !== value) : (value === value)) {
2215
+ object[key] = result;
2216
+ }
2217
+ }
2218
+
2219
+ module.exports = baseMergeDeep;
2220
+
2221
+ },{"../lang/isArguments":126,"../lang/isArray":127,"../lang/isPlainObject":132,"../lang/isTypedArray":134,"../lang/toPlainObject":136,"./arrayCopy":24,"./isArrayLike":102}],59:[function(require,module,exports){
2222
+ /**
2223
+ * The base implementation of `_.property` without support for deep paths.
2224
+ *
2225
+ * @private
2226
+ * @param {string} key The key of the property to get.
2227
+ * @returns {Function} Returns the new function.
2228
+ */
2229
+ function baseProperty(key) {
2230
+ return function(object) {
2231
+ return object == null ? undefined : object[key];
2232
+ };
2233
+ }
2234
+
2235
+ module.exports = baseProperty;
2236
+
2237
+ },{}],60:[function(require,module,exports){
2238
+ var baseGet = require('./baseGet'),
2239
+ toPath = require('./toPath');
2240
+
2241
+ /**
2242
+ * A specialized version of `baseProperty` which supports deep paths.
2243
+ *
2244
+ * @private
2245
+ * @param {Array|string} path The path of the property to get.
2246
+ * @returns {Function} Returns the new function.
2247
+ */
2248
+ function basePropertyDeep(path) {
2249
+ var pathKey = (path + '');
2250
+ path = toPath(path);
2251
+ return function(object) {
2252
+ return baseGet(object, path, pathKey);
2253
+ };
2254
+ }
2255
+
2256
+ module.exports = basePropertyDeep;
2257
+
2258
+ },{"./baseGet":48,"./toPath":122}],61:[function(require,module,exports){
2259
+ /**
2260
+ * The base implementation of `_.reduce` and `_.reduceRight` without support
2261
+ * for callback shorthands and `this` binding, which iterates over `collection`
2262
+ * using the provided `eachFunc`.
2263
+ *
2264
+ * @private
2265
+ * @param {Array|Object|string} collection The collection to iterate over.
2266
+ * @param {Function} iteratee The function invoked per iteration.
2267
+ * @param {*} accumulator The initial value.
2268
+ * @param {boolean} initFromCollection Specify using the first or last element
2269
+ * of `collection` as the initial value.
2270
+ * @param {Function} eachFunc The function to iterate over `collection`.
2271
+ * @returns {*} Returns the accumulated value.
2272
+ */
2273
+ function baseReduce(collection, iteratee, accumulator, initFromCollection, eachFunc) {
2274
+ eachFunc(collection, function(value, index, collection) {
2275
+ accumulator = initFromCollection
2276
+ ? (initFromCollection = false, value)
2277
+ : iteratee(accumulator, value, index, collection);
2278
+ });
2279
+ return accumulator;
2280
+ }
2281
+
2282
+ module.exports = baseReduce;
2283
+
2284
+ },{}],62:[function(require,module,exports){
2285
+ var identity = require('../utility/identity'),
2286
+ metaMap = require('./metaMap');
2287
+
2288
+ /**
2289
+ * The base implementation of `setData` without support for hot loop detection.
2290
+ *
2291
+ * @private
2292
+ * @param {Function} func The function to associate metadata with.
2293
+ * @param {*} data The metadata.
2294
+ * @returns {Function} Returns `func`.
2295
+ */
2296
+ var baseSetData = !metaMap ? identity : function(func, data) {
2297
+ metaMap.set(func, data);
2298
+ return func;
2299
+ };
2300
+
2301
+ module.exports = baseSetData;
2302
+
2303
+ },{"../utility/identity":148,"./metaMap":112}],63:[function(require,module,exports){
2304
+ /**
2305
+ * The base implementation of `_.slice` without an iteratee call guard.
2306
+ *
2307
+ * @private
2308
+ * @param {Array} array The array to slice.
2309
+ * @param {number} [start=0] The start position.
2310
+ * @param {number} [end=array.length] The end position.
2311
+ * @returns {Array} Returns the slice of `array`.
2312
+ */
2313
+ function baseSlice(array, start, end) {
2314
+ var index = -1,
2315
+ length = array.length;
2316
+
2317
+ start = start == null ? 0 : (+start || 0);
2318
+ if (start < 0) {
2319
+ start = -start > length ? 0 : (length + start);
2320
+ }
2321
+ end = (end === undefined || end > length) ? length : (+end || 0);
2322
+ if (end < 0) {
2323
+ end += length;
2324
+ }
2325
+ length = start > end ? 0 : ((end - start) >>> 0);
2326
+ start >>>= 0;
2327
+
2328
+ var result = Array(length);
2329
+ while (++index < length) {
2330
+ result[index] = array[index + start];
2331
+ }
2332
+ return result;
2333
+ }
2334
+
2335
+ module.exports = baseSlice;
2336
+
2337
+ },{}],64:[function(require,module,exports){
2338
+ /**
2339
+ * The base implementation of `_.sortBy` which uses `comparer` to define
2340
+ * the sort order of `array` and replaces criteria objects with their
2341
+ * corresponding values.
2342
+ *
2343
+ * @private
2344
+ * @param {Array} array The array to sort.
2345
+ * @param {Function} comparer The function to define sort order.
2346
+ * @returns {Array} Returns `array`.
2347
+ */
2348
+ function baseSortBy(array, comparer) {
2349
+ var length = array.length;
2350
+
2351
+ array.sort(comparer);
2352
+ while (length--) {
2353
+ array[length] = array[length].value;
2354
+ }
2355
+ return array;
2356
+ }
2357
+
2358
+ module.exports = baseSortBy;
2359
+
2360
+ },{}],65:[function(require,module,exports){
2361
+ var arrayMap = require('./arrayMap'),
2362
+ baseCallback = require('./baseCallback'),
2363
+ baseMap = require('./baseMap'),
2364
+ baseSortBy = require('./baseSortBy'),
2365
+ compareMultiple = require('./compareMultiple');
2366
+
2367
+ /**
2368
+ * The base implementation of `_.sortByOrder` without param guards.
2369
+ *
2370
+ * @private
2371
+ * @param {Array|Object|string} collection The collection to iterate over.
2372
+ * @param {Function[]|Object[]|string[]} iteratees The iteratees to sort by.
2373
+ * @param {boolean[]} orders The sort orders of `iteratees`.
2374
+ * @returns {Array} Returns the new sorted array.
2375
+ */
2376
+ function baseSortByOrder(collection, iteratees, orders) {
2377
+ var index = -1;
2378
+
2379
+ iteratees = arrayMap(iteratees, function(iteratee) { return baseCallback(iteratee); });
2380
+
2381
+ var result = baseMap(collection, function(value) {
2382
+ var criteria = arrayMap(iteratees, function(iteratee) { return iteratee(value); });
2383
+ return { 'criteria': criteria, 'index': ++index, 'value': value };
2384
+ });
2385
+
2386
+ return baseSortBy(result, function(object, other) {
2387
+ return compareMultiple(object, other, orders);
2388
+ });
2389
+ }
2390
+
2391
+ module.exports = baseSortByOrder;
2392
+
2393
+ },{"./arrayMap":27,"./baseCallback":35,"./baseMap":54,"./baseSortBy":64,"./compareMultiple":76}],66:[function(require,module,exports){
2394
+ var baseEach = require('./baseEach');
2395
+
2396
+ /**
2397
+ * The base implementation of `_.sum` without support for callback shorthands
2398
+ * and `this` binding.
2399
+ *
2400
+ * @private
2401
+ * @param {Array|Object|string} collection The collection to iterate over.
2402
+ * @param {Function} iteratee The function invoked per iteration.
2403
+ * @returns {number} Returns the sum.
2404
+ */
2405
+ function baseSum(collection, iteratee) {
2406
+ var result = 0;
2407
+ baseEach(collection, function(value, index, collection) {
2408
+ result += +iteratee(value, index, collection) || 0;
2409
+ });
2410
+ return result;
2411
+ }
2412
+
2413
+ module.exports = baseSum;
2414
+
2415
+ },{"./baseEach":40}],67:[function(require,module,exports){
2416
+ /**
2417
+ * Converts `value` to a string if it's not one. An empty string is returned
2418
+ * for `null` or `undefined` values.
2419
+ *
2420
+ * @private
2421
+ * @param {*} value The value to process.
2422
+ * @returns {string} Returns the string.
2423
+ */
2424
+ function baseToString(value) {
2425
+ return value == null ? '' : (value + '');
2426
+ }
2427
+
2428
+ module.exports = baseToString;
2429
+
2430
+ },{}],68:[function(require,module,exports){
2431
+ /**
2432
+ * The base implementation of `_.values` and `_.valuesIn` which creates an
2433
+ * array of `object` property values corresponding to the property names
2434
+ * of `props`.
2435
+ *
2436
+ * @private
2437
+ * @param {Object} object The object to query.
2438
+ * @param {Array} props The property names to get values for.
2439
+ * @returns {Object} Returns the array of property values.
2440
+ */
2441
+ function baseValues(object, props) {
2442
+ var index = -1,
2443
+ length = props.length,
2444
+ result = Array(length);
2445
+
2446
+ while (++index < length) {
2447
+ result[index] = object[props[index]];
2448
+ }
2449
+ return result;
2450
+ }
2451
+
2452
+ module.exports = baseValues;
2453
+
2454
+ },{}],69:[function(require,module,exports){
2455
+ var binaryIndexBy = require('./binaryIndexBy'),
2456
+ identity = require('../utility/identity');
2457
+
2458
+ /** Used as references for the maximum length and index of an array. */
2459
+ var MAX_ARRAY_LENGTH = 4294967295,
2460
+ HALF_MAX_ARRAY_LENGTH = MAX_ARRAY_LENGTH >>> 1;
2461
+
2462
+ /**
2463
+ * Performs a binary search of `array` to determine the index at which `value`
2464
+ * should be inserted into `array` in order to maintain its sort order.
2465
+ *
2466
+ * @private
2467
+ * @param {Array} array The sorted array to inspect.
2468
+ * @param {*} value The value to evaluate.
2469
+ * @param {boolean} [retHighest] Specify returning the highest qualified index.
2470
+ * @returns {number} Returns the index at which `value` should be inserted
2471
+ * into `array`.
2472
+ */
2473
+ function binaryIndex(array, value, retHighest) {
2474
+ var low = 0,
2475
+ high = array ? array.length : low;
2476
+
2477
+ if (typeof value == 'number' && value === value && high <= HALF_MAX_ARRAY_LENGTH) {
2478
+ while (low < high) {
2479
+ var mid = (low + high) >>> 1,
2480
+ computed = array[mid];
2481
+
2482
+ if ((retHighest ? (computed <= value) : (computed < value)) && computed !== null) {
2483
+ low = mid + 1;
2484
+ } else {
2485
+ high = mid;
2486
+ }
2487
+ }
2488
+ return high;
2489
+ }
2490
+ return binaryIndexBy(array, value, identity, retHighest);
2491
+ }
2492
+
2493
+ module.exports = binaryIndex;
2494
+
2495
+ },{"../utility/identity":148,"./binaryIndexBy":70}],70:[function(require,module,exports){
2496
+ /* Native method references for those with the same name as other `lodash` methods. */
2497
+ var nativeFloor = Math.floor,
2498
+ nativeMin = Math.min;
2499
+
2500
+ /** Used as references for the maximum length and index of an array. */
2501
+ var MAX_ARRAY_LENGTH = 4294967295,
2502
+ MAX_ARRAY_INDEX = MAX_ARRAY_LENGTH - 1;
2503
+
2504
+ /**
2505
+ * This function is like `binaryIndex` except that it invokes `iteratee` for
2506
+ * `value` and each element of `array` to compute their sort ranking. The
2507
+ * iteratee is invoked with one argument; (value).
2508
+ *
2509
+ * @private
2510
+ * @param {Array} array The sorted array to inspect.
2511
+ * @param {*} value The value to evaluate.
2512
+ * @param {Function} iteratee The function invoked per iteration.
2513
+ * @param {boolean} [retHighest] Specify returning the highest qualified index.
2514
+ * @returns {number} Returns the index at which `value` should be inserted
2515
+ * into `array`.
2516
+ */
2517
+ function binaryIndexBy(array, value, iteratee, retHighest) {
2518
+ value = iteratee(value);
2519
+
2520
+ var low = 0,
2521
+ high = array ? array.length : 0,
2522
+ valIsNaN = value !== value,
2523
+ valIsNull = value === null,
2524
+ valIsUndef = value === undefined;
2525
+
2526
+ while (low < high) {
2527
+ var mid = nativeFloor((low + high) / 2),
2528
+ computed = iteratee(array[mid]),
2529
+ isDef = computed !== undefined,
2530
+ isReflexive = computed === computed;
2531
+
2532
+ if (valIsNaN) {
2533
+ var setLow = isReflexive || retHighest;
2534
+ } else if (valIsNull) {
2535
+ setLow = isReflexive && isDef && (retHighest || computed != null);
2536
+ } else if (valIsUndef) {
2537
+ setLow = isReflexive && (retHighest || isDef);
2538
+ } else if (computed == null) {
2539
+ setLow = false;
2540
+ } else {
2541
+ setLow = retHighest ? (computed <= value) : (computed < value);
2542
+ }
2543
+ if (setLow) {
2544
+ low = mid + 1;
2545
+ } else {
2546
+ high = mid;
2547
+ }
2548
+ }
2549
+ return nativeMin(high, MAX_ARRAY_INDEX);
2550
+ }
2551
+
2552
+ module.exports = binaryIndexBy;
2553
+
2554
+ },{}],71:[function(require,module,exports){
2555
+ var identity = require('../utility/identity');
2556
+
2557
+ /**
2558
+ * A specialized version of `baseCallback` which only supports `this` binding
2559
+ * and specifying the number of arguments to provide to `func`.
2560
+ *
2561
+ * @private
2562
+ * @param {Function} func The function to bind.
2563
+ * @param {*} thisArg The `this` binding of `func`.
2564
+ * @param {number} [argCount] The number of arguments to provide to `func`.
2565
+ * @returns {Function} Returns the callback.
2566
+ */
2567
+ function bindCallback(func, thisArg, argCount) {
2568
+ if (typeof func != 'function') {
2569
+ return identity;
2570
+ }
2571
+ if (thisArg === undefined) {
2572
+ return func;
2573
+ }
2574
+ switch (argCount) {
2575
+ case 1: return function(value) {
2576
+ return func.call(thisArg, value);
2577
+ };
2578
+ case 3: return function(value, index, collection) {
2579
+ return func.call(thisArg, value, index, collection);
2580
+ };
2581
+ case 4: return function(accumulator, value, index, collection) {
2582
+ return func.call(thisArg, accumulator, value, index, collection);
2583
+ };
2584
+ case 5: return function(value, other, key, object, source) {
2585
+ return func.call(thisArg, value, other, key, object, source);
2586
+ };
2587
+ }
2588
+ return function() {
2589
+ return func.apply(thisArg, arguments);
2590
+ };
2591
+ }
2592
+
2593
+ module.exports = bindCallback;
2594
+
2595
+ },{"../utility/identity":148}],72:[function(require,module,exports){
2596
+ var isObject = require('../lang/isObject');
2597
+
2598
+ /**
2599
+ * Checks if `value` is in `cache` mimicking the return signature of
2600
+ * `_.indexOf` by returning `0` if the value is found, else `-1`.
2601
+ *
2602
+ * @private
2603
+ * @param {Object} cache The cache to search.
2604
+ * @param {*} value The value to search for.
2605
+ * @returns {number} Returns `0` if `value` is found, else `-1`.
2606
+ */
2607
+ function cacheIndexOf(cache, value) {
2608
+ var data = cache.data,
2609
+ result = (typeof value == 'string' || isObject(value)) ? data.set.has(value) : data.hash[value];
2610
+
2611
+ return result ? 0 : -1;
2612
+ }
2613
+
2614
+ module.exports = cacheIndexOf;
2615
+
2616
+ },{"../lang/isObject":131}],73:[function(require,module,exports){
2617
+ var isObject = require('../lang/isObject');
2618
+
2619
+ /**
2620
+ * Adds `value` to the cache.
2621
+ *
2622
+ * @private
2623
+ * @name push
2624
+ * @memberOf SetCache
2625
+ * @param {*} value The value to cache.
2626
+ */
2627
+ function cachePush(value) {
2628
+ var data = this.data;
2629
+ if (typeof value == 'string' || isObject(value)) {
2630
+ data.set.add(value);
2631
+ } else {
2632
+ data.hash[value] = true;
2633
+ }
2634
+ }
2635
+
2636
+ module.exports = cachePush;
2637
+
2638
+ },{"../lang/isObject":131}],74:[function(require,module,exports){
2639
+ /**
2640
+ * Used by `_.trim` and `_.trimLeft` to get the index of the first character
2641
+ * of `string` that is not found in `chars`.
2642
+ *
2643
+ * @private
2644
+ * @param {string} string The string to inspect.
2645
+ * @param {string} chars The characters to find.
2646
+ * @returns {number} Returns the index of the first character not found in `chars`.
2647
+ */
2648
+ function charsLeftIndex(string, chars) {
2649
+ var index = -1,
2650
+ length = string.length;
2651
+
2652
+ while (++index < length && chars.indexOf(string.charAt(index)) > -1) {}
2653
+ return index;
2654
+ }
2655
+
2656
+ module.exports = charsLeftIndex;
2657
+
2658
+ },{}],75:[function(require,module,exports){
2659
+ /**
2660
+ * Used by `_.trim` and `_.trimRight` to get the index of the last character
2661
+ * of `string` that is not found in `chars`.
2662
+ *
2663
+ * @private
2664
+ * @param {string} string The string to inspect.
2665
+ * @param {string} chars The characters to find.
2666
+ * @returns {number} Returns the index of the last character not found in `chars`.
2667
+ */
2668
+ function charsRightIndex(string, chars) {
2669
+ var index = string.length;
2670
+
2671
+ while (index-- && chars.indexOf(string.charAt(index)) > -1) {}
2672
+ return index;
2673
+ }
2674
+
2675
+ module.exports = charsRightIndex;
2676
+
2677
+ },{}],76:[function(require,module,exports){
2678
+ var baseCompareAscending = require('./baseCompareAscending');
2679
+
2680
+ /**
2681
+ * Used by `_.sortByOrder` to compare multiple properties of a value to another
2682
+ * and stable sort them.
2683
+ *
2684
+ * If `orders` is unspecified, all valuess are sorted in ascending order. Otherwise,
2685
+ * a value is sorted in ascending order if its corresponding order is "asc", and
2686
+ * descending if "desc".
2687
+ *
2688
+ * @private
2689
+ * @param {Object} object The object to compare.
2690
+ * @param {Object} other The other object to compare.
2691
+ * @param {boolean[]} orders The order to sort by for each property.
2692
+ * @returns {number} Returns the sort order indicator for `object`.
2693
+ */
2694
+ function compareMultiple(object, other, orders) {
2695
+ var index = -1,
2696
+ objCriteria = object.criteria,
2697
+ othCriteria = other.criteria,
2698
+ length = objCriteria.length,
2699
+ ordersLength = orders.length;
2700
+
2701
+ while (++index < length) {
2702
+ var result = baseCompareAscending(objCriteria[index], othCriteria[index]);
2703
+ if (result) {
2704
+ if (index >= ordersLength) {
2705
+ return result;
2706
+ }
2707
+ var order = orders[index];
2708
+ return result * ((order === 'asc' || order === true) ? 1 : -1);
2709
+ }
2710
+ }
2711
+ // Fixes an `Array#sort` bug in the JS engine embedded in Adobe applications
2712
+ // that causes it, under certain circumstances, to provide the same value for
2713
+ // `object` and `other`. See https://github.com/jashkenas/underscore/pull/1247
2714
+ // for more details.
2715
+ //
2716
+ // This also ensures a stable sort in V8 and other engines.
2717
+ // See https://code.google.com/p/v8/issues/detail?id=90 for more details.
2718
+ return object.index - other.index;
2719
+ }
2720
+
2721
+ module.exports = compareMultiple;
2722
+
2723
+ },{"./baseCompareAscending":36}],77:[function(require,module,exports){
2724
+ /* Native method references for those with the same name as other `lodash` methods. */
2725
+ var nativeMax = Math.max;
2726
+
2727
+ /**
2728
+ * Creates an array that is the composition of partially applied arguments,
2729
+ * placeholders, and provided arguments into a single array of arguments.
2730
+ *
2731
+ * @private
2732
+ * @param {Array|Object} args The provided arguments.
2733
+ * @param {Array} partials The arguments to prepend to those provided.
2734
+ * @param {Array} holders The `partials` placeholder indexes.
2735
+ * @returns {Array} Returns the new array of composed arguments.
2736
+ */
2737
+ function composeArgs(args, partials, holders) {
2738
+ var holdersLength = holders.length,
2739
+ argsIndex = -1,
2740
+ argsLength = nativeMax(args.length - holdersLength, 0),
2741
+ leftIndex = -1,
2742
+ leftLength = partials.length,
2743
+ result = Array(leftLength + argsLength);
2744
+
2745
+ while (++leftIndex < leftLength) {
2746
+ result[leftIndex] = partials[leftIndex];
2747
+ }
2748
+ while (++argsIndex < holdersLength) {
2749
+ result[holders[argsIndex]] = args[argsIndex];
2750
+ }
2751
+ while (argsLength--) {
2752
+ result[leftIndex++] = args[argsIndex++];
2753
+ }
2754
+ return result;
2755
+ }
2756
+
2757
+ module.exports = composeArgs;
2758
+
2759
+ },{}],78:[function(require,module,exports){
2760
+ /* Native method references for those with the same name as other `lodash` methods. */
2761
+ var nativeMax = Math.max;
2762
+
2763
+ /**
2764
+ * This function is like `composeArgs` except that the arguments composition
2765
+ * is tailored for `_.partialRight`.
2766
+ *
2767
+ * @private
2768
+ * @param {Array|Object} args The provided arguments.
2769
+ * @param {Array} partials The arguments to append to those provided.
2770
+ * @param {Array} holders The `partials` placeholder indexes.
2771
+ * @returns {Array} Returns the new array of composed arguments.
2772
+ */
2773
+ function composeArgsRight(args, partials, holders) {
2774
+ var holdersIndex = -1,
2775
+ holdersLength = holders.length,
2776
+ argsIndex = -1,
2777
+ argsLength = nativeMax(args.length - holdersLength, 0),
2778
+ rightIndex = -1,
2779
+ rightLength = partials.length,
2780
+ result = Array(argsLength + rightLength);
2781
+
2782
+ while (++argsIndex < argsLength) {
2783
+ result[argsIndex] = args[argsIndex];
2784
+ }
2785
+ var offset = argsIndex;
2786
+ while (++rightIndex < rightLength) {
2787
+ result[offset + rightIndex] = partials[rightIndex];
2788
+ }
2789
+ while (++holdersIndex < holdersLength) {
2790
+ result[offset + holders[holdersIndex]] = args[argsIndex++];
2791
+ }
2792
+ return result;
2793
+ }
2794
+
2795
+ module.exports = composeArgsRight;
2796
+
2797
+ },{}],79:[function(require,module,exports){
2798
+ var bindCallback = require('./bindCallback'),
2799
+ isIterateeCall = require('./isIterateeCall'),
2800
+ restParam = require('../function/restParam');
2801
+
2802
+ /**
2803
+ * Creates a `_.assign`, `_.defaults`, or `_.merge` function.
2804
+ *
2805
+ * @private
2806
+ * @param {Function} assigner The function to assign values.
2807
+ * @returns {Function} Returns the new assigner function.
2808
+ */
2809
+ function createAssigner(assigner) {
2810
+ return restParam(function(object, sources) {
2811
+ var index = -1,
2812
+ length = object == null ? 0 : sources.length,
2813
+ customizer = length > 2 ? sources[length - 2] : undefined,
2814
+ guard = length > 2 ? sources[2] : undefined,
2815
+ thisArg = length > 1 ? sources[length - 1] : undefined;
2816
+
2817
+ if (typeof customizer == 'function') {
2818
+ customizer = bindCallback(customizer, thisArg, 5);
2819
+ length -= 2;
2820
+ } else {
2821
+ customizer = typeof thisArg == 'function' ? thisArg : undefined;
2822
+ length -= (customizer ? 1 : 0);
2823
+ }
2824
+ if (guard && isIterateeCall(sources[0], sources[1], guard)) {
2825
+ customizer = length < 3 ? undefined : customizer;
2826
+ length = 1;
2827
+ }
2828
+ while (++index < length) {
2829
+ var source = sources[index];
2830
+ if (source) {
2831
+ assigner(object, source, customizer);
2832
+ }
2833
+ }
2834
+ return object;
2835
+ });
2836
+ }
2837
+
2838
+ module.exports = createAssigner;
2839
+
2840
+ },{"../function/restParam":20,"./bindCallback":71,"./isIterateeCall":104}],80:[function(require,module,exports){
2841
+ var getLength = require('./getLength'),
2842
+ isLength = require('./isLength'),
2843
+ toObject = require('./toObject');
2844
+
2845
+ /**
2846
+ * Creates a `baseEach` or `baseEachRight` function.
2847
+ *
2848
+ * @private
2849
+ * @param {Function} eachFunc The function to iterate over a collection.
2850
+ * @param {boolean} [fromRight] Specify iterating from right to left.
2851
+ * @returns {Function} Returns the new base function.
2852
+ */
2853
+ function createBaseEach(eachFunc, fromRight) {
2854
+ return function(collection, iteratee) {
2855
+ var length = collection ? getLength(collection) : 0;
2856
+ if (!isLength(length)) {
2857
+ return eachFunc(collection, iteratee);
2858
+ }
2859
+ var index = fromRight ? length : -1,
2860
+ iterable = toObject(collection);
2861
+
2862
+ while ((fromRight ? index-- : ++index < length)) {
2863
+ if (iteratee(iterable[index], index, iterable) === false) {
2864
+ break;
2865
+ }
2866
+ }
2867
+ return collection;
2868
+ };
2869
+ }
2870
+
2871
+ module.exports = createBaseEach;
2872
+
2873
+ },{"./getLength":98,"./isLength":107,"./toObject":121}],81:[function(require,module,exports){
2874
+ var toObject = require('./toObject');
2875
+
2876
+ /**
2877
+ * Creates a base function for `_.forIn` or `_.forInRight`.
2878
+ *
2879
+ * @private
2880
+ * @param {boolean} [fromRight] Specify iterating from right to left.
2881
+ * @returns {Function} Returns the new base function.
2882
+ */
2883
+ function createBaseFor(fromRight) {
2884
+ return function(object, iteratee, keysFunc) {
2885
+ var iterable = toObject(object),
2886
+ props = keysFunc(object),
2887
+ length = props.length,
2888
+ index = fromRight ? length : -1;
2889
+
2890
+ while ((fromRight ? index-- : ++index < length)) {
2891
+ var key = props[index];
2892
+ if (iteratee(iterable[key], key, iterable) === false) {
2893
+ break;
2894
+ }
2895
+ }
2896
+ return object;
2897
+ };
2898
+ }
2899
+
2900
+ module.exports = createBaseFor;
2901
+
2902
+ },{"./toObject":121}],82:[function(require,module,exports){
2903
+ (function (global){
2904
+ var createCtorWrapper = require('./createCtorWrapper');
2905
+
2906
+ /**
2907
+ * Creates a function that wraps `func` and invokes it with the `this`
2908
+ * binding of `thisArg`.
2909
+ *
2910
+ * @private
2911
+ * @param {Function} func The function to bind.
2912
+ * @param {*} [thisArg] The `this` binding of `func`.
2913
+ * @returns {Function} Returns the new bound function.
2914
+ */
2915
+ function createBindWrapper(func, thisArg) {
2916
+ var Ctor = createCtorWrapper(func);
2917
+
2918
+ function wrapper() {
2919
+ var fn = (this && this !== global && this instanceof wrapper) ? Ctor : func;
2920
+ return fn.apply(thisArg, arguments);
2921
+ }
2922
+ return wrapper;
2923
+ }
2924
+
2925
+ module.exports = createBindWrapper;
2926
+
2927
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
2928
+ },{"./createCtorWrapper":84}],83:[function(require,module,exports){
2929
+ (function (global){
2930
+ var SetCache = require('./SetCache'),
2931
+ getNative = require('./getNative');
2932
+
2933
+ /** Native method references. */
2934
+ var Set = getNative(global, 'Set');
2935
+
2936
+ /* Native method references for those with the same name as other `lodash` methods. */
2937
+ var nativeCreate = getNative(Object, 'create');
2938
+
2939
+ /**
2940
+ * Creates a `Set` cache object to optimize linear searches of large arrays.
2941
+ *
2942
+ * @private
2943
+ * @param {Array} [values] The values to cache.
2944
+ * @returns {null|Object} Returns the new cache object if `Set` is supported, else `null`.
2945
+ */
2946
+ function createCache(values) {
2947
+ return (nativeCreate && Set) ? new SetCache(values) : null;
2948
+ }
2949
+
2950
+ module.exports = createCache;
2951
+
2952
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
2953
+ },{"./SetCache":23,"./getNative":100}],84:[function(require,module,exports){
2954
+ var baseCreate = require('./baseCreate'),
2955
+ isObject = require('../lang/isObject');
2956
+
2957
+ /**
2958
+ * Creates a function that produces an instance of `Ctor` regardless of
2959
+ * whether it was invoked as part of a `new` expression or by `call` or `apply`.
2960
+ *
2961
+ * @private
2962
+ * @param {Function} Ctor The constructor to wrap.
2963
+ * @returns {Function} Returns the new wrapped function.
2964
+ */
2965
+ function createCtorWrapper(Ctor) {
2966
+ return function() {
2967
+ // Use a `switch` statement to work with class constructors.
2968
+ // See http://ecma-international.org/ecma-262/6.0/#sec-ecmascript-function-objects-call-thisargument-argumentslist
2969
+ // for more details.
2970
+ var args = arguments;
2971
+ switch (args.length) {
2972
+ case 0: return new Ctor;
2973
+ case 1: return new Ctor(args[0]);
2974
+ case 2: return new Ctor(args[0], args[1]);
2975
+ case 3: return new Ctor(args[0], args[1], args[2]);
2976
+ case 4: return new Ctor(args[0], args[1], args[2], args[3]);
2977
+ case 5: return new Ctor(args[0], args[1], args[2], args[3], args[4]);
2978
+ case 6: return new Ctor(args[0], args[1], args[2], args[3], args[4], args[5]);
2979
+ case 7: return new Ctor(args[0], args[1], args[2], args[3], args[4], args[5], args[6]);
2980
+ }
2981
+ var thisBinding = baseCreate(Ctor.prototype),
2982
+ result = Ctor.apply(thisBinding, args);
2983
+
2984
+ // Mimic the constructor's `return` behavior.
2985
+ // See https://es5.github.io/#x13.2.2 for more details.
2986
+ return isObject(result) ? result : thisBinding;
2987
+ };
2988
+ }
2989
+
2990
+ module.exports = createCtorWrapper;
2991
+
2992
+ },{"../lang/isObject":131,"./baseCreate":38}],85:[function(require,module,exports){
2993
+ var restParam = require('../function/restParam');
2994
+
2995
+ /**
2996
+ * Creates a `_.defaults` or `_.defaultsDeep` function.
2997
+ *
2998
+ * @private
2999
+ * @param {Function} assigner The function to assign values.
3000
+ * @param {Function} customizer The function to customize assigned values.
3001
+ * @returns {Function} Returns the new defaults function.
3002
+ */
3003
+ function createDefaults(assigner, customizer) {
3004
+ return restParam(function(args) {
3005
+ var object = args[0];
3006
+ if (object == null) {
3007
+ return object;
3008
+ }
3009
+ args.push(customizer);
3010
+ return assigner.apply(undefined, args);
3011
+ });
3012
+ }
3013
+
3014
+ module.exports = createDefaults;
3015
+
3016
+ },{"../function/restParam":20}],86:[function(require,module,exports){
3017
+ var baseCallback = require('./baseCallback'),
3018
+ baseFind = require('./baseFind'),
3019
+ baseFindIndex = require('./baseFindIndex'),
3020
+ isArray = require('../lang/isArray');
3021
+
3022
+ /**
3023
+ * Creates a `_.find` or `_.findLast` function.
3024
+ *
3025
+ * @private
3026
+ * @param {Function} eachFunc The function to iterate over a collection.
3027
+ * @param {boolean} [fromRight] Specify iterating from right to left.
3028
+ * @returns {Function} Returns the new find function.
3029
+ */
3030
+ function createFind(eachFunc, fromRight) {
3031
+ return function(collection, predicate, thisArg) {
3032
+ predicate = baseCallback(predicate, thisArg, 3);
3033
+ if (isArray(collection)) {
3034
+ var index = baseFindIndex(collection, predicate, fromRight);
3035
+ return index > -1 ? collection[index] : undefined;
3036
+ }
3037
+ return baseFind(collection, predicate, eachFunc);
3038
+ };
3039
+ }
3040
+
3041
+ module.exports = createFind;
3042
+
3043
+ },{"../lang/isArray":127,"./baseCallback":35,"./baseFind":42,"./baseFindIndex":43}],87:[function(require,module,exports){
3044
+ var baseCallback = require('./baseCallback'),
3045
+ baseFindIndex = require('./baseFindIndex');
3046
+
3047
+ /**
3048
+ * Creates a `_.findIndex` or `_.findLastIndex` function.
3049
+ *
3050
+ * @private
3051
+ * @param {boolean} [fromRight] Specify iterating from right to left.
3052
+ * @returns {Function} Returns the new find function.
3053
+ */
3054
+ function createFindIndex(fromRight) {
3055
+ return function(array, predicate, thisArg) {
3056
+ if (!(array && array.length)) {
3057
+ return -1;
3058
+ }
3059
+ predicate = baseCallback(predicate, thisArg, 3);
3060
+ return baseFindIndex(array, predicate, fromRight);
3061
+ };
3062
+ }
3063
+
3064
+ module.exports = createFindIndex;
3065
+
3066
+ },{"./baseCallback":35,"./baseFindIndex":43}],88:[function(require,module,exports){
3067
+ var bindCallback = require('./bindCallback'),
3068
+ isArray = require('../lang/isArray');
3069
+
3070
+ /**
3071
+ * Creates a function for `_.forEach` or `_.forEachRight`.
3072
+ *
3073
+ * @private
3074
+ * @param {Function} arrayFunc The function to iterate over an array.
3075
+ * @param {Function} eachFunc The function to iterate over a collection.
3076
+ * @returns {Function} Returns the new each function.
3077
+ */
3078
+ function createForEach(arrayFunc, eachFunc) {
3079
+ return function(collection, iteratee, thisArg) {
3080
+ return (typeof iteratee == 'function' && thisArg === undefined && isArray(collection))
3081
+ ? arrayFunc(collection, iteratee)
3082
+ : eachFunc(collection, bindCallback(iteratee, thisArg, 3));
3083
+ };
3084
+ }
3085
+
3086
+ module.exports = createForEach;
3087
+
3088
+ },{"../lang/isArray":127,"./bindCallback":71}],89:[function(require,module,exports){
3089
+ (function (global){
3090
+ var arrayCopy = require('./arrayCopy'),
3091
+ composeArgs = require('./composeArgs'),
3092
+ composeArgsRight = require('./composeArgsRight'),
3093
+ createCtorWrapper = require('./createCtorWrapper'),
3094
+ isLaziable = require('./isLaziable'),
3095
+ reorder = require('./reorder'),
3096
+ replaceHolders = require('./replaceHolders'),
3097
+ setData = require('./setData');
3098
+
3099
+ /** Used to compose bitmasks for wrapper metadata. */
3100
+ var BIND_FLAG = 1,
3101
+ BIND_KEY_FLAG = 2,
3102
+ CURRY_BOUND_FLAG = 4,
3103
+ CURRY_FLAG = 8,
3104
+ CURRY_RIGHT_FLAG = 16,
3105
+ PARTIAL_FLAG = 32,
3106
+ PARTIAL_RIGHT_FLAG = 64,
3107
+ ARY_FLAG = 128;
3108
+
3109
+ /* Native method references for those with the same name as other `lodash` methods. */
3110
+ var nativeMax = Math.max;
3111
+
3112
+ /**
3113
+ * Creates a function that wraps `func` and invokes it with optional `this`
3114
+ * binding of, partial application, and currying.
3115
+ *
3116
+ * @private
3117
+ * @param {Function|string} func The function or method name to reference.
3118
+ * @param {number} bitmask The bitmask of flags. See `createWrapper` for more details.
3119
+ * @param {*} [thisArg] The `this` binding of `func`.
3120
+ * @param {Array} [partials] The arguments to prepend to those provided to the new function.
3121
+ * @param {Array} [holders] The `partials` placeholder indexes.
3122
+ * @param {Array} [partialsRight] The arguments to append to those provided to the new function.
3123
+ * @param {Array} [holdersRight] The `partialsRight` placeholder indexes.
3124
+ * @param {Array} [argPos] The argument positions of the new function.
3125
+ * @param {number} [ary] The arity cap of `func`.
3126
+ * @param {number} [arity] The arity of `func`.
3127
+ * @returns {Function} Returns the new wrapped function.
3128
+ */
3129
+ function createHybridWrapper(func, bitmask, thisArg, partials, holders, partialsRight, holdersRight, argPos, ary, arity) {
3130
+ var isAry = bitmask & ARY_FLAG,
3131
+ isBind = bitmask & BIND_FLAG,
3132
+ isBindKey = bitmask & BIND_KEY_FLAG,
3133
+ isCurry = bitmask & CURRY_FLAG,
3134
+ isCurryBound = bitmask & CURRY_BOUND_FLAG,
3135
+ isCurryRight = bitmask & CURRY_RIGHT_FLAG,
3136
+ Ctor = isBindKey ? undefined : createCtorWrapper(func);
3137
+
3138
+ function wrapper() {
3139
+ // Avoid `arguments` object use disqualifying optimizations by
3140
+ // converting it to an array before providing it to other functions.
3141
+ var length = arguments.length,
3142
+ index = length,
3143
+ args = Array(length);
3144
+
3145
+ while (index--) {
3146
+ args[index] = arguments[index];
3147
+ }
3148
+ if (partials) {
3149
+ args = composeArgs(args, partials, holders);
3150
+ }
3151
+ if (partialsRight) {
3152
+ args = composeArgsRight(args, partialsRight, holdersRight);
3153
+ }
3154
+ if (isCurry || isCurryRight) {
3155
+ var placeholder = wrapper.placeholder,
3156
+ argsHolders = replaceHolders(args, placeholder);
3157
+
3158
+ length -= argsHolders.length;
3159
+ if (length < arity) {
3160
+ var newArgPos = argPos ? arrayCopy(argPos) : undefined,
3161
+ newArity = nativeMax(arity - length, 0),
3162
+ newsHolders = isCurry ? argsHolders : undefined,
3163
+ newHoldersRight = isCurry ? undefined : argsHolders,
3164
+ newPartials = isCurry ? args : undefined,
3165
+ newPartialsRight = isCurry ? undefined : args;
3166
+
3167
+ bitmask |= (isCurry ? PARTIAL_FLAG : PARTIAL_RIGHT_FLAG);
3168
+ bitmask &= ~(isCurry ? PARTIAL_RIGHT_FLAG : PARTIAL_FLAG);
3169
+
3170
+ if (!isCurryBound) {
3171
+ bitmask &= ~(BIND_FLAG | BIND_KEY_FLAG);
3172
+ }
3173
+ var newData = [func, bitmask, thisArg, newPartials, newsHolders, newPartialsRight, newHoldersRight, newArgPos, ary, newArity],
3174
+ result = createHybridWrapper.apply(undefined, newData);
3175
+
3176
+ if (isLaziable(func)) {
3177
+ setData(result, newData);
3178
+ }
3179
+ result.placeholder = placeholder;
3180
+ return result;
3181
+ }
3182
+ }
3183
+ var thisBinding = isBind ? thisArg : this,
3184
+ fn = isBindKey ? thisBinding[func] : func;
3185
+
3186
+ if (argPos) {
3187
+ args = reorder(args, argPos);
3188
+ }
3189
+ if (isAry && ary < args.length) {
3190
+ args.length = ary;
3191
+ }
3192
+ if (this && this !== global && this instanceof wrapper) {
3193
+ fn = Ctor || createCtorWrapper(func);
3194
+ }
3195
+ return fn.apply(thisBinding, args);
3196
+ }
3197
+ return wrapper;
3198
+ }
3199
+
3200
+ module.exports = createHybridWrapper;
3201
+
3202
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
3203
+ },{"./arrayCopy":24,"./composeArgs":77,"./composeArgsRight":78,"./createCtorWrapper":84,"./isLaziable":106,"./reorder":116,"./replaceHolders":117,"./setData":118}],90:[function(require,module,exports){
3204
+ (function (global){
3205
+ var createCtorWrapper = require('./createCtorWrapper');
3206
+
3207
+ /** Used to compose bitmasks for wrapper metadata. */
3208
+ var BIND_FLAG = 1;
3209
+
3210
+ /**
3211
+ * Creates a function that wraps `func` and invokes it with the optional `this`
3212
+ * binding of `thisArg` and the `partials` prepended to those provided to
3213
+ * the wrapper.
3214
+ *
3215
+ * @private
3216
+ * @param {Function} func The function to partially apply arguments to.
3217
+ * @param {number} bitmask The bitmask of flags. See `createWrapper` for more details.
3218
+ * @param {*} thisArg The `this` binding of `func`.
3219
+ * @param {Array} partials The arguments to prepend to those provided to the new function.
3220
+ * @returns {Function} Returns the new bound function.
3221
+ */
3222
+ function createPartialWrapper(func, bitmask, thisArg, partials) {
3223
+ var isBind = bitmask & BIND_FLAG,
3224
+ Ctor = createCtorWrapper(func);
3225
+
3226
+ function wrapper() {
3227
+ // Avoid `arguments` object use disqualifying optimizations by
3228
+ // converting it to an array before providing it `func`.
3229
+ var argsIndex = -1,
3230
+ argsLength = arguments.length,
3231
+ leftIndex = -1,
3232
+ leftLength = partials.length,
3233
+ args = Array(leftLength + argsLength);
3234
+
3235
+ while (++leftIndex < leftLength) {
3236
+ args[leftIndex] = partials[leftIndex];
3237
+ }
3238
+ while (argsLength--) {
3239
+ args[leftIndex++] = arguments[++argsIndex];
3240
+ }
3241
+ var fn = (this && this !== global && this instanceof wrapper) ? Ctor : func;
3242
+ return fn.apply(isBind ? thisArg : this, args);
3243
+ }
3244
+ return wrapper;
3245
+ }
3246
+
3247
+ module.exports = createPartialWrapper;
3248
+
3249
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
3250
+ },{"./createCtorWrapper":84}],91:[function(require,module,exports){
3251
+ var baseCallback = require('./baseCallback'),
3252
+ baseReduce = require('./baseReduce'),
3253
+ isArray = require('../lang/isArray');
3254
+
3255
+ /**
3256
+ * Creates a function for `_.reduce` or `_.reduceRight`.
3257
+ *
3258
+ * @private
3259
+ * @param {Function} arrayFunc The function to iterate over an array.
3260
+ * @param {Function} eachFunc The function to iterate over a collection.
3261
+ * @returns {Function} Returns the new each function.
3262
+ */
3263
+ function createReduce(arrayFunc, eachFunc) {
3264
+ return function(collection, iteratee, accumulator, thisArg) {
3265
+ var initFromArray = arguments.length < 3;
3266
+ return (typeof iteratee == 'function' && thisArg === undefined && isArray(collection))
3267
+ ? arrayFunc(collection, iteratee, accumulator, initFromArray)
3268
+ : baseReduce(collection, baseCallback(iteratee, thisArg, 4), accumulator, initFromArray, eachFunc);
3269
+ };
3270
+ }
3271
+
3272
+ module.exports = createReduce;
3273
+
3274
+ },{"../lang/isArray":127,"./baseCallback":35,"./baseReduce":61}],92:[function(require,module,exports){
3275
+ var baseSetData = require('./baseSetData'),
3276
+ createBindWrapper = require('./createBindWrapper'),
3277
+ createHybridWrapper = require('./createHybridWrapper'),
3278
+ createPartialWrapper = require('./createPartialWrapper'),
3279
+ getData = require('./getData'),
3280
+ mergeData = require('./mergeData'),
3281
+ setData = require('./setData');
3282
+
3283
+ /** Used to compose bitmasks for wrapper metadata. */
3284
+ var BIND_FLAG = 1,
3285
+ BIND_KEY_FLAG = 2,
3286
+ PARTIAL_FLAG = 32,
3287
+ PARTIAL_RIGHT_FLAG = 64;
3288
+
3289
+ /** Used as the `TypeError` message for "Functions" methods. */
3290
+ var FUNC_ERROR_TEXT = 'Expected a function';
3291
+
3292
+ /* Native method references for those with the same name as other `lodash` methods. */
3293
+ var nativeMax = Math.max;
3294
+
3295
+ /**
3296
+ * Creates a function that either curries or invokes `func` with optional
3297
+ * `this` binding and partially applied arguments.
3298
+ *
3299
+ * @private
3300
+ * @param {Function|string} func The function or method name to reference.
3301
+ * @param {number} bitmask The bitmask of flags.
3302
+ * The bitmask may be composed of the following flags:
3303
+ * 1 - `_.bind`
3304
+ * 2 - `_.bindKey`
3305
+ * 4 - `_.curry` or `_.curryRight` of a bound function
3306
+ * 8 - `_.curry`
3307
+ * 16 - `_.curryRight`
3308
+ * 32 - `_.partial`
3309
+ * 64 - `_.partialRight`
3310
+ * 128 - `_.rearg`
3311
+ * 256 - `_.ary`
3312
+ * @param {*} [thisArg] The `this` binding of `func`.
3313
+ * @param {Array} [partials] The arguments to be partially applied.
3314
+ * @param {Array} [holders] The `partials` placeholder indexes.
3315
+ * @param {Array} [argPos] The argument positions of the new function.
3316
+ * @param {number} [ary] The arity cap of `func`.
3317
+ * @param {number} [arity] The arity of `func`.
3318
+ * @returns {Function} Returns the new wrapped function.
3319
+ */
3320
+ function createWrapper(func, bitmask, thisArg, partials, holders, argPos, ary, arity) {
3321
+ var isBindKey = bitmask & BIND_KEY_FLAG;
3322
+ if (!isBindKey && typeof func != 'function') {
3323
+ throw new TypeError(FUNC_ERROR_TEXT);
3324
+ }
3325
+ var length = partials ? partials.length : 0;
3326
+ if (!length) {
3327
+ bitmask &= ~(PARTIAL_FLAG | PARTIAL_RIGHT_FLAG);
3328
+ partials = holders = undefined;
3329
+ }
3330
+ length -= (holders ? holders.length : 0);
3331
+ if (bitmask & PARTIAL_RIGHT_FLAG) {
3332
+ var partialsRight = partials,
3333
+ holdersRight = holders;
3334
+
3335
+ partials = holders = undefined;
3336
+ }
3337
+ var data = isBindKey ? undefined : getData(func),
3338
+ newData = [func, bitmask, thisArg, partials, holders, partialsRight, holdersRight, argPos, ary, arity];
3339
+
3340
+ if (data) {
3341
+ mergeData(newData, data);
3342
+ bitmask = newData[1];
3343
+ arity = newData[9];
3344
+ }
3345
+ newData[9] = arity == null
3346
+ ? (isBindKey ? 0 : func.length)
3347
+ : (nativeMax(arity - length, 0) || 0);
3348
+
3349
+ if (bitmask == BIND_FLAG) {
3350
+ var result = createBindWrapper(newData[0], newData[2]);
3351
+ } else if ((bitmask == PARTIAL_FLAG || bitmask == (BIND_FLAG | PARTIAL_FLAG)) && !newData[4].length) {
3352
+ result = createPartialWrapper.apply(undefined, newData);
3353
+ } else {
3354
+ result = createHybridWrapper.apply(undefined, newData);
3355
+ }
3356
+ var setter = data ? baseSetData : setData;
3357
+ return setter(result, newData);
3358
+ }
3359
+
3360
+ module.exports = createWrapper;
3361
+
3362
+ },{"./baseSetData":62,"./createBindWrapper":82,"./createHybridWrapper":89,"./createPartialWrapper":90,"./getData":96,"./mergeData":111,"./setData":118}],93:[function(require,module,exports){
3363
+ var arraySome = require('./arraySome');
3364
+
3365
+ /**
3366
+ * A specialized version of `baseIsEqualDeep` for arrays with support for
3367
+ * partial deep comparisons.
3368
+ *
3369
+ * @private
3370
+ * @param {Array} array The array to compare.
3371
+ * @param {Array} other The other array to compare.
3372
+ * @param {Function} equalFunc The function to determine equivalents of values.
3373
+ * @param {Function} [customizer] The function to customize comparing arrays.
3374
+ * @param {boolean} [isLoose] Specify performing partial comparisons.
3375
+ * @param {Array} [stackA] Tracks traversed `value` objects.
3376
+ * @param {Array} [stackB] Tracks traversed `other` objects.
3377
+ * @returns {boolean} Returns `true` if the arrays are equivalent, else `false`.
3378
+ */
3379
+ function equalArrays(array, other, equalFunc, customizer, isLoose, stackA, stackB) {
3380
+ var index = -1,
3381
+ arrLength = array.length,
3382
+ othLength = other.length;
3383
+
3384
+ if (arrLength != othLength && !(isLoose && othLength > arrLength)) {
3385
+ return false;
3386
+ }
3387
+ // Ignore non-index properties.
3388
+ while (++index < arrLength) {
3389
+ var arrValue = array[index],
3390
+ othValue = other[index],
3391
+ result = customizer ? customizer(isLoose ? othValue : arrValue, isLoose ? arrValue : othValue, index) : undefined;
3392
+
3393
+ if (result !== undefined) {
3394
+ if (result) {
3395
+ continue;
3396
+ }
3397
+ return false;
3398
+ }
3399
+ // Recursively compare arrays (susceptible to call stack limits).
3400
+ if (isLoose) {
3401
+ if (!arraySome(other, function(othValue) {
3402
+ return arrValue === othValue || equalFunc(arrValue, othValue, customizer, isLoose, stackA, stackB);
3403
+ })) {
3404
+ return false;
3405
+ }
3406
+ } else if (!(arrValue === othValue || equalFunc(arrValue, othValue, customizer, isLoose, stackA, stackB))) {
3407
+ return false;
3408
+ }
3409
+ }
3410
+ return true;
3411
+ }
3412
+
3413
+ module.exports = equalArrays;
3414
+
3415
+ },{"./arraySome":30}],94:[function(require,module,exports){
3416
+ /** `Object#toString` result references. */
3417
+ var boolTag = '[object Boolean]',
3418
+ dateTag = '[object Date]',
3419
+ errorTag = '[object Error]',
3420
+ numberTag = '[object Number]',
3421
+ regexpTag = '[object RegExp]',
3422
+ stringTag = '[object String]';
3423
+
3424
+ /**
3425
+ * A specialized version of `baseIsEqualDeep` for comparing objects of
3426
+ * the same `toStringTag`.
3427
+ *
3428
+ * **Note:** This function only supports comparing values with tags of
3429
+ * `Boolean`, `Date`, `Error`, `Number`, `RegExp`, or `String`.
3430
+ *
3431
+ * @private
3432
+ * @param {Object} object The object to compare.
3433
+ * @param {Object} other The other object to compare.
3434
+ * @param {string} tag The `toStringTag` of the objects to compare.
3435
+ * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
3436
+ */
3437
+ function equalByTag(object, other, tag) {
3438
+ switch (tag) {
3439
+ case boolTag:
3440
+ case dateTag:
3441
+ // Coerce dates and booleans to numbers, dates to milliseconds and booleans
3442
+ // to `1` or `0` treating invalid dates coerced to `NaN` as not equal.
3443
+ return +object == +other;
3444
+
3445
+ case errorTag:
3446
+ return object.name == other.name && object.message == other.message;
3447
+
3448
+ case numberTag:
3449
+ // Treat `NaN` vs. `NaN` as equal.
3450
+ return (object != +object)
3451
+ ? other != +other
3452
+ : object == +other;
3453
+
3454
+ case regexpTag:
3455
+ case stringTag:
3456
+ // Coerce regexes to strings and treat strings primitives and string
3457
+ // objects as equal. See https://es5.github.io/#x15.10.6.4 for more details.
3458
+ return object == (other + '');
3459
+ }
3460
+ return false;
3461
+ }
3462
+
3463
+ module.exports = equalByTag;
3464
+
3465
+ },{}],95:[function(require,module,exports){
3466
+ var keys = require('../object/keys');
3467
+
3468
+ /** Used for native method references. */
3469
+ var objectProto = Object.prototype;
3470
+
3471
+ /** Used to check objects for own properties. */
3472
+ var hasOwnProperty = objectProto.hasOwnProperty;
3473
+
3474
+ /**
3475
+ * A specialized version of `baseIsEqualDeep` for objects with support for
3476
+ * partial deep comparisons.
3477
+ *
3478
+ * @private
3479
+ * @param {Object} object The object to compare.
3480
+ * @param {Object} other The other object to compare.
3481
+ * @param {Function} equalFunc The function to determine equivalents of values.
3482
+ * @param {Function} [customizer] The function to customize comparing values.
3483
+ * @param {boolean} [isLoose] Specify performing partial comparisons.
3484
+ * @param {Array} [stackA] Tracks traversed `value` objects.
3485
+ * @param {Array} [stackB] Tracks traversed `other` objects.
3486
+ * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
3487
+ */
3488
+ function equalObjects(object, other, equalFunc, customizer, isLoose, stackA, stackB) {
3489
+ var objProps = keys(object),
3490
+ objLength = objProps.length,
3491
+ othProps = keys(other),
3492
+ othLength = othProps.length;
3493
+
3494
+ if (objLength != othLength && !isLoose) {
3495
+ return false;
3496
+ }
3497
+ var index = objLength;
3498
+ while (index--) {
3499
+ var key = objProps[index];
3500
+ if (!(isLoose ? key in other : hasOwnProperty.call(other, key))) {
3501
+ return false;
3502
+ }
3503
+ }
3504
+ var skipCtor = isLoose;
3505
+ while (++index < objLength) {
3506
+ key = objProps[index];
3507
+ var objValue = object[key],
3508
+ othValue = other[key],
3509
+ result = customizer ? customizer(isLoose ? othValue : objValue, isLoose? objValue : othValue, key) : undefined;
3510
+
3511
+ // Recursively compare objects (susceptible to call stack limits).
3512
+ if (!(result === undefined ? equalFunc(objValue, othValue, customizer, isLoose, stackA, stackB) : result)) {
3513
+ return false;
3514
+ }
3515
+ skipCtor || (skipCtor = key == 'constructor');
3516
+ }
3517
+ if (!skipCtor) {
3518
+ var objCtor = object.constructor,
3519
+ othCtor = other.constructor;
3520
+
3521
+ // Non `Object` object instances with different constructors are not equal.
3522
+ if (objCtor != othCtor &&
3523
+ ('constructor' in object && 'constructor' in other) &&
3524
+ !(typeof objCtor == 'function' && objCtor instanceof objCtor &&
3525
+ typeof othCtor == 'function' && othCtor instanceof othCtor)) {
3526
+ return false;
3527
+ }
3528
+ }
3529
+ return true;
3530
+ }
3531
+
3532
+ module.exports = equalObjects;
3533
+
3534
+ },{"../object/keys":140}],96:[function(require,module,exports){
3535
+ var metaMap = require('./metaMap'),
3536
+ noop = require('../utility/noop');
3537
+
3538
+ /**
3539
+ * Gets metadata for `func`.
3540
+ *
3541
+ * @private
3542
+ * @param {Function} func The function to query.
3543
+ * @returns {*} Returns the metadata for `func`.
3544
+ */
3545
+ var getData = !metaMap ? noop : function(func) {
3546
+ return metaMap.get(func);
3547
+ };
3548
+
3549
+ module.exports = getData;
3550
+
3551
+ },{"../utility/noop":149,"./metaMap":112}],97:[function(require,module,exports){
3552
+ var realNames = require('./realNames');
3553
+
3554
+ /**
3555
+ * Gets the name of `func`.
3556
+ *
3557
+ * @private
3558
+ * @param {Function} func The function to query.
3559
+ * @returns {string} Returns the function name.
3560
+ */
3561
+ function getFuncName(func) {
3562
+ var result = func.name,
3563
+ array = realNames[result],
3564
+ length = array ? array.length : 0;
3565
+
3566
+ while (length--) {
3567
+ var data = array[length],
3568
+ otherFunc = data.func;
3569
+ if (otherFunc == null || otherFunc == func) {
3570
+ return data.name;
3571
+ }
3572
+ }
3573
+ return result;
3574
+ }
3575
+
3576
+ module.exports = getFuncName;
3577
+
3578
+ },{"./realNames":115}],98:[function(require,module,exports){
3579
+ var baseProperty = require('./baseProperty');
3580
+
3581
+ /**
3582
+ * Gets the "length" property value of `object`.
3583
+ *
3584
+ * **Note:** This function is used to avoid a [JIT bug](https://bugs.webkit.org/show_bug.cgi?id=142792)
3585
+ * that affects Safari on at least iOS 8.1-8.3 ARM64.
3586
+ *
3587
+ * @private
3588
+ * @param {Object} object The object to query.
3589
+ * @returns {*} Returns the "length" value.
3590
+ */
3591
+ var getLength = baseProperty('length');
3592
+
3593
+ module.exports = getLength;
3594
+
3595
+ },{"./baseProperty":59}],99:[function(require,module,exports){
3596
+ var isStrictComparable = require('./isStrictComparable'),
3597
+ pairs = require('../object/pairs');
3598
+
3599
+ /**
3600
+ * Gets the propery names, values, and compare flags of `object`.
3601
+ *
3602
+ * @private
3603
+ * @param {Object} object The object to query.
3604
+ * @returns {Array} Returns the match data of `object`.
3605
+ */
3606
+ function getMatchData(object) {
3607
+ var result = pairs(object),
3608
+ length = result.length;
3609
+
3610
+ while (length--) {
3611
+ result[length][2] = isStrictComparable(result[length][1]);
3612
+ }
3613
+ return result;
3614
+ }
3615
+
3616
+ module.exports = getMatchData;
3617
+
3618
+ },{"../object/pairs":144,"./isStrictComparable":110}],100:[function(require,module,exports){
3619
+ var isNative = require('../lang/isNative');
3620
+
3621
+ /**
3622
+ * Gets the native function at `key` of `object`.
3623
+ *
3624
+ * @private
3625
+ * @param {Object} object The object to query.
3626
+ * @param {string} key The key of the method to get.
3627
+ * @returns {*} Returns the function if it's native, else `undefined`.
3628
+ */
3629
+ function getNative(object, key) {
3630
+ var value = object == null ? undefined : object[key];
3631
+ return isNative(value) ? value : undefined;
3632
+ }
3633
+
3634
+ module.exports = getNative;
3635
+
3636
+ },{"../lang/isNative":130}],101:[function(require,module,exports){
3637
+ /**
3638
+ * Gets the index at which the first occurrence of `NaN` is found in `array`.
3639
+ *
3640
+ * @private
3641
+ * @param {Array} array The array to search.
3642
+ * @param {number} fromIndex The index to search from.
3643
+ * @param {boolean} [fromRight] Specify iterating from right to left.
3644
+ * @returns {number} Returns the index of the matched `NaN`, else `-1`.
3645
+ */
3646
+ function indexOfNaN(array, fromIndex, fromRight) {
3647
+ var length = array.length,
3648
+ index = fromIndex + (fromRight ? 0 : -1);
3649
+
3650
+ while ((fromRight ? index-- : ++index < length)) {
3651
+ var other = array[index];
3652
+ if (other !== other) {
3653
+ return index;
3654
+ }
3655
+ }
3656
+ return -1;
3657
+ }
3658
+
3659
+ module.exports = indexOfNaN;
3660
+
3661
+ },{}],102:[function(require,module,exports){
3662
+ var getLength = require('./getLength'),
3663
+ isLength = require('./isLength');
3664
+
3665
+ /**
3666
+ * Checks if `value` is array-like.
3667
+ *
3668
+ * @private
3669
+ * @param {*} value The value to check.
3670
+ * @returns {boolean} Returns `true` if `value` is array-like, else `false`.
3671
+ */
3672
+ function isArrayLike(value) {
3673
+ return value != null && isLength(getLength(value));
3674
+ }
3675
+
3676
+ module.exports = isArrayLike;
3677
+
3678
+ },{"./getLength":98,"./isLength":107}],103:[function(require,module,exports){
3679
+ /** Used to detect unsigned integer values. */
3680
+ var reIsUint = /^\d+$/;
3681
+
3682
+ /**
3683
+ * Used as the [maximum length](http://ecma-international.org/ecma-262/6.0/#sec-number.max_safe_integer)
3684
+ * of an array-like value.
3685
+ */
3686
+ var MAX_SAFE_INTEGER = 9007199254740991;
3687
+
3688
+ /**
3689
+ * Checks if `value` is a valid array-like index.
3690
+ *
3691
+ * @private
3692
+ * @param {*} value The value to check.
3693
+ * @param {number} [length=MAX_SAFE_INTEGER] The upper bounds of a valid index.
3694
+ * @returns {boolean} Returns `true` if `value` is a valid index, else `false`.
3695
+ */
3696
+ function isIndex(value, length) {
3697
+ value = (typeof value == 'number' || reIsUint.test(value)) ? +value : -1;
3698
+ length = length == null ? MAX_SAFE_INTEGER : length;
3699
+ return value > -1 && value % 1 == 0 && value < length;
3700
+ }
3701
+
3702
+ module.exports = isIndex;
3703
+
3704
+ },{}],104:[function(require,module,exports){
3705
+ var isArrayLike = require('./isArrayLike'),
3706
+ isIndex = require('./isIndex'),
3707
+ isObject = require('../lang/isObject');
3708
+
3709
+ /**
3710
+ * Checks if the provided arguments are from an iteratee call.
3711
+ *
3712
+ * @private
3713
+ * @param {*} value The potential iteratee value argument.
3714
+ * @param {*} index The potential iteratee index or key argument.
3715
+ * @param {*} object The potential iteratee object argument.
3716
+ * @returns {boolean} Returns `true` if the arguments are from an iteratee call, else `false`.
3717
+ */
3718
+ function isIterateeCall(value, index, object) {
3719
+ if (!isObject(object)) {
3720
+ return false;
3721
+ }
3722
+ var type = typeof index;
3723
+ if (type == 'number'
3724
+ ? (isArrayLike(object) && isIndex(index, object.length))
3725
+ : (type == 'string' && index in object)) {
3726
+ var other = object[index];
3727
+ return value === value ? (value === other) : (other !== other);
3728
+ }
3729
+ return false;
3730
+ }
3731
+
3732
+ module.exports = isIterateeCall;
3733
+
3734
+ },{"../lang/isObject":131,"./isArrayLike":102,"./isIndex":103}],105:[function(require,module,exports){
3735
+ var isArray = require('../lang/isArray'),
3736
+ toObject = require('./toObject');
3737
+
3738
+ /** Used to match property names within property paths. */
3739
+ var reIsDeepProp = /\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\n\\]|\\.)*?\1)\]/,
3740
+ reIsPlainProp = /^\w*$/;
3741
+
3742
+ /**
3743
+ * Checks if `value` is a property name and not a property path.
3744
+ *
3745
+ * @private
3746
+ * @param {*} value The value to check.
3747
+ * @param {Object} [object] The object to query keys on.
3748
+ * @returns {boolean} Returns `true` if `value` is a property name, else `false`.
3749
+ */
3750
+ function isKey(value, object) {
3751
+ var type = typeof value;
3752
+ if ((type == 'string' && reIsPlainProp.test(value)) || type == 'number') {
3753
+ return true;
3754
+ }
3755
+ if (isArray(value)) {
3756
+ return false;
3757
+ }
3758
+ var result = !reIsDeepProp.test(value);
3759
+ return result || (object != null && value in toObject(object));
3760
+ }
3761
+
3762
+ module.exports = isKey;
3763
+
3764
+ },{"../lang/isArray":127,"./toObject":121}],106:[function(require,module,exports){
3765
+ var LazyWrapper = require('./LazyWrapper'),
3766
+ getData = require('./getData'),
3767
+ getFuncName = require('./getFuncName'),
3768
+ lodash = require('../chain/lodash');
3769
+
3770
+ /**
3771
+ * Checks if `func` has a lazy counterpart.
3772
+ *
3773
+ * @private
3774
+ * @param {Function} func The function to check.
3775
+ * @returns {boolean} Returns `true` if `func` has a lazy counterpart, else `false`.
3776
+ */
3777
+ function isLaziable(func) {
3778
+ var funcName = getFuncName(func);
3779
+ if (!(funcName in LazyWrapper.prototype)) {
3780
+ return false;
3781
+ }
3782
+ var other = lodash[funcName];
3783
+ if (func === other) {
3784
+ return true;
3785
+ }
3786
+ var data = getData(other);
3787
+ return !!data && func === data[0];
3788
+ }
3789
+
3790
+ module.exports = isLaziable;
3791
+
3792
+ },{"../chain/lodash":8,"./LazyWrapper":21,"./getData":96,"./getFuncName":97}],107:[function(require,module,exports){
3793
+ /**
3794
+ * Used as the [maximum length](http://ecma-international.org/ecma-262/6.0/#sec-number.max_safe_integer)
3795
+ * of an array-like value.
3796
+ */
3797
+ var MAX_SAFE_INTEGER = 9007199254740991;
3798
+
3799
+ /**
3800
+ * Checks if `value` is a valid array-like length.
3801
+ *
3802
+ * **Note:** This function is based on [`ToLength`](http://ecma-international.org/ecma-262/6.0/#sec-tolength).
3803
+ *
3804
+ * @private
3805
+ * @param {*} value The value to check.
3806
+ * @returns {boolean} Returns `true` if `value` is a valid length, else `false`.
3807
+ */
3808
+ function isLength(value) {
3809
+ return typeof value == 'number' && value > -1 && value % 1 == 0 && value <= MAX_SAFE_INTEGER;
3810
+ }
3811
+
3812
+ module.exports = isLength;
3813
+
3814
+ },{}],108:[function(require,module,exports){
3815
+ /**
3816
+ * Checks if `value` is object-like.
3817
+ *
3818
+ * @private
3819
+ * @param {*} value The value to check.
3820
+ * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
3821
+ */
3822
+ function isObjectLike(value) {
3823
+ return !!value && typeof value == 'object';
3824
+ }
3825
+
3826
+ module.exports = isObjectLike;
3827
+
3828
+ },{}],109:[function(require,module,exports){
3829
+ /**
3830
+ * Used by `trimmedLeftIndex` and `trimmedRightIndex` to determine if a
3831
+ * character code is whitespace.
3832
+ *
3833
+ * @private
3834
+ * @param {number} charCode The character code to inspect.
3835
+ * @returns {boolean} Returns `true` if `charCode` is whitespace, else `false`.
3836
+ */
3837
+ function isSpace(charCode) {
3838
+ return ((charCode <= 160 && (charCode >= 9 && charCode <= 13) || charCode == 32 || charCode == 160) || charCode == 5760 || charCode == 6158 ||
3839
+ (charCode >= 8192 && (charCode <= 8202 || charCode == 8232 || charCode == 8233 || charCode == 8239 || charCode == 8287 || charCode == 12288 || charCode == 65279)));
3840
+ }
3841
+
3842
+ module.exports = isSpace;
3843
+
3844
+ },{}],110:[function(require,module,exports){
3845
+ var isObject = require('../lang/isObject');
3846
+
3847
+ /**
3848
+ * Checks if `value` is suitable for strict equality comparisons, i.e. `===`.
3849
+ *
3850
+ * @private
3851
+ * @param {*} value The value to check.
3852
+ * @returns {boolean} Returns `true` if `value` if suitable for strict
3853
+ * equality comparisons, else `false`.
3854
+ */
3855
+ function isStrictComparable(value) {
3856
+ return value === value && !isObject(value);
3857
+ }
3858
+
3859
+ module.exports = isStrictComparable;
3860
+
3861
+ },{"../lang/isObject":131}],111:[function(require,module,exports){
3862
+ var arrayCopy = require('./arrayCopy'),
3863
+ composeArgs = require('./composeArgs'),
3864
+ composeArgsRight = require('./composeArgsRight'),
3865
+ replaceHolders = require('./replaceHolders');
3866
+
3867
+ /** Used to compose bitmasks for wrapper metadata. */
3868
+ var BIND_FLAG = 1,
3869
+ CURRY_BOUND_FLAG = 4,
3870
+ CURRY_FLAG = 8,
3871
+ ARY_FLAG = 128,
3872
+ REARG_FLAG = 256;
3873
+
3874
+ /** Used as the internal argument placeholder. */
3875
+ var PLACEHOLDER = '__lodash_placeholder__';
3876
+
3877
+ /* Native method references for those with the same name as other `lodash` methods. */
3878
+ var nativeMin = Math.min;
3879
+
3880
+ /**
3881
+ * Merges the function metadata of `source` into `data`.
3882
+ *
3883
+ * Merging metadata reduces the number of wrappers required to invoke a function.
3884
+ * This is possible because methods like `_.bind`, `_.curry`, and `_.partial`
3885
+ * may be applied regardless of execution order. Methods like `_.ary` and `_.rearg`
3886
+ * augment function arguments, making the order in which they are executed important,
3887
+ * preventing the merging of metadata. However, we make an exception for a safe
3888
+ * common case where curried functions have `_.ary` and or `_.rearg` applied.
3889
+ *
3890
+ * @private
3891
+ * @param {Array} data The destination metadata.
3892
+ * @param {Array} source The source metadata.
3893
+ * @returns {Array} Returns `data`.
3894
+ */
3895
+ function mergeData(data, source) {
3896
+ var bitmask = data[1],
3897
+ srcBitmask = source[1],
3898
+ newBitmask = bitmask | srcBitmask,
3899
+ isCommon = newBitmask < ARY_FLAG;
3900
+
3901
+ var isCombo =
3902
+ (srcBitmask == ARY_FLAG && bitmask == CURRY_FLAG) ||
3903
+ (srcBitmask == ARY_FLAG && bitmask == REARG_FLAG && data[7].length <= source[8]) ||
3904
+ (srcBitmask == (ARY_FLAG | REARG_FLAG) && bitmask == CURRY_FLAG);
3905
+
3906
+ // Exit early if metadata can't be merged.
3907
+ if (!(isCommon || isCombo)) {
3908
+ return data;
3909
+ }
3910
+ // Use source `thisArg` if available.
3911
+ if (srcBitmask & BIND_FLAG) {
3912
+ data[2] = source[2];
3913
+ // Set when currying a bound function.
3914
+ newBitmask |= (bitmask & BIND_FLAG) ? 0 : CURRY_BOUND_FLAG;
3915
+ }
3916
+ // Compose partial arguments.
3917
+ var value = source[3];
3918
+ if (value) {
3919
+ var partials = data[3];
3920
+ data[3] = partials ? composeArgs(partials, value, source[4]) : arrayCopy(value);
3921
+ data[4] = partials ? replaceHolders(data[3], PLACEHOLDER) : arrayCopy(source[4]);
3922
+ }
3923
+ // Compose partial right arguments.
3924
+ value = source[5];
3925
+ if (value) {
3926
+ partials = data[5];
3927
+ data[5] = partials ? composeArgsRight(partials, value, source[6]) : arrayCopy(value);
3928
+ data[6] = partials ? replaceHolders(data[5], PLACEHOLDER) : arrayCopy(source[6]);
3929
+ }
3930
+ // Use source `argPos` if available.
3931
+ value = source[7];
3932
+ if (value) {
3933
+ data[7] = arrayCopy(value);
3934
+ }
3935
+ // Use source `ary` if it's smaller.
3936
+ if (srcBitmask & ARY_FLAG) {
3937
+ data[8] = data[8] == null ? source[8] : nativeMin(data[8], source[8]);
3938
+ }
3939
+ // Use source `arity` if one is not provided.
3940
+ if (data[9] == null) {
3941
+ data[9] = source[9];
3942
+ }
3943
+ // Use source `func` and merge bitmasks.
3944
+ data[0] = source[0];
3945
+ data[1] = newBitmask;
3946
+
3947
+ return data;
3948
+ }
3949
+
3950
+ module.exports = mergeData;
3951
+
3952
+ },{"./arrayCopy":24,"./composeArgs":77,"./composeArgsRight":78,"./replaceHolders":117}],112:[function(require,module,exports){
3953
+ (function (global){
3954
+ var getNative = require('./getNative');
3955
+
3956
+ /** Native method references. */
3957
+ var WeakMap = getNative(global, 'WeakMap');
3958
+
3959
+ /** Used to store function metadata. */
3960
+ var metaMap = WeakMap && new WeakMap;
3961
+
3962
+ module.exports = metaMap;
3963
+
3964
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
3965
+ },{"./getNative":100}],113:[function(require,module,exports){
3966
+ var toObject = require('./toObject');
3967
+
3968
+ /**
3969
+ * A specialized version of `_.pick` which picks `object` properties specified
3970
+ * by `props`.
3971
+ *
3972
+ * @private
3973
+ * @param {Object} object The source object.
3974
+ * @param {string[]} props The property names to pick.
3975
+ * @returns {Object} Returns the new object.
3976
+ */
3977
+ function pickByArray(object, props) {
3978
+ object = toObject(object);
3979
+
3980
+ var index = -1,
3981
+ length = props.length,
3982
+ result = {};
3983
+
3984
+ while (++index < length) {
3985
+ var key = props[index];
3986
+ if (key in object) {
3987
+ result[key] = object[key];
3988
+ }
3989
+ }
3990
+ return result;
3991
+ }
3992
+
3993
+ module.exports = pickByArray;
3994
+
3995
+ },{"./toObject":121}],114:[function(require,module,exports){
3996
+ var baseForIn = require('./baseForIn');
3997
+
3998
+ /**
3999
+ * A specialized version of `_.pick` which picks `object` properties `predicate`
4000
+ * returns truthy for.
4001
+ *
4002
+ * @private
4003
+ * @param {Object} object The source object.
4004
+ * @param {Function} predicate The function invoked per iteration.
4005
+ * @returns {Object} Returns the new object.
4006
+ */
4007
+ function pickByCallback(object, predicate) {
4008
+ var result = {};
4009
+ baseForIn(object, function(value, key, object) {
4010
+ if (predicate(value, key, object)) {
4011
+ result[key] = value;
4012
+ }
4013
+ });
4014
+ return result;
4015
+ }
4016
+
4017
+ module.exports = pickByCallback;
4018
+
4019
+ },{"./baseForIn":46}],115:[function(require,module,exports){
4020
+ /** Used to lookup unminified function names. */
4021
+ var realNames = {};
4022
+
4023
+ module.exports = realNames;
4024
+
4025
+ },{}],116:[function(require,module,exports){
4026
+ var arrayCopy = require('./arrayCopy'),
4027
+ isIndex = require('./isIndex');
4028
+
4029
+ /* Native method references for those with the same name as other `lodash` methods. */
4030
+ var nativeMin = Math.min;
4031
+
4032
+ /**
4033
+ * Reorder `array` according to the specified indexes where the element at
4034
+ * the first index is assigned as the first element, the element at
4035
+ * the second index is assigned as the second element, and so on.
4036
+ *
4037
+ * @private
4038
+ * @param {Array} array The array to reorder.
4039
+ * @param {Array} indexes The arranged array indexes.
4040
+ * @returns {Array} Returns `array`.
4041
+ */
4042
+ function reorder(array, indexes) {
4043
+ var arrLength = array.length,
4044
+ length = nativeMin(indexes.length, arrLength),
4045
+ oldArray = arrayCopy(array);
4046
+
4047
+ while (length--) {
4048
+ var index = indexes[length];
4049
+ array[length] = isIndex(index, arrLength) ? oldArray[index] : undefined;
4050
+ }
4051
+ return array;
4052
+ }
4053
+
4054
+ module.exports = reorder;
4055
+
4056
+ },{"./arrayCopy":24,"./isIndex":103}],117:[function(require,module,exports){
4057
+ /** Used as the internal argument placeholder. */
4058
+ var PLACEHOLDER = '__lodash_placeholder__';
4059
+
4060
+ /**
4061
+ * Replaces all `placeholder` elements in `array` with an internal placeholder
4062
+ * and returns an array of their indexes.
4063
+ *
4064
+ * @private
4065
+ * @param {Array} array The array to modify.
4066
+ * @param {*} placeholder The placeholder to replace.
4067
+ * @returns {Array} Returns the new array of placeholder indexes.
4068
+ */
4069
+ function replaceHolders(array, placeholder) {
4070
+ var index = -1,
4071
+ length = array.length,
4072
+ resIndex = -1,
4073
+ result = [];
4074
+
4075
+ while (++index < length) {
4076
+ if (array[index] === placeholder) {
4077
+ array[index] = PLACEHOLDER;
4078
+ result[++resIndex] = index;
4079
+ }
4080
+ }
4081
+ return result;
4082
+ }
4083
+
4084
+ module.exports = replaceHolders;
4085
+
4086
+ },{}],118:[function(require,module,exports){
4087
+ var baseSetData = require('./baseSetData'),
4088
+ now = require('../date/now');
4089
+
4090
+ /** Used to detect when a function becomes hot. */
4091
+ var HOT_COUNT = 150,
4092
+ HOT_SPAN = 16;
4093
+
4094
+ /**
4095
+ * Sets metadata for `func`.
4096
+ *
4097
+ * **Note:** If this function becomes hot, i.e. is invoked a lot in a short
4098
+ * period of time, it will trip its breaker and transition to an identity function
4099
+ * to avoid garbage collection pauses in V8. See [V8 issue 2070](https://code.google.com/p/v8/issues/detail?id=2070)
4100
+ * for more details.
4101
+ *
4102
+ * @private
4103
+ * @param {Function} func The function to associate metadata with.
4104
+ * @param {*} data The metadata.
4105
+ * @returns {Function} Returns `func`.
4106
+ */
4107
+ var setData = (function() {
4108
+ var count = 0,
4109
+ lastCalled = 0;
4110
+
4111
+ return function(key, value) {
4112
+ var stamp = now(),
4113
+ remaining = HOT_SPAN - (stamp - lastCalled);
4114
+
4115
+ lastCalled = stamp;
4116
+ if (remaining > 0) {
4117
+ if (++count >= HOT_COUNT) {
4118
+ return key;
4119
+ }
4120
+ } else {
4121
+ count = 0;
4122
+ }
4123
+ return baseSetData(key, value);
4124
+ };
4125
+ }());
4126
+
4127
+ module.exports = setData;
4128
+
4129
+ },{"../date/now":18,"./baseSetData":62}],119:[function(require,module,exports){
4130
+ var isArguments = require('../lang/isArguments'),
4131
+ isArray = require('../lang/isArray'),
4132
+ isIndex = require('./isIndex'),
4133
+ isLength = require('./isLength'),
4134
+ keysIn = require('../object/keysIn');
4135
+
4136
+ /** Used for native method references. */
4137
+ var objectProto = Object.prototype;
4138
+
4139
+ /** Used to check objects for own properties. */
4140
+ var hasOwnProperty = objectProto.hasOwnProperty;
4141
+
4142
+ /**
4143
+ * A fallback implementation of `Object.keys` which creates an array of the
4144
+ * own enumerable property names of `object`.
4145
+ *
4146
+ * @private
4147
+ * @param {Object} object The object to query.
4148
+ * @returns {Array} Returns the array of property names.
4149
+ */
4150
+ function shimKeys(object) {
4151
+ var props = keysIn(object),
4152
+ propsLength = props.length,
4153
+ length = propsLength && object.length;
4154
+
4155
+ var allowIndexes = !!length && isLength(length) &&
4156
+ (isArray(object) || isArguments(object));
4157
+
4158
+ var index = -1,
4159
+ result = [];
4160
+
4161
+ while (++index < propsLength) {
4162
+ var key = props[index];
4163
+ if ((allowIndexes && isIndex(key, length)) || hasOwnProperty.call(object, key)) {
4164
+ result.push(key);
4165
+ }
4166
+ }
4167
+ return result;
4168
+ }
4169
+
4170
+ module.exports = shimKeys;
4171
+
4172
+ },{"../lang/isArguments":126,"../lang/isArray":127,"../object/keysIn":141,"./isIndex":103,"./isLength":107}],120:[function(require,module,exports){
4173
+ var isArrayLike = require('./isArrayLike'),
4174
+ isObject = require('../lang/isObject'),
4175
+ values = require('../object/values');
4176
+
4177
+ /**
4178
+ * Converts `value` to an array-like object if it's not one.
4179
+ *
4180
+ * @private
4181
+ * @param {*} value The value to process.
4182
+ * @returns {Array|Object} Returns the array-like object.
4183
+ */
4184
+ function toIterable(value) {
4185
+ if (value == null) {
4186
+ return [];
4187
+ }
4188
+ if (!isArrayLike(value)) {
4189
+ return values(value);
4190
+ }
4191
+ return isObject(value) ? value : Object(value);
4192
+ }
4193
+
4194
+ module.exports = toIterable;
4195
+
4196
+ },{"../lang/isObject":131,"../object/values":146,"./isArrayLike":102}],121:[function(require,module,exports){
4197
+ var isObject = require('../lang/isObject');
4198
+
4199
+ /**
4200
+ * Converts `value` to an object if it's not one.
4201
+ *
4202
+ * @private
4203
+ * @param {*} value The value to process.
4204
+ * @returns {Object} Returns the object.
4205
+ */
4206
+ function toObject(value) {
4207
+ return isObject(value) ? value : Object(value);
4208
+ }
4209
+
4210
+ module.exports = toObject;
4211
+
4212
+ },{"../lang/isObject":131}],122:[function(require,module,exports){
4213
+ var baseToString = require('./baseToString'),
4214
+ isArray = require('../lang/isArray');
4215
+
4216
+ /** Used to match property names within property paths. */
4217
+ var rePropName = /[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\n\\]|\\.)*?)\2)\]/g;
4218
+
4219
+ /** Used to match backslashes in property paths. */
4220
+ var reEscapeChar = /\\(\\)?/g;
4221
+
4222
+ /**
4223
+ * Converts `value` to property path array if it's not one.
4224
+ *
4225
+ * @private
4226
+ * @param {*} value The value to process.
4227
+ * @returns {Array} Returns the property path array.
4228
+ */
4229
+ function toPath(value) {
4230
+ if (isArray(value)) {
4231
+ return value;
4232
+ }
4233
+ var result = [];
4234
+ baseToString(value).replace(rePropName, function(match, number, quote, string) {
4235
+ result.push(quote ? string.replace(reEscapeChar, '$1') : (number || match));
4236
+ });
4237
+ return result;
4238
+ }
4239
+
4240
+ module.exports = toPath;
4241
+
4242
+ },{"../lang/isArray":127,"./baseToString":67}],123:[function(require,module,exports){
4243
+ var isSpace = require('./isSpace');
4244
+
4245
+ /**
4246
+ * Used by `_.trim` and `_.trimLeft` to get the index of the first non-whitespace
4247
+ * character of `string`.
4248
+ *
4249
+ * @private
4250
+ * @param {string} string The string to inspect.
4251
+ * @returns {number} Returns the index of the first non-whitespace character.
4252
+ */
4253
+ function trimmedLeftIndex(string) {
4254
+ var index = -1,
4255
+ length = string.length;
4256
+
4257
+ while (++index < length && isSpace(string.charCodeAt(index))) {}
4258
+ return index;
4259
+ }
4260
+
4261
+ module.exports = trimmedLeftIndex;
4262
+
4263
+ },{"./isSpace":109}],124:[function(require,module,exports){
4264
+ var isSpace = require('./isSpace');
4265
+
4266
+ /**
4267
+ * Used by `_.trim` and `_.trimRight` to get the index of the last non-whitespace
4268
+ * character of `string`.
4269
+ *
4270
+ * @private
4271
+ * @param {string} string The string to inspect.
4272
+ * @returns {number} Returns the index of the last non-whitespace character.
4273
+ */
4274
+ function trimmedRightIndex(string) {
4275
+ var index = string.length;
4276
+
4277
+ while (index-- && isSpace(string.charCodeAt(index))) {}
4278
+ return index;
4279
+ }
4280
+
4281
+ module.exports = trimmedRightIndex;
4282
+
4283
+ },{"./isSpace":109}],125:[function(require,module,exports){
4284
+ var LazyWrapper = require('./LazyWrapper'),
4285
+ LodashWrapper = require('./LodashWrapper'),
4286
+ arrayCopy = require('./arrayCopy');
4287
+
4288
+ /**
4289
+ * Creates a clone of `wrapper`.
4290
+ *
4291
+ * @private
4292
+ * @param {Object} wrapper The wrapper to clone.
4293
+ * @returns {Object} Returns the cloned wrapper.
4294
+ */
4295
+ function wrapperClone(wrapper) {
4296
+ return wrapper instanceof LazyWrapper
4297
+ ? wrapper.clone()
4298
+ : new LodashWrapper(wrapper.__wrapped__, wrapper.__chain__, arrayCopy(wrapper.__actions__));
4299
+ }
4300
+
4301
+ module.exports = wrapperClone;
4302
+
4303
+ },{"./LazyWrapper":21,"./LodashWrapper":22,"./arrayCopy":24}],126:[function(require,module,exports){
4304
+ var isArrayLike = require('../internal/isArrayLike'),
4305
+ isObjectLike = require('../internal/isObjectLike');
4306
+
4307
+ /** Used for native method references. */
4308
+ var objectProto = Object.prototype;
4309
+
4310
+ /** Used to check objects for own properties. */
4311
+ var hasOwnProperty = objectProto.hasOwnProperty;
4312
+
4313
+ /** Native method references. */
4314
+ var propertyIsEnumerable = objectProto.propertyIsEnumerable;
4315
+
4316
+ /**
4317
+ * Checks if `value` is classified as an `arguments` object.
4318
+ *
4319
+ * @static
4320
+ * @memberOf _
4321
+ * @category Lang
4322
+ * @param {*} value The value to check.
4323
+ * @returns {boolean} Returns `true` if `value` is correctly classified, else `false`.
4324
+ * @example
4325
+ *
4326
+ * _.isArguments(function() { return arguments; }());
4327
+ * // => true
4328
+ *
4329
+ * _.isArguments([1, 2, 3]);
4330
+ * // => false
4331
+ */
4332
+ function isArguments(value) {
4333
+ return isObjectLike(value) && isArrayLike(value) &&
4334
+ hasOwnProperty.call(value, 'callee') && !propertyIsEnumerable.call(value, 'callee');
4335
+ }
4336
+
4337
+ module.exports = isArguments;
4338
+
4339
+ },{"../internal/isArrayLike":102,"../internal/isObjectLike":108}],127:[function(require,module,exports){
4340
+ var getNative = require('../internal/getNative'),
4341
+ isLength = require('../internal/isLength'),
4342
+ isObjectLike = require('../internal/isObjectLike');
4343
+
4344
+ /** `Object#toString` result references. */
4345
+ var arrayTag = '[object Array]';
4346
+
4347
+ /** Used for native method references. */
4348
+ var objectProto = Object.prototype;
4349
+
4350
+ /**
4351
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
4352
+ * of values.
4353
+ */
4354
+ var objToString = objectProto.toString;
4355
+
4356
+ /* Native method references for those with the same name as other `lodash` methods. */
4357
+ var nativeIsArray = getNative(Array, 'isArray');
4358
+
4359
+ /**
4360
+ * Checks if `value` is classified as an `Array` object.
4361
+ *
4362
+ * @static
4363
+ * @memberOf _
4364
+ * @category Lang
4365
+ * @param {*} value The value to check.
4366
+ * @returns {boolean} Returns `true` if `value` is correctly classified, else `false`.
4367
+ * @example
4368
+ *
4369
+ * _.isArray([1, 2, 3]);
4370
+ * // => true
4371
+ *
4372
+ * _.isArray(function() { return arguments; }());
4373
+ * // => false
4374
+ */
4375
+ var isArray = nativeIsArray || function(value) {
4376
+ return isObjectLike(value) && isLength(value.length) && objToString.call(value) == arrayTag;
4377
+ };
4378
+
4379
+ module.exports = isArray;
4380
+
4381
+ },{"../internal/getNative":100,"../internal/isLength":107,"../internal/isObjectLike":108}],128:[function(require,module,exports){
4382
+ var isArguments = require('./isArguments'),
4383
+ isArray = require('./isArray'),
4384
+ isArrayLike = require('../internal/isArrayLike'),
4385
+ isFunction = require('./isFunction'),
4386
+ isObjectLike = require('../internal/isObjectLike'),
4387
+ isString = require('./isString'),
4388
+ keys = require('../object/keys');
4389
+
4390
+ /**
4391
+ * Checks if `value` is empty. A value is considered empty unless it is an
4392
+ * `arguments` object, array, string, or jQuery-like collection with a length
4393
+ * greater than `0` or an object with own enumerable properties.
4394
+ *
4395
+ * @static
4396
+ * @memberOf _
4397
+ * @category Lang
4398
+ * @param {Array|Object|string} value The value to inspect.
4399
+ * @returns {boolean} Returns `true` if `value` is empty, else `false`.
4400
+ * @example
4401
+ *
4402
+ * _.isEmpty(null);
4403
+ * // => true
4404
+ *
4405
+ * _.isEmpty(true);
4406
+ * // => true
4407
+ *
4408
+ * _.isEmpty(1);
4409
+ * // => true
4410
+ *
4411
+ * _.isEmpty([1, 2, 3]);
4412
+ * // => false
4413
+ *
4414
+ * _.isEmpty({ 'a': 1 });
4415
+ * // => false
4416
+ */
4417
+ function isEmpty(value) {
4418
+ if (value == null) {
4419
+ return true;
4420
+ }
4421
+ if (isArrayLike(value) && (isArray(value) || isString(value) || isArguments(value) ||
4422
+ (isObjectLike(value) && isFunction(value.splice)))) {
4423
+ return !value.length;
4424
+ }
4425
+ return !keys(value).length;
4426
+ }
4427
+
4428
+ module.exports = isEmpty;
4429
+
4430
+ },{"../internal/isArrayLike":102,"../internal/isObjectLike":108,"../object/keys":140,"./isArguments":126,"./isArray":127,"./isFunction":129,"./isString":133}],129:[function(require,module,exports){
4431
+ var isObject = require('./isObject');
4432
+
4433
+ /** `Object#toString` result references. */
4434
+ var funcTag = '[object Function]';
4435
+
4436
+ /** Used for native method references. */
4437
+ var objectProto = Object.prototype;
4438
+
4439
+ /**
4440
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
4441
+ * of values.
4442
+ */
4443
+ var objToString = objectProto.toString;
4444
+
4445
+ /**
4446
+ * Checks if `value` is classified as a `Function` object.
4447
+ *
4448
+ * @static
4449
+ * @memberOf _
4450
+ * @category Lang
4451
+ * @param {*} value The value to check.
4452
+ * @returns {boolean} Returns `true` if `value` is correctly classified, else `false`.
4453
+ * @example
4454
+ *
4455
+ * _.isFunction(_);
4456
+ * // => true
4457
+ *
4458
+ * _.isFunction(/abc/);
4459
+ * // => false
4460
+ */
4461
+ function isFunction(value) {
4462
+ // The use of `Object#toString` avoids issues with the `typeof` operator
4463
+ // in older versions of Chrome and Safari which return 'function' for regexes
4464
+ // and Safari 8 equivalents which return 'object' for typed array constructors.
4465
+ return isObject(value) && objToString.call(value) == funcTag;
4466
+ }
4467
+
4468
+ module.exports = isFunction;
4469
+
4470
+ },{"./isObject":131}],130:[function(require,module,exports){
4471
+ var isFunction = require('./isFunction'),
4472
+ isObjectLike = require('../internal/isObjectLike');
4473
+
4474
+ /** Used to detect host constructors (Safari > 5). */
4475
+ var reIsHostCtor = /^\[object .+?Constructor\]$/;
4476
+
4477
+ /** Used for native method references. */
4478
+ var objectProto = Object.prototype;
4479
+
4480
+ /** Used to resolve the decompiled source of functions. */
4481
+ var fnToString = Function.prototype.toString;
4482
+
4483
+ /** Used to check objects for own properties. */
4484
+ var hasOwnProperty = objectProto.hasOwnProperty;
4485
+
4486
+ /** Used to detect if a method is native. */
4487
+ var reIsNative = RegExp('^' +
4488
+ fnToString.call(hasOwnProperty).replace(/[\\^$.*+?()[\]{}|]/g, '\\$&')
4489
+ .replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$'
4490
+ );
4491
+
4492
+ /**
4493
+ * Checks if `value` is a native function.
4494
+ *
4495
+ * @static
4496
+ * @memberOf _
4497
+ * @category Lang
4498
+ * @param {*} value The value to check.
4499
+ * @returns {boolean} Returns `true` if `value` is a native function, else `false`.
4500
+ * @example
4501
+ *
4502
+ * _.isNative(Array.prototype.push);
4503
+ * // => true
4504
+ *
4505
+ * _.isNative(_);
4506
+ * // => false
4507
+ */
4508
+ function isNative(value) {
4509
+ if (value == null) {
4510
+ return false;
4511
+ }
4512
+ if (isFunction(value)) {
4513
+ return reIsNative.test(fnToString.call(value));
4514
+ }
4515
+ return isObjectLike(value) && reIsHostCtor.test(value);
4516
+ }
4517
+
4518
+ module.exports = isNative;
4519
+
4520
+ },{"../internal/isObjectLike":108,"./isFunction":129}],131:[function(require,module,exports){
4521
+ /**
4522
+ * Checks if `value` is the [language type](https://es5.github.io/#x8) of `Object`.
4523
+ * (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
4524
+ *
4525
+ * @static
4526
+ * @memberOf _
4527
+ * @category Lang
4528
+ * @param {*} value The value to check.
4529
+ * @returns {boolean} Returns `true` if `value` is an object, else `false`.
4530
+ * @example
4531
+ *
4532
+ * _.isObject({});
4533
+ * // => true
4534
+ *
4535
+ * _.isObject([1, 2, 3]);
4536
+ * // => true
4537
+ *
4538
+ * _.isObject(1);
4539
+ * // => false
4540
+ */
4541
+ function isObject(value) {
4542
+ // Avoid a V8 JIT bug in Chrome 19-20.
4543
+ // See https://code.google.com/p/v8/issues/detail?id=2291 for more details.
4544
+ var type = typeof value;
4545
+ return !!value && (type == 'object' || type == 'function');
4546
+ }
4547
+
4548
+ module.exports = isObject;
4549
+
4550
+ },{}],132:[function(require,module,exports){
4551
+ var baseForIn = require('../internal/baseForIn'),
4552
+ isArguments = require('./isArguments'),
4553
+ isObjectLike = require('../internal/isObjectLike');
4554
+
4555
+ /** `Object#toString` result references. */
4556
+ var objectTag = '[object Object]';
4557
+
4558
+ /** Used for native method references. */
4559
+ var objectProto = Object.prototype;
4560
+
4561
+ /** Used to check objects for own properties. */
4562
+ var hasOwnProperty = objectProto.hasOwnProperty;
4563
+
4564
+ /**
4565
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
4566
+ * of values.
4567
+ */
4568
+ var objToString = objectProto.toString;
4569
+
4570
+ /**
4571
+ * Checks if `value` is a plain object, that is, an object created by the
4572
+ * `Object` constructor or one with a `[[Prototype]]` of `null`.
4573
+ *
4574
+ * **Note:** This method assumes objects created by the `Object` constructor
4575
+ * have no inherited enumerable properties.
4576
+ *
4577
+ * @static
4578
+ * @memberOf _
4579
+ * @category Lang
4580
+ * @param {*} value The value to check.
4581
+ * @returns {boolean} Returns `true` if `value` is a plain object, else `false`.
4582
+ * @example
4583
+ *
4584
+ * function Foo() {
4585
+ * this.a = 1;
4586
+ * }
4587
+ *
4588
+ * _.isPlainObject(new Foo);
4589
+ * // => false
4590
+ *
4591
+ * _.isPlainObject([1, 2, 3]);
4592
+ * // => false
4593
+ *
4594
+ * _.isPlainObject({ 'x': 0, 'y': 0 });
4595
+ * // => true
4596
+ *
4597
+ * _.isPlainObject(Object.create(null));
4598
+ * // => true
4599
+ */
4600
+ function isPlainObject(value) {
4601
+ var Ctor;
4602
+
4603
+ // Exit early for non `Object` objects.
4604
+ if (!(isObjectLike(value) && objToString.call(value) == objectTag && !isArguments(value)) ||
4605
+ (!hasOwnProperty.call(value, 'constructor') && (Ctor = value.constructor, typeof Ctor == 'function' && !(Ctor instanceof Ctor)))) {
4606
+ return false;
4607
+ }
4608
+ // IE < 9 iterates inherited properties before own properties. If the first
4609
+ // iterated property is an object's own property then there are no inherited
4610
+ // enumerable properties.
4611
+ var result;
4612
+ // In most environments an object's own properties are iterated before
4613
+ // its inherited properties. If the last iterated property is an object's
4614
+ // own property then there are no inherited enumerable properties.
4615
+ baseForIn(value, function(subValue, key) {
4616
+ result = key;
4617
+ });
4618
+ return result === undefined || hasOwnProperty.call(value, result);
4619
+ }
4620
+
4621
+ module.exports = isPlainObject;
4622
+
4623
+ },{"../internal/baseForIn":46,"../internal/isObjectLike":108,"./isArguments":126}],133:[function(require,module,exports){
4624
+ var isObjectLike = require('../internal/isObjectLike');
4625
+
4626
+ /** `Object#toString` result references. */
4627
+ var stringTag = '[object String]';
4628
+
4629
+ /** Used for native method references. */
4630
+ var objectProto = Object.prototype;
4631
+
4632
+ /**
4633
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
4634
+ * of values.
4635
+ */
4636
+ var objToString = objectProto.toString;
4637
+
4638
+ /**
4639
+ * Checks if `value` is classified as a `String` primitive or object.
4640
+ *
4641
+ * @static
4642
+ * @memberOf _
4643
+ * @category Lang
4644
+ * @param {*} value The value to check.
4645
+ * @returns {boolean} Returns `true` if `value` is correctly classified, else `false`.
4646
+ * @example
4647
+ *
4648
+ * _.isString('abc');
4649
+ * // => true
4650
+ *
4651
+ * _.isString(1);
4652
+ * // => false
4653
+ */
4654
+ function isString(value) {
4655
+ return typeof value == 'string' || (isObjectLike(value) && objToString.call(value) == stringTag);
4656
+ }
4657
+
4658
+ module.exports = isString;
4659
+
4660
+ },{"../internal/isObjectLike":108}],134:[function(require,module,exports){
4661
+ var isLength = require('../internal/isLength'),
4662
+ isObjectLike = require('../internal/isObjectLike');
4663
+
4664
+ /** `Object#toString` result references. */
4665
+ var argsTag = '[object Arguments]',
4666
+ arrayTag = '[object Array]',
4667
+ boolTag = '[object Boolean]',
4668
+ dateTag = '[object Date]',
4669
+ errorTag = '[object Error]',
4670
+ funcTag = '[object Function]',
4671
+ mapTag = '[object Map]',
4672
+ numberTag = '[object Number]',
4673
+ objectTag = '[object Object]',
4674
+ regexpTag = '[object RegExp]',
4675
+ setTag = '[object Set]',
4676
+ stringTag = '[object String]',
4677
+ weakMapTag = '[object WeakMap]';
4678
+
4679
+ var arrayBufferTag = '[object ArrayBuffer]',
4680
+ float32Tag = '[object Float32Array]',
4681
+ float64Tag = '[object Float64Array]',
4682
+ int8Tag = '[object Int8Array]',
4683
+ int16Tag = '[object Int16Array]',
4684
+ int32Tag = '[object Int32Array]',
4685
+ uint8Tag = '[object Uint8Array]',
4686
+ uint8ClampedTag = '[object Uint8ClampedArray]',
4687
+ uint16Tag = '[object Uint16Array]',
4688
+ uint32Tag = '[object Uint32Array]';
4689
+
4690
+ /** Used to identify `toStringTag` values of typed arrays. */
4691
+ var typedArrayTags = {};
4692
+ typedArrayTags[float32Tag] = typedArrayTags[float64Tag] =
4693
+ typedArrayTags[int8Tag] = typedArrayTags[int16Tag] =
4694
+ typedArrayTags[int32Tag] = typedArrayTags[uint8Tag] =
4695
+ typedArrayTags[uint8ClampedTag] = typedArrayTags[uint16Tag] =
4696
+ typedArrayTags[uint32Tag] = true;
4697
+ typedArrayTags[argsTag] = typedArrayTags[arrayTag] =
4698
+ typedArrayTags[arrayBufferTag] = typedArrayTags[boolTag] =
4699
+ typedArrayTags[dateTag] = typedArrayTags[errorTag] =
4700
+ typedArrayTags[funcTag] = typedArrayTags[mapTag] =
4701
+ typedArrayTags[numberTag] = typedArrayTags[objectTag] =
4702
+ typedArrayTags[regexpTag] = typedArrayTags[setTag] =
4703
+ typedArrayTags[stringTag] = typedArrayTags[weakMapTag] = false;
4704
+
4705
+ /** Used for native method references. */
4706
+ var objectProto = Object.prototype;
4707
+
4708
+ /**
4709
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
4710
+ * of values.
4711
+ */
4712
+ var objToString = objectProto.toString;
4713
+
4714
+ /**
4715
+ * Checks if `value` is classified as a typed array.
4716
+ *
4717
+ * @static
4718
+ * @memberOf _
4719
+ * @category Lang
4720
+ * @param {*} value The value to check.
4721
+ * @returns {boolean} Returns `true` if `value` is correctly classified, else `false`.
4722
+ * @example
4723
+ *
4724
+ * _.isTypedArray(new Uint8Array);
4725
+ * // => true
4726
+ *
4727
+ * _.isTypedArray([]);
4728
+ * // => false
4729
+ */
4730
+ function isTypedArray(value) {
4731
+ return isObjectLike(value) && isLength(value.length) && !!typedArrayTags[objToString.call(value)];
4732
+ }
4733
+
4734
+ module.exports = isTypedArray;
4735
+
4736
+ },{"../internal/isLength":107,"../internal/isObjectLike":108}],135:[function(require,module,exports){
4737
+ /**
4738
+ * Checks if `value` is `undefined`.
4739
+ *
4740
+ * @static
4741
+ * @memberOf _
4742
+ * @category Lang
4743
+ * @param {*} value The value to check.
4744
+ * @returns {boolean} Returns `true` if `value` is `undefined`, else `false`.
4745
+ * @example
4746
+ *
4747
+ * _.isUndefined(void 0);
4748
+ * // => true
4749
+ *
4750
+ * _.isUndefined(null);
4751
+ * // => false
4752
+ */
4753
+ function isUndefined(value) {
4754
+ return value === undefined;
4755
+ }
4756
+
4757
+ module.exports = isUndefined;
4758
+
4759
+ },{}],136:[function(require,module,exports){
4760
+ var baseCopy = require('../internal/baseCopy'),
4761
+ keysIn = require('../object/keysIn');
4762
+
4763
+ /**
4764
+ * Converts `value` to a plain object flattening inherited enumerable
4765
+ * properties of `value` to own properties of the plain object.
4766
+ *
4767
+ * @static
4768
+ * @memberOf _
4769
+ * @category Lang
4770
+ * @param {*} value The value to convert.
4771
+ * @returns {Object} Returns the converted plain object.
4772
+ * @example
4773
+ *
4774
+ * function Foo() {
4775
+ * this.b = 2;
4776
+ * }
4777
+ *
4778
+ * Foo.prototype.c = 3;
4779
+ *
4780
+ * _.assign({ 'a': 1 }, new Foo);
4781
+ * // => { 'a': 1, 'b': 2 }
4782
+ *
4783
+ * _.assign({ 'a': 1 }, _.toPlainObject(new Foo));
4784
+ * // => { 'a': 1, 'b': 2, 'c': 3 }
4785
+ */
4786
+ function toPlainObject(value) {
4787
+ return baseCopy(value, keysIn(value));
4788
+ }
4789
+
4790
+ module.exports = toPlainObject;
4791
+
4792
+ },{"../internal/baseCopy":37,"../object/keysIn":141}],137:[function(require,module,exports){
4793
+ var arraySum = require('../internal/arraySum'),
4794
+ baseCallback = require('../internal/baseCallback'),
4795
+ baseSum = require('../internal/baseSum'),
4796
+ isArray = require('../lang/isArray'),
4797
+ isIterateeCall = require('../internal/isIterateeCall'),
4798
+ toIterable = require('../internal/toIterable');
4799
+
4800
+ /**
4801
+ * Gets the sum of the values in `collection`.
4802
+ *
4803
+ * @static
4804
+ * @memberOf _
4805
+ * @category Math
4806
+ * @param {Array|Object|string} collection The collection to iterate over.
4807
+ * @param {Function|Object|string} [iteratee] The function invoked per iteration.
4808
+ * @param {*} [thisArg] The `this` binding of `iteratee`.
4809
+ * @returns {number} Returns the sum.
4810
+ * @example
4811
+ *
4812
+ * _.sum([4, 6]);
4813
+ * // => 10
4814
+ *
4815
+ * _.sum({ 'a': 4, 'b': 6 });
4816
+ * // => 10
4817
+ *
4818
+ * var objects = [
4819
+ * { 'n': 4 },
4820
+ * { 'n': 6 }
4821
+ * ];
4822
+ *
4823
+ * _.sum(objects, function(object) {
4824
+ * return object.n;
4825
+ * });
4826
+ * // => 10
4827
+ *
4828
+ * // using the `_.property` callback shorthand
4829
+ * _.sum(objects, 'n');
4830
+ * // => 10
4831
+ */
4832
+ function sum(collection, iteratee, thisArg) {
4833
+ if (thisArg && isIterateeCall(collection, iteratee, thisArg)) {
4834
+ iteratee = undefined;
4835
+ }
4836
+ iteratee = baseCallback(iteratee, thisArg, 3);
4837
+ return iteratee.length == 1
4838
+ ? arraySum(isArray(collection) ? collection : toIterable(collection), iteratee)
4839
+ : baseSum(collection, iteratee);
4840
+ }
4841
+
4842
+ module.exports = sum;
4843
+
4844
+ },{"../internal/arraySum":31,"../internal/baseCallback":35,"../internal/baseSum":66,"../internal/isIterateeCall":104,"../internal/toIterable":120,"../lang/isArray":127}],138:[function(require,module,exports){
4845
+ var assignWith = require('../internal/assignWith'),
4846
+ baseAssign = require('../internal/baseAssign'),
4847
+ createAssigner = require('../internal/createAssigner');
4848
+
4849
+ /**
4850
+ * Assigns own enumerable properties of source object(s) to the destination
4851
+ * object. Subsequent sources overwrite property assignments of previous sources.
4852
+ * If `customizer` is provided it is invoked to produce the assigned values.
4853
+ * The `customizer` is bound to `thisArg` and invoked with five arguments:
4854
+ * (objectValue, sourceValue, key, object, source).
4855
+ *
4856
+ * **Note:** This method mutates `object` and is based on
4857
+ * [`Object.assign`](http://ecma-international.org/ecma-262/6.0/#sec-object.assign).
4858
+ *
4859
+ * @static
4860
+ * @memberOf _
4861
+ * @alias extend
4862
+ * @category Object
4863
+ * @param {Object} object The destination object.
4864
+ * @param {...Object} [sources] The source objects.
4865
+ * @param {Function} [customizer] The function to customize assigned values.
4866
+ * @param {*} [thisArg] The `this` binding of `customizer`.
4867
+ * @returns {Object} Returns `object`.
4868
+ * @example
4869
+ *
4870
+ * _.assign({ 'user': 'barney' }, { 'age': 40 }, { 'user': 'fred' });
4871
+ * // => { 'user': 'fred', 'age': 40 }
4872
+ *
4873
+ * // using a customizer callback
4874
+ * var defaults = _.partialRight(_.assign, function(value, other) {
4875
+ * return _.isUndefined(value) ? other : value;
4876
+ * });
4877
+ *
4878
+ * defaults({ 'user': 'barney' }, { 'age': 36 }, { 'user': 'fred' });
4879
+ * // => { 'user': 'barney', 'age': 36 }
4880
+ */
4881
+ var assign = createAssigner(function(object, source, customizer) {
4882
+ return customizer
4883
+ ? assignWith(object, source, customizer)
4884
+ : baseAssign(object, source);
4885
+ });
4886
+
4887
+ module.exports = assign;
4888
+
4889
+ },{"../internal/assignWith":33,"../internal/baseAssign":34,"../internal/createAssigner":79}],139:[function(require,module,exports){
4890
+ var assign = require('./assign'),
4891
+ assignDefaults = require('../internal/assignDefaults'),
4892
+ createDefaults = require('../internal/createDefaults');
4893
+
4894
+ /**
4895
+ * Assigns own enumerable properties of source object(s) to the destination
4896
+ * object for all destination properties that resolve to `undefined`. Once a
4897
+ * property is set, additional values of the same property are ignored.
4898
+ *
4899
+ * **Note:** This method mutates `object`.
4900
+ *
4901
+ * @static
4902
+ * @memberOf _
4903
+ * @category Object
4904
+ * @param {Object} object The destination object.
4905
+ * @param {...Object} [sources] The source objects.
4906
+ * @returns {Object} Returns `object`.
4907
+ * @example
4908
+ *
4909
+ * _.defaults({ 'user': 'barney' }, { 'age': 36 }, { 'user': 'fred' });
4910
+ * // => { 'user': 'barney', 'age': 36 }
4911
+ */
4912
+ var defaults = createDefaults(assign, assignDefaults);
4913
+
4914
+ module.exports = defaults;
4915
+
4916
+ },{"../internal/assignDefaults":32,"../internal/createDefaults":85,"./assign":138}],140:[function(require,module,exports){
4917
+ var getNative = require('../internal/getNative'),
4918
+ isArrayLike = require('../internal/isArrayLike'),
4919
+ isObject = require('../lang/isObject'),
4920
+ shimKeys = require('../internal/shimKeys');
4921
+
4922
+ /* Native method references for those with the same name as other `lodash` methods. */
4923
+ var nativeKeys = getNative(Object, 'keys');
4924
+
4925
+ /**
4926
+ * Creates an array of the own enumerable property names of `object`.
4927
+ *
4928
+ * **Note:** Non-object values are coerced to objects. See the
4929
+ * [ES spec](http://ecma-international.org/ecma-262/6.0/#sec-object.keys)
4930
+ * for more details.
4931
+ *
4932
+ * @static
4933
+ * @memberOf _
4934
+ * @category Object
4935
+ * @param {Object} object The object to query.
4936
+ * @returns {Array} Returns the array of property names.
4937
+ * @example
4938
+ *
4939
+ * function Foo() {
4940
+ * this.a = 1;
4941
+ * this.b = 2;
4942
+ * }
4943
+ *
4944
+ * Foo.prototype.c = 3;
4945
+ *
4946
+ * _.keys(new Foo);
4947
+ * // => ['a', 'b'] (iteration order is not guaranteed)
4948
+ *
4949
+ * _.keys('hi');
4950
+ * // => ['0', '1']
4951
+ */
4952
+ var keys = !nativeKeys ? shimKeys : function(object) {
4953
+ var Ctor = object == null ? undefined : object.constructor;
4954
+ if ((typeof Ctor == 'function' && Ctor.prototype === object) ||
4955
+ (typeof object != 'function' && isArrayLike(object))) {
4956
+ return shimKeys(object);
4957
+ }
4958
+ return isObject(object) ? nativeKeys(object) : [];
4959
+ };
4960
+
4961
+ module.exports = keys;
4962
+
4963
+ },{"../internal/getNative":100,"../internal/isArrayLike":102,"../internal/shimKeys":119,"../lang/isObject":131}],141:[function(require,module,exports){
4964
+ var isArguments = require('../lang/isArguments'),
4965
+ isArray = require('../lang/isArray'),
4966
+ isIndex = require('../internal/isIndex'),
4967
+ isLength = require('../internal/isLength'),
4968
+ isObject = require('../lang/isObject');
4969
+
4970
+ /** Used for native method references. */
4971
+ var objectProto = Object.prototype;
4972
+
4973
+ /** Used to check objects for own properties. */
4974
+ var hasOwnProperty = objectProto.hasOwnProperty;
4975
+
4976
+ /**
4977
+ * Creates an array of the own and inherited enumerable property names of `object`.
4978
+ *
4979
+ * **Note:** Non-object values are coerced to objects.
4980
+ *
4981
+ * @static
4982
+ * @memberOf _
4983
+ * @category Object
4984
+ * @param {Object} object The object to query.
4985
+ * @returns {Array} Returns the array of property names.
4986
+ * @example
4987
+ *
4988
+ * function Foo() {
4989
+ * this.a = 1;
4990
+ * this.b = 2;
4991
+ * }
4992
+ *
4993
+ * Foo.prototype.c = 3;
4994
+ *
4995
+ * _.keysIn(new Foo);
4996
+ * // => ['a', 'b', 'c'] (iteration order is not guaranteed)
4997
+ */
4998
+ function keysIn(object) {
4999
+ if (object == null) {
5000
+ return [];
5001
+ }
5002
+ if (!isObject(object)) {
5003
+ object = Object(object);
5004
+ }
5005
+ var length = object.length;
5006
+ length = (length && isLength(length) &&
5007
+ (isArray(object) || isArguments(object)) && length) || 0;
5008
+
5009
+ var Ctor = object.constructor,
5010
+ index = -1,
5011
+ isProto = typeof Ctor == 'function' && Ctor.prototype === object,
5012
+ result = Array(length),
5013
+ skipIndexes = length > 0;
5014
+
5015
+ while (++index < length) {
5016
+ result[index] = (index + '');
5017
+ }
5018
+ for (var key in object) {
5019
+ if (!(skipIndexes && isIndex(key, length)) &&
5020
+ !(key == 'constructor' && (isProto || !hasOwnProperty.call(object, key)))) {
5021
+ result.push(key);
5022
+ }
5023
+ }
5024
+ return result;
5025
+ }
5026
+
5027
+ module.exports = keysIn;
5028
+
5029
+ },{"../internal/isIndex":103,"../internal/isLength":107,"../lang/isArguments":126,"../lang/isArray":127,"../lang/isObject":131}],142:[function(require,module,exports){
5030
+ var baseMerge = require('../internal/baseMerge'),
5031
+ createAssigner = require('../internal/createAssigner');
5032
+
5033
+ /**
5034
+ * Recursively merges own enumerable properties of the source object(s), that
5035
+ * don't resolve to `undefined` into the destination object. Subsequent sources
5036
+ * overwrite property assignments of previous sources. If `customizer` is
5037
+ * provided it is invoked to produce the merged values of the destination and
5038
+ * source properties. If `customizer` returns `undefined` merging is handled
5039
+ * by the method instead. The `customizer` is bound to `thisArg` and invoked
5040
+ * with five arguments: (objectValue, sourceValue, key, object, source).
5041
+ *
5042
+ * @static
5043
+ * @memberOf _
5044
+ * @category Object
5045
+ * @param {Object} object The destination object.
5046
+ * @param {...Object} [sources] The source objects.
5047
+ * @param {Function} [customizer] The function to customize assigned values.
5048
+ * @param {*} [thisArg] The `this` binding of `customizer`.
5049
+ * @returns {Object} Returns `object`.
5050
+ * @example
5051
+ *
5052
+ * var users = {
5053
+ * 'data': [{ 'user': 'barney' }, { 'user': 'fred' }]
5054
+ * };
5055
+ *
5056
+ * var ages = {
5057
+ * 'data': [{ 'age': 36 }, { 'age': 40 }]
5058
+ * };
5059
+ *
5060
+ * _.merge(users, ages);
5061
+ * // => { 'data': [{ 'user': 'barney', 'age': 36 }, { 'user': 'fred', 'age': 40 }] }
5062
+ *
5063
+ * // using a customizer callback
5064
+ * var object = {
5065
+ * 'fruits': ['apple'],
5066
+ * 'vegetables': ['beet']
5067
+ * };
5068
+ *
5069
+ * var other = {
5070
+ * 'fruits': ['banana'],
5071
+ * 'vegetables': ['carrot']
5072
+ * };
5073
+ *
5074
+ * _.merge(object, other, function(a, b) {
5075
+ * if (_.isArray(a)) {
5076
+ * return a.concat(b);
5077
+ * }
5078
+ * });
5079
+ * // => { 'fruits': ['apple', 'banana'], 'vegetables': ['beet', 'carrot'] }
5080
+ */
5081
+ var merge = createAssigner(baseMerge);
5082
+
5083
+ module.exports = merge;
5084
+
5085
+ },{"../internal/baseMerge":57,"../internal/createAssigner":79}],143:[function(require,module,exports){
5086
+ var arrayMap = require('../internal/arrayMap'),
5087
+ baseDifference = require('../internal/baseDifference'),
5088
+ baseFlatten = require('../internal/baseFlatten'),
5089
+ bindCallback = require('../internal/bindCallback'),
5090
+ keysIn = require('./keysIn'),
5091
+ pickByArray = require('../internal/pickByArray'),
5092
+ pickByCallback = require('../internal/pickByCallback'),
5093
+ restParam = require('../function/restParam');
5094
+
5095
+ /**
5096
+ * The opposite of `_.pick`; this method creates an object composed of the
5097
+ * own and inherited enumerable properties of `object` that are not omitted.
5098
+ *
5099
+ * @static
5100
+ * @memberOf _
5101
+ * @category Object
5102
+ * @param {Object} object The source object.
5103
+ * @param {Function|...(string|string[])} [predicate] The function invoked per
5104
+ * iteration or property names to omit, specified as individual property
5105
+ * names or arrays of property names.
5106
+ * @param {*} [thisArg] The `this` binding of `predicate`.
5107
+ * @returns {Object} Returns the new object.
5108
+ * @example
5109
+ *
5110
+ * var object = { 'user': 'fred', 'age': 40 };
5111
+ *
5112
+ * _.omit(object, 'age');
5113
+ * // => { 'user': 'fred' }
5114
+ *
5115
+ * _.omit(object, _.isNumber);
5116
+ * // => { 'user': 'fred' }
5117
+ */
5118
+ var omit = restParam(function(object, props) {
5119
+ if (object == null) {
5120
+ return {};
5121
+ }
5122
+ if (typeof props[0] != 'function') {
5123
+ var props = arrayMap(baseFlatten(props), String);
5124
+ return pickByArray(object, baseDifference(keysIn(object), props));
5125
+ }
5126
+ var predicate = bindCallback(props[0], props[1], 3);
5127
+ return pickByCallback(object, function(value, key, object) {
5128
+ return !predicate(value, key, object);
5129
+ });
5130
+ });
5131
+
5132
+ module.exports = omit;
5133
+
5134
+ },{"../function/restParam":20,"../internal/arrayMap":27,"../internal/baseDifference":39,"../internal/baseFlatten":44,"../internal/bindCallback":71,"../internal/pickByArray":113,"../internal/pickByCallback":114,"./keysIn":141}],144:[function(require,module,exports){
5135
+ var keys = require('./keys'),
5136
+ toObject = require('../internal/toObject');
5137
+
5138
+ /**
5139
+ * Creates a two dimensional array of the key-value pairs for `object`,
5140
+ * e.g. `[[key1, value1], [key2, value2]]`.
5141
+ *
5142
+ * @static
5143
+ * @memberOf _
5144
+ * @category Object
5145
+ * @param {Object} object The object to query.
5146
+ * @returns {Array} Returns the new array of key-value pairs.
5147
+ * @example
5148
+ *
5149
+ * _.pairs({ 'barney': 36, 'fred': 40 });
5150
+ * // => [['barney', 36], ['fred', 40]] (iteration order is not guaranteed)
5151
+ */
5152
+ function pairs(object) {
5153
+ object = toObject(object);
5154
+
5155
+ var index = -1,
5156
+ props = keys(object),
5157
+ length = props.length,
5158
+ result = Array(length);
5159
+
5160
+ while (++index < length) {
5161
+ var key = props[index];
5162
+ result[index] = [key, object[key]];
5163
+ }
5164
+ return result;
5165
+ }
5166
+
5167
+ module.exports = pairs;
5168
+
5169
+ },{"../internal/toObject":121,"./keys":140}],145:[function(require,module,exports){
5170
+ var baseFlatten = require('../internal/baseFlatten'),
5171
+ bindCallback = require('../internal/bindCallback'),
5172
+ pickByArray = require('../internal/pickByArray'),
5173
+ pickByCallback = require('../internal/pickByCallback'),
5174
+ restParam = require('../function/restParam');
5175
+
5176
+ /**
5177
+ * Creates an object composed of the picked `object` properties. Property
5178
+ * names may be specified as individual arguments or as arrays of property
5179
+ * names. If `predicate` is provided it is invoked for each property of `object`
5180
+ * picking the properties `predicate` returns truthy for. The predicate is
5181
+ * bound to `thisArg` and invoked with three arguments: (value, key, object).
5182
+ *
5183
+ * @static
5184
+ * @memberOf _
5185
+ * @category Object
5186
+ * @param {Object} object The source object.
5187
+ * @param {Function|...(string|string[])} [predicate] The function invoked per
5188
+ * iteration or property names to pick, specified as individual property
5189
+ * names or arrays of property names.
5190
+ * @param {*} [thisArg] The `this` binding of `predicate`.
5191
+ * @returns {Object} Returns the new object.
5192
+ * @example
5193
+ *
5194
+ * var object = { 'user': 'fred', 'age': 40 };
5195
+ *
5196
+ * _.pick(object, 'user');
5197
+ * // => { 'user': 'fred' }
5198
+ *
5199
+ * _.pick(object, _.isString);
5200
+ * // => { 'user': 'fred' }
5201
+ */
5202
+ var pick = restParam(function(object, props) {
5203
+ if (object == null) {
5204
+ return {};
5205
+ }
5206
+ return typeof props[0] == 'function'
5207
+ ? pickByCallback(object, bindCallback(props[0], props[1], 3))
5208
+ : pickByArray(object, baseFlatten(props));
5209
+ });
5210
+
5211
+ module.exports = pick;
5212
+
5213
+ },{"../function/restParam":20,"../internal/baseFlatten":44,"../internal/bindCallback":71,"../internal/pickByArray":113,"../internal/pickByCallback":114}],146:[function(require,module,exports){
5214
+ var baseValues = require('../internal/baseValues'),
5215
+ keys = require('./keys');
5216
+
5217
+ /**
5218
+ * Creates an array of the own enumerable property values of `object`.
5219
+ *
5220
+ * **Note:** Non-object values are coerced to objects.
5221
+ *
5222
+ * @static
5223
+ * @memberOf _
5224
+ * @category Object
5225
+ * @param {Object} object The object to query.
5226
+ * @returns {Array} Returns the array of property values.
5227
+ * @example
5228
+ *
5229
+ * function Foo() {
5230
+ * this.a = 1;
5231
+ * this.b = 2;
5232
+ * }
5233
+ *
5234
+ * Foo.prototype.c = 3;
5235
+ *
5236
+ * _.values(new Foo);
5237
+ * // => [1, 2] (iteration order is not guaranteed)
5238
+ *
5239
+ * _.values('hi');
5240
+ * // => ['h', 'i']
5241
+ */
5242
+ function values(object) {
5243
+ return baseValues(object, keys(object));
5244
+ }
5245
+
5246
+ module.exports = values;
5247
+
5248
+ },{"../internal/baseValues":68,"./keys":140}],147:[function(require,module,exports){
5249
+ var baseToString = require('../internal/baseToString'),
5250
+ charsLeftIndex = require('../internal/charsLeftIndex'),
5251
+ charsRightIndex = require('../internal/charsRightIndex'),
5252
+ isIterateeCall = require('../internal/isIterateeCall'),
5253
+ trimmedLeftIndex = require('../internal/trimmedLeftIndex'),
5254
+ trimmedRightIndex = require('../internal/trimmedRightIndex');
5255
+
5256
+ /**
5257
+ * Removes leading and trailing whitespace or specified characters from `string`.
5258
+ *
5259
+ * @static
5260
+ * @memberOf _
5261
+ * @category String
5262
+ * @param {string} [string=''] The string to trim.
5263
+ * @param {string} [chars=whitespace] The characters to trim.
5264
+ * @param- {Object} [guard] Enables use as a callback for functions like `_.map`.
5265
+ * @returns {string} Returns the trimmed string.
5266
+ * @example
5267
+ *
5268
+ * _.trim(' abc ');
5269
+ * // => 'abc'
5270
+ *
5271
+ * _.trim('-_-abc-_-', '_-');
5272
+ * // => 'abc'
5273
+ *
5274
+ * _.map([' foo ', ' bar '], _.trim);
5275
+ * // => ['foo', 'bar']
5276
+ */
5277
+ function trim(string, chars, guard) {
5278
+ var value = string;
5279
+ string = baseToString(string);
5280
+ if (!string) {
5281
+ return string;
5282
+ }
5283
+ if (guard ? isIterateeCall(value, chars, guard) : chars == null) {
5284
+ return string.slice(trimmedLeftIndex(string), trimmedRightIndex(string) + 1);
5285
+ }
5286
+ chars = (chars + '');
5287
+ return string.slice(charsLeftIndex(string, chars), charsRightIndex(string, chars) + 1);
5288
+ }
5289
+
5290
+ module.exports = trim;
5291
+
5292
+ },{"../internal/baseToString":67,"../internal/charsLeftIndex":74,"../internal/charsRightIndex":75,"../internal/isIterateeCall":104,"../internal/trimmedLeftIndex":123,"../internal/trimmedRightIndex":124}],148:[function(require,module,exports){
5293
+ /**
5294
+ * This method returns the first argument provided to it.
5295
+ *
5296
+ * @static
5297
+ * @memberOf _
5298
+ * @category Utility
5299
+ * @param {*} value Any value.
5300
+ * @returns {*} Returns `value`.
5301
+ * @example
5302
+ *
5303
+ * var object = { 'user': 'fred' };
5304
+ *
5305
+ * _.identity(object) === object;
5306
+ * // => true
5307
+ */
5308
+ function identity(value) {
5309
+ return value;
5310
+ }
5311
+
5312
+ module.exports = identity;
5313
+
5314
+ },{}],149:[function(require,module,exports){
5315
+ /**
5316
+ * A no-operation function that returns `undefined` regardless of the
5317
+ * arguments it receives.
5318
+ *
5319
+ * @static
5320
+ * @memberOf _
5321
+ * @category Utility
5322
+ * @example
5323
+ *
5324
+ * var object = { 'user': 'fred' };
5325
+ *
5326
+ * _.noop(object) === undefined;
5327
+ * // => true
5328
+ */
5329
+ function noop() {
5330
+ // No operation performed.
5331
+ }
5332
+
5333
+ module.exports = noop;
5334
+
5335
+ },{}],150:[function(require,module,exports){
5336
+ var baseProperty = require('../internal/baseProperty'),
5337
+ basePropertyDeep = require('../internal/basePropertyDeep'),
5338
+ isKey = require('../internal/isKey');
5339
+
5340
+ /**
5341
+ * Creates a function that returns the property value at `path` on a
5342
+ * given object.
5343
+ *
5344
+ * @static
5345
+ * @memberOf _
5346
+ * @category Utility
5347
+ * @param {Array|string} path The path of the property to get.
5348
+ * @returns {Function} Returns the new function.
5349
+ * @example
5350
+ *
5351
+ * var objects = [
5352
+ * { 'a': { 'b': { 'c': 2 } } },
5353
+ * { 'a': { 'b': { 'c': 1 } } }
5354
+ * ];
5355
+ *
5356
+ * _.map(objects, _.property('a.b.c'));
5357
+ * // => [2, 1]
5358
+ *
5359
+ * _.pluck(_.sortBy(objects, _.property(['a', 'b', 'c'])), 'a.b.c');
5360
+ * // => [1, 2]
5361
+ */
5362
+ function property(path) {
5363
+ return isKey(path) ? baseProperty(path) : basePropertyDeep(path);
5364
+ }
5365
+
5366
+ module.exports = property;
5367
+
5368
+ },{"../internal/baseProperty":59,"../internal/basePropertyDeep":60,"../internal/isKey":105}],151:[function(require,module,exports){
5369
+ 'use strict';
5370
+
5371
+ /**
5372
+ * Functions to manipulate refinement lists
5373
+ *
5374
+ * The RefinementList is not formally defined through a prototype but is based
5375
+ * on a specific structure.
5376
+ *
5377
+ * @module SearchParameters.refinementList
5378
+ *
5379
+ * @typedef {string[]} SearchParameters.refinementList.Refinements
5380
+ * @typedef {Object.<string, SearchParameters.refinementList.Refinements>} SearchParameters.refinementList.RefinementList
5381
+ */
5382
+
5383
+ var isUndefined = require('lodash/lang/isUndefined');
5384
+ var isString = require('lodash/lang/isString');
5385
+ var isFunction = require('lodash/lang/isFunction');
5386
+ var isEmpty = require('lodash/lang/isEmpty');
5387
+ var defaults = require('lodash/object/defaults');
5388
+
5389
+ var reduce = require('lodash/collection/reduce');
5390
+ var filter = require('lodash/collection/filter');
5391
+ var omit = require('lodash/object/omit');
5392
+
5393
+ var lib = {
5394
+ /**
5395
+ * Adds a refinement to a RefinementList
5396
+ * @param {RefinementList} refinementList the initial list
5397
+ * @param {string} attribute the attribute to refine
5398
+ * @param {string} value the value of the refinement, if the value is not a string it will be converted
5399
+ * @return {RefinementList} a new and updated prefinement list
5400
+ */
5401
+ addRefinement: function addRefinement(refinementList, attribute, value) {
5402
+ if (lib.isRefined(refinementList, attribute, value)) {
5403
+ return refinementList;
5404
+ }
5405
+
5406
+ var valueAsString = '' + value;
5407
+
5408
+ var facetRefinement = !refinementList[attribute] ?
5409
+ [valueAsString] :
5410
+ refinementList[attribute].concat(valueAsString);
5411
+
5412
+ var mod = {};
5413
+
5414
+ mod[attribute] = facetRefinement;
5415
+
5416
+ return defaults({}, mod, refinementList);
5417
+ },
5418
+ /**
5419
+ * Removes refinement(s) for an attribute:
5420
+ * - if the value is specified removes the refinement for the value on the attribute
5421
+ * - if no value is specified removes all the refinements for this attribute
5422
+ * @param {RefinementList} refinementList the initial list
5423
+ * @param {string} attribute the attribute to refine
5424
+ * @param {string} [value] the value of the refinement
5425
+ * @return {RefinementList} a new and updated refinement lst
5426
+ */
5427
+ removeRefinement: function removeRefinement(refinementList, attribute, value) {
5428
+ if (isUndefined(value)) {
5429
+ return lib.clearRefinement(refinementList, attribute);
5430
+ }
5431
+
5432
+ var valueAsString = '' + value;
5433
+
5434
+ return lib.clearRefinement(refinementList, function(v, f) {
5435
+ return attribute === f && valueAsString === v;
5436
+ });
5437
+ },
5438
+ /**
5439
+ * Toggles the refinement value for an attribute.
5440
+ * @param {RefinementList} refinementList the initial list
5441
+ * @param {string} attribute the attribute to refine
5442
+ * @param {string} value the value of the refinement
5443
+ * @return {RefinementList} a new and updated list
5444
+ */
5445
+ toggleRefinement: function toggleRefinement(refinementList, attribute, value) {
5446
+ if (isUndefined(value)) throw new Error('toggleRefinement should be used with a value');
5447
+
5448
+ if (lib.isRefined(refinementList, attribute, value)) {
5449
+ return lib.removeRefinement(refinementList, attribute, value);
5450
+ }
5451
+
5452
+ return lib.addRefinement(refinementList, attribute, value);
5453
+ },
5454
+ /**
5455
+ * Clear all or parts of a RefinementList. Depending on the arguments, three
5456
+ * behaviors can happen:
5457
+ * - if no attribute is provided: clears the whole list
5458
+ * - if an attribute is provided as a string: clears the list for the specific attribute
5459
+ * - if an attribute is provided as a function: discards the elements for which the function returns true
5460
+ * @param {RefinementList} refinementList the initial list
5461
+ * @param {string} [attribute] the attribute or function to discard
5462
+ * @param {string} [refinementType] optionnal parameter to give more context to the attribute function
5463
+ * @return {RefinementList} a new and updated refinement list
5464
+ */
5465
+ clearRefinement: function clearRefinement(refinementList, attribute, refinementType) {
5466
+ if (isUndefined(attribute)) {
5467
+ return {};
5468
+ } else if (isString(attribute)) {
5469
+ return omit(refinementList, attribute);
5470
+ } else if (isFunction(attribute)) {
5471
+ return reduce(refinementList, function(memo, values, key) {
5472
+ var facetList = filter(values, function(value) {
5473
+ return !attribute(value, key, refinementType);
5474
+ });
5475
+
5476
+ if (!isEmpty(facetList)) memo[key] = facetList;
5477
+
5478
+ return memo;
5479
+ }, {});
5480
+ }
5481
+ },
5482
+ /**
5483
+ * Test if the refinement value is used for the attribute. If no refinement value
5484
+ * is provided, test if the refinementList contains any refinement for the
5485
+ * given attribute.
5486
+ * @param {RefinementList} refinementList the list of refinement
5487
+ * @param {string} attribute name of the attribute
5488
+ * @param {string} refinementValue value of the filter/refinement
5489
+ * @return {boolean}
5490
+ */
5491
+ isRefined: function isRefined(refinementList, attribute, refinementValue) {
5492
+ var indexOf = require('lodash/array/indexOf');
5493
+
5494
+ var containsRefinements = !!refinementList[attribute] &&
5495
+ refinementList[attribute].length > 0;
5496
+
5497
+ if (isUndefined(refinementValue) || !containsRefinements) {
5498
+ return containsRefinements;
5499
+ }
5500
+
5501
+ var refinementValueAsString = '' + refinementValue;
5502
+
5503
+ return indexOf(refinementList[attribute], refinementValueAsString) !== -1;
5504
+ }
5505
+ };
5506
+
5507
+ module.exports = lib;
5508
+
5509
+ },{"lodash/array/indexOf":5,"lodash/collection/filter":9,"lodash/collection/reduce":15,"lodash/lang/isEmpty":128,"lodash/lang/isFunction":129,"lodash/lang/isString":133,"lodash/lang/isUndefined":135,"lodash/object/defaults":139,"lodash/object/omit":143}],152:[function(require,module,exports){
5510
+ 'use strict';
5511
+
5512
+ var keys = require('lodash/object/keys');
5513
+ var intersection = require('lodash/array/intersection');
5514
+ var forEach = require('lodash/collection/forEach');
5515
+ var reduce = require('lodash/collection/reduce');
5516
+ var filter = require('lodash/collection/filter');
5517
+ var omit = require('lodash/object/omit');
5518
+ var indexOf = require('lodash/array/indexOf');
5519
+ var isEmpty = require('lodash/lang/isEmpty');
5520
+ var isUndefined = require('lodash/lang/isUndefined');
5521
+ var isString = require('lodash/lang/isString');
5522
+ var isFunction = require('lodash/lang/isFunction');
5523
+ var find = require('lodash/collection/find');
5524
+ var pluck = require('lodash/collection/pluck');
5525
+
5526
+ var defaults = require('lodash/object/defaults');
5527
+ var merge = require('lodash/object/merge');
5528
+ var deepFreeze = require('../functions/deepFreeze');
5529
+
5530
+ var RefinementList = require('./RefinementList');
5531
+
5532
+ /**
5533
+ * @typedef {string[]} SearchParameters.FacetList
5534
+ */
5535
+
5536
+ /**
5537
+ * @typedef {Object.<string, number>} SearchParameters.OperatorList
5538
+ */
5539
+
5540
+ /**
5541
+ * SearchParameters is the data structure that contains all the informations
5542
+ * usable for making a search to Algolia API. It doesn't do the search itself,
5543
+ * nor does it contains logic about the parameters.
5544
+ * It is an immutable object, therefore it has been created in a way that each
5545
+ * changes does not change the object itself but returns a copy with the
5546
+ * modification.
5547
+ * This object should probably not be instantiated outside of the helper. It will
5548
+ * be provided when needed. This object is documented for reference as you'll
5549
+ * get it from events generated by the {@link AlgoliaSearchHelper}.
5550
+ * If need be, instanciate the Helper from the factory function {@link SearchParameters.make}
5551
+ * @constructor
5552
+ * @classdesc contains all the parameters of a search
5553
+ * @param {object|SearchParameters} newParameters existing parameters or partial object for the properties of a new SearchParameters
5554
+ * @see SearchParameters.make
5555
+ * @example <caption>SearchParameters of the first query in <a href="http://demos.algolia.com/instant-search-demo">the instant search demo</a></caption>
5556
+ {
5557
+ "query": "",
5558
+ "disjunctiveFacets": [
5559
+ "customerReviewCount",
5560
+ "category",
5561
+ "salePrice_range",
5562
+ "manufacturer"
5563
+ ],
5564
+ "maxValuesPerFacet": 30,
5565
+ "page": 0,
5566
+ "hitsPerPage": 10,
5567
+ "facets": [
5568
+ "type",
5569
+ "shipping"
5570
+ ]
5571
+ }
5572
+ */
5573
+ function SearchParameters(newParameters) {
5574
+ var params = newParameters || {};
5575
+
5576
+ // Query
5577
+ /**
5578
+ * Query string of the instant search. The empty string is a valid query.
5579
+ * @member {string}
5580
+ * @see https://www.algolia.com/doc#query
5581
+ */
5582
+ this.query = params.query || '';
5583
+
5584
+ // Facets
5585
+ /**
5586
+ * All the facets that will be requested to the server
5587
+ * @member {string[]}
5588
+ */
5589
+ this.facets = params.facets || [];
5590
+ /**
5591
+ * All the declared disjunctive facets
5592
+ * @member {string[]}
5593
+ */
5594
+ this.disjunctiveFacets = params.disjunctiveFacets || [];
5595
+ /**
5596
+ * All the declared hierarchical facets,
5597
+ * a hierarchical facet is a disjunctive facet with some specific behavior
5598
+ * @member {string[]|object[]}
5599
+ */
5600
+ this.hierarchicalFacets = params.hierarchicalFacets || [];
5601
+
5602
+ // Refinements
5603
+ /**
5604
+ * @private
5605
+ * @member {Object.<string, SearchParameters.FacetList>}
5606
+ */
5607
+ this.facetsRefinements = params.facetsRefinements || {};
5608
+ /**
5609
+ * @private
5610
+ * @member {Object.<string, SearchParameters.FacetList>}
5611
+ */
5612
+ this.facetsExcludes = params.facetsExcludes || {};
5613
+ /**
5614
+ * @private
5615
+ * @member {Object.<string, SearchParameters.FacetList>}
5616
+ */
5617
+ this.disjunctiveFacetsRefinements = params.disjunctiveFacetsRefinements || {};
5618
+ /**
5619
+ * @private
5620
+ * @member {Object.<string, SearchParameters.OperatorList>}
5621
+ */
5622
+ this.numericRefinements = params.numericRefinements || {};
5623
+ /**
5624
+ * Contains the tags used to refine the query
5625
+ * Associated property in the query: tagFilters
5626
+ * @private
5627
+ * @member {string[]}
5628
+ */
5629
+ this.tagRefinements = params.tagRefinements || [];
5630
+ /**
5631
+ * @private
5632
+ * @member {Object.<string, SearchParameters.FacetList>}
5633
+ */
5634
+ this.hierarchicalFacetsRefinements = params.hierarchicalFacetsRefinements || {};
5635
+
5636
+ /**
5637
+ * Contains the tag filters in the raw format of the Algolia API. Setting this
5638
+ * parameter is not compatible with the of the add/remove/toggle methods of the
5639
+ * tag api.
5640
+ * @see https://www.algolia.com/doc#tagFilters
5641
+ * @member {string}
5642
+ */
5643
+ this.tagFilters = params.tagFilters;
5644
+
5645
+ // Misc. parameters
5646
+ /**
5647
+ * Number of hits to be returned by the search API
5648
+ * @member {number}
5649
+ * @see https://www.algolia.com/doc#hitsPerPage
5650
+ */
5651
+ this.hitsPerPage = params.hitsPerPage;
5652
+ /**
5653
+ * Number of values for each facetted attribute
5654
+ * @member {number}
5655
+ * @see https://www.algolia.com/doc#maxValuesPerFacet
5656
+ */
5657
+ this.maxValuesPerFacet = params.maxValuesPerFacet;
5658
+ /**
5659
+ * The current page number
5660
+ * @member {number}
5661
+ * @see https://www.algolia.com/doc#page
5662
+ */
5663
+ this.page = params.page || 0;
5664
+ /**
5665
+ * How the query should be treated by the search engine.
5666
+ * Possible values: prefixAll, prefixLast, prefixNone
5667
+ * @see https://www.algolia.com/doc#queryType
5668
+ * @member {string}
5669
+ */
5670
+ this.queryType = params.queryType;
5671
+ /**
5672
+ * How the typo tolerance behave in the search engine.
5673
+ * Possible values: true, false, min, strict
5674
+ * @see https://www.algolia.com/doc#typoTolerance
5675
+ * @member {string}
5676
+ */
5677
+ this.typoTolerance = params.typoTolerance;
5678
+
5679
+ /**
5680
+ * Number of characters to wait before doing one character replacement.
5681
+ * @see https://www.algolia.com/doc#minWordSizefor1Typo
5682
+ * @member {number}
5683
+ */
5684
+ this.minWordSizefor1Typo = params.minWordSizefor1Typo;
5685
+ /**
5686
+ * Number of characters to wait before doing a second character replacement.
5687
+ * @see https://www.algolia.com/doc#minWordSizefor2Typos
5688
+ * @member {number}
5689
+ */
5690
+ this.minWordSizefor2Typos = params.minWordSizefor2Typos;
5691
+ /**
5692
+ * Should the engine allow typos on numerics.
5693
+ * @see https://www.algolia.com/doc#allowTyposOnNumericTokens
5694
+ * @member {boolean}
5695
+ */
5696
+ this.allowTyposOnNumericTokens = params.allowTyposOnNumericTokens;
5697
+ /**
5698
+ * Should the plurals be ignored
5699
+ * @see https://www.algolia.com/doc#ignorePlurals
5700
+ * @member {boolean}
5701
+ */
5702
+ this.ignorePlurals = params.ignorePlurals;
5703
+ /**
5704
+ * Restrict which attribute is searched.
5705
+ * @see https://www.algolia.com/doc#restrictSearchableAttributes
5706
+ * @member {string}
5707
+ */
5708
+ this.restrictSearchableAttributes = params.restrictSearchableAttributes;
5709
+ /**
5710
+ * Enable the advanced syntax.
5711
+ * @see https://www.algolia.com/doc#advancedSyntax
5712
+ * @member {boolean}
5713
+ */
5714
+ this.advancedSyntax = params.advancedSyntax;
5715
+ /**
5716
+ * Enable the analytics
5717
+ * @see https://www.algolia.com/doc#analytics
5718
+ * @member {boolean}
5719
+ */
5720
+ this.analytics = params.analytics;
5721
+ /**
5722
+ * Tag of the query in the analytics.
5723
+ * @see https://www.algolia.com/doc#analyticsTags
5724
+ * @member {string}
5725
+ */
5726
+ this.analyticsTags = params.analyticsTags;
5727
+ /**
5728
+ * Enable the synonyms
5729
+ * @see https://www.algolia.com/doc#synonyms
5730
+ * @member {boolean}
5731
+ */
5732
+ this.synonyms = params.synonyms;
5733
+ /**
5734
+ * Should the engine replace the synonyms in the highlighted results.
5735
+ * @see https://www.algolia.com/doc#replaceSynonymsInHighlight
5736
+ * @member {boolean}
5737
+ */
5738
+ this.replaceSynonymsInHighlight = params.replaceSynonymsInHighlight;
5739
+ /**
5740
+ * Add some optional words to those defined in the dashboard
5741
+ * @see https://www.algolia.com/doc#optionalWords
5742
+ * @member {string}
5743
+ */
5744
+ this.optionalWords = params.optionalWords;
5745
+ /**
5746
+ * Possible values are "lastWords" "firstWords" "allOptionnal" "none" (default)
5747
+ * @see https://www.algolia.com/doc#removeWordsIfNoResults
5748
+ * @member {string}
5749
+ */
5750
+ this.removeWordsIfNoResults = params.removeWordsIfNoResults;
5751
+ /**
5752
+ * List of attributes to retrieve
5753
+ * @see https://www.algolia.com/doc#attributesToRetrieve
5754
+ * @member {string}
5755
+ */
5756
+ this.attributesToRetrieve = params.attributesToRetrieve;
5757
+ /**
5758
+ * List of attributes to highlight
5759
+ * @see https://www.algolia.com/doc#attributesToHighlight
5760
+ * @member {string}
5761
+ */
5762
+ this.attributesToHighlight = params.attributesToHighlight;
5763
+ /**
5764
+ * Code to be embedded on the left part of the highlighted results
5765
+ * @see https://www.algolia.com/doc#highlightPreTag
5766
+ * @member {string}
5767
+ */
5768
+ this.highlightPreTag = params.highlightPreTag;
5769
+ /**
5770
+ * Code to be embedded on the right part of the highlighted results
5771
+ * @see https://www.algolia.com/doc#highlightPostTag
5772
+ * @member {string}
5773
+ */
5774
+ this.highlightPostTag = params.highlightPostTag;
5775
+ /**
5776
+ * List of attributes to snippet
5777
+ * @see https://www.algolia.com/doc#attributesToSnippet
5778
+ * @member {string}
5779
+ */
5780
+ this.attributesToSnippet = params.attributesToSnippet;
5781
+ /**
5782
+ * Enable the ranking informations in the response
5783
+ * @see https://www.algolia.com/doc#getRankingInfo
5784
+ * @member {integer}
5785
+ */
5786
+ this.getRankingInfo = params.getRankingInfo;
5787
+ /**
5788
+ * Remove duplicates based on the index setting attributeForDistinct
5789
+ * @see https://www.algolia.com/doc#distinct
5790
+ * @member {boolean}
5791
+ */
5792
+ this.distinct = params.distinct;
5793
+ /**
5794
+ * Center of the geo search.
5795
+ * @see https://www.algolia.com/doc#aroundLatLng
5796
+ * @member {string}
5797
+ */
5798
+ this.aroundLatLng = params.aroundLatLng;
5799
+ /**
5800
+ * Center of the search, retrieve from the user IP.
5801
+ * @see https://www.algolia.com/doc#aroundLatLngViaIP
5802
+ * @member {boolean}
5803
+ */
5804
+ this.aroundLatLngViaIP = params.aroundLatLngViaIP;
5805
+ /**
5806
+ * Radius of the geo search.
5807
+ * @see https://www.algolia.com/doc#aroundRadius
5808
+ * @member {number}
5809
+ */
5810
+ this.aroundRadius = params.aroundRadius;
5811
+ /**
5812
+ * Precision of the geo search.
5813
+ * @see https://www.algolia.com/doc#aroundPrecision
5814
+ * @member {number}
5815
+ */
5816
+ this.aroundPrecision = params.aroundPrecision;
5817
+ /**
5818
+ * Geo search inside a box.
5819
+ * @see https://www.algolia.com/doc#insideBoundingBox
5820
+ * @member {string}
5821
+ */
5822
+ this.insideBoundingBox = params.insideBoundingBox;
5823
+ }
5824
+
5825
+ /**
5826
+ * Factory for SearchParameters
5827
+ * @param {object|SearchParameters} newParameters existing parameters or partial object for the properties of a new SearchParameters
5828
+ * @return {SearchParameters} frozen instance of SearchParameters
5829
+ */
5830
+ SearchParameters.make = function makeSearchParameters(newParameters) {
5831
+ var instance = new SearchParameters(newParameters);
5832
+
5833
+ return deepFreeze(instance);
5834
+ };
5835
+
5836
+ /**
5837
+ * Validates the new parameters based on the previous state
5838
+ * @param {SearchParameters} currentState the current state
5839
+ * @param {object|SearchParameters} parameters the new parameters to set
5840
+ * @return {Error|null} Error if the modification is invalid, null otherwise
5841
+ */
5842
+ SearchParameters.validate = function(currentState, parameters) {
5843
+ var params = parameters || {};
5844
+
5845
+ var ks = keys(params);
5846
+ var unknownKeys = filter(ks, function(k) {
5847
+ return !currentState.hasOwnProperty(k);
5848
+ });
5849
+
5850
+ if (unknownKeys.length === 1) return new Error('Property ' + unknownKeys[0] + ' is not defined on SearchParameters (see http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html)');
5851
+ if (unknownKeys.length > 1) return new Error('Properties ' + unknownKeys.join(' ') + ' are not defined on SearchParameters (see http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html)');
5852
+
5853
+ if (currentState.tagFilters && params.tagRefinements && params.tagRefinements.length > 0) {
5854
+ return new Error("[Tags] Can't switch from the managed tag API to the advanced API. It is probably an error, if it's really what you want, you should first clear the tags with clearTags method.");
5855
+ }
5856
+
5857
+ if (currentState.tagRefinements.length > 0 && params.tagFilters) {
5858
+ return new Error("[Tags] Can't switch from the advanced tag API to the managed API. It is probably an error, if it's not, you should first clear the tags with clearTags method.");
5859
+ }
5860
+
5861
+ return null;
5862
+ };
5863
+
5864
+ SearchParameters.prototype = {
5865
+ constructor: SearchParameters,
5866
+
5867
+ /**
5868
+ * Remove all refinements (disjunctive + conjunctive + excludes + numeric filters)
5869
+ * @method
5870
+ * @param {string|SearchParameters.clearCallback} [attribute] optionnal string or function
5871
+ * - If not given, means to clear all the filters.
5872
+ * - If `string`, means to clear all refinements for the `attribute` named filter.
5873
+ * - If `function`, means to clear all the refinements that return truthy values.
5874
+ * @return {SearchParameters}
5875
+ */
5876
+ clearRefinements: function clearRefinements(attribute) {
5877
+ return this.setQueryParameters({
5878
+ page: 0,
5879
+ numericRefinements: this._clearNumericRefinements(attribute),
5880
+ facetsRefinements: RefinementList.clearRefinement(this.facetsRefinements, attribute, 'conjunctiveFacet'),
5881
+ facetsExcludes: RefinementList.clearRefinement(this.facetsExcludes, attribute, 'exclude'),
5882
+ disjunctiveFacetsRefinements: RefinementList.clearRefinement(this.disjunctiveFacetsRefinements, attribute, 'disjunctiveFacet'),
5883
+ hierarchicalFacetsRefinements: RefinementList.clearRefinement(this.hierarchicalFacetsRefinements, attribute, 'hierarchicalFacet')
5884
+ });
5885
+ },
5886
+ /**
5887
+ * Remove all the refined tags from the SearchParameters
5888
+ * @method
5889
+ * @return {SearchParameters}
5890
+ */
5891
+ clearTags: function clearTags() {
5892
+ if (this.tagFilters === undefined && this.tagRefinements.length === 0) return this;
5893
+
5894
+ return this.setQueryParameters({
5895
+ page: 0,
5896
+ tagFilters: undefined,
5897
+ tagRefinements: []
5898
+ });
5899
+ },
5900
+ /**
5901
+ * Query setter
5902
+ * @method
5903
+ * @param {string} newQuery value for the new query
5904
+ * @return {SearchParameters}
5905
+ */
5906
+ setQuery: function setQuery(newQuery) {
5907
+ if (newQuery === this.query) return this;
5908
+
5909
+ return this.setQueryParameters({
5910
+ query: newQuery,
5911
+ page: 0
5912
+ });
5913
+ },
5914
+ /**
5915
+ * Page setter
5916
+ * @method
5917
+ * @param {number} newPage new page number
5918
+ * @return {SearchParameters}
5919
+ */
5920
+ setPage: function setPage(newPage) {
5921
+ if (newPage === this.page) return this;
5922
+
5923
+ return this.setQueryParameters({
5924
+ page: newPage
5925
+ });
5926
+ },
5927
+ /**
5928
+ * Facets setter
5929
+ * The facets are the simple facets, used for conjunctive (and) facetting.
5930
+ * @method
5931
+ * @param {string[]} facets all the attributes of the algolia records used for conjunctive facetting
5932
+ * @return {SearchParameters}
5933
+ */
5934
+ setFacets: function setFacets(facets) {
5935
+ return this.setQueryParameters({
5936
+ facets: facets
5937
+ });
5938
+ },
5939
+ /**
5940
+ * Disjunctive facets setter
5941
+ * Change the list of disjunctive (or) facets the helper chan handle.
5942
+ * @method
5943
+ * @param {string[]} facets all the attributes of the algolia records used for disjunctive facetting
5944
+ * @return {SearchParameters}
5945
+ */
5946
+ setDisjunctiveFacets: function setDisjunctiveFacets(facets) {
5947
+ return this.setQueryParameters({
5948
+ disjunctiveFacets: facets
5949
+ });
5950
+ },
5951
+ /**
5952
+ * HitsPerPage setter
5953
+ * Hits per page represents the number of hits retrieved for this query
5954
+ * @method
5955
+ * @param {number} n number of hits retrieved per page of results
5956
+ * @return {SearchParameters}
5957
+ */
5958
+ setHitsPerPage: function setHitsPerPage(n) {
5959
+ if (this.hitsPerPage === n) return this;
5960
+
5961
+ return this.setQueryParameters({
5962
+ hitsPerPage: n,
5963
+ page: 0
5964
+ });
5965
+ },
5966
+ /**
5967
+ * typoTolerance setter
5968
+ * Set the value of typoTolerance
5969
+ * @method
5970
+ * @param {string} typoTolerance new value of typoTolerance ("true", "false", "min" or "strict")
5971
+ * @return {SearchParameters}
5972
+ */
5973
+ setTypoTolerance: function setTypoTolerance(typoTolerance) {
5974
+ if (this.typoTolerance === typoTolerance) return this;
5975
+
5976
+ return this.setQueryParameters({
5977
+ typoTolerance: typoTolerance,
5978
+ page: 0
5979
+ });
5980
+ },
5981
+ /**
5982
+ * Add or update a numeric filter for a given attribute
5983
+ * Current limitation of the numeric filters: you can't have more than one value
5984
+ * filtered for each (attribute, oprator). It means that you can't have a filter
5985
+ * for ("attribute", "=", 3 ) and ("attribute", "=", 8)
5986
+ * @method
5987
+ * @param {string} attribute attribute to set the filter on
5988
+ * @param {string} operator operator of the filter (possible values: =, >, >=, <, <=, !=)
5989
+ * @param {number} value value of the filter
5990
+ * @return {SearchParameters}
5991
+ */
5992
+ addNumericRefinement: function(attribute, operator, value) {
5993
+ if (this.isNumericRefined(attribute, operator, value)) return this;
5994
+
5995
+ var mod = merge({}, this.numericRefinements);
5996
+
5997
+ mod[attribute] = merge({}, mod[attribute]);
5998
+ mod[attribute][operator] = value;
5999
+
6000
+ return this.setQueryParameters({
6001
+ page: 0,
6002
+ numericRefinements: mod
6003
+ });
6004
+ },
6005
+ /**
6006
+ * Get the list of conjunctive refinements for a single facet
6007
+ * @param {string} facetName name of the attribute used for facetting
6008
+ * @return {string[]} list of refinements
6009
+ */
6010
+ getConjunctiveRefinements: function(facetName) {
6011
+ if (!this.isConjunctiveFacet(facetName)) {
6012
+ throw new Error(facetName + ' is not defined in the facets attribute of the helper configuration');
6013
+ }
6014
+ return this.facetsRefinements[facetName] || [];
6015
+ },
6016
+ /**
6017
+ * Get the list of disjunctive refinements for a single facet
6018
+ * @param {string} facetName name of the attribute used for facetting
6019
+ * @return {string[]} list of refinements
6020
+ */
6021
+ getDisjunctiveRefinements: function(facetName) {
6022
+ if (!this.isDisjunctiveFacet(facetName)) {
6023
+ throw new Error(facetName + ' is not defined in the disjunctiveFacets attribute of the helper configuration');
6024
+ }
6025
+ return this.disjunctiveFacetsRefinements[facetName] || [];
6026
+ },
6027
+ /**
6028
+ * Get the list of hierarchical refinements for a single facet
6029
+ * @param {string} facetName name of the attribute used for facetting
6030
+ * @return {string[]} list of refinements
6031
+ */
6032
+ getHierarchicalRefinement: function(facetName) {
6033
+ // we send an array but we currently do not support multiple hierarchicalRefinements for a hierarchicalFacet
6034
+ return this.hierarchicalFacetsRefinements[facetName] || [];
6035
+ },
6036
+ /**
6037
+ * Get the list of exclude refinements for a single facet
6038
+ * @param {string} facetName name of the attribute used for facetting
6039
+ * @return {string[]} list of refinements
6040
+ */
6041
+ getExcludeRefinements: function(facetName) {
6042
+ if (!this.isConjunctiveFacet(facetName)) {
6043
+ throw new Error(facetName + ' is not defined in the facets attribute of the helper configuration');
6044
+ }
6045
+ return this.facetsExcludes[facetName] || [];
6046
+ },
6047
+ /**
6048
+ * Remove a numeric filter
6049
+ * @method
6050
+ * @param {string} attribute attribute to set the filter on
6051
+ * @param {string} operator operator of the filter (possible values: =, >, >=, <, <=, !=)
6052
+ * @return {SearchParameters}
6053
+ */
6054
+ removeNumericRefinement: function(attribute, operator) {
6055
+ if (!this.isNumericRefined(attribute, operator)) return this;
6056
+
6057
+ return this.setQueryParameters({
6058
+ page: 0,
6059
+ numericRefinements: this._clearNumericRefinements(function(value, key) {
6060
+ return key === attribute && value.op === operator;
6061
+ })
6062
+ });
6063
+ },
6064
+ /**
6065
+ * Get the list of numeric refinements for a single facet
6066
+ * @param {string} facetName name of the attribute used for facetting
6067
+ * @return {SearchParameters.OperatorList[]} list of refinements
6068
+ */
6069
+ getNumericRefinements: function(facetName) {
6070
+ return this.numericRefinements[facetName] || [];
6071
+ },
6072
+ /**
6073
+ * Return the current refinement for the (attribute, operator)
6074
+ * @param {string} attribute of the record
6075
+ * @param {string} operator applied
6076
+ * @return {number} value of the refinement
6077
+ */
6078
+ getNumericRefinement: function(attribute, operator) {
6079
+ return this.numericRefinements[attribute] && this.numericRefinements[attribute][operator];
6080
+ },
6081
+ /**
6082
+ * Clear numeric filters.
6083
+ * @method
6084
+ * @private
6085
+ * @param {string|SearchParameters.clearCallback} [attribute] optionnal string or function
6086
+ * - If not given, means to clear all the filters.
6087
+ * - If `string`, means to clear all refinements for the `attribute` named filter.
6088
+ * - If `function`, means to clear all the refinements that return truthy values.
6089
+ * @return {Object.<string, OperatorList>}
6090
+ */
6091
+ _clearNumericRefinements: function _clearNumericRefinements(attribute) {
6092
+ if (isUndefined(attribute)) {
6093
+ return {};
6094
+ } else if (isString(attribute)) {
6095
+ return omit(this.numericRefinements, attribute);
6096
+ } else if (isFunction(attribute)) {
6097
+ return reduce(this.numericRefinements, function(memo, operators, key) {
6098
+ var operatorList = omit(operators, function(value, operator) {
6099
+ return attribute({val: value, op: operator}, key, 'numeric');
6100
+ });
6101
+
6102
+ if (!isEmpty(operatorList)) memo[key] = operatorList;
6103
+
6104
+ return memo;
6105
+ }, {});
6106
+ }
6107
+ },
6108
+ /**
6109
+ * Add a refinement on a "normal" facet
6110
+ * @method
6111
+ * @param {string} facet attribute to apply the facetting on
6112
+ * @param {string} value value of the attribute (will be converted to string)
6113
+ * @return {SearchParameters}
6114
+ */
6115
+ addFacetRefinement: function addFacetRefinement(facet, value) {
6116
+ if (!this.isConjunctiveFacet(facet)) {
6117
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6118
+ }
6119
+ if (RefinementList.isRefined(this.facetsRefinements, facet, value)) return this;
6120
+
6121
+ return this.setQueryParameters({
6122
+ page: 0,
6123
+ facetsRefinements: RefinementList.addRefinement(this.facetsRefinements, facet, value)
6124
+ });
6125
+ },
6126
+ /**
6127
+ * Exclude a value from a "normal" facet
6128
+ * @method
6129
+ * @param {string} facet attribute to apply the exclusion on
6130
+ * @param {string} value value of the attribute (will be converted to string)
6131
+ * @return {SearchParameters}
6132
+ */
6133
+ addExcludeRefinement: function addExcludeRefinement(facet, value) {
6134
+ if (!this.isConjunctiveFacet(facet)) {
6135
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6136
+ }
6137
+ if (RefinementList.isRefined(this.facetsExcludes, facet, value)) return this;
6138
+
6139
+ return this.setQueryParameters({
6140
+ page: 0,
6141
+ facetsExcludes: RefinementList.addRefinement(this.facetsExcludes, facet, value)
6142
+ });
6143
+ },
6144
+ /**
6145
+ * Adds a refinement on a disjunctive facet.
6146
+ * @method
6147
+ * @param {string} facet attribute to apply the facetting on
6148
+ * @param {string} value value of the attribute (will be converted to string)
6149
+ * @return {SearchParameters}
6150
+ */
6151
+ addDisjunctiveFacetRefinement: function addDisjunctiveFacetRefinement(facet, value) {
6152
+ if (!this.isDisjunctiveFacet(facet)) {
6153
+ throw new Error(facet + ' is not defined in the disjunctiveFacets attribute of the helper configuration');
6154
+ }
6155
+
6156
+ if (RefinementList.isRefined(this.disjunctiveFacetsRefinements, facet, value)) return this;
6157
+
6158
+ return this.setQueryParameters({
6159
+ page: 0,
6160
+ disjunctiveFacetsRefinements: RefinementList.addRefinement(this.disjunctiveFacetsRefinements, facet, value)
6161
+ });
6162
+ },
6163
+ /**
6164
+ * addTagRefinement adds a tag to the list used to filter the results
6165
+ * @param {string} tag tag to be added
6166
+ * @return {SearchParameters}
6167
+ */
6168
+ addTagRefinement: function addTagRefinement(tag) {
6169
+ if (this.isTagRefined(tag)) return this;
6170
+
6171
+ var modification = {
6172
+ page: 0,
6173
+ tagRefinements: this.tagRefinements.concat(tag)
6174
+ };
6175
+
6176
+ return this.setQueryParameters(modification);
6177
+ },
6178
+ /**
6179
+ * Remove a refinement set on facet. If a value is provided, it will clear the
6180
+ * refinement for the given value, otherwise it will clear all the refinement
6181
+ * values for the facetted attribute.
6182
+ * @method
6183
+ * @param {string} facet name of the attribute used for facetting
6184
+ * @param {string} value value used to filter
6185
+ * @return {SearchParameters}
6186
+ */
6187
+ removeFacetRefinement: function removeFacetRefinement(facet, value) {
6188
+ if (!this.isConjunctiveFacet(facet)) {
6189
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6190
+ }
6191
+ if (!RefinementList.isRefined(this.facetsRefinements, facet, value)) return this;
6192
+
6193
+ return this.setQueryParameters({
6194
+ page: 0,
6195
+ facetsRefinements: RefinementList.removeRefinement(this.facetsRefinements, facet, value)
6196
+ });
6197
+ },
6198
+ /**
6199
+ * Remove a negative refinement on a facet
6200
+ * @method
6201
+ * @param {string} facet name of the attribute used for facetting
6202
+ * @param {string} value value used to filter
6203
+ * @return {SearchParameters}
6204
+ */
6205
+ removeExcludeRefinement: function removeExcludeRefinement(facet, value) {
6206
+ if (!this.isConjunctiveFacet(facet)) {
6207
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6208
+ }
6209
+ if (!RefinementList.isRefined(this.facetsExcludes, facet, value)) return this;
6210
+
6211
+ return this.setQueryParameters({
6212
+ page: 0,
6213
+ facetsExcludes: RefinementList.removeRefinement(this.facetsExcludes, facet, value)
6214
+ });
6215
+ },
6216
+ /**
6217
+ * Remove a refinement on a disjunctive facet
6218
+ * @method
6219
+ * @param {string} facet name of the attribute used for facetting
6220
+ * @param {string} value value used to filter
6221
+ * @return {SearchParameters}
6222
+ */
6223
+ removeDisjunctiveFacetRefinement: function removeDisjunctiveFacetRefinement(facet, value) {
6224
+ if (!this.isDisjunctiveFacet(facet)) {
6225
+ throw new Error(facet + ' is not defined in the disjunctiveFacets attribute of the helper configuration');
6226
+ }
6227
+ if (!RefinementList.isRefined(this.disjunctiveFacetsRefinements, facet, value)) return this;
6228
+
6229
+ return this.setQueryParameters({
6230
+ page: 0,
6231
+ disjunctiveFacetsRefinements: RefinementList.removeRefinement(this.disjunctiveFacetsRefinements, facet, value)
6232
+ });
6233
+ },
6234
+ /**
6235
+ * Remove a tag from the list of tag refinements
6236
+ * @method
6237
+ * @param {string} tag the tag to remove
6238
+ * @return {SearchParameters}
6239
+ */
6240
+ removeTagRefinement: function removeTagRefinement(tag) {
6241
+ if (!this.isTagRefined(tag)) return this;
6242
+
6243
+ var modification = {
6244
+ page: 0,
6245
+ tagRefinements: filter(this.tagRefinements, function(t) { return t !== tag; })
6246
+ };
6247
+
6248
+ return this.setQueryParameters(modification);
6249
+ },
6250
+ /**
6251
+ * Switch the refinement applied over a facet/value
6252
+ * @method
6253
+ * @param {string} facet name of the attribute used for facetting
6254
+ * @param {value} value value used for filtering
6255
+ * @return {SearchParameters}
6256
+ */
6257
+ toggleFacetRefinement: function toggleFacetRefinement(facet, value) {
6258
+ if (!this.isConjunctiveFacet(facet)) {
6259
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6260
+ }
6261
+
6262
+ return this.setQueryParameters({
6263
+ page: 0,
6264
+ facetsRefinements: RefinementList.toggleRefinement(this.facetsRefinements, facet, value)
6265
+ });
6266
+ },
6267
+ /**
6268
+ * Switch the refinement applied over a facet/value
6269
+ * @method
6270
+ * @param {string} facet name of the attribute used for facetting
6271
+ * @param {value} value value used for filtering
6272
+ * @return {SearchParameters}
6273
+ */
6274
+ toggleExcludeFacetRefinement: function toggleExcludeFacetRefinement(facet, value) {
6275
+ if (!this.isConjunctiveFacet(facet)) {
6276
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6277
+ }
6278
+
6279
+ return this.setQueryParameters({
6280
+ page: 0,
6281
+ facetsExcludes: RefinementList.toggleRefinement(this.facetsExcludes, facet, value)
6282
+ });
6283
+ },
6284
+ /**
6285
+ * Switch the refinement applied over a facet/value
6286
+ * @method
6287
+ * @param {string} facet name of the attribute used for facetting
6288
+ * @param {value} value value used for filtering
6289
+ * @return {SearchParameters}
6290
+ */
6291
+ toggleDisjunctiveFacetRefinement: function toggleDisjunctiveFacetRefinement(facet, value) {
6292
+ if (!this.isDisjunctiveFacet(facet)) {
6293
+ throw new Error(facet + ' is not defined in the disjunctiveFacets attribute of the helper configuration');
6294
+ }
6295
+
6296
+ return this.setQueryParameters({
6297
+ page: 0,
6298
+ disjunctiveFacetsRefinements: RefinementList.toggleRefinement(this.disjunctiveFacetsRefinements, facet, value)
6299
+ });
6300
+ },
6301
+ /**
6302
+ * Switch the refinement applied over a facet/value
6303
+ * @method
6304
+ * @param {string} facet name of the attribute used for facetting
6305
+ * @param {value} value value used for filtering
6306
+ * @return {SearchParameters}
6307
+ */
6308
+ toggleHierarchicalFacetRefinement: function toggleHierarchicalFacetRefinement(facet, value) {
6309
+ if (!this.isHierarchicalFacet(facet)) {
6310
+ throw new Error(facet + ' is not defined in the hierarchicalFacets attribute of the helper configuration');
6311
+ }
6312
+
6313
+ var separator = this._getHierarchicalFacetSeparator(this.getHierarchicalFacetByName(facet));
6314
+
6315
+ var mod = {};
6316
+
6317
+ var upOneOrMultipleLevel = this.hierarchicalFacetsRefinements[facet] !== undefined &&
6318
+ this.hierarchicalFacetsRefinements[facet].length > 0 && (
6319
+ // remove current refinement:
6320
+ // refinement was 'beer > IPA', call is toggleRefine('beer > IPA'), refinement should be `beer`
6321
+ this.hierarchicalFacetsRefinements[facet][0] === value ||
6322
+ // remove a parent refinement of the current refinement:
6323
+ // - refinement was 'beer > IPA > Flying dog'
6324
+ // - call is toggleRefine('beer > IPA')
6325
+ // - refinement should be `beer`
6326
+ this.hierarchicalFacetsRefinements[facet][0].indexOf(value + separator) === 0
6327
+ );
6328
+
6329
+ if (upOneOrMultipleLevel) {
6330
+ if (value.indexOf(separator) === -1) {
6331
+ // go back to root level
6332
+ mod[facet] = [];
6333
+ } else {
6334
+ mod[facet] = [value.slice(0, value.lastIndexOf(separator))];
6335
+ }
6336
+ } else {
6337
+ mod[facet] = [value];
6338
+ }
6339
+
6340
+ return this.setQueryParameters({
6341
+ hierarchicalFacetsRefinements: defaults({}, mod, this.hierarchicalFacetsRefinements)
6342
+ });
6343
+ },
6344
+ /**
6345
+ * Switch the tag refinement
6346
+ * @method
6347
+ * @param {string} tag the tag to remove or add
6348
+ * @return {SearchParameters}
6349
+ */
6350
+ toggleTagRefinement: function toggleTagRefinement(tag) {
6351
+ if (this.isTagRefined(tag)) {
6352
+ return this.removeTagRefinement(tag);
6353
+ }
6354
+
6355
+ return this.addTagRefinement(tag);
6356
+ },
6357
+ /**
6358
+ * Test if the facet name is from one of the disjunctive facets
6359
+ * @method
6360
+ * @param {string} facet facet name to test
6361
+ * @return {boolean}
6362
+ */
6363
+ isDisjunctiveFacet: function(facet) {
6364
+ return indexOf(this.disjunctiveFacets, facet) > -1;
6365
+ },
6366
+ /**
6367
+ * Test if the facet name is from one of the hierarchical facets
6368
+ * @method
6369
+ * @param {string} facetName facet name to test
6370
+ * @return {boolean}
6371
+ */
6372
+ isHierarchicalFacet: function(facetName) {
6373
+ return this.getHierarchicalFacetByName(facetName) !== undefined;
6374
+ },
6375
+ /**
6376
+ * Test if the facet name is from one of the conjunctive/normal facets
6377
+ * @method
6378
+ * @param {string} facet facet name to test
6379
+ * @return {boolean}
6380
+ */
6381
+ isConjunctiveFacet: function(facet) {
6382
+ return indexOf(this.facets, facet) > -1;
6383
+ },
6384
+ /**
6385
+ * Returns true if the facet is refined, either for a specific value or in
6386
+ * general.
6387
+ * @method
6388
+ * @param {string} facet name of the attribute for used for facetting
6389
+ * @param {string} value, optionnal value. If passed will test that this value
6390
+ * is filtering the given facet.
6391
+ * @return {boolean} returns true if refined
6392
+ */
6393
+ isFacetRefined: function isFacetRefined(facet, value) {
6394
+ if (!this.isConjunctiveFacet(facet)) {
6395
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6396
+ }
6397
+ return RefinementList.isRefined(this.facetsRefinements, facet, value);
6398
+ },
6399
+ /**
6400
+ * Returns true if the facet contains exclusions or if a specific value is
6401
+ * excluded
6402
+ * @method
6403
+ * @param {string} facet name of the attribute for used for facetting
6404
+ * @param {string} value, optionnal value. If passed will test that this value
6405
+ * is filtering the given facet.
6406
+ * @return {boolean} returns true if refined
6407
+ */
6408
+ isExcludeRefined: function isExcludeRefined(facet, value) {
6409
+ if (!this.isConjunctiveFacet(facet)) {
6410
+ throw new Error(facet + ' is not defined in the facets attribute of the helper configuration');
6411
+ }
6412
+ return RefinementList.isRefined(this.facetsExcludes, facet, value);
6413
+ },
6414
+ /**
6415
+ * Returns true if the facet contains a refinement, or if a value passed is a
6416
+ * refinement for the facet.
6417
+ * @method
6418
+ * @param {string} facet name of the attribute for used for facetting
6419
+ * @param {string} value optionnal, will test if the value is used for refinement
6420
+ * if there is one, otherwise will test if the facet contains any refinement
6421
+ * @return {boolean}
6422
+ */
6423
+ isDisjunctiveFacetRefined: function isDisjunctiveFacetRefined(facet, value) {
6424
+ if (!this.isDisjunctiveFacet(facet)) {
6425
+ throw new Error(facet + ' is not defined in the disjunctiveFacets attribute of the helper configuration');
6426
+ }
6427
+ return RefinementList.isRefined(this.disjunctiveFacetsRefinements, facet, value);
6428
+ },
6429
+ /**
6430
+ * Test if the triple (attribute, operator, value) is already refined.
6431
+ * If only the attribute and the operator are provided, it tests if the
6432
+ * contains any refinement value.
6433
+ * @method
6434
+ * @param {string} attribute attribute for which the refinement is applied
6435
+ * @param {string} operator operator of the refinement
6436
+ * @param {string} [value] value of the refinement
6437
+ * @return {boolean} true if it is refined
6438
+ */
6439
+ isNumericRefined: function isNumericRefined(attribute, operator, value) {
6440
+ if (isUndefined(value)) {
6441
+ return this.numericRefinements[attribute] &&
6442
+ !isUndefined(this.numericRefinements[attribute][operator]);
6443
+ }
6444
+
6445
+ return this.numericRefinements[attribute] &&
6446
+ !isUndefined(this.numericRefinements[attribute][operator]) &&
6447
+ this.numericRefinements[attribute][operator] === value;
6448
+ },
6449
+ /**
6450
+ * Returns true if the tag refined, false otherwise
6451
+ * @method
6452
+ * @param {string} tag the tag to check
6453
+ * @return {boolean}
6454
+ */
6455
+ isTagRefined: function isTagRefined(tag) {
6456
+ return indexOf(this.tagRefinements, tag) !== -1;
6457
+ },
6458
+ /**
6459
+ * Returns the list of all disjunctive facets refined
6460
+ * @method
6461
+ * @param {string} facet name of the attribute used for facetting
6462
+ * @param {value} value value used for filtering
6463
+ * @return {string[]}
6464
+ */
6465
+ getRefinedDisjunctiveFacets: function getRefinedDisjunctiveFacets() {
6466
+ // attributes used for numeric filter can also be disjunctive
6467
+ var disjunctiveNumericRefinedFacets = intersection(
6468
+ keys(this.numericRefinements),
6469
+ this.disjunctiveFacets
6470
+ );
6471
+
6472
+ return keys(this.disjunctiveFacetsRefinements)
6473
+ .concat(disjunctiveNumericRefinedFacets)
6474
+ .concat(this.getRefinedHierarchicalFacets());
6475
+ },
6476
+ /**
6477
+ * Returns the list of all disjunctive facets refined
6478
+ * @method
6479
+ * @param {string} facet name of the attribute used for facetting
6480
+ * @param {value} value value used for filtering
6481
+ * @return {string[]}
6482
+ */
6483
+ getRefinedHierarchicalFacets: function getRefinedHierarchicalFacets() {
6484
+ return intersection(
6485
+ // enforce the order between the two arrays,
6486
+ // so that refinement name index === hierarchical facet index
6487
+ pluck(this.hierarchicalFacets, 'name'),
6488
+ keys(this.hierarchicalFacetsRefinements)
6489
+ );
6490
+ },
6491
+ /**
6492
+ * Returned the list of all disjunctive facets not refined
6493
+ * @method
6494
+ * @return {string[]}
6495
+ */
6496
+ getUnrefinedDisjunctiveFacets: function() {
6497
+ var refinedFacets = this.getRefinedDisjunctiveFacets();
6498
+
6499
+ return filter(this.disjunctiveFacets, function(f) {
6500
+ return indexOf(refinedFacets, f) === -1;
6501
+ });
6502
+ },
6503
+
6504
+ managedParameters: [
6505
+ 'facets', 'disjunctiveFacets', 'facetsRefinements',
6506
+ 'facetsExcludes', 'disjunctiveFacetsRefinements',
6507
+ 'numericRefinements', 'tagRefinements', 'hierarchicalFacets', 'hierarchicalFacetsRefinements'
6508
+ ],
6509
+ getQueryParams: function getQueryParams() {
6510
+ var managedParameters = this.managedParameters;
6511
+
6512
+ // FIXME with lodash
6513
+ return reduce(this, function(memo, value, parameter, parameters) {
6514
+ if (indexOf(managedParameters, parameter) === -1 &&
6515
+ parameters[parameter] !== undefined) {
6516
+ memo[parameter] = value;
6517
+ }
6518
+
6519
+ return memo;
6520
+ }, {});
6521
+ },
6522
+ /**
6523
+ * Let the user retrieve any parameter value from the SearchParameters
6524
+ * @param {string} paramName name of the parameter
6525
+ * @return {any} the value of the parameter
6526
+ */
6527
+ getQueryParameter: function getQueryParameter(paramName) {
6528
+ if (!this.hasOwnProperty(paramName)) throw new Error("Parameter '" + paramName + "' is not an attribute of SearchParameters (http://algolia.github.io/algoliasearch-helper-js/docs/SearchParameters.html)");
6529
+
6530
+ return this[paramName];
6531
+ },
6532
+ /**
6533
+ * Let the user set a specific value for a given parameter. Will return the
6534
+ * same instance if the parameter is invalid or if the value is the same as the
6535
+ * previous one.
6536
+ * @method
6537
+ * @param {string} parameter the parameter name
6538
+ * @param {any} value the value to be set, must be compliant with the definition of the attribute on the object
6539
+ * @return {SearchParameters} the updated state
6540
+ */
6541
+ setQueryParameter: function setParameter(parameter, value) {
6542
+ if (this[parameter] === value) return this;
6543
+
6544
+ var modification = {};
6545
+
6546
+ modification[parameter] = value;
6547
+
6548
+ return this.setQueryParameters(modification);
6549
+ },
6550
+ /**
6551
+ * Let the user set any of the parameters with a plain object.
6552
+ * It won't let the user define custom properties.
6553
+ * @method
6554
+ * @param {object} params all the keys and the values to be updated
6555
+ * @return {SearchParameters} a new updated instance
6556
+ */
6557
+ setQueryParameters: function setQueryParameters(params) {
6558
+ var error = SearchParameters.validate(this, params);
6559
+
6560
+ if (error) {
6561
+ throw error;
6562
+ }
6563
+
6564
+ return this.mutateMe(function mergeWith(newInstance) {
6565
+ var ks = keys(params);
6566
+
6567
+ forEach(ks, function(k) {
6568
+ newInstance[k] = params[k];
6569
+ });
6570
+
6571
+ return newInstance;
6572
+ });
6573
+ },
6574
+ /**
6575
+ * Helper function to make it easier to build new instances from a mutating
6576
+ * function
6577
+ * @private
6578
+ * @param {function} fn newMutableState -> previousState -> () function that will
6579
+ * change the value of the newMutable to the desired state
6580
+ * @return {SearchParameters} a new instance with the specified modifications applied
6581
+ */
6582
+ mutateMe: function mutateMe(fn) {
6583
+ var newState = new this.constructor(this);
6584
+
6585
+ fn(newState, this);
6586
+ return deepFreeze(newState);
6587
+ },
6588
+
6589
+ /**
6590
+ * Helper function to get the hierarchicalFacet separator or the default one (`>`)
6591
+ * @param {object} hierarchicalFacet
6592
+ * @return {string} returns the hierarchicalFacet.separator or `>` as default
6593
+ */
6594
+ _getHierarchicalFacetSortBy: function(hierarchicalFacet) {
6595
+ return hierarchicalFacet.sortBy || ['isRefined:desc', 'name:asc'];
6596
+ },
6597
+
6598
+ /**
6599
+ * Helper function to get the hierarchicalFacet separator or the default one (`>`)
6600
+ * @param {object} hierarchicalFacet
6601
+ * @return {string} returns the hierarchicalFacet.separator or `>` as default
6602
+ */
6603
+ _getHierarchicalFacetSeparator: function(hierarchicalFacet) {
6604
+ return hierarchicalFacet.separator || ' > ';
6605
+ },
6606
+
6607
+ /**
6608
+ * Helper function to get the hierarchicalFacet by it's name
6609
+ * @param {string} hierarchicalFacetName
6610
+ * @return {object} a hierarchicalFacet
6611
+ */
6612
+ getHierarchicalFacetByName: function(hierarchicalFacetName) {
6613
+ return find(
6614
+ this.hierarchicalFacets,
6615
+ {name: hierarchicalFacetName}
6616
+ );
6617
+ }
6618
+ };
6619
+
6620
+ /**
6621
+ * Callback used for clearRefinement method
6622
+ * @callback SearchParameters.clearCallback
6623
+ * @param {OperatorList|FacetList} value
6624
+ * @param {string} key
6625
+ * @param {string} type numeric, disjunctiveFacet, conjunctiveFacet or exclude
6626
+ * depending on the type of facet
6627
+ * @return {boolean}
6628
+ */
6629
+ module.exports = SearchParameters;
6630
+
6631
+ },{"../functions/deepFreeze":156,"./RefinementList":151,"lodash/array/indexOf":5,"lodash/array/intersection":6,"lodash/collection/filter":9,"lodash/collection/find":10,"lodash/collection/forEach":11,"lodash/collection/pluck":14,"lodash/collection/reduce":15,"lodash/lang/isEmpty":128,"lodash/lang/isFunction":129,"lodash/lang/isString":133,"lodash/lang/isUndefined":135,"lodash/object/defaults":139,"lodash/object/keys":140,"lodash/object/merge":142,"lodash/object/omit":143}],153:[function(require,module,exports){
6632
+ 'use strict';
6633
+
6634
+ module.exports = generateTrees;
6635
+
6636
+ var last = require('lodash/array/last');
6637
+ var map = require('lodash/collection/map');
6638
+ var reduce = require('lodash/collection/reduce');
6639
+ var sortByOrder = require('lodash/collection/sortByOrder');
6640
+ var trim = require('lodash/string/trim');
6641
+ var find = require('lodash/collection/find');
6642
+ var pick = require('lodash/object/pick');
6643
+
6644
+ function generateTrees(state) {
6645
+ return function generate(hierarchicalFacetResult, hierarchicalFacetIndex) {
6646
+ var hierarchicalFacet = state.hierarchicalFacets[hierarchicalFacetIndex];
6647
+ var hierarchicalFacetRefinement = state.hierarchicalFacetsRefinements[hierarchicalFacet.name] &&
6648
+ state.hierarchicalFacetsRefinements[hierarchicalFacet.name][0] || '';
6649
+ var hierarchicalSeparator = state._getHierarchicalFacetSeparator(hierarchicalFacet);
6650
+ var sortBy = prepareHierarchicalFacetSortBy(state._getHierarchicalFacetSortBy(hierarchicalFacet));
6651
+ var alwaysGetRootLevel = hierarchicalFacet.alwaysGetRootLevel;
6652
+
6653
+ return reduce(hierarchicalFacetResult, generateHierarchicalTree(sortBy, hierarchicalSeparator, hierarchicalFacetRefinement, alwaysGetRootLevel), {
6654
+ name: state.hierarchicalFacets[hierarchicalFacetIndex].name,
6655
+ count: null, // root level, no count
6656
+ isRefined: true, // root level, always refined
6657
+ path: null, // root level, no path
6658
+ data: null
6659
+ });
6660
+ };
6661
+ }
6662
+
6663
+ function generateHierarchicalTree(sortBy, hierarchicalSeparator, currentRefinement, alwaysGetRootLevel) {
6664
+ return function generateTree(hierarchicalTree, hierarchicalFacetResult, currentHierarchicalLevel) {
6665
+ var parent = hierarchicalTree;
6666
+
6667
+ if (currentHierarchicalLevel > 0) {
6668
+ var level = 0;
6669
+
6670
+ parent = hierarchicalTree;
6671
+
6672
+ while (level < currentHierarchicalLevel) {
6673
+ parent = parent && find(parent.data, {isRefined: true});
6674
+ level++;
6675
+ }
6676
+ }
6677
+
6678
+ // we found a refined parent, let's add current level data under it
6679
+ if (parent) {
6680
+ parent.data = sortByOrder(
6681
+ map(
6682
+ // filter values in case an object has:
6683
+ // {
6684
+ // categories: {
6685
+ // level0: ['beers', 'bières'],
6686
+ // level1: ['beers > IPA', 'bières > Belges']
6687
+ // }
6688
+ // }
6689
+ //
6690
+ // If parent refinement is `beers`, then we do not want to have `bières > Belges`
6691
+ // showing up
6692
+ pick(hierarchicalFacetResult.data, filterFacetValues(parent.path, currentRefinement, hierarchicalSeparator, alwaysGetRootLevel)),
6693
+ formatHierarchicalFacetValue(hierarchicalSeparator, currentRefinement)
6694
+ ),
6695
+ sortBy[0], sortBy[1]
6696
+ );
6697
+ }
6698
+
6699
+ return hierarchicalTree;
6700
+ };
6701
+ }
6702
+
6703
+ function filterFacetValues(parentPath, currentRefinement, hierarchicalSeparator, alwaysGetRootLevel) {
6704
+ return function(facetCount, facetValue) {
6705
+ // we always want root levels and facetValue is a root level
6706
+ return alwaysGetRootLevel === true && facetValue.indexOf(hierarchicalSeparator) === -1 ||
6707
+ // if current refinement is a root level and current facetValue is a root level,
6708
+ // keep the facetValue
6709
+ facetValue.indexOf(hierarchicalSeparator) === -1 &&
6710
+ currentRefinement.indexOf(hierarchicalSeparator) === -1 ||
6711
+ // currentRefinement is a child of the facet value
6712
+ currentRefinement.indexOf(facetValue + hierarchicalSeparator) === 0 ||
6713
+ // facetValue is a child of the current parent, add it
6714
+ facetValue.indexOf(parentPath + hierarchicalSeparator) === 0;
6715
+ };
6716
+ }
6717
+
6718
+ function formatHierarchicalFacetValue(hierarchicalSeparator, currentRefinement) {
6719
+ return function format(facetCount, facetValue) {
6720
+ return {
6721
+ name: trim(last(facetValue.split(hierarchicalSeparator))),
6722
+ path: facetValue,
6723
+ count: facetCount,
6724
+ isRefined: currentRefinement === facetValue || currentRefinement.indexOf(facetValue + hierarchicalSeparator) === 0,
6725
+ data: null
6726
+ };
6727
+ };
6728
+ }
6729
+
6730
+ // ['isRefined:desc', 'count:asc'] => [['isRefined', 'count'], ['desc', 'asc']] (lodash sortByOrder format)
6731
+ function prepareHierarchicalFacetSortBy(sortBy) {
6732
+ return reduce(sortBy, function prepare(out, sortInstruction) {
6733
+ var sortInstructions = sortInstruction.split(':');
6734
+ out[0].push(sortInstructions[0]);
6735
+ out[1].push(sortInstructions[1]);
6736
+ return out;
6737
+ }, [[], []]);
6738
+ }
6739
+
6740
+ },{"lodash/array/last":7,"lodash/collection/find":10,"lodash/collection/map":13,"lodash/collection/reduce":15,"lodash/collection/sortByOrder":16,"lodash/object/pick":145,"lodash/string/trim":147}],154:[function(require,module,exports){
6741
+ 'use strict';
6742
+
6743
+ var forEach = require('lodash/collection/forEach');
6744
+ var compact = require('lodash/array/compact');
6745
+ var indexOf = require('lodash/array/indexOf');
6746
+ var sum = require('lodash/collection/sum');
6747
+ var find = require('lodash/collection/find');
6748
+ var includes = require('lodash/collection/includes');
6749
+ var map = require('lodash/collection/map');
6750
+ var findIndex = require('lodash/array/findIndex');
6751
+ var defaults = require('lodash/object/defaults');
6752
+ var merge = require('lodash/object/merge');
6753
+
6754
+ var generateHierarchicalTree = require('./generate-hierarchical-tree');
6755
+
6756
+ /**
6757
+ * @typedef SearchResults.Facet
6758
+ * @type {object}
6759
+ * @property {string} name name of the attribute in the record
6760
+ * @property {object.<string, number>} data the facetting data: value, number of entries
6761
+ * @property {object} stats undefined unless facet_stats is retrieved from algolia
6762
+ */
6763
+
6764
+ function getIndices(obj) {
6765
+ var indices = {};
6766
+
6767
+ forEach(obj, function(val, idx) { indices[val] = idx; });
6768
+
6769
+ return indices;
6770
+ }
6771
+
6772
+ function assignFacetStats(dest, facetStats, key) {
6773
+ if (facetStats && facetStats[key]) {
6774
+ dest.stats = facetStats[key];
6775
+ }
6776
+ }
6777
+
6778
+ function findMatchingHierarchicalFacetFromAttributeName(hierarchicalFacets, hierarchicalAttributeName) {
6779
+ return find(
6780
+ hierarchicalFacets,
6781
+ function facetKeyMatchesAttribute(hierarchicalFacet) {
6782
+ return includes(hierarchicalFacet.attributes, hierarchicalAttributeName);
6783
+ }
6784
+ );
6785
+ }
6786
+
6787
+ /**
6788
+ * Constructor for SearchResults
6789
+ * @class
6790
+ * @classdesc SearchResults contains the results of a query to Algolia using the
6791
+ * {@link AlgoliaSearchHelper}.
6792
+ * @param {SearchParameters} state state that led to the response
6793
+ * @param {object} algoliaResponse the response from algolia client
6794
+ * @example <caption>SearchResults of the first query in <a href="http://demos.algolia.com/instant-search-demo">the instant search demo</a></caption>
6795
+ {
6796
+ "hitsPerPage": 10,
6797
+ "processingTimeMS": 2,
6798
+ "facets": [
6799
+ {
6800
+ "name": "type",
6801
+ "data": {
6802
+ "HardGood": 6627,
6803
+ "BlackTie": 550,
6804
+ "Music": 665,
6805
+ "Software": 131,
6806
+ "Game": 456,
6807
+ "Movie": 1571
6808
+ },
6809
+ "exhaustive": false
6810
+ },
6811
+ {
6812
+ "exhaustive": false,
6813
+ "data": {
6814
+ "Free shipping": 5507
6815
+ },
6816
+ "name": "shipping"
6817
+ }
6818
+ ],
6819
+ "hits": [
6820
+ {
6821
+ "thumbnailImage": "http://img.bbystatic.com/BestBuy_US/images/products/1688/1688832_54x108_s.gif",
6822
+ "_highlightResult": {
6823
+ "shortDescription": {
6824
+ "matchLevel": "none",
6825
+ "value": "Safeguard your PC, Mac, Android and iOS devices with comprehensive Internet protection",
6826
+ "matchedWords": []
6827
+ },
6828
+ "category": {
6829
+ "matchLevel": "none",
6830
+ "value": "Computer Security Software",
6831
+ "matchedWords": []
6832
+ },
6833
+ "manufacturer": {
6834
+ "matchedWords": [],
6835
+ "value": "Webroot",
6836
+ "matchLevel": "none"
6837
+ },
6838
+ "name": {
6839
+ "value": "Webroot SecureAnywhere Internet Security (3-Device) (1-Year Subscription) - Mac/Windows",
6840
+ "matchedWords": [],
6841
+ "matchLevel": "none"
6842
+ }
6843
+ },
6844
+ "image": "http://img.bbystatic.com/BestBuy_US/images/products/1688/1688832_105x210_sc.jpg",
6845
+ "shipping": "Free shipping",
6846
+ "bestSellingRank": 4,
6847
+ "shortDescription": "Safeguard your PC, Mac, Android and iOS devices with comprehensive Internet protection",
6848
+ "url": "http://www.bestbuy.com/site/webroot-secureanywhere-internet-security-3-devi…d=1219060687969&skuId=1688832&cmp=RMX&ky=2d3GfEmNIzjA0vkzveHdZEBgpPCyMnLTJ",
6849
+ "name": "Webroot SecureAnywhere Internet Security (3-Device) (1-Year Subscription) - Mac/Windows",
6850
+ "category": "Computer Security Software",
6851
+ "salePrice_range": "1 - 50",
6852
+ "objectID": "1688832",
6853
+ "type": "Software",
6854
+ "customerReviewCount": 5980,
6855
+ "salePrice": 49.99,
6856
+ "manufacturer": "Webroot"
6857
+ },
6858
+ ....
6859
+ ],
6860
+ "nbHits": 10000,
6861
+ "disjunctiveFacets": [
6862
+ {
6863
+ "exhaustive": false,
6864
+ "data": {
6865
+ "5": 183,
6866
+ "12": 112,
6867
+ "7": 149,
6868
+ ...
6869
+ },
6870
+ "name": "customerReviewCount",
6871
+ "stats": {
6872
+ "max": 7461,
6873
+ "avg": 157.939,
6874
+ "min": 1
6875
+ }
6876
+ },
6877
+ {
6878
+ "data": {
6879
+ "Printer Ink": 142,
6880
+ "Wireless Speakers": 60,
6881
+ "Point & Shoot Cameras": 48,
6882
+ ...
6883
+ },
6884
+ "name": "category",
6885
+ "exhaustive": false
6886
+ },
6887
+ {
6888
+ "exhaustive": false,
6889
+ "data": {
6890
+ "> 5000": 2,
6891
+ "1 - 50": 6524,
6892
+ "501 - 2000": 566,
6893
+ "201 - 500": 1501,
6894
+ "101 - 200": 1360,
6895
+ "2001 - 5000": 47
6896
+ },
6897
+ "name": "salePrice_range"
6898
+ },
6899
+ {
6900
+ "data": {
6901
+ "Dynex™": 202,
6902
+ "Insignia™": 230,
6903
+ "PNY": 72,
6904
+ ...
6905
+ },
6906
+ "name": "manufacturer",
6907
+ "exhaustive": false
6908
+ }
6909
+ ],
6910
+ "query": "",
6911
+ "nbPages": 100,
6912
+ "page": 0,
6913
+ "index": "bestbuy"
6914
+ }
6915
+ **/
6916
+ function SearchResults(state, algoliaResponse) {
6917
+ var mainSubResponse = algoliaResponse.results[0];
6918
+
6919
+ /**
6920
+ * query used to generate the results
6921
+ * @member {string}
6922
+ */
6923
+ this.query = mainSubResponse.query;
6924
+ /**
6925
+ * all the records that match the search parameters. It also contains _highlightResult,
6926
+ * which describe which and how the attributes are matched.
6927
+ * @member {object[]}
6928
+ */
6929
+ this.hits = mainSubResponse.hits;
6930
+ /**
6931
+ * index where the results come from
6932
+ * @member {string}
6933
+ */
6934
+ this.index = mainSubResponse.index;
6935
+ /**
6936
+ * number of hits per page requested
6937
+ * @member {number}
6938
+ */
6939
+ this.hitsPerPage = mainSubResponse.hitsPerPage;
6940
+ /**
6941
+ * total number of hits of this query on the index
6942
+ * @member {number}
6943
+ */
6944
+ this.nbHits = mainSubResponse.nbHits;
6945
+ /**
6946
+ * total number of pages with respect to the number of hits per page and the total number of hits
6947
+ * @member {number}
6948
+ */
6949
+ this.nbPages = mainSubResponse.nbPages;
6950
+ /**
6951
+ * current page
6952
+ * @member {number}
6953
+ */
6954
+ this.page = mainSubResponse.page;
6955
+ /**
6956
+ * sum of the processing time of all the queries
6957
+ * @member {number}
6958
+ */
6959
+ this.processingTimeMS = sum(algoliaResponse.results, 'processingTimeMS');
6960
+ /**
6961
+ * disjunctive facets results
6962
+ * @member {SearchResults.Facet[]}
6963
+ */
6964
+ this.disjunctiveFacets = [];
6965
+ /**
6966
+ * disjunctive facets results
6967
+ * @member {SearchResults.Facet[]}
6968
+ */
6969
+ this.hierarchicalFacets = map(state.hierarchicalFacets, function initFutureTree() {
6970
+ return [];
6971
+ });
6972
+ /**
6973
+ * other facets results
6974
+ * @member {SearchResults.Facet[]}
6975
+ */
6976
+ this.facets = [];
6977
+
6978
+ var disjunctiveFacets = state.getRefinedDisjunctiveFacets();
6979
+
6980
+ var facetsIndices = getIndices(state.facets);
6981
+ var disjunctiveFacetsIndices = getIndices(state.disjunctiveFacets);
6982
+ var disjunctiveIndexResult;
6983
+
6984
+ // Since we send request only for disjunctive facets that have been refined,
6985
+ // we get the facets informations from the first, general, response.
6986
+ forEach(mainSubResponse.facets, function(facetValueObject, facetKey) {
6987
+ var hierarchicalFacet;
6988
+
6989
+ if (hierarchicalFacet = findMatchingHierarchicalFacetFromAttributeName(state.hierarchicalFacets, facetKey)) {
6990
+ this.hierarchicalFacets[findIndex(state.hierarchicalFacets, {name: hierarchicalFacet.name})].push({
6991
+ attribute: facetKey,
6992
+ data: facetValueObject,
6993
+ exhaustive: mainSubResponse.exhaustiveFacetsCount
6994
+ });
6995
+ } else {
6996
+ var isFacetDisjunctive = indexOf(state.disjunctiveFacets, facetKey) !== -1;
6997
+ var position = isFacetDisjunctive ? disjunctiveFacetsIndices[facetKey] :
6998
+ facetsIndices[facetKey];
6999
+
7000
+ if (isFacetDisjunctive) {
7001
+ this.disjunctiveFacets[position] = {
7002
+ name: facetKey,
7003
+ data: facetValueObject,
7004
+ exhaustive: mainSubResponse.exhaustiveFacetsCount
7005
+ };
7006
+ assignFacetStats(this.disjunctiveFacets[position], mainSubResponse.facets_stats, facetKey);
7007
+ } else {
7008
+ this.facets[position] = {
7009
+ name: facetKey,
7010
+ data: facetValueObject,
7011
+ exhaustive: mainSubResponse.exhaustiveFacetsCount
7012
+ };
7013
+ assignFacetStats(this.facets[position], mainSubResponse.facets_stats, facetKey);
7014
+ }
7015
+ }
7016
+ }, this);
7017
+
7018
+ // aggregate the refined disjunctive facets
7019
+ forEach(disjunctiveFacets, function(disjunctiveFacet, idx) {
7020
+ disjunctiveIndexResult = idx + 1;
7021
+ var result = algoliaResponse.results[disjunctiveIndexResult];
7022
+ // TODO if alwaysGetRootLevel && current refinement > level 2 (in another loop)
7023
+ var hierarchicalFacet = state.getHierarchicalFacetByName(disjunctiveFacet);
7024
+
7025
+ // There should be only item in facets.
7026
+ forEach(result.facets, function(facetResults, dfacet) {
7027
+ var position;
7028
+
7029
+ if (hierarchicalFacet) {
7030
+ position = findIndex(state.hierarchicalFacets, {name: hierarchicalFacet.name});
7031
+ var attributeIndex = findIndex(this.hierarchicalFacets[position], {attribute: dfacet});
7032
+ // if (hierarchicalFacet.alwaysGetRootLevel) {
7033
+ // // when we always get root levels, if the hits refinement is `beers > IPA` (count: 5),
7034
+ // // then the disjunctive values will be `beers` (count: 100),
7035
+ // // but we do not want to display
7036
+ // // | beers (100)
7037
+ // // > IPA (5)
7038
+ // // We want
7039
+ // // | beers (5)
7040
+ // // > IPA (5)
7041
+ // var currentRefinement = state.getHierarchicalRefinement(hierarchicalFacet.name);
7042
+ // var defaultData = {};
7043
+
7044
+ // if (currentRefinement && currentRefinement.length > 0) {
7045
+ // var root = currentRefinement[0].split(state._getHierarchicalFacetSeparator(hierarchicalFacet))[0];
7046
+ // defaultData[root] = this.hierarchicalFacets[position][attributeIndex].data[root];
7047
+ // }
7048
+
7049
+ // this.hierarchicalFacets[position][attributeIndex].data = defaults(defaultData, facetResults, this.hierarchicalFacets[position][attributeIndex].data);
7050
+ // } else {
7051
+ this.hierarchicalFacets[position][attributeIndex].data = merge({}, this.hierarchicalFacets[position][attributeIndex].data, facetResults);
7052
+ // }
7053
+ } else {
7054
+ position = disjunctiveFacetsIndices[dfacet];
7055
+
7056
+ var dataFromMainRequest = mainSubResponse.facets && mainSubResponse.facets[dfacet] || {};
7057
+
7058
+ this.disjunctiveFacets[position] = {
7059
+ name: dfacet,
7060
+ data: defaults({}, facetResults, dataFromMainRequest),
7061
+ exhaustive: result.exhaustiveFacetsCount
7062
+ };
7063
+ assignFacetStats(this.disjunctiveFacets[position], result.facets_stats, dfacet);
7064
+
7065
+ if (state.disjunctiveFacetsRefinements[dfacet]) {
7066
+ forEach(state.disjunctiveFacetsRefinements[dfacet], function(refinementValue) {
7067
+ // add the disjunctive refinements if it is no more retrieved
7068
+ if (!this.disjunctiveFacets[position].data[refinementValue] &&
7069
+ indexOf(state.disjunctiveFacetsRefinements[dfacet], refinementValue) > -1) {
7070
+ this.disjunctiveFacets[position].data[refinementValue] = 0;
7071
+ }
7072
+ }, this);
7073
+ }
7074
+ }
7075
+ }, this);
7076
+ }, this);
7077
+
7078
+ // if we have some root level values for hierarchical facets, merge them
7079
+ forEach(state.getRefinedHierarchicalFacets(), function(refinedFacet) {
7080
+ var hierarchicalFacet = state.getHierarchicalFacetByName(refinedFacet);
7081
+
7082
+ if (hierarchicalFacet.alwaysGetRootLevel !== true) {
7083
+ return;
7084
+ }
7085
+
7086
+ var currentRefinement = state.getHierarchicalRefinement(refinedFacet);
7087
+ // if we are already at a root refinement (or no refinement at all), there is no
7088
+ // root level values request
7089
+ if (currentRefinement.length === 0 || currentRefinement[0].split(state._getHierarchicalFacetSeparator(hierarchicalFacet)).length < 2) {
7090
+ return;
7091
+ }
7092
+
7093
+ disjunctiveIndexResult++;
7094
+
7095
+ var result = algoliaResponse.results[disjunctiveIndexResult];
7096
+
7097
+ forEach(result.facets, function(facetResults, dfacet) {
7098
+ var position = findIndex(state.hierarchicalFacets, {name: hierarchicalFacet.name});
7099
+ var attributeIndex = findIndex(this.hierarchicalFacets[position], {attribute: dfacet});
7100
+
7101
+ // when we always get root levels, if the hits refinement is `beers > IPA` (count: 5),
7102
+ // then the disjunctive values will be `beers` (count: 100),
7103
+ // but we do not want to display
7104
+ // | beers (100)
7105
+ // > IPA (5)
7106
+ // We want
7107
+ // | beers (5)
7108
+ // > IPA (5)
7109
+ var defaultData = {};
7110
+
7111
+ if (currentRefinement.length > 0) {
7112
+ var root = currentRefinement[0].split(state._getHierarchicalFacetSeparator(hierarchicalFacet))[0];
7113
+ defaultData[root] = this.hierarchicalFacets[position][attributeIndex].data[root];
7114
+ }
7115
+
7116
+ this.hierarchicalFacets[position][attributeIndex].data = defaults(defaultData, facetResults, this.hierarchicalFacets[position][attributeIndex].data);
7117
+ }, this);
7118
+ }, this);
7119
+
7120
+ // add the excludes
7121
+ forEach(state.facetsExcludes, function(excludes, facetName) {
7122
+ var position = facetsIndices[facetName];
7123
+
7124
+ this.facets[position] = {
7125
+ name: facetName,
7126
+ data: mainSubResponse.facets[facetName],
7127
+ exhaustive: mainSubResponse.exhaustiveFacetsCount
7128
+ };
7129
+ forEach(excludes, function(facetValue) {
7130
+ this.facets[position] = this.facets[position] || {name: facetName};
7131
+ this.facets[position].data = this.facets[position].data || {};
7132
+ this.facets[position].data[facetValue] = 0;
7133
+ }, this);
7134
+ }, this);
7135
+
7136
+ this.hierarchicalFacets = map(this.hierarchicalFacets, generateHierarchicalTree(state));
7137
+
7138
+ this.facets = compact(this.facets);
7139
+ this.disjunctiveFacets = compact(this.disjunctiveFacets);
7140
+
7141
+ this._state = state;
7142
+ }
7143
+
7144
+ /**
7145
+ * Get a facet object with its name
7146
+ * @param {string} name name of the attribute facetted
7147
+ * @return {SearchResults.Facet} the facet object
7148
+ */
7149
+ SearchResults.prototype.getFacetByName = function(name) {
7150
+ var predicate = {name: name};
7151
+
7152
+ return find(this.facets, predicate) ||
7153
+ find(this.disjunctiveFacets, predicate) ||
7154
+ find(this.hierarchicalFacets, predicate);
7155
+ };
7156
+
7157
+ module.exports = SearchResults;
7158
+
7159
+ },{"./generate-hierarchical-tree":153,"lodash/array/compact":3,"lodash/array/findIndex":4,"lodash/array/indexOf":5,"lodash/collection/find":10,"lodash/collection/forEach":11,"lodash/collection/includes":12,"lodash/collection/map":13,"lodash/collection/sum":17,"lodash/object/defaults":139,"lodash/object/merge":142}],155:[function(require,module,exports){
7160
+ 'use strict';
7161
+
7162
+ var SearchParameters = require('./SearchParameters');
7163
+ var SearchResults = require('./SearchResults');
7164
+ var util = require('util');
7165
+ var events = require('events');
7166
+ var forEach = require('lodash/collection/forEach');
7167
+ var isEmpty = require('lodash/lang/isEmpty');
7168
+ var bind = require('lodash/function/bind');
7169
+ var reduce = require('lodash/collection/reduce');
7170
+ var map = require('lodash/collection/map');
7171
+ var trim = require('lodash/string/trim');
7172
+ var merge = require('lodash/object/merge');
7173
+
7174
+ /**
7175
+ * Initialize a new AlgoliaSearchHelper
7176
+ * @class
7177
+ * @classdesc The AlgoliaSearchHelper is a class that ease the management of the
7178
+ * search. It provides an event based interface for search callbacks:
7179
+ * - change: when the internal search state is changed.
7180
+ * This event contains a {@link SearchParameters} object and the {@link SearchResults} of the last result if any.
7181
+ * - result: when the response is retrieved from Algolia and is processed.
7182
+ * This event contains a {@link SearchResults} object and the {@link SearchParameters} corresponding to this answer.
7183
+ * - error: when the response is an error. This event contains the error returned by the server.
7184
+ * @param {AlgoliaSearch} client an AlgoliaSearch client
7185
+ * @param {string} index the index name to query
7186
+ * @param {SearchParameters | object} options an object defining the initial config of the search. It doesn't have to be a {SearchParameters}, just an object containing the properties you need from it.
7187
+ */
7188
+ function AlgoliaSearchHelper(client, index, options) {
7189
+ this.client = client;
7190
+ this.index = index;
7191
+ this.state = SearchParameters.make(options);
7192
+ this.lastResults = null;
7193
+ this._queryId = 0;
7194
+ this._lastQueryIdReceived = -1;
7195
+ }
7196
+
7197
+ util.inherits(AlgoliaSearchHelper, events.EventEmitter);
7198
+
7199
+ /**
7200
+ * Start the search with the parameters set in the state.
7201
+ * @return {AlgoliaSearchHelper}
7202
+ */
7203
+ AlgoliaSearchHelper.prototype.search = function() {
7204
+ this._search();
7205
+ return this;
7206
+ };
7207
+
7208
+ /**
7209
+ * Sets the query. Also sets the current page to 0.
7210
+ * @param {string} q the user query
7211
+ * @return {AlgoliaSearchHelper}
7212
+ */
7213
+ AlgoliaSearchHelper.prototype.setQuery = function(q) {
7214
+ this.state = this.state.setQuery(q);
7215
+ this._change();
7216
+ return this;
7217
+ };
7218
+
7219
+ /**
7220
+ * Remove all refinements (disjunctive + conjunctive + excludes + numeric filters)
7221
+ * @param {string} [name] - If given, name of the facet / attribute on which we want to remove all refinements
7222
+ * @return {AlgoliaSearchHelper}
7223
+ */
7224
+ AlgoliaSearchHelper.prototype.clearRefinements = function(name) {
7225
+ this.state = this.state.clearRefinements(name);
7226
+ this._change();
7227
+ return this;
7228
+ };
7229
+
7230
+ /**
7231
+ * Remove all the tag filtering
7232
+ * @return {AlgoliaSearchHelper}
7233
+ */
7234
+ AlgoliaSearchHelper.prototype.clearTags = function() {
7235
+ this.state = this.state.clearTags();
7236
+ this._change();
7237
+ return this;
7238
+ };
7239
+
7240
+ /**
7241
+ * Ensure a facet refinement exists
7242
+ * @param {string} facet the facet to refine
7243
+ * @param {string} value the associated value (will be converted to string)
7244
+ * @return {AlgoliaSearchHelper}
7245
+ */
7246
+ AlgoliaSearchHelper.prototype.addDisjunctiveRefine = function(facet, value) {
7247
+ this.state = this.state.addDisjunctiveFacetRefinement(facet, value);
7248
+ this._change();
7249
+ return this;
7250
+ };
7251
+
7252
+ /**
7253
+ * Add a numeric refinement on the given attribute
7254
+ * @param {string} attribute the attribute on which the numeric filter applies
7255
+ * @param {string} operator the operator of the filter
7256
+ * @param {number} value the value of the filter
7257
+ * @return {AlgoliaSearchHelper}
7258
+ */
7259
+ AlgoliaSearchHelper.prototype.addNumericRefinement = function(attribute, operator, value) {
7260
+ this.state = this.state.addNumericRefinement(attribute, operator, value);
7261
+ this._change();
7262
+ return this;
7263
+ };
7264
+
7265
+ /**
7266
+ * Ensure a facet refinement exists
7267
+ * @param {string} facet the facet to refine
7268
+ * @param {string} value the associated value (will be converted to string)
7269
+ * @return {AlgoliaSearchHelper}
7270
+ */
7271
+ AlgoliaSearchHelper.prototype.addRefine = function(facet, value) {
7272
+ this.state = this.state.addFacetRefinement(facet, value);
7273
+ this._change();
7274
+ return this;
7275
+ };
7276
+
7277
+ /**
7278
+ * Ensure a facet exclude exists
7279
+ * @param {string} facet the facet to refine
7280
+ * @param {string} value the associated value (will be converted to string)
7281
+ * @return {AlgoliaSearchHelper}
7282
+ */
7283
+ AlgoliaSearchHelper.prototype.addExclude = function(facet, value) {
7284
+ this.state = this.state.addExcludeRefinement(facet, value);
7285
+ this._change();
7286
+ return this;
7287
+ };
7288
+
7289
+ /**
7290
+ * Add a tag refinement
7291
+ * @param {string} tag the tag to add to the filter
7292
+ * @return {AlgoliaSearchHelper}
7293
+ */
7294
+ AlgoliaSearchHelper.prototype.addTag = function(tag) {
7295
+ this.state = this.state.addTagRefinement(tag);
7296
+ this._change();
7297
+ return this;
7298
+ };
7299
+
7300
+ /**
7301
+ * Remove a numeric filter.
7302
+ * @param {string} attribute the attribute on which the numeric filter applies
7303
+ * @param {string} operator the operator of the filter
7304
+ * @param {number} value the value of the filter
7305
+ * @return {AlgoliaSearchHelper}
7306
+ */
7307
+ AlgoliaSearchHelper.prototype.removeNumericRefinement = function(attribute, operator, value) {
7308
+ this.state = this.state.removeNumericRefinement(attribute, operator, value);
7309
+ this._change();
7310
+ return this;
7311
+ };
7312
+
7313
+ /**
7314
+ * Ensure a facet refinement does not exist
7315
+ * @param {string} facet the facet to refine
7316
+ * @param {string} value the associated value
7317
+ * @return {AlgoliaSearchHelper}
7318
+ */
7319
+ AlgoliaSearchHelper.prototype.removeDisjunctiveRefine = function(facet, value) {
7320
+ this.state = this.state.removeDisjunctiveFacetRefinement(facet, value);
7321
+ this._change();
7322
+ return this;
7323
+ };
7324
+
7325
+ /**
7326
+ * Ensure a facet refinement does not exist
7327
+ * @param {string} facet the facet to refine
7328
+ * @param {string} value the associated value
7329
+ * @return {AlgoliaSearchHelper}
7330
+ */
7331
+ AlgoliaSearchHelper.prototype.removeRefine = function(facet, value) {
7332
+ this.state = this.state.removeFacetRefinement(facet, value);
7333
+ this._change();
7334
+ return this;
7335
+ };
7336
+
7337
+ /**
7338
+ * Ensure a facet exclude does not exist
7339
+ * @param {string} facet the facet to refine
7340
+ * @param {string} value the associated value
7341
+ * @return {AlgoliaSearchHelper}
7342
+ */
7343
+ AlgoliaSearchHelper.prototype.removeExclude = function(facet, value) {
7344
+ this.state = this.state.removeExcludeRefinement(facet, value);
7345
+ this._change();
7346
+ return this;
7347
+ };
7348
+
7349
+ /**
7350
+ * Ensure that a tag is not filtering the results
7351
+ * @param {string} tag tag to remove from the filter
7352
+ * @return {AlgoliaSearchHelper}
7353
+ */
7354
+ AlgoliaSearchHelper.prototype.removeTag = function(tag) {
7355
+ this.state = this.state.removeTagRefinement(tag);
7356
+ this._change();
7357
+ return this;
7358
+ };
7359
+
7360
+ /**
7361
+ * Toggle refinement state of an exclude
7362
+ * @param {string} facet the facet to refine
7363
+ * @param {string} value the associated value
7364
+ * @return {AlgoliaSearchHelper}
7365
+ */
7366
+ AlgoliaSearchHelper.prototype.toggleExclude = function(facet, value) {
7367
+ this.state = this.state.toggleExcludeFacetRefinement(facet, value);
7368
+ this._change();
7369
+ return this;
7370
+ };
7371
+
7372
+ /**
7373
+ * Toggle refinement state of a facet
7374
+ * @param {string} facet the facet to refine
7375
+ * @param {string} value the associated value
7376
+ * @return {AlgoliaSearchHelper}
7377
+ * @throws will throw an error if the facet is not declared in the settings of the helper
7378
+ */
7379
+ AlgoliaSearchHelper.prototype.toggleRefine = function(facet, value) {
7380
+ if (this.state.isHierarchicalFacet(facet)) {
7381
+ this.state = this.state.toggleHierarchicalFacetRefinement(facet, value);
7382
+ } else if (this.state.isConjunctiveFacet(facet)) {
7383
+ this.state = this.state.toggleFacetRefinement(facet, value);
7384
+ } else if (this.state.isDisjunctiveFacet(facet)) {
7385
+ this.state = this.state.toggleDisjunctiveFacetRefinement(facet, value);
7386
+ } else {
7387
+ throw new Error('Cannot refine the undeclared facet ' + facet +
7388
+ '; it should be added to the helper options facets or disjunctiveFacets');
7389
+ }
7390
+
7391
+ this._change();
7392
+ return this;
7393
+ };
7394
+
7395
+ /**
7396
+ * Toggle tag refinement
7397
+ * @param {string} tag tag to remove or add
7398
+ * @return {AlgoliaSearchHelper}
7399
+ */
7400
+ AlgoliaSearchHelper.prototype.toggleTag = function(tag) {
7401
+ this.state = this.state.toggleTagRefinement(tag);
7402
+ this._change();
7403
+ return this;
7404
+ };
7405
+
7406
+ /**
7407
+ * Go to next page
7408
+ * @return {AlgoliaSearchHelper}
7409
+ */
7410
+ AlgoliaSearchHelper.prototype.nextPage = function() {
7411
+ return this.setCurrentPage(this.state.page + 1);
7412
+ };
7413
+
7414
+ /**
7415
+ * Go to previous page
7416
+ * @return {AlgoliaSearchHelper}
7417
+ */
7418
+ AlgoliaSearchHelper.prototype.previousPage = function() {
7419
+ return this.setCurrentPage(this.state.page - 1);
7420
+ };
7421
+
7422
+ /**
7423
+ * Change the current page
7424
+ * @param {integer} page The page number
7425
+ * @return {AlgoliaSearchHelper}
7426
+ */
7427
+ AlgoliaSearchHelper.prototype.setCurrentPage = function(page) {
7428
+ if (page < 0) throw new Error('Page requested below 0.');
7429
+
7430
+ this.state = this.state.setPage(page);
7431
+ this._change();
7432
+ return this;
7433
+ };
7434
+
7435
+ /**
7436
+ * Configure the underlying index name
7437
+ * @param {string} name the index name
7438
+ * @return {AlgoliaSearchHelper}
7439
+ */
7440
+ AlgoliaSearchHelper.prototype.setIndex = function(name) {
7441
+ this.index = name;
7442
+ this.setCurrentPage(0);
7443
+ return this;
7444
+ };
7445
+
7446
+ /**
7447
+ * Update any single parameter of the state/configuration (based on SearchParameters).
7448
+ * @param {string} parameter name of the parameter to update
7449
+ * @param {any} value new value of the parameter
7450
+ * @return {AlgoliaSearchHelper}
7451
+ */
7452
+ AlgoliaSearchHelper.prototype.setQueryParameter = function(parameter, value) {
7453
+ var newState = this.state.setQueryParameter(parameter, value);
7454
+
7455
+ if (this.state === newState) return this;
7456
+
7457
+ this.state = newState;
7458
+ this._change();
7459
+ return this;
7460
+ };
7461
+
7462
+ /**
7463
+ * Set the whole state (warning: will erase previous state)
7464
+ * @param {SearchParameters} newState the whole new state
7465
+ * @return {AlgoliaSearchHelper}
7466
+ */
7467
+ AlgoliaSearchHelper.prototype.setState = function(newState) {
7468
+ this.state = new SearchParameters(newState);
7469
+ this._change();
7470
+ return this;
7471
+ };
7472
+
7473
+ /**
7474
+ * Get the current search state stored in the helper. This object is immutable.
7475
+ * @return {SearchParameters}
7476
+ */
7477
+ AlgoliaSearchHelper.prototype.getState = function() {
7478
+ return this.state;
7479
+ };
7480
+
7481
+ /**
7482
+ * Override the current state without triggering a change event.
7483
+ * Do not use this method unless you know what you are doing. (see the example
7484
+ * for a legit use case)
7485
+ * @param {SearchParameters} newState the whole new state
7486
+ * @return {AlgoliaSearchHelper}
7487
+ * @example
7488
+ * helper.on('change', function(state){
7489
+ * // In this function you might want to find a way to store the state in the url/history
7490
+ * updateYourURL(state)
7491
+ * })
7492
+ * window.onpopstate = function(event){
7493
+ * // This is naive though as you should check if the state is really defined etc.
7494
+ * helper.overrideStateWithoutTriggeringChangeEvent(event.state).search()
7495
+ * }
7496
+ */
7497
+ AlgoliaSearchHelper.prototype.overrideStateWithoutTriggeringChangeEvent = function(newState) {
7498
+ this.state = new SearchParameters(newState);
7499
+ return this;
7500
+ };
7501
+
7502
+ /**
7503
+ * Check the refinement state of a given value for a facet
7504
+ * @param {string} facet the facet
7505
+ * @param {string} value the associated value
7506
+ * @return {boolean} true if refined
7507
+ */
7508
+ AlgoliaSearchHelper.prototype.isRefined = function(facet, value) {
7509
+ if (this.state.isConjunctiveFacet(facet)) {
7510
+ return this.state.isFacetRefined(facet, value);
7511
+ } else if (this.state.isDisjunctiveFacet(facet)) {
7512
+ return this.state.isDisjunctiveFacetRefined(facet, value);
7513
+ }
7514
+
7515
+ throw new Error(facet +
7516
+ ' is not properly defined in this helper configuration' +
7517
+ '(use the facets or disjunctiveFacets keys to configure it)');
7518
+ };
7519
+
7520
+ /**
7521
+ * Check if the attribute has any numeric, disjunctive or conjunctive refinements
7522
+ * @param {string} attribute the name of the attribute
7523
+ * @return {boolean} true if the attribute is filtered by at least one value
7524
+ */
7525
+ AlgoliaSearchHelper.prototype.hasRefinements = function(attribute) {
7526
+ var attributeHasNumericRefinements = !isEmpty(this.state.getNumericRefinements(attribute));
7527
+ var isFacetDeclared = this.state.isConjunctiveFacet(attribute) || this.state.isDisjunctiveFacet(attribute);
7528
+
7529
+ if (!attributeHasNumericRefinements && isFacetDeclared) {
7530
+ return this.state.isFacetRefined(attribute);
7531
+ }
7532
+
7533
+ return attributeHasNumericRefinements;
7534
+ };
7535
+
7536
+ /**
7537
+ * Check the exclude state of a facet
7538
+ * @param {string} facet the facet
7539
+ * @param {string} value the associated value
7540
+ * @return {boolean} true if refined
7541
+ */
7542
+ AlgoliaSearchHelper.prototype.isExcluded = function(facet, value) {
7543
+ return this.state.isExcludeRefined(facet, value);
7544
+ };
7545
+
7546
+ /**
7547
+ * Check the refinement state of the disjunctive facet
7548
+ * @param {string} facet the facet
7549
+ * @param {string} value the associated value
7550
+ * @return {boolean} true if refined
7551
+ */
7552
+ AlgoliaSearchHelper.prototype.isDisjunctiveRefined = function(facet, value) {
7553
+ return this.state.isDisjunctiveFacetRefined(facet, value);
7554
+ };
7555
+
7556
+ /**
7557
+ * Check if the string is a currently filtering tag
7558
+ * @param {string} tag tag to check
7559
+ * @return {boolean}
7560
+ */
7561
+ AlgoliaSearchHelper.prototype.isTagRefined = function(tag) {
7562
+ return this.state.isTagRefined(tag);
7563
+ };
7564
+
7565
+ /**
7566
+ * Get the underlying configured index name
7567
+ * @return {string}
7568
+ */
7569
+ AlgoliaSearchHelper.prototype.getIndex = function() {
7570
+ return this.index;
7571
+ };
7572
+
7573
+ /**
7574
+ * Get the currently selected page
7575
+ * @return {number} the current page
7576
+ */
7577
+ AlgoliaSearchHelper.prototype.getCurrentPage = function() {
7578
+ return this.state.page;
7579
+ };
7580
+
7581
+ /**
7582
+ * Get all the filtering tags
7583
+ * @return {string[]}
7584
+ */
7585
+ AlgoliaSearchHelper.prototype.getTags = function() {
7586
+ return this.state.tagRefinements;
7587
+ };
7588
+
7589
+ /**
7590
+ * Get a parameter of the search by its name
7591
+ * @param {string} parameterName the parameter name
7592
+ * @return {any} the parameter value
7593
+ */
7594
+ AlgoliaSearchHelper.prototype.getQueryParameter = function(parameterName) {
7595
+ return this.state.getQueryParameter(parameterName);
7596
+ };
7597
+
7598
+ /**
7599
+ * Get the list of refinements for a given attribute.
7600
+ * @param {string} facetName attribute name used for facetting
7601
+ * @return {Refinement[]} All Refinement are objects that contain a value, and a type. Numeric also contains an operator.
7602
+ */
7603
+ AlgoliaSearchHelper.prototype.getRefinements = function(facetName) {
7604
+ var refinements = [];
7605
+
7606
+ if (this.state.isConjunctiveFacet(facetName)) {
7607
+ var conjRefinements = this.state.getConjunctiveRefinements(facetName);
7608
+
7609
+ forEach(conjRefinements, function(r) {
7610
+ refinements.push({
7611
+ value: r,
7612
+ type: 'conjunctive'
7613
+ });
7614
+ });
7615
+
7616
+ var excludeRefinements = this.state.getExcludeRefinements(facetName);
7617
+
7618
+ forEach(excludeRefinements, function(r) {
7619
+ refinements.push({
7620
+ value: r,
7621
+ type: 'exclude'
7622
+ });
7623
+ });
7624
+ } else if (this.state.isDisjunctiveFacet(facetName)) {
7625
+ var disjRefinements = this.state.getDisjunctiveRefinements(facetName);
7626
+
7627
+ forEach(disjRefinements, function(r) {
7628
+ refinements.push({
7629
+ value: r,
7630
+ type: 'disjunctive'
7631
+ });
7632
+ });
7633
+ }
7634
+
7635
+ var numericRefinements = this.state.getNumericRefinements(facetName);
7636
+
7637
+ forEach(numericRefinements, function(value, operator) {
7638
+ refinements.push({
7639
+ value: value,
7640
+ operator: operator,
7641
+ type: 'numeric'
7642
+ });
7643
+ });
7644
+
7645
+ return refinements;
7646
+ };
7647
+
7648
+ /**
7649
+ * Get the current breadcrumb for a hierarchical facet, as an array
7650
+ * @param {string} facetName Hierarchical facet name
7651
+ * @return {array}
7652
+ */
7653
+ AlgoliaSearchHelper.prototype.getHierarchicalFacetBreadcrumb = function(facetName) {
7654
+ return map(
7655
+ this
7656
+ .state
7657
+ .getHierarchicalRefinement(facetName)[0]
7658
+ .split(this.state._getHierarchicalFacetSeparator(
7659
+ this.state.getHierarchicalFacetByName(facetName)
7660
+ )), function trimName(facetValue) { return trim(facetValue); }
7661
+ );
7662
+ };
7663
+
7664
+ // /////////// PRIVATE
7665
+
7666
+ /**
7667
+ * Perform the underlying queries
7668
+ * @private
7669
+ * @return {undefined}
7670
+ */
7671
+ AlgoliaSearchHelper.prototype._search = function() {
7672
+ var state = this.state;
7673
+
7674
+ this.client.search(this._getQueries(),
7675
+ bind(this._handleResponse,
7676
+ this,
7677
+ state,
7678
+ this._queryId++));
7679
+ };
7680
+
7681
+ /**
7682
+ * Get all the queries to send to the client, those queries can used directly
7683
+ * with the Algolia client.
7684
+ * @private
7685
+ * @return {object[]} The queries
7686
+ */
7687
+ AlgoliaSearchHelper.prototype._getQueries = function getQueries() {
7688
+ var queries = [];
7689
+
7690
+ // One query for the hits
7691
+ queries.push({
7692
+ indexName: this.index,
7693
+ query: this.state.query,
7694
+ params: this._getHitsSearchParams()
7695
+ });
7696
+
7697
+ // One for each disjunctive facets
7698
+ forEach(this.state.getRefinedDisjunctiveFacets(), function(refinedFacet) {
7699
+ queries.push({
7700
+ indexName: this.index,
7701
+ query: this.state.query,
7702
+ params: this._getDisjunctiveFacetSearchParams(refinedFacet)
7703
+ });
7704
+ }, this);
7705
+
7706
+ // maybe more to get the root level of hierarchical facets when activated
7707
+ forEach(this.state.getRefinedHierarchicalFacets(), function(refinedFacet) {
7708
+ var hierarchicalFacet = this.state.getHierarchicalFacetByName(refinedFacet);
7709
+
7710
+ if (hierarchicalFacet.alwaysGetRootLevel !== true) {
7711
+ return;
7712
+ }
7713
+
7714
+ var currentRefinement = this.state.getHierarchicalRefinement(refinedFacet);
7715
+ // if we are deeper than level 0 (starting from `beer > IPA`)
7716
+ // we want to get the root values
7717
+ if (currentRefinement.length > 0 && currentRefinement[0].split(this.state._getHierarchicalFacetSeparator(hierarchicalFacet)).length > 1) {
7718
+ queries.push({
7719
+ indexName: this.index,
7720
+ query: this.state.query,
7721
+ params: this._getDisjunctiveFacetSearchParams(refinedFacet, true)
7722
+ });
7723
+ }
7724
+ }, this);
7725
+
7726
+ return queries;
7727
+ };
7728
+
7729
+ /**
7730
+ * Transform the response as sent by the server and transform it into a user
7731
+ * usable objet that merge the results of all the batch requests.
7732
+ * @private
7733
+ * @param {SearchParameters} state state used for to generate the request
7734
+ * @param {number} queryId id of the current request
7735
+ * @param {Error} err error if any, null otherwise
7736
+ * @param {object} content content of the response
7737
+ * @return {undefined}
7738
+ */
7739
+ AlgoliaSearchHelper.prototype._handleResponse = function(state, queryId, err, content) {
7740
+ if (queryId < this._lastQueryIdReceived) {
7741
+ // Outdated answer
7742
+ return;
7743
+ }
7744
+
7745
+ this._lastQueryIdReceived = queryId;
7746
+
7747
+ if (err) {
7748
+ this.emit('error', err);
7749
+ return;
7750
+ }
7751
+
7752
+ var formattedResponse = this.lastResults = new SearchResults(state, content);
7753
+
7754
+ this.emit('result', formattedResponse, state);
7755
+ };
7756
+
7757
+ /**
7758
+ * Build search parameters used to fetch hits
7759
+ * @private
7760
+ * @return {object.<string, any>}
7761
+ */
7762
+ AlgoliaSearchHelper.prototype._getHitsSearchParams = function() {
7763
+ var facets = this.state.facets
7764
+ .concat(this.state.disjunctiveFacets)
7765
+ .concat(this._getHitsHierarchicalFacetsAttributes());
7766
+
7767
+ var facetFilters = this._getFacetFilters();
7768
+ var numericFilters = this._getNumericFilters();
7769
+ var tagFilters = this._getTagFilters();
7770
+ var additionalParams = {
7771
+ facets: facets,
7772
+ tagFilters: tagFilters
7773
+ };
7774
+
7775
+ if (this.state.distinct === true || this.state.distinct === false) {
7776
+ additionalParams.distinct = this.state.distinct;
7777
+ }
7778
+
7779
+ if (facetFilters.length > 0) {
7780
+ additionalParams.facetFilters = facetFilters;
7781
+ }
7782
+
7783
+ if (numericFilters.length > 0) {
7784
+ additionalParams.numericFilters = numericFilters;
7785
+ }
7786
+
7787
+ return merge(this.state.getQueryParams(), additionalParams);
7788
+ };
7789
+
7790
+ /**
7791
+ * Build search parameters used to fetch a disjunctive facet
7792
+ * @private
7793
+ * @param {string} facet the associated facet name
7794
+ * @return {object}
7795
+ */
7796
+ AlgoliaSearchHelper.prototype._getDisjunctiveFacetSearchParams = function(facet, hierarchicalRootLevel) {
7797
+ var facetFilters = this._getFacetFilters(facet, hierarchicalRootLevel);
7798
+ var numericFilters = this._getNumericFilters(facet);
7799
+ var tagFilters = this._getTagFilters();
7800
+ var additionalParams = {
7801
+ hitsPerPage: 1,
7802
+ page: 0,
7803
+ attributesToRetrieve: [],
7804
+ attributesToHighlight: [],
7805
+ attributesToSnippet: [],
7806
+ tagFilters: tagFilters
7807
+ };
7808
+
7809
+ var hierarchicalFacet = this.state.getHierarchicalFacetByName(facet);
7810
+
7811
+ if (hierarchicalFacet) {
7812
+ additionalParams.facets = this._getDisjunctiveHierarchicalFacetAttribute(hierarchicalFacet, hierarchicalRootLevel);
7813
+ } else {
7814
+ additionalParams.facets = facet;
7815
+ }
7816
+
7817
+ if (this.state.distinct === true || this.state.distinct === false) {
7818
+ additionalParams.distinct = this.state.distinct;
7819
+ }
7820
+
7821
+ if (numericFilters.length > 0) {
7822
+ additionalParams.numericFilters = numericFilters;
7823
+ }
7824
+
7825
+ if (facetFilters.length > 0) {
7826
+ additionalParams.facetFilters = facetFilters;
7827
+ }
7828
+
7829
+ return merge(this.state.getQueryParams(), additionalParams);
7830
+ };
7831
+
7832
+ AlgoliaSearchHelper.prototype.containsRefinement = function(query, facetFilters, numericFilters, tagFilters) {
7833
+ return query ||
7834
+ facetFilters.length !== 0 ||
7835
+ numericFilters.length !== 0 ||
7836
+ tagFilters.length !== 0;
7837
+ };
7838
+
7839
+ /**
7840
+ * Return the numeric filters in an algolia request fashion
7841
+ * @private
7842
+ * @param {string} [facetName] the name of the attribute for which the filters should be excluded
7843
+ * @return {string[]} the numeric filters in the algolia format
7844
+ */
7845
+ AlgoliaSearchHelper.prototype._getNumericFilters = function(facetName) {
7846
+ var numericFilters = [];
7847
+
7848
+ forEach(this.state.numericRefinements, function(operators, attribute) {
7849
+ forEach(operators, function(value, operator) {
7850
+ if (facetName !== attribute) {
7851
+ numericFilters.push(attribute + operator + value);
7852
+ }
7853
+ });
7854
+ });
7855
+
7856
+ return numericFilters;
7857
+ };
7858
+
7859
+ /**
7860
+ * Return the tags filters depending
7861
+ * @private
7862
+ * @return {string}
7863
+ */
7864
+ AlgoliaSearchHelper.prototype._getTagFilters = function() {
7865
+ if (this.state.tagFilters) {
7866
+ return this.state.tagFilters;
7867
+ }
7868
+
7869
+ return this.state.tagRefinements.join(',');
7870
+ };
7871
+
7872
+ /**
7873
+ * Test if there are some disjunctive refinements on the facet
7874
+ * @private
7875
+ * @param {string} facet the attribute to test
7876
+ * @return {boolean}
7877
+ */
7878
+ AlgoliaSearchHelper.prototype._hasDisjunctiveRefinements = function(facet) {
7879
+ return this.state.disjunctiveRefinements[facet] &&
7880
+ this.state.disjunctiveRefinements[facet].length > 0;
7881
+ };
7882
+
7883
+ /**
7884
+ * Build facetFilters parameter based on current refinements. The array returned
7885
+ * contains strings representing the facet filters in the algolia format.
7886
+ * @private
7887
+ * @param {string} [facet] if set, the current disjunctive facet
7888
+ * @return {array.<string>}
7889
+ */
7890
+ AlgoliaSearchHelper.prototype._getFacetFilters = function(facet, hierarchicalRootLevel) {
7891
+ var facetFilters = [];
7892
+
7893
+ forEach(this.state.facetsRefinements, function(facetValues, facetName) {
7894
+ forEach(facetValues, function(facetValue) {
7895
+ facetFilters.push(facetName + ':' + facetValue);
7896
+ });
7897
+ });
7898
+
7899
+ forEach(this.state.facetsExcludes, function(facetValues, facetName) {
7900
+ forEach(facetValues, function(facetValue) {
7901
+ facetFilters.push(facetName + ':-' + facetValue);
7902
+ });
7903
+ });
7904
+
7905
+ forEach(this.state.disjunctiveFacetsRefinements, function(facetValues, facetName) {
7906
+ if (facetName === facet || !facetValues || facetValues.length === 0) return;
7907
+ var orFilters = [];
7908
+
7909
+ forEach(facetValues, function(facetValue) {
7910
+ orFilters.push(facetName + ':' + facetValue);
7911
+ });
7912
+
7913
+ facetFilters.push(orFilters);
7914
+ });
7915
+
7916
+ forEach(this.state.hierarchicalFacetsRefinements, function(facetValues, facetName) {
7917
+ var facetValue = facetValues[0];
7918
+
7919
+ if (facetValue === undefined) {
7920
+ return;
7921
+ }
7922
+
7923
+ var hierarchicalFacet = this.state.getHierarchicalFacetByName(facetName);
7924
+ var separator = this.state._getHierarchicalFacetSeparator(hierarchicalFacet);
7925
+ var attributeToRefine;
7926
+
7927
+ // we ask for parent facet values only when the `facet` is the current hierarchical facet
7928
+ if (facet === facetName) {
7929
+ // if we are at the root level already, no need to ask for facet values, we get them from
7930
+ // the hits query
7931
+ if (facetValue.indexOf(separator) === -1 || hierarchicalRootLevel === true) {
7932
+ return;
7933
+ }
7934
+
7935
+ attributeToRefine = hierarchicalFacet.attributes[facetValue.split(separator).length - 2];
7936
+ facetValue = facetValue.slice(0, facetValue.lastIndexOf(separator));
7937
+ } else {
7938
+ attributeToRefine = hierarchicalFacet.attributes[facetValue.split(separator).length - 1];
7939
+ }
7940
+
7941
+ facetFilters.push([attributeToRefine + ':' + facetValue]);
7942
+ }, this);
7943
+
7944
+ return facetFilters;
7945
+ };
7946
+
7947
+ AlgoliaSearchHelper.prototype._change = function() {
7948
+ this.emit('change', this.state, this.lastResults);
7949
+ };
7950
+
7951
+ AlgoliaSearchHelper.prototype._getHitsHierarchicalFacetsAttributes = function() {
7952
+ var out = [];
7953
+
7954
+ return reduce(
7955
+ this.state.hierarchicalFacets,
7956
+ // ask for as much levels as there's hierarchical refinements
7957
+ function getHitsAttributesForHierarchicalFacet(allAttributes, hierarchicalFacet) {
7958
+ var hierarchicalRefinement = this.state.getHierarchicalRefinement(hierarchicalFacet.name)[0];
7959
+
7960
+ // if no refinement, ask for root level
7961
+ if (!hierarchicalRefinement) {
7962
+ allAttributes.push(hierarchicalFacet.attributes[0]);
7963
+ return allAttributes;
7964
+ }
7965
+
7966
+ var level = hierarchicalRefinement.split(this.state._getHierarchicalFacetSeparator(hierarchicalFacet)).length;
7967
+ var newAttributes = hierarchicalFacet.attributes.slice(0, level + 1);
7968
+
7969
+ return allAttributes.concat(newAttributes);
7970
+ }, out, this);
7971
+ };
7972
+
7973
+ AlgoliaSearchHelper.prototype._getDisjunctiveHierarchicalFacetAttribute = function(hierarchicalFacet, rootLevel) {
7974
+ if (rootLevel === true) {
7975
+ return hierarchicalFacet.attributes[0];
7976
+ }
7977
+
7978
+ var hierarchicalRefinement = this.state.getHierarchicalRefinement(hierarchicalFacet.name)[0] || '';
7979
+ // if refinement is 'beers > IPA > Flying dog',
7980
+ // then we want `facets: ['beers > IPA']` as disjunctive facet (parent level values)
7981
+
7982
+ var parentLevel = hierarchicalRefinement.split(this.state._getHierarchicalFacetSeparator(hierarchicalFacet)).length - 1;
7983
+ return hierarchicalFacet.attributes.slice(0, parentLevel + 1);
7984
+ };
7985
+
7986
+ module.exports = AlgoliaSearchHelper;
7987
+
7988
+ },{"./SearchParameters":152,"./SearchResults":154,"events":219,"lodash/collection/forEach":11,"lodash/collection/map":13,"lodash/collection/reduce":15,"lodash/function/bind":19,"lodash/lang/isEmpty":128,"lodash/object/merge":142,"lodash/string/trim":147,"util":226}],156:[function(require,module,exports){
7989
+ 'use strict';
7990
+
7991
+ var forEach = require('lodash/collection/forEach');
7992
+ var identity = require('lodash/utility/identity');
7993
+ var isObject = require('lodash/lang/isObject');
7994
+
7995
+ /**
7996
+ * Recursively freeze the parts of an object that are not frozen.
7997
+ * @private
7998
+ * @param {object} obj object to freeze
7999
+ * @return {object} the object frozen
8000
+ */
8001
+ var deepFreeze = function(obj) {
8002
+ if (!isObject(obj)) return obj;
8003
+
8004
+ forEach(obj, deepFreeze);
8005
+ if (!Object.isFrozen(obj)) {
8006
+ Object.freeze(obj);
8007
+ }
8008
+
8009
+ return obj;
8010
+ };
8011
+
8012
+ module.exports = Object.freeze ? deepFreeze : identity;
8013
+
8014
+ },{"lodash/collection/forEach":11,"lodash/lang/isObject":131,"lodash/utility/identity":148}],157:[function(require,module,exports){
8015
+
8016
+ /**
8017
+ * This is the web browser implementation of `debug()`.
8018
+ *
8019
+ * Expose `debug()` as the module.
8020
+ */
8021
+
8022
+ exports = module.exports = require('./debug');
8023
+ exports.log = log;
8024
+ exports.formatArgs = formatArgs;
8025
+ exports.save = save;
8026
+ exports.load = load;
8027
+ exports.useColors = useColors;
8028
+ exports.storage = 'undefined' != typeof chrome
8029
+ && 'undefined' != typeof chrome.storage
8030
+ ? chrome.storage.local
8031
+ : localstorage();
8032
+
8033
+ /**
8034
+ * Colors.
8035
+ */
8036
+
8037
+ exports.colors = [
8038
+ 'lightseagreen',
8039
+ 'forestgreen',
8040
+ 'goldenrod',
8041
+ 'dodgerblue',
8042
+ 'darkorchid',
8043
+ 'crimson'
8044
+ ];
8045
+
8046
+ /**
8047
+ * Currently only WebKit-based Web Inspectors, Firefox >= v31,
8048
+ * and the Firebug extension (any Firefox version) are known
8049
+ * to support "%c" CSS customizations.
8050
+ *
8051
+ * TODO: add a `localStorage` variable to explicitly enable/disable colors
8052
+ */
8053
+
8054
+ function useColors() {
8055
+ // is webkit? http://stackoverflow.com/a/16459606/376773
8056
+ return ('WebkitAppearance' in document.documentElement.style) ||
8057
+ // is firebug? http://stackoverflow.com/a/398120/376773
8058
+ (window.console && (console.firebug || (console.exception && console.table))) ||
8059
+ // is firefox >= v31?
8060
+ // https://developer.mozilla.org/en-US/docs/Tools/Web_Console#Styling_messages
8061
+ (navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/) && parseInt(RegExp.$1, 10) >= 31);
8062
+ }
8063
+
8064
+ /**
8065
+ * Map %j to `JSON.stringify()`, since no Web Inspectors do that by default.
8066
+ */
8067
+
8068
+ exports.formatters.j = function(v) {
8069
+ return JSON.stringify(v);
8070
+ };
8071
+
8072
+
8073
+ /**
8074
+ * Colorize log arguments if enabled.
8075
+ *
8076
+ * @api public
8077
+ */
8078
+
8079
+ function formatArgs() {
8080
+ var args = arguments;
8081
+ var useColors = this.useColors;
8082
+
8083
+ args[0] = (useColors ? '%c' : '')
8084
+ + this.namespace
8085
+ + (useColors ? ' %c' : ' ')
8086
+ + args[0]
8087
+ + (useColors ? '%c ' : ' ')
8088
+ + '+' + exports.humanize(this.diff);
8089
+
8090
+ if (!useColors) return args;
8091
+
8092
+ var c = 'color: ' + this.color;
8093
+ args = [args[0], c, 'color: inherit'].concat(Array.prototype.slice.call(args, 1));
8094
+
8095
+ // the final "%c" is somewhat tricky, because there could be other
8096
+ // arguments passed either before or after the %c, so we need to
8097
+ // figure out the correct index to insert the CSS into
8098
+ var index = 0;
8099
+ var lastC = 0;
8100
+ args[0].replace(/%[a-z%]/g, function(match) {
8101
+ if ('%%' === match) return;
8102
+ index++;
8103
+ if ('%c' === match) {
8104
+ // we only are interested in the *last* %c
8105
+ // (the user may have provided their own)
8106
+ lastC = index;
8107
+ }
8108
+ });
8109
+
8110
+ args.splice(lastC, 0, c);
8111
+ return args;
8112
+ }
8113
+
8114
+ /**
8115
+ * Invokes `console.log()` when available.
8116
+ * No-op when `console.log` is not a "function".
8117
+ *
8118
+ * @api public
8119
+ */
8120
+
8121
+ function log() {
8122
+ // this hackery is required for IE8/9, where
8123
+ // the `console.log` function doesn't have 'apply'
8124
+ return 'object' === typeof console
8125
+ && console.log
8126
+ && Function.prototype.apply.call(console.log, console, arguments);
8127
+ }
8128
+
8129
+ /**
8130
+ * Save `namespaces`.
8131
+ *
8132
+ * @param {String} namespaces
8133
+ * @api private
8134
+ */
8135
+
8136
+ function save(namespaces) {
8137
+ try {
8138
+ if (null == namespaces) {
8139
+ exports.storage.removeItem('debug');
8140
+ } else {
8141
+ exports.storage.debug = namespaces;
8142
+ }
8143
+ } catch(e) {}
8144
+ }
8145
+
8146
+ /**
8147
+ * Load `namespaces`.
8148
+ *
8149
+ * @return {String} returns the previously persisted debug modes
8150
+ * @api private
8151
+ */
8152
+
8153
+ function load() {
8154
+ var r;
8155
+ try {
8156
+ r = exports.storage.debug;
8157
+ } catch(e) {}
8158
+ return r;
8159
+ }
8160
+
8161
+ /**
8162
+ * Enable namespaces listed in `localStorage.debug` initially.
8163
+ */
8164
+
8165
+ exports.enable(load());
8166
+
8167
+ /**
8168
+ * Localstorage attempts to return the localstorage.
8169
+ *
8170
+ * This is necessary because safari throws
8171
+ * when a user disables cookies/localstorage
8172
+ * and you attempt to access it.
8173
+ *
8174
+ * @return {LocalStorage}
8175
+ * @api private
8176
+ */
8177
+
8178
+ function localstorage(){
8179
+ try {
8180
+ return window.localStorage;
8181
+ } catch (e) {}
8182
+ }
8183
+
8184
+ },{"./debug":158}],158:[function(require,module,exports){
8185
+
8186
+ /**
8187
+ * This is the common logic for both the Node.js and web browser
8188
+ * implementations of `debug()`.
8189
+ *
8190
+ * Expose `debug()` as the module.
8191
+ */
8192
+
8193
+ exports = module.exports = debug;
8194
+ exports.coerce = coerce;
8195
+ exports.disable = disable;
8196
+ exports.enable = enable;
8197
+ exports.enabled = enabled;
8198
+ exports.humanize = require('algolia-ms');
8199
+
8200
+ /**
8201
+ * The currently active debug mode names, and names to skip.
8202
+ */
8203
+
8204
+ exports.names = [];
8205
+ exports.skips = [];
8206
+
8207
+ /**
8208
+ * Map of special "%n" handling functions, for the debug "format" argument.
8209
+ *
8210
+ * Valid key names are a single, lowercased letter, i.e. "n".
8211
+ */
8212
+
8213
+ exports.formatters = {};
8214
+
8215
+ /**
8216
+ * Previously assigned color.
8217
+ */
8218
+
8219
+ var prevColor = 0;
8220
+
8221
+ /**
8222
+ * Previous log timestamp.
8223
+ */
8224
+
8225
+ var prevTime;
8226
+
8227
+ /**
8228
+ * Select a color.
8229
+ *
8230
+ * @return {Number}
8231
+ * @api private
8232
+ */
8233
+
8234
+ function selectColor() {
8235
+ return exports.colors[prevColor++ % exports.colors.length];
8236
+ }
8237
+
8238
+ /**
8239
+ * Create a debugger with the given `namespace`.
8240
+ *
8241
+ * @param {String} namespace
8242
+ * @return {Function}
8243
+ * @api public
8244
+ */
8245
+
8246
+ function debug(namespace) {
8247
+
8248
+ // define the `disabled` version
8249
+ function disabled() {
8250
+ }
8251
+ disabled.enabled = false;
8252
+
8253
+ // define the `enabled` version
8254
+ function enabled() {
8255
+
8256
+ var self = enabled;
8257
+
8258
+ // set `diff` timestamp
8259
+ var curr = +new Date();
8260
+ var ms = curr - (prevTime || curr);
8261
+ self.diff = ms;
8262
+ self.prev = prevTime;
8263
+ self.curr = curr;
8264
+ prevTime = curr;
8265
+
8266
+ // add the `color` if not set
8267
+ if (null == self.useColors) self.useColors = exports.useColors();
8268
+ if (null == self.color && self.useColors) self.color = selectColor();
8269
+
8270
+ var args = Array.prototype.slice.call(arguments);
8271
+
8272
+ args[0] = exports.coerce(args[0]);
8273
+
8274
+ if ('string' !== typeof args[0]) {
8275
+ // anything else let's inspect with %o
8276
+ args = ['%o'].concat(args);
8277
+ }
8278
+
8279
+ // apply any `formatters` transformations
8280
+ var index = 0;
8281
+ args[0] = args[0].replace(/%([a-z%])/g, function(match, format) {
8282
+ // if we encounter an escaped % then don't increase the array index
8283
+ if (match === '%%') return match;
8284
+ index++;
8285
+ var formatter = exports.formatters[format];
8286
+ if ('function' === typeof formatter) {
8287
+ var val = args[index];
8288
+ match = formatter.call(self, val);
8289
+
8290
+ // now we need to remove `args[index]` since it's inlined in the `format`
8291
+ args.splice(index, 1);
8292
+ index--;
8293
+ }
8294
+ return match;
8295
+ });
8296
+
8297
+ if ('function' === typeof exports.formatArgs) {
8298
+ args = exports.formatArgs.apply(self, args);
8299
+ }
8300
+ var logFn = enabled.log || exports.log || console.log.bind(console);
8301
+ logFn.apply(self, args);
8302
+ }
8303
+ enabled.enabled = true;
8304
+
8305
+ var fn = exports.enabled(namespace) ? enabled : disabled;
8306
+
8307
+ fn.namespace = namespace;
8308
+
8309
+ return fn;
8310
+ }
8311
+
8312
+ /**
8313
+ * Enables a debug mode by namespaces. This can include modes
8314
+ * separated by a colon and wildcards.
8315
+ *
8316
+ * @param {String} namespaces
8317
+ * @api public
8318
+ */
8319
+
8320
+ function enable(namespaces) {
8321
+ exports.save(namespaces);
8322
+
8323
+ var split = (namespaces || '').split(/[\s,]+/);
8324
+ var len = split.length;
8325
+
8326
+ for (var i = 0; i < len; i++) {
8327
+ if (!split[i]) continue; // ignore empty strings
8328
+ namespaces = split[i].replace(/\*/g, '.*?');
8329
+ if (namespaces[0] === '-') {
8330
+ exports.skips.push(new RegExp('^' + namespaces.substr(1) + '$'));
8331
+ } else {
8332
+ exports.names.push(new RegExp('^' + namespaces + '$'));
8333
+ }
8334
+ }
8335
+ }
8336
+
8337
+ /**
8338
+ * Disable debug output.
8339
+ *
8340
+ * @api public
8341
+ */
8342
+
8343
+ function disable() {
8344
+ exports.enable('');
8345
+ }
8346
+
8347
+ /**
8348
+ * Returns true if the given mode name is enabled, false otherwise.
8349
+ *
8350
+ * @param {String} name
8351
+ * @return {Boolean}
8352
+ * @api public
8353
+ */
8354
+
8355
+ function enabled(name) {
8356
+ var i, len;
8357
+ for (i = 0, len = exports.skips.length; i < len; i++) {
8358
+ if (exports.skips[i].test(name)) {
8359
+ return false;
8360
+ }
8361
+ }
8362
+ for (i = 0, len = exports.names.length; i < len; i++) {
8363
+ if (exports.names[i].test(name)) {
8364
+ return true;
8365
+ }
8366
+ }
8367
+ return false;
8368
+ }
8369
+
8370
+ /**
8371
+ * Coerce `val`.
8372
+ *
8373
+ * @param {Mixed} val
8374
+ * @return {Mixed}
8375
+ * @api private
8376
+ */
8377
+
8378
+ function coerce(val) {
8379
+ if (val instanceof Error) return val.stack || val.message;
8380
+ return val;
8381
+ }
8382
+
8383
+ },{"algolia-ms":159}],159:[function(require,module,exports){
8384
+ /**
8385
+ * Helpers.
8386
+ */
8387
+
8388
+ var s = 1000;
8389
+ var m = s * 60;
8390
+ var h = m * 60;
8391
+ var d = h * 24;
8392
+ var y = d * 365.25;
8393
+
8394
+ /**
8395
+ * Parse or format the given `val`.
8396
+ *
8397
+ * Options:
8398
+ *
8399
+ * - `long` verbose formatting [false]
8400
+ *
8401
+ * @param {String|Number} val
8402
+ * @param {Object} options
8403
+ * @return {String|Number}
8404
+ * @api public
8405
+ */
8406
+
8407
+ module.exports = function(val, options){
8408
+ options = options || {};
8409
+ if ('string' == typeof val) return parse(val);
8410
+ // long, short were "future reserved words in js", YUI compressor fail on them
8411
+ // https://github.com/algolia/algoliasearch-client-js/issues/113#issuecomment-111978606
8412
+ // https://github.com/yui/yuicompressor/issues/47
8413
+ // https://github.com/rauchg/ms.js/pull/40
8414
+ return options['long']
8415
+ ? _long(val)
8416
+ : _short(val);
8417
+ };
8418
+
8419
+ /**
8420
+ * Parse the given `str` and return milliseconds.
8421
+ *
8422
+ * @param {String} str
8423
+ * @return {Number}
8424
+ * @api private
8425
+ */
8426
+
8427
+ function parse(str) {
8428
+ str = '' + str;
8429
+ if (str.length > 10000) return;
8430
+ var match = /^((?:\d+)?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|years?|yrs?|y)?$/i.exec(str);
8431
+ if (!match) return;
8432
+ var n = parseFloat(match[1]);
8433
+ var type = (match[2] || 'ms').toLowerCase();
8434
+ switch (type) {
8435
+ case 'years':
8436
+ case 'year':
8437
+ case 'yrs':
8438
+ case 'yr':
8439
+ case 'y':
8440
+ return n * y;
8441
+ case 'days':
8442
+ case 'day':
8443
+ case 'd':
8444
+ return n * d;
8445
+ case 'hours':
8446
+ case 'hour':
8447
+ case 'hrs':
8448
+ case 'hr':
8449
+ case 'h':
8450
+ return n * h;
8451
+ case 'minutes':
8452
+ case 'minute':
8453
+ case 'mins':
8454
+ case 'min':
8455
+ case 'm':
8456
+ return n * m;
8457
+ case 'seconds':
8458
+ case 'second':
8459
+ case 'secs':
8460
+ case 'sec':
8461
+ case 's':
8462
+ return n * s;
8463
+ case 'milliseconds':
8464
+ case 'millisecond':
8465
+ case 'msecs':
8466
+ case 'msec':
8467
+ case 'ms':
8468
+ return n;
8469
+ }
8470
+ }
8471
+
8472
+ /**
8473
+ * Short format for `ms`.
8474
+ *
8475
+ * @param {Number} ms
8476
+ * @return {String}
8477
+ * @api private
8478
+ */
8479
+
8480
+ function _short(ms) {
8481
+ if (ms >= d) return Math.round(ms / d) + 'd';
8482
+ if (ms >= h) return Math.round(ms / h) + 'h';
8483
+ if (ms >= m) return Math.round(ms / m) + 'm';
8484
+ if (ms >= s) return Math.round(ms / s) + 's';
8485
+ return ms + 'ms';
8486
+ }
8487
+
8488
+ /**
8489
+ * Long format for `ms`.
8490
+ *
8491
+ * @param {Number} ms
8492
+ * @return {String}
8493
+ * @api private
8494
+ */
8495
+
8496
+ function _long(ms) {
8497
+ return plural(ms, d, 'day')
8498
+ || plural(ms, h, 'hour')
8499
+ || plural(ms, m, 'minute')
8500
+ || plural(ms, s, 'second')
8501
+ || ms + ' ms';
8502
+ }
8503
+
8504
+ /**
8505
+ * Pluralization helper.
8506
+ */
8507
+
8508
+ function plural(ms, n, name) {
8509
+ if (ms < n) return;
8510
+ if (ms < n * 1.5) return Math.floor(ms / n) + ' ' + name;
8511
+ return Math.ceil(ms / n) + ' ' + name + 's';
8512
+ }
8513
+
8514
+ },{}],160:[function(require,module,exports){
8515
+ (function (process,global){
8516
+ /*!
8517
+ * @overview es6-promise - a tiny implementation of Promises/A+.
8518
+ * @copyright Copyright (c) 2014 Yehuda Katz, Tom Dale, Stefan Penner and contributors (Conversion to ES6 API by Jake Archibald)
8519
+ * @license Licensed under MIT license
8520
+ * See https://raw.githubusercontent.com/jakearchibald/es6-promise/master/LICENSE
8521
+ * @version 2.3.0
8522
+ */
8523
+
8524
+ (function() {
8525
+ "use strict";
8526
+ function lib$es6$promise$utils$$objectOrFunction(x) {
8527
+ return typeof x === 'function' || (typeof x === 'object' && x !== null);
8528
+ }
8529
+
8530
+ function lib$es6$promise$utils$$isFunction(x) {
8531
+ return typeof x === 'function';
8532
+ }
8533
+
8534
+ function lib$es6$promise$utils$$isMaybeThenable(x) {
8535
+ return typeof x === 'object' && x !== null;
8536
+ }
8537
+
8538
+ var lib$es6$promise$utils$$_isArray;
8539
+ if (!Array.isArray) {
8540
+ lib$es6$promise$utils$$_isArray = function (x) {
8541
+ return Object.prototype.toString.call(x) === '[object Array]';
8542
+ };
8543
+ } else {
8544
+ lib$es6$promise$utils$$_isArray = Array.isArray;
8545
+ }
8546
+
8547
+ var lib$es6$promise$utils$$isArray = lib$es6$promise$utils$$_isArray;
8548
+ var lib$es6$promise$asap$$len = 0;
8549
+ var lib$es6$promise$asap$$toString = {}.toString;
8550
+ var lib$es6$promise$asap$$vertxNext;
8551
+ var lib$es6$promise$asap$$customSchedulerFn;
8552
+
8553
+ var lib$es6$promise$asap$$asap = function asap(callback, arg) {
8554
+ lib$es6$promise$asap$$queue[lib$es6$promise$asap$$len] = callback;
8555
+ lib$es6$promise$asap$$queue[lib$es6$promise$asap$$len + 1] = arg;
8556
+ lib$es6$promise$asap$$len += 2;
8557
+ if (lib$es6$promise$asap$$len === 2) {
8558
+ // If len is 2, that means that we need to schedule an async flush.
8559
+ // If additional callbacks are queued before the queue is flushed, they
8560
+ // will be processed by this flush that we are scheduling.
8561
+ if (lib$es6$promise$asap$$customSchedulerFn) {
8562
+ lib$es6$promise$asap$$customSchedulerFn(lib$es6$promise$asap$$flush);
8563
+ } else {
8564
+ lib$es6$promise$asap$$scheduleFlush();
8565
+ }
8566
+ }
8567
+ }
8568
+
8569
+ function lib$es6$promise$asap$$setScheduler(scheduleFn) {
8570
+ lib$es6$promise$asap$$customSchedulerFn = scheduleFn;
8571
+ }
8572
+
8573
+ function lib$es6$promise$asap$$setAsap(asapFn) {
8574
+ lib$es6$promise$asap$$asap = asapFn;
8575
+ }
8576
+
8577
+ var lib$es6$promise$asap$$browserWindow = (typeof window !== 'undefined') ? window : undefined;
8578
+ var lib$es6$promise$asap$$browserGlobal = lib$es6$promise$asap$$browserWindow || {};
8579
+ var lib$es6$promise$asap$$BrowserMutationObserver = lib$es6$promise$asap$$browserGlobal.MutationObserver || lib$es6$promise$asap$$browserGlobal.WebKitMutationObserver;
8580
+ var lib$es6$promise$asap$$isNode = typeof process !== 'undefined' && {}.toString.call(process) === '[object process]';
8581
+
8582
+ // test for web worker but not in IE10
8583
+ var lib$es6$promise$asap$$isWorker = typeof Uint8ClampedArray !== 'undefined' &&
8584
+ typeof importScripts !== 'undefined' &&
8585
+ typeof MessageChannel !== 'undefined';
8586
+
8587
+ // node
8588
+ function lib$es6$promise$asap$$useNextTick() {
8589
+ var nextTick = process.nextTick;
8590
+ // node version 0.10.x displays a deprecation warning when nextTick is used recursively
8591
+ // setImmediate should be used instead instead
8592
+ var version = process.versions.node.match(/^(?:(\d+)\.)?(?:(\d+)\.)?(\*|\d+)$/);
8593
+ if (Array.isArray(version) && version[1] === '0' && version[2] === '10') {
8594
+ nextTick = setImmediate;
8595
+ }
8596
+ return function() {
8597
+ nextTick(lib$es6$promise$asap$$flush);
8598
+ };
8599
+ }
8600
+
8601
+ // vertx
8602
+ function lib$es6$promise$asap$$useVertxTimer() {
8603
+ return function() {
8604
+ lib$es6$promise$asap$$vertxNext(lib$es6$promise$asap$$flush);
8605
+ };
8606
+ }
8607
+
8608
+ function lib$es6$promise$asap$$useMutationObserver() {
8609
+ var iterations = 0;
8610
+ var observer = new lib$es6$promise$asap$$BrowserMutationObserver(lib$es6$promise$asap$$flush);
8611
+ var node = document.createTextNode('');
8612
+ observer.observe(node, { characterData: true });
8613
+
8614
+ return function() {
8615
+ node.data = (iterations = ++iterations % 2);
8616
+ };
8617
+ }
8618
+
8619
+ // web worker
8620
+ function lib$es6$promise$asap$$useMessageChannel() {
8621
+ var channel = new MessageChannel();
8622
+ channel.port1.onmessage = lib$es6$promise$asap$$flush;
8623
+ return function () {
8624
+ channel.port2.postMessage(0);
8625
+ };
8626
+ }
8627
+
8628
+ function lib$es6$promise$asap$$useSetTimeout() {
8629
+ return function() {
8630
+ setTimeout(lib$es6$promise$asap$$flush, 1);
8631
+ };
8632
+ }
8633
+
8634
+ var lib$es6$promise$asap$$queue = new Array(1000);
8635
+ function lib$es6$promise$asap$$flush() {
8636
+ for (var i = 0; i < lib$es6$promise$asap$$len; i+=2) {
8637
+ var callback = lib$es6$promise$asap$$queue[i];
8638
+ var arg = lib$es6$promise$asap$$queue[i+1];
8639
+
8640
+ callback(arg);
8641
+
8642
+ lib$es6$promise$asap$$queue[i] = undefined;
8643
+ lib$es6$promise$asap$$queue[i+1] = undefined;
8644
+ }
8645
+
8646
+ lib$es6$promise$asap$$len = 0;
8647
+ }
8648
+
8649
+ function lib$es6$promise$asap$$attemptVertex() {
8650
+ try {
8651
+ var r = require;
8652
+ var vertx = r('vertx');
8653
+ lib$es6$promise$asap$$vertxNext = vertx.runOnLoop || vertx.runOnContext;
8654
+ return lib$es6$promise$asap$$useVertxTimer();
8655
+ } catch(e) {
8656
+ return lib$es6$promise$asap$$useSetTimeout();
8657
+ }
8658
+ }
8659
+
8660
+ var lib$es6$promise$asap$$scheduleFlush;
8661
+ // Decide what async method to use to triggering processing of queued callbacks:
8662
+ if (lib$es6$promise$asap$$isNode) {
8663
+ lib$es6$promise$asap$$scheduleFlush = lib$es6$promise$asap$$useNextTick();
8664
+ } else if (lib$es6$promise$asap$$BrowserMutationObserver) {
8665
+ lib$es6$promise$asap$$scheduleFlush = lib$es6$promise$asap$$useMutationObserver();
8666
+ } else if (lib$es6$promise$asap$$isWorker) {
8667
+ lib$es6$promise$asap$$scheduleFlush = lib$es6$promise$asap$$useMessageChannel();
8668
+ } else if (lib$es6$promise$asap$$browserWindow === undefined && typeof require === 'function') {
8669
+ lib$es6$promise$asap$$scheduleFlush = lib$es6$promise$asap$$attemptVertex();
8670
+ } else {
8671
+ lib$es6$promise$asap$$scheduleFlush = lib$es6$promise$asap$$useSetTimeout();
8672
+ }
8673
+
8674
+ function lib$es6$promise$$internal$$noop() {}
8675
+
8676
+ var lib$es6$promise$$internal$$PENDING = void 0;
8677
+ var lib$es6$promise$$internal$$FULFILLED = 1;
8678
+ var lib$es6$promise$$internal$$REJECTED = 2;
8679
+
8680
+ var lib$es6$promise$$internal$$GET_THEN_ERROR = new lib$es6$promise$$internal$$ErrorObject();
8681
+
8682
+ function lib$es6$promise$$internal$$selfFullfillment() {
8683
+ return new TypeError("You cannot resolve a promise with itself");
8684
+ }
8685
+
8686
+ function lib$es6$promise$$internal$$cannotReturnOwn() {
8687
+ return new TypeError('A promises callback cannot return that same promise.');
8688
+ }
8689
+
8690
+ function lib$es6$promise$$internal$$getThen(promise) {
8691
+ try {
8692
+ return promise.then;
8693
+ } catch(error) {
8694
+ lib$es6$promise$$internal$$GET_THEN_ERROR.error = error;
8695
+ return lib$es6$promise$$internal$$GET_THEN_ERROR;
8696
+ }
8697
+ }
8698
+
8699
+ function lib$es6$promise$$internal$$tryThen(then, value, fulfillmentHandler, rejectionHandler) {
8700
+ try {
8701
+ then.call(value, fulfillmentHandler, rejectionHandler);
8702
+ } catch(e) {
8703
+ return e;
8704
+ }
8705
+ }
8706
+
8707
+ function lib$es6$promise$$internal$$handleForeignThenable(promise, thenable, then) {
8708
+ lib$es6$promise$asap$$asap(function(promise) {
8709
+ var sealed = false;
8710
+ var error = lib$es6$promise$$internal$$tryThen(then, thenable, function(value) {
8711
+ if (sealed) { return; }
8712
+ sealed = true;
8713
+ if (thenable !== value) {
8714
+ lib$es6$promise$$internal$$resolve(promise, value);
8715
+ } else {
8716
+ lib$es6$promise$$internal$$fulfill(promise, value);
8717
+ }
8718
+ }, function(reason) {
8719
+ if (sealed) { return; }
8720
+ sealed = true;
8721
+
8722
+ lib$es6$promise$$internal$$reject(promise, reason);
8723
+ }, 'Settle: ' + (promise._label || ' unknown promise'));
8724
+
8725
+ if (!sealed && error) {
8726
+ sealed = true;
8727
+ lib$es6$promise$$internal$$reject(promise, error);
8728
+ }
8729
+ }, promise);
8730
+ }
8731
+
8732
+ function lib$es6$promise$$internal$$handleOwnThenable(promise, thenable) {
8733
+ if (thenable._state === lib$es6$promise$$internal$$FULFILLED) {
8734
+ lib$es6$promise$$internal$$fulfill(promise, thenable._result);
8735
+ } else if (thenable._state === lib$es6$promise$$internal$$REJECTED) {
8736
+ lib$es6$promise$$internal$$reject(promise, thenable._result);
8737
+ } else {
8738
+ lib$es6$promise$$internal$$subscribe(thenable, undefined, function(value) {
8739
+ lib$es6$promise$$internal$$resolve(promise, value);
8740
+ }, function(reason) {
8741
+ lib$es6$promise$$internal$$reject(promise, reason);
8742
+ });
8743
+ }
8744
+ }
8745
+
8746
+ function lib$es6$promise$$internal$$handleMaybeThenable(promise, maybeThenable) {
8747
+ if (maybeThenable.constructor === promise.constructor) {
8748
+ lib$es6$promise$$internal$$handleOwnThenable(promise, maybeThenable);
8749
+ } else {
8750
+ var then = lib$es6$promise$$internal$$getThen(maybeThenable);
8751
+
8752
+ if (then === lib$es6$promise$$internal$$GET_THEN_ERROR) {
8753
+ lib$es6$promise$$internal$$reject(promise, lib$es6$promise$$internal$$GET_THEN_ERROR.error);
8754
+ } else if (then === undefined) {
8755
+ lib$es6$promise$$internal$$fulfill(promise, maybeThenable);
8756
+ } else if (lib$es6$promise$utils$$isFunction(then)) {
8757
+ lib$es6$promise$$internal$$handleForeignThenable(promise, maybeThenable, then);
8758
+ } else {
8759
+ lib$es6$promise$$internal$$fulfill(promise, maybeThenable);
8760
+ }
8761
+ }
8762
+ }
8763
+
8764
+ function lib$es6$promise$$internal$$resolve(promise, value) {
8765
+ if (promise === value) {
8766
+ lib$es6$promise$$internal$$reject(promise, lib$es6$promise$$internal$$selfFullfillment());
8767
+ } else if (lib$es6$promise$utils$$objectOrFunction(value)) {
8768
+ lib$es6$promise$$internal$$handleMaybeThenable(promise, value);
8769
+ } else {
8770
+ lib$es6$promise$$internal$$fulfill(promise, value);
8771
+ }
8772
+ }
8773
+
8774
+ function lib$es6$promise$$internal$$publishRejection(promise) {
8775
+ if (promise._onerror) {
8776
+ promise._onerror(promise._result);
8777
+ }
8778
+
8779
+ lib$es6$promise$$internal$$publish(promise);
8780
+ }
8781
+
8782
+ function lib$es6$promise$$internal$$fulfill(promise, value) {
8783
+ if (promise._state !== lib$es6$promise$$internal$$PENDING) { return; }
8784
+
8785
+ promise._result = value;
8786
+ promise._state = lib$es6$promise$$internal$$FULFILLED;
8787
+
8788
+ if (promise._subscribers.length !== 0) {
8789
+ lib$es6$promise$asap$$asap(lib$es6$promise$$internal$$publish, promise);
8790
+ }
8791
+ }
8792
+
8793
+ function lib$es6$promise$$internal$$reject(promise, reason) {
8794
+ if (promise._state !== lib$es6$promise$$internal$$PENDING) { return; }
8795
+ promise._state = lib$es6$promise$$internal$$REJECTED;
8796
+ promise._result = reason;
8797
+
8798
+ lib$es6$promise$asap$$asap(lib$es6$promise$$internal$$publishRejection, promise);
8799
+ }
8800
+
8801
+ function lib$es6$promise$$internal$$subscribe(parent, child, onFulfillment, onRejection) {
8802
+ var subscribers = parent._subscribers;
8803
+ var length = subscribers.length;
8804
+
8805
+ parent._onerror = null;
8806
+
8807
+ subscribers[length] = child;
8808
+ subscribers[length + lib$es6$promise$$internal$$FULFILLED] = onFulfillment;
8809
+ subscribers[length + lib$es6$promise$$internal$$REJECTED] = onRejection;
8810
+
8811
+ if (length === 0 && parent._state) {
8812
+ lib$es6$promise$asap$$asap(lib$es6$promise$$internal$$publish, parent);
8813
+ }
8814
+ }
8815
+
8816
+ function lib$es6$promise$$internal$$publish(promise) {
8817
+ var subscribers = promise._subscribers;
8818
+ var settled = promise._state;
8819
+
8820
+ if (subscribers.length === 0) { return; }
8821
+
8822
+ var child, callback, detail = promise._result;
8823
+
8824
+ for (var i = 0; i < subscribers.length; i += 3) {
8825
+ child = subscribers[i];
8826
+ callback = subscribers[i + settled];
8827
+
8828
+ if (child) {
8829
+ lib$es6$promise$$internal$$invokeCallback(settled, child, callback, detail);
8830
+ } else {
8831
+ callback(detail);
8832
+ }
8833
+ }
8834
+
8835
+ promise._subscribers.length = 0;
8836
+ }
8837
+
8838
+ function lib$es6$promise$$internal$$ErrorObject() {
8839
+ this.error = null;
8840
+ }
8841
+
8842
+ var lib$es6$promise$$internal$$TRY_CATCH_ERROR = new lib$es6$promise$$internal$$ErrorObject();
8843
+
8844
+ function lib$es6$promise$$internal$$tryCatch(callback, detail) {
8845
+ try {
8846
+ return callback(detail);
8847
+ } catch(e) {
8848
+ lib$es6$promise$$internal$$TRY_CATCH_ERROR.error = e;
8849
+ return lib$es6$promise$$internal$$TRY_CATCH_ERROR;
8850
+ }
8851
+ }
8852
+
8853
+ function lib$es6$promise$$internal$$invokeCallback(settled, promise, callback, detail) {
8854
+ var hasCallback = lib$es6$promise$utils$$isFunction(callback),
8855
+ value, error, succeeded, failed;
8856
+
8857
+ if (hasCallback) {
8858
+ value = lib$es6$promise$$internal$$tryCatch(callback, detail);
8859
+
8860
+ if (value === lib$es6$promise$$internal$$TRY_CATCH_ERROR) {
8861
+ failed = true;
8862
+ error = value.error;
8863
+ value = null;
8864
+ } else {
8865
+ succeeded = true;
8866
+ }
8867
+
8868
+ if (promise === value) {
8869
+ lib$es6$promise$$internal$$reject(promise, lib$es6$promise$$internal$$cannotReturnOwn());
8870
+ return;
8871
+ }
8872
+
8873
+ } else {
8874
+ value = detail;
8875
+ succeeded = true;
8876
+ }
8877
+
8878
+ if (promise._state !== lib$es6$promise$$internal$$PENDING) {
8879
+ // noop
8880
+ } else if (hasCallback && succeeded) {
8881
+ lib$es6$promise$$internal$$resolve(promise, value);
8882
+ } else if (failed) {
8883
+ lib$es6$promise$$internal$$reject(promise, error);
8884
+ } else if (settled === lib$es6$promise$$internal$$FULFILLED) {
8885
+ lib$es6$promise$$internal$$fulfill(promise, value);
8886
+ } else if (settled === lib$es6$promise$$internal$$REJECTED) {
8887
+ lib$es6$promise$$internal$$reject(promise, value);
8888
+ }
8889
+ }
8890
+
8891
+ function lib$es6$promise$$internal$$initializePromise(promise, resolver) {
8892
+ try {
8893
+ resolver(function resolvePromise(value){
8894
+ lib$es6$promise$$internal$$resolve(promise, value);
8895
+ }, function rejectPromise(reason) {
8896
+ lib$es6$promise$$internal$$reject(promise, reason);
8897
+ });
8898
+ } catch(e) {
8899
+ lib$es6$promise$$internal$$reject(promise, e);
8900
+ }
8901
+ }
8902
+
8903
+ function lib$es6$promise$enumerator$$Enumerator(Constructor, input) {
8904
+ var enumerator = this;
8905
+
8906
+ enumerator._instanceConstructor = Constructor;
8907
+ enumerator.promise = new Constructor(lib$es6$promise$$internal$$noop);
8908
+
8909
+ if (enumerator._validateInput(input)) {
8910
+ enumerator._input = input;
8911
+ enumerator.length = input.length;
8912
+ enumerator._remaining = input.length;
8913
+
8914
+ enumerator._init();
8915
+
8916
+ if (enumerator.length === 0) {
8917
+ lib$es6$promise$$internal$$fulfill(enumerator.promise, enumerator._result);
8918
+ } else {
8919
+ enumerator.length = enumerator.length || 0;
8920
+ enumerator._enumerate();
8921
+ if (enumerator._remaining === 0) {
8922
+ lib$es6$promise$$internal$$fulfill(enumerator.promise, enumerator._result);
8923
+ }
8924
+ }
8925
+ } else {
8926
+ lib$es6$promise$$internal$$reject(enumerator.promise, enumerator._validationError());
8927
+ }
8928
+ }
8929
+
8930
+ lib$es6$promise$enumerator$$Enumerator.prototype._validateInput = function(input) {
8931
+ return lib$es6$promise$utils$$isArray(input);
8932
+ };
8933
+
8934
+ lib$es6$promise$enumerator$$Enumerator.prototype._validationError = function() {
8935
+ return new Error('Array Methods must be provided an Array');
8936
+ };
8937
+
8938
+ lib$es6$promise$enumerator$$Enumerator.prototype._init = function() {
8939
+ this._result = new Array(this.length);
8940
+ };
8941
+
8942
+ var lib$es6$promise$enumerator$$default = lib$es6$promise$enumerator$$Enumerator;
8943
+
8944
+ lib$es6$promise$enumerator$$Enumerator.prototype._enumerate = function() {
8945
+ var enumerator = this;
8946
+
8947
+ var length = enumerator.length;
8948
+ var promise = enumerator.promise;
8949
+ var input = enumerator._input;
8950
+
8951
+ for (var i = 0; promise._state === lib$es6$promise$$internal$$PENDING && i < length; i++) {
8952
+ enumerator._eachEntry(input[i], i);
8953
+ }
8954
+ };
8955
+
8956
+ lib$es6$promise$enumerator$$Enumerator.prototype._eachEntry = function(entry, i) {
8957
+ var enumerator = this;
8958
+ var c = enumerator._instanceConstructor;
8959
+
8960
+ if (lib$es6$promise$utils$$isMaybeThenable(entry)) {
8961
+ if (entry.constructor === c && entry._state !== lib$es6$promise$$internal$$PENDING) {
8962
+ entry._onerror = null;
8963
+ enumerator._settledAt(entry._state, i, entry._result);
8964
+ } else {
8965
+ enumerator._willSettleAt(c.resolve(entry), i);
8966
+ }
8967
+ } else {
8968
+ enumerator._remaining--;
8969
+ enumerator._result[i] = entry;
8970
+ }
8971
+ };
8972
+
8973
+ lib$es6$promise$enumerator$$Enumerator.prototype._settledAt = function(state, i, value) {
8974
+ var enumerator = this;
8975
+ var promise = enumerator.promise;
8976
+
8977
+ if (promise._state === lib$es6$promise$$internal$$PENDING) {
8978
+ enumerator._remaining--;
8979
+
8980
+ if (state === lib$es6$promise$$internal$$REJECTED) {
8981
+ lib$es6$promise$$internal$$reject(promise, value);
8982
+ } else {
8983
+ enumerator._result[i] = value;
8984
+ }
8985
+ }
8986
+
8987
+ if (enumerator._remaining === 0) {
8988
+ lib$es6$promise$$internal$$fulfill(promise, enumerator._result);
8989
+ }
8990
+ };
8991
+
8992
+ lib$es6$promise$enumerator$$Enumerator.prototype._willSettleAt = function(promise, i) {
8993
+ var enumerator = this;
8994
+
8995
+ lib$es6$promise$$internal$$subscribe(promise, undefined, function(value) {
8996
+ enumerator._settledAt(lib$es6$promise$$internal$$FULFILLED, i, value);
8997
+ }, function(reason) {
8998
+ enumerator._settledAt(lib$es6$promise$$internal$$REJECTED, i, reason);
8999
+ });
9000
+ };
9001
+ function lib$es6$promise$promise$all$$all(entries) {
9002
+ return new lib$es6$promise$enumerator$$default(this, entries).promise;
9003
+ }
9004
+ var lib$es6$promise$promise$all$$default = lib$es6$promise$promise$all$$all;
9005
+ function lib$es6$promise$promise$race$$race(entries) {
9006
+ /*jshint validthis:true */
9007
+ var Constructor = this;
9008
+
9009
+ var promise = new Constructor(lib$es6$promise$$internal$$noop);
9010
+
9011
+ if (!lib$es6$promise$utils$$isArray(entries)) {
9012
+ lib$es6$promise$$internal$$reject(promise, new TypeError('You must pass an array to race.'));
9013
+ return promise;
9014
+ }
9015
+
9016
+ var length = entries.length;
9017
+
9018
+ function onFulfillment(value) {
9019
+ lib$es6$promise$$internal$$resolve(promise, value);
9020
+ }
9021
+
9022
+ function onRejection(reason) {
9023
+ lib$es6$promise$$internal$$reject(promise, reason);
9024
+ }
9025
+
9026
+ for (var i = 0; promise._state === lib$es6$promise$$internal$$PENDING && i < length; i++) {
9027
+ lib$es6$promise$$internal$$subscribe(Constructor.resolve(entries[i]), undefined, onFulfillment, onRejection);
9028
+ }
9029
+
9030
+ return promise;
9031
+ }
9032
+ var lib$es6$promise$promise$race$$default = lib$es6$promise$promise$race$$race;
9033
+ function lib$es6$promise$promise$resolve$$resolve(object) {
9034
+ /*jshint validthis:true */
9035
+ var Constructor = this;
9036
+
9037
+ if (object && typeof object === 'object' && object.constructor === Constructor) {
9038
+ return object;
9039
+ }
9040
+
9041
+ var promise = new Constructor(lib$es6$promise$$internal$$noop);
9042
+ lib$es6$promise$$internal$$resolve(promise, object);
9043
+ return promise;
9044
+ }
9045
+ var lib$es6$promise$promise$resolve$$default = lib$es6$promise$promise$resolve$$resolve;
9046
+ function lib$es6$promise$promise$reject$$reject(reason) {
9047
+ /*jshint validthis:true */
9048
+ var Constructor = this;
9049
+ var promise = new Constructor(lib$es6$promise$$internal$$noop);
9050
+ lib$es6$promise$$internal$$reject(promise, reason);
9051
+ return promise;
9052
+ }
9053
+ var lib$es6$promise$promise$reject$$default = lib$es6$promise$promise$reject$$reject;
9054
+
9055
+ var lib$es6$promise$promise$$counter = 0;
9056
+
9057
+ function lib$es6$promise$promise$$needsResolver() {
9058
+ throw new TypeError('You must pass a resolver function as the first argument to the promise constructor');
9059
+ }
9060
+
9061
+ function lib$es6$promise$promise$$needsNew() {
9062
+ throw new TypeError("Failed to construct 'Promise': Please use the 'new' operator, this object constructor cannot be called as a function.");
9063
+ }
9064
+
9065
+ var lib$es6$promise$promise$$default = lib$es6$promise$promise$$Promise;
9066
+ /**
9067
+ Promise objects represent the eventual result of an asynchronous operation. The
9068
+ primary way of interacting with a promise is through its `then` method, which
9069
+ registers callbacks to receive either a promise's eventual value or the reason
9070
+ why the promise cannot be fulfilled.
9071
+
9072
+ Terminology
9073
+ -----------
9074
+
9075
+ - `promise` is an object or function with a `then` method whose behavior conforms to this specification.
9076
+ - `thenable` is an object or function that defines a `then` method.
9077
+ - `value` is any legal JavaScript value (including undefined, a thenable, or a promise).
9078
+ - `exception` is a value that is thrown using the throw statement.
9079
+ - `reason` is a value that indicates why a promise was rejected.
9080
+ - `settled` the final resting state of a promise, fulfilled or rejected.
9081
+
9082
+ A promise can be in one of three states: pending, fulfilled, or rejected.
9083
+
9084
+ Promises that are fulfilled have a fulfillment value and are in the fulfilled
9085
+ state. Promises that are rejected have a rejection reason and are in the
9086
+ rejected state. A fulfillment value is never a thenable.
9087
+
9088
+ Promises can also be said to *resolve* a value. If this value is also a
9089
+ promise, then the original promise's settled state will match the value's
9090
+ settled state. So a promise that *resolves* a promise that rejects will
9091
+ itself reject, and a promise that *resolves* a promise that fulfills will
9092
+ itself fulfill.
9093
+
9094
+
9095
+ Basic Usage:
9096
+ ------------
9097
+
9098
+ ```js
9099
+ var promise = new Promise(function(resolve, reject) {
9100
+ // on success
9101
+ resolve(value);
9102
+
9103
+ // on failure
9104
+ reject(reason);
9105
+ });
9106
+
9107
+ promise.then(function(value) {
9108
+ // on fulfillment
9109
+ }, function(reason) {
9110
+ // on rejection
9111
+ });
9112
+ ```
9113
+
9114
+ Advanced Usage:
9115
+ ---------------
9116
+
9117
+ Promises shine when abstracting away asynchronous interactions such as
9118
+ `XMLHttpRequest`s.
9119
+
9120
+ ```js
9121
+ function getJSON(url) {
9122
+ return new Promise(function(resolve, reject){
9123
+ var xhr = new XMLHttpRequest();
9124
+
9125
+ xhr.open('GET', url);
9126
+ xhr.onreadystatechange = handler;
9127
+ xhr.responseType = 'json';
9128
+ xhr.setRequestHeader('Accept', 'application/json');
9129
+ xhr.send();
9130
+
9131
+ function handler() {
9132
+ if (this.readyState === this.DONE) {
9133
+ if (this.status === 200) {
9134
+ resolve(this.response);
9135
+ } else {
9136
+ reject(new Error('getJSON: `' + url + '` failed with status: [' + this.status + ']'));
9137
+ }
9138
+ }
9139
+ };
9140
+ });
9141
+ }
9142
+
9143
+ getJSON('/posts.json').then(function(json) {
9144
+ // on fulfillment
9145
+ }, function(reason) {
9146
+ // on rejection
9147
+ });
9148
+ ```
9149
+
9150
+ Unlike callbacks, promises are great composable primitives.
9151
+
9152
+ ```js
9153
+ Promise.all([
9154
+ getJSON('/posts'),
9155
+ getJSON('/comments')
9156
+ ]).then(function(values){
9157
+ values[0] // => postsJSON
9158
+ values[1] // => commentsJSON
9159
+
9160
+ return values;
9161
+ });
9162
+ ```
9163
+
9164
+ @class Promise
9165
+ @param {function} resolver
9166
+ Useful for tooling.
9167
+ @constructor
9168
+ */
9169
+ function lib$es6$promise$promise$$Promise(resolver) {
9170
+ this._id = lib$es6$promise$promise$$counter++;
9171
+ this._state = undefined;
9172
+ this._result = undefined;
9173
+ this._subscribers = [];
9174
+
9175
+ if (lib$es6$promise$$internal$$noop !== resolver) {
9176
+ if (!lib$es6$promise$utils$$isFunction(resolver)) {
9177
+ lib$es6$promise$promise$$needsResolver();
9178
+ }
9179
+
9180
+ if (!(this instanceof lib$es6$promise$promise$$Promise)) {
9181
+ lib$es6$promise$promise$$needsNew();
9182
+ }
9183
+
9184
+ lib$es6$promise$$internal$$initializePromise(this, resolver);
9185
+ }
9186
+ }
9187
+
9188
+ lib$es6$promise$promise$$Promise.all = lib$es6$promise$promise$all$$default;
9189
+ lib$es6$promise$promise$$Promise.race = lib$es6$promise$promise$race$$default;
9190
+ lib$es6$promise$promise$$Promise.resolve = lib$es6$promise$promise$resolve$$default;
9191
+ lib$es6$promise$promise$$Promise.reject = lib$es6$promise$promise$reject$$default;
9192
+ lib$es6$promise$promise$$Promise._setScheduler = lib$es6$promise$asap$$setScheduler;
9193
+ lib$es6$promise$promise$$Promise._setAsap = lib$es6$promise$asap$$setAsap;
9194
+ lib$es6$promise$promise$$Promise._asap = lib$es6$promise$asap$$asap;
9195
+
9196
+ lib$es6$promise$promise$$Promise.prototype = {
9197
+ constructor: lib$es6$promise$promise$$Promise,
9198
+
9199
+ /**
9200
+ The primary way of interacting with a promise is through its `then` method,
9201
+ which registers callbacks to receive either a promise's eventual value or the
9202
+ reason why the promise cannot be fulfilled.
9203
+
9204
+ ```js
9205
+ findUser().then(function(user){
9206
+ // user is available
9207
+ }, function(reason){
9208
+ // user is unavailable, and you are given the reason why
9209
+ });
9210
+ ```
9211
+
9212
+ Chaining
9213
+ --------
9214
+
9215
+ The return value of `then` is itself a promise. This second, 'downstream'
9216
+ promise is resolved with the return value of the first promise's fulfillment
9217
+ or rejection handler, or rejected if the handler throws an exception.
9218
+
9219
+ ```js
9220
+ findUser().then(function (user) {
9221
+ return user.name;
9222
+ }, function (reason) {
9223
+ return 'default name';
9224
+ }).then(function (userName) {
9225
+ // If `findUser` fulfilled, `userName` will be the user's name, otherwise it
9226
+ // will be `'default name'`
9227
+ });
9228
+
9229
+ findUser().then(function (user) {
9230
+ throw new Error('Found user, but still unhappy');
9231
+ }, function (reason) {
9232
+ throw new Error('`findUser` rejected and we're unhappy');
9233
+ }).then(function (value) {
9234
+ // never reached
9235
+ }, function (reason) {
9236
+ // if `findUser` fulfilled, `reason` will be 'Found user, but still unhappy'.
9237
+ // If `findUser` rejected, `reason` will be '`findUser` rejected and we're unhappy'.
9238
+ });
9239
+ ```
9240
+ If the downstream promise does not specify a rejection handler, rejection reasons will be propagated further downstream.
9241
+
9242
+ ```js
9243
+ findUser().then(function (user) {
9244
+ throw new PedagogicalException('Upstream error');
9245
+ }).then(function (value) {
9246
+ // never reached
9247
+ }).then(function (value) {
9248
+ // never reached
9249
+ }, function (reason) {
9250
+ // The `PedgagocialException` is propagated all the way down to here
9251
+ });
9252
+ ```
9253
+
9254
+ Assimilation
9255
+ ------------
9256
+
9257
+ Sometimes the value you want to propagate to a downstream promise can only be
9258
+ retrieved asynchronously. This can be achieved by returning a promise in the
9259
+ fulfillment or rejection handler. The downstream promise will then be pending
9260
+ until the returned promise is settled. This is called *assimilation*.
9261
+
9262
+ ```js
9263
+ findUser().then(function (user) {
9264
+ return findCommentsByAuthor(user);
9265
+ }).then(function (comments) {
9266
+ // The user's comments are now available
9267
+ });
9268
+ ```
9269
+
9270
+ If the assimliated promise rejects, then the downstream promise will also reject.
9271
+
9272
+ ```js
9273
+ findUser().then(function (user) {
9274
+ return findCommentsByAuthor(user);
9275
+ }).then(function (comments) {
9276
+ // If `findCommentsByAuthor` fulfills, we'll have the value here
9277
+ }, function (reason) {
9278
+ // If `findCommentsByAuthor` rejects, we'll have the reason here
9279
+ });
9280
+ ```
9281
+
9282
+ Simple Example
9283
+ --------------
9284
+
9285
+ Synchronous Example
9286
+
9287
+ ```javascript
9288
+ var result;
9289
+
9290
+ try {
9291
+ result = findResult();
9292
+ // success
9293
+ } catch(reason) {
9294
+ // failure
9295
+ }
9296
+ ```
9297
+
9298
+ Errback Example
9299
+
9300
+ ```js
9301
+ findResult(function(result, err){
9302
+ if (err) {
9303
+ // failure
9304
+ } else {
9305
+ // success
9306
+ }
9307
+ });
9308
+ ```
9309
+
9310
+ Promise Example;
9311
+
9312
+ ```javascript
9313
+ findResult().then(function(result){
9314
+ // success
9315
+ }, function(reason){
9316
+ // failure
9317
+ });
9318
+ ```
9319
+
9320
+ Advanced Example
9321
+ --------------
9322
+
9323
+ Synchronous Example
9324
+
9325
+ ```javascript
9326
+ var author, books;
9327
+
9328
+ try {
9329
+ author = findAuthor();
9330
+ books = findBooksByAuthor(author);
9331
+ // success
9332
+ } catch(reason) {
9333
+ // failure
9334
+ }
9335
+ ```
9336
+
9337
+ Errback Example
9338
+
9339
+ ```js
9340
+
9341
+ function foundBooks(books) {
9342
+
9343
+ }
9344
+
9345
+ function failure(reason) {
9346
+
9347
+ }
9348
+
9349
+ findAuthor(function(author, err){
9350
+ if (err) {
9351
+ failure(err);
9352
+ // failure
9353
+ } else {
9354
+ try {
9355
+ findBoooksByAuthor(author, function(books, err) {
9356
+ if (err) {
9357
+ failure(err);
9358
+ } else {
9359
+ try {
9360
+ foundBooks(books);
9361
+ } catch(reason) {
9362
+ failure(reason);
9363
+ }
9364
+ }
9365
+ });
9366
+ } catch(error) {
9367
+ failure(err);
9368
+ }
9369
+ // success
9370
+ }
9371
+ });
9372
+ ```
9373
+
9374
+ Promise Example;
9375
+
9376
+ ```javascript
9377
+ findAuthor().
9378
+ then(findBooksByAuthor).
9379
+ then(function(books){
9380
+ // found books
9381
+ }).catch(function(reason){
9382
+ // something went wrong
9383
+ });
9384
+ ```
9385
+
9386
+ @method then
9387
+ @param {Function} onFulfilled
9388
+ @param {Function} onRejected
9389
+ Useful for tooling.
9390
+ @return {Promise}
9391
+ */
9392
+ then: function(onFulfillment, onRejection) {
9393
+ var parent = this;
9394
+ var state = parent._state;
9395
+
9396
+ if (state === lib$es6$promise$$internal$$FULFILLED && !onFulfillment || state === lib$es6$promise$$internal$$REJECTED && !onRejection) {
9397
+ return this;
9398
+ }
9399
+
9400
+ var child = new this.constructor(lib$es6$promise$$internal$$noop);
9401
+ var result = parent._result;
9402
+
9403
+ if (state) {
9404
+ var callback = arguments[state - 1];
9405
+ lib$es6$promise$asap$$asap(function(){
9406
+ lib$es6$promise$$internal$$invokeCallback(state, child, callback, result);
9407
+ });
9408
+ } else {
9409
+ lib$es6$promise$$internal$$subscribe(parent, child, onFulfillment, onRejection);
9410
+ }
9411
+
9412
+ return child;
9413
+ },
9414
+
9415
+ /**
9416
+ `catch` is simply sugar for `then(undefined, onRejection)` which makes it the same
9417
+ as the catch block of a try/catch statement.
9418
+
9419
+ ```js
9420
+ function findAuthor(){
9421
+ throw new Error('couldn't find that author');
9422
+ }
9423
+
9424
+ // synchronous
9425
+ try {
9426
+ findAuthor();
9427
+ } catch(reason) {
9428
+ // something went wrong
9429
+ }
9430
+
9431
+ // async with promises
9432
+ findAuthor().catch(function(reason){
9433
+ // something went wrong
9434
+ });
9435
+ ```
9436
+
9437
+ @method catch
9438
+ @param {Function} onRejection
9439
+ Useful for tooling.
9440
+ @return {Promise}
9441
+ */
9442
+ 'catch': function(onRejection) {
9443
+ return this.then(null, onRejection);
9444
+ }
9445
+ };
9446
+ function lib$es6$promise$polyfill$$polyfill() {
9447
+ var local;
9448
+
9449
+ if (typeof global !== 'undefined') {
9450
+ local = global;
9451
+ } else if (typeof self !== 'undefined') {
9452
+ local = self;
9453
+ } else {
9454
+ try {
9455
+ local = Function('return this')();
9456
+ } catch (e) {
9457
+ throw new Error('polyfill failed because global object is unavailable in this environment');
9458
+ }
9459
+ }
9460
+
9461
+ var P = local.Promise;
9462
+
9463
+ if (P && Object.prototype.toString.call(P.resolve()) === '[object Promise]' && !P.cast) {
9464
+ return;
9465
+ }
9466
+
9467
+ local.Promise = lib$es6$promise$promise$$default;
9468
+ }
9469
+ var lib$es6$promise$polyfill$$default = lib$es6$promise$polyfill$$polyfill;
9470
+
9471
+ var lib$es6$promise$umd$$ES6Promise = {
9472
+ 'Promise': lib$es6$promise$promise$$default,
9473
+ 'polyfill': lib$es6$promise$polyfill$$default
9474
+ };
9475
+
9476
+ /* global define:true module:true window: true */
9477
+ if (typeof define === 'function' && define['amd']) {
9478
+ define(function() { return lib$es6$promise$umd$$ES6Promise; });
9479
+ } else if (typeof module !== 'undefined' && module['exports']) {
9480
+ module['exports'] = lib$es6$promise$umd$$ES6Promise;
9481
+ } else if (typeof this !== 'undefined') {
9482
+ this['ES6Promise'] = lib$es6$promise$umd$$ES6Promise;
9483
+ }
9484
+
9485
+ lib$es6$promise$polyfill$$default();
9486
+ }).call(this);
9487
+
9488
+
9489
+ }).call(this,require('_process'),typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
9490
+ },{"_process":221}],161:[function(require,module,exports){
9491
+ if (typeof Object.create === 'function') {
9492
+ // implementation from standard node.js 'util' module
9493
+ module.exports = function inherits(ctor, superCtor) {
9494
+ ctor.super_ = superCtor
9495
+ ctor.prototype = Object.create(superCtor.prototype, {
9496
+ constructor: {
9497
+ value: ctor,
9498
+ enumerable: false,
9499
+ writable: true,
9500
+ configurable: true
9501
+ }
9502
+ });
9503
+ };
9504
+ } else {
9505
+ // old school shim for old browsers
9506
+ module.exports = function inherits(ctor, superCtor) {
9507
+ ctor.super_ = superCtor
9508
+ var TempCtor = function () {}
9509
+ TempCtor.prototype = superCtor.prototype
9510
+ ctor.prototype = new TempCtor()
9511
+ ctor.prototype.constructor = ctor
9512
+ }
9513
+ }
9514
+
9515
+ },{}],162:[function(require,module,exports){
9516
+ arguments[4][11][0].apply(exports,arguments)
9517
+ },{"../internal/arrayEach":165,"../internal/baseEach":169,"../internal/createForEach":181,"dup":11}],163:[function(require,module,exports){
9518
+ arguments[4][20][0].apply(exports,arguments)
9519
+ },{"dup":20}],164:[function(require,module,exports){
9520
+ arguments[4][24][0].apply(exports,arguments)
9521
+ },{"dup":24}],165:[function(require,module,exports){
9522
+ arguments[4][25][0].apply(exports,arguments)
9523
+ },{"dup":25}],166:[function(require,module,exports){
9524
+ arguments[4][34][0].apply(exports,arguments)
9525
+ },{"../object/keys":206,"./baseCopy":168,"dup":34}],167:[function(require,module,exports){
9526
+ var arrayCopy = require('./arrayCopy'),
9527
+ arrayEach = require('./arrayEach'),
9528
+ baseAssign = require('./baseAssign'),
9529
+ baseForOwn = require('./baseForOwn'),
9530
+ initCloneArray = require('./initCloneArray'),
9531
+ initCloneByTag = require('./initCloneByTag'),
9532
+ initCloneObject = require('./initCloneObject'),
9533
+ isArray = require('../lang/isArray'),
9534
+ isHostObject = require('./isHostObject'),
9535
+ isObject = require('../lang/isObject');
9536
+
9537
+ /** `Object#toString` result references. */
9538
+ var argsTag = '[object Arguments]',
9539
+ arrayTag = '[object Array]',
9540
+ boolTag = '[object Boolean]',
9541
+ dateTag = '[object Date]',
9542
+ errorTag = '[object Error]',
9543
+ funcTag = '[object Function]',
9544
+ mapTag = '[object Map]',
9545
+ numberTag = '[object Number]',
9546
+ objectTag = '[object Object]',
9547
+ regexpTag = '[object RegExp]',
9548
+ setTag = '[object Set]',
9549
+ stringTag = '[object String]',
9550
+ weakMapTag = '[object WeakMap]';
9551
+
9552
+ var arrayBufferTag = '[object ArrayBuffer]',
9553
+ float32Tag = '[object Float32Array]',
9554
+ float64Tag = '[object Float64Array]',
9555
+ int8Tag = '[object Int8Array]',
9556
+ int16Tag = '[object Int16Array]',
9557
+ int32Tag = '[object Int32Array]',
9558
+ uint8Tag = '[object Uint8Array]',
9559
+ uint8ClampedTag = '[object Uint8ClampedArray]',
9560
+ uint16Tag = '[object Uint16Array]',
9561
+ uint32Tag = '[object Uint32Array]';
9562
+
9563
+ /** Used to identify `toStringTag` values supported by `_.clone`. */
9564
+ var cloneableTags = {};
9565
+ cloneableTags[argsTag] = cloneableTags[arrayTag] =
9566
+ cloneableTags[arrayBufferTag] = cloneableTags[boolTag] =
9567
+ cloneableTags[dateTag] = cloneableTags[float32Tag] =
9568
+ cloneableTags[float64Tag] = cloneableTags[int8Tag] =
9569
+ cloneableTags[int16Tag] = cloneableTags[int32Tag] =
9570
+ cloneableTags[numberTag] = cloneableTags[objectTag] =
9571
+ cloneableTags[regexpTag] = cloneableTags[stringTag] =
9572
+ cloneableTags[uint8Tag] = cloneableTags[uint8ClampedTag] =
9573
+ cloneableTags[uint16Tag] = cloneableTags[uint32Tag] = true;
9574
+ cloneableTags[errorTag] = cloneableTags[funcTag] =
9575
+ cloneableTags[mapTag] = cloneableTags[setTag] =
9576
+ cloneableTags[weakMapTag] = false;
9577
+
9578
+ /** Used for native method references. */
9579
+ var objectProto = Object.prototype;
9580
+
9581
+ /**
9582
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
9583
+ * of values.
9584
+ */
9585
+ var objToString = objectProto.toString;
9586
+
9587
+ /**
9588
+ * The base implementation of `_.clone` without support for argument juggling
9589
+ * and `this` binding `customizer` functions.
9590
+ *
9591
+ * @private
9592
+ * @param {*} value The value to clone.
9593
+ * @param {boolean} [isDeep] Specify a deep clone.
9594
+ * @param {Function} [customizer] The function to customize cloning values.
9595
+ * @param {string} [key] The key of `value`.
9596
+ * @param {Object} [object] The object `value` belongs to.
9597
+ * @param {Array} [stackA=[]] Tracks traversed source objects.
9598
+ * @param {Array} [stackB=[]] Associates clones with source counterparts.
9599
+ * @returns {*} Returns the cloned value.
9600
+ */
9601
+ function baseClone(value, isDeep, customizer, key, object, stackA, stackB) {
9602
+ var result;
9603
+ if (customizer) {
9604
+ result = object ? customizer(value, key, object) : customizer(value);
9605
+ }
9606
+ if (result !== undefined) {
9607
+ return result;
9608
+ }
9609
+ if (!isObject(value)) {
9610
+ return value;
9611
+ }
9612
+ var isArr = isArray(value);
9613
+ if (isArr) {
9614
+ result = initCloneArray(value);
9615
+ if (!isDeep) {
9616
+ return arrayCopy(value, result);
9617
+ }
9618
+ } else {
9619
+ var tag = objToString.call(value),
9620
+ isFunc = tag == funcTag;
9621
+
9622
+ if (tag == objectTag || tag == argsTag || (isFunc && !object)) {
9623
+ if (isHostObject(value)) {
9624
+ return object ? value : {};
9625
+ }
9626
+ result = initCloneObject(isFunc ? {} : value);
9627
+ if (!isDeep) {
9628
+ return baseAssign(result, value);
9629
+ }
9630
+ } else {
9631
+ return cloneableTags[tag]
9632
+ ? initCloneByTag(value, tag, isDeep)
9633
+ : (object ? value : {});
9634
+ }
9635
+ }
9636
+ // Check for circular references and return its corresponding clone.
9637
+ stackA || (stackA = []);
9638
+ stackB || (stackB = []);
9639
+
9640
+ var length = stackA.length;
9641
+ while (length--) {
9642
+ if (stackA[length] == value) {
9643
+ return stackB[length];
9644
+ }
9645
+ }
9646
+ // Add the source value to the stack of traversed objects and associate it with its clone.
9647
+ stackA.push(value);
9648
+ stackB.push(result);
9649
+
9650
+ // Recursively populate clone (susceptible to call stack limits).
9651
+ (isArr ? arrayEach : baseForOwn)(value, function(subValue, key) {
9652
+ result[key] = baseClone(subValue, isDeep, customizer, key, value, stackA, stackB);
9653
+ });
9654
+ return result;
9655
+ }
9656
+
9657
+ module.exports = baseClone;
9658
+
9659
+ },{"../lang/isArray":198,"../lang/isObject":201,"./arrayCopy":164,"./arrayEach":165,"./baseAssign":166,"./baseForOwn":172,"./initCloneArray":184,"./initCloneByTag":185,"./initCloneObject":186,"./isHostObject":188}],168:[function(require,module,exports){
9660
+ arguments[4][37][0].apply(exports,arguments)
9661
+ },{"dup":37}],169:[function(require,module,exports){
9662
+ arguments[4][40][0].apply(exports,arguments)
9663
+ },{"./baseForOwn":172,"./createBaseEach":179,"dup":40}],170:[function(require,module,exports){
9664
+ arguments[4][45][0].apply(exports,arguments)
9665
+ },{"./createBaseFor":180,"dup":45}],171:[function(require,module,exports){
9666
+ arguments[4][46][0].apply(exports,arguments)
9667
+ },{"../object/keysIn":207,"./baseFor":170,"dup":46}],172:[function(require,module,exports){
9668
+ arguments[4][47][0].apply(exports,arguments)
9669
+ },{"../object/keys":206,"./baseFor":170,"dup":47}],173:[function(require,module,exports){
9670
+ arguments[4][57][0].apply(exports,arguments)
9671
+ },{"../lang/isArray":198,"../lang/isObject":201,"../lang/isTypedArray":204,"../object/keys":206,"./arrayEach":165,"./baseMergeDeep":174,"./isArrayLike":187,"./isObjectLike":192,"dup":57}],174:[function(require,module,exports){
9672
+ arguments[4][58][0].apply(exports,arguments)
9673
+ },{"../lang/isArguments":197,"../lang/isArray":198,"../lang/isPlainObject":202,"../lang/isTypedArray":204,"../lang/toPlainObject":205,"./arrayCopy":164,"./isArrayLike":187,"dup":58}],175:[function(require,module,exports){
9674
+ var toObject = require('./toObject');
9675
+
9676
+ /**
9677
+ * The base implementation of `_.property` without support for deep paths.
9678
+ *
9679
+ * @private
9680
+ * @param {string} key The key of the property to get.
9681
+ * @returns {Function} Returns the new function.
9682
+ */
9683
+ function baseProperty(key) {
9684
+ return function(object) {
9685
+ return object == null ? undefined : toObject(object)[key];
9686
+ };
9687
+ }
9688
+
9689
+ module.exports = baseProperty;
9690
+
9691
+ },{"./toObject":194}],176:[function(require,module,exports){
9692
+ arguments[4][71][0].apply(exports,arguments)
9693
+ },{"../utility/identity":210,"dup":71}],177:[function(require,module,exports){
9694
+ (function (global){
9695
+ /** Native method references. */
9696
+ var ArrayBuffer = global.ArrayBuffer,
9697
+ Uint8Array = global.Uint8Array;
9698
+
9699
+ /**
9700
+ * Creates a clone of the given array buffer.
9701
+ *
9702
+ * @private
9703
+ * @param {ArrayBuffer} buffer The array buffer to clone.
9704
+ * @returns {ArrayBuffer} Returns the cloned array buffer.
9705
+ */
9706
+ function bufferClone(buffer) {
9707
+ var result = new ArrayBuffer(buffer.byteLength),
9708
+ view = new Uint8Array(result);
9709
+
9710
+ view.set(new Uint8Array(buffer));
9711
+ return result;
9712
+ }
9713
+
9714
+ module.exports = bufferClone;
9715
+
9716
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
9717
+ },{}],178:[function(require,module,exports){
9718
+ arguments[4][79][0].apply(exports,arguments)
9719
+ },{"../function/restParam":163,"./bindCallback":176,"./isIterateeCall":190,"dup":79}],179:[function(require,module,exports){
9720
+ arguments[4][80][0].apply(exports,arguments)
9721
+ },{"./getLength":182,"./isLength":191,"./toObject":194,"dup":80}],180:[function(require,module,exports){
9722
+ arguments[4][81][0].apply(exports,arguments)
9723
+ },{"./toObject":194,"dup":81}],181:[function(require,module,exports){
9724
+ arguments[4][88][0].apply(exports,arguments)
9725
+ },{"../lang/isArray":198,"./bindCallback":176,"dup":88}],182:[function(require,module,exports){
9726
+ arguments[4][98][0].apply(exports,arguments)
9727
+ },{"./baseProperty":175,"dup":98}],183:[function(require,module,exports){
9728
+ arguments[4][100][0].apply(exports,arguments)
9729
+ },{"../lang/isNative":200,"dup":100}],184:[function(require,module,exports){
9730
+ /** Used for native method references. */
9731
+ var objectProto = Object.prototype;
9732
+
9733
+ /** Used to check objects for own properties. */
9734
+ var hasOwnProperty = objectProto.hasOwnProperty;
9735
+
9736
+ /**
9737
+ * Initializes an array clone.
9738
+ *
9739
+ * @private
9740
+ * @param {Array} array The array to clone.
9741
+ * @returns {Array} Returns the initialized clone.
9742
+ */
9743
+ function initCloneArray(array) {
9744
+ var length = array.length,
9745
+ result = new array.constructor(length);
9746
+
9747
+ // Add array properties assigned by `RegExp#exec`.
9748
+ if (length && typeof array[0] == 'string' && hasOwnProperty.call(array, 'index')) {
9749
+ result.index = array.index;
9750
+ result.input = array.input;
9751
+ }
9752
+ return result;
9753
+ }
9754
+
9755
+ module.exports = initCloneArray;
9756
+
9757
+ },{}],185:[function(require,module,exports){
9758
+ (function (global){
9759
+ var bufferClone = require('./bufferClone');
9760
+
9761
+ /** `Object#toString` result references. */
9762
+ var boolTag = '[object Boolean]',
9763
+ dateTag = '[object Date]',
9764
+ numberTag = '[object Number]',
9765
+ regexpTag = '[object RegExp]',
9766
+ stringTag = '[object String]';
9767
+
9768
+ var arrayBufferTag = '[object ArrayBuffer]',
9769
+ float32Tag = '[object Float32Array]',
9770
+ float64Tag = '[object Float64Array]',
9771
+ int8Tag = '[object Int8Array]',
9772
+ int16Tag = '[object Int16Array]',
9773
+ int32Tag = '[object Int32Array]',
9774
+ uint8Tag = '[object Uint8Array]',
9775
+ uint8ClampedTag = '[object Uint8ClampedArray]',
9776
+ uint16Tag = '[object Uint16Array]',
9777
+ uint32Tag = '[object Uint32Array]';
9778
+
9779
+ /** Used to match `RegExp` flags from their coerced string values. */
9780
+ var reFlags = /\w*$/;
9781
+
9782
+ /** Native method references. */
9783
+ var Uint8Array = global.Uint8Array;
9784
+
9785
+ /** Used to lookup a type array constructors by `toStringTag`. */
9786
+ var ctorByTag = {};
9787
+ ctorByTag[float32Tag] = global.Float32Array;
9788
+ ctorByTag[float64Tag] = global.Float64Array;
9789
+ ctorByTag[int8Tag] = global.Int8Array;
9790
+ ctorByTag[int16Tag] = global.Int16Array;
9791
+ ctorByTag[int32Tag] = global.Int32Array;
9792
+ ctorByTag[uint8Tag] = Uint8Array;
9793
+ ctorByTag[uint8ClampedTag] = global.Uint8ClampedArray;
9794
+ ctorByTag[uint16Tag] = global.Uint16Array;
9795
+ ctorByTag[uint32Tag] = global.Uint32Array;
9796
+
9797
+ /**
9798
+ * Initializes an object clone based on its `toStringTag`.
9799
+ *
9800
+ * **Note:** This function only supports cloning values with tags of
9801
+ * `Boolean`, `Date`, `Error`, `Number`, `RegExp`, or `String`.
9802
+ *
9803
+ * @private
9804
+ * @param {Object} object The object to clone.
9805
+ * @param {string} tag The `toStringTag` of the object to clone.
9806
+ * @param {boolean} [isDeep] Specify a deep clone.
9807
+ * @returns {Object} Returns the initialized clone.
9808
+ */
9809
+ function initCloneByTag(object, tag, isDeep) {
9810
+ var Ctor = object.constructor;
9811
+ switch (tag) {
9812
+ case arrayBufferTag:
9813
+ return bufferClone(object);
9814
+
9815
+ case boolTag:
9816
+ case dateTag:
9817
+ return new Ctor(+object);
9818
+
9819
+ case float32Tag: case float64Tag:
9820
+ case int8Tag: case int16Tag: case int32Tag:
9821
+ case uint8Tag: case uint8ClampedTag: case uint16Tag: case uint32Tag:
9822
+ // Safari 5 mobile incorrectly has `Object` as the constructor of typed arrays.
9823
+ if (Ctor instanceof Ctor) {
9824
+ Ctor = ctorByTag[tag];
9825
+ }
9826
+ var buffer = object.buffer;
9827
+ return new Ctor(isDeep ? bufferClone(buffer) : buffer, object.byteOffset, object.length);
9828
+
9829
+ case numberTag:
9830
+ case stringTag:
9831
+ return new Ctor(object);
9832
+
9833
+ case regexpTag:
9834
+ var result = new Ctor(object.source, reFlags.exec(object));
9835
+ result.lastIndex = object.lastIndex;
9836
+ }
9837
+ return result;
9838
+ }
9839
+
9840
+ module.exports = initCloneByTag;
9841
+
9842
+ }).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
9843
+ },{"./bufferClone":177}],186:[function(require,module,exports){
9844
+ /**
9845
+ * Initializes an object clone.
9846
+ *
9847
+ * @private
9848
+ * @param {Object} object The object to clone.
9849
+ * @returns {Object} Returns the initialized clone.
9850
+ */
9851
+ function initCloneObject(object) {
9852
+ var Ctor = object.constructor;
9853
+ if (!(typeof Ctor == 'function' && Ctor instanceof Ctor)) {
9854
+ Ctor = Object;
9855
+ }
9856
+ return new Ctor;
9857
+ }
9858
+
9859
+ module.exports = initCloneObject;
9860
+
9861
+ },{}],187:[function(require,module,exports){
9862
+ arguments[4][102][0].apply(exports,arguments)
9863
+ },{"./getLength":182,"./isLength":191,"dup":102}],188:[function(require,module,exports){
9864
+ /**
9865
+ * Checks if `value` is a host object in IE < 9.
9866
+ *
9867
+ * @private
9868
+ * @param {*} value The value to check.
9869
+ * @returns {boolean} Returns `true` if `value` is a host object, else `false`.
9870
+ */
9871
+ var isHostObject = (function() {
9872
+ try {
9873
+ Object({ 'toString': 0 } + '');
9874
+ } catch(e) {
9875
+ return function() { return false; };
9876
+ }
9877
+ return function(value) {
9878
+ // IE < 9 presents many host objects as `Object` objects that can coerce
9879
+ // to strings despite having improperly defined `toString` methods.
9880
+ return typeof value.toString != 'function' && typeof (value + '') == 'string';
9881
+ };
9882
+ }());
9883
+
9884
+ module.exports = isHostObject;
9885
+
9886
+ },{}],189:[function(require,module,exports){
9887
+ arguments[4][103][0].apply(exports,arguments)
9888
+ },{"dup":103}],190:[function(require,module,exports){
9889
+ arguments[4][104][0].apply(exports,arguments)
9890
+ },{"../lang/isObject":201,"./isArrayLike":187,"./isIndex":189,"dup":104}],191:[function(require,module,exports){
9891
+ arguments[4][107][0].apply(exports,arguments)
9892
+ },{"dup":107}],192:[function(require,module,exports){
9893
+ arguments[4][108][0].apply(exports,arguments)
9894
+ },{"dup":108}],193:[function(require,module,exports){
9895
+ var isArguments = require('../lang/isArguments'),
9896
+ isArray = require('../lang/isArray'),
9897
+ isIndex = require('./isIndex'),
9898
+ isLength = require('./isLength'),
9899
+ isString = require('../lang/isString'),
9900
+ keysIn = require('../object/keysIn');
9901
+
9902
+ /** Used for native method references. */
9903
+ var objectProto = Object.prototype;
9904
+
9905
+ /** Used to check objects for own properties. */
9906
+ var hasOwnProperty = objectProto.hasOwnProperty;
9907
+
9908
+ /**
9909
+ * A fallback implementation of `Object.keys` which creates an array of the
9910
+ * own enumerable property names of `object`.
9911
+ *
9912
+ * @private
9913
+ * @param {Object} object The object to query.
9914
+ * @returns {Array} Returns the array of property names.
9915
+ */
9916
+ function shimKeys(object) {
9917
+ var props = keysIn(object),
9918
+ propsLength = props.length,
9919
+ length = propsLength && object.length;
9920
+
9921
+ var allowIndexes = !!length && isLength(length) &&
9922
+ (isArray(object) || isArguments(object) || isString(object));
9923
+
9924
+ var index = -1,
9925
+ result = [];
9926
+
9927
+ while (++index < propsLength) {
9928
+ var key = props[index];
9929
+ if ((allowIndexes && isIndex(key, length)) || hasOwnProperty.call(object, key)) {
9930
+ result.push(key);
9931
+ }
9932
+ }
9933
+ return result;
9934
+ }
9935
+
9936
+ module.exports = shimKeys;
9937
+
9938
+ },{"../lang/isArguments":197,"../lang/isArray":198,"../lang/isString":203,"../object/keysIn":207,"./isIndex":189,"./isLength":191}],194:[function(require,module,exports){
9939
+ var isObject = require('../lang/isObject'),
9940
+ isString = require('../lang/isString'),
9941
+ support = require('../support');
9942
+
9943
+ /**
9944
+ * Converts `value` to an object if it's not one.
9945
+ *
9946
+ * @private
9947
+ * @param {*} value The value to process.
9948
+ * @returns {Object} Returns the object.
9949
+ */
9950
+ function toObject(value) {
9951
+ if (support.unindexedChars && isString(value)) {
9952
+ var index = -1,
9953
+ length = value.length,
9954
+ result = Object(value);
9955
+
9956
+ while (++index < length) {
9957
+ result[index] = value.charAt(index);
9958
+ }
9959
+ return result;
9960
+ }
9961
+ return isObject(value) ? value : Object(value);
9962
+ }
9963
+
9964
+ module.exports = toObject;
9965
+
9966
+ },{"../lang/isObject":201,"../lang/isString":203,"../support":209}],195:[function(require,module,exports){
9967
+ var baseClone = require('../internal/baseClone'),
9968
+ bindCallback = require('../internal/bindCallback'),
9969
+ isIterateeCall = require('../internal/isIterateeCall');
9970
+
9971
+ /**
9972
+ * Creates a clone of `value`. If `isDeep` is `true` nested objects are cloned,
9973
+ * otherwise they are assigned by reference. If `customizer` is provided it is
9974
+ * invoked to produce the cloned values. If `customizer` returns `undefined`
9975
+ * cloning is handled by the method instead. The `customizer` is bound to
9976
+ * `thisArg` and invoked with two argument; (value [, index|key, object]).
9977
+ *
9978
+ * **Note:** This method is loosely based on the
9979
+ * [structured clone algorithm](http://www.w3.org/TR/html5/infrastructure.html#internal-structured-cloning-algorithm).
9980
+ * The enumerable properties of `arguments` objects and objects created by
9981
+ * constructors other than `Object` are cloned to plain `Object` objects. An
9982
+ * empty object is returned for uncloneable values such as functions, DOM nodes,
9983
+ * Maps, Sets, and WeakMaps.
9984
+ *
9985
+ * @static
9986
+ * @memberOf _
9987
+ * @category Lang
9988
+ * @param {*} value The value to clone.
9989
+ * @param {boolean} [isDeep] Specify a deep clone.
9990
+ * @param {Function} [customizer] The function to customize cloning values.
9991
+ * @param {*} [thisArg] The `this` binding of `customizer`.
9992
+ * @returns {*} Returns the cloned value.
9993
+ * @example
9994
+ *
9995
+ * var users = [
9996
+ * { 'user': 'barney' },
9997
+ * { 'user': 'fred' }
9998
+ * ];
9999
+ *
10000
+ * var shallow = _.clone(users);
10001
+ * shallow[0] === users[0];
10002
+ * // => true
10003
+ *
10004
+ * var deep = _.clone(users, true);
10005
+ * deep[0] === users[0];
10006
+ * // => false
10007
+ *
10008
+ * // using a customizer callback
10009
+ * var el = _.clone(document.body, function(value) {
10010
+ * if (_.isElement(value)) {
10011
+ * return value.cloneNode(false);
10012
+ * }
10013
+ * });
10014
+ *
10015
+ * el === document.body
10016
+ * // => false
10017
+ * el.nodeName
10018
+ * // => BODY
10019
+ * el.childNodes.length;
10020
+ * // => 0
10021
+ */
10022
+ function clone(value, isDeep, customizer, thisArg) {
10023
+ if (isDeep && typeof isDeep != 'boolean' && isIterateeCall(value, isDeep, customizer)) {
10024
+ isDeep = false;
10025
+ }
10026
+ else if (typeof isDeep == 'function') {
10027
+ thisArg = customizer;
10028
+ customizer = isDeep;
10029
+ isDeep = false;
10030
+ }
10031
+ return typeof customizer == 'function'
10032
+ ? baseClone(value, isDeep, bindCallback(customizer, thisArg, 1))
10033
+ : baseClone(value, isDeep);
10034
+ }
10035
+
10036
+ module.exports = clone;
10037
+
10038
+ },{"../internal/baseClone":167,"../internal/bindCallback":176,"../internal/isIterateeCall":190}],196:[function(require,module,exports){
10039
+ var baseClone = require('../internal/baseClone'),
10040
+ bindCallback = require('../internal/bindCallback');
10041
+
10042
+ /**
10043
+ * Creates a deep clone of `value`. If `customizer` is provided it is invoked
10044
+ * to produce the cloned values. If `customizer` returns `undefined` cloning
10045
+ * is handled by the method instead. The `customizer` is bound to `thisArg`
10046
+ * and invoked with two argument; (value [, index|key, object]).
10047
+ *
10048
+ * **Note:** This method is loosely based on the
10049
+ * [structured clone algorithm](http://www.w3.org/TR/html5/infrastructure.html#internal-structured-cloning-algorithm).
10050
+ * The enumerable properties of `arguments` objects and objects created by
10051
+ * constructors other than `Object` are cloned to plain `Object` objects. An
10052
+ * empty object is returned for uncloneable values such as functions, DOM nodes,
10053
+ * Maps, Sets, and WeakMaps.
10054
+ *
10055
+ * @static
10056
+ * @memberOf _
10057
+ * @category Lang
10058
+ * @param {*} value The value to deep clone.
10059
+ * @param {Function} [customizer] The function to customize cloning values.
10060
+ * @param {*} [thisArg] The `this` binding of `customizer`.
10061
+ * @returns {*} Returns the deep cloned value.
10062
+ * @example
10063
+ *
10064
+ * var users = [
10065
+ * { 'user': 'barney' },
10066
+ * { 'user': 'fred' }
10067
+ * ];
10068
+ *
10069
+ * var deep = _.cloneDeep(users);
10070
+ * deep[0] === users[0];
10071
+ * // => false
10072
+ *
10073
+ * // using a customizer callback
10074
+ * var el = _.cloneDeep(document.body, function(value) {
10075
+ * if (_.isElement(value)) {
10076
+ * return value.cloneNode(true);
10077
+ * }
10078
+ * });
10079
+ *
10080
+ * el === document.body
10081
+ * // => false
10082
+ * el.nodeName
10083
+ * // => BODY
10084
+ * el.childNodes.length;
10085
+ * // => 20
10086
+ */
10087
+ function cloneDeep(value, customizer, thisArg) {
10088
+ return typeof customizer == 'function'
10089
+ ? baseClone(value, true, bindCallback(customizer, thisArg, 1))
10090
+ : baseClone(value, true);
10091
+ }
10092
+
10093
+ module.exports = cloneDeep;
10094
+
10095
+ },{"../internal/baseClone":167,"../internal/bindCallback":176}],197:[function(require,module,exports){
10096
+ arguments[4][126][0].apply(exports,arguments)
10097
+ },{"../internal/isArrayLike":187,"../internal/isObjectLike":192,"dup":126}],198:[function(require,module,exports){
10098
+ arguments[4][127][0].apply(exports,arguments)
10099
+ },{"../internal/getNative":183,"../internal/isLength":191,"../internal/isObjectLike":192,"dup":127}],199:[function(require,module,exports){
10100
+ arguments[4][129][0].apply(exports,arguments)
10101
+ },{"./isObject":201,"dup":129}],200:[function(require,module,exports){
10102
+ var isFunction = require('./isFunction'),
10103
+ isHostObject = require('../internal/isHostObject'),
10104
+ isObjectLike = require('../internal/isObjectLike');
10105
+
10106
+ /** Used to detect host constructors (Safari > 5). */
10107
+ var reIsHostCtor = /^\[object .+?Constructor\]$/;
10108
+
10109
+ /** Used for native method references. */
10110
+ var objectProto = Object.prototype;
10111
+
10112
+ /** Used to resolve the decompiled source of functions. */
10113
+ var fnToString = Function.prototype.toString;
10114
+
10115
+ /** Used to check objects for own properties. */
10116
+ var hasOwnProperty = objectProto.hasOwnProperty;
10117
+
10118
+ /** Used to detect if a method is native. */
10119
+ var reIsNative = RegExp('^' +
10120
+ fnToString.call(hasOwnProperty).replace(/[\\^$.*+?()[\]{}|]/g, '\\$&')
10121
+ .replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$'
10122
+ );
10123
+
10124
+ /**
10125
+ * Checks if `value` is a native function.
10126
+ *
10127
+ * @static
10128
+ * @memberOf _
10129
+ * @category Lang
10130
+ * @param {*} value The value to check.
10131
+ * @returns {boolean} Returns `true` if `value` is a native function, else `false`.
10132
+ * @example
10133
+ *
10134
+ * _.isNative(Array.prototype.push);
10135
+ * // => true
10136
+ *
10137
+ * _.isNative(_);
10138
+ * // => false
10139
+ */
10140
+ function isNative(value) {
10141
+ if (value == null) {
10142
+ return false;
10143
+ }
10144
+ if (isFunction(value)) {
10145
+ return reIsNative.test(fnToString.call(value));
10146
+ }
10147
+ return isObjectLike(value) && (isHostObject(value) ? reIsNative : reIsHostCtor).test(value);
10148
+ }
10149
+
10150
+ module.exports = isNative;
10151
+
10152
+ },{"../internal/isHostObject":188,"../internal/isObjectLike":192,"./isFunction":199}],201:[function(require,module,exports){
10153
+ arguments[4][131][0].apply(exports,arguments)
10154
+ },{"dup":131}],202:[function(require,module,exports){
10155
+ var baseForIn = require('../internal/baseForIn'),
10156
+ isArguments = require('./isArguments'),
10157
+ isHostObject = require('../internal/isHostObject'),
10158
+ isObjectLike = require('../internal/isObjectLike'),
10159
+ support = require('../support');
10160
+
10161
+ /** `Object#toString` result references. */
10162
+ var objectTag = '[object Object]';
10163
+
10164
+ /** Used for native method references. */
10165
+ var objectProto = Object.prototype;
10166
+
10167
+ /** Used to check objects for own properties. */
10168
+ var hasOwnProperty = objectProto.hasOwnProperty;
10169
+
10170
+ /**
10171
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
10172
+ * of values.
10173
+ */
10174
+ var objToString = objectProto.toString;
10175
+
10176
+ /**
10177
+ * Checks if `value` is a plain object, that is, an object created by the
10178
+ * `Object` constructor or one with a `[[Prototype]]` of `null`.
10179
+ *
10180
+ * **Note:** This method assumes objects created by the `Object` constructor
10181
+ * have no inherited enumerable properties.
10182
+ *
10183
+ * @static
10184
+ * @memberOf _
10185
+ * @category Lang
10186
+ * @param {*} value The value to check.
10187
+ * @returns {boolean} Returns `true` if `value` is a plain object, else `false`.
10188
+ * @example
10189
+ *
10190
+ * function Foo() {
10191
+ * this.a = 1;
10192
+ * }
10193
+ *
10194
+ * _.isPlainObject(new Foo);
10195
+ * // => false
10196
+ *
10197
+ * _.isPlainObject([1, 2, 3]);
10198
+ * // => false
10199
+ *
10200
+ * _.isPlainObject({ 'x': 0, 'y': 0 });
10201
+ * // => true
10202
+ *
10203
+ * _.isPlainObject(Object.create(null));
10204
+ * // => true
10205
+ */
10206
+ function isPlainObject(value) {
10207
+ var Ctor;
10208
+
10209
+ // Exit early for non `Object` objects.
10210
+ if (!(isObjectLike(value) && objToString.call(value) == objectTag && !isHostObject(value) && !isArguments(value)) ||
10211
+ (!hasOwnProperty.call(value, 'constructor') && (Ctor = value.constructor, typeof Ctor == 'function' && !(Ctor instanceof Ctor)))) {
10212
+ return false;
10213
+ }
10214
+ // IE < 9 iterates inherited properties before own properties. If the first
10215
+ // iterated property is an object's own property then there are no inherited
10216
+ // enumerable properties.
10217
+ var result;
10218
+ if (support.ownLast) {
10219
+ baseForIn(value, function(subValue, key, object) {
10220
+ result = hasOwnProperty.call(object, key);
10221
+ return false;
10222
+ });
10223
+ return result !== false;
10224
+ }
10225
+ // In most environments an object's own properties are iterated before
10226
+ // its inherited properties. If the last iterated property is an object's
10227
+ // own property then there are no inherited enumerable properties.
10228
+ baseForIn(value, function(subValue, key) {
10229
+ result = key;
10230
+ });
10231
+ return result === undefined || hasOwnProperty.call(value, result);
10232
+ }
10233
+
10234
+ module.exports = isPlainObject;
10235
+
10236
+ },{"../internal/baseForIn":171,"../internal/isHostObject":188,"../internal/isObjectLike":192,"../support":209,"./isArguments":197}],203:[function(require,module,exports){
10237
+ arguments[4][133][0].apply(exports,arguments)
10238
+ },{"../internal/isObjectLike":192,"dup":133}],204:[function(require,module,exports){
10239
+ arguments[4][134][0].apply(exports,arguments)
10240
+ },{"../internal/isLength":191,"../internal/isObjectLike":192,"dup":134}],205:[function(require,module,exports){
10241
+ arguments[4][136][0].apply(exports,arguments)
10242
+ },{"../internal/baseCopy":168,"../object/keysIn":207,"dup":136}],206:[function(require,module,exports){
10243
+ var getNative = require('../internal/getNative'),
10244
+ isArrayLike = require('../internal/isArrayLike'),
10245
+ isObject = require('../lang/isObject'),
10246
+ shimKeys = require('../internal/shimKeys'),
10247
+ support = require('../support');
10248
+
10249
+ /* Native method references for those with the same name as other `lodash` methods. */
10250
+ var nativeKeys = getNative(Object, 'keys');
10251
+
10252
+ /**
10253
+ * Creates an array of the own enumerable property names of `object`.
10254
+ *
10255
+ * **Note:** Non-object values are coerced to objects. See the
10256
+ * [ES spec](http://ecma-international.org/ecma-262/6.0/#sec-object.keys)
10257
+ * for more details.
10258
+ *
10259
+ * @static
10260
+ * @memberOf _
10261
+ * @category Object
10262
+ * @param {Object} object The object to query.
10263
+ * @returns {Array} Returns the array of property names.
10264
+ * @example
10265
+ *
10266
+ * function Foo() {
10267
+ * this.a = 1;
10268
+ * this.b = 2;
10269
+ * }
10270
+ *
10271
+ * Foo.prototype.c = 3;
10272
+ *
10273
+ * _.keys(new Foo);
10274
+ * // => ['a', 'b'] (iteration order is not guaranteed)
10275
+ *
10276
+ * _.keys('hi');
10277
+ * // => ['0', '1']
10278
+ */
10279
+ var keys = !nativeKeys ? shimKeys : function(object) {
10280
+ var Ctor = object == null ? undefined : object.constructor;
10281
+ if ((typeof Ctor == 'function' && Ctor.prototype === object) ||
10282
+ (typeof object == 'function' ? support.enumPrototypes : isArrayLike(object))) {
10283
+ return shimKeys(object);
10284
+ }
10285
+ return isObject(object) ? nativeKeys(object) : [];
10286
+ };
10287
+
10288
+ module.exports = keys;
10289
+
10290
+ },{"../internal/getNative":183,"../internal/isArrayLike":187,"../internal/shimKeys":193,"../lang/isObject":201,"../support":209}],207:[function(require,module,exports){
10291
+ var arrayEach = require('../internal/arrayEach'),
10292
+ isArguments = require('../lang/isArguments'),
10293
+ isArray = require('../lang/isArray'),
10294
+ isFunction = require('../lang/isFunction'),
10295
+ isIndex = require('../internal/isIndex'),
10296
+ isLength = require('../internal/isLength'),
10297
+ isObject = require('../lang/isObject'),
10298
+ isString = require('../lang/isString'),
10299
+ support = require('../support');
10300
+
10301
+ /** `Object#toString` result references. */
10302
+ var arrayTag = '[object Array]',
10303
+ boolTag = '[object Boolean]',
10304
+ dateTag = '[object Date]',
10305
+ errorTag = '[object Error]',
10306
+ funcTag = '[object Function]',
10307
+ numberTag = '[object Number]',
10308
+ objectTag = '[object Object]',
10309
+ regexpTag = '[object RegExp]',
10310
+ stringTag = '[object String]';
10311
+
10312
+ /** Used to fix the JScript `[[DontEnum]]` bug. */
10313
+ var shadowProps = [
10314
+ 'constructor', 'hasOwnProperty', 'isPrototypeOf', 'propertyIsEnumerable',
10315
+ 'toLocaleString', 'toString', 'valueOf'
10316
+ ];
10317
+
10318
+ /** Used for native method references. */
10319
+ var errorProto = Error.prototype,
10320
+ objectProto = Object.prototype,
10321
+ stringProto = String.prototype;
10322
+
10323
+ /** Used to check objects for own properties. */
10324
+ var hasOwnProperty = objectProto.hasOwnProperty;
10325
+
10326
+ /**
10327
+ * Used to resolve the [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
10328
+ * of values.
10329
+ */
10330
+ var objToString = objectProto.toString;
10331
+
10332
+ /** Used to avoid iterating over non-enumerable properties in IE < 9. */
10333
+ var nonEnumProps = {};
10334
+ nonEnumProps[arrayTag] = nonEnumProps[dateTag] = nonEnumProps[numberTag] = { 'constructor': true, 'toLocaleString': true, 'toString': true, 'valueOf': true };
10335
+ nonEnumProps[boolTag] = nonEnumProps[stringTag] = { 'constructor': true, 'toString': true, 'valueOf': true };
10336
+ nonEnumProps[errorTag] = nonEnumProps[funcTag] = nonEnumProps[regexpTag] = { 'constructor': true, 'toString': true };
10337
+ nonEnumProps[objectTag] = { 'constructor': true };
10338
+
10339
+ arrayEach(shadowProps, function(key) {
10340
+ for (var tag in nonEnumProps) {
10341
+ if (hasOwnProperty.call(nonEnumProps, tag)) {
10342
+ var props = nonEnumProps[tag];
10343
+ props[key] = hasOwnProperty.call(props, key);
10344
+ }
10345
+ }
10346
+ });
10347
+
10348
+ /**
10349
+ * Creates an array of the own and inherited enumerable property names of `object`.
10350
+ *
10351
+ * **Note:** Non-object values are coerced to objects.
10352
+ *
10353
+ * @static
10354
+ * @memberOf _
10355
+ * @category Object
10356
+ * @param {Object} object The object to query.
10357
+ * @returns {Array} Returns the array of property names.
10358
+ * @example
10359
+ *
10360
+ * function Foo() {
10361
+ * this.a = 1;
10362
+ * this.b = 2;
10363
+ * }
10364
+ *
10365
+ * Foo.prototype.c = 3;
10366
+ *
10367
+ * _.keysIn(new Foo);
10368
+ * // => ['a', 'b', 'c'] (iteration order is not guaranteed)
10369
+ */
10370
+ function keysIn(object) {
10371
+ if (object == null) {
10372
+ return [];
10373
+ }
10374
+ if (!isObject(object)) {
10375
+ object = Object(object);
10376
+ }
10377
+ var length = object.length;
10378
+
10379
+ length = (length && isLength(length) &&
10380
+ (isArray(object) || isArguments(object) || isString(object)) && length) || 0;
10381
+
10382
+ var Ctor = object.constructor,
10383
+ index = -1,
10384
+ proto = (isFunction(Ctor) && Ctor.prototype) || objectProto,
10385
+ isProto = proto === object,
10386
+ result = Array(length),
10387
+ skipIndexes = length > 0,
10388
+ skipErrorProps = support.enumErrorProps && (object === errorProto || object instanceof Error),
10389
+ skipProto = support.enumPrototypes && isFunction(object);
10390
+
10391
+ while (++index < length) {
10392
+ result[index] = (index + '');
10393
+ }
10394
+ // lodash skips the `constructor` property when it infers it is iterating
10395
+ // over a `prototype` object because IE < 9 can't set the `[[Enumerable]]`
10396
+ // attribute of an existing property and the `constructor` property of a
10397
+ // prototype defaults to non-enumerable.
10398
+ for (var key in object) {
10399
+ if (!(skipProto && key == 'prototype') &&
10400
+ !(skipErrorProps && (key == 'message' || key == 'name')) &&
10401
+ !(skipIndexes && isIndex(key, length)) &&
10402
+ !(key == 'constructor' && (isProto || !hasOwnProperty.call(object, key)))) {
10403
+ result.push(key);
10404
+ }
10405
+ }
10406
+ if (support.nonEnumShadows && object !== objectProto) {
10407
+ var tag = object === stringProto ? stringTag : (object === errorProto ? errorTag : objToString.call(object)),
10408
+ nonEnums = nonEnumProps[tag] || nonEnumProps[objectTag];
10409
+
10410
+ if (tag == objectTag) {
10411
+ proto = objectProto;
10412
+ }
10413
+ length = shadowProps.length;
10414
+ while (length--) {
10415
+ key = shadowProps[length];
10416
+ var nonEnum = nonEnums[key];
10417
+ if (!(isProto && nonEnum) &&
10418
+ (nonEnum ? hasOwnProperty.call(object, key) : object[key] !== proto[key])) {
10419
+ result.push(key);
10420
+ }
10421
+ }
10422
+ }
10423
+ return result;
10424
+ }
10425
+
10426
+ module.exports = keysIn;
10427
+
10428
+ },{"../internal/arrayEach":165,"../internal/isIndex":189,"../internal/isLength":191,"../lang/isArguments":197,"../lang/isArray":198,"../lang/isFunction":199,"../lang/isObject":201,"../lang/isString":203,"../support":209}],208:[function(require,module,exports){
10429
+ arguments[4][142][0].apply(exports,arguments)
10430
+ },{"../internal/baseMerge":173,"../internal/createAssigner":178,"dup":142}],209:[function(require,module,exports){
10431
+ /** Used for native method references. */
10432
+ var arrayProto = Array.prototype,
10433
+ errorProto = Error.prototype,
10434
+ objectProto = Object.prototype;
10435
+
10436
+ /** Native method references. */
10437
+ var propertyIsEnumerable = objectProto.propertyIsEnumerable,
10438
+ splice = arrayProto.splice;
10439
+
10440
+ /**
10441
+ * An object environment feature flags.
10442
+ *
10443
+ * @static
10444
+ * @memberOf _
10445
+ * @type Object
10446
+ */
10447
+ var support = {};
10448
+
10449
+ (function(x) {
10450
+ var Ctor = function() { this.x = x; },
10451
+ object = { '0': x, 'length': x },
10452
+ props = [];
10453
+
10454
+ Ctor.prototype = { 'valueOf': x, 'y': x };
10455
+ for (var key in new Ctor) { props.push(key); }
10456
+
10457
+ /**
10458
+ * Detect if `name` or `message` properties of `Error.prototype` are
10459
+ * enumerable by default (IE < 9, Safari < 5.1).
10460
+ *
10461
+ * @memberOf _.support
10462
+ * @type boolean
10463
+ */
10464
+ support.enumErrorProps = propertyIsEnumerable.call(errorProto, 'message') ||
10465
+ propertyIsEnumerable.call(errorProto, 'name');
10466
+
10467
+ /**
10468
+ * Detect if `prototype` properties are enumerable by default.
10469
+ *
10470
+ * Firefox < 3.6, Opera > 9.50 - Opera < 11.60, and Safari < 5.1
10471
+ * (if the prototype or a property on the prototype has been set)
10472
+ * incorrectly set the `[[Enumerable]]` value of a function's `prototype`
10473
+ * property to `true`.
10474
+ *
10475
+ * @memberOf _.support
10476
+ * @type boolean
10477
+ */
10478
+ support.enumPrototypes = propertyIsEnumerable.call(Ctor, 'prototype');
10479
+
10480
+ /**
10481
+ * Detect if properties shadowing those on `Object.prototype` are non-enumerable.
10482
+ *
10483
+ * In IE < 9 an object's own properties, shadowing non-enumerable ones,
10484
+ * are made non-enumerable as well (a.k.a the JScript `[[DontEnum]]` bug).
10485
+ *
10486
+ * @memberOf _.support
10487
+ * @type boolean
10488
+ */
10489
+ support.nonEnumShadows = !/valueOf/.test(props);
10490
+
10491
+ /**
10492
+ * Detect if own properties are iterated after inherited properties (IE < 9).
10493
+ *
10494
+ * @memberOf _.support
10495
+ * @type boolean
10496
+ */
10497
+ support.ownLast = props[0] != 'x';
10498
+
10499
+ /**
10500
+ * Detect if `Array#shift` and `Array#splice` augment array-like objects
10501
+ * correctly.
10502
+ *
10503
+ * Firefox < 10, compatibility modes of IE 8, and IE < 9 have buggy Array
10504
+ * `shift()` and `splice()` functions that fail to remove the last element,
10505
+ * `value[0]`, of array-like objects even though the "length" property is
10506
+ * set to `0`. The `shift()` method is buggy in compatibility modes of IE 8,
10507
+ * while `splice()` is buggy regardless of mode in IE < 9.
10508
+ *
10509
+ * @memberOf _.support
10510
+ * @type boolean
10511
+ */
10512
+ support.spliceObjects = (splice.call(object, 0, 1), !object[0]);
10513
+
10514
+ /**
10515
+ * Detect lack of support for accessing string characters by index.
10516
+ *
10517
+ * IE < 8 can't access characters by index. IE 8 can only access characters
10518
+ * by index on string literals, not string objects.
10519
+ *
10520
+ * @memberOf _.support
10521
+ * @type boolean
10522
+ */
10523
+ support.unindexedChars = ('x'[0] + Object('x')[0]) != 'xx';
10524
+ }(1, 0));
10525
+
10526
+ module.exports = support;
10527
+
10528
+ },{}],210:[function(require,module,exports){
10529
+ arguments[4][148][0].apply(exports,arguments)
10530
+ },{"dup":148}],211:[function(require,module,exports){
10531
+ (function (process){
10532
+ 'use strict';
10533
+
10534
+ module.exports = AlgoliaSearch;
10535
+
10536
+ // default debug activated in dev environments
10537
+ // this is triggered in package.json, using the envify transform
10538
+ if (process.env.APP_ENV === 'development') {
10539
+ require('debug').enable('algoliasearch*');
10540
+ }
10541
+
10542
+ var errors = require('./errors');
10543
+
10544
+ /*
10545
+ * Algolia Search library initialization
10546
+ * https://www.algolia.com/
10547
+ *
10548
+ * @param {string} applicationID - Your applicationID, found in your dashboard
10549
+ * @param {string} apiKey - Your API key, found in your dashboard
10550
+ * @param {Object} [opts]
10551
+ * @param {number} [opts.timeout=2000] - The request timeout set in milliseconds,
10552
+ * another request will be issued after this timeout
10553
+ * @param {string} [opts.protocol='http:'] - The protocol used to query Algolia Search API.
10554
+ * Set to 'https:' to force using https.
10555
+ * Default to document.location.protocol in browsers
10556
+ * @param {Object|Array} [opts.hosts={
10557
+ * read: [this.applicationID + '-dsn.algolia.net'].concat([
10558
+ * this.applicationID + '-1.algolianet.com',
10559
+ * this.applicationID + '-2.algolianet.com',
10560
+ * this.applicationID + '-3.algolianet.com']
10561
+ * ]),
10562
+ * write: [this.applicationID + '.algolia.net'].concat([
10563
+ * this.applicationID + '-1.algolianet.com',
10564
+ * this.applicationID + '-2.algolianet.com',
10565
+ * this.applicationID + '-3.algolianet.com']
10566
+ * ]) - The hosts to use for Algolia Search API.
10567
+ * If you provide them, you will less benefit from our HA implementation
10568
+ */
10569
+ function AlgoliaSearch(applicationID, apiKey, opts) {
10570
+ var debug = require('debug')('algoliasearch');
10571
+
10572
+ var clone = require('lodash-compat/lang/clone');
10573
+ var isArray = require('lodash-compat/lang/isArray');
10574
+
10575
+ var usage = 'Usage: algoliasearch(applicationID, apiKey, opts)';
10576
+
10577
+ if (!applicationID) {
10578
+ throw new errors.AlgoliaSearchError('Please provide an application ID. ' + usage);
10579
+ }
10580
+
10581
+ if (!apiKey) {
10582
+ throw new errors.AlgoliaSearchError('Please provide an API key. ' + usage);
10583
+ }
10584
+
10585
+ this.applicationID = applicationID;
10586
+ this.apiKey = apiKey;
10587
+
10588
+ var defaultHosts = [
10589
+ this.applicationID + '-1.algolianet.com',
10590
+ this.applicationID + '-2.algolianet.com',
10591
+ this.applicationID + '-3.algolianet.com'
10592
+ ];
10593
+ this.hosts = {
10594
+ read: [],
10595
+ write: []
10596
+ };
10597
+
10598
+ this.hostIndex = {
10599
+ read: 0,
10600
+ write: 0
10601
+ };
10602
+
10603
+ opts = opts || {};
10604
+
10605
+ var protocol = opts.protocol || 'https:';
10606
+ var timeout = opts.timeout === undefined ? 2000 : opts.timeout;
10607
+
10608
+ // while we advocate for colon-at-the-end values: 'http:' for `opts.protocol`
10609
+ // we also accept `http` and `https`. It's a common error.
10610
+ if (!/:$/.test(protocol)) {
10611
+ protocol = protocol + ':';
10612
+ }
10613
+
10614
+ if (opts.protocol !== 'http:' && opts.protocol !== 'https:') {
10615
+ throw new errors.AlgoliaSearchError('protocol must be `http:` or `https:` (was `' + opts.protocol + '`)');
10616
+ }
10617
+
10618
+ // no hosts given, add defaults
10619
+ if (!opts.hosts) {
10620
+ this.hosts.read = [this.applicationID + '-dsn.algolia.net'].concat(defaultHosts);
10621
+ this.hosts.write = [this.applicationID + '.algolia.net'].concat(defaultHosts);
10622
+ } else if (isArray(opts.hosts)) {
10623
+ this.hosts.read = clone(opts.hosts);
10624
+ this.hosts.write = clone(opts.hosts);
10625
+ } else {
10626
+ this.hosts.read = clone(opts.hosts.read);
10627
+ this.hosts.write = clone(opts.hosts.write);
10628
+ }
10629
+
10630
+ // add protocol and lowercase hosts
10631
+ this.hosts.read = map(this.hosts.read, prepareHost(protocol));
10632
+ this.hosts.write = map(this.hosts.write, prepareHost(protocol));
10633
+ this.requestTimeout = timeout;
10634
+
10635
+ this.extraHeaders = [];
10636
+ this.cache = {};
10637
+
10638
+ this._ua = opts._ua;
10639
+ this._useCache = opts._useCache === undefined ? true : opts._useCache;
10640
+
10641
+ this._setTimeout = opts._setTimeout;
10642
+
10643
+ debug('init done, %j', this);
10644
+ }
10645
+
10646
+ AlgoliaSearch.prototype = {
10647
+ /*
10648
+ * Delete an index
10649
+ *
10650
+ * @param indexName the name of index to delete
10651
+ * @param callback the result callback called with two arguments
10652
+ * error: null or Error('message')
10653
+ * content: the server answer that contains the task ID
10654
+ */
10655
+ deleteIndex: function(indexName, callback) {
10656
+ return this._jsonRequest({
10657
+ method: 'DELETE',
10658
+ url: '/1/indexes/' + encodeURIComponent(indexName),
10659
+ hostType: 'write',
10660
+ callback: callback
10661
+ });
10662
+ },
10663
+ /**
10664
+ * Move an existing index.
10665
+ * @param srcIndexName the name of index to copy.
10666
+ * @param dstIndexName the new index name that will contains a copy of
10667
+ * srcIndexName (destination will be overriten if it already exist).
10668
+ * @param callback the result callback called with two arguments
10669
+ * error: null or Error('message')
10670
+ * content: the server answer that contains the task ID
10671
+ */
10672
+ moveIndex: function(srcIndexName, dstIndexName, callback) {
10673
+ var postObj = {
10674
+ operation: 'move', destination: dstIndexName
10675
+ };
10676
+ return this._jsonRequest({
10677
+ method: 'POST',
10678
+ url: '/1/indexes/' + encodeURIComponent(srcIndexName) + '/operation',
10679
+ body: postObj,
10680
+ hostType: 'write',
10681
+ callback: callback
10682
+ });
10683
+ },
10684
+ /**
10685
+ * Copy an existing index.
10686
+ * @param srcIndexName the name of index to copy.
10687
+ * @param dstIndexName the new index name that will contains a copy
10688
+ * of srcIndexName (destination will be overriten if it already exist).
10689
+ * @param callback the result callback called with two arguments
10690
+ * error: null or Error('message')
10691
+ * content: the server answer that contains the task ID
10692
+ */
10693
+ copyIndex: function(srcIndexName, dstIndexName, callback) {
10694
+ var postObj = {
10695
+ operation: 'copy', destination: dstIndexName
10696
+ };
10697
+ return this._jsonRequest({
10698
+ method: 'POST',
10699
+ url: '/1/indexes/' + encodeURIComponent(srcIndexName) + '/operation',
10700
+ body: postObj,
10701
+ hostType: 'write',
10702
+ callback: callback
10703
+ });
10704
+ },
10705
+ /**
10706
+ * Return last log entries.
10707
+ * @param offset Specify the first entry to retrieve (0-based, 0 is the most recent log entry).
10708
+ * @param length Specify the maximum number of entries to retrieve starting
10709
+ * at offset. Maximum allowed value: 1000.
10710
+ * @param callback the result callback called with two arguments
10711
+ * error: null or Error('message')
10712
+ * content: the server answer that contains the task ID
10713
+ */
10714
+ getLogs: function(offset, length, callback) {
10715
+ if (arguments.length === 0 || typeof offset === 'function') {
10716
+ // getLogs([cb])
10717
+ callback = offset;
10718
+ offset = 0;
10719
+ length = 10;
10720
+ } else if (arguments.length === 1 || typeof length === 'function') {
10721
+ // getLogs(1, [cb)]
10722
+ callback = length;
10723
+ length = 10;
10724
+ }
10725
+
10726
+ return this._jsonRequest({
10727
+ method: 'GET',
10728
+ url: '/1/logs?offset=' + offset + '&length=' + length,
10729
+ hostType: 'read',
10730
+ callback: callback
10731
+ });
10732
+ },
10733
+ /*
10734
+ * List all existing indexes (paginated)
10735
+ *
10736
+ * @param page The page to retrieve, starting at 0.
10737
+ * @param callback the result callback called with two arguments
10738
+ * error: null or Error('message')
10739
+ * content: the server answer with index list
10740
+ */
10741
+ listIndexes: function(page, callback) {
10742
+ var params = '';
10743
+
10744
+ if (page === undefined || typeof page === 'function') {
10745
+ callback = page;
10746
+ } else {
10747
+ params = '?page=' + page;
10748
+ }
10749
+
10750
+ return this._jsonRequest({
10751
+ method: 'GET',
10752
+ url: '/1/indexes' + params,
10753
+ hostType: 'read',
10754
+ callback: callback
10755
+ });
10756
+ },
10757
+
10758
+ /*
10759
+ * Get the index object initialized
10760
+ *
10761
+ * @param indexName the name of index
10762
+ * @param callback the result callback with one argument (the Index instance)
10763
+ */
10764
+ initIndex: function(indexName) {
10765
+ return new this.Index(this, indexName);
10766
+ },
10767
+ /*
10768
+ * List all existing user keys with their associated ACLs
10769
+ *
10770
+ * @param callback the result callback called with two arguments
10771
+ * error: null or Error('message')
10772
+ * content: the server answer with user keys list
10773
+ */
10774
+ listUserKeys: function(callback) {
10775
+ return this._jsonRequest({
10776
+ method: 'GET',
10777
+ url: '/1/keys',
10778
+ hostType: 'read',
10779
+ callback: callback
10780
+ });
10781
+ },
10782
+ /*
10783
+ * Get ACL of a user key
10784
+ *
10785
+ * @param key
10786
+ * @param callback the result callback called with two arguments
10787
+ * error: null or Error('message')
10788
+ * content: the server answer with user keys list
10789
+ */
10790
+ getUserKeyACL: function(key, callback) {
10791
+ return this._jsonRequest({
10792
+ method: 'GET',
10793
+ url: '/1/keys/' + key,
10794
+ hostType: 'read',
10795
+ callback: callback
10796
+ });
10797
+ },
10798
+ /*
10799
+ * Delete an existing user key
10800
+ * @param key
10801
+ * @param callback the result callback called with two arguments
10802
+ * error: null or Error('message')
10803
+ * content: the server answer with user keys list
10804
+ */
10805
+ deleteUserKey: function(key, callback) {
10806
+ return this._jsonRequest({
10807
+ method: 'DELETE',
10808
+ url: '/1/keys/' + key,
10809
+ hostType: 'write',
10810
+ callback: callback
10811
+ });
10812
+ },
10813
+ /*
10814
+ * Add a new global API key
10815
+ *
10816
+ * @param {string[]} acls - The list of ACL for this key. Defined by an array of strings that
10817
+ * can contains the following values:
10818
+ * - search: allow to search (https and http)
10819
+ * - addObject: allows to add/update an object in the index (https only)
10820
+ * - deleteObject : allows to delete an existing object (https only)
10821
+ * - deleteIndex : allows to delete index content (https only)
10822
+ * - settings : allows to get index settings (https only)
10823
+ * - editSettings : allows to change index settings (https only)
10824
+ * @param {Object} [params] - Optionnal parameters to set for the key
10825
+ * @param {number} params.validity - Number of seconds after which the key will be automatically removed (0 means no time limit for this key)
10826
+ * @param {number} params.maxQueriesPerIPPerHour - Number of API calls allowed from an IP address per hour
10827
+ * @param {number} params.maxHitsPerQuery - Number of hits this API key can retrieve in one call
10828
+ * @param {string[]} params.indexes - Allowed targeted indexes for this key
10829
+ * @param {string} params.description - A description for your key
10830
+ * @param {string[]} params.referers - A list of authorized referers
10831
+ * @param {Object} params.queryParameters - Force the key to use specific query parameters
10832
+ * @param {Function} callback - The result callback called with two arguments
10833
+ * error: null or Error('message')
10834
+ * content: the server answer with user keys list
10835
+ * @return {Promise|undefined} Returns a promise if no callback given
10836
+ * @example
10837
+ * client.addUserKey(['search'], {
10838
+ * validity: 300,
10839
+ * maxQueriesPerIPPerHour: 2000,
10840
+ * maxHitsPerQuery: 3,
10841
+ * indexes: ['fruits'],
10842
+ * description: 'Eat three fruits',
10843
+ * referers: ['*.algolia.com'],
10844
+ * queryParameters: {
10845
+ * tagFilters: ['public'],
10846
+ * }
10847
+ * })
10848
+ * @see {@link https://www.algolia.com/doc/rest_api#AddKey|Algolia REST API Documentation}
10849
+ */
10850
+ addUserKey: function(acls, params, callback) {
10851
+ if (arguments.length === 1 || typeof params === 'function') {
10852
+ callback = params;
10853
+ params = null;
10854
+ }
10855
+
10856
+ var postObj = {
10857
+ acl: acls
10858
+ };
10859
+
10860
+ if (params) {
10861
+ postObj.validity = params.validity;
10862
+ postObj.maxQueriesPerIPPerHour = params.maxQueriesPerIPPerHour;
10863
+ postObj.maxHitsPerQuery = params.maxHitsPerQuery;
10864
+ postObj.indexes = params.indexes;
10865
+ postObj.description = params.description;
10866
+
10867
+ if (params.queryParameters) {
10868
+ postObj.queryParameters = this._getSearchParams(params.queryParameters, '');
10869
+ }
10870
+
10871
+ postObj.referers = params.referers;
10872
+ }
10873
+
10874
+ return this._jsonRequest({
10875
+ method: 'POST',
10876
+ url: '/1/keys',
10877
+ body: postObj,
10878
+ hostType: 'write',
10879
+ callback: callback
10880
+ });
10881
+ },
10882
+ /**
10883
+ * Add a new global API key
10884
+ * @deprecated Please use client.addUserKey()
10885
+ */
10886
+ addUserKeyWithValidity: deprecate(function(acls, params, callback) {
10887
+ return this.addUserKey(acls, params, callback);
10888
+ }, deprecatedMessage('client.addUserKeyWithValidity()', 'client.addUserKey()')),
10889
+
10890
+ /**
10891
+ * Update an existing API key
10892
+ * @param {string} key - The key to update
10893
+ * @param {string[]} acls - The list of ACL for this key. Defined by an array of strings that
10894
+ * can contains the following values:
10895
+ * - search: allow to search (https and http)
10896
+ * - addObject: allows to add/update an object in the index (https only)
10897
+ * - deleteObject : allows to delete an existing object (https only)
10898
+ * - deleteIndex : allows to delete index content (https only)
10899
+ * - settings : allows to get index settings (https only)
10900
+ * - editSettings : allows to change index settings (https only)
10901
+ * @param {Object} [params] - Optionnal parameters to set for the key
10902
+ * @param {number} params.validity - Number of seconds after which the key will be automatically removed (0 means no time limit for this key)
10903
+ * @param {number} params.maxQueriesPerIPPerHour - Number of API calls allowed from an IP address per hour
10904
+ * @param {number} params.maxHitsPerQuery - Number of hits this API key can retrieve in one call
10905
+ * @param {string[]} params.indexes - Allowed targeted indexes for this key
10906
+ * @param {string} params.description - A description for your key
10907
+ * @param {string[]} params.referers - A list of authorized referers
10908
+ * @param {Object} params.queryParameters - Force the key to use specific query parameters
10909
+ * @param {Function} callback - The result callback called with two arguments
10910
+ * error: null or Error('message')
10911
+ * content: the server answer with user keys list
10912
+ * @return {Promise|undefined} Returns a promise if no callback given
10913
+ * @example
10914
+ * client.updateUserKey('APIKEY', ['search'], {
10915
+ * validity: 300,
10916
+ * maxQueriesPerIPPerHour: 2000,
10917
+ * maxHitsPerQuery: 3,
10918
+ * indexes: ['fruits'],
10919
+ * description: 'Eat three fruits',
10920
+ * referers: ['*.algolia.com'],
10921
+ * queryParameters: {
10922
+ * tagFilters: ['public'],
10923
+ * }
10924
+ * })
10925
+ * @see {@link https://www.algolia.com/doc/rest_api#UpdateIndexKey|Algolia REST API Documentation}
10926
+ */
10927
+ updateUserKey: function(key, acls, params, callback) {
10928
+ if (arguments.length === 2 || typeof params === 'function') {
10929
+ callback = params;
10930
+ params = null;
10931
+ }
10932
+
10933
+ var putObj = {
10934
+ acl: acls
10935
+ };
10936
+
10937
+ if (params) {
10938
+ putObj.validity = params.validity;
10939
+ putObj.maxQueriesPerIPPerHour = params.maxQueriesPerIPPerHour;
10940
+ putObj.maxHitsPerQuery = params.maxHitsPerQuery;
10941
+ putObj.indexes = params.indexes;
10942
+ putObj.description = params.description;
10943
+
10944
+ if (params.queryParameters) {
10945
+ putObj.queryParameters = this._getSearchParams(params.queryParameters, '');
10946
+ }
10947
+
10948
+ putObj.referers = params.referers;
10949
+ }
10950
+
10951
+ return this._jsonRequest({
10952
+ method: 'PUT',
10953
+ url: '/1/keys/' + key,
10954
+ body: putObj,
10955
+ hostType: 'write',
10956
+ callback: callback
10957
+ });
10958
+ },
10959
+
10960
+ /**
10961
+ * Set the extra security tagFilters header
10962
+ * @param {string|array} tags The list of tags defining the current security filters
10963
+ */
10964
+ setSecurityTags: function(tags) {
10965
+ if (Object.prototype.toString.call(tags) === '[object Array]') {
10966
+ var strTags = [];
10967
+ for (var i = 0; i < tags.length; ++i) {
10968
+ if (Object.prototype.toString.call(tags[i]) === '[object Array]') {
10969
+ var oredTags = [];
10970
+ for (var j = 0; j < tags[i].length; ++j) {
10971
+ oredTags.push(tags[i][j]);
10972
+ }
10973
+ strTags.push('(' + oredTags.join(',') + ')');
10974
+ } else {
10975
+ strTags.push(tags[i]);
10976
+ }
10977
+ }
10978
+ tags = strTags.join(',');
10979
+ }
10980
+
10981
+ this.securityTags = tags;
10982
+ },
10983
+
10984
+ /**
10985
+ * Set the extra user token header
10986
+ * @param {string} userToken The token identifying a uniq user (used to apply rate limits)
10987
+ */
10988
+ setUserToken: function(userToken) {
10989
+ this.userToken = userToken;
10990
+ },
10991
+
10992
+ /**
10993
+ * Initialize a new batch of search queries
10994
+ * @deprecated use client.search()
10995
+ */
10996
+ startQueriesBatch: deprecate(function startQueriesBatchDeprecated() {
10997
+ this._batch = [];
10998
+ }, deprecatedMessage('client.startQueriesBatch()', 'client.search()')),
10999
+
11000
+ /**
11001
+ * Add a search query in the batch
11002
+ * @deprecated use client.search()
11003
+ */
11004
+ addQueryInBatch: deprecate(function addQueryInBatchDeprecated(indexName, query, args) {
11005
+ this._batch.push({
11006
+ indexName: indexName,
11007
+ query: query,
11008
+ params: args
11009
+ });
11010
+ }, deprecatedMessage('client.addQueryInBatch()', 'client.search()')),
11011
+
11012
+ /**
11013
+ * Clear all queries in client's cache
11014
+ * @return undefined
11015
+ */
11016
+ clearCache: function() {
11017
+ this.cache = {};
11018
+ },
11019
+
11020
+ /**
11021
+ * Launch the batch of queries using XMLHttpRequest.
11022
+ * @deprecated use client.search()
11023
+ */
11024
+ sendQueriesBatch: deprecate(function sendQueriesBatchDeprecated(callback) {
11025
+ return this.search(this._batch, callback);
11026
+ }, deprecatedMessage('client.sendQueriesBatch()', 'client.search()')),
11027
+
11028
+ /**
11029
+ * Set the number of milliseconds a request can take before automatically being terminated.
11030
+ *
11031
+ * @param {Number} milliseconds
11032
+ */
11033
+ setRequestTimeout: function(milliseconds) {
11034
+ if (milliseconds) {
11035
+ this.requestTimeout = parseInt(milliseconds, 10);
11036
+ }
11037
+ },
11038
+
11039
+ /**
11040
+ * Search through multiple indices at the same time
11041
+ * @param {Object[]} queries An array of queries you want to run.
11042
+ * @param {string} queries[].indexName The index name you want to target
11043
+ * @param {string} [queries[].query] The query to issue on this index. Can also be passed into `params`
11044
+ * @param {Object} queries[].params Any search param like hitsPerPage, ..
11045
+ * @param {Function} callback Callback to be called
11046
+ * @return {Promise|undefined} Returns a promise if no callback given
11047
+ */
11048
+ search: function(queries, callback) {
11049
+ var client = this;
11050
+
11051
+ var postObj = {
11052
+ requests: map(queries, function prepareRequest(query) {
11053
+ var params = '';
11054
+
11055
+ // allow query.query
11056
+ // so we are mimicing the index.search(query, params) method
11057
+ // {indexName:, query:, params:}
11058
+ if (query.query !== undefined) {
11059
+ params += 'query=' + encodeURIComponent(query.query);
11060
+ }
11061
+
11062
+ return {
11063
+ indexName: query.indexName,
11064
+ params: client._getSearchParams(query.params, params)
11065
+ };
11066
+ })
11067
+ };
11068
+
11069
+ return this._jsonRequest({
11070
+ cache: this.cache,
11071
+ method: 'POST',
11072
+ url: '/1/indexes/*/queries',
11073
+ body: postObj,
11074
+ hostType: 'read',
11075
+ callback: callback
11076
+ });
11077
+ },
11078
+
11079
+ /**
11080
+ * Perform write operations accross multiple indexes.
11081
+ *
11082
+ * To reduce the amount of time spent on network round trips,
11083
+ * you can create, update, or delete several objects in one call,
11084
+ * using the batch endpoint (all operations are done in the given order).
11085
+ *
11086
+ * Available actions:
11087
+ * - addObject
11088
+ * - updateObject
11089
+ * - partialUpdateObject
11090
+ * - partialUpdateObjectNoCreate
11091
+ * - deleteObject
11092
+ *
11093
+ * https://www.algolia.com/doc/rest_api#Indexes
11094
+ * @param {Object[]} operations An array of operations to perform
11095
+ * @return {Promise|undefined} Returns a promise if no callback given
11096
+ * @example
11097
+ * client.batch([{
11098
+ * action: 'addObject',
11099
+ * indexName: 'clients',
11100
+ * body: {
11101
+ * name: 'Bill'
11102
+ * }
11103
+ * }, {
11104
+ * action: 'udpateObject',
11105
+ * indexName: 'fruits',
11106
+ * body: {
11107
+ * objectID: '29138',
11108
+ * name: 'banana'
11109
+ * }
11110
+ * }], cb)
11111
+ */
11112
+ batch: function(operations, callback) {
11113
+ return this._jsonRequest({
11114
+ method: 'POST',
11115
+ url: '/1/indexes/*/batch',
11116
+ body: {
11117
+ requests: operations
11118
+ },
11119
+ hostType: 'write',
11120
+ callback: callback
11121
+ });
11122
+ },
11123
+
11124
+ // environment specific methods
11125
+ destroy: notImplemented,
11126
+ enableRateLimitForward: notImplemented,
11127
+ disableRateLimitForward: notImplemented,
11128
+ useSecuredAPIKey: notImplemented,
11129
+ disableSecuredAPIKey: notImplemented,
11130
+ generateSecuredApiKey: notImplemented,
11131
+ /*
11132
+ * Index class constructor.
11133
+ * You should not use this method directly but use initIndex() function
11134
+ */
11135
+ Index: function(algoliasearch, indexName) {
11136
+ this.indexName = indexName;
11137
+ this.as = algoliasearch;
11138
+ this.typeAheadArgs = null;
11139
+ this.typeAheadValueOption = null;
11140
+
11141
+ // make sure every index instance has it's own cache
11142
+ this.cache = {};
11143
+ },
11144
+ /**
11145
+ * Add an extra field to the HTTP request
11146
+ *
11147
+ * @param name the header field name
11148
+ * @param value the header field value
11149
+ */
11150
+ setExtraHeader: function(name, value) {
11151
+ this.extraHeaders.push({
11152
+ name: name.toLowerCase(), value: value
11153
+ });
11154
+ },
11155
+
11156
+ _sendQueriesBatch: function(params, callback) {
11157
+ function prepareParams() {
11158
+ var reqParams = '';
11159
+ for (var i = 0; i < params.requests.length; ++i) {
11160
+ var q = '/1/indexes/' +
11161
+ encodeURIComponent(params.requests[i].indexName) +
11162
+ '?' + params.requests[i].params;
11163
+ reqParams += i + '=' + encodeURIComponent(q) + '&';
11164
+ }
11165
+ return reqParams;
11166
+ }
11167
+
11168
+ return this._jsonRequest({
11169
+ cache: this.cache,
11170
+ method: 'POST',
11171
+ url: '/1/indexes/*/queries',
11172
+ body: params,
11173
+ hostType: 'read',
11174
+ fallback: {
11175
+ method: 'GET',
11176
+ url: '/1/indexes/*',
11177
+ body: {
11178
+ params: prepareParams()
11179
+ }
11180
+ },
11181
+ callback: callback
11182
+ });
11183
+ },
11184
+ /*
11185
+ * Wrapper that try all hosts to maximize the quality of service
11186
+ */
11187
+ _jsonRequest: function(opts) {
11188
+ var requestDebug = require('debug')('algoliasearch:' + opts.url);
11189
+
11190
+ var body;
11191
+ var cache = opts.cache;
11192
+ var client = this;
11193
+ var tries = 0;
11194
+ var usingFallback = false;
11195
+
11196
+ if (opts.body !== undefined) {
11197
+ body = safeJSONStringify(opts.body);
11198
+ }
11199
+
11200
+ requestDebug('request start');
11201
+
11202
+ function doRequest(requester, reqOpts) {
11203
+ var cacheID;
11204
+
11205
+ if (client._useCache) {
11206
+ cacheID = opts.url;
11207
+ }
11208
+
11209
+ // as we sometime use POST requests to pass parameters (like query='aa'),
11210
+ // the cacheID must also include the body to be different between calls
11211
+ if (client._useCache && body) {
11212
+ cacheID += '_body_' + reqOpts.body;
11213
+ }
11214
+
11215
+ // handle cache existence
11216
+ if (client._useCache && cache && cache[cacheID] !== undefined) {
11217
+ requestDebug('serving response from cache');
11218
+ return client._promise.resolve(JSON.parse(safeJSONStringify(cache[cacheID])));
11219
+ }
11220
+
11221
+ // if we reached max tries
11222
+ if (tries >= client.hosts[opts.hostType].length ||
11223
+ // or we need to switch to fallback
11224
+ client.useFallback && !usingFallback) {
11225
+ // and there's no fallback or we are already using a fallback
11226
+ if (!opts.fallback || !client._request.fallback || usingFallback) {
11227
+ requestDebug('could not get any response');
11228
+ // then stop
11229
+ return client._promise.reject(new errors.AlgoliaSearchError(
11230
+ 'Cannot connect to the AlgoliaSearch API.' +
11231
+ ' Send an email to support@algolia.com to report and resolve the issue.' +
11232
+ ' Application id was: ' + client.applicationID
11233
+ ));
11234
+ }
11235
+
11236
+ requestDebug('switching to fallback');
11237
+
11238
+ // let's try the fallback starting from here
11239
+ tries = 0;
11240
+
11241
+ // method, url and body are fallback dependent
11242
+ reqOpts.method = opts.fallback.method;
11243
+ reqOpts.url = opts.fallback.url;
11244
+ reqOpts.jsonBody = opts.fallback.body;
11245
+ if (reqOpts.jsonBody) {
11246
+ reqOpts.body = safeJSONStringify(reqOpts.jsonBody);
11247
+ }
11248
+
11249
+ reqOpts.timeout = client.requestTimeout * (tries + 1);
11250
+ client.hostIndex[opts.hostType] = 0;
11251
+ usingFallback = true; // the current request is now using fallback
11252
+ return doRequest(client._request.fallback, reqOpts);
11253
+ }
11254
+
11255
+ var url = client.hosts[opts.hostType][client.hostIndex[opts.hostType]] + reqOpts.url;
11256
+ var options = {
11257
+ body: body,
11258
+ jsonBody: opts.body,
11259
+ method: reqOpts.method,
11260
+ headers: client._computeRequestHeaders(),
11261
+ timeout: reqOpts.timeout,
11262
+ debug: requestDebug
11263
+ };
11264
+
11265
+ requestDebug('method: %s, url: %s, headers: %j, timeout: %d',
11266
+ options.method, url, options.headers, options.timeout);
11267
+
11268
+ if (requester === client._request.fallback) {
11269
+ requestDebug('using fallback');
11270
+ }
11271
+
11272
+ // `requester` is any of this._request or this._request.fallback
11273
+ // thus it needs to be called using the client as context
11274
+ return requester.call(client, url, options).then(success, tryFallback);
11275
+
11276
+ function success(httpResponse) {
11277
+ // compute the status of the response,
11278
+ //
11279
+ // When in browser mode, using XDR or JSONP, we have no statusCode available
11280
+ // So we rely on our API response `status` property.
11281
+ // But `waitTask` can set a `status` property which is not the statusCode (it's the task status)
11282
+ // So we check if there's a `message` along `status` and it means it's an error
11283
+ //
11284
+ // That's the only case where we have a response.status that's not the http statusCode
11285
+ var status = httpResponse && httpResponse.body && httpResponse.body.message && httpResponse.body.status ||
11286
+
11287
+ // this is important to check the request statusCode AFTER the body eventual
11288
+ // statusCode because some implementations (jQuery XDomainRequest transport) may
11289
+ // send statusCode 200 while we had an error
11290
+ httpResponse.statusCode ||
11291
+
11292
+ // When in browser mode, using XDR or JSONP
11293
+ // we default to success when no error (no response.status && response.message)
11294
+ // If there was a JSON.parse() error then body is null and it fails
11295
+ httpResponse && httpResponse.body && 200;
11296
+
11297
+ requestDebug('received response: statusCode: %s, computed statusCode: %d, headers: %j',
11298
+ httpResponse.statusCode, status, httpResponse.headers);
11299
+
11300
+ if (process.env.DEBUG && process.env.DEBUG.indexOf('debugBody') !== -1) {
11301
+ requestDebug('body: %j', httpResponse.body);
11302
+ }
11303
+
11304
+ var ok = status === 200 || status === 201;
11305
+ var retry = !ok && Math.floor(status / 100) !== 4 && Math.floor(status / 100) !== 1;
11306
+
11307
+ if (client._useCache && ok && cache) {
11308
+ cache[cacheID] = httpResponse.body;
11309
+ }
11310
+
11311
+ if (ok) {
11312
+ return httpResponse.body;
11313
+ }
11314
+
11315
+ if (retry) {
11316
+ tries += 1;
11317
+ return retryRequest();
11318
+ }
11319
+
11320
+ var unrecoverableError = new errors.AlgoliaSearchError(
11321
+ httpResponse.body && httpResponse.body.message
11322
+ );
11323
+
11324
+ return client._promise.reject(unrecoverableError);
11325
+ }
11326
+
11327
+ function tryFallback(err) {
11328
+ // error cases:
11329
+ // While not in fallback mode:
11330
+ // - CORS not supported
11331
+ // - network error
11332
+ // While in fallback mode:
11333
+ // - timeout
11334
+ // - network error
11335
+ // - badly formatted JSONP (script loaded, did not call our callback)
11336
+ // In both cases:
11337
+ // - uncaught exception occurs (TypeError)
11338
+ requestDebug('error: %s, stack: %s', err.message, err.stack);
11339
+
11340
+ if (!(err instanceof errors.AlgoliaSearchError)) {
11341
+ err = new errors.Unknown(err && err.message, err);
11342
+ }
11343
+
11344
+ tries += 1;
11345
+
11346
+ // stop the request implementation when:
11347
+ if (
11348
+ // we did not generate this error,
11349
+ // it comes from a throw in some other piece of code
11350
+ err instanceof errors.Unknown ||
11351
+
11352
+ // server sent unparsable JSON
11353
+ err instanceof errors.UnparsableJSON ||
11354
+
11355
+ // no fallback and a network error occured (No CORS, bad APPID)
11356
+ !requester.fallback && err instanceof errors.Network ||
11357
+
11358
+ // max tries and already using fallback or no fallback
11359
+ tries >= client.hosts[opts.hostType].length &&
11360
+ (usingFallback || !opts.fallback || !client._request.fallback)) {
11361
+ // stop request implementation for this command
11362
+ return client._promise.reject(err);
11363
+ }
11364
+
11365
+ client.hostIndex[opts.hostType] = ++client.hostIndex[opts.hostType] % client.hosts[opts.hostType].length;
11366
+
11367
+ if (err instanceof errors.RequestTimeout) {
11368
+ return retryRequest();
11369
+ } else if (client._request.fallback && !client.useFallback) {
11370
+ // if any error occured but timeout, use fallback for the rest
11371
+ // of the session
11372
+ client.useFallback = true;
11373
+ }
11374
+
11375
+ return doRequest(requester, reqOpts);
11376
+ }
11377
+
11378
+ function retryRequest() {
11379
+ client.hostIndex[opts.hostType] = ++client.hostIndex[opts.hostType] % client.hosts[opts.hostType].length;
11380
+ reqOpts.timeout = client.requestTimeout * (tries + 1);
11381
+ return doRequest(requester, reqOpts);
11382
+ }
11383
+ }
11384
+
11385
+ // we can use a fallback if forced AND fallback parameters are available
11386
+ var useFallback = client.useFallback && opts.fallback;
11387
+ var requestOptions = useFallback ? opts.fallback : opts;
11388
+
11389
+ var promise = doRequest(
11390
+ // set the requester
11391
+ useFallback ? client._request.fallback : client._request, {
11392
+ url: requestOptions.url,
11393
+ method: requestOptions.method,
11394
+ body: body,
11395
+ jsonBody: opts.body,
11396
+ timeout: client.requestTimeout * (tries + 1)
11397
+ }
11398
+ );
11399
+
11400
+ // either we have a callback
11401
+ // either we are using promises
11402
+ if (opts.callback) {
11403
+ promise.then(function okCb(content) {
11404
+ exitPromise(function() {
11405
+ opts.callback(null, content);
11406
+ }, client._setTimeout || setTimeout);
11407
+ }, function nookCb(err) {
11408
+ exitPromise(function() {
11409
+ opts.callback(err);
11410
+ }, client._setTimeout || setTimeout);
11411
+ });
11412
+ } else {
11413
+ return promise;
11414
+ }
11415
+ },
11416
+
11417
+ /*
11418
+ * Transform search param object in query string
11419
+ */
11420
+ _getSearchParams: function(args, params) {
11421
+ if (this._isUndefined(args) || args === null) {
11422
+ return params;
11423
+ }
11424
+ for (var key in args) {
11425
+ if (key !== null && args[key] !== undefined && args.hasOwnProperty(key)) {
11426
+ params += params === '' ? '' : '&';
11427
+ params += key + '=' + encodeURIComponent(Object.prototype.toString.call(args[key]) === '[object Array]' ? safeJSONStringify(args[key]) : args[key]);
11428
+ }
11429
+ }
11430
+ return params;
11431
+ },
11432
+
11433
+ _isUndefined: function(obj) {
11434
+ return obj === void 0;
11435
+ },
11436
+
11437
+ _computeRequestHeaders: function() {
11438
+ var forEach = require('lodash-compat/collection/forEach');
11439
+
11440
+ var requestHeaders = {
11441
+ 'x-algolia-api-key': this.apiKey,
11442
+ 'x-algolia-application-id': this.applicationID,
11443
+ 'x-algolia-agent': this._ua
11444
+ };
11445
+
11446
+ if (this.userToken) {
11447
+ requestHeaders['x-algolia-usertoken'] = this.userToken;
11448
+ }
11449
+
11450
+ if (this.securityTags) {
11451
+ requestHeaders['x-algolia-tagfilters'] = this.securityTags;
11452
+ }
11453
+
11454
+ if (this.extraHeaders) {
11455
+ forEach(this.extraHeaders, function addToRequestHeaders(header) {
11456
+ requestHeaders[header.name] = header.value;
11457
+ });
11458
+ }
11459
+
11460
+ return requestHeaders;
11461
+ }
11462
+ };
11463
+
11464
+ /*
11465
+ * Contains all the functions related to one index
11466
+ * You should use AlgoliaSearch.initIndex(indexName) to retrieve this object
11467
+ */
11468
+ AlgoliaSearch.prototype.Index.prototype = {
11469
+ /*
11470
+ * Clear all queries in cache
11471
+ */
11472
+ clearCache: function() {
11473
+ this.cache = {};
11474
+ },
11475
+ /*
11476
+ * Add an object in this index
11477
+ *
11478
+ * @param content contains the javascript object to add inside the index
11479
+ * @param objectID (optional) an objectID you want to attribute to this object
11480
+ * (if the attribute already exist the old object will be overwrite)
11481
+ * @param callback (optional) the result callback called with two arguments:
11482
+ * error: null or Error('message')
11483
+ * content: the server answer that contains 3 elements: createAt, taskId and objectID
11484
+ */
11485
+ addObject: function(content, objectID, callback) {
11486
+ var indexObj = this;
11487
+
11488
+ if (arguments.length === 1 || typeof objectID === 'function') {
11489
+ callback = objectID;
11490
+ objectID = undefined;
11491
+ }
11492
+
11493
+ return this.as._jsonRequest({
11494
+ method: objectID !== undefined ?
11495
+ 'PUT' : // update or create
11496
+ 'POST', // create (API generates an objectID)
11497
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + // create
11498
+ (objectID !== undefined ? '/' + encodeURIComponent(objectID) : ''), // update or create
11499
+ body: content,
11500
+ hostType: 'write',
11501
+ callback: callback
11502
+ });
11503
+ },
11504
+ /*
11505
+ * Add several objects
11506
+ *
11507
+ * @param objects contains an array of objects to add
11508
+ * @param callback (optional) the result callback called with two arguments:
11509
+ * error: null or Error('message')
11510
+ * content: the server answer that updateAt and taskID
11511
+ */
11512
+ addObjects: function(objects, callback) {
11513
+ var indexObj = this;
11514
+ var postObj = {
11515
+ requests: []
11516
+ };
11517
+ for (var i = 0; i < objects.length; ++i) {
11518
+ var request = {
11519
+ action: 'addObject',
11520
+ body: objects[i]
11521
+ };
11522
+ postObj.requests.push(request);
11523
+ }
11524
+ return this.as._jsonRequest({
11525
+ method: 'POST',
11526
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/batch',
11527
+ body: postObj,
11528
+ hostType: 'write',
11529
+ callback: callback
11530
+ });
11531
+ },
11532
+ /*
11533
+ * Get an object from this index
11534
+ *
11535
+ * @param objectID the unique identifier of the object to retrieve
11536
+ * @param attrs (optional) if set, contains the array of attribute names to retrieve
11537
+ * @param callback (optional) the result callback called with two arguments
11538
+ * error: null or Error('message')
11539
+ * content: the object to retrieve or the error message if a failure occured
11540
+ */
11541
+ getObject: function(objectID, attrs, callback) {
11542
+ var indexObj = this;
11543
+
11544
+ if (arguments.length === 1 || typeof attrs === 'function') {
11545
+ callback = attrs;
11546
+ attrs = undefined;
11547
+ }
11548
+
11549
+ var params = '';
11550
+ if (attrs !== undefined) {
11551
+ params = '?attributes=';
11552
+ for (var i = 0; i < attrs.length; ++i) {
11553
+ if (i !== 0) {
11554
+ params += ',';
11555
+ }
11556
+ params += attrs[i];
11557
+ }
11558
+ }
11559
+
11560
+ return this.as._jsonRequest({
11561
+ method: 'GET',
11562
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/' + encodeURIComponent(objectID) + params,
11563
+ hostType: 'read',
11564
+ callback: callback
11565
+ });
11566
+ },
11567
+
11568
+ /*
11569
+ * Get several objects from this index
11570
+ *
11571
+ * @param objectIDs the array of unique identifier of objects to retrieve
11572
+ */
11573
+ getObjects: function(objectIDs, attributesToRetrieve, callback) {
11574
+ var indexObj = this;
11575
+
11576
+ if (arguments.length === 1 || typeof attributesToRetrieve === 'function') {
11577
+ callback = attributesToRetrieve;
11578
+ attributesToRetrieve = undefined;
11579
+ }
11580
+
11581
+ var body = {
11582
+ requests: map(objectIDs, function prepareRequest(objectID) {
11583
+ var request = {
11584
+ 'indexName': indexObj.indexName,
11585
+ 'objectID': objectID
11586
+ };
11587
+
11588
+ if (attributesToRetrieve) {
11589
+ request.attributesToRetrieve = attributesToRetrieve.join(',');
11590
+ }
11591
+
11592
+ return request;
11593
+ })
11594
+ };
11595
+
11596
+ return this.as._jsonRequest({
11597
+ method: 'POST',
11598
+ url: '/1/indexes/*/objects',
11599
+ hostType: 'read',
11600
+ body: body,
11601
+ callback: callback
11602
+ });
11603
+ },
11604
+
11605
+ /*
11606
+ * Update partially an object (only update attributes passed in argument)
11607
+ *
11608
+ * @param partialObject contains the javascript attributes to override, the
11609
+ * object must contains an objectID attribute
11610
+ * @param callback (optional) the result callback called with two arguments:
11611
+ * error: null or Error('message')
11612
+ * content: the server answer that contains 3 elements: createAt, taskId and objectID
11613
+ */
11614
+ partialUpdateObject: function(partialObject, callback) {
11615
+ var indexObj = this;
11616
+ return this.as._jsonRequest({
11617
+ method: 'POST',
11618
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/' + encodeURIComponent(partialObject.objectID) + '/partial',
11619
+ body: partialObject,
11620
+ hostType: 'write',
11621
+ callback: callback
11622
+ });
11623
+ },
11624
+ /*
11625
+ * Partially Override the content of several objects
11626
+ *
11627
+ * @param objects contains an array of objects to update (each object must contains a objectID attribute)
11628
+ * @param callback (optional) the result callback called with two arguments:
11629
+ * error: null or Error('message')
11630
+ * content: the server answer that updateAt and taskID
11631
+ */
11632
+ partialUpdateObjects: function(objects, callback) {
11633
+ var indexObj = this;
11634
+ var postObj = {
11635
+ requests: []
11636
+ };
11637
+ for (var i = 0; i < objects.length; ++i) {
11638
+ var request = {
11639
+ action: 'partialUpdateObject',
11640
+ objectID: objects[i].objectID,
11641
+ body: objects[i]
11642
+ };
11643
+ postObj.requests.push(request);
11644
+ }
11645
+ return this.as._jsonRequest({
11646
+ method: 'POST',
11647
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/batch',
11648
+ body: postObj,
11649
+ hostType: 'write',
11650
+ callback: callback
11651
+ });
11652
+ },
11653
+ /*
11654
+ * Override the content of object
11655
+ *
11656
+ * @param object contains the javascript object to save, the object must contains an objectID attribute
11657
+ * @param callback (optional) the result callback called with two arguments:
11658
+ * error: null or Error('message')
11659
+ * content: the server answer that updateAt and taskID
11660
+ */
11661
+ saveObject: function(object, callback) {
11662
+ var indexObj = this;
11663
+ return this.as._jsonRequest({
11664
+ method: 'PUT',
11665
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/' + encodeURIComponent(object.objectID),
11666
+ body: object,
11667
+ hostType: 'write',
11668
+ callback: callback
11669
+ });
11670
+ },
11671
+ /*
11672
+ * Override the content of several objects
11673
+ *
11674
+ * @param objects contains an array of objects to update (each object must contains a objectID attribute)
11675
+ * @param callback (optional) the result callback called with two arguments:
11676
+ * error: null or Error('message')
11677
+ * content: the server answer that updateAt and taskID
11678
+ */
11679
+ saveObjects: function(objects, callback) {
11680
+ var indexObj = this;
11681
+ var postObj = {
11682
+ requests: []
11683
+ };
11684
+ for (var i = 0; i < objects.length; ++i) {
11685
+ var request = {
11686
+ action: 'updateObject',
11687
+ objectID: objects[i].objectID,
11688
+ body: objects[i]
11689
+ };
11690
+ postObj.requests.push(request);
11691
+ }
11692
+ return this.as._jsonRequest({
11693
+ method: 'POST',
11694
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/batch',
11695
+ body: postObj,
11696
+ hostType: 'write',
11697
+ callback: callback
11698
+ });
11699
+ },
11700
+ /*
11701
+ * Delete an object from the index
11702
+ *
11703
+ * @param objectID the unique identifier of object to delete
11704
+ * @param callback (optional) the result callback called with two arguments:
11705
+ * error: null or Error('message')
11706
+ * content: the server answer that contains 3 elements: createAt, taskId and objectID
11707
+ */
11708
+ deleteObject: function(objectID, callback) {
11709
+ if (typeof objectID === 'function' || typeof objectID !== 'string' && typeof objectID !== 'number') {
11710
+ var err = new errors.AlgoliaSearchError('Cannot delete an object without an objectID');
11711
+ callback = objectID;
11712
+ if (typeof callback === 'function') {
11713
+ return callback(err);
11714
+ }
11715
+
11716
+ return this.as._promise.reject(err);
11717
+ }
11718
+
11719
+ var indexObj = this;
11720
+ return this.as._jsonRequest({
11721
+ method: 'DELETE',
11722
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/' + encodeURIComponent(objectID),
11723
+ hostType: 'write',
11724
+ callback: callback
11725
+ });
11726
+ },
11727
+ /*
11728
+ * Delete several objects from an index
11729
+ *
11730
+ * @param objectIDs contains an array of objectID to delete
11731
+ * @param callback (optional) the result callback called with two arguments:
11732
+ * error: null or Error('message')
11733
+ * content: the server answer that contains 3 elements: createAt, taskId and objectID
11734
+ */
11735
+ deleteObjects: function(objectIDs, callback) {
11736
+ var indexObj = this;
11737
+ var postObj = {
11738
+ requests: map(objectIDs, function prepareRequest(objectID) {
11739
+ return {
11740
+ action: 'deleteObject',
11741
+ objectID: objectID,
11742
+ body: {
11743
+ objectID: objectID
11744
+ }
11745
+ };
11746
+ })
11747
+ };
11748
+
11749
+ return this.as._jsonRequest({
11750
+ method: 'POST',
11751
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/batch',
11752
+ body: postObj,
11753
+ hostType: 'write',
11754
+ callback: callback
11755
+ });
11756
+ },
11757
+ /*
11758
+ * Delete all objects matching a query
11759
+ *
11760
+ * @param query the query string
11761
+ * @param params the optional query parameters
11762
+ * @param callback (optional) the result callback called with one argument
11763
+ * error: null or Error('message')
11764
+ */
11765
+ deleteByQuery: function(query, params, callback) {
11766
+ var indexObj = this;
11767
+ var client = indexObj.as;
11768
+
11769
+ if (arguments.length === 1 || typeof params === 'function') {
11770
+ callback = params;
11771
+ params = {};
11772
+ }
11773
+
11774
+ params.attributesToRetrieve = 'objectID';
11775
+ params.hitsPerPage = 1000;
11776
+
11777
+ // when deleting, we should never use cache to get the
11778
+ // search results
11779
+ this.clearCache();
11780
+
11781
+ // there's a problem in how we use the promise chain,
11782
+ // see how waitTask is done
11783
+ var promise = this
11784
+ .search(query, params)
11785
+ .then(stopOrDelete);
11786
+
11787
+ function stopOrDelete(searchContent) {
11788
+ // stop here
11789
+ if (searchContent.nbHits === 0) {
11790
+ // return indexObj.as._request.resolve();
11791
+ return searchContent;
11792
+ }
11793
+
11794
+ // continue and do a recursive call
11795
+ var objectIDs = map(searchContent.hits, function getObjectID(object) {
11796
+ return object.objectID;
11797
+ });
11798
+
11799
+ return indexObj
11800
+ .deleteObjects(objectIDs)
11801
+ .then(waitTask)
11802
+ .then(doDeleteByQuery);
11803
+ }
11804
+
11805
+ function waitTask(deleteObjectsContent) {
11806
+ return indexObj.waitTask(deleteObjectsContent.taskID);
11807
+ }
11808
+
11809
+ function doDeleteByQuery() {
11810
+ return indexObj.deleteByQuery(query, params);
11811
+ }
11812
+
11813
+ if (!callback) {
11814
+ return promise;
11815
+ }
11816
+
11817
+ promise.then(success, failure);
11818
+
11819
+ function success() {
11820
+ exitPromise(function exit() {
11821
+ callback(null);
11822
+ }, client._setTimeout || setTimeout);
11823
+ }
11824
+
11825
+ function failure(err) {
11826
+ exitPromise(function exit() {
11827
+ callback(err);
11828
+ }, client._setTimeout || setTimeout);
11829
+ }
11830
+ },
11831
+ /*
11832
+ * Search inside the index using XMLHttpRequest request (Using a POST query to
11833
+ * minimize number of OPTIONS queries: Cross-Origin Resource Sharing).
11834
+ *
11835
+ * @param query the full text query
11836
+ * @param args (optional) if set, contains an object with query parameters:
11837
+ * - page: (integer) Pagination parameter used to select the page to retrieve.
11838
+ * Page is zero-based and defaults to 0. Thus,
11839
+ * to retrieve the 10th page you need to set page=9
11840
+ * - hitsPerPage: (integer) Pagination parameter used to select the number of hits per page. Defaults to 20.
11841
+ * - attributesToRetrieve: a string that contains the list of object attributes
11842
+ * you want to retrieve (let you minimize the answer size).
11843
+ * Attributes are separated with a comma (for example "name,address").
11844
+ * You can also use an array (for example ["name","address"]).
11845
+ * By default, all attributes are retrieved. You can also use '*' to retrieve all
11846
+ * values when an attributesToRetrieve setting is specified for your index.
11847
+ * - attributesToHighlight: a string that contains the list of attributes you
11848
+ * want to highlight according to the query.
11849
+ * Attributes are separated by a comma. You can also use an array (for example ["name","address"]).
11850
+ * If an attribute has no match for the query, the raw value is returned.
11851
+ * By default all indexed text attributes are highlighted.
11852
+ * You can use `*` if you want to highlight all textual attributes.
11853
+ * Numerical attributes are not highlighted.
11854
+ * A matchLevel is returned for each highlighted attribute and can contain:
11855
+ * - full: if all the query terms were found in the attribute,
11856
+ * - partial: if only some of the query terms were found,
11857
+ * - none: if none of the query terms were found.
11858
+ * - attributesToSnippet: a string that contains the list of attributes to snippet alongside
11859
+ * the number of words to return (syntax is `attributeName:nbWords`).
11860
+ * Attributes are separated by a comma (Example: attributesToSnippet=name:10,content:10).
11861
+ * You can also use an array (Example: attributesToSnippet: ['name:10','content:10']).
11862
+ * By default no snippet is computed.
11863
+ * - minWordSizefor1Typo: the minimum number of characters in a query word to accept one typo in this word.
11864
+ *D efaults to 3.
11865
+ * - minWordSizefor2Typos: the minimum number of characters in a query word
11866
+ * to accept two typos in this word. Defaults to 7.
11867
+ * - getRankingInfo: if set to 1, the result hits will contain ranking
11868
+ * information in _rankingInfo attribute.
11869
+ * - aroundLatLng: search for entries around a given
11870
+ * latitude/longitude (specified as two floats separated by a comma).
11871
+ * For example aroundLatLng=47.316669,5.016670).
11872
+ * You can specify the maximum distance in meters with the aroundRadius parameter (in meters)
11873
+ * and the precision for ranking with aroundPrecision
11874
+ * (for example if you set aroundPrecision=100, two objects that are distant of
11875
+ * less than 100m will be considered as identical for "geo" ranking parameter).
11876
+ * At indexing, you should specify geoloc of an object with the _geoloc attribute
11877
+ * (in the form {"_geoloc":{"lat":48.853409, "lng":2.348800}})
11878
+ * - insideBoundingBox: search entries inside a given area defined by the two extreme points
11879
+ * of a rectangle (defined by 4 floats: p1Lat,p1Lng,p2Lat,p2Lng).
11880
+ * For example insideBoundingBox=47.3165,4.9665,47.3424,5.0201).
11881
+ * At indexing, you should specify geoloc of an object with the _geoloc attribute
11882
+ * (in the form {"_geoloc":{"lat":48.853409, "lng":2.348800}})
11883
+ * - numericFilters: a string that contains the list of numeric filters you want to
11884
+ * apply separated by a comma.
11885
+ * The syntax of one filter is `attributeName` followed by `operand` followed by `value`.
11886
+ * Supported operands are `<`, `<=`, `=`, `>` and `>=`.
11887
+ * You can have multiple conditions on one attribute like for example numericFilters=price>100,price<1000.
11888
+ * You can also use an array (for example numericFilters: ["price>100","price<1000"]).
11889
+ * - tagFilters: filter the query by a set of tags. You can AND tags by separating them by commas.
11890
+ * To OR tags, you must add parentheses. For example, tags=tag1,(tag2,tag3) means tag1 AND (tag2 OR tag3).
11891
+ * You can also use an array, for example tagFilters: ["tag1",["tag2","tag3"]]
11892
+ * means tag1 AND (tag2 OR tag3).
11893
+ * At indexing, tags should be added in the _tags** attribute
11894
+ * of objects (for example {"_tags":["tag1","tag2"]}).
11895
+ * - facetFilters: filter the query by a list of facets.
11896
+ * Facets are separated by commas and each facet is encoded as `attributeName:value`.
11897
+ * For example: `facetFilters=category:Book,author:John%20Doe`.
11898
+ * You can also use an array (for example `["category:Book","author:John%20Doe"]`).
11899
+ * - facets: List of object attributes that you want to use for faceting.
11900
+ * Comma separated list: `"category,author"` or array `['category','author']`
11901
+ * Only attributes that have been added in **attributesForFaceting** index setting
11902
+ * can be used in this parameter.
11903
+ * You can also use `*` to perform faceting on all attributes specified in **attributesForFaceting**.
11904
+ * - queryType: select how the query words are interpreted, it can be one of the following value:
11905
+ * - prefixAll: all query words are interpreted as prefixes,
11906
+ * - prefixLast: only the last word is interpreted as a prefix (default behavior),
11907
+ * - prefixNone: no query word is interpreted as a prefix. This option is not recommended.
11908
+ * - optionalWords: a string that contains the list of words that should
11909
+ * be considered as optional when found in the query.
11910
+ * Comma separated and array are accepted.
11911
+ * - distinct: If set to 1, enable the distinct feature (disabled by default)
11912
+ * if the attributeForDistinct index setting is set.
11913
+ * This feature is similar to the SQL "distinct" keyword: when enabled
11914
+ * in a query with the distinct=1 parameter,
11915
+ * all hits containing a duplicate value for the attributeForDistinct attribute are removed from results.
11916
+ * For example, if the chosen attribute is show_name and several hits have
11917
+ * the same value for show_name, then only the best
11918
+ * one is kept and others are removed.
11919
+ * - restrictSearchableAttributes: List of attributes you want to use for
11920
+ * textual search (must be a subset of the attributesToIndex index setting)
11921
+ * either comma separated or as an array
11922
+ * @param callback the result callback called with two arguments:
11923
+ * error: null or Error('message'). If false, the content contains the error.
11924
+ * content: the server answer that contains the list of results.
11925
+ */
11926
+ search: function(query, args, callback) {
11927
+ // warn V2 users on how to search
11928
+ if (typeof query === 'function' && typeof args === 'object' ||
11929
+ typeof callback === 'object') {
11930
+ // .search(query, params, cb)
11931
+ // .search(cb, params)
11932
+ throw new errors.AlgoliaSearchError('index.search usage is index.search(query, params, cb)');
11933
+ }
11934
+
11935
+ if (arguments.length === 0 || typeof query === 'function') {
11936
+ // .search(), .search(cb)
11937
+ callback = query;
11938
+ query = '';
11939
+ } else if (arguments.length === 1 || typeof args === 'function') {
11940
+ // .search(query/args), .search(query, cb)
11941
+ callback = args;
11942
+ args = undefined;
11943
+ }
11944
+
11945
+ // .search(args), careful: typeof null === 'object'
11946
+ if (typeof query === 'object' && query !== null) {
11947
+ args = query;
11948
+ query = undefined;
11949
+ } else if (query === undefined || query === null) { // .search(undefined/null)
11950
+ query = '';
11951
+ }
11952
+
11953
+ var params = '';
11954
+
11955
+ if (query !== undefined) {
11956
+ params += 'query=' + encodeURIComponent(query);
11957
+ }
11958
+
11959
+ if (args !== undefined) {
11960
+ // `_getSearchParams` will augment params, do not be fooled by the = versus += from previous if
11961
+ params = this.as._getSearchParams(args, params);
11962
+ }
11963
+
11964
+ return this._search(params, callback);
11965
+ },
11966
+
11967
+ /*
11968
+ * Browse index content. The response content will have a `cursor` property that you can use
11969
+ * to browse subsequent pages for this query. Use `index.browseNext(cursor)` when you want.
11970
+ *
11971
+ * @param {string} query - The full text query
11972
+ * @param {Object} [queryParameters] - Any search query parameter
11973
+ * @param {Function} [callback] - The result callback called with two arguments
11974
+ * error: null or Error('message')
11975
+ * content: the server answer with the browse result
11976
+ * @return {Promise|undefined} Returns a promise if no callback given
11977
+ * @example
11978
+ * index.browse('cool songs', {
11979
+ * tagFilters: 'public,comments',
11980
+ * hitsPerPage: 500
11981
+ * }, callback);
11982
+ * @see {@link https://www.algolia.com/doc/rest_api#Browse|Algolia REST API Documentation}
11983
+ */
11984
+ // pre 3.5.0 usage, backward compatible
11985
+ // browse: function(page, hitsPerPage, callback) {
11986
+ browse: function(query, queryParameters, callback) {
11987
+ var merge = require('lodash-compat/object/merge');
11988
+
11989
+ var indexObj = this;
11990
+
11991
+ var page;
11992
+ var hitsPerPage;
11993
+
11994
+ // we check variadic calls that are not the one defined
11995
+ // .browse()/.browse(fn)
11996
+ // => page = 0
11997
+ if (arguments.length === 0 || arguments.length === 1 && typeof arguments[0] === 'function') {
11998
+ page = 0;
11999
+ callback = arguments[0];
12000
+ query = undefined;
12001
+ } else if (typeof arguments[0] === 'number') {
12002
+ // .browse(2)/.browse(2, 10)/.browse(2, fn)/.browse(2, 10, fn)
12003
+ page = arguments[0];
12004
+ if (typeof arguments[1] === 'number') {
12005
+ hitsPerPage = arguments[1];
12006
+ } else if (typeof arguments[1] === 'function') {
12007
+ callback = arguments[1];
12008
+ hitsPerPage = undefined;
12009
+ }
12010
+ query = undefined;
12011
+ queryParameters = undefined;
12012
+ } else if (typeof arguments[0] === 'object') {
12013
+ // .browse(queryParameters)/.browse(queryParameters, cb)
12014
+ if (typeof arguments[1] === 'function') {
12015
+ callback = arguments[1];
12016
+ }
12017
+ queryParameters = arguments[0];
12018
+ query = undefined;
12019
+ } else if (typeof arguments[0] === 'string' && typeof arguments[1] === 'function') {
12020
+ // .browse(query, cb)
12021
+ callback = arguments[1];
12022
+ queryParameters = undefined;
12023
+ }
12024
+
12025
+ // otherwise it's a .browse(query)/.browse(query, queryParameters)/.browse(query, queryParameters, cb)
12026
+
12027
+ // get search query parameters combining various possible calls
12028
+ // to .browse();
12029
+ queryParameters = merge({}, queryParameters || {}, {
12030
+ page: page,
12031
+ hitsPerPage: hitsPerPage,
12032
+ query: query
12033
+ });
12034
+
12035
+ var params = this.as._getSearchParams(queryParameters, '');
12036
+
12037
+ return this.as._jsonRequest({
12038
+ method: 'GET',
12039
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/browse?' + params,
12040
+ hostType: 'read',
12041
+ callback: callback
12042
+ });
12043
+ },
12044
+
12045
+ /*
12046
+ * Continue browsing from a previous position (cursor), obtained via a call to `.browse()`.
12047
+ *
12048
+ * @param {string} query - The full text query
12049
+ * @param {Object} [queryParameters] - Any search query parameter
12050
+ * @param {Function} [callback] - The result callback called with two arguments
12051
+ * error: null or Error('message')
12052
+ * content: the server answer with the browse result
12053
+ * @return {Promise|undefined} Returns a promise if no callback given
12054
+ * @example
12055
+ * index.browseFrom('14lkfsakl32', callback);
12056
+ * @see {@link https://www.algolia.com/doc/rest_api#Browse|Algolia REST API Documentation}
12057
+ */
12058
+ browseFrom: function(cursor, callback) {
12059
+ return this.as._jsonRequest({
12060
+ method: 'GET',
12061
+ url: '/1/indexes/' + encodeURIComponent(this.indexName) + '/browse?cursor=' + cursor,
12062
+ hostType: 'read',
12063
+ callback: callback
12064
+ });
12065
+ },
12066
+
12067
+ /*
12068
+ * Browse all content from an index using events. Basically this will do
12069
+ * .browse() -> .browseFrom -> .browseFrom -> .. until all the results are returned
12070
+ *
12071
+ * @param {string} query - The full text query
12072
+ * @param {Object} [queryParameters] - Any search query parameter
12073
+ * @return {EventEmitter}
12074
+ * @example
12075
+ * var browser = index.browseAll('cool songs', {
12076
+ * tagFilters: 'public,comments',
12077
+ * hitsPerPage: 500
12078
+ * });
12079
+ *
12080
+ * browser.on('result', function resultCallback(content) {
12081
+ * console.log(content.hits);
12082
+ * });
12083
+ *
12084
+ * // if any error occurs, you get it
12085
+ * browser.on('error', function(err) {
12086
+ * throw err;
12087
+ * });
12088
+ *
12089
+ * // when you have browsed the whole index, you get this event
12090
+ * browser.on('end', function() {
12091
+ * console.log('finished');
12092
+ * });
12093
+ *
12094
+ * // at any point if you want to stop the browsing process, you can stop it manually
12095
+ * // otherwise it will go on and on
12096
+ * browser.stop();
12097
+ *
12098
+ * @see {@link https://www.algolia.com/doc/rest_api#Browse|Algolia REST API Documentation}
12099
+ */
12100
+ browseAll: function(query, queryParameters) {
12101
+ if (typeof query === 'object') {
12102
+ queryParameters = query;
12103
+ query = undefined;
12104
+ }
12105
+
12106
+ var merge = require('lodash-compat/object/merge');
12107
+
12108
+ var IndexBrowser = require('./IndexBrowser');
12109
+
12110
+ var browser = new IndexBrowser();
12111
+ var client = this.as;
12112
+ var index = this;
12113
+ var params = client._getSearchParams(
12114
+ merge({}, queryParameters || {}, {
12115
+ query: query
12116
+ }), ''
12117
+ );
12118
+
12119
+ // start browsing
12120
+ browseLoop();
12121
+
12122
+ function browseLoop(cursor) {
12123
+ if (browser._stopped) {
12124
+ return;
12125
+ }
12126
+
12127
+ var queryString;
12128
+
12129
+ if (cursor !== undefined) {
12130
+ queryString = 'cursor=' + encodeURIComponent(cursor);
12131
+ } else {
12132
+ queryString = params;
12133
+ }
12134
+
12135
+ client._jsonRequest({
12136
+ method: 'GET',
12137
+ url: '/1/indexes/' + encodeURIComponent(index.indexName) + '/browse?' + queryString,
12138
+ hostType: 'read',
12139
+ callback: browseCallback
12140
+ });
12141
+ }
12142
+
12143
+ function browseCallback(err, content) {
12144
+ if (browser._stopped) {
12145
+ return;
12146
+ }
12147
+
12148
+ if (err) {
12149
+ browser._error(err);
12150
+ return;
12151
+ }
12152
+
12153
+ browser._result(content);
12154
+
12155
+ // no cursor means we are finished browsing
12156
+ if (content.cursor === undefined) {
12157
+ browser._end();
12158
+ return;
12159
+ }
12160
+
12161
+ browseLoop(content.cursor);
12162
+ }
12163
+
12164
+ return browser;
12165
+ },
12166
+
12167
+ /*
12168
+ * Get a Typeahead.js adapter
12169
+ * @param searchParams contains an object with query parameters (see search for details)
12170
+ */
12171
+ ttAdapter: function(params) {
12172
+ var self = this;
12173
+ return function ttAdapter(query, syncCb, asyncCb) {
12174
+ var cb;
12175
+
12176
+ if (typeof asyncCb === 'function') {
12177
+ // typeahead 0.11
12178
+ cb = asyncCb;
12179
+ } else {
12180
+ // pre typeahead 0.11
12181
+ cb = syncCb;
12182
+ }
12183
+
12184
+ self.search(query, params, function searchDone(err, content) {
12185
+ if (err) {
12186
+ cb(err);
12187
+ return;
12188
+ }
12189
+
12190
+ cb(content.hits);
12191
+ });
12192
+ };
12193
+ },
12194
+
12195
+ /*
12196
+ * Wait the publication of a task on the server.
12197
+ * All server task are asynchronous and you can check with this method that the task is published.
12198
+ *
12199
+ * @param taskID the id of the task returned by server
12200
+ * @param callback the result callback with with two arguments:
12201
+ * error: null or Error('message')
12202
+ * content: the server answer that contains the list of results
12203
+ */
12204
+ waitTask: function(taskID, callback) {
12205
+ // wait minimum 100ms before retrying
12206
+ var baseDelay = 100;
12207
+ // wait maximum 5s before retrying
12208
+ var maxDelay = 5000;
12209
+ var loop = 0;
12210
+
12211
+ // waitTask() must be handled differently from other methods,
12212
+ // it's a recursive method using a timeout
12213
+ var indexObj = this;
12214
+ var client = indexObj.as;
12215
+
12216
+ var promise = retryLoop();
12217
+
12218
+ function retryLoop() {
12219
+ return client._jsonRequest({
12220
+ method: 'GET',
12221
+ hostType: 'read',
12222
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/task/' + taskID
12223
+ }).then(function success(content) {
12224
+ loop++;
12225
+ var delay = baseDelay * loop * loop;
12226
+ if (delay > maxDelay) {
12227
+ delay = maxDelay;
12228
+ }
12229
+
12230
+ if (content.status !== 'published') {
12231
+ return client._promise.delay(delay).then(retryLoop);
12232
+ }
12233
+
12234
+ return content;
12235
+ });
12236
+ }
12237
+
12238
+ if (!callback) {
12239
+ return promise;
12240
+ }
12241
+
12242
+ promise.then(successCb, failureCb);
12243
+
12244
+ function successCb(content) {
12245
+ exitPromise(function exit() {
12246
+ callback(null, content);
12247
+ }, client._setTimeout || setTimeout);
12248
+ }
12249
+
12250
+ function failureCb(err) {
12251
+ exitPromise(function exit() {
12252
+ callback(err);
12253
+ }, client._setTimeout || setTimeout);
12254
+ }
12255
+ },
12256
+
12257
+ /*
12258
+ * This function deletes the index content. Settings and index specific API keys are kept untouched.
12259
+ *
12260
+ * @param callback (optional) the result callback called with two arguments
12261
+ * error: null or Error('message')
12262
+ * content: the settings object or the error message if a failure occured
12263
+ */
12264
+ clearIndex: function(callback) {
12265
+ var indexObj = this;
12266
+ return this.as._jsonRequest({
12267
+ method: 'POST',
12268
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/clear',
12269
+ hostType: 'write',
12270
+ callback: callback
12271
+ });
12272
+ },
12273
+ /*
12274
+ * Get settings of this index
12275
+ *
12276
+ * @param callback (optional) the result callback called with two arguments
12277
+ * error: null or Error('message')
12278
+ * content: the settings object or the error message if a failure occured
12279
+ */
12280
+ getSettings: function(callback) {
12281
+ var indexObj = this;
12282
+ return this.as._jsonRequest({
12283
+ method: 'GET',
12284
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/settings',
12285
+ hostType: 'read',
12286
+ callback: callback
12287
+ });
12288
+ },
12289
+
12290
+ /*
12291
+ * Set settings for this index
12292
+ *
12293
+ * @param settigns the settings object that can contains :
12294
+ * - minWordSizefor1Typo: (integer) the minimum number of characters to accept one typo (default = 3).
12295
+ * - minWordSizefor2Typos: (integer) the minimum number of characters to accept two typos (default = 7).
12296
+ * - hitsPerPage: (integer) the number of hits per page (default = 10).
12297
+ * - attributesToRetrieve: (array of strings) default list of attributes to retrieve in objects.
12298
+ * If set to null, all attributes are retrieved.
12299
+ * - attributesToHighlight: (array of strings) default list of attributes to highlight.
12300
+ * If set to null, all indexed attributes are highlighted.
12301
+ * - attributesToSnippet**: (array of strings) default list of attributes to snippet alongside the number
12302
+ * of words to return (syntax is attributeName:nbWords).
12303
+ * By default no snippet is computed. If set to null, no snippet is computed.
12304
+ * - attributesToIndex: (array of strings) the list of fields you want to index.
12305
+ * If set to null, all textual and numerical attributes of your objects are indexed,
12306
+ * but you should update it to get optimal results.
12307
+ * This parameter has two important uses:
12308
+ * - Limit the attributes to index: For example if you store a binary image in base64,
12309
+ * you want to store it and be able to
12310
+ * retrieve it but you don't want to search in the base64 string.
12311
+ * - Control part of the ranking*: (see the ranking parameter for full explanation)
12312
+ * Matches in attributes at the beginning of
12313
+ * the list will be considered more important than matches in attributes further down the list.
12314
+ * In one attribute, matching text at the beginning of the attribute will be
12315
+ * considered more important than text after, you can disable
12316
+ * this behavior if you add your attribute inside `unordered(AttributeName)`,
12317
+ * for example attributesToIndex: ["title", "unordered(text)"].
12318
+ * - attributesForFaceting: (array of strings) The list of fields you want to use for faceting.
12319
+ * All strings in the attribute selected for faceting are extracted and added as a facet.
12320
+ * If set to null, no attribute is used for faceting.
12321
+ * - attributeForDistinct: (string) The attribute name used for the Distinct feature.
12322
+ * This feature is similar to the SQL "distinct" keyword: when enabled
12323
+ * in query with the distinct=1 parameter, all hits containing a duplicate
12324
+ * value for this attribute are removed from results.
12325
+ * For example, if the chosen attribute is show_name and several hits have
12326
+ * the same value for show_name, then only the best one is kept and others are removed.
12327
+ * - ranking: (array of strings) controls the way results are sorted.
12328
+ * We have six available criteria:
12329
+ * - typo: sort according to number of typos,
12330
+ * - geo: sort according to decreassing distance when performing a geo-location based search,
12331
+ * - proximity: sort according to the proximity of query words in hits,
12332
+ * - attribute: sort according to the order of attributes defined by attributesToIndex,
12333
+ * - exact:
12334
+ * - if the user query contains one word: sort objects having an attribute
12335
+ * that is exactly the query word before others.
12336
+ * For example if you search for the "V" TV show, you want to find it
12337
+ * with the "V" query and avoid to have all popular TV
12338
+ * show starting by the v letter before it.
12339
+ * - if the user query contains multiple words: sort according to the
12340
+ * number of words that matched exactly (and not as a prefix).
12341
+ * - custom: sort according to a user defined formula set in **customRanking** attribute.
12342
+ * The standard order is ["typo", "geo", "proximity", "attribute", "exact", "custom"]
12343
+ * - customRanking: (array of strings) lets you specify part of the ranking.
12344
+ * The syntax of this condition is an array of strings containing attributes
12345
+ * prefixed by asc (ascending order) or desc (descending order) operator.
12346
+ * For example `"customRanking" => ["desc(population)", "asc(name)"]`
12347
+ * - queryType: Select how the query words are interpreted, it can be one of the following value:
12348
+ * - prefixAll: all query words are interpreted as prefixes,
12349
+ * - prefixLast: only the last word is interpreted as a prefix (default behavior),
12350
+ * - prefixNone: no query word is interpreted as a prefix. This option is not recommended.
12351
+ * - highlightPreTag: (string) Specify the string that is inserted before
12352
+ * the highlighted parts in the query result (default to "<em>").
12353
+ * - highlightPostTag: (string) Specify the string that is inserted after
12354
+ * the highlighted parts in the query result (default to "</em>").
12355
+ * - optionalWords: (array of strings) Specify a list of words that should
12356
+ * be considered as optional when found in the query.
12357
+ * @param callback (optional) the result callback called with two arguments
12358
+ * error: null or Error('message')
12359
+ * content: the server answer or the error message if a failure occured
12360
+ */
12361
+ setSettings: function(settings, callback) {
12362
+ var indexObj = this;
12363
+ return this.as._jsonRequest({
12364
+ method: 'PUT',
12365
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/settings',
12366
+ hostType: 'write',
12367
+ body: settings,
12368
+ callback: callback
12369
+ });
12370
+ },
12371
+ /*
12372
+ * List all existing user keys associated to this index
12373
+ *
12374
+ * @param callback the result callback called with two arguments
12375
+ * error: null or Error('message')
12376
+ * content: the server answer with user keys list
12377
+ */
12378
+ listUserKeys: function(callback) {
12379
+ var indexObj = this;
12380
+ return this.as._jsonRequest({
12381
+ method: 'GET',
12382
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/keys',
12383
+ hostType: 'read',
12384
+ callback: callback
12385
+ });
12386
+ },
12387
+ /*
12388
+ * Get ACL of a user key associated to this index
12389
+ *
12390
+ * @param key
12391
+ * @param callback the result callback called with two arguments
12392
+ * error: null or Error('message')
12393
+ * content: the server answer with user keys list
12394
+ */
12395
+ getUserKeyACL: function(key, callback) {
12396
+ var indexObj = this;
12397
+ return this.as._jsonRequest({
12398
+ method: 'GET',
12399
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/keys/' + key,
12400
+ hostType: 'read',
12401
+ callback: callback
12402
+ });
12403
+ },
12404
+ /*
12405
+ * Delete an existing user key associated to this index
12406
+ *
12407
+ * @param key
12408
+ * @param callback the result callback called with two arguments
12409
+ * error: null or Error('message')
12410
+ * content: the server answer with user keys list
12411
+ */
12412
+ deleteUserKey: function(key, callback) {
12413
+ var indexObj = this;
12414
+ return this.as._jsonRequest({
12415
+ method: 'DELETE',
12416
+ url: '/1/indexes/' + encodeURIComponent(indexObj.indexName) + '/keys/' + key,
12417
+ hostType: 'write',
12418
+ callback: callback
12419
+ });
12420
+ },
12421
+ /*
12422
+ * Add a new API key to this index
12423
+ *
12424
+ * @param {string[]} acls - The list of ACL for this key. Defined by an array of strings that
12425
+ * can contains the following values:
12426
+ * - search: allow to search (https and http)
12427
+ * - addObject: allows to add/update an object in the index (https only)
12428
+ * - deleteObject : allows to delete an existing object (https only)
12429
+ * - deleteIndex : allows to delete index content (https only)
12430
+ * - settings : allows to get index settings (https only)
12431
+ * - editSettings : allows to change index settings (https only)
12432
+ * @param {Object} [params] - Optionnal parameters to set for the key
12433
+ * @param {number} params.validity - Number of seconds after which the key will
12434
+ * be automatically removed (0 means no time limit for this key)
12435
+ * @param {number} params.maxQueriesPerIPPerHour - Number of API calls allowed from an IP address per hour
12436
+ * @param {number} params.maxHitsPerQuery - Number of hits this API key can retrieve in one call
12437
+ * @param {string} params.description - A description for your key
12438
+ * @param {string[]} params.referers - A list of authorized referers
12439
+ * @param {Object} params.queryParameters - Force the key to use specific query parameters
12440
+ * @param {Function} callback - The result callback called with two arguments
12441
+ * error: null or Error('message')
12442
+ * content: the server answer with user keys list
12443
+ * @return {Promise|undefined} Returns a promise if no callback given
12444
+ * @example
12445
+ * index.addUserKey(['search'], {
12446
+ * validity: 300,
12447
+ * maxQueriesPerIPPerHour: 2000,
12448
+ * maxHitsPerQuery: 3,
12449
+ * description: 'Eat three fruits',
12450
+ * referers: ['*.algolia.com'],
12451
+ * queryParameters: {
12452
+ * tagFilters: ['public'],
12453
+ * }
12454
+ * })
12455
+ * @see {@link https://www.algolia.com/doc/rest_api#AddIndexKey|Algolia REST API Documentation}
12456
+ */
12457
+ addUserKey: function(acls, params, callback) {
12458
+ if (arguments.length === 1 || typeof params === 'function') {
12459
+ callback = params;
12460
+ params = null;
12461
+ }
12462
+
12463
+ var postObj = {
12464
+ acl: acls
12465
+ };
12466
+
12467
+ if (params) {
12468
+ postObj.validity = params.validity;
12469
+ postObj.maxQueriesPerIPPerHour = params.maxQueriesPerIPPerHour;
12470
+ postObj.maxHitsPerQuery = params.maxHitsPerQuery;
12471
+ postObj.description = params.description;
12472
+
12473
+ if (params.queryParameters) {
12474
+ postObj.queryParameters = this.as._getSearchParams(params.queryParameters, '');
12475
+ }
12476
+
12477
+ postObj.referers = params.referers;
12478
+ }
12479
+
12480
+ return this.as._jsonRequest({
12481
+ method: 'POST',
12482
+ url: '/1/indexes/' + encodeURIComponent(this.indexName) + '/keys',
12483
+ body: postObj,
12484
+ hostType: 'write',
12485
+ callback: callback
12486
+ });
12487
+ },
12488
+
12489
+ /**
12490
+ * Add an existing user key associated to this index
12491
+ * @deprecated use index.addUserKey()
12492
+ */
12493
+ addUserKeyWithValidity: deprecate(function deprecatedAddUserKeyWithValidity(acls, params, callback) {
12494
+ return this.addUserKey(acls, params, callback);
12495
+ }, deprecatedMessage('index.addUserKeyWithValidity()', 'index.addUserKey()')),
12496
+
12497
+ /**
12498
+ * Update an existing API key of this index
12499
+ * @param {string} key - The key to update
12500
+ * @param {string[]} acls - The list of ACL for this key. Defined by an array of strings that
12501
+ * can contains the following values:
12502
+ * - search: allow to search (https and http)
12503
+ * - addObject: allows to add/update an object in the index (https only)
12504
+ * - deleteObject : allows to delete an existing object (https only)
12505
+ * - deleteIndex : allows to delete index content (https only)
12506
+ * - settings : allows to get index settings (https only)
12507
+ * - editSettings : allows to change index settings (https only)
12508
+ * @param {Object} [params] - Optionnal parameters to set for the key
12509
+ * @param {number} params.validity - Number of seconds after which the key will
12510
+ * be automatically removed (0 means no time limit for this key)
12511
+ * @param {number} params.maxQueriesPerIPPerHour - Number of API calls allowed from an IP address per hour
12512
+ * @param {number} params.maxHitsPerQuery - Number of hits this API key can retrieve in one call
12513
+ * @param {string} params.description - A description for your key
12514
+ * @param {string[]} params.referers - A list of authorized referers
12515
+ * @param {Object} params.queryParameters - Force the key to use specific query parameters
12516
+ * @param {Function} callback - The result callback called with two arguments
12517
+ * error: null or Error('message')
12518
+ * content: the server answer with user keys list
12519
+ * @return {Promise|undefined} Returns a promise if no callback given
12520
+ * @example
12521
+ * index.updateUserKey('APIKEY', ['search'], {
12522
+ * validity: 300,
12523
+ * maxQueriesPerIPPerHour: 2000,
12524
+ * maxHitsPerQuery: 3,
12525
+ * description: 'Eat three fruits',
12526
+ * referers: ['*.algolia.com'],
12527
+ * queryParameters: {
12528
+ * tagFilters: ['public'],
12529
+ * }
12530
+ * })
12531
+ * @see {@link https://www.algolia.com/doc/rest_api#UpdateIndexKey|Algolia REST API Documentation}
12532
+ */
12533
+ updateUserKey: function(key, acls, params, callback) {
12534
+ if (arguments.length === 2 || typeof params === 'function') {
12535
+ callback = params;
12536
+ params = null;
12537
+ }
12538
+
12539
+ var putObj = {
12540
+ acl: acls
12541
+ };
12542
+
12543
+ if (params) {
12544
+ putObj.validity = params.validity;
12545
+ putObj.maxQueriesPerIPPerHour = params.maxQueriesPerIPPerHour;
12546
+ putObj.maxHitsPerQuery = params.maxHitsPerQuery;
12547
+ putObj.description = params.description;
12548
+
12549
+ if (params.queryParameters) {
12550
+ putObj.queryParameters = this.as._getSearchParams(params.queryParameters, '');
12551
+ }
12552
+
12553
+ putObj.referers = params.referers;
12554
+ }
12555
+
12556
+ return this.as._jsonRequest({
12557
+ method: 'PUT',
12558
+ url: '/1/indexes/' + encodeURIComponent(this.indexName) + '/keys/' + key,
12559
+ body: putObj,
12560
+ hostType: 'write',
12561
+ callback: callback
12562
+ });
12563
+ },
12564
+
12565
+ _search: function(params, callback) {
12566
+ return this.as._jsonRequest({
12567
+ cache: this.cache,
12568
+ method: 'POST',
12569
+ url: '/1/indexes/' + encodeURIComponent(this.indexName) + '/query',
12570
+ body: {params: params},
12571
+ hostType: 'read',
12572
+ fallback: {
12573
+ method: 'GET',
12574
+ url: '/1/indexes/' + encodeURIComponent(this.indexName),
12575
+ body: {params: params}
12576
+ },
12577
+ callback: callback
12578
+ });
12579
+ },
12580
+
12581
+ as: null,
12582
+ indexName: null,
12583
+ typeAheadArgs: null,
12584
+ typeAheadValueOption: null
12585
+ };
12586
+
12587
+ // extracted from https://github.com/component/map/blob/master/index.js
12588
+ // without the crazy toFunction thing
12589
+ function map(arr, fn) {
12590
+ var ret = [];
12591
+ for (var i = 0; i < arr.length; ++i) {
12592
+ ret.push(fn(arr[i], i));
12593
+ }
12594
+ return ret;
12595
+ }
12596
+
12597
+ function prepareHost(protocol) {
12598
+ return function prepare(host) {
12599
+ return protocol + '//' + host.toLowerCase();
12600
+ };
12601
+ }
12602
+
12603
+ function notImplemented() {
12604
+ var message = 'Not implemented in this environment.\n' +
12605
+ 'If you feel this is a mistake, write to support@algolia.com';
12606
+
12607
+ throw new errors.AlgoliaSearchError(message);
12608
+ }
12609
+
12610
+ function deprecatedMessage(previousUsage, newUsage) {
12611
+ var githubAnchorLink = previousUsage.toLowerCase()
12612
+ .replace('.', '')
12613
+ .replace('()', '');
12614
+
12615
+ return 'algoliasearch: `' + previousUsage + '` was replaced by `' + newUsage +
12616
+ '`. Please see https://github.com/algolia/algoliasearch-client-js/wiki/Deprecated#' + githubAnchorLink;
12617
+ }
12618
+
12619
+ // Parse cloud does not supports setTimeout
12620
+ // We do not store a setTimeout reference in the client everytime
12621
+ // We only fallback to a fake setTimeout when not available
12622
+ // setTimeout cannot be override globally sadly
12623
+ function exitPromise(fn, _setTimeout) {
12624
+ _setTimeout(fn, 0);
12625
+ }
12626
+
12627
+ function deprecate(fn, message) {
12628
+ var warned = false;
12629
+
12630
+ function deprecated() {
12631
+ if (!warned) {
12632
+ /* eslint no-console:0 */
12633
+ console.log(message);
12634
+ warned = true;
12635
+ }
12636
+
12637
+ return fn.apply(this, arguments);
12638
+ }
12639
+
12640
+ return deprecated;
12641
+ }
12642
+
12643
+ // Prototype.js < 1.7, a widely used library, defines a weird
12644
+ // Array.prototype.toJSON function that will fail to stringify our content
12645
+ // appropriately
12646
+ // refs:
12647
+ // - https://groups.google.com/forum/#!topic/prototype-core/E-SAVvV_V9Q
12648
+ // - https://github.com/sstephenson/prototype/commit/038a2985a70593c1a86c230fadbdfe2e4898a48c
12649
+ // - http://stackoverflow.com/a/3148441/147079
12650
+ function safeJSONStringify(obj) {
12651
+ /* eslint no-extend-native:0 */
12652
+
12653
+ if (Array.prototype.toJSON === undefined) {
12654
+ return JSON.stringify(obj);
12655
+ }
12656
+
12657
+ var toJSON = Array.prototype.toJSON;
12658
+ delete Array.prototype.toJSON;
12659
+ var out = JSON.stringify(obj);
12660
+ Array.prototype.toJSON = toJSON;
12661
+
12662
+ return out;
12663
+ }
12664
+
12665
+ }).call(this,require('_process'))
12666
+ },{"./IndexBrowser":212,"./errors":217,"_process":221,"debug":157,"lodash-compat/collection/forEach":162,"lodash-compat/lang/clone":195,"lodash-compat/lang/isArray":198,"lodash-compat/object/merge":208}],212:[function(require,module,exports){
12667
+ 'use strict';
12668
+
12669
+ // This is the object returned by the `index.browseAll()` method
12670
+
12671
+ module.exports = IndexBrowser;
12672
+
12673
+ var inherits = require('inherits');
12674
+ var EventEmitter = require('events').EventEmitter;
12675
+
12676
+ function IndexBrowser() {
12677
+ }
12678
+
12679
+ inherits(IndexBrowser, EventEmitter);
12680
+
12681
+ IndexBrowser.prototype.stop = function() {
12682
+ this._stopped = true;
12683
+ this._clean();
12684
+ };
12685
+
12686
+ IndexBrowser.prototype._end = function() {
12687
+ this.emit('end');
12688
+ this._clean();
12689
+ };
12690
+
12691
+ IndexBrowser.prototype._error = function(err) {
12692
+ this.emit('error', err);
12693
+ this._clean();
12694
+ };
12695
+
12696
+ IndexBrowser.prototype._result = function(content) {
12697
+ this.emit('result', content);
12698
+ };
12699
+
12700
+ IndexBrowser.prototype._clean = function() {
12701
+ this.removeAllListeners('stop');
12702
+ this.removeAllListeners('end');
12703
+ this.removeAllListeners('error');
12704
+ this.removeAllListeners('result');
12705
+ };
12706
+
12707
+ },{"events":219,"inherits":161}],213:[function(require,module,exports){
12708
+ 'use strict';
12709
+
12710
+ // This is the standalone browser build entry point
12711
+ // Browser implementation of the Algolia Search JavaScript client,
12712
+ // using XMLHttpRequest, XDomainRequest and JSONP as fallback
12713
+ module.exports = algoliasearch;
12714
+
12715
+ var inherits = require('inherits');
12716
+ var Promise = window.Promise || require('es6-promise').Promise;
12717
+
12718
+ var AlgoliaSearch = require('../../AlgoliaSearch');
12719
+ var errors = require('../../errors');
12720
+ var inlineHeaders = require('../inline-headers');
12721
+ var jsonpRequest = require('../jsonp-request');
12722
+
12723
+ function algoliasearch(applicationID, apiKey, opts) {
12724
+ var cloneDeep = require('lodash-compat/lang/cloneDeep');
12725
+
12726
+ var getDocumentProtocol = require('../get-document-protocol');
12727
+
12728
+ opts = cloneDeep(opts || {});
12729
+
12730
+ if (opts.protocol === undefined) {
12731
+ opts.protocol = getDocumentProtocol();
12732
+ }
12733
+
12734
+ opts._ua = opts._ua || algoliasearch.ua;
12735
+
12736
+ return new AlgoliaSearchBrowser(applicationID, apiKey, opts);
12737
+ }
12738
+
12739
+ algoliasearch.version = require('../../version.json');
12740
+ algoliasearch.ua = 'Algolia for vanilla JavaScript ' + algoliasearch.version;
12741
+
12742
+ // we expose into window no matter how we are used, this will allow
12743
+ // us to easily debug any website running algolia
12744
+ window.__algolia = {
12745
+ debug: require('debug'),
12746
+ algoliasearch: algoliasearch
12747
+ };
12748
+
12749
+ var support = {
12750
+ hasXMLHttpRequest: 'XMLHttpRequest' in window,
12751
+ hasXDomainRequest: 'XDomainRequest' in window,
12752
+ cors: 'withCredentials' in new XMLHttpRequest(),
12753
+ timeout: 'timeout' in new XMLHttpRequest()
12754
+ };
12755
+
12756
+ function AlgoliaSearchBrowser() {
12757
+ // call AlgoliaSearch constructor
12758
+ AlgoliaSearch.apply(this, arguments);
12759
+ }
12760
+
12761
+ inherits(AlgoliaSearchBrowser, AlgoliaSearch);
12762
+
12763
+ AlgoliaSearchBrowser.prototype._request = function request(url, opts) {
12764
+ return new Promise(function wrapRequest(resolve, reject) {
12765
+ // no cors or XDomainRequest, no request
12766
+ if (!support.cors && !support.hasXDomainRequest) {
12767
+ // very old browser, not supported
12768
+ reject(new errors.Network('CORS not supported'));
12769
+ return;
12770
+ }
12771
+
12772
+ url = inlineHeaders(url, opts.headers);
12773
+
12774
+ var body = opts.body;
12775
+ var req = support.cors ? new XMLHttpRequest() : new XDomainRequest();
12776
+ var ontimeout;
12777
+ var timedOut;
12778
+
12779
+ // do not rely on default XHR async flag, as some analytics code like hotjar
12780
+ // breaks it and set it to false by default
12781
+ if (req instanceof XMLHttpRequest) {
12782
+ req.open(opts.method, url, true);
12783
+ } else {
12784
+ req.open(opts.method, url);
12785
+ }
12786
+
12787
+ if (support.cors) {
12788
+ if (body) {
12789
+ if (opts.method === 'POST') {
12790
+ // https://developer.mozilla.org/en-US/docs/Web/HTTP/Access_control_CORS#Simple_requests
12791
+ req.setRequestHeader('content-type', 'application/x-www-form-urlencoded');
12792
+ } else {
12793
+ req.setRequestHeader('content-type', 'application/json');
12794
+ }
12795
+ }
12796
+ req.setRequestHeader('accept', 'application/json');
12797
+ }
12798
+
12799
+ // we set an empty onprogress listener
12800
+ // so that XDomainRequest on IE9 is not aborted
12801
+ // refs:
12802
+ // - https://github.com/algolia/algoliasearch-client-js/issues/76
12803
+ // - https://social.msdn.microsoft.com/Forums/ie/en-US/30ef3add-767c-4436-b8a9-f1ca19b4812e/ie9-rtm-xdomainrequest-issued-requests-may-abort-if-all-event-handlers-not-specified?forum=iewebdevelopment
12804
+ req.onprogress = function noop() {};
12805
+
12806
+ req.onload = load;
12807
+ req.onerror = error;
12808
+
12809
+ if (support.timeout) {
12810
+ // .timeout supported by both XHR and XDR,
12811
+ // we do receive timeout event, tested
12812
+ req.timeout = opts.timeout;
12813
+
12814
+ req.ontimeout = timeout;
12815
+ } else {
12816
+ ontimeout = setTimeout(timeout, opts.timeout);
12817
+ }
12818
+
12819
+ req.send(body);
12820
+
12821
+ // event object not received in IE8, at least
12822
+ // but we do not use it, still important to note
12823
+ function load(/*event*/) {
12824
+ // When browser does not supports req.timeout, we can
12825
+ // have both a load and timeout event, since handled by a dumb setTimeout
12826
+ if (timedOut) {
12827
+ return;
12828
+ }
12829
+
12830
+ if (!support.timeout) {
12831
+ clearTimeout(ontimeout);
12832
+ }
12833
+
12834
+ var out;
12835
+
12836
+ try {
12837
+ out = {
12838
+ body: JSON.parse(req.responseText),
12839
+ statusCode: req.status,
12840
+ // XDomainRequest does not have any response headers
12841
+ headers: req.getAllResponseHeaders && req.getAllResponseHeaders() || {}
12842
+ };
12843
+ } catch (e) {
12844
+ out = new errors.UnparsableJSON({
12845
+ more: req.responseText
12846
+ });
12847
+ }
12848
+
12849
+ if (out instanceof errors.UnparsableJSON) {
12850
+ reject(out);
12851
+ } else {
12852
+ resolve(out);
12853
+ }
12854
+ }
12855
+
12856
+ function error(event) {
12857
+ if (timedOut) {
12858
+ return;
12859
+ }
12860
+
12861
+ if (!support.timeout) {
12862
+ clearTimeout(ontimeout);
12863
+ }
12864
+
12865
+ // error event is trigerred both with XDR/XHR on:
12866
+ // - DNS error
12867
+ // - unallowed cross domain request
12868
+ reject(
12869
+ new errors.Network({
12870
+ more: event
12871
+ })
12872
+ );
12873
+ }
12874
+
12875
+ function timeout() {
12876
+ if (!support.timeout) {
12877
+ timedOut = true;
12878
+ req.abort();
12879
+ }
12880
+
12881
+ reject(new errors.RequestTimeout());
12882
+ }
12883
+ });
12884
+ };
12885
+
12886
+ AlgoliaSearchBrowser.prototype._request.fallback = function requestFallback(url, opts) {
12887
+ url = inlineHeaders(url, opts.headers);
12888
+
12889
+ return new Promise(function wrapJsonpRequest(resolve, reject) {
12890
+ jsonpRequest(url, opts, function jsonpRequestDone(err, content) {
12891
+ if (err) {
12892
+ reject(err);
12893
+ return;
12894
+ }
12895
+
12896
+ resolve(content);
12897
+ });
12898
+ });
12899
+ };
12900
+
12901
+ AlgoliaSearchBrowser.prototype._promise = {
12902
+ reject: function rejectPromise(val) {
12903
+ return Promise.reject(val);
12904
+ },
12905
+ resolve: function resolvePromise(val) {
12906
+ return Promise.resolve(val);
12907
+ },
12908
+ delay: function delayPromise(ms) {
12909
+ return new Promise(function resolveOnTimeout(resolve/*, reject*/) {
12910
+ setTimeout(resolve, ms);
12911
+ });
12912
+ }
12913
+ };
12914
+
12915
+ },{"../../AlgoliaSearch":211,"../../errors":217,"../../version.json":218,"../get-document-protocol":214,"../inline-headers":215,"../jsonp-request":216,"debug":157,"es6-promise":160,"inherits":161,"lodash-compat/lang/cloneDeep":196}],214:[function(require,module,exports){
12916
+ 'use strict';
12917
+
12918
+ module.exports = getDocumentProtocol;
12919
+
12920
+ function getDocumentProtocol() {
12921
+ var protocol = window.document.location.protocol;
12922
+
12923
+ // when in `file:` mode (local html file), default to `http:`
12924
+ if (protocol !== 'http:' && protocol !== 'https:') {
12925
+ protocol = 'http:';
12926
+ }
12927
+
12928
+ return protocol;
12929
+ }
12930
+
12931
+ },{}],215:[function(require,module,exports){
12932
+ 'use strict';
12933
+
12934
+ module.exports = inlineHeaders;
12935
+
12936
+ var querystring = require('querystring');
12937
+
12938
+ function inlineHeaders(url, headers) {
12939
+ if (/\?/.test(url)) {
12940
+ url += '&';
12941
+ } else {
12942
+ url += '?';
12943
+ }
12944
+
12945
+ return url + querystring.encode(headers);
12946
+ }
12947
+
12948
+ },{"querystring":224}],216:[function(require,module,exports){
12949
+ 'use strict';
12950
+
12951
+ module.exports = jsonpRequest;
12952
+
12953
+ var errors = require('../errors');
12954
+
12955
+ var JSONPCounter = 0;
12956
+
12957
+ function jsonpRequest(url, opts, cb) {
12958
+ if (opts.method !== 'GET') {
12959
+ cb(new Error('Method ' + opts.method + ' ' + url + ' is not supported by JSONP.'));
12960
+ return;
12961
+ }
12962
+
12963
+ opts.debug('JSONP: start');
12964
+
12965
+ var cbCalled = false;
12966
+ var timedOut = false;
12967
+
12968
+ JSONPCounter += 1;
12969
+ var head = document.getElementsByTagName('head')[0];
12970
+ var script = document.createElement('script');
12971
+ var cbName = 'algoliaJSONP_' + JSONPCounter;
12972
+ var done = false;
12973
+
12974
+ window[cbName] = function(data) {
12975
+ try {
12976
+ delete window[cbName];
12977
+ } catch (e) {
12978
+ window[cbName] = undefined;
12979
+ }
12980
+
12981
+ if (timedOut) {
12982
+ return;
12983
+ }
12984
+
12985
+ cbCalled = true;
12986
+
12987
+ clean();
12988
+
12989
+ cb(null, {
12990
+ body: data/*,
12991
+ // We do not send the statusCode, there's no statusCode in JSONP, it will be
12992
+ // computed using data.status && data.message like with XDR
12993
+ statusCode*/
12994
+ });
12995
+ };
12996
+
12997
+ // add callback by hand
12998
+ url += '&callback=' + cbName;
12999
+
13000
+ // add body params manually
13001
+ if (opts.jsonBody && opts.jsonBody.params) {
13002
+ url += '&' + opts.jsonBody.params;
13003
+ }
13004
+
13005
+ var ontimeout = setTimeout(timeout, opts.timeout);
13006
+
13007
+ // script onreadystatechange needed only for
13008
+ // <= IE8
13009
+ // https://github.com/angular/angular.js/issues/4523
13010
+ script.onreadystatechange = readystatechange;
13011
+ script.onload = success;
13012
+ script.onerror = error;
13013
+
13014
+ script.async = true;
13015
+ script.defer = true;
13016
+ script.src = url;
13017
+ head.appendChild(script);
13018
+
13019
+ function success() {
13020
+ opts.debug('JSONP: success');
13021
+
13022
+ if (done || timedOut) {
13023
+ return;
13024
+ }
13025
+
13026
+ done = true;
13027
+
13028
+ // script loaded but did not call the fn => script loading error
13029
+ if (!cbCalled) {
13030
+ opts.debug('JSONP: Fail. Script loaded but did not call the callback');
13031
+ clean();
13032
+ cb(new errors.JSONPScriptFail());
13033
+ }
13034
+ }
13035
+
13036
+ function readystatechange() {
13037
+ if (this.readyState === 'loaded' || this.readyState === 'complete') {
13038
+ success();
13039
+ }
13040
+ }
13041
+
13042
+ function clean() {
13043
+ clearTimeout(ontimeout);
13044
+ script.onload = null;
13045
+ script.onreadystatechange = null;
13046
+ script.onerror = null;
13047
+ head.removeChild(script);
13048
+
13049
+ try {
13050
+ delete window[cbName];
13051
+ delete window[cbName + '_loaded'];
13052
+ } catch (e) {
13053
+ window[cbName] = null;
13054
+ window[cbName + '_loaded'] = null;
13055
+ }
13056
+ }
13057
+
13058
+ function timeout() {
13059
+ opts.debug('JSONP: Script timeout');
13060
+
13061
+ timedOut = true;
13062
+ clean();
13063
+ cb(new errors.RequestTimeout());
13064
+ }
13065
+
13066
+ function error() {
13067
+ opts.debug('JSONP: Script error');
13068
+
13069
+ if (done || timedOut) {
13070
+ return;
13071
+ }
13072
+
13073
+ clean();
13074
+ cb(new errors.JSONPScriptError());
13075
+ }
13076
+ }
13077
+
13078
+ },{"../errors":217}],217:[function(require,module,exports){
13079
+ 'use strict';
13080
+
13081
+ // This file hosts our error definitions
13082
+ // We use custom error "types" so that we can act on them when we need it
13083
+ // e.g.: if error instanceof errors.UnparsableJSON then..
13084
+
13085
+ var inherits = require('inherits');
13086
+
13087
+ function AlgoliaSearchError(message, extraProperties) {
13088
+ var forEach = require('lodash-compat/collection/forEach');
13089
+
13090
+ var error = this;
13091
+
13092
+ // try to get a stacktrace
13093
+ if (typeof Error.captureStackTrace === 'function') {
13094
+ Error.captureStackTrace(this, this.constructor);
13095
+ } else {
13096
+ error.stack = (new Error()).stack || 'Cannot get a stacktrace, browser is too old';
13097
+ }
13098
+
13099
+ this.name = this.constructor.name;
13100
+ this.message = message || 'Unknown error';
13101
+
13102
+ if (extraProperties) {
13103
+ forEach(extraProperties, function addToErrorObject(value, key) {
13104
+ error[key] = value;
13105
+ });
13106
+ }
13107
+ }
13108
+
13109
+ inherits(AlgoliaSearchError, Error);
13110
+
13111
+ function createCustomError(name, message) {
13112
+ function AlgoliaSearchCustomError() {
13113
+ var args = Array.prototype.slice.call(arguments, 0);
13114
+
13115
+ // custom message not set, use default
13116
+ if (typeof args[0] !== 'string') {
13117
+ args.unshift(message);
13118
+ }
13119
+
13120
+ AlgoliaSearchError.apply(this, args);
13121
+ this.name = 'AlgoliaSearch' + name + 'Error';
13122
+ }
13123
+
13124
+ inherits(AlgoliaSearchCustomError, AlgoliaSearchError);
13125
+
13126
+ return AlgoliaSearchCustomError;
13127
+ }
13128
+
13129
+ // late exports to let various fn defs and inherits take place
13130
+ module.exports = {
13131
+ AlgoliaSearchError: AlgoliaSearchError,
13132
+ UnparsableJSON: createCustomError(
13133
+ 'UnparsableJSON',
13134
+ 'Could not parse the incoming response as JSON, see err.more for details'
13135
+ ),
13136
+ RequestTimeout: createCustomError(
13137
+ 'RequestTimeout',
13138
+ 'Request timedout before getting a response'
13139
+ ),
13140
+ Network: createCustomError(
13141
+ 'Network',
13142
+ 'Network issue, see err.more for details'
13143
+ ),
13144
+ JSONPScriptFail: createCustomError(
13145
+ 'JSONPScriptFail',
13146
+ '<script> was loaded but did not call our provided callback'
13147
+ ),
13148
+ JSONPScriptError: createCustomError(
13149
+ 'JSONPScriptError',
13150
+ '<script> unable to load due to an `error` event on it'
13151
+ ),
13152
+ Unknown: createCustomError(
13153
+ 'Unknown',
13154
+ 'Unknown error occured'
13155
+ )
13156
+ };
13157
+
13158
+ },{"inherits":161,"lodash-compat/collection/forEach":162}],218:[function(require,module,exports){
13159
+ module.exports="3.7.4"
13160
+ },{}],219:[function(require,module,exports){
13161
+ // Copyright Joyent, Inc. and other Node contributors.
13162
+ //
13163
+ // Permission is hereby granted, free of charge, to any person obtaining a
13164
+ // copy of this software and associated documentation files (the
13165
+ // "Software"), to deal in the Software without restriction, including
13166
+ // without limitation the rights to use, copy, modify, merge, publish,
13167
+ // distribute, sublicense, and/or sell copies of the Software, and to permit
13168
+ // persons to whom the Software is furnished to do so, subject to the
13169
+ // following conditions:
13170
+ //
13171
+ // The above c