public void testAssociateNode() {

    String message = "Some error happened.";
    Throwable cause = new Throwable();
    SoySyntaxException sse = SoySyntaxException.createCausedWithoutMetaInfo(message, cause);

    String testFileContent =
        "{namespace boo}\n"
            + "\n"
            + "/** @param goo */\n"
            + "{template name=\".foo\"}\n"
            + "  {$goo}\n"
            + "{/template}\n";
    SoyFileSetNode soyTree = SharedTestUtils.parseSoyFiles(testFileContent);
    PrintNode pn = (PrintNode) soyTree.getChild(0).getChild(0).getChild(0);

    // Before.
    assertTrue(sse.getMessage().contains(message));
    assertEquals(cause, sse.getCause());
    assertEquals("unknown", sse.getSourceLocation().getFilePath());
    assertEquals(null, sse.getTemplateName());

    SoySyntaxExceptionUtils.associateNode(sse, pn);

    // After.
    assertTrue(sse.getMessage().contains(message));
    assertEquals(cause, sse.getCause());
    assertEquals("no-path", sse.getSourceLocation().getFilePath());
    assertEquals("boo.foo", sse.getTemplateName());
  }
Exemple #2
0
 private void assertParseError(String typeInput, String msg) {
   try {
     parseType(typeInput);
     fail("Input string '" + typeInput + "' should have failed to parse.");
   } catch (SoySyntaxException e) {
     assertThat(e.getMessage()).isEqualTo(msg);
   }
 }
  private void assertCheckIcuEscapingIsNotNeededFails(
      String rawText, String expectedErrorMsgSubstr) {

    try {
      IcuSyntaxUtils.checkIcuEscapingIsNotNeeded(rawText);
      fail();
    } catch (SoySyntaxException sse) {
      assertThat(sse.getMessage()).contains(expectedErrorMsgSubstr);
    }
  }
 /** Private helper for {@code testGenNoncollidingBaseNames()}. */
 private void assertErrorMsgWhenGenNoncollidingBaseNamesForExprs(
     String expectedErrorMsg, String exprListText) {
   List<ExprRootNode<?>> exprRoots =
       ExprParseUtils.parseExprListElseThrowSoySyntaxException(exprListText, "");
   try {
     MsgSubstUnitBaseVarNameUtils.genNoncollidingBaseNamesForExprs(exprRoots, "FALLBACK");
     MsgNodeTest.fail();
   } catch (SoySyntaxException sse) {
     MsgNodeTest.assertTrue(sse.getMessage().contains(expectedErrorMsg));
   }
 }
 /**
  * Assertions function that checks to make sure that name resolution fails with the expected
  * exception.
  *
  * @param fileContent The template source.
  * @param expectedError The expected failure message (a substring).
  */
 private void assertResolveExpressionTypesFails(String expectedError, String fileContent) {
   SoyFileSetNode soyTree =
       SoyFileSetParserBuilder.forFileContents(fileContent)
           .declaredSyntaxVersion(SyntaxVersion.V2_0)
           .doRunInitialParsingPasses(false)
           .typeRegistry(typeRegistry)
           .parse();
   createResolveNamesVisitorForMaxSyntaxVersion().exec(soyTree);
   try {
     createResolveExpressionTypesVisitorForMaxSyntaxVersion().exec(soyTree);
     fail("Expected SoySyntaxException");
   } catch (SoySyntaxException e) {
     assertThat(e.getMessage()).contains(expectedError);
   } catch (IllegalStateException e) {
     // from the exploding error reporter
     assertThat(e.getMessage()).startsWith("Unexpected SoyError:");
     assertThat(e.getMessage()).contains(expectedError);
   }
 }
  public void testAssertNoUnboundGlobals() throws Exception {

    ExprRootNode<?> expr = (new ExpressionParser("BOO + 'aaa' + foo.GOO")).parseExpression();

    Map<String, PrimitiveData> globals =
        ImmutableMap.<String, PrimitiveData>of(
            "BOO",
            StringData.forValue("boo"),
            "GOO",
            StringData.forValue("goo"),
            "foo.MOO",
            StringData.forValue("moo"));

    try {
      ((new SubstituteGlobalsVisitor(globals, null, true)).new SubstituteGlobalsInExprVisitor())
          .exec(expr);
      fail();
    } catch (SoySyntaxException sse) {
      assertTrue(sse.getMessage().contains("Found unbound global 'foo.GOO'."));
    }
  }
  /** Performs checks that only involve templates (uses templateRegistry only). */
  private void checkTemplates() {

    Map<String, TemplateBasicNode> basicTemplatesMap = templateRegistry.getBasicTemplatesMap();
    Map<DelTemplateKey, List<DelegateTemplateDivision>> delTemplatesMap =
        templateRegistry.getDelTemplatesMap();
    Map<String, Set<DelTemplateKey>> delTemplateNameToKeysMap =
        templateRegistry.getDelTemplateNameToKeysMap();

    // Check that no name is reused for both basic and delegate templates.
    Set<String> reusedTemplateNames = Sets.newLinkedHashSet();
    for (DelTemplateKey delTemplateKey : delTemplatesMap.keySet()) {
      if (basicTemplatesMap.containsKey(delTemplateKey.name)) {
        reusedTemplateNames.add(delTemplateKey.name);
      }
    }
    if (reusedTemplateNames.size() > 0) {
      throw SoySyntaxException.createWithoutMetaInfo(
          "Found template name "
              + reusedTemplateNames
              + " being reused for both basic and"
              + " delegate templates.");
    }

    // Check that all delegate templates with the same name have the same declared params and
    // content kind. First, we iterate over template names:
    for (Set<DelTemplateKey> delTemplateKeys : delTemplateNameToKeysMap.values()) {

      TemplateDelegateNode firstDelTemplate = null;
      Set<TemplateParam> firstParamSet = null;
      ContentKind firstContentKind = null;

      // Then, loop over keys that share the same name (effectively, over variants):
      for (DelTemplateKey delTemplateKey : delTemplateKeys) {
        // Then, loop over divisions with the same key (effectively, over priorities):
        for (DelegateTemplateDivision division : delTemplatesMap.get(delTemplateKey)) {
          // Now, over templates in the division (effectively, delpackages):
          for (TemplateDelegateNode delTemplate :
              division.delPackageNameToDelTemplateMap.values()) {
            String currDelPackageName =
                (delTemplate.getDelPackageName() != null)
                    ? delTemplate.getDelPackageName()
                    : "<default>";

            if (firstDelTemplate == null) {
              // First template encountered.
              firstDelTemplate = delTemplate;
              firstParamSet = Sets.newHashSet(delTemplate.getParams());
              firstContentKind = delTemplate.getContentKind();

            } else {
              // Not first template encountered.
              Set<TemplateParam> currParamSet = Sets.newHashSet(delTemplate.getParams());
              if (!currParamSet.equals(firstParamSet)) {
                throw SoySyntaxExceptionUtils.createWithNode(
                    String.format(
                        "Found delegate template with same name '%s' but different param"
                            + " declarations compared to the definition at %s.",
                        firstDelTemplate.getDelTemplateName(),
                        firstDelTemplate.getSourceLocation().toString()),
                    delTemplate);
              }
              if (delTemplate.getContentKind() != firstContentKind) {
                // TODO: This is only *truly* a requirement if the strict mode deltemplates are
                // being called by contextual templates. For a strict-to-strict call, everything
                // is escaped at runtime at the call sites. You could imagine delegating between
                // either a plain-text or rich-html template. However, most developers will write
                // their deltemplates in a parallel manner, and will want to know when the
                // templates differ. Plus, requiring them all to be the same early-on will allow
                // future optimizations to avoid the run-time checks, so it's better to start out
                // as strict as possible and only open up if needed.
                throw SoySyntaxExceptionUtils.createWithNode(
                    String.format(
                        "If one deltemplate has strict autoescaping, all its peers must also be "
                            + "strictly autoescaped with the same content kind: %s != %s. "
                            + "Conflicting definition at %s.",
                        firstContentKind,
                        delTemplate.getContentKind(),
                        firstDelTemplate.getSourceLocation().toString()),
                    delTemplate);
              }
            }
          }
        }
      }
    }
  }