<commit_before>const VinylFile = require('vinyl');
const fs = require('fs-extra');
const yaml = require('js-yaml');

const JEKYLL_README_PREFIX = '<!--docs:'
const FRONT_MATTER_DELIMITER = '---';
const FRONT_MATTER_PATTERN = /^(---|<!--docs:)([^]*?)^(---|-->)/m;

/**
 * The set of extensions to the Vinyl file interface.
 */
const BUILT_IN_PROPS = new Set([
  'isValidJekyll',
  'jekyllMetadata_',
  'jekyllMetadata',
  'shouldBecomeIndex',
  'stringContents',
]);

/**
 * A grab bag of convenience extensions to vinyl files for working with Jekyll.
 */
class JekyllFile extends VinylFile {
  constructor(fileInfo) {
    super(fileInfo);
  }

  /**
   * @return {string} The contents of this file as a string.
   */
  get stringContents() {
    return this.contents.toString();
  }

  /**
   * Sets the contents of the file from a string.
   */
  set stringContents(value) {
    this.contents = Buffer.from(value);
  }

  /**
   * @return {Object}
   */
  get jekyllMetadata() {
    if (!this.isValidJekyll) {
      return null;
    } else if (!this.jekyllMetadata_) {
      this.jekyllMetadata_ = this.parseMetadata_();
    }

    return this.jekyllMetadata_;
  }

  /**
   * Sets the Jekyll Front Matter metadata.
   */
  set jekyllMetadata(metadata) {
    this.jekyllMetadata_ = metadata;

    const { stringContents } = this;
    const metadataYaml = yaml.safeDump(metadata);
    if (!this.isValidJekyll) {
      this.stringContents = `---\n${metadataYaml}\n---\n${stringContents}`;
    } else {
      this.stringContents = stringContents.replace(FRONT_MATTER_PATTERN, `$1\n${metadataYaml}$3`);
    }
  }

  /**
   * @return {boolean} Whether this file begins with Front Matter metadata,
   *     which indicates that it should be processed by Jekyll.
   */
  get isValidJekyll() {
    const { stringContents } = this;
    return stringContents.startsWith(JEKYLL_README_PREFIX) ||
           stringContents.startsWith(FRONT_MATTER_DELIMITER);
  }

  /**
   * @return {boolean} Whether the file is intended to be used as index.html for
   *     its directory.
   */
  get shouldBecomeIndex() {
    return /(site-index|README)\.md$/.test(this.basename);
  }

  /**
   * Uncomments all Liquid/HTML code that was commented out as to not appear
   * in Github.
   */
  uncommentHiddenCode() {
    let { stringContents } = this;
    if (stringContents.includes(JEKYLL_README_PREFIX)) {
      stringContents = stringContents
          .replace(JEKYLL_README_PREFIX, FRONT_MATTER_DELIMITER)
          .replace(/-->/, FRONT_MATTER_DELIMITER)
    }

    this.stringContents = stringContents
        // Note that [^] matches any character including newlines, whereas "."
        // does not. For anyone who's wondering, [^] the negation of the empty
        // set.
        .replace(/<!--([{<][^]*?[>}])-->/g, '$1')
        // Rewrite links that point to markdown files to point to html files
        // instead.
        .replace(/\[([^\]]+)\]\((.*)\.md\)/g, (match, p1, p2) => {
          return /^https?:\/\//.test(p2) ? match : `[${p1}](${p2}.html)`;
        });
  }

  /**
   * Writes the file to disk, ensuring that its target directory exists.
   */
  write() {
    const { path, encoding, contents, stat: { mode } } = this;
    fs.ensureDirSync(this.dirname);
    fs.writeFileSync(path, contents, {
      encoding,
      mode,
    });
  }

  /**
   * Parses Front Matter (YAML) metadata out of the file header.
   */
  parseMetadata_() {
    const metadataMatch = this.stringContents.match(FRONT_MATTER_PATTERN);
    return metadataMatch && yaml.safeLoad(metadataMatch[2]);
  }

  /**
   * Reads the file at path, and constructs a new JekyllFile instance with its
   * contents.
   */
  static readFromPath(filePath, base, encoding='utf8') {
    return new JekyllFile({
      path: filePath,
      base,
      encoding,
      stat: fs.lstatSync(filePath),
      contents: fs.readFileSync(filePath),
    });
  }

  /**
   * Required by Vinyl subclasses.
   */
  static isCustomProp(name) {
    return super.isCustomProp(name) && !BUILT_IN_PROPS.has(name);
  }
}

module.exports = {
  JekyllFile,
};
<commit_msg>Introduces custom list item styling syntax.<commit_after>const VinylFile = require('vinyl');
const fs = require('fs-extra');
const yaml = require('js-yaml');

const JEKYLL_README_PREFIX = '<!--docs:'
const FRONT_MATTER_DELIMITER = '---';
const FRONT_MATTER_PATTERN = /^(---|<!--docs:)([^]*?)^(---|-->)/m;

/**
 * The set of extensions to the Vinyl file interface.
 */
const BUILT_IN_PROPS = new Set([
  'isValidJekyll',
  'jekyllMetadata_',
  'jekyllMetadata',
  'shouldBecomeIndex',
  'stringContents',
]);

/**
 * A grab bag of convenience extensions to vinyl files for working with Jekyll.
 */
class JekyllFile extends VinylFile {
  constructor(fileInfo) {
    super(fileInfo);
  }

  /**
   * @return {string} The contents of this file as a string.
   */
  get stringContents() {
    return this.contents.toString();
  }

  /**
   * Sets the contents of the file from a string.
   */
  set stringContents(value) {
    this.contents = Buffer.from(value);
  }

  /**
   * @return {Object}
   */
  get jekyllMetadata() {
    if (!this.isValidJekyll) {
      return null;
    } else if (!this.jekyllMetadata_) {
      this.jekyllMetadata_ = this.parseMetadata_();
    }

    return this.jekyllMetadata_;
  }

  /**
   * Sets the Jekyll Front Matter metadata.
   */
  set jekyllMetadata(metadata) {
    this.jekyllMetadata_ = metadata;

    const { stringContents } = this;
    const metadataYaml = yaml.safeDump(metadata);
    if (!this.isValidJekyll) {
      this.stringContents = `---\n${metadataYaml}\n---\n${stringContents}`;
    } else {
      this.stringContents = stringContents.replace(FRONT_MATTER_PATTERN, `$1\n${metadataYaml}$3`);
    }
  }

  /**
   * @return {boolean} Whether this file begins with Front Matter metadata,
   *     which indicates that it should be processed by Jekyll.
   */
  get isValidJekyll() {
    const { stringContents } = this;
    return stringContents.startsWith(JEKYLL_README_PREFIX) ||
           stringContents.startsWith(FRONT_MATTER_DELIMITER);
  }

  /**
   * @return {boolean} Whether the file is intended to be used as index.html for
   *     its directory.
   */
  get shouldBecomeIndex() {
    return /(site-index|README)\.md$/.test(this.basename);
  }

  /**
   * Uncomments all Liquid/HTML code that was commented out as to not appear
   * in Github.
   */
  uncommentHiddenCode() {
    let { stringContents } = this;
    if (stringContents.includes(JEKYLL_README_PREFIX)) {
      stringContents = stringContents
          .replace(JEKYLL_README_PREFIX, FRONT_MATTER_DELIMITER)
          .replace(/-->/, FRONT_MATTER_DELIMITER)
    }

    this.stringContents = stringContents
        // Uncomment liquid tags and HTML.
        //
        // Note that [^] matches any character including newlines, whereas "."
        // does not. For anyone who's wondering, [^] the negation of the empty
        // set.
        .replace(/<!--([{<][^]*?[>}])-->/g, '$1')
        // Move list item styling template tags into the correct position.
        //
        // Custom list item styling syntax had to be introduced so that the
        // template tags could be successfully commented out when displayed in
        // GitHub, which was not an option with the syntax supported by Jekyll.
        //
        // From:
        //     * This is a list item
        //       {: .list-item-css-class }
        // To:
        //     * {: .list-item-css-class } This is a list item
        //
        .replace(/^(\s*)([*-])(\s+)([^\n]+)\n\1\s\3({:[^}]+})/gm, '$1$2 $5 $4')
        // Rewrite links that point to markdown files to point to html files
        // instead.
        .replace(/\[([^\]]+)\]\((.*)\.md\)/g, (match, p1, p2) => {
          return /^https?:\/\//.test(p2) ? match : `[${p1}](${p2}.html)`;
        });
  }

  /**
   * Writes the file to disk, ensuring that its target directory exists.
   */
  write() {
    const { path, encoding, contents, stat: { mode } } = this;
    fs.ensureDirSync(this.dirname);
    fs.writeFileSync(path, contents, {
      encoding,
      mode,
    });
  }

  /**
   * Parses Front Matter (YAML) metadata out of the file header.
   */
  parseMetadata_() {
    const metadataMatch = this.stringContents.match(FRONT_MATTER_PATTERN);
    return metadataMatch && yaml.safeLoad(metadataMatch[2]);
  }

  /**
   * Reads the file at path, and constructs a new JekyllFile instance with its
   * contents.
   */
  static readFromPath(filePath, base, encoding='utf8') {
    return new JekyllFile({
      path: filePath,
      base,
      encoding,
      stat: fs.lstatSync(filePath),
      contents: fs.readFileSync(filePath),
    });
  }

  /**
   * Required by Vinyl subclasses.
   */
  static isCustomProp(name) {
    return super.isCustomProp(name) && !BUILT_IN_PROPS.has(name);
  }
}

module.exports = {
  JekyllFile,
};
<|endoftext|>


<commit_before>/*
 * Licensed to Cloudkick, Inc ('Cloudkick') under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * Cloudkick licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

process.chdir(__dirname);
require.paths.unshift('../lib');

var fs = require('fs');
var sys = require('sys');
var path = require('path');
var spawn = require('child_process').spawn;
var config = require('util/config');
var ps = require('util/pubsub');
var async = require('extern/async');
var sprintf = require('extern/sprintf').sprintf;

var TEST_TIMEOUT = 5 * 1000;
var MAX_BUFFER = 512 * 1024;
var EXCLUDE_DIRS = [
  'data'
];

var total = 0;
var successes = 0;
var failures = 0;

var succeeded_tests = [];
var failed_tests = [];

function equals_line(str) {
  return  "\033[34m===================="
        + "\033[31m " + str + " "
        + "\033[34m===================="
        + "\033[0m";
}

function execute_test(dir, file, callback) {
  var args = ['common.js', sprintf('./%s/%s', dir, file)];
  var child = spawn(process.execPath, args);
  var stderr = [];
  var stdout = [];
  var dead = false;
  var timed_out = false;
  var timeout_id;

  child.stderr.on('data', function(chunk) {
    stderr.push(chunk);
  });

  child.stdout.on('data', function(chunk) {
    stdout.push(chunk);
  });

  child.on('exit', function(code) {
    clearTimeout(timeout_id);
    if (code !== 0) {
      sys.puts(equals_line(sprintf("%s/%s", dir, file)));
      if (timed_out) {
        sys.puts('--- test timed out ---');
      }
      sys.puts('--- exit code: ' + code + ' ---');
      if (stderr.length > 0) {
        sys.puts('--- stderr ---');
        sys.puts(stderr.join(''));
      }
      if (stdout.length > 0) {
        sys.puts('--- stdout ---');
        sys.puts(stdout.join(''));
      }
      failures += 1;
      failed_tests.push(file);
    }
    else {
      successes += 1;
      succeeded_tests.push(file);
    }
    total += 1;
    return callback();
  });

  timeout_id = setTimeout(function() {
    timed_out = true;
    child.kill('SIGKILL');
  }, TEST_TIMEOUT);
}

function print_test_results(tests) {
  var i = 0;
  var tests_len = tests.length;

  for (i = 0; i < tests_len; i++) {
    test = tests[i];
    sys.puts(sprintf('     - %s', test));
  }
}

fs.readdir(__dirname, function(err, dirs) {
  async.forEachSeries(dirs, function(dir, callback) {
    // Skip excluded directories
    if (EXCLUDE_DIRS.indexOf(dir) !== -1) {
      return callback();
    }

    fs.readdir(dir, function(err, files) {
      // This is the dirty way to skip non-directories
      if (err) {
        return callback();
      }

      async.forEachSeries(files, function(file, callback) {
        if (!file.match(/.*\.js$/)) {
          return callback();
        }

        // Execute the test file and report any errors
        execute_test(dir, file, callback);
      }, callback);
    });
  },
  function() {
    sys.puts(equals_line("Tests Complete"));
    sys.puts(sprintf("    Successes: %d", successes));
    print_test_results(succeeded_tests);
    sys.puts(sprintf("     Failures: %d", failures));
    sys.puts("    ------------------");
    print_test_results(failed_tests);
    sys.puts("        Total: " + total);
  });
});
<commit_msg>Use terminal.puts instead of sys.puts.<commit_after>/*
 * Licensed to Cloudkick, Inc ('Cloudkick') under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * Cloudkick licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

process.chdir(__dirname);
require.paths.unshift('../lib');

var fs = require('fs');
var sys = require('sys');
var path = require('path');
var spawn = require('child_process').spawn;

var async = require('extern/async');
var sprintf = require('extern/sprintf').sprintf;

var config = require('util/config');
var ps = require('util/pubsub');
var terminal = require('util/terminal');

var TEST_TIMEOUT = 5 * 1000;
var MAX_BUFFER = 512 * 1024;
var EXCLUDE_DIRS = [
  'data'
];

var total = 0;
var successes = 0;
var failures = 0;

var succeeded_tests = [];
var failed_tests = [];

function equals_line(str) {
  return  "[blue]====================[/blue]"
        + " [red]" + str + "[/red] "
        + "[blue]====================[/blue]";
}

function execute_test(dir, file, callback) {
  var args = ['common.js', sprintf('./%s/%s', dir, file)];
  var child = spawn(process.execPath, args);
  var stderr = [];
  var stdout = [];
  var dead = false;
  var timed_out = false;
  var timeout_id;

  child.stderr.on('data', function(chunk) {
    stderr.push(chunk);
  });

  child.stdout.on('data', function(chunk) {
    stdout.push(chunk);
  });

  child.on('exit', function(code) {
    clearTimeout(timeout_id);
    if (code !== 0) {
      terminal.puts(equals_line(sprintf("%s/%s", dir, file)));
      if (timed_out) {
        terminal.puts('--- test timed out ---');
      }
      terminal.puts('--- exit code: ' + code + ' ---');
      if (stderr.length > 0) {
        terminal.puts('--- stderr ---');
        terminal.puts(stderr.join(''));
      }
      if (stdout.length > 0) {
        terminal.puts('--- stdout ---');
        terminal.puts(stdout.join(''));
      }
      failures += 1;
      failed_tests.push(file);
    }
    else {
      successes += 1;
      succeeded_tests.push(file);
    }
    total += 1;
    return callback();
  });

  timeout_id = setTimeout(function() {
    timed_out = true;
    child.kill('SIGKILL');
  }, TEST_TIMEOUT);
}

function print_test_results(tests) {
  var i = 0;
  var tests_len = tests.length;

  for (i = 0; i < tests_len; i++) {
    test = tests[i];
    terminal.puts(sprintf('     - %s', test));
  }
}

fs.readdir(__dirname, function(err, dirs) {
  async.forEachSeries(dirs, function(dir, callback) {
    // Skip excluded directories
    if (EXCLUDE_DIRS.indexOf(dir) !== -1) {
      return callback();
    }

    fs.readdir(dir, function(err, files) {
      // This is the dirty way to skip non-directories
      if (err) {
        return callback();
      }

      async.forEachSeries(files, function(file, callback) {
        if (!file.match(/.*\.js$/)) {
          return callback();
        }

        // Execute the test file and report any errors
        execute_test(dir, file, callback);
      }, callback);
    });
  },
  function() {
    terminal.puts(equals_line("Tests Complete"));
    terminal.puts(sprintf("    Successes: [green]%s[/green]", successes));
    print_test_results(succeeded_tests);
    terminal.puts(sprintf("     Failures: [red]%s[/red]", failures));
    terminal.puts("    ------------------");
    print_test_results(failed_tests);
    terminal.puts("        Total: " + total);
  });
});
<|endoftext|>


<commit_before>// Example of importer for blockly core blocks. Importer API experiment - work in progress, importer will be a class.

// List of blockly blocks, info about this importer implementation and the case in which implements.
/*
  * Logic
    - controls_if               // IMPLEMENTED -> "IfStatement"
    - logic_compare             // IMPLEMENTED -> "BinaryExpression"
    - logic_operation           // IMPLEMENTED -> "LogicalExpression"
    - logic_negate              // IMPLEMENTED -> "UnaryExpression"
    - logic_boolean             // IMPLEMENTED -> "Literal"
    - logic_null                // IMPLEMENTED -> "Literal"
    - logic_ternary             // IMPLEMENTED -> "ConditionalExpression"
  * Loops
    - controls_repeat_ext       // IMPLEMENTED -> "ForStatement" -> var handling: if initializer name starts with 'count' this block is rendered
    - controls_whileUntil       // IMPLEMENTED -> "WhileStatement"
    - controls_for              // IMPLEMENTED -> "ForStatement"
    - controls_forEach          // IMPLEMENTED -> "ForInStatement"
    - controls_flow_statements  // ...
  * Math
    - math_number               // IMPLEMENTED -> "Literal"
    - math_arithmetic           // IMPLEMENTED -> "BinaryExpression"
    - math_single
    - math_trig
    - math_constant
    - math_number_property
    - math_change
    - math_round
    - math_on_list
    - math_modulo
    - math_constrain
    - math_random_int
    - math_random_float
  * Text
    - text                      // IMPLEMENTED -> "Literal"
    - text_join
    - text_append
    - text_length
    - text_isEmpty
    - text_indexOf
    - text_charAt
    - text_getSubstring
    - text_changeCase
    - text_trim
    - text_print
    - text_prompt_ext
  * Lists
    - lists_create_empty
    - lists_create_with        // IMPLEMENTED -> "ArrayExpression"
    - lists_repeat
    - lists_length
    - lists_isEmpty
    - lists_indexOf
    - lists_getIndex
    - lists_setIndex
    - lists_getSublist
    - lists_split
  * Colour
    - colour_picker
    - colour_random
    - colour_rgb
    - colour_blend
  * Variables
    - variables_set           // IMPLEMENTED -> "VariabeDeclaration" could not generate the same code
                              // because in Blockly core not are a variable multiple initialization block.
                              // (not multiple - partially)
    - variables_get
  * Functions
*/

// first import js block generators into blockly js generator context
for (var el in Blocklify.JavaScript.Generator) {
  if (el.substring(0,3) == 'js_') {
    Blockly.JavaScript[el] = Blocklify.JavaScript.Generator[el];
  }
}

// Probably useless
/*Blockly.JavaScript.statementName = function(node) {
  if (node.type == 'Program') {
    return 'body';
  } else if (node.type == 'BlockStatement') {
    return 'body';
  }
};*/

// now the block importer
Blockly.JavaScript.importer = function(node, parent, options) {
  // this is the importer for blockly block (pattern converter)
  //the returned block
  var block = null, field;
  //none-estetic inline blocks
  var no_inline_blocks = [];
  switch (node.type) {
    case "Program":
      block = goog.dom.createDom('xml');
      Blocklify.JavaScript.importer.appendStatement(block, node.body, node, options);
      break;
    case "BlockStatement":
      block = Blocklify.JavaScript.importer.appendStatement(null, node.body, node, options);
      break;
    case "Literal":    // logic_null, math_number, text, logic_boolean
      block = goog.dom.createDom('block');
      if (node.value == null) {
        block.setAttribute('type' ,'logic_null');
      } else {
        var nodeType = typeof(node.value);
        if (nodeType == "number") {
          block.setAttribute('type' ,'math_number');
          Blocklify.JavaScript.importer.appendField(block, 'NUM', node.value + '');
        } else if(nodeType == "string") {
          block.setAttribute('type' ,'text');
          Blocklify.JavaScript.importer.appendField(block, 'TEXT', node.value);
        } else if(nodeType == "boolean") {
          block.setAttribute('type' ,'logic_boolean');
          Blocklify.JavaScript.importer.appendField(block, 'BOOL', node.raw);
        }
      }
      break;
    case "IfStatement":    // controls_if
      block = Blocklify.JavaScript.importer.createBlock('controls_if');
      var tests = [], consequents = [], current_node = node.alternate, countElseIf = 0, countElse = 0;
      tests.push(Blocklify.JavaScript.importer.convert_atomic(node.test, node, options));
      Blocklify.JavaScript.importer.setOutput(tests[0], true);
      consequents.push(Blocklify.JavaScript.importer.convert_atomic(node.consequent, node, options));
      Blocklify.JavaScript.importer.setOutput(tests[0], true);
      while (current_node) {
        if (current_node.type == 'IfStatement') {
          countElseIf++;
          tests.push(Blocklify.JavaScript.importer.convert_atomic(current_node.test, current_node, options));
          Blocklify.JavaScript.importer.setOutput(tests[tests.length-1], true);
          consequents.push(Blocklify.JavaScript.importer.convert_atomic(current_node.consequent, current_node, options));
          current_node = current_node.alternate;
        } else {
          countElse = 1;
          var alternate = Blocklify.JavaScript.importer.convert_atomic(current_node.alternate || current_node, node, options);
          current_node = null;
        }
      };
      var mutation = goog.dom.createDom('mutation');
      block.appendChild(mutation);
      mutation.setAttribute('elseif', countElseIf + '');
      mutation.setAttribute('else', countElse + '');
      Blocklify.JavaScript.importer.appendValueInput(block, 'IF0', tests[0]);
      Blocklify.JavaScript.importer.appendValueInput(block, 'DO0', consequents[0]);
      for (var i = 1; i <= countElseIf; i++) {
        Blocklify.JavaScript.importer.appendValueInput(block, 'IF' + i, tests[i]);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO' + i, consequents[i]);
      }
      if (countElse == 1) {
        Blocklify.JavaScript.importer.appendValueInput(block, 'ELSE', alternate);
      }
      break;
    case "ArrayExpression":
      block = Blocklify.JavaScript.importer.createBlock('lists_create_with');
      Blocklify.JavaScript.importer.appendCloneMutation(block, 'items', 'ADD', node.elements, node, options);
      break;
    case "WhileStatement":    // controls_whileUntil
      block = Blocklify.JavaScript.importer.createBlock('controls_whileUntil');
      if (node.test.type == 'UnaryExpression' && node.test.operator == '!') {
        mode = 'UNTIL';
        procesedTest = node.test.argument;
      } else {
        mode = 'WHILE';
        procesedTest = node.test;
      }
      Blocklify.JavaScript.importer.appendField(block, 'MODE', mode);
      var test = Blocklify.JavaScript.importer.convert_atomic(procesedTest, node, options);
      var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
      Blocklify.JavaScript.importer.appendValueInput(block, 'BOOL', test);
      Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
      break;
    case "BinaryExpression": case "LogicalExpression":
      // math_arithmetic, logic_compare, logic_operation
      if (['+', '-', '*', '/', '==', '!=',
             '<', '>', '<=', '>=', '&&', '||'].indexOf(node.operator) != -1) { // Blockly-JavaScript acepted operators

        var A = Blocklify.JavaScript.importer.convert_atomic(node.left, node, options);
        var B = Blocklify.JavaScript.importer.convert_atomic(node.right, node, options);

        if (['+', '-', '*', '/'].indexOf(node.operator) != -1) { // math_arithmetic
          var operators = {'+': 'ADD', '-': 'MINUS', '*': 'MULTIPLY', '/': 'DIVIDE'};
          block = Blocklify.JavaScript.importer.createBlock('math_arithmetic');
        } else if (['==', '!=', '<', '>', '<=', '>='].indexOf(node.operator) != -1) { // logic_compare
          var operators = {'==': 'EQ', '!=': 'NEQ',
                           '<': 'LT', '>': 'GT',
                           '<=': 'LTE', '>=': 'GTE'};
          block = Blocklify.JavaScript.importer.createBlock('logic_compare');
        } else if (['&&', '||'].indexOf(node.operator) != -1) { // logic_operation
          var operators = {'&&': 'AND', '||': 'OR'};
          block = Blocklify.JavaScript.importer.createBlock('logic_operation');
        }
        Blocklify.JavaScript.importer.appendField(block, 'OP', operators[node.operator]);
        Blocklify.JavaScript.importer.appendValueInput(block, 'A', A);
        Blocklify.JavaScript.importer.appendValueInput(block, 'B', B);
        break;
      }
    case "UnaryExpression":    // logic_negate
      if (node.operator == '!') {
        block = Blocklify.JavaScript.importer.createBlock('logic_negate');
        var argument = Blocklify.JavaScript.importer.convert_atomic(node.argument, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'BOOL', argument);
        break;
      }
    case "ConditionalExpression":    // logic_ternary
      block = Blocklify.JavaScript.importer.createBlock('logic_ternary');
      var test = Blocklify.JavaScript.importer.convert_atomic(node.test, node, options);
      var consequent = Blocklify.JavaScript.importer.convert_atomic(node.consequent, node, options);
      var alternate = Blocklify.JavaScript.importer.convert_atomic(node.alternate, node, options);
      Blocklify.JavaScript.importer.appendValueInput(block, 'IF', test);
      Blocklify.JavaScript.importer.appendValueInput(block, 'THEN', consequent);
      Blocklify.JavaScript.importer.appendValueInput(block, 'ELSE', alternate);
      break;
    case "ForStatement":    // controls_repeat_ext, controls_for
      var blockType;
      // All conditions for pattern recognizing
      // controls_repeat_ext
      // -- initializer conditions
      var flag = (node.init.type == 'VariableDeclaration' && node.init.declarations.length == 1)
              && (node.init.declarations[0].init.type == 'Literal')
              && (node.init.declarations[0].id.name.substr(0,5) == 'count') && (node.init.declarations[0].init.value == 0);
      // -- test conditions
      flag = flag && (node.test.type == 'BinaryExpression' && node.test.left.type == 'Identifier'
                      && node.test.operator == '<'
                      && node.test.left.name == node.init.declarations[0].id.name);
      // -- update conditions
      flag = flag && (node.update.type == 'UpdateExpression' && node.update.operator == '++'
                      && node.update.argument.type == 'Identifier' && node.test.left.name == node.update.argument.name);
      // TODO: search in the body for uses of 'count' (advanced feature - AST node search), now any for with 'count' initializer and acomplish
      //       with the pattern will be converted in this block and may be some variable conflicts with Blockly core blocks
      if (flag) {
        blockType = 'controls_repeat_ext';
      } else {
        // controls_for
        // -- initializer conditions
        flag = (node.init.type == 'AssignmentExpression')
                && (node.init.left.name == node.test.left.name)
                && (node.init.left.type == 'Identifier') && (node.init.right.type == 'Literal');
        // -- update conditions
        var byValue;
        var flag1 = flag && (node.update.type == 'UpdateExpression' && node.update.operator == '++'
                      && node.update.argument.type == 'Identifier' && node.test.left.name == node.update.argument.name);
        if (flag1) {
          byValue = '1';
        }
        var flag2 = (node.update.type == 'AssignmentExpression' && node.update.operator == '+='
                      && node.update.left.type == 'Identifier' && node.test.left.name == node.update.left.name);
        flag2 = flag2 && (node.update.right.type == 'Literal');
        if (flag2) {
          byValue = node.update.right.raw;
        }
        flag = flag && (flag1 || flag2);
        if (flag) {  // controls_for
          blockType = 'controls_for';
        }
      }

      if (blockType == 'controls_repeat_ext') {
        block = Blocklify.JavaScript.importer.createBlock('controls_repeat_ext');
        var times = Blocklify.JavaScript.importer.convert_atomic(node.test.right, node, options);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'TIMES', times);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
        break;
      } else if (blockType == 'controls_for') {
        block = Blocklify.JavaScript.importer.createBlock('controls_for');
        Blocklify.JavaScript.importer.appendField(block, 'VAR', node.test.left.name);
        var from = Blocklify.JavaScript.importer.convert_atomic(node.init.right, node, options);
        var to = Blocklify.JavaScript.importer.convert_atomic(node.test.right, node, options);
        var by = Blocklify.JavaScript.importer.createBlock('math_number');
        Blocklify.JavaScript.importer.appendField(by, 'NUM', byValue);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'FROM', from);
        Blocklify.JavaScript.importer.appendValueInput(block, 'TO', to);
        Blocklify.JavaScript.importer.appendValueInput(block, 'BY', by);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
      }
    case "ForInStatement":    // controls_forEach
      var flag = true;
      if (flag) {
        block = Blocklify.JavaScript.importer.createBlock('controls_forEach');
        // cut the first statement: 'i = i_list[i_index];'
        node.body.body = node.body.body.slice(1);
        var varName = node.left.declarations[0].id.name.substr(0, node.left.declarations[0].id.name.length - 6);
        var list = Blocklify.JavaScript.importer.convert_atomic(node.right, node, options);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendField(block, 'VAR', varName);
        Blocklify.JavaScript.importer.appendValueInput(block, 'LIST', list);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
        break;
      }
    case "VariableDeclaration":   // variables_set
      if (parent.type == 'Program' || parent.type == 'BlockStatement') {
        if (node.declarations.length == 1) {
          if (node.declarations[0].init == null) {
            block = 'Ignore'; // Ignore declarations like 'var i;' beause Blockly handle this itself
            break;
          } else if (parent.body[options.statementIndex + 1]
                     && parent.body[options.statementIndex + 1].type == 'ForInStatement'
                     && parent.body[options.statementIndex + 1].right.type == 'Identifier'
                     && node.declarations[0].id.name == parent.body[options.statementIndex + 1].right.name) {
            parent.body[options.statementIndex + 1].right = node.declarations[0].init;
            block = 'Ignore'; // Ignore declarations like 'var i;' beause Blockly handle this itself
            break;
          } else { // variables_set
            block = Blocklify.JavaScript.importer.createBlock('variables_set');
            Blocklify.JavaScript.importer.appendField(block, 'VAR', node.declarations[0].id.name);
            var value = Blocklify.JavaScript.importer.convert_atomic(node.declarations[0].init, node, options);
            Blocklify.JavaScript.importer.appendValueInput(block, 'VALUE', value);
          }
        }
      }

    default:  // if not implemented block
      break;
  }
  return block;
};

// register the importer
Blocklify.JavaScript.importer.importers.push(Blockly.JavaScript.importer);
<commit_msg>variables_set importer added<commit_after>// Example of importer for blockly core blocks. Importer API experiment - work in progress, importer will be a class.

// List of blockly blocks, info about this importer implementation and the case in which implements.
/*
  * Logic
    - controls_if               // IMPLEMENTED -> "IfStatement"
    - logic_compare             // IMPLEMENTED -> "BinaryExpression"
    - logic_operation           // IMPLEMENTED -> "LogicalExpression"
    - logic_negate              // IMPLEMENTED -> "UnaryExpression"
    - logic_boolean             // IMPLEMENTED -> "Literal"
    - logic_null                // IMPLEMENTED -> "Literal"
    - logic_ternary             // IMPLEMENTED -> "ConditionalExpression"
  * Loops
    - controls_repeat_ext       // IMPLEMENTED -> "ForStatement" -> var handling: if initializer name starts with 'count' this block is rendered
    - controls_whileUntil       // IMPLEMENTED -> "WhileStatement"
    - controls_for              // IMPLEMENTED -> "ForStatement"
    - controls_forEach          // IMPLEMENTED -> "ForInStatement"
    - controls_flow_statements  // ...
  * Math
    - math_number               // IMPLEMENTED -> "Literal"
    - math_arithmetic           // IMPLEMENTED -> "BinaryExpression"
    - math_single
    - math_trig
    - math_constant
    - math_number_property
    - math_change
    - math_round
    - math_on_list
    - math_modulo
    - math_constrain
    - math_random_int
    - math_random_float
  * Text
    - text                      // IMPLEMENTED -> "Literal"
    - text_join
    - text_append
    - text_length
    - text_isEmpty
    - text_indexOf
    - text_charAt
    - text_getSubstring
    - text_changeCase
    - text_trim
    - text_print
    - text_prompt_ext
  * Lists
    - lists_create_empty
    - lists_create_with        // IMPLEMENTED -> "ArrayExpression"
    - lists_repeat
    - lists_length
    - lists_isEmpty
    - lists_indexOf
    - lists_getIndex
    - lists_setIndex
    - lists_getSublist
    - lists_split
  * Colour
    - colour_picker
    - colour_random
    - colour_rgb
    - colour_blend
  * Variables
    - variables_set           // IMPLEMENTED -> "VariabeDeclaration", "AssignmentExpression" could not generate the same code
                              // because in Blockly core not are a variable multiple initialization block.
                              // (not multiple - partially)
    - variables_get
  * Functions
*/

// first import js block generators into blockly js generator context
for (var el in Blocklify.JavaScript.Generator) {
  if (el.substring(0,3) == 'js_') {
    Blockly.JavaScript[el] = Blocklify.JavaScript.Generator[el];
  }
}

// Probably useless
/*Blockly.JavaScript.statementName = function(node) {
  if (node.type == 'Program') {
    return 'body';
  } else if (node.type == 'BlockStatement') {
    return 'body';
  }
};*/

// now the block importer
Blockly.JavaScript.importer = function(node, parent, options) {
  // this is the importer for blockly block (pattern converter)
  //the returned block
  var block = null, field;
  //none-estetic inline blocks
  var no_inline_blocks = [];
  switch (node.type) {
    case "Program":
      block = goog.dom.createDom('xml');
      Blocklify.JavaScript.importer.appendStatement(block, node.body, node, options);
      break;
    case "BlockStatement":
      block = Blocklify.JavaScript.importer.appendStatement(null, node.body, node, options);
      break;
    case "Literal":    // logic_null, math_number, text, logic_boolean
      block = goog.dom.createDom('block');
      if (node.value == null) {
        block.setAttribute('type' ,'logic_null');
      } else {
        var nodeType = typeof(node.value);
        if (nodeType == "number") {
          block.setAttribute('type' ,'math_number');
          Blocklify.JavaScript.importer.appendField(block, 'NUM', node.value + '');
        } else if(nodeType == "string") {
          block.setAttribute('type' ,'text');
          Blocklify.JavaScript.importer.appendField(block, 'TEXT', node.value);
        } else if(nodeType == "boolean") {
          block.setAttribute('type' ,'logic_boolean');
          Blocklify.JavaScript.importer.appendField(block, 'BOOL', node.raw);
        }
      }
      break;
    case "IfStatement":    // controls_if
      block = Blocklify.JavaScript.importer.createBlock('controls_if');
      var tests = [], consequents = [], current_node = node.alternate, countElseIf = 0, countElse = 0;
      tests.push(Blocklify.JavaScript.importer.convert_atomic(node.test, node, options));
      Blocklify.JavaScript.importer.setOutput(tests[0], true);
      consequents.push(Blocklify.JavaScript.importer.convert_atomic(node.consequent, node, options));
      Blocklify.JavaScript.importer.setOutput(tests[0], true);
      while (current_node) {
        if (current_node.type == 'IfStatement') {
          countElseIf++;
          tests.push(Blocklify.JavaScript.importer.convert_atomic(current_node.test, current_node, options));
          Blocklify.JavaScript.importer.setOutput(tests[tests.length-1], true);
          consequents.push(Blocklify.JavaScript.importer.convert_atomic(current_node.consequent, current_node, options));
          current_node = current_node.alternate;
        } else {
          countElse = 1;
          var alternate = Blocklify.JavaScript.importer.convert_atomic(current_node.alternate || current_node, node, options);
          current_node = null;
        }
      };
      var mutation = goog.dom.createDom('mutation');
      block.appendChild(mutation);
      mutation.setAttribute('elseif', countElseIf + '');
      mutation.setAttribute('else', countElse + '');
      Blocklify.JavaScript.importer.appendValueInput(block, 'IF0', tests[0]);
      Blocklify.JavaScript.importer.appendValueInput(block, 'DO0', consequents[0]);
      for (var i = 1; i <= countElseIf; i++) {
        Blocklify.JavaScript.importer.appendValueInput(block, 'IF' + i, tests[i]);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO' + i, consequents[i]);
      }
      if (countElse == 1) {
        Blocklify.JavaScript.importer.appendValueInput(block, 'ELSE', alternate);
      }
      break;
    case "ArrayExpression":
      block = Blocklify.JavaScript.importer.createBlock('lists_create_with');
      Blocklify.JavaScript.importer.appendCloneMutation(block, 'items', 'ADD', node.elements, node, options);
      break;
    case "WhileStatement":    // controls_whileUntil
      block = Blocklify.JavaScript.importer.createBlock('controls_whileUntil');
      if (node.test.type == 'UnaryExpression' && node.test.operator == '!') {
        mode = 'UNTIL';
        procesedTest = node.test.argument;
      } else {
        mode = 'WHILE';
        procesedTest = node.test;
      }
      Blocklify.JavaScript.importer.appendField(block, 'MODE', mode);
      var test = Blocklify.JavaScript.importer.convert_atomic(procesedTest, node, options);
      var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
      Blocklify.JavaScript.importer.appendValueInput(block, 'BOOL', test);
      Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
      break;
    case "BinaryExpression": case "LogicalExpression":
      // math_arithmetic, logic_compare, logic_operation
      if (['+', '-', '*', '/', '==', '!=',
             '<', '>', '<=', '>=', '&&', '||'].indexOf(node.operator) != -1) { // Blockly-JavaScript acepted operators

        var A = Blocklify.JavaScript.importer.convert_atomic(node.left, node, options);
        var B = Blocklify.JavaScript.importer.convert_atomic(node.right, node, options);

        if (['+', '-', '*', '/'].indexOf(node.operator) != -1) { // math_arithmetic
          var operators = {'+': 'ADD', '-': 'MINUS', '*': 'MULTIPLY', '/': 'DIVIDE'};
          block = Blocklify.JavaScript.importer.createBlock('math_arithmetic');
        } else if (['==', '!=', '<', '>', '<=', '>='].indexOf(node.operator) != -1) { // logic_compare
          var operators = {'==': 'EQ', '!=': 'NEQ',
                           '<': 'LT', '>': 'GT',
                           '<=': 'LTE', '>=': 'GTE'};
          block = Blocklify.JavaScript.importer.createBlock('logic_compare');
        } else if (['&&', '||'].indexOf(node.operator) != -1) { // logic_operation
          var operators = {'&&': 'AND', '||': 'OR'};
          block = Blocklify.JavaScript.importer.createBlock('logic_operation');
        }
        Blocklify.JavaScript.importer.appendField(block, 'OP', operators[node.operator]);
        Blocklify.JavaScript.importer.appendValueInput(block, 'A', A);
        Blocklify.JavaScript.importer.appendValueInput(block, 'B', B);
        break;
      }
    case "UnaryExpression":    // logic_negate
      if (node.operator == '!') {
        block = Blocklify.JavaScript.importer.createBlock('logic_negate');
        var argument = Blocklify.JavaScript.importer.convert_atomic(node.argument, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'BOOL', argument);
        break;
      }
    case "ConditionalExpression":    // logic_ternary
      block = Blocklify.JavaScript.importer.createBlock('logic_ternary');
      var test = Blocklify.JavaScript.importer.convert_atomic(node.test, node, options);
      var consequent = Blocklify.JavaScript.importer.convert_atomic(node.consequent, node, options);
      var alternate = Blocklify.JavaScript.importer.convert_atomic(node.alternate, node, options);
      Blocklify.JavaScript.importer.appendValueInput(block, 'IF', test);
      Blocklify.JavaScript.importer.appendValueInput(block, 'THEN', consequent);
      Blocklify.JavaScript.importer.appendValueInput(block, 'ELSE', alternate);
      break;
    case "ForStatement":    // controls_repeat_ext, controls_for
      var blockType;
      // All conditions for pattern recognizing
      // controls_repeat_ext
      // -- initializer conditions
      var flag = (node.init.type == 'VariableDeclaration' && node.init.declarations.length == 1)
              && (node.init.declarations[0].init.type == 'Literal')
              && (node.init.declarations[0].id.name.substr(0,5) == 'count') && (node.init.declarations[0].init.value == 0);
      // -- test conditions
      flag = flag && (node.test.type == 'BinaryExpression' && node.test.left.type == 'Identifier'
                      && node.test.operator == '<'
                      && node.test.left.name == node.init.declarations[0].id.name);
      // -- update conditions
      flag = flag && (node.update.type == 'UpdateExpression' && node.update.operator == '++'
                      && node.update.argument.type == 'Identifier' && node.test.left.name == node.update.argument.name);
      // TODO: search in the body for uses of 'count' (advanced feature - AST node search), now any for with 'count' initializer and acomplish
      //       with the pattern will be converted in this block and may be some variable conflicts with Blockly core blocks
      if (flag) {
        blockType = 'controls_repeat_ext';
      } else {
        // controls_for
        // -- initializer conditions
        flag = (node.init.type == 'AssignmentExpression')
                && (node.init.left.name == node.test.left.name)
                && (node.init.left.type == 'Identifier') && (node.init.right.type == 'Literal');
        // -- update conditions
        var byValue;
        var flag1 = flag && (node.update.type == 'UpdateExpression' && node.update.operator == '++'
                      && node.update.argument.type == 'Identifier' && node.test.left.name == node.update.argument.name);
        if (flag1) {
          byValue = '1';
        }
        var flag2 = (node.update.type == 'AssignmentExpression' && node.update.operator == '+='
                      && node.update.left.type == 'Identifier' && node.test.left.name == node.update.left.name);
        flag2 = flag2 && (node.update.right.type == 'Literal');
        if (flag2) {
          byValue = node.update.right.raw;
        }
        flag = flag && (flag1 || flag2);
        if (flag) {  // controls_for
          blockType = 'controls_for';
        }
      }

      if (blockType == 'controls_repeat_ext') {
        block = Blocklify.JavaScript.importer.createBlock('controls_repeat_ext');
        var times = Blocklify.JavaScript.importer.convert_atomic(node.test.right, node, options);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'TIMES', times);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
        break;
      } else if (blockType == 'controls_for') {
        block = Blocklify.JavaScript.importer.createBlock('controls_for');
        Blocklify.JavaScript.importer.appendField(block, 'VAR', node.test.left.name);
        var from = Blocklify.JavaScript.importer.convert_atomic(node.init.right, node, options);
        var to = Blocklify.JavaScript.importer.convert_atomic(node.test.right, node, options);
        var by = Blocklify.JavaScript.importer.createBlock('math_number');
        Blocklify.JavaScript.importer.appendField(by, 'NUM', byValue);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'FROM', from);
        Blocklify.JavaScript.importer.appendValueInput(block, 'TO', to);
        Blocklify.JavaScript.importer.appendValueInput(block, 'BY', by);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
      }
    case "ForInStatement":    // controls_forEach
      var flag = true;
      if (flag) {
        block = Blocklify.JavaScript.importer.createBlock('controls_forEach');
        // cut the first statement: 'i = i_list[i_index];'
        node.body.body = node.body.body.slice(1);
        var varName = node.left.declarations[0].id.name.substr(0, node.left.declarations[0].id.name.length - 6);
        var list = Blocklify.JavaScript.importer.convert_atomic(node.right, node, options);
        var body = Blocklify.JavaScript.importer.convert_atomic(node.body, node, options);
        Blocklify.JavaScript.importer.appendField(block, 'VAR', varName);
        Blocklify.JavaScript.importer.appendValueInput(block, 'LIST', list);
        Blocklify.JavaScript.importer.appendValueInput(block, 'DO', body);
        break;
      }
    case "VariableDeclaration":   // variables_set
      if (parent.type == 'Program' || parent.type == 'BlockStatement') {
        if (node.declarations.length == 1) {
          if (node.declarations[0].init == null) {
            block = 'Ignore'; // Ignore declarations like 'var i;' beause Blockly handle this itself
            break;
          } else if (parent.body[options.statementIndex + 1]
                     && parent.body[options.statementIndex + 1].type == 'ForInStatement'
                     && parent.body[options.statementIndex + 1].right.type == 'Identifier'
                     && node.declarations[0].id.name == parent.body[options.statementIndex + 1].right.name) {
            parent.body[options.statementIndex + 1].right = node.declarations[0].init;
            block = 'Ignore'; // Ignore declarations like 'var i;' beause Blockly handle this itself
            break;
          } else { // variables_set
            block = Blocklify.JavaScript.importer.createBlock('variables_set');
            Blocklify.JavaScript.importer.appendField(block, 'VAR', node.declarations[0].id.name);
            var value = Blocklify.JavaScript.importer.convert_atomic(node.declarations[0].init, node, options);
            Blocklify.JavaScript.importer.appendValueInput(block, 'VALUE', value);
          }
        }
      }
    case "AssignmentExpression":    // variables_set
      if (node.left.type == 'Identifier' && node.operator == '=') {
        block = Blocklify.JavaScript.importer.createBlock('variables_set');
        Blocklify.JavaScript.importer.appendField(block, 'VAR', node.left.name);
        var value = Blocklify.JavaScript.importer.convert_atomic(node.right, node, options);
        Blocklify.JavaScript.importer.appendValueInput(block, 'VALUE', value);
        break;
      }

    default:  // if not implemented block
      break;
  }
  return block;
};

// register the importer
Blocklify.JavaScript.importer.importers.push(Blockly.JavaScript.importer);
<|endoftext|>


<commit_before>define('app/views/machine', [
    'text!app/templates/machine.html','ember', 'd3', 'cubism'],
    /**
     *
     * Machine page
     *
     * @returns Class
     */
    function(machine_html) {
        return Ember.View.extend({
            tagName: false,
            machineBinding: 'Mist.machine',

            disabledShellClass: function(){
                if(this.machine && this.machine.hasKey){
                    return '';
                } else {
                    return 'ui-disabled';
                }
            }.property('machine.hasKey'),

            disabledTagClass: function(){
                if(this.machine && this.machine.can_tag){
                    return '';
                } else {
                    return 'ui-disabled';
                }
            }.property('machine.can_tag'),

            disabledPowerClass: function(){
                if(this.machine && this.machine.state === 'terminated') {
                    return 'ui-disabled';
                } else {
                    return '';
                }
            }.property('machine.state'),

            pendingMonitoringClass: function() {
                if (this.machine && this.machine.pendingMonitoring) {
                    return 'pending-monitoring';
                } else {
                    return '';
                }
            }.property('machine.pendingMonitoring'),

            metadata: function(){
                if(!this.machine || !this.machine.extra){
                    return [];
                }
                var ret = new Array();

                $.each(this.machine.extra, function(key, value){
                    if (typeof(value) == 'string' || typeof(value) == 'number') {
                        ret.push({key:key, value: value});
                    }
                });
                return ret;
            }.property("machine"),

            basicvars: function(){
                if(!this.machine){
                    return [];
                }

                var publicIps = null;

                if($.isArray(this.machine.public_ips)){
                    publicIps = this.machine.public_ips.join();
                } else if(typeof this.machine.public_ips === 'string'){
                    publicIps = this.machine.public_ips;
                }

                var privateIps = null;

                if($.isArray(this.machine.private_ips)){
                    privateIps = this.machine.private_ips.join();
                } else if(typeof this.machine.private_ips === 'string'){
                    privateIps = this.machine.private_ips;
                }

                var basicvars = {
                        'Public IPs': publicIps,
                        'Private IPs': privateIps,
                        'DNS Name': this.machine.extra.dns_name,
                        'Launch Date': this.machine.extra.launchdatetime
                };

                if(this.machine.image && 'image' in this.machine &&
                        'name' in this.machine.image){
                    basicvars['Image'] = this.machine.image.name;
                }

                var ret = new Array();

                $.each(basicvars, function(key, value){
                    if (typeof(value) == 'string'){
                        ret.push({key:key, value: value});
                    }
                });

                return ret;

            }.property("machine"),

            name: function(){
                if(!this.machine){
                    return "";
                }
                return this.machine.name || this.machine.id;
            }.property("machine"),

            upFor: function(){
                if(this.machine && this.machine.uptime){
                    var ret = "";
                    var x = Math.floor(this.machine.uptime / 1000);
                    var seconds = x % 60;
                    x = Math.floor(x / 60);
                    var minutes = x % 60;
                    x = Math.floor(x / 60);
                    var hours = x % 24;
                    x = Math.floor(x / 24);
                    var days = x;
                    if(days){
                        ret = ret + days + " days, ";
                    }

                    if(hours){
                        ret = ret + hours + " hours, ";
                    }

                    if(minutes){
                        ret = ret + minutes + " minutes, ";
                    }

                    if(seconds){
                        ret = ret + seconds + " seconds";
                    } else {
                        ret = ret + "0 seconds";
                    }

                    return ret;
                } else {
                    return '';
                }
            }.property("machine.uptime"),

            providerIconClass: function() {
                if(!this.machine){
                    return "";
                }
                // TODO: in css this currently works only for ec2 us east
                // other amazon providers have different ids
                return 'provider-' + this.machine.backend.provider;
            }.property("machine"),

            setGraph: function() {

                if(!this.machine || !this.machine.hasMonitoring){
                    return;
                }

                var machine = this.machine;

                var stats = {};

                Em.run.next(function(){
                    var changes_since = 0;

                    function createGraphs() {
                        function stat(x, y, z) {
                          var value = 0,
                              values = [],
                              i = 0,
                              last;
                          return context.metric(function(start, stop, step, callback) {
                            var values = [];

                            // convert start & stop to milliseconds
                            start = +start;
                            stop = +stop;

                            var uri = URL_PREFIX + '/backends/' +
                                    machine.backend.index + '/machines/' +
                                    machine.id + '/stats' + "?expression=" + x +
                                    "&start=" + start/1000 + "&stop=" + stop/1000 +
                                    "&step=" + step;

                            d3.json(uri, function(data) {
                                if (!data) return callback(new Error("unable to load data"));
                                console.warn(data[x][y]);

                                callback(null, data[x][y].map(function(d) { return d*100}));
                            });

                        });
                        }

                        var context = cubism.context()
                            .serverDelay(0)
                            .clientDelay(0)
                            .step(5*1000)
                            .size($(window).width()-180);

                        //var load_avg1 = stat('load','v',0);
                        var cpu_user = stat('cpu','util',0);

                        /*d3.select("#machineGraph").call(function(div) {
                          div.datum(load_avg1);

                          div.append("div")
                              .attr("class", "horizon")
                              .call(context.horizon()
                                .height(30)
                                .colors(["#08519c","#3182bd","#6baed6","#bdd7e7","#bae4b3","#74c476","#31a354","#006d2c"])
                                .title("LOAD ")
                                .extent([0, 1]));

                        });*/

                        $('#machineGraph *').remove();
                        d3.select("#machineGraph").call(function(div) {
                          div.datum(cpu_user);

                          div.append("div")
                              .attr("class", "horizon")
                              .call(context.horizon()
                                .height(30)
                                .colors(["#08519c","#3182bd","#6baed6","#bdd7e7","#bae4b3","#74c476","#31a354","#006d2c"])
                                .title("CPU ")
                                .extent([0, 100]));

                        });

                        d3.select("#machineGraph").append("g")
                              .call(d3.svg.axis()
                                .scale(d3.time.scale())
                                .orient("bottom"));

                        // On mousemove, reposition the chart values to match the rule.
                        context.on("focus", function(i) {
                          d3.selectAll(".value").style("right", i == null ? null : context.size() - i + "px");
                        });
                    }

                    createGraphs();

                });

            }.observes('machine.hasMonitoring'),

            init: function() {
                this._super();
                // cannot have template in home.pt as pt complains
                this.set('template', Ember.Handlebars.compile(machine_html));
            },
        });
    }
);
<commit_msg>Update from where to get cpu stats<commit_after>define('app/views/machine', [
    'text!app/templates/machine.html','ember', 'd3', 'cubism'],
    /**
     *
     * Machine page
     *
     * @returns Class
     */
    function(machine_html) {
        return Ember.View.extend({
            tagName: false,
            machineBinding: 'Mist.machine',

            disabledShellClass: function(){
                if(this.machine && this.machine.hasKey){
                    return '';
                } else {
                    return 'ui-disabled';
                }
            }.property('machine.hasKey'),

            disabledTagClass: function(){
                if(this.machine && this.machine.can_tag){
                    return '';
                } else {
                    return 'ui-disabled';
                }
            }.property('machine.can_tag'),

            disabledPowerClass: function(){
                if(this.machine && this.machine.state === 'terminated') {
                    return 'ui-disabled';
                } else {
                    return '';
                }
            }.property('machine.state'),

            pendingMonitoringClass: function() {
                if (this.machine && this.machine.pendingMonitoring) {
                    return 'pending-monitoring';
                } else {
                    return '';
                }
            }.property('machine.pendingMonitoring'),

            metadata: function(){
                if(!this.machine || !this.machine.extra){
                    return [];
                }
                var ret = new Array();

                $.each(this.machine.extra, function(key, value){
                    if (typeof(value) == 'string' || typeof(value) == 'number') {
                        ret.push({key:key, value: value});
                    }
                });
                return ret;
            }.property("machine"),

            basicvars: function(){
                if(!this.machine){
                    return [];
                }

                var publicIps = null;

                if($.isArray(this.machine.public_ips)){
                    publicIps = this.machine.public_ips.join();
                } else if(typeof this.machine.public_ips === 'string'){
                    publicIps = this.machine.public_ips;
                }

                var privateIps = null;

                if($.isArray(this.machine.private_ips)){
                    privateIps = this.machine.private_ips.join();
                } else if(typeof this.machine.private_ips === 'string'){
                    privateIps = this.machine.private_ips;
                }

                var basicvars = {
                        'Public IPs': publicIps,
                        'Private IPs': privateIps,
                        'DNS Name': this.machine.extra.dns_name,
                        'Launch Date': this.machine.extra.launchdatetime
                };

                if(this.machine.image && 'image' in this.machine &&
                        'name' in this.machine.image){
                    basicvars['Image'] = this.machine.image.name;
                }

                var ret = new Array();

                $.each(basicvars, function(key, value){
                    if (typeof(value) == 'string'){
                        ret.push({key:key, value: value});
                    }
                });

                return ret;

            }.property("machine"),

            name: function(){
                if(!this.machine){
                    return "";
                }
                return this.machine.name || this.machine.id;
            }.property("machine"),

            upFor: function(){
                if(this.machine && this.machine.uptime){
                    var ret = "";
                    var x = Math.floor(this.machine.uptime / 1000);
                    var seconds = x % 60;
                    x = Math.floor(x / 60);
                    var minutes = x % 60;
                    x = Math.floor(x / 60);
                    var hours = x % 24;
                    x = Math.floor(x / 24);
                    var days = x;
                    if(days){
                        ret = ret + days + " days, ";
                    }

                    if(hours){
                        ret = ret + hours + " hours, ";
                    }

                    if(minutes){
                        ret = ret + minutes + " minutes, ";
                    }

                    if(seconds){
                        ret = ret + seconds + " seconds";
                    } else {
                        ret = ret + "0 seconds";
                    }

                    return ret;
                } else {
                    return '';
                }
            }.property("machine.uptime"),

            providerIconClass: function() {
                if(!this.machine){
                    return "";
                }
                // TODO: in css this currently works only for ec2 us east
                // other amazon providers have different ids
                return 'provider-' + this.machine.backend.provider;
            }.property("machine"),

            setGraph: function() {

                if(!this.machine || !this.machine.hasMonitoring){
                    return;
                }

                var machine = this.machine;

                var stats = {};

                Em.run.next(function(){
                    var changes_since = 0;

                    function createGraphs() {
                        function stat(x, y, z) {
                          var value = 0,
                              values = [],
                              i = 0,
                              last;
                          return context.metric(function(start, stop, step, callback) {
                            var values = [];

                            // convert start & stop to milliseconds
                            start = +start;
                            stop = +stop;

                            var uri = URL_PREFIX + '/backends/' +
                                    machine.backend.index + '/machines/' +
                                    machine.id + '/stats' + "?expression=" + x +
                                    "&start=" + start/1000 + "&stop=" + stop/1000 +
                                    "&step=" + step;

                            d3.json(uri, function(data) {
                                if (!data) return callback(new Error("unable to load data"));
                                console.warn(data[x][y]);

                                callback(null, data[x][y].map(function(d) { return d*100}));
                            });

                        });
                        }

                        var context = cubism.context()
                            .serverDelay(0)
                            .clientDelay(0)
                            .step(5*1000)
                            .size($(window).width()-180);

                        //var load_avg1 = stat('load','v',0);
                        var cpu_user = stat('cpu', 'utilization', 0);

                        /*d3.select("#machineGraph").call(function(div) {
                          div.datum(load_avg1);

                          div.append("div")
                              .attr("class", "horizon")
                              .call(context.horizon()
                                .height(30)
                                .colors(["#08519c","#3182bd","#6baed6","#bdd7e7","#bae4b3","#74c476","#31a354","#006d2c"])
                                .title("LOAD ")
                                .extent([0, 1]));

                        });*/

                        $('#machineGraph *').remove();
                        d3.select("#machineGraph").call(function(div) {
                          div.datum(cpu_user);

                          div.append("div")
                              .attr("class", "horizon")
                              .call(context.horizon()
                                .height(30)
                                .colors(["#08519c","#3182bd","#6baed6","#bdd7e7","#bae4b3","#74c476","#31a354","#006d2c"])
                                .title("CPU ")
                                .extent([0, 100]));

                        });

                        d3.select("#machineGraph").append("g")
                              .call(d3.svg.axis()
                                .scale(d3.time.scale())
                                .orient("bottom"));

                        // On mousemove, reposition the chart values to match the rule.
                        context.on("focus", function(i) {
                          d3.selectAll(".value").style("right", i == null ? null : context.size() - i + "px");
                        });
                    }

                    createGraphs();

                });

            }.observes('machine.hasMonitoring'),

            init: function() {
                this._super();
                // cannot have template in home.pt as pt complains
                this.set('template', Ember.Handlebars.compile(machine_html));
            },
        });
    }
);
<|endoftext|>


<commit_before>// Sample View

enyo.kind({
	name: "moon.sample.music.SimilarTracksNarrowSample",
	kind: "moon.Panels",
	pattern: "alwaysviewing",
	useHandle: false,
	components: [
		{
			title: "Similar Tracks",
			titleAbove: "04",
			titleBelow: "10 Tracks",
			headerComponents: [
				{kind: "moon.IconButton", src: "../assets/icon-like.png"},
				{kind: "moon.IconButton", src: "../assets/icon-next.png"}
			],
			components: [
				{
					name: "trackList",
					kind: "moon.DataList",
					scrollerOptions: { kind:"moon.Scroller", horizontal: "hidden" },
					fit: true,
					components: [
						{
							bindings: [
								{from: ".model.coverUrl", to: ".$.enyoImage.src"},
								{from: ".model.track", to: ".$.imageTrack.content"},
								{from: ".model.artist", to: ".$.imageArtist.content"},
								{from: ".model.time", to: ".$.imageTime.content"}
							],
							components: [
								{kind: "moon.Item", ontap: "changeName", layoutKind: "FittableColumnsLayout", components: [
									{name: "enyoImage", kind: "enyo.Image", style: "width: 170px; height: 126px; padding-right: 30px;"},
									{components: [
										{name: "imageTrack"},
										{name: "imageArtist", classes: "moon-superscript"},
										{name: "imageTime", classes: "moon-superscript"}
									]}
								]}
							]
						}
					]
				}
			]
		}
	],
	bindings: [
		{from: ".controller.track", to: ".$.trackList.controller"}
	]
});

// Sample model

enyo.ready(function (){
    var sampleModel = new enyo.Model({
        track: new enyo.Collection([
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"}
        ])
    });

// Sample Application

    new enyo.Application({
        view: {
            classes: "enyo-unselectable moon",
            components: [
                {
                    kind: "moon.sample.music.SimilarTracksNarrowSample",
                    controller: ".app.controllers.trackController",
                    classes: "enyo-fit"
                }
            ]
        },
        controllers: [
            {
                name: "trackController",
                kind: "enyo.ModelController",
                model: sampleModel,
                changeName: function(inSender, inEvent) {
                    inSender.parent.controller.set("track", "Good track");
                }
            }
        ]
    });
});<commit_msg>GF-11479: Use moon-hspacing instead of FittableColumns and padding. DCO-1.1-Signed-Off-By: Kevin Schaaf (kevin.schaaf@lge.com)<commit_after>// Sample View

enyo.kind({
	name: "moon.sample.music.SimilarTracksNarrowSample",
	kind: "moon.Panels",
	pattern: "alwaysviewing",
	useHandle: false,
	components: [
		{
			title: "Similar Tracks",
			titleAbove: "04",
			titleBelow: "10 Tracks",
			headerComponents: [
				{kind: "moon.IconButton", src: "../assets/icon-like.png"},
				{kind: "moon.IconButton", src: "../assets/icon-next.png"}
			],
			components: [
				{
					name: "trackList",
					kind: "moon.DataList",
					scrollerOptions: { kind:"moon.Scroller", horizontal: "hidden" },
					fit: true,
					components: [
						{
							bindings: [
								{from: ".model.coverUrl", to: ".$.enyoImage.src"},
								{from: ".model.track", to: ".$.imageTrack.content"},
								{from: ".model.artist", to: ".$.imageArtist.content"},
								{from: ".model.time", to: ".$.imageTime.content"}
							],
							components: [
								{kind: "moon.Item", ontap: "changeName", classes:"moon-hspacing", components: [
									{name: "enyoImage", kind: "enyo.Image", style: "width: 126px; height: 126px;"},
									{components: [
										{name: "imageTrack"},
										{name: "imageArtist", classes: "moon-superscript"},
										{name: "imageTime", classes: "moon-superscript"}
									]}
								]}
							]
						}
					]
				}
			]
		}
	],
	bindings: [
		{from: ".controller.track", to: ".$.trackList.controller"}
	]
});

// Sample model

enyo.ready(function (){
    var sampleModel = new enyo.Model({
        track: new enyo.Collection([
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"},
            {coverUrl: "../assets/default-music.png", track: "Track name", artist: "Artist name", time: "3:40"}
        ])
    });

// Sample Application

    new enyo.Application({
        view: {
            classes: "enyo-unselectable moon",
            components: [
                {
                    kind: "moon.sample.music.SimilarTracksNarrowSample",
                    controller: ".app.controllers.trackController",
                    classes: "enyo-fit"
                }
            ]
        },
        controllers: [
            {
                name: "trackController",
                kind: "enyo.ModelController",
                model: sampleModel,
                changeName: function(inSender, inEvent) {
                    inSender.parent.controller.set("track", "Good track");
                }
            }
        ]
    });
});<|endoftext|>


<commit_before>Handsontable.FocusCatcher = function (instance) {
  this.el = document.createElement('DIV');
  this.el.style.position = 'fixed';
  this.el.style.top = '0';
  this.el.style.left = '0';
  this.el.style.background = 'red';
  this.el.style.width = '1px';
  this.el.style.height = '1px';
  this.el.setAttribute('tabindex', 10000); //http://www.barryvan.com.au/2009/01/onfocus-and-onblur-for-divs-in-fx/; 32767 is max tabindex for IE7,8
  instance.rootElement.append(this.el);

  this.$el = $(this.el);
};

Handsontable.FocusCatcher.prototype.listen = function () {
  this.el.focus();
};<commit_msg>make focusCatcher invisible<commit_after>Handsontable.FocusCatcher = function (instance) {
  this.el = document.createElement('DIV');
  this.el.style.position = 'fixed';
  this.el.style.top = '0';
  this.el.style.left = '0';
  this.el.style.width = '1px';
  this.el.style.height = '1px';
  this.el.setAttribute('tabindex', 10000); //http://www.barryvan.com.au/2009/01/onfocus-and-onblur-for-divs-in-fx/; 32767 is max tabindex for IE7,8
  instance.rootElement.append(this.el);

  this.$el = $(this.el);
};

Handsontable.FocusCatcher.prototype.listen = function () {
  this.el.focus();
};<|endoftext|>


<commit_before>/***** DEFINIZIONE ESPRESSIONI REGOLARI PER I QUATTRO TIPI DI DOMANDE: *****/
// VF = DOMANDA VERO FALSO
// MU = RISPOSTA MULTIPLA (CON UNA SOLA RISPOSTA ESATTA)
// MX = RISPOSTA MULTIPLA (CON PIÙ RISPOSTE ESATTE)
// AS = DOMANDA ASSOCIAZIONE
// OD = DOMANDA ORDINAMENTO
var VF = /^[\s]*<question [\s]*type[\s]*=[\s]*"(VF)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*<\/question>[\s]*$/;
var MU = /^[\s]*<question [\s]*type[\s]*=[\s]*"(MU)">[\s]*<text>[\s]*(.*)[\s]*<\/text>(([\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var MX = /^[\s]*<question [\s]*type[\s]*=[\s]*"(MX)">[\s]*<text>[\s]*(.*)[\s]*<\/text>(([\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var AS = /^[\s]*<question [\s]*type[\s]*=[\s]*"(AS)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*((<answer [\s]*set[\s]*=[\s]*"(A|B)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var OD = /^[\s]*<question [\s]*type[\s]*=[\s]*"(OD)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*((<answer [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;

var str; // stringa in cui viene memorizzato il testo di input compilato dall'utente
var m; // array in cui viene memorizzata la domanda scomposta secondo l'espressione regolare definita
// per capire il funzionamento della funzione exec() e quindi la variabile m risultante, basta guardare questo sito:
// https://regex101.com/ dove metti l'espressione regolare e il testo che vuoi controllare e vedi come viene suddiviso il testo.
// l'array m quindi contiene tutti i gruppi definiti dalle parentesi tonde delle espressioni regolari

export default function QML2HTML(QMLtesto)
{
    // AR è l'array che contiene le espressioni regolari definite globalmente fuori dalla funzione
    var AR = [VF, MU, AS, MX, OD];
    var match = false;
    // questo ciclo controlla tramite il metodo exec() se il testo matcha
    // con una delle espressioni regolari definite dell'array AR
    for (var i = 0; i < AR.length && !match; i++)
    {
        //debugger;
        if ((m = AR[i].exec(QMLtesto)) !== null)
        {
            match = true;
            if (m.index === AR[i].lastIndex)
                AR[i].lastIndex++;
        }
        else match = false;
    }
    if(!match) return false;

    switch (m[1])
    {   case "VF":
            var element = {
                  type: m[1],
                  text: m[2],
                  ans: m[3]
                };
            break;
        case "MU":
            var element = {
                type: m[1],
                text: m[2],
                ans: m[6],
                rightAns: getRightAnsMU()
            };
            break;
        case "MX":
            var element = {
                type: m[1],
                text: m[2],
                ans: m[6],
                rightAns: getRightAnsMX()
            };
            break;
        case "AS":
            debugger;
            var sets = getAnswersAS();
            var rightAns = getRightAnsAS(sets[0], sets[1]);
            var element = {
                type: m[1],
                text: m[2],
                sets: sets, //
                rightAns: rightAns
            };

            break;
        case "OD": // DA FARE
            var ans = getAnsOD();
            //var orderedAns = getOrderedAnsOD(set);
            var element = {
                type: m[1],
                text: m[2],
                ans: ans,
                //orderedSet:
            }
            //ok = checkOD(); // OD -> si controlla che ogni elemento abbia una posizione diversa
            break;
        default:
            element = null;
            //ok = false;
        }
    //console.log(element);
    return element;
}

function getRightAnsMU()
{
    var re = /[\s]*isRight[\s]*=[\s]*\"yes\"[\s]*>(.*)<\/answer>[\s]*/;
    var s;
    var rAns = [];

    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var counter = 0;
    for (var i = 0; i < lines.length; i++)
    {
        if ((s = re.exec(lines[i])) !== null)
        {
            if (s.index === re.lastIndex)
                re.lastIndex++;

            rAns.push(s[1]);
            counter++;
        }
    }
    //debugger;
    if (counter == 1) return rAns;
    return null;
}

function getRightAnsMX()
{
    var re = /[\s]*isRight[\s]*=[\s]*\"yes\"[\s]*>(.*)<\/answer>[\s]*/;
    var s;
    var rAns = [];

    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var counter = 0;
    for (var i = 0; i < lines.length; i++)
    {
        if ((s = re.exec(lines[i])) !== null)
        {
            if (s.index === re.lastIndex)
                re.lastIndex++;

            rAns.push(s[1]);
            counter++;
        }
    }
    //debugger;
    if (counter >= 1) return rAns;
    return null;
}

function getAnswersAS()
{
    var reA = /<answer [\s]*set[\s]*=[\s]*"(A)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var reB = /<answer [\s]*set[\s]*=[\s]*"(B)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var s;
    //debugger;
    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var A = [],
        B = [];

    for (var i = 0; i < lines.length; i++)
    {
        if ((s = reA.exec(lines[i])) !== null) // cerco i match per l'insieme A
        {
            if (s.index === reA.lastIndex)
                reA.lastIndex++;

            var element  = {
                text: s[3],
                id: s[2]
            };
            A.push(element);
        }

        if ((s = reB.exec(lines[i])) !== null) // cerco i match per l'insieme B
        {
            if (s.index === reB.lastIndex)
                reB.lastIndex++;

            var element  = {
                text: s[3],
                id: s[2]
            };
            B.push(element);
        }
    }
    debugger;
    var element = {
        A: A,
        B: B
    }
    return element;  // ritorna un elemento con due array A e B con i rispettivi campi A.text e A.id
}

function getRightAnsAS(A, B)
{
    var set = [];
    var first,
        second;

    if(A.length <= B.length)
    {
        first = A;
        second = B;
    }
    else
    {
        first = B;
        second = A;
    }

    for (var i = 0; i < first.length; i++)
    {
        for (var j = 0; j < second.length; j++)
        {
            if(first[i].pos === second[j].pos)
            {
                var temp = [first[i].text, second[j].text];
                set.push(temp);
            }

        }
    }
    console.log(set);
    return set;
}

function getAnsOD()
{
    var reA = /<answer [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var s;
    //debugger;
    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);
    //debugger;
    var matchA = true;

    var A = [];

    for (var i = 0; i < lines.length; i++)
    {
        if ((s = reA.exec(lines[i])) !== null) // cerco i match per l'insieme A
        {
            if (s.index === reA.lastIndex)
                reA.lastIndex++;

            var element  = {
                text: s[2],
                id: s[1]
            };
            A.push(element);
        }
        debugger;
    }
    for (var i = 0; i < A.length; i++) {
        console.log(A[i].pos);
    }

    return A;
}

function getOrderedAnsOD(A)
{
    console.log(A.sort());
    return A;
}<commit_msg>QML2HTML.js again<commit_after>/***** DEFINIZIONE ESPRESSIONI REGOLARI PER I QUATTRO TIPI DI DOMANDE: *****/
// VF = DOMANDA VERO FALSO
// MU = RISPOSTA MULTIPLA (CON UNA SOLA RISPOSTA ESATTA)
// MX = RISPOSTA MULTIPLA (CON PIÙ RISPOSTE ESATTE)
// AS = DOMANDA ASSOCIAZIONE
// OD = DOMANDA ORDINAMENTO
var VF = /^[\s]*<question [\s]*type[\s]*=[\s]*"(VF)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*<\/question>[\s]*$/;
var MU = /^[\s]*<question [\s]*type[\s]*=[\s]*"(MU)">[\s]*<text>[\s]*(.*)[\s]*<\/text>(([\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var MX = /^[\s]*<question [\s]*type[\s]*=[\s]*"(MX)">[\s]*<text>[\s]*(.*)[\s]*<\/text>(([\s]*<answer [\s]*isRight[\s]*=[\s]*"(yes|no)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var AS = /^[\s]*<question [\s]*type[\s]*=[\s]*"(AS)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*((<answer [\s]*set[\s]*=[\s]*"(A|B)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;
var OD = /^[\s]*<question [\s]*type[\s]*=[\s]*"(OD)">[\s]*<text>[\s]*(.*)[\s]*<\/text>[\s]*((<answer [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>[\s]*){2,})<\/question>[\s]*$/;

var str; // stringa in cui viene memorizzato il testo di input compilato dall'utente
var m; // array in cui viene memorizzata la domanda scomposta secondo l'espressione regolare definita
// per capire il funzionamento della funzione exec() e quindi la variabile m risultante, basta guardare questo sito:
// https://regex101.com/ dove metti l'espressione regolare e il testo che vuoi controllare e vedi come viene suddiviso il testo.
// l'array m quindi contiene tutti i gruppi definiti dalle parentesi tonde delle espressioni regolari

export default function QML2HTML(QMLtesto)
{
    // AR è l'array che contiene le espressioni regolari definite globalmente fuori dalla funzione
    var AR = [VF, MU, AS, MX, OD];
    var match = false;
    // questo ciclo controlla tramite il metodo exec() se il testo matcha
    // con una delle espressioni regolari definite dell'array AR
    for (var i = 0; i < AR.length && !match; i++)
    {
        //debugger;
        if ((m = AR[i].exec(QMLtesto)) !== null)
        {
            match = true;
            if (m.index === AR[i].lastIndex)
                AR[i].lastIndex++;
        }
        else match = false;
    }
    if(!match) return false;

    switch (m[1])
    {   case "VF":
            var element = {
                  type: m[1],
                  text: m[2],
                  ans: m[3]
                };
            break;
        case "MU":
            var element = {
                type: m[1],
                text: m[2],
                ans: m[6],
                rightAns: getRightAnsMU()
            };
            break;
        case "MX":
            var element = {
                type: m[1],
                text: m[2],
                ans: m[6],
                rightAns: getRightAnsMX()
            };
            break;
        case "AS":
            debugger;
            var sets = getAnswersAS();
            var rightAns = getRightAnsAS(sets[0], sets[1]);
            var element = {
                type: m[1],
                text: m[2],
                sets: sets, //
                rightAns: rightAns
            };

            break;
        case "OD": // DA FARE
            var ans = getAnsOD();
            //var orderedAns = getOrderedAnsOD(set);
            var element = {
                type: m[1],
                text: m[2],
                ans: ans
                //orderedSet:
            };
            //ok = checkOD(); // OD -> si controlla che ogni elemento abbia una posizione diversa
            break;
        default:
            element = null;
            //ok = false;
        }
    //console.log(element);
    return element;
}

function getRightAnsMU()
{
    var re = /[\s]*isRight[\s]*=[\s]*\"yes\"[\s]*>(.*)<\/answer>[\s]*/;
    var s;
    var rAns;

    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var counter = 0;
    for (var i = 0; i < lines.length; i++)
    {
        if ((s = re.exec(lines[i])) !== null)
        {
            if (s.index === re.lastIndex)
                re.lastIndex++;

            rAns = i;
            counter++;
        }
    }
    //debugger;
    if (counter == 1) return rAns;
    return null;
}

function getRightAnsMX()
{
    var re = /[\s]*isRight[\s]*=[\s]*\"(yes|no)\"[\s]*>(.*)<\/answer>[\s]*/;
    var s;
    var rAns = [];

    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var counter = 0;
    for (var i = 0; i < lines.length; i++)
    {
        if ((s = re.exec(lines[i])) !== null)
        {
            var element;
            if (s.index === re.lastIndex)
                re.lastIndex++;

            if(s[1]==="yes"){
                counter++;
                element = { i: true };
            }
            else
                element = { i: false };
        }
        rAns.push(element);
    }

    //debugger;
    if (counter >= 1) return rAns;
    return null;
}

function getAnswersAS()
{
    var reA = /<answer [\s]*set[\s]*=[\s]*"(A)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var reB = /<answer [\s]*set[\s]*=[\s]*"(B)" [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var s;
    //debugger;
    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);

    var A = [],
        B = [];

    for (var i = 0; i < lines.length; i++)
    {
        if ((s = reA.exec(lines[i])) !== null) // cerco i match per l'insieme A
        {
            if (s.index === reA.lastIndex)
                reA.lastIndex++;

            var element  = {
                text: s[3],
                id: s[2]
            };
            A.push(element);
        }

        if ((s = reB.exec(lines[i])) !== null) // cerco i match per l'insieme B
        {
            if (s.index === reB.lastIndex)
                reB.lastIndex++;

            var element  = {
                text: s[3],
                id: s[2]
            };
            B.push(element);
        }
    }
    debugger;
    var element = {
        A: A,
        B: B
    }
    return element;  // ritorna un elemento con due array A e B con i rispettivi campi A.text e A.id
}

function getRightAnsAS(A, B)
{
    var set = [];
    var first,
        second;

    if(A.length <= B.length)
    {
        first = A;
        second = B;
    }
    else
    {
        first = B;
        second = A;
    }

    for (var i = 0; i < first.length; i++)
    {
        for (var j = 0; j < second.length; j++)
        {
            if(first[i].pos === second[j].pos)
            {
                var temp = [first[i].text, second[j].text];
                set.push(temp);
            }

        }
    }
    console.log(set);
    return set;
}

function getAnsOD()
{
    var reA = /<answer [\s]*pos[\s]*=[\s]*"(\d)"[\s]*>(.*)<\/answer>/;
    var s;
    //debugger;
    var lines = m[3].split('\n');
    var j = 0;
    for (var i = 0; i < lines.length; i++) {
        if(lines[i] == null)
            j = i;
    }
    lines.pop(j);
    //debugger;
    var matchA = true;

    var A = [];

    for (var i = 0; i < lines.length; i++)
    {
        if ((s = reA.exec(lines[i])) !== null) // cerco i match per l'insieme A
        {
            if (s.index === reA.lastIndex)
                reA.lastIndex++;

            var element  = {
                text: s[2],
                id: s[1]
            };
            A.push(element);
        }
        debugger;
    }
    for (var i = 0; i < A.length; i++) {
        console.log(A[i].pos);
    }

    return A;
}

function getOrderedAnsOD(A)
{
    console.log(A.sort());
    return A;
}<|endoftext|>