All files / src/helpers normalize-arguments.js

6.45% Statements 2/31
0% Branches 0/14
0% Functions 0/9
6.45% Lines 2/31

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 872x                                                                                                                                                                         2x  
const t = require('@babel/types');
 
function assertType(nodePath, type, opts) {
  if (!t[`is${type}`](nodePath.node, opts)) {
    throw nodePath.buildCodeFrameError(`Unsupported type ${nodePath.type}`);
  }
}
 
function assertInStyles(stringOrIdentifier, styleNames) {
  const value = t.isStringLiteral(stringOrIdentifier)
    ? stringOrIdentifier.node.value
    : stringOrIdentifier.node.name;
 
  if (!styleNames.includes(value)) {
    throw stringOrIdentifier.buildCodeFrameError(
      `Property ${value} does not exist in style object`
    );
  }
}
 
function normalizeObjectExpression(objectExpr, styleNames) {
  return objectExpr.get('properties').map(prop => {
    assertType(prop, 'ObjectProperty', { computed: false });
    assertInStyles(prop.get('key'), styleNames);
 
    return {
      test: prop.node.value,
      value: prop.node.key.name
    };
  });
}
 
function normalizeLogicalExpression(logicalExpr, styleNames) {
  assertType(logicalExpr.get('right'), 'StringLiteral');
  assertInStyles(logicalExpr.get('right'), styleNames);
 
  return {
    test: logicalExpr.node.left,
    value: logicalExpr.node.right.value
  };
}
 
function normalizeConditionalExpression(conditionalExpr, styleNames) {
  assertType(conditionalExpr.get('consequent'), 'StringLiteral');
  assertType(conditionalExpr.get('alternate'), 'StringLiteral');
  assertInStyles(conditionalExpr.get('alternate'), styleNames);
  assertInStyles(conditionalExpr.get('consequent'), styleNames);
 
  return [
    conditionalExpr.node.alternate.value,
    {
      test: conditionalExpr.node.test,
      value: conditionalExpr.node.consequent.value
    }
  ];
}
 
function normalizeStringLiteral(stringLiteral, styleNames) {
  assertInStyles(stringLiteral, styleNames);
  return stringLiteral.node.value;
}
 
// Map resolver arguments to strings and logical ANDs
function normalizeArguments(callExpr, styleNames) {
  return callExpr.get('arguments').flatMap(arg => {
    if (t.isObjectExpression(arg.node)) {
      return normalizeObjectExpression(arg, styleNames);
    }
 
    if (t.isStringLiteral(arg.node)) {
      return normalizeStringLiteral(arg, styleNames);
    }
 
    if (t.isLogicalExpression(arg.node, { operator: '&&' })) {
      return normalizeLogicalExpression(arg, styleNames);
    }
 
    if (t.isConditionalExpression(arg.node)) {
      return normalizeConditionalExpression(arg, styleNames);
    }
 
    throw arg.buildCodeFrameError(`Unsupported type ${arg.node.type}`);
  });
}
 
module.exports = normalizeArguments;