Package com.google.caja.plugin.stages

Source Code of com.google.caja.plugin.stages.CompileHtmlStage

// Copyright (C) 2007 Google Inc.
//
// Licensed 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.

package com.google.caja.plugin.stages;

import com.google.caja.lang.css.CssSchema;
import com.google.caja.lang.html.HtmlSchema;
import com.google.caja.parser.css.CssTree;
import com.google.caja.parser.html.Dom;
import com.google.caja.parser.html.DomParser;
import com.google.caja.parser.js.Block;
import com.google.caja.parser.js.CajoledModule;
import com.google.caja.plugin.Job;
import com.google.caja.plugin.JobEnvelope;
import com.google.caja.plugin.Jobs;
import com.google.caja.plugin.templates.IhtmlRoot;
import com.google.caja.plugin.templates.SafeHtmlChunk;
import com.google.caja.plugin.templates.SafeJsChunk;
import com.google.caja.plugin.templates.ScriptPlaceholder;
import com.google.caja.plugin.templates.TemplateCompiler;
import com.google.caja.plugin.templates.TemplateSanitizer;
import com.google.caja.plugin.templates.ValidatedStylesheet;
import com.google.caja.reporting.MessageQueue;
import com.google.caja.util.Lists;
import com.google.caja.util.Pair;
import com.google.caja.util.Pipeline;

import java.net.URI;
import java.util.Iterator;
import java.util.List;

import org.w3c.dom.Node;

/**
* Compile the HTML, CSS, and JS to HTML and JS.
*
* @author mikesamuel@gmail.com
*/
abstract class CompileHtmlStage implements Pipeline.Stage<Jobs> {
  private final CssSchema cssSchema;
  private final HtmlSchema htmlSchema;

  public CompileHtmlStage(CssSchema cssSchema, HtmlSchema htmlSchema) {
    if (null == cssSchema) { throw new NullPointerException(); }
    if (null == htmlSchema) { throw new NullPointerException(); }
    this.cssSchema = cssSchema;
    this.htmlSchema = htmlSchema;
  }

  public boolean apply(Jobs jobs) {
    List<IhtmlRoot> html = Lists.newArrayList();
    List<ValidatedStylesheet> css = Lists.newArrayList();
    List<ScriptPlaceholder> js = Lists.newArrayList();
    URI baseUriForJsModules = null;

    for (Iterator<JobEnvelope> it = jobs.getJobs().iterator(); it.hasNext();) {
      JobEnvelope env = it.next();
      Job job = env.job;
      switch (env.sourceType) {
        case CSS:
          if (!env.fromCache) {
            css.add(new ValidatedStylesheet(
                env, (CssTree.StyleSheet) job.getRoot(), job.getBaseUri()));
            it.remove();
          }
          break;
        case HTML:
          html.add(new IhtmlRoot(
              env, ((Dom) job.getRoot()).getValue(), job.getBaseUri()));
          // Module loading in embedded <script>s should use the URI of the
          // HTML file as the base URI. We use a heuristic that there's only
          // one HTML file per compilation task, and use the URI of that.
          if (baseUriForJsModules == null) {
            baseUriForJsModules = job.getBaseUri();
          }
          it.remove();
          break;
        case JS:
          if (env.placeholderId != null) {
            js.add(new ScriptPlaceholder(env, env.job.getRoot()));
            it.remove();
          }
          break;
        default: break;
      }
    }

    // TODO(ihab.awad): We do *not* want to support multiple HTML files
    // being cajoled at once since this can be mis-used for modularity
    // and we set up expectations on the part of our users to
    // maintain this behavior, regardless of whatever complexity that
    // might entail.

    MessageQueue mq = jobs.getMessageQueue();

    TemplateSanitizer ts = new TemplateSanitizer(htmlSchema, mq);
    for (IhtmlRoot ihtmlRoot : html) {
      ts.sanitize(ihtmlRoot.root);
    }

    TemplateCompiler tc = new TemplateCompiler(
        html, css, js, cssSchema, htmlSchema,
        jobs.getPluginMeta(), jobs.getMessageContext(), mq);
    Pair<List<SafeHtmlChunk>, List<SafeJsChunk>> htmlAndJs = tc.getSafeHtml(
        DomParser.makeDocument(null, null));

    for (SafeHtmlChunk outputHtml : htmlAndJs.a) {
      Job outJob = makeJobFromHtml(outputHtml.root, outputHtml.baseUri);
      if (outJob != null) {
        jobs.getJobs().add(outputHtml.source.withJob(outJob));
      }
    }

    for (SafeJsChunk outputJs : htmlAndJs.b) {
      if (outputJs.body instanceof Block) {  // Further processing required.
        assert !outputJs.source.fromCache;
        jobs.getJobs().add(outputJs.source.withJob(Job.jsJob(
            (Block) outputJs.body, baseUriForJsModules)));
      } else // Routed through from cache.
        assert outputJs.source.fromCache;
        jobs.getJobs().add(outputJs.source.withJob(Job.cajoledJob(
            (CajoledModule) outputJs.body)));
      }
    }

    return jobs.hasNoFatalErrors();
  }

  abstract Job makeJobFromHtml(Node html, URI baseUri);
}
TOP

Related Classes of com.google.caja.plugin.stages.CompileHtmlStage

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.