<commit_before>import React from 'react';
import _ from 'lodash';
import { Card, Alert, ButtonGroup, Button, Spinner } from 'elemental';
import VolunteerForm from './VolunteerForm';
import LoginLinkForm from './LoginLinkForm';
import Mission from './Mission';
import * as http from '../lib/http';

export default React.createClass({

   childContextTypes: {
      volunteer: React.PropTypes.object,
   },

   getInitialState() {
      return {
         volunteer: null,
         missions: null,
         isEditing: false,
         error: null,
         message: null,
         hasVisitedBefore: !!window.localStorage.getItem('hasVisitedBefore'),
      };
   },

   getChildContext() {
      return {
         volunteer: this.state.volunteer,
      };
   },

   componentDidMount() {
      if (!this.state.hasVisitedBefore) {
         window.localStorage.setItem('hasVisitedBefore', true);
      }

      http.get('/api/volunteer')
         .then(({ volunteer, missions }) => this.setState({ volunteer, missions }))
         .catch(({ error }) => this.setState({ error }));
   },

   setMessage(message) {
      this.setState({ message });
      _.delay(() => this.setState({ message: null }), 3000);
   },

   setVolunteer(volunteer) {
      this.setState({ volunteer });
   },

   toggleEditMode() {
      this.setState({ isEditing: !this.state.isEditing });
   },

   updateMission(newMission) {
      const missions = this.state.missions;
      const index = _.findIndex(missions, mission => mission.id === newMission.id);
      missions[index] = newMission;
      this.setState({ missions });
   },

   renderMissions() {
      if (!this.state.missions) return null;

      if (!this.state.missions.length) {
         return <Card>You're not on any missions yet.</Card>;
      }

      return (

            {this.state.missions.map(mission => <Mission key={mission.id} mission={mission} onChange={this.updateMission} />)}

      );
   },

   render() {
      if (this.state.error) {
         return (

               <Alert type="danger">Error: {this.state.error || 'Something went wrong.'}</Alert>

         );
      }

      if (this.state.volunteer === null) {
         return
<Spinner size="lg" />
;
      }

      if (_.isEmpty(this.state.volunteer)) {
         return <LoginLinkForm />;
      }

      return (

               <Card style={{ overflow: 'hidden' }}>

                  <ButtonGroup style={{ float: 'right' }}>
                     <Button type="link" size="sm" onClick={this.toggleEditMode}>Change Data</Button>
                     {this.state.volunteer.name.first}
                  </ButtonGroup>
               </Card>

            {this.state.message &&
               <Alert type="success">{this.state.message}</Alert>
            }
            {!this.state.hasVisitedBefore && !this.state.isEditing &&
               <Alert type="info">Welcome! To edit your personal information, click on “Change Data” ↗</Alert>
            }

            {this.state.isEditing
               ? <VolunteerForm volunteer={this.state.volunteer} onChange={this.setVolunteer} />
               : this.renderMissions()
            }

      );
   },

});
<commit_msg>Volunteer: Edit profile as initial page<commit_after>import React from 'react';
import _ from 'lodash';
import { Card, Alert, ButtonGroup, Button, Spinner } from 'elemental';
import VolunteerForm from './VolunteerForm';
import LoginLinkForm from './LoginLinkForm';
import Mission from './Mission';
import * as http from '../lib/http';

export default React.createClass({

   childContextTypes: {
      volunteer: React.PropTypes.object,
   },

   getInitialState() {
      return {
         volunteer: null,
         missions: null,
         isEditing: true,
         error: null,
         message: null,
         hasVisitedBefore: !!window.localStorage.getItem('hasVisitedBefore'),
      };
   },

   getChildContext() {
      return {
         volunteer: this.state.volunteer,
      };
   },

   componentDidMount() {
      if (!this.state.hasVisitedBefore) {
         window.localStorage.setItem('hasVisitedBefore', true);
      }

      http.get('/api/volunteer')
         .then(({ volunteer, missions }) => this.setState({ volunteer, missions }))
         .catch(({ error }) => this.setState({ error }));
   },

   setMessage(message) {
      this.setState({ message });
      _.delay(() => this.setState({ message: null }), 3000);
   },

   setVolunteer(volunteer) {
      this.setState({ volunteer });
   },

   toggleEditMode() {
      this.setState({ isEditing: !this.state.isEditing });
   },

   updateMission(newMission) {
      const missions = this.state.missions;
      const index = _.findIndex(missions, mission => mission.id === newMission.id);
      missions[index] = newMission;
      this.setState({ missions });
   },

   renderMissions() {
      if (!this.state.missions) return null;

      if (!this.state.missions.length) {
         return <Card>You're not on any missions yet.</Card>;
      }

      return (

            {this.state.missions.map(mission => <Mission key={mission.id} mission={mission} onChange={this.updateMission} />)}

      );
   },

   render() {
      if (this.state.error) {
         return (

               <Alert type="danger">Error: {this.state.error || 'Something went wrong.'}</Alert>

         );
      }

      if (this.state.volunteer === null) {
         return
<Spinner size="lg" />
;
      }

      if (_.isEmpty(this.state.volunteer)) {
         return <LoginLinkForm />;
      }

      return (

               <Card style={{ overflow: 'hidden' }}>

                  <ButtonGroup style={{ float: 'right' }}>
                     {/*<Button type="link" size="sm" onClick={this.toggleEditMode}>Change Data</Button>*/}
                     {this.state.volunteer.name.first}
                  </ButtonGroup>
               </Card>

            {this.state.message &&
               <Alert type="success">{this.state.message}</Alert>
            }
            {!this.state.hasVisitedBefore && !this.state.isEditing &&
               <Alert type="info">Welcome! To edit your personal information, click on “Change Data” ↗</Alert>
            }

            {this.state.isEditing
               ? <VolunteerForm volunteer={this.state.volunteer} onChange={this.setVolunteer} />
               : this.renderMissions()
            }

      );
   },

});
<|endoftext|>


<commit_before>// Refreshes guide form data.

'use strict';

var camelToHyphen  = require('es5-ext/string/#/camel-to-hyphen')
  , $              = require('mano-legacy')
  , formatCurrency = require('./format-currency');

require('es3-ext/array/#/for-each/implement');
require('mano-legacy/for-each');
require('mano-legacy/on-env-update');
require('mano-legacy/dbjs-form-fill');

// Each hook is an array of scripts which are executed in corresponding parts of refresh guide
$.refreshGuideHooks = { atEnd: [],
	beforeRegistrationsApplicable: [], beforeRequirementsApplicable: [],
	beforeRegistrationsRequested: [] };

require('mano-legacy/get-text-child');

var getNamedListElements = function (listId) {
	var listElement = $(listId), result = {};

	if (listElement) {
		$.forEach(listElement.getElementsByTagName('li'), function (element) {
			var elementDataKey = element.getAttribute('data-key');

			if (element.parentNode !== listElement || !elementDataKey) return;

			result[elementDataKey] = $(element);
		});
	}

	return result;
};

var getPropertyValue = function (target, property) {
	return typeof target[property] === 'function' ? target[property]($.dbjsObserveMock)
		: target[property];
};

var buildCostsPrintLink = function (currentLink, cost, field, prefix) {
	if (!prefix) prefix = '';
	currentLink.search += (currentLink.search.length) ?
			'&' + prefix + cost.key + '=' + cost[field].toFixed(2) :
			'?' + prefix + cost.key + '=' + cost[field].toFixed(2);

	return currentLink;
};

var toggleConditionally = function (element, condition) {
	if (element) {
		element.toggle(condition);
	}
};

// A legacy refreshGuide method for Part A Guide page.
// Used in: /view/business-process-guide.js
module.exports = $.refreshGuide = function (guideFormId, businessProcessId,
		businessProcessTypeName) {
	var guideForm = $(guideFormId)
	  , noRequstedRegistrationsSection, mandatoryRegistrationsSection
	  , mandatoryRegistrationsListElements
	  , optionalRegistrationsSection, optionalRegistrationsListElements
	  , requirementsSection, requirementsListElements, requirementsLabelElements = {}
	  , costsListElements, costsAmountsElements = {}, costsLabelElements = {}
	  , costsTotalElement, costsPrintLink, guideSaveButton
	  , costsSection, zeroCostsClass;

	// Create mock BusinessProcess
	var BusinessProcess = function () {};
	BusinessProcess.prototype = $.legacyDb[businessProcessTypeName].prototype;

	// Gather required list elements

	noRequstedRegistrationsSection = $('no-requested-registrations-section');
	mandatoryRegistrationsSection = $('mandatory-registrations-section');
	mandatoryRegistrationsListElements = getNamedListElements('mandatory-registrations-list');
	optionalRegistrationsSection = $('optional-registrations-section');
	optionalRegistrationsListElements = getNamedListElements('optional-registrations-list');
	requirementsSection      = $('requirements-section');
	requirementsListElements = getNamedListElements('requirements-list');
	costsListElements = getNamedListElements('costs-list');
	costsPrintLink  = $('print-costs-link');
	costsSection    = $('costs-section');
	zeroCostsClass  = 'user-guide-zero-costs-amount';
	guideSaveButton = $('guide-save-button');

	$.forIn(costsListElements, function (li, name) {
		costsAmountsElements[name] = $.getTextChild('cost-amount-' + camelToHyphen.call(name));
		costsLabelElements[name] = $.getTextChild('cost-label-' + camelToHyphen.call(name));
	});

	$.forIn(requirementsListElements, function (li, name) {
		var labelElement = $('requirement-label-' + camelToHyphen.call(name));

		if (labelElement) requirementsLabelElements[name] = $.getTextChild(labelElement);
	});

	if ($('costs-total')) {
		costsTotalElement = $.getTextChild('costs-total');
	}

	// Crazy train...
	$.onEnvUpdate(guideForm, function () {
		// Create mock business process
		var businessProcess = new BusinessProcess();
		businessProcess.__id__ = businessProcessId;

		// -- First FormFill pass --

		// Perform dbjsFormFill
		$.dbjsFormFill(businessProcess, guideForm);

		$.refreshGuideHooks.beforeRegistrationsApplicable.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
		// Resolve applicable, mandatory and optional registrations
		businessProcess.registrations.map.forEach(function (registration) {
			registration.isApplicable = getPropertyValue(registration, 'isApplicable');
			registration.isMandatory = getPropertyValue(registration, 'isMandatory');
		});

		businessProcess.registrations.applicable =
			$.setify(businessProcess.registrations.applicable($.dbjsObserveMock));
		businessProcess.registrations.mandatory =
			$.setify(businessProcess.registrations.mandatory($.dbjsObserveMock));
		businessProcess.registrations.optional =
			$.setify(businessProcess.registrations.optional($.dbjsObserveMock));

		// Filter mandatory and optional registration lists
		if (businessProcess.registrations.mandatory.size === 0) {
			toggleConditionally(mandatoryRegistrationsSection, false);
		} else {
			toggleConditionally(mandatoryRegistrationsSection, true);
			$.forIn(mandatoryRegistrationsListElements, function (li, name) {
				li.toggle(businessProcess.registrations.mandatory.has(
					businessProcess.registrations.map[name]
				));
			});
		}

		if (businessProcess.registrations.optional.size === 0) {
			toggleConditionally(optionalRegistrationsSection, false);
		} else {
			toggleConditionally(optionalRegistrationsSection, true);
			$.forIn(optionalRegistrationsListElements, function (li, name) {
				li.toggle(businessProcess.registrations.optional.has(
					businessProcess.registrations.map[name]
				));
			});
		}
		// -- Second FormFill pass --

		// Clear each registration isRequested
		businessProcess.registrations.map.forEach(function (registration) {
			// One time in a galaxy far far away, isRequested was SetLike!?!
			delete registration.isRequested;
		});

		// Perform dbjsFormFill
		$.dbjsFormFill(businessProcess, guideForm);

		$.refreshGuideHooks.beforeRegistrationsRequested.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});

		// Resolve requested registrations
		businessProcess.registrations.map.forEach(function (registration) {
			registration.isRequested = getPropertyValue(registration, 'isRequested');
		});

		businessProcess.registrations.requested =
			$.setify(businessProcess.registrations.requested($.dbjsObserveMock));

		// Resolve each registration certificates, requirements and costs
		businessProcess.registrations.map.forEach(function (registration) {
			registration.certificates =
					typeof registration.certificates === 'function' ?
						$.setify(registration.certificates($.dbjsObserveMock))
							: registration.certificates;
			registration.requirements =
					typeof registration.requirements === 'function' ?
						$.setify(registration.requirements($.dbjsObserveMock))
							: registration.requirements;
			registration.costs =
					typeof registration.costs === 'function' ?
						$.setify(registration.costs($.dbjsObserveMock)) : registration.costs;
		});
		// Resolve certificates
		businessProcess.certificates.applicable =
			$.setify(businessProcess.certificates.applicable($.dbjsObserveMock));

		// Resolve requirements
		businessProcess.requirements.resolved =
			$.setify(businessProcess.requirements.resolved($.dbjsObserveMock));

		$.refreshGuideHooks.beforeRequirementsApplicable.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
		// Resolve applicable requirements
		businessProcess.requirements.map.forEach(function (requirement) {
			requirement.isApplicable = getPropertyValue(requirement, 'isApplicable');
		});

		businessProcess.requirements.applicable =
			$.setify(businessProcess.requirements.applicable($.dbjsObserveMock));

		businessProcess.requirements.map.forEach(function (requirement) {
			requirement.label = getPropertyValue(requirement, 'label');
		});

		//Resolve costs
		businessProcess.costs.applicable =
			$.setify(businessProcess.costs.applicable($.dbjsObserveMock));

		businessProcess.costs.map.forEach(function (cost) {
			cost.amount     = getPropertyValue(cost, 'amount');
			cost.sideAmount = getPropertyValue(cost, 'sideAmount');
			cost.label      = getPropertyValue(cost, 'label');
		});

		businessProcess.costs.payable =
			$.setify(businessProcess.costs.payable($.dbjsObserveMock));
		businessProcess.costs.totalAmount = typeof businessProcess.costs.totalAmount === 'function'
			? businessProcess.costs.totalAmount($.dbjsObserveMock) : businessProcess.costs.totalAmount;

		// Filter requirements and costs lists
		$.forIn(requirementsListElements, function (li, name) {
			var enabled = businessProcess.requirements.applicable.has(
				businessProcess.requirements.map[name]
			);

			li.toggle(enabled);
			if (enabled) {
				if (requirementsLabelElements[name]) {
					requirementsLabelElements[name].data = businessProcess.requirements.map[name].label;
				}
			}
		});

		$.forIn(costsListElements, function (li, name) {
			var enabled = businessProcess.costs.payable.has(businessProcess.costs.map[name]);

			li.toggle(enabled);
			if (enabled) {
				if (costsAmountsElements[name]) {
					costsAmountsElements[name].data = formatCurrency(businessProcess.costs.map[name].amount);
				}
				if (costsLabelElements[name]) {
					costsLabelElements[name].data = businessProcess.costs.map[name].label;
				}
			}
		});

		if (costsTotalElement) {
			costsTotalElement.data = formatCurrency(businessProcess.costs.totalAmount);
		}

		// Build costs print link
		if (costsPrintLink) {
			costsPrintLink.search = '';

			businessProcess.costs.payable.forEach(function (cost) {
				buildCostsPrintLink(costsPrintLink, cost, 'amount');
			});

			if (costsPrintLink.search.length) {
				costsPrintLink.search += '&total=' + businessProcess.costs.totalAmount.toFixed(2);
			}

			businessProcess.costs.applicable.forEach(function (cost) {
				if (!cost.sideAmount) return;
				buildCostsPrintLink(costsPrintLink, cost, 'sideAmount', 'side-');
			});
		}

		if (costsSection) {
			if (businessProcess.costs.totalAmount) {
				costsSection.removeClass(zeroCostsClass);
			} else {
				costsSection.addClass(zeroCostsClass);
			}
		}

		toggleConditionally(noRequstedRegistrationsSection,
			!businessProcess.registrations.requested.size);
		toggleConditionally(costsSection, businessProcess.registrations.requested.size);
		toggleConditionally(requirementsSection, businessProcess.registrations.requested.size);
		toggleConditionally(guideSaveButton, businessProcess.registrations.requested.size);

		$.refreshGuideHooks.atEnd.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
	});
};
<commit_msg>Improve empty values display<commit_after>// Refreshes guide form data.

'use strict';

var camelToHyphen  = require('es5-ext/string/#/camel-to-hyphen')
  , $              = require('mano-legacy')
  , formatCurrency = require('./format-currency');

require('es3-ext/array/#/for-each/implement');
require('mano-legacy/for-each');
require('mano-legacy/on-env-update');
require('mano-legacy/dbjs-form-fill');

// Each hook is an array of scripts which are executed in corresponding parts of refresh guide
$.refreshGuideHooks = { atEnd: [],
	beforeRegistrationsApplicable: [], beforeRequirementsApplicable: [],
	beforeRegistrationsRequested: [] };

require('mano-legacy/get-text-child');

var getNamedListElements = function (listId) {
	var listElement = $(listId), result = {};

	if (listElement) {
		$.forEach(listElement.getElementsByTagName('li'), function (element) {
			var elementDataKey = element.getAttribute('data-key');

			if (element.parentNode !== listElement || !elementDataKey) return;

			result[elementDataKey] = $(element);
		});
	}

	return result;
};

var getPropertyValue = function (target, property) {
	var result = typeof target[property] === 'function'
		? target[property]($.dbjsObserveMock) : target[property];
	return result || ''; // Do not pass null/undefined literally
};

var buildCostsPrintLink = function (currentLink, cost, field, prefix) {
	if (!prefix) prefix = '';
	currentLink.search += (currentLink.search.length) ?
			'&' + prefix + cost.key + '=' + cost[field].toFixed(2) :
			'?' + prefix + cost.key + '=' + cost[field].toFixed(2);

	return currentLink;
};

var toggleConditionally = function (element, condition) {
	if (element) {
		element.toggle(condition);
	}
};

// A legacy refreshGuide method for Part A Guide page.
// Used in: /view/business-process-guide.js
module.exports = $.refreshGuide = function (guideFormId, businessProcessId,
		businessProcessTypeName) {
	var guideForm = $(guideFormId)
	  , noRequstedRegistrationsSection, mandatoryRegistrationsSection
	  , mandatoryRegistrationsListElements
	  , optionalRegistrationsSection, optionalRegistrationsListElements
	  , requirementsSection, requirementsListElements, requirementsLabelElements = {}
	  , costsListElements, costsAmountsElements = {}, costsLabelElements = {}
	  , costsTotalElement, costsPrintLink, guideSaveButton
	  , costsSection, zeroCostsClass;

	// Create mock BusinessProcess
	var BusinessProcess = function () {};
	BusinessProcess.prototype = $.legacyDb[businessProcessTypeName].prototype;

	// Gather required list elements

	noRequstedRegistrationsSection = $('no-requested-registrations-section');
	mandatoryRegistrationsSection = $('mandatory-registrations-section');
	mandatoryRegistrationsListElements = getNamedListElements('mandatory-registrations-list');
	optionalRegistrationsSection = $('optional-registrations-section');
	optionalRegistrationsListElements = getNamedListElements('optional-registrations-list');
	requirementsSection      = $('requirements-section');
	requirementsListElements = getNamedListElements('requirements-list');
	costsListElements = getNamedListElements('costs-list');
	costsPrintLink  = $('print-costs-link');
	costsSection    = $('costs-section');
	zeroCostsClass  = 'user-guide-zero-costs-amount';
	guideSaveButton = $('guide-save-button');

	$.forIn(costsListElements, function (li, name) {
		costsAmountsElements[name] = $.getTextChild('cost-amount-' + camelToHyphen.call(name));
		costsLabelElements[name] = $.getTextChild('cost-label-' + camelToHyphen.call(name));
	});

	$.forIn(requirementsListElements, function (li, name) {
		var labelElement = $('requirement-label-' + camelToHyphen.call(name));

		if (labelElement) requirementsLabelElements[name] = $.getTextChild(labelElement);
	});

	if ($('costs-total')) {
		costsTotalElement = $.getTextChild('costs-total');
	}

	// Crazy train...
	$.onEnvUpdate(guideForm, function () {
		// Create mock business process
		var businessProcess = new BusinessProcess();
		businessProcess.__id__ = businessProcessId;

		// -- First FormFill pass --

		// Perform dbjsFormFill
		$.dbjsFormFill(businessProcess, guideForm);

		$.refreshGuideHooks.beforeRegistrationsApplicable.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
		// Resolve applicable, mandatory and optional registrations
		businessProcess.registrations.map.forEach(function (registration) {
			registration.isApplicable = getPropertyValue(registration, 'isApplicable');
			registration.isMandatory = getPropertyValue(registration, 'isMandatory');
		});

		businessProcess.registrations.applicable =
			$.setify(businessProcess.registrations.applicable($.dbjsObserveMock));
		businessProcess.registrations.mandatory =
			$.setify(businessProcess.registrations.mandatory($.dbjsObserveMock));
		businessProcess.registrations.optional =
			$.setify(businessProcess.registrations.optional($.dbjsObserveMock));

		// Filter mandatory and optional registration lists
		if (businessProcess.registrations.mandatory.size === 0) {
			toggleConditionally(mandatoryRegistrationsSection, false);
		} else {
			toggleConditionally(mandatoryRegistrationsSection, true);
			$.forIn(mandatoryRegistrationsListElements, function (li, name) {
				li.toggle(businessProcess.registrations.mandatory.has(
					businessProcess.registrations.map[name]
				));
			});
		}

		if (businessProcess.registrations.optional.size === 0) {
			toggleConditionally(optionalRegistrationsSection, false);
		} else {
			toggleConditionally(optionalRegistrationsSection, true);
			$.forIn(optionalRegistrationsListElements, function (li, name) {
				li.toggle(businessProcess.registrations.optional.has(
					businessProcess.registrations.map[name]
				));
			});
		}
		// -- Second FormFill pass --

		// Clear each registration isRequested
		businessProcess.registrations.map.forEach(function (registration) {
			// One time in a galaxy far far away, isRequested was SetLike!?!
			delete registration.isRequested;
		});

		// Perform dbjsFormFill
		$.dbjsFormFill(businessProcess, guideForm);

		$.refreshGuideHooks.beforeRegistrationsRequested.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});

		// Resolve requested registrations
		businessProcess.registrations.map.forEach(function (registration) {
			registration.isRequested = getPropertyValue(registration, 'isRequested');
		});

		businessProcess.registrations.requested =
			$.setify(businessProcess.registrations.requested($.dbjsObserveMock));

		// Resolve each registration certificates, requirements and costs
		businessProcess.registrations.map.forEach(function (registration) {
			registration.certificates =
					typeof registration.certificates === 'function' ?
						$.setify(registration.certificates($.dbjsObserveMock))
							: registration.certificates;
			registration.requirements =
					typeof registration.requirements === 'function' ?
						$.setify(registration.requirements($.dbjsObserveMock))
							: registration.requirements;
			registration.costs =
					typeof registration.costs === 'function' ?
						$.setify(registration.costs($.dbjsObserveMock)) : registration.costs;
		});
		// Resolve certificates
		businessProcess.certificates.applicable =
			$.setify(businessProcess.certificates.applicable($.dbjsObserveMock));

		// Resolve requirements
		businessProcess.requirements.resolved =
			$.setify(businessProcess.requirements.resolved($.dbjsObserveMock));

		$.refreshGuideHooks.beforeRequirementsApplicable.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
		// Resolve applicable requirements
		businessProcess.requirements.map.forEach(function (requirement) {
			requirement.isApplicable = getPropertyValue(requirement, 'isApplicable');
		});

		businessProcess.requirements.applicable =
			$.setify(businessProcess.requirements.applicable($.dbjsObserveMock));

		businessProcess.requirements.map.forEach(function (requirement) {
			requirement.label = getPropertyValue(requirement, 'label');
		});

		//Resolve costs
		businessProcess.costs.applicable =
			$.setify(businessProcess.costs.applicable($.dbjsObserveMock));

		businessProcess.costs.map.forEach(function (cost) {
			cost.amount     = getPropertyValue(cost, 'amount');
			cost.sideAmount = getPropertyValue(cost, 'sideAmount');
			cost.label      = getPropertyValue(cost, 'label');
		});

		businessProcess.costs.payable =
			$.setify(businessProcess.costs.payable($.dbjsObserveMock));
		businessProcess.costs.totalAmount = typeof businessProcess.costs.totalAmount === 'function'
			? businessProcess.costs.totalAmount($.dbjsObserveMock) : businessProcess.costs.totalAmount;

		// Filter requirements and costs lists
		$.forIn(requirementsListElements, function (li, name) {
			var enabled = businessProcess.requirements.applicable.has(
				businessProcess.requirements.map[name]
			);

			li.toggle(enabled);
			if (enabled) {
				if (requirementsLabelElements[name]) {
					requirementsLabelElements[name].data = businessProcess.requirements.map[name].label;
				}
			}
		});

		$.forIn(costsListElements, function (li, name) {
			var enabled = businessProcess.costs.payable.has(businessProcess.costs.map[name]);

			li.toggle(enabled);
			if (enabled) {
				if (costsAmountsElements[name]) {
					costsAmountsElements[name].data = formatCurrency(businessProcess.costs.map[name].amount);
				}
				if (costsLabelElements[name]) {
					costsLabelElements[name].data = businessProcess.costs.map[name].label;
				}
			}
		});

		if (costsTotalElement) {
			costsTotalElement.data = formatCurrency(businessProcess.costs.totalAmount);
		}

		// Build costs print link
		if (costsPrintLink) {
			costsPrintLink.search = '';

			businessProcess.costs.payable.forEach(function (cost) {
				buildCostsPrintLink(costsPrintLink, cost, 'amount');
			});

			if (costsPrintLink.search.length) {
				costsPrintLink.search += '&total=' + businessProcess.costs.totalAmount.toFixed(2);
			}

			businessProcess.costs.applicable.forEach(function (cost) {
				if (!cost.sideAmount) return;
				buildCostsPrintLink(costsPrintLink, cost, 'sideAmount', 'side-');
			});
		}

		if (costsSection) {
			if (businessProcess.costs.totalAmount) {
				costsSection.removeClass(zeroCostsClass);
			} else {
				costsSection.addClass(zeroCostsClass);
			}
		}

		toggleConditionally(noRequstedRegistrationsSection,
			!businessProcess.registrations.requested.size);
		toggleConditionally(costsSection, businessProcess.registrations.requested.size);
		toggleConditionally(requirementsSection, businessProcess.registrations.requested.size);
		toggleConditionally(guideSaveButton, businessProcess.registrations.requested.size);

		$.refreshGuideHooks.atEnd.forEach(function (hook) {
			hook(businessProcess, guideForm);
		});
	});
};
<|endoftext|>


<commit_before>//
var ENME = {
    config : function() {
      return "";
    },
    getMessage : function(){
      return "text";
    }
};

//

encuestame = {};
encuestame.activity = {};
encuestame.service = {};
encuestame.service.offline = false;
encuestame.service.timeout = ENME.config('delay');
encuestame.contextDefault = ENME.config('contextPath');
encuestame.signin = encuestame.contextDefault+"/signin";

// encuestame.shortUrlProvider = [
//                     {code:"googl",label:"http://googl.com"},
//                     {code:"tinyurl",label:"http://tinyurl.com"},
//                     {code:"bitly",label:"http://bit.ly/"}
//                    ];

encuestame.error = {};
encuestame.error.debug = true;
encuestame.error.dialog = null;

encuestame.utilities = {};
encuestame.utilities.vote = 1;
encuestame.utilities.GRADINENT_CLASS = "gradient-gray";
encuestame.utilities.HIDDEN_CLASS = "hidden";

/**
 * Create a no results message node.
 */
encuestame.utilities.noResults = function(classCSS) {
    var norR = dojo.create("div");
    dojo.addClass(norR, "no-results");
    if (classCSS !== null) {
        dojo.addClass(norR, classCSS);
    }
    norR.innerHTML = encuestame.constants.messageCodes["024"];
    return norR;
};

encuestame.utilities.randomString = function() {
    var text = "";
    var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
    for( var i=0; i < 5; i++ )
        text += possible.charAt(Math.floor(Math.random() * possible.length));
    return text;
};

/**
 * Checking if a string is empty, null or undefined.
 * @param string value
 */
encuestame.utilities.isEmpty = function(str) {
     return (!str || 0 === str.length);
};

encuestame.utilities.url = {};

/*
 * summary :: build hashtag url
 *    hashtagName : hashtag name;
 */
encuestame.utilities.url.hashtag  = function(hashtagName) {
    if (hashtagName) {
        var url = encuestame.contextDefault;
        url = url.concat("/tag/");
        url = url.concat(hashtagName);
        url = url.concat("/");
        return url;
    } else {
        throw new Error("hashtag name is required");
    }
};

/*
 * clear dialog.
 */
encuestame.error.clear = function(){
    console.info("clean", encuestame.error.dialog);
    if (encuestame.error.dialog != null){
        console.info("hidding dialog");
        encuestame.error.dialog.hide();
    }
};

/*
 * denied dialog.
 */
encuestame.error.denied = function(error){
    var div = dojo.doc.createElement('div');
    var h3 = dojo.doc.createElement('h3');
        h3.innerHTML = error;
        var p = dojo.doc.createElement('p');
        p.innerHTML = status;
        div.appendChild(h3);
        div.appendChild(p);
    encuestame.error.createDialog("Opps, What's happening?", div);
};

/*
 * unknow error dialog.
 */
encuestame.error.unknown = function(error, status){
    var div = dojo.doc.createElement('div');
    var h3 = dojo.doc.createElement('h3');
        h3.innerHTML = error;
        var p = dojo.doc.createElement('p');
        p.innerHTML = status;
        div.appendChild(h3);
        div.appendChild(p);
    encuestame.error.createDialog("Opps, What's happening?", div, true);
};

/*
 * conexion error.
 */
encuestame.error.conexion = function(message){
    var div = dojo.doc.createElement('div');
    var h3 = dojo.doc.createElement('h3');
    h3.innerHTML = message;
    div.appendChild(h3);
    encuestame.error.createDialog("Network Issues", div, true);
};

/*
 * expired sesion dialog.
 */
encuestame.error.session = function(message){
    var div = dojo.doc.createElement('div');
    var h3 = dojo.doc.createElement('h3');
    h3.innerHTML = message;
    var widgetButton = new dijit.form.Button({
        label: "Sign In",
        onClick: dojo.hitch(this, function(event) {
            dojo.stopEvent(event);
            document.location.href = encuestame.signin;
        })
    });
    div.appendChild(h3);
    div.appendChild(widgetButton.domNode);
    encuestame.error.createDialog("Not logged in", div, true);
};

/*
 * Create New Error Dialog.
 */
encuestame.error.createDialog = function(title, content, addcloseButton){
    //var node = dojo.byId("errorHandler");
    console.error("error dialog "+title, content);
};

encuestame.error.messages = {};
encuestame.error.messages.denied = "Application does not have permission for this action";
encuestame.error.messages.session = "Your session has expired, please sign in to contiue.";

encuestame.filter = {};

/**
 * {"error":{"message":"Access is denied"}}
 */
encuestame.filter.response = function(response){
    console.info("encuestame.filter.response", response);
    //no permissions or session
    if(response == undefined){
        //no response

    }else if (response.error.message != undefined && response.success == undefined ) {
        encuestame.session.getSession();
    } else if(response.success == undefined ) {
        console.info("sucess response no existe");
    }
};

encuestame.session = {};
encuestame.session.getSession = function(){
    //JSESSIONID=dh3u2xvj7fwd1llbddl33dhcq; path=/encuestame; domain=demo2.encuestame.org
    var sessionCookie = dojo.cookie("JSESSIONID");
    if(sessionCookie == undefined){
        encuestame.error.session(encuestame.error.messages.denied);
    } else {
        console.info("session is valid");
    }
};

encuestame.status = ['SUCCESS','FAILED', 'STAND_BY', 'RE_SCHEDULED', 'RE_SEND'];

encuestame.surveys = ['TWEETPOLL', 'POLl', 'SURVEY', 'HASHTAG'];

encuestame.social = {};

encuestame.social.shortPicture = function(provider){
     var url = encuestame.contextDefault + "/resources/images/social/"+provider.toLowerCase()
               +"/enme_icon_"+provider.toLowerCase()+".png";
     return url;
};

encuestame.notification = {};
encuestame.notification.load = {};
encuestame.notification.load.limit = 100;

encuestame.session.activity = {};

encuestame.session.activity.name = "enme-ac";
encuestame.session.activity.notification = {t:0,n:0};

/*
 *  Creates the cookie with default values.
 */
encuestame.session.update = function(name, data){
    dojo.cookie(
        name,
        dojo.toJson(data),
        {path:'/'}
    );
};

encuestame.date = {};
encuestame.date.timeFormat = "hh:mm:ss";
encuestame.date.dateFormat = "M/d/yy";
encuestame.date.getFormatTime = function(date, fmt){
    return dojo.date.locale.format(date, {
        selector: "date",
        datePattern: fmt
    });
}

encuestame.service.handler = {};

/*
 * get context widget.
 */
encuestame.contextWidget = function() {
        //return encuestame.contextDefault;
  return "encuestame/";
};

encuestame.contextDefault = "encuestame/";

//short url service.
//encuestame.service.short = {};
//encuestame.service.short.google = "/api/short/url/google.json";
//encuestame.service.short.tinyurl = "/api/short/url/tinyurl.json";

encuestame.constants = {};
// encuestame.constants.passwordExcludes = [];
encuestame.constants.imageSizes = {
    thumbnail : "thumbnail",
    defaultType : "default",
    profile : "profile",
    preview : "preview",
    web : "web"
};

encuestame.messages = {};

// publish a message on main frame.
/*
 * MESSAGE: "message",
            WARNING: "warning",
            ERROR: "error",
            FATAL: "fatal"
 */
encuestame.messages.pubish = function(message, type, duration) {
    //console.info("encuestame.messages.pubish", message);
    //console.info("encuestame.messages.pubish", type);
    //console.info("encuestame.messages.pubish", duration);
    dojo.publish('/encuestame/message/publish', [{ message: message, type: type, duration: duration}]);
};

encuestame.modalbox = {};

encuestame.constants.errorCodes = {
    "002" : "Enter your first and last name.",
    "003" : "Whats your email address?",
    "006" : "Doesn't look like a valid email.",
    "007" : "An email is required!",
    "008" : "This email is already registered",
    "012" : "Password is too obvious.",
    "013" : "Password is not secure enough.",
    "014" : "Password must be at least 6 characters. No whitespace.",
    "015" : "Password cannot be blank!",
    "017" : "This username is already taken!",
    "018" : "Invalid username!",
    "019" : "A username is required!",
    "020" : "Your Tweet contains more than 140 characters. You will have to be more ingenious.",
    "021" : "Your Tweet no contains required answers, imagine a sky without clouds?",
    "022" : "You need at least 1 social account to publish your beautiful creation.",
    "023" : "Ops, something is wrong.",
    "024" : "Please, save your tweetpoll first"
};

encuestame.constants.warningCodes = {
    "001" : "Warning message to define"
};

encuestame.constants.messageCodes = {
    "001" : "Name looks great",
    "004" : "We will email you a confirmation.",
    "005" : "Validating...",
    "007" : "An email is required!",
    "008" : "This email is already registered",
    "009" : "Password is perfect!",
    "010" : "Password is okay.",
    "011" : "Password could be more secure.",
    "016" : "Don't worry, you can change it later.",
    "020" : "",
    "021" : "Drag your gadget here !!",
    "022" : "Be the first to comment on this publication.",
    "023" : "Updated Successfully",
    "024" : "Sorry, no results found",
    "025" : "Publishing your tweets, please wait ..."
 };

encuestame.constants.version = { version : "1.143"};
<commit_msg>Removed old and non used js code<commit_after><|endoftext|>


<commit_before>async function delay(duration) {
  return new Promise(function (resolve) {
    setTimeout(resolve, duration)
  })
}

module.exports = async (action) => {
  await delay(1)
  action.log("Hello World!")
  await delay(1)
}
<commit_msg>Better timeout (#1060)<commit_after>const util = require("util")
const delay = util.promisify(setTimeout)

module.exports = async (action) => {
  await delay(1)
  action.log("Hello World!")
  await delay(1)
}
<|endoftext|>


<commit_before>/*
 * Windows Process Handling.
 * A wrapper to integrate processHandlingCore into GPII.
 *
 * Copyright 2016 Raising the Floor - International
 *
 * Licensed under the New BSD license. You may not use this file except in
 * compliance with this License.
 *
 * The research leading to these results has received funding from the European Union's
 * Seventh Framework Programme (FP7/2007-2013)
 * under grant agreement no. 289016.
 *
 * You may obtain a copy of the License at
 * https://github.com/GPII/universal/blob/master/LICENSE.txt
 */

"use strict";

var fluid = require("universal");
var ref = require("ref");

var gpii = fluid.registerNamespace("gpii");
var windows = fluid.registerNamespace("gpii.windows");

require("../WindowsUtilities/WindowsUtilities.js");

var c = windows.API_constants;

/**
 * Kills any windows processes with a given application filename.
 * http://stackoverflow.com/questions/7956519/how-to-kill-processes-by-name-win32-api
 *
 * @param {String} The filename of the application. For example, the Windows on
 * screen keyboard is "osk.exe". Other examples include "Magnify.exe" and
 * "firefox.exe".
 */
gpii.windows.killProcessByName = function (filename) {
    var pids = gpii.windows.findProcessByName(filename, true);
    if (pids) {
        for (var n = 0, len = pids.length; n < len; n++) {
            var hProcess = windows.kernel32.OpenProcess(c.PROCESS_TERMINATE, 0, pids[n]);
            if (hProcess !== ref.NULL) {
                windows.kernel32.TerminateProcess(hProcess, 9);
                windows.kernel32.CloseHandle(hProcess);
            }
        }
    }
};

/**
 * Finds a running process with the given name.
 *
 * The CreateToolhelp32Snapshot Windows API call captures the running processes, and the Process32First/Next
 * functions are used to enumerate them.
 *
 * @param filename The exe file name to search for.
 * @param all {boolean?} Set to true to return an array containing all matching processes.
 * @returns {?number|number[]} The Process ID of the matching processes, otherwise null.
 */
gpii.windows.findProcessByName = function (filename, all) {

    // Get a snapshot of the processes.
    var hSnapShot = windows.kernel32.CreateToolhelp32Snapshot(windows.API_constants.TH32CS_SNAPPROCESS, null);
    if (hSnapShot === windows.API_constants.INVALID_HANDLE_VALUE) {
        console.error("CreateToolhelp32Snapshot failed. Win32 error: " + windows.GetLastError());
        return null;
    }

    var matches = [];

    try {
        // Create the structure for the return parameter of Process32First/Next.
        var pEntry = new windows.PROCESSENTRY32();
        pEntry.dwSize = windows.PROCESSENTRY32.size;

        // Enumerate the processes.
        var hRes = windows.kernel32.Process32First(hSnapShot, pEntry.ref());
        while (hRes) {
            var buf = new Buffer(pEntry.szExeFile);
            var processName = ref.readCString(buf, 0);

            if (processName === filename) {
                if (all) {
                    // Add it to the array of matches.
                    matches.push(pEntry.th32ProcessID);
                } else {
                    // Only want the first one - return it.
                    return pEntry.th32ProcessID;
                }
            }

            hRes = windows.kernel32.Process32Next(hSnapShot, pEntry.ref());
        }
    } finally {
        // Make sure the snapshot is closed.
        if (hSnapShot) {
            windows.kernel32.CloseHandle(hSnapShot);
        }
    }

    return all ? matches : null;
};

/**
 * Waits for a process to either start or terminate, returning a promise which will resolve when the existence of a
 * process is in the desired state.
 *
 * The promise will reject if the process has yet to become in the desired state after the timeout.
 *
 * @param filename The executable.
 * @param options The options.
 * @param options.start The desired state: true to wait for the process to start, false to wait for the termination, or
 *   null to wait for a change (if the process isn't running then wait for it to start, otherwise wait for termination).
 * @param options.timeout Approximate milliseconds to wait, or null for infinite.
 * @param options.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when the process is in the desired state, or will reject if after the
 *   timeout the process is still in the same state.
 */
gpii.windows.waitForProcessStateChange = function (filename, options) {
    var timeoutTime = null;
    var defaultOptions = {
        pollDelay: 500,
        timeout: null,
        start: null
    };

    options = fluid.extend(defaultOptions, options);

    if (options.timeout !== null) {
        timeoutTime = Date.now() + options.timeout;
    }

    var promise = fluid.promise();

    // Continuously check for a matching process, until there is none.
    var checkProcess = function () {
        // Get the pid of a matching process.
        var running = windows.findProcessByName(filename) !== null;
        var changed = false;

        if (options.start === null) {
            // Auto-detect the mode based on whether or not it's currently running.
            options.start = !running;
        } else if (running === options.start) {
            changed = true;
        }

        if (changed) {
            // The state has changed.
            promise.resolve();
        } else {
            if (!options.timeout || Date.now() < timeoutTime) {
                // It's still in the same state - keep checking.
                setTimeout(checkProcess, options.pollDelay);
            } else {
                // Ran out of time.
                promise.reject({
                    isError: true,
                    message: "Timed out waiting for process " + filename +
                        " to " + (options.start ? "start" : "terminate") + " after " + options.timeout + "ms"
                });
            }
        }
    };

    checkProcess(promise);
    return promise;
};

/**
 * Waits for a process to terminate, returning a promise which will resolve when there are no matching processes
 * running. If there are no processes running when the function is called, the promise will already be resolved.
 * The promise will reject if the process is still running after the timeout.
 *
 * @param filename The executable.
 * @param options The options.
 * @param options.timeout Approximate milliseconds to wait, or null for infinite.
 * @param options.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when there are no matching processes running, or will reject if a matching
 *  process is still running after the timeout.
 */
gpii.windows.waitForProcessTermination = function (filename, options) {
    options = options || {};
    options.start = false;
    return gpii.windows.waitForProcessStateChange(filename, options);
};

/**
 * Waits for a process to start, returning a promise which will resolve when there there is a matching process running.
 * If there are already processes running when the function is called, the promise will already be resolved.
 * The promise will reject if a matching process is still not running after the timeout.
 *
 * @param filename The executable.
 * @param options The options.
 * @param options.timeout Approximate milliseconds to wait, or null for infinite.
 * @param options.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when there is a matching processes running, or will reject if a matching
 *  process is still not running after the timeout.
 */
gpii.windows.waitForProcessStart = function (filename, options) {
    options = options || {};
    options.start = true;
    return gpii.windows.waitForProcessStateChange(filename, options);
};

fluid.defaults("gpii.windows.killProcessByName", {
    gradeNames: "fluid.function",
    argumentMap: {
        filename: 0
    }
});
<commit_msg>GPII-581: Tidy up of waitForProcessState Made options immutable, renamed waitForProcessStateChange to waitForProcessState<commit_after>/*
 * Windows Process Handling.
 * A wrapper to integrate processHandlingCore into GPII.
 *
 * Copyright 2016 Raising the Floor - International
 *
 * Licensed under the New BSD license. You may not use this file except in
 * compliance with this License.
 *
 * The research leading to these results has received funding from the European Union's
 * Seventh Framework Programme (FP7/2007-2013)
 * under grant agreement no. 289016.
 *
 * You may obtain a copy of the License at
 * https://github.com/GPII/universal/blob/master/LICENSE.txt
 */

"use strict";

var fluid = require("universal");
var ref = require("ref");

var gpii = fluid.registerNamespace("gpii");
var windows = fluid.registerNamespace("gpii.windows");

require("../WindowsUtilities/WindowsUtilities.js");

var c = windows.API_constants;

/**
 * Kills any windows processes with a given application filename.
 * http://stackoverflow.com/questions/7956519/how-to-kill-processes-by-name-win32-api
 *
 * @param {String} The filename of the application. For example, the Windows on
 * screen keyboard is "osk.exe". Other examples include "Magnify.exe" and
 * "firefox.exe".
 */
gpii.windows.killProcessByName = function (filename) {
    var pids = gpii.windows.findProcessByName(filename, true);
    if (pids) {
        for (var n = 0, len = pids.length; n < len; n++) {
            var hProcess = windows.kernel32.OpenProcess(c.PROCESS_TERMINATE, 0, pids[n]);
            if (hProcess !== ref.NULL) {
                windows.kernel32.TerminateProcess(hProcess, 9);
                windows.kernel32.CloseHandle(hProcess);
            }
        }
    }
};

/**
 * Finds a running process with the given name.
 *
 * The CreateToolhelp32Snapshot Windows API call captures the running processes, and the Process32First/Next
 * functions are used to enumerate them.
 *
 * @param filename The exe file name to search for.
 * @param all {boolean?} Set to true to return an array containing all matching processes.
 * @returns {?number|number[]} The Process ID of the matching processes, otherwise null.
 */
gpii.windows.findProcessByName = function (filename, all) {

    // Get a snapshot of the processes.
    var hSnapShot = windows.kernel32.CreateToolhelp32Snapshot(windows.API_constants.TH32CS_SNAPPROCESS, null);
    if (hSnapShot === windows.API_constants.INVALID_HANDLE_VALUE) {
        console.error("CreateToolhelp32Snapshot failed. Win32 error: " + windows.GetLastError());
        return null;
    }

    var matches = [];

    try {
        // Create the structure for the return parameter of Process32First/Next.
        var pEntry = new windows.PROCESSENTRY32();
        pEntry.dwSize = windows.PROCESSENTRY32.size;

        // Enumerate the processes.
        var hRes = windows.kernel32.Process32First(hSnapShot, pEntry.ref());
        while (hRes) {
            var buf = new Buffer(pEntry.szExeFile);
            var processName = ref.readCString(buf, 0);

            if (processName === filename) {
                if (all) {
                    // Add it to the array of matches.
                    matches.push(pEntry.th32ProcessID);
                } else {
                    // Only want the first one - return it.
                    return pEntry.th32ProcessID;
                }
            }

            hRes = windows.kernel32.Process32Next(hSnapShot, pEntry.ref());
        }
    } finally {
        // Make sure the snapshot is closed.
        if (hSnapShot) {
            windows.kernel32.CloseHandle(hSnapShot);
        }
    }

    return all ? matches : null;
};

/**
 * Waits for a process to either start or terminate, returning a promise which will resolve when the existence of a
 * process is in the desired state.
 *
 * The promise will reject if the process has yet to become in the desired state after the timeout.
 *
 * @param filename The executable.
 * @param options The options.
 * @param options.start The desired state: true to wait for the process to start, false to wait for the termination.
 * @param options.timeout Approximate milliseconds to wait, or null for infinite.
 * @param options.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when the process is in the desired state, or will reject if after the
 *   timeout the process is still in the same state.
 */
gpii.windows.waitForProcessState = function (filename, options) {
    var timeoutTime = null;
    var defaultOptions = {
        pollDelay: 500,
        timeout: null,
        start: false
    };

    options = fluid.extend(true, defaultOptions, options);

    if (options.timeout !== null) {
        timeoutTime = Date.now() + options.timeout;
    }

    var promise = fluid.promise();

    // Continuously check for a matching process, until there is none.
    var checkProcess = function () {
        // Get the pid of a matching process.
        var running = windows.findProcessByName(filename) !== null;

        if (running === options.start) {
            // Now in the desired state.
            promise.resolve();
        } else {
            if (!options.timeout || Date.now() < timeoutTime) {
                // It's still in the same state - keep checking.
                setTimeout(checkProcess, options.pollDelay);
            } else {
                // Ran out of time.
                promise.reject({
                    isError: true,
                    message: "Timed out waiting for process " + filename +
                        " to " + (options.start ? "start" : "terminate") + " after " + options.timeout + "ms"
                });
            }
        }
    };

    checkProcess(promise);
    return promise;
};

/**
 * Waits for a process to terminate, returning a promise which will resolve when there are no matching processes
 * running. If there are no processes running when the function is called, the promise will already be resolved.
 * The promise will reject if the process is still running after the timeout.
 *
 * @param filename The executable.
 * @param userOptions The options.
 * @param userOptions.timeout Approximate milliseconds to wait, or null for infinite.
 * @param userOptions.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when there are no matching processes running, or will reject if a matching
 *  process is still running after the timeout.
 */
gpii.windows.waitForProcessTermination = function (filename, userOptions) {
    var options = fluid.extend(true, {start: false}, userOptions);
    return gpii.windows.waitForProcessState(filename, options);
};

/**
 * Waits for a process to start, returning a promise which will resolve when there there is a matching process running.
 * If there are already processes running when the function is called, the promise will already be resolved.
 * The promise will reject if a matching process is still not running after the timeout.
 *
 * @param filename The executable.
 * @param userOptions The options.
 * @param userOptions.timeout Approximate milliseconds to wait, or null for infinite.
 * @param userOptions.pollDelay How long to wait, in milliseconds, between checking for the process.
 * @return {promise} The promise will resolve when there is a matching processes running, or will reject if a matching
 *  process is still not running after the timeout.
 */
gpii.windows.waitForProcessStart = function (filename, userOptions) {
    var options = fluid.extend(true, {start: true}, userOptions);
    return gpii.windows.waitForProcessState(filename, options);
};

fluid.defaults("gpii.windows.killProcessByName", {
    gradeNames: "fluid.function",
    argumentMap: {
        filename: 0
    }
});
<|endoftext|>


<commit_before>var models = require('../../models');

module.exports = function (data, callbackToStripe) {
  if (isCanceled(data)) {

    var removeProStatus = function(customer){
      return models.user.setProAccount(customer.user, false);
    };

    var sendStripe200 = callbackTostripe.bind(null, null);

    models.customer.setActive(data.customer, false)
      .then(removeProStatus)
      //.then(removeTeamStatus)
      .then(sendStripe200)
      .catch(callbackToStripe);

  } else {
    callbackToStripe(null);
  }
};

function isCanceled(obj) {
  return obj.status ? obj.status === 'canceled' : isCanceled(obj.data || obj.object);
}
<commit_msg>Adding sessionStore reference to stripe subscribtion deleted handler<commit_after>var models = require('../../models');
var sessionStore = require('../../app').sessionStore;

module.exports = function (data, callbackToStripe) {
  if (isCanceled(data)) {

    var removeProStatus = function(customer){
      sessionStore.destroyByName(customer.user);
      return models.user.setProAccount(customer.user, false);
    };

    var sendStripe200 = callbackTostripe.bind(null, null);

    models.customer.setActive(data.customer, false)
      .then(removeProStatus)
      //.then(removeTeamStatus)
      .then(sendStripe200)
      .catch(callbackToStripe);

  } else {
    callbackToStripe(null);
  }
};

function isCanceled(obj) {
  return obj.status ? obj.status === 'canceled' : isCanceled(obj.data || obj.object);
}
<|endoftext|>


<commit_before>const ActionWindow = require('../actionwindow.js');

class DynastyActionWindow extends ActionWindow {
    constructor(game) {
        super(game, 'Play cards from provinces', 'dynasty');
    }

    activePrompt() {
        let props = super.activePrompt();
        return {
            menuTitle: 'Click pass when done',
            buttons: props.buttons,
            promptTitle: this.title
        };
    }

    pass() {
        this.currentPlayer.passDynasty();
        if(!this.currentPlayer.opponent || !this.currentPlayer.opponent.passedDynasty) {
            this.game.addMessage('{0} is the first to pass, and gains 1 fate', this.currentPlayer);
            this.game.raiseEvent('onFirstPassDuringDynasty', { player: this.currentPlayer }, event => this.game.addFate(event.player, 1));
        } else {
            this.game.addMessage('{0} passes', this.currentPlayer);
        }
        if(!this.currentPlayer.opponent || this.currentPlayer.opponent.passedDynasty) {
           this.complete();
        } else {
            this.nextPlayer();
        }
    }

    nextPlayer() {
        let otherPlayer = this.currentPlayer.opponent;
        if(otherPlayer && !otherPlayer.passedDynasty) {
            this.currentPlayer = otherPlayer;
        }
    }
}

module.exports = DynastyActionWindow;
<commit_msg>lint fix<commit_after>const ActionWindow = require('../actionwindow.js');

class DynastyActionWindow extends ActionWindow {
    constructor(game) {
        super(game, 'Play cards from provinces', 'dynasty');
    }

    activePrompt() {
        let props = super.activePrompt();
        return {
            menuTitle: 'Click pass when done',
            buttons: props.buttons,
            promptTitle: this.title
        };
    }

    pass() {
        this.currentPlayer.passDynasty();
        if(!this.currentPlayer.opponent || !this.currentPlayer.opponent.passedDynasty) {
            this.game.addMessage('{0} is the first to pass, and gains 1 fate', this.currentPlayer);
            this.game.raiseEvent('onFirstPassDuringDynasty', { player: this.currentPlayer }, event => this.game.addFate(event.player, 1));
        } else {
            this.game.addMessage('{0} passes', this.currentPlayer);
        }
        if(!this.currentPlayer.opponent || this.currentPlayer.opponent.passedDynasty) {
            this.complete();
        } else {
            this.nextPlayer();
        }
    }

    nextPlayer() {
        let otherPlayer = this.currentPlayer.opponent;
        if(otherPlayer && !otherPlayer.passedDynasty) {
            this.currentPlayer = otherPlayer;
        }
    }
}

module.exports = DynastyActionWindow;
<|endoftext|>


<commit_before>Clazz.load (["java.io.Serializable"], "java.lang.Number", null, function () {
java.lang.Number = Number;
if (Clazz.supportsNativeObject) {
	for (var i = 0; i < Clazz.extendedObjectMethods.length; i++) {
		var p = Clazz.extendedObjectMethods[i];
		Number.prototype[p] = JavaObject.prototype[p];
	}
}
//Clazz.decorateAsType (Number, "Number", null, java.io.Serializable, null, true);
Number.__CLASS_NAME__ = "Number";
Clazz.implementOf (Number, java.io.Serializable);
Number.equals = Clazz.innerFunctions.equals;
Number.getName = Clazz.innerFunctions.getName;

Number.serialVersionUID = Number.prototype.serialVersionUID = -8742448824652078965;

Clazz.defineMethod (Number, "shortValue",
function () {
return Math.round (this) & 0xffff;
});

Clazz.defineMethod (Number, "byteValue",
function () {
return Math.round (this) & 0xff;
});

Clazz.defineMethod (Number, "intValue",
function () {
return Math.round (this) & 0xffffffff;
});

Clazz.defineMethod (Number, "longValue",
function () {
return Math.round (this);
});

Clazz.defineMethod (Number, "floatValue",
function () {
return this.valueOf();
});

Clazz.defineMethod (Number, "doubleValue",
function () {
return this.valueOf();
});

//sgurin : added this because if not, a native number in native code will print as [Object Number] instead printing the number value...
Clazz.defineMethod (Number, "toString",
function () {
return this.valueOf()+"";
});

Clazz.defineMethod (Number, "hashCode",
function () {
return this.valueOf ();
});
});
<commit_msg>make sure the method toString of Number in javascript work well<commit_after>Clazz.load (["java.io.Serializable"], "java.lang.Number", null, function () {
java.lang.Number = Number;
if (Clazz.supportsNativeObject) {
	for (var i = 0; i < Clazz.extendedObjectMethods.length; i++) {
		var p = Clazz.extendedObjectMethods[i];
		Number.prototype[p] = JavaObject.prototype[p];
	}
}
//Clazz.decorateAsType (Number, "Number", null, java.io.Serializable, null, true);
Number.__CLASS_NAME__ = "Number";
Clazz.implementOf (Number, java.io.Serializable);
Number.equals = Clazz.innerFunctions.equals;
Number.getName = Clazz.innerFunctions.getName;

Number.serialVersionUID = Number.prototype.serialVersionUID = -8742448824652078965;

Clazz.defineMethod (Number, "shortValue",
function () {
return Math.round (this) & 0xffff;
});

Clazz.defineMethod (Number, "byteValue",
function () {
return Math.round (this) & 0xff;
});

Clazz.defineMethod (Number, "intValue",
function () {
return Math.round (this) & 0xffffffff;
});

Clazz.defineMethod (Number, "longValue",
function () {
return Math.round (this);
});

Clazz.defineMethod (Number, "floatValue",
function () {
return this.valueOf();
});

Clazz.defineMethod (Number, "doubleValue",
function () {
return this.valueOf();
});
/*
* this method will be override the original toString of Number in javascript.
* lead to method toString(radix) of Number in javascript doesn't work.
* so need remove it keeps the method in javascript is ok.
*/
//sgurin : added this because if not, a native number in native code will print as [Object Number] instead printing the number value...
/*Clazz.defineMethod (Number, "toString",
function () {
return this.valueOf()+"";
});*/

Clazz.defineMethod (Number, "hashCode",
function () {
return this.valueOf ();
});
});
<|endoftext|>


<commit_before>define( [
            'dojo/_base/declare',
            'dojo/_base/lang',
            'JBrowse/Model/Range',
            'jszlib/inflate',
            'jszlib/arrayCopy'
        ],
        function( declare, dlang, Range, inflate, arrayCopy ) {

var dlog = function(){ console.log.apply(console, arguments); };

var gettable = declare( null, {
    get: function(name) {
        return this[ { start: 'min', end: 'max', seq_id: 'segment' }[name] || name ];
    },
    tags: function() {
        return ['start','end','seq_id','score','type','source'];
    }
});
var Feature = declare( gettable, {} );
var Group = declare( gettable, {} );

var RequestWorker = declare( null,
 /**
  * @lends JBrowse.Store.BigWig.Window.RequestWorker.prototype
  */
 {

    BIG_WIG_TYPE_GRAPH: 1,
    BIG_WIG_TYPE_VSTEP: 2,
    BIG_WIG_TYPE_FSTEP: 3,

    /**
     * Worker object for reading data from a bigwig or bigbed file.
     * Manages the state necessary for traversing the index trees and
     * so forth.
     *
     * Adapted by Robert Buels from bigwig.js in the Dalliance Genome
     * Explorer by Thomas Down.
     * @constructs
     */
    constructor: function( window, chr, min, max, callback, errorCallback ) {
        this.window = window;
        this.source = window.bwg.name || undefined;

        this.blocksToFetch = [];
        this.outstanding = 0;

        this.chr = chr;
        this.min = min;
        this.max = max;
        this.callback = callback;
        this.errorCallback = errorCallback || function(e) { console.error( e, e.stack, arguments.caller ); };
    },

    cirFobRecur: function(offset, level) {
        this.outstanding += offset.length;

        var maxCirBlockSpan = 4 +  (this.window.cirBlockSize * 32);   // Upper bound on size, based on a completely full leaf node.
        var spans;
        for (var i = 0; i < offset.length; ++i) {
            var blockSpan = new Range(offset[i], Math.min(offset[i] + maxCirBlockSpan, this.window.cirTreeOffset + this.window.cirTreeLength));
            spans = spans ? spans.union( blockSpan ) : blockSpan;
        }

        var fetchRanges = spans.ranges();
        //dlog('fetchRanges: ' + fetchRanges);
        for (var r = 0; r < fetchRanges.length; ++r) {
            var fr = fetchRanges[r];
            this.cirFobStartFetch(offset, fr, level);
        }
    },

    cirFobStartFetch: function(offset, fr, level, attempts) {
        var length = fr.max() - fr.min();
        //dlog('fetching ' + fr.min() + '-' + fr.max() + ' (' + (fr.max() - fr.min()) + ')');
        //console.log('cirfobstartfetch');
        this.window.bwg.data
            .slice(fr.min(), fr.max() - fr.min())
            .fetch( dlang.hitch( this,function(resultBuffer) {
                                     for (var i = 0; i < offset.length; ++i) {
                                         if (fr.contains(offset[i])) {
                                             this.cirFobRecur2(resultBuffer, offset[i] - fr.min(), level);
                                             --this.outstanding;
                                             if (this.outstanding == 0) {
                                                 this.cirCompleted();
                                             }
                                         }
                                     }
                                 }), this.errorCallback );
    },

    cirFobRecur2: function(cirBlockData, offset, level) {
        var ba = new Int8Array(cirBlockData);
        var sa = new Int16Array(cirBlockData);
        var la = new Int32Array(cirBlockData);

        var isLeaf = ba[offset];
        var cnt = sa[offset/2 + 1];
        // dlog('cir level=' + level + '; cnt=' + cnt);
        offset += 4;

        if (isLeaf != 0) {
            for (var i = 0; i < cnt; ++i) {
                var lo = offset/4;
                var startChrom = la[lo];
                var startBase = la[lo + 1];
                var endChrom = la[lo + 2];
                var endBase = la[lo + 3];
                var blockOffset = (la[lo + 4]<<32) | (la[lo + 5]);
                var blockSize = (la[lo + 6]<<32) | (la[lo + 7]);
                if ((startChrom < this.chr || (startChrom == this.chr && startBase <= this.max)) &&
                    (endChrom   > this.chr || (endChrom == this.chr && endBase >= this.min)))
                {
                    // dlog('Got an interesting block: startBase=' + startBase + '; endBase=' + endBase + '; offset=' + blockOffset + '; size=' + blockSize);
                    this.blocksToFetch.push({offset: blockOffset, size: blockSize});
                }
                offset += 32;
            }
        } else {
            var recurOffsets = [];
            for (var i = 0; i < cnt; ++i) {
                var lo = offset/4;
                var startChrom = la[lo];
                var startBase = la[lo + 1];
                var endChrom = la[lo + 2];
                var endBase = la[lo + 3];
                var blockOffset = (la[lo + 4]<<32) | (la[lo + 5]);
                if ((startChrom < this.chr || (startChrom == this.chr && startBase <= this.max)) &&
                    (endChrom   > this.chr || (endChrom == this.chr && endBase >= this.min)))
                {
                    recurOffsets.push(blockOffset);
                }
                offset += 24;
            }
            if (recurOffsets.length > 0) {
                this.cirFobRecur(recurOffsets, level + 1);
            }
        }
    },

    cirCompleted: function() {
        this.blocksToFetch.sort(function(b0, b1) {
                               return (b0.offset|0) - (b1.offset|0);
                           });

        if (this.blocksToFetch.length == 0) {
            this.callback([]);
        } else {
            this.features = [];
            this.tramp();
        }
    },

    createFeature: function(fmin, fmax, opts) {
        // dlog('createFeature(' + fmin +', ' + fmax + ')');

        if (!opts) {
            opts = {};
        }

        var f = new Feature();
        f.segment = (this.window.bwg.refsByNumber[this.chr]||{}).name;
        f.min = fmin;
        f.max = fmax;
        f.type = 'remark';
        f.source = this.source;
        f.parent = function(){ return undefined; }

        for (k in opts) {
            f[k] = opts[k];
        }

        this.features.push(f);
    },
    maybeCreateFeature: function(fmin, fmax, opts) {
        if (fmin <= this.max && fmax >= this.min) {
            this.createFeature( fmin, fmax, opts );
        }
    },
    tramp: function() {
        if (this.blocksToFetch.length == 0) {
            //var afterBWG = new Date();
            // dlog('BWG fetch took ' + (afterBWG - beforeBWG) + 'ms');
            this.callback( this.features );
            return;  // just in case...
        } else {
            var block = this.blocksToFetch[0];
            if (block.data) {
                var ba = new Uint8Array(block.data);

                if (this.window.isSummary) {
                    var sa = new Int16Array(block.data);
                    var la = new Int32Array(block.data);
                    var fa = new Float32Array(block.data);

                    var itemCount = block.data.byteLength/32;
                    for (var i = 0; i < itemCount; ++i) {
                        var chromId =   la[(i*8)];
                        var start =     la[(i*8)+1];
                        var end =       la[(i*8)+2];
                        var validCnt =  la[(i*8)+3];
                        var minVal    = fa[(i*8)+4];
                        var maxVal    = fa[(i*8)+5];
                        var sumData   = fa[(i*8)+6];
                        var sumSqData = fa[(i*8)+7];

                        if (chromId == this.chr) {
                            var summaryOpts = {score: sumData/validCnt};
                            if (this.window.bwg.type == 'bigbed') {
                                summaryOpts.type = 'density';
                            }
                            this.maybeCreateFeature( start, end, summaryOpts);
                        }
                    }
                } else if (this.window.bwg.type == 'bigwig') {
                    var sa = new Int16Array(block.data);
                    var la = new Int32Array(block.data);
                    var fa = new Float32Array(block.data);

                    var chromId = la[0];
                    var blockStart = la[1];
                    var blockEnd = la[2];
                    var itemStep = la[3];
                    var itemSpan = la[4];
                    var blockType = ba[20];
                    var itemCount = sa[11];

                    // dlog('processing bigwig block, type=' + blockType + '; count=' + itemCount);

                    if (blockType == this.BIG_WIG_TYPE_FSTEP) {
                        for (var i = 0; i < itemCount; ++i) {
                            var score = fa[i + 6];
                            this.maybeCreateFeature( blockStart + (i*itemStep), blockStart + (i*itemStep) + itemSpan, {score: score});
                        }
                    } else if (blockType == this.BIG_WIG_TYPE_VSTEP) {
                        for (var i = 0; i < itemCount; ++i) {
                            var start = la[(i*2) + 6];
                            var score = fa[(i*2) + 7];
                            this.maybeCreateFeature( start, start + itemSpan, {score: score});
                        }
                    } else if (blockType == this.BIG_WIG_TYPE_GRAPH) {
                        for (var i = 0; i < itemCount; ++i) {
                            var start = la[(i*3) + 6];
                            var end   = la[(i*3) + 7];
                            var score = fa[(i*3) + 8];
                            if (start > end) {
                                start = end;
                            }
                            this.maybeCreateFeature( start, end, {score: score});
                        }
                    } else {
                        dlog('Currently not handling bwgType=' + blockType);
                    }
                } else if (this.window.bwg.type == 'bigbed') {
                    var offset = 0;
                    while (offset < ba.length) {
                        var chromId = (ba[offset+3]<<24) | (ba[offset+2]<<16) | (ba[offset+1]<<8) | (ba[offset+0]);
                        var start = (ba[offset+7]<<24) | (ba[offset+6]<<16) | (ba[offset+5]<<8) | (ba[offset+4]);
                        var end = (ba[offset+11]<<24) | (ba[offset+10]<<16) | (ba[offset+9]<<8) | (ba[offset+8]);
                        offset += 12;
                        var rest = '';
                        while (true) {
                            var ch = ba[offset++];
                            if (ch != 0) {
                                rest += String.fromCharCode(ch);
                            } else {
                                break;
                            }
                        }

                        var featureOpts = {};

                        var bedColumns = rest.split('\t');
                        if (bedColumns.length > 0) {
                            featureOpts.label = bedColumns[0];
                        }
                        if (bedColumns.length > 1) {
                            featureOpts.score = stringToInt(bedColumns[1]);
                        }
                        if (bedColumns.length > 2) {
                            featureOpts.orientation = bedColumns[2];
                        }
                        if (bedColumns.length > 5) {
                            var color = bedColumns[5];
                            if (this.window.BED_COLOR_REGEXP.test(color)) {
                                featureOpts.override_color = 'rgb(' + color + ')';
                            }
                        }

                        if (bedColumns.length < 9) {
                            if (chromId == this.chr) {
                                this.maybeCreateFeature( start, end, featureOpts);
                            }
                        } else if (chromId == this.chr && start <= this.max && end >= this.min) {
                            // Complex-BED?
                            // FIXME this is currently a bit of a hack to do Clever Things with ensGene.bb

                            var thickStart = bedColumns[3]|0;
                            var thickEnd   = bedColumns[4]|0;
                            var blockCount = bedColumns[6]|0;
                            var blockSizes = bedColumns[7].split(',');
                            var blockStarts = bedColumns[8].split(',');

                            featureOpts.type = 'bb-transcript';
                            var grp = new Group();
                            grp.id = bedColumns[0];
                            grp.type = 'bb-transcript';
                            grp.notes = [];
                            featureOpts.groups = [grp];

                            if (bedColumns.length > 10) {
                                var geneId = bedColumns[9];
                                var geneName = bedColumns[10];
                                var gg = new Group();
                                gg.id = geneId;
                                gg.label = geneName;
                                gg.type = 'gene';
                                featureOpts.groups.push(gg);
                            }

                            var spans = null;
                            for (var b = 0; b < blockCount; ++b) {
                                var bmin = (blockStarts[b]|0) + start;
                                var bmax = bmin + (blockSizes[b]|0);
                                var span = new Range(bmin, bmax);
                                if (spans) {
                                    spans = spans.union( span );
                                } else {
                                    spans = span;
                                }
                            }

                            var tsList = spans.ranges();
                            for (var s = 0; s < tsList.length; ++s) {
                                var ts = tsList[s];
                                this.createFeature( ts.min(), ts.max(), featureOpts);
                            }

                            if (thickEnd > thickStart) {
                                var tl = spans.intersection( new Range(thickStart, thickEnd) );
                                if (tl) {
                                    featureOpts.type = 'bb-translation';
                                    var tlList = tl.ranges();
                                    for (var s = 0; s < tlList.length; ++s) {
                                        var ts = tlList[s];
                                        this.createFeature( ts.min(), ts.max(), featureOpts);
                                    }
                                }
                            }
                        }
                    }
                } else {
                    dlog("Don't know what to do with " + this.window.bwg.type);
                }
                this.blocksToFetch.splice(0, 1);
                this.tramp();
            } else {
                var fetchStart = block.offset;
                var fetchSize = block.size;
                var bi = 1;
                while (bi < this.blocksToFetch.length && this.blocksToFetch[bi].offset == (fetchStart + fetchSize)) {
                    fetchSize += this.blocksToFetch[bi].size;
                    ++bi;
                }

                //dlog('other thing');
                this.window.bwg.data
                    .slice(fetchStart, fetchSize)
                    .fetch(dlang.hitch( this, function(result) {
                                            var offset = 0;
                                            var bi = 0;
                                            while (offset < fetchSize) {
                                                var fb = this.blocksToFetch[bi];

                                                var data;
                                                if (this.window.bwg.uncompressBufSize > 0) {
                                                    // var beforeInf = new Date();
                                                    data = inflate(result, offset + 2, fb.size - 2);
                                                    // var afterInf = new Date();
                                                    // dlog('inflate: ' + (afterInf - beforeInf) + 'ms');
                                                } else {
                                                    var tmp = new Uint8Array(fb.size);    // FIXME is this really the best we can do?
                                                    arrayCopy(new Uint8Array(result, offset, fb.size), 0, tmp, 0, fb.size);
                                                    data = tmp.buffer;
                                                }
                                                fb.data = data;

                                                offset += fb.size;
                                                ++bi;
                                            }
                                            this.tramp();
                                        }), this.errorCallback );
            }
        }
    }
});

return RequestWorker;

});<commit_msg>missing semicolon!<commit_after>define( [
            'dojo/_base/declare',
            'dojo/_base/lang',
            'JBrowse/Model/Range',
            'jszlib/inflate',
            'jszlib/arrayCopy'
        ],
        function( declare, dlang, Range, inflate, arrayCopy ) {

var dlog = function(){ console.log.apply(console, arguments); };

var gettable = declare( null, {
    get: function(name) {
        return this[ { start: 'min', end: 'max', seq_id: 'segment' }[name] || name ];
    },
    tags: function() {
        return ['start','end','seq_id','score','type','source'];
    }
});
var Feature = declare( gettable, {} );
var Group = declare( gettable, {} );

var RequestWorker = declare( null,
 /**
  * @lends JBrowse.Store.BigWig.Window.RequestWorker.prototype
  */
 {

    BIG_WIG_TYPE_GRAPH: 1,
    BIG_WIG_TYPE_VSTEP: 2,
    BIG_WIG_TYPE_FSTEP: 3,

    /**
     * Worker object for reading data from a bigwig or bigbed file.
     * Manages the state necessary for traversing the index trees and
     * so forth.
     *
     * Adapted by Robert Buels from bigwig.js in the Dalliance Genome
     * Explorer by Thomas Down.
     * @constructs
     */
    constructor: function( window, chr, min, max, callback, errorCallback ) {
        this.window = window;
        this.source = window.bwg.name || undefined;

        this.blocksToFetch = [];
        this.outstanding = 0;

        this.chr = chr;
        this.min = min;
        this.max = max;
        this.callback = callback;
        this.errorCallback = errorCallback || function(e) { console.error( e, e.stack, arguments.caller ); };
    },

    cirFobRecur: function(offset, level) {
        this.outstanding += offset.length;

        var maxCirBlockSpan = 4 +  (this.window.cirBlockSize * 32);   // Upper bound on size, based on a completely full leaf node.
        var spans;
        for (var i = 0; i < offset.length; ++i) {
            var blockSpan = new Range(offset[i], Math.min(offset[i] + maxCirBlockSpan, this.window.cirTreeOffset + this.window.cirTreeLength));
            spans = spans ? spans.union( blockSpan ) : blockSpan;
        }

        var fetchRanges = spans.ranges();
        //dlog('fetchRanges: ' + fetchRanges);
        for (var r = 0; r < fetchRanges.length; ++r) {
            var fr = fetchRanges[r];
            this.cirFobStartFetch(offset, fr, level);
        }
    },

    cirFobStartFetch: function(offset, fr, level, attempts) {
        var length = fr.max() - fr.min();
        //dlog('fetching ' + fr.min() + '-' + fr.max() + ' (' + (fr.max() - fr.min()) + ')');
        //console.log('cirfobstartfetch');
        this.window.bwg.data
            .slice(fr.min(), fr.max() - fr.min())
            .fetch( dlang.hitch( this,function(resultBuffer) {
                                     for (var i = 0; i < offset.length; ++i) {
                                         if (fr.contains(offset[i])) {
                                             this.cirFobRecur2(resultBuffer, offset[i] - fr.min(), level);
                                             --this.outstanding;
                                             if (this.outstanding == 0) {
                                                 this.cirCompleted();
                                             }
                                         }
                                     }
                                 }), this.errorCallback );
    },

    cirFobRecur2: function(cirBlockData, offset, level) {
        var ba = new Int8Array(cirBlockData);
        var sa = new Int16Array(cirBlockData);
        var la = new Int32Array(cirBlockData);

        var isLeaf = ba[offset];
        var cnt = sa[offset/2 + 1];
        // dlog('cir level=' + level + '; cnt=' + cnt);
        offset += 4;

        if (isLeaf != 0) {
            for (var i = 0; i < cnt; ++i) {
                var lo = offset/4;
                var startChrom = la[lo];
                var startBase = la[lo + 1];
                var endChrom = la[lo + 2];
                var endBase = la[lo + 3];
                var blockOffset = (la[lo + 4]<<32) | (la[lo + 5]);
                var blockSize = (la[lo + 6]<<32) | (la[lo + 7]);
                if ((startChrom < this.chr || (startChrom == this.chr && startBase <= this.max)) &&
                    (endChrom   > this.chr || (endChrom == this.chr && endBase >= this.min)))
                {
                    // dlog('Got an interesting block: startBase=' + startBase + '; endBase=' + endBase + '; offset=' + blockOffset + '; size=' + blockSize);
                    this.blocksToFetch.push({offset: blockOffset, size: blockSize});
                }
                offset += 32;
            }
        } else {
            var recurOffsets = [];
            for (var i = 0; i < cnt; ++i) {
                var lo = offset/4;
                var startChrom = la[lo];
                var startBase = la[lo + 1];
                var endChrom = la[lo + 2];
                var endBase = la[lo + 3];
                var blockOffset = (la[lo + 4]<<32) | (la[lo + 5]);
                if ((startChrom < this.chr || (startChrom == this.chr && startBase <= this.max)) &&
                    (endChrom   > this.chr || (endChrom == this.chr && endBase >= this.min)))
                {
                    recurOffsets.push(blockOffset);
                }
                offset += 24;
            }
            if (recurOffsets.length > 0) {
                this.cirFobRecur(recurOffsets, level + 1);
            }
        }
    },

    cirCompleted: function() {
        this.blocksToFetch.sort(function(b0, b1) {
                               return (b0.offset|0) - (b1.offset|0);
                           });

        if (this.blocksToFetch.length == 0) {
            this.callback([]);
        } else {
            this.features = [];
            this.tramp();
        }
    },

    createFeature: function(fmin, fmax, opts) {
        // dlog('createFeature(' + fmin +', ' + fmax + ')');

        if (!opts) {
            opts = {};
        }

        var f = new Feature();
        f.segment = (this.window.bwg.refsByNumber[this.chr]||{}).name;
        f.min = fmin;
        f.max = fmax;
        f.type = 'remark';
        f.source = this.source;
        f.parent = function(){ return undefined; };

        for (k in opts) {
            f[k] = opts[k];
        }

        this.features.push(f);
    },
    maybeCreateFeature: function(fmin, fmax, opts) {
        if (fmin <= this.max && fmax >= this.min) {
            this.createFeature( fmin, fmax, opts );
        }
    },
    tramp: function() {
        if (this.blocksToFetch.length == 0) {
            //var afterBWG = new Date();
            // dlog('BWG fetch took ' + (afterBWG - beforeBWG) + 'ms');
            this.callback( this.features );
            return;  // just in case...
        } else {
            var block = this.blocksToFetch[0];
            if (block.data) {
                var ba = new Uint8Array(block.data);

                if (this.window.isSummary) {
                    var sa = new Int16Array(block.data);
                    var la = new Int32Array(block.data);
                    var fa = new Float32Array(block.data);

                    var itemCount = block.data.byteLength/32;
                    for (var i = 0; i < itemCount; ++i) {
                        var chromId =   la[(i*8)];
                        var start =     la[(i*8)+1];
                        var end =       la[(i*8)+2];
                        var validCnt =  la[(i*8)+3];
                        var minVal    = fa[(i*8)+4];
                        var maxVal    = fa[(i*8)+5];
                        var sumData   = fa[(i*8)+6];
                        var sumSqData = fa[(i*8)+7];

                        if (chromId == this.chr) {
                            var summaryOpts = {score: sumData/validCnt};
                            if (this.window.bwg.type == 'bigbed') {
                                summaryOpts.type = 'density';
                            }
                            this.maybeCreateFeature( start, end, summaryOpts);
                        }
                    }
                } else if (this.window.bwg.type == 'bigwig') {
                    var sa = new Int16Array(block.data);
                    var la = new Int32Array(block.data);
                    var fa = new Float32Array(block.data);

                    var chromId = la[0];
                    var blockStart = la[1];
                    var blockEnd = la[2];
                    var itemStep = la[3];
                    var itemSpan = la[4];
                    var blockType = ba[20];
                    var itemCount = sa[11];

                    // dlog('processing bigwig block, type=' + blockType + '; count=' + itemCount);

                    if (blockType == this.BIG_WIG_TYPE_FSTEP) {
                        for (var i = 0; i < itemCount; ++i) {
                            var score = fa[i + 6];
                            this.maybeCreateFeature( blockStart + (i*itemStep), blockStart + (i*itemStep) + itemSpan, {score: score});
                        }
                    } else if (blockType == this.BIG_WIG_TYPE_VSTEP) {
                        for (var i = 0; i < itemCount; ++i) {
                            var start = la[(i*2) + 6];
                            var score = fa[(i*2) + 7];
                            this.maybeCreateFeature( start, start + itemSpan, {score: score});
                        }
                    } else if (blockType == this.BIG_WIG_TYPE_GRAPH) {
                        for (var i = 0; i < itemCount; ++i) {
                            var start = la[(i*3) + 6];
                            var end   = la[(i*3) + 7];
                            var score = fa[(i*3) + 8];
                            if (start > end) {
                                start = end;
                            }
                            this.maybeCreateFeature( start, end, {score: score});
                        }
                    } else {
                        dlog('Currently not handling bwgType=' + blockType);
                    }
                } else if (this.window.bwg.type == 'bigbed') {
                    var offset = 0;
                    while (offset < ba.length) {
                        var chromId = (ba[offset+3]<<24) | (ba[offset+2]<<16) | (ba[offset+1]<<8) | (ba[offset+0]);
                        var start = (ba[offset+7]<<24) | (ba[offset+6]<<16) | (ba[offset+5]<<8) | (ba[offset+4]);
                        var end = (ba[offset+11]<<24) | (ba[offset+10]<<16) | (ba[offset+9]<<8) | (ba[offset+8]);
                        offset += 12;
                        var rest = '';
                        while (true) {
                            var ch = ba[offset++];
                            if (ch != 0) {
                                rest += String.fromCharCode(ch);
                            } else {
                                break;
                            }
                        }

                        var featureOpts = {};

                        var bedColumns = rest.split('\t');
                        if (bedColumns.length > 0) {
                            featureOpts.label = bedColumns[0];
                        }
                        if (bedColumns.length > 1) {
                            featureOpts.score = stringToInt(bedColumns[1]);
                        }
                        if (bedColumns.length > 2) {
                            featureOpts.orientation = bedColumns[2];
                        }
                        if (bedColumns.length > 5) {
                            var color = bedColumns[5];
                            if (this.window.BED_COLOR_REGEXP.test(color)) {
                                featureOpts.override_color = 'rgb(' + color + ')';
                            }
                        }

                        if (bedColumns.length < 9) {
                            if (chromId == this.chr) {
                                this.maybeCreateFeature( start, end, featureOpts);
                            }
                        } else if (chromId == this.chr && start <= this.max && end >= this.min) {
                            // Complex-BED?
                            // FIXME this is currently a bit of a hack to do Clever Things with ensGene.bb

                            var thickStart = bedColumns[3]|0;
                            var thickEnd   = bedColumns[4]|0;
                            var blockCount = bedColumns[6]|0;
                            var blockSizes = bedColumns[7].split(',');
                            var blockStarts = bedColumns[8].split(',');

                            featureOpts.type = 'bb-transcript';
                            var grp = new Group();
                            grp.id = bedColumns[0];
                            grp.type = 'bb-transcript';
                            grp.notes = [];
                            featureOpts.groups = [grp];

                            if (bedColumns.length > 10) {
                                var geneId = bedColumns[9];
                                var geneName = bedColumns[10];
                                var gg = new Group();
                                gg.id = geneId;
                                gg.label = geneName;
                                gg.type = 'gene';
                                featureOpts.groups.push(gg);
                            }

                            var spans = null;
                            for (var b = 0; b < blockCount; ++b) {
                                var bmin = (blockStarts[b]|0) + start;
                                var bmax = bmin + (blockSizes[b]|0);
                                var span = new Range(bmin, bmax);
                                if (spans) {
                                    spans = spans.union( span );
                                } else {
                                    spans = span;
                                }
                            }

                            var tsList = spans.ranges();
                            for (var s = 0; s < tsList.length; ++s) {
                                var ts = tsList[s];
                                this.createFeature( ts.min(), ts.max(), featureOpts);
                            }

                            if (thickEnd > thickStart) {
                                var tl = spans.intersection( new Range(thickStart, thickEnd) );
                                if (tl) {
                                    featureOpts.type = 'bb-translation';
                                    var tlList = tl.ranges();
                                    for (var s = 0; s < tlList.length; ++s) {
                                        var ts = tlList[s];
                                        this.createFeature( ts.min(), ts.max(), featureOpts);
                                    }
                                }
                            }
                        }
                    }
                } else {
                    dlog("Don't know what to do with " + this.window.bwg.type);
                }
                this.blocksToFetch.splice(0, 1);
                this.tramp();
            } else {
                var fetchStart = block.offset;
                var fetchSize = block.size;
                var bi = 1;
                while (bi < this.blocksToFetch.length && this.blocksToFetch[bi].offset == (fetchStart + fetchSize)) {
                    fetchSize += this.blocksToFetch[bi].size;
                    ++bi;
                }

                //dlog('other thing');
                this.window.bwg.data
                    .slice(fetchStart, fetchSize)
                    .fetch(dlang.hitch( this, function(result) {
                                            var offset = 0;
                                            var bi = 0;
                                            while (offset < fetchSize) {
                                                var fb = this.blocksToFetch[bi];

                                                var data;
                                                if (this.window.bwg.uncompressBufSize > 0) {
                                                    // var beforeInf = new Date();
                                                    data = inflate(result, offset + 2, fb.size - 2);
                                                    // var afterInf = new Date();
                                                    // dlog('inflate: ' + (afterInf - beforeInf) + 'ms');
                                                } else {
                                                    var tmp = new Uint8Array(fb.size);    // FIXME is this really the best we can do?
                                                    arrayCopy(new Uint8Array(result, offset, fb.size), 0, tmp, 0, fb.size);
                                                    data = tmp.buffer;
                                                }
                                                fb.data = data;

                                                offset += fb.size;
                                                ++bi;
                                            }
                                            this.tramp();
                                        }), this.errorCallback );
            }
        }
    }
});

return RequestWorker;

});<|endoftext|>