servo: Merge #12451 - Generate a list of supported DOM APIs from parsed WebIDLs (from jdm:generate-dom-apis); r=Ms2ger
authorJosh Matthews <josh@joshmatthews.net>
Fri, 15 Jul 2016 15:13:22 -0700
changeset 339305 2f5db0f9f6e0e800de7b5a997428004b91233bdc
parent 339304 a26977fad24652d68810b6936efa2af6a1fc1574
child 339306 06a3525560321ad6f69dc7ede4035c73f8ef2cde
push id31307
push usergszorc@mozilla.com
push dateSat, 04 Feb 2017 00:59:06 +0000
treeherdermozilla-central@94079d43835f [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersMs2ger
servo: Merge #12451 - Generate a list of supported DOM APIs from parsed WebIDLs (from jdm:generate-dom-apis); r=Ms2ger Supplement the existing list of supported CSS properties with an equivalent list of DOM APIs. --- <!-- Thank you for contributing to Servo! Please replace each `[ ]` by `[X]` when the step is complete, and replace `__` with appropriate data: --> - [X] `./mach build -d` does not report any errors - [X] `./mach test-tidy` does not report any errors - [X] These changes do not require tests because automatic generated documentation Source-Repo: https://github.com/servo/servo Source-Revision: 73ad0b928dd158be1eeba30dd21e67d4b9d82048
servo/components/script/dom/bindings/codegen/CodegenRust.py
servo/components/script/dom/bindings/codegen/Configuration.py
servo/components/script/dom/bindings/codegen/GlobalGen.py
servo/components/script/dom/bindings/codegen/api.html.template
servo/components/script/dom/bindings/codegen/apis.html.template
servo/components/script/dom/bindings/codegen/interface.html.template
servo/components/script/dom/bindings/codegen/property.html.template
servo/components/script/makefile.cargo
servo/etc/ci/upload_docs.sh
--- a/servo/components/script/dom/bindings/codegen/CodegenRust.py
+++ b/servo/components/script/dom/bindings/codegen/CodegenRust.py
@@ -3,16 +3,17 @@
 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
 
 # Common codegen classes.
 
 from collections import defaultdict
 from itertools import groupby
 
 import operator
+import os
 import re
 import string
 import textwrap
 import functools
 
 from WebIDL import (
     BuiltinTypes,
     IDLBuiltinType,
@@ -6432,8 +6433,41 @@ impl %(base)s {
                           config.getCallbacks(),
                           config)
 
         # Add the auto-generated comment.
         curr = CGWrapper(curr, pre=AUTOGENERATED_WARNING_COMMENT)
 
         # Done.
         return curr
+
+    @staticmethod
+    def SupportedDomApis(config):
+        descriptors = config.getDescriptors(isExposedConditionally=False)
+
+        base_path = os.path.join('dom', 'bindings', 'codegen')
+        with open(os.path.join(base_path, 'apis.html.template')) as f:
+            base_template = f.read()
+        with open(os.path.join(base_path, 'api.html.template')) as f:
+            api_template = f.read()
+        with open(os.path.join(base_path, 'property.html.template')) as f:
+            property_template = f.read()
+        with open(os.path.join(base_path, 'interface.html.template')) as f:
+            interface_template = f.read()
+
+        apis = []
+        interfaces = []
+        for descriptor in descriptors:
+            props = []
+            for m in descriptor.interface.members:
+                if PropertyDefiner.getStringAttr(m, 'Pref') or \
+                   PropertyDefiner.getStringAttr(m, 'Func') or \
+                   (m.isMethod() and m.isIdentifierLess()):
+                    continue
+                display = m.identifier.name + ('()' if m.isMethod() else '')
+                props += [property_template.replace('${name}', display)]
+            name = descriptor.interface.identifier.name
+            apis += [(api_template.replace('${interface}', name)
+                                  .replace('${properties}', '\n'.join(props)))]
+            interfaces += [interface_template.replace('${interface}', name)]
+
+        return CGGeneric((base_template.replace('${apis}', '\n'.join(apis))
+                                       .replace('${interfaces}', '\n'.join(interfaces))))
--- a/servo/components/script/dom/bindings/codegen/Configuration.py
+++ b/servo/components/script/dom/bindings/codegen/Configuration.py
@@ -82,16 +82,18 @@ class Configuration:
             elif key == 'hasInterfaceObject':
                 getter = lambda x: x.interface.hasInterfaceObject()
             elif key == 'isCallback':
                 getter = lambda x: x.interface.isCallback()
             elif key == 'isJSImplemented':
                 getter = lambda x: x.interface.isJSImplemented()
             elif key == 'isGlobal':
                 getter = lambda x: x.isGlobal()
+            elif key == 'isExposedConditionally':
+                getter = lambda x: x.interface.isExposedConditionally()
             else:
                 getter = lambda x: getattr(x, key)
             curr = filter(lambda x: getter(x) == val, curr)
         return curr
 
     def getEnums(self, webIDLFile):
         return filter(lambda e: e.filename() == webIDLFile, self.enums)
 
--- a/servo/components/script/dom/bindings/codegen/GlobalGen.py
+++ b/servo/components/script/dom/bindings/codegen/GlobalGen.py
@@ -27,16 +27,18 @@ def generate_file(config, name, filename
 
 def main():
     # Parse arguments.
     from optparse import OptionParser
     usageString = "usage: %prog [options] configFile outputdir webidldir [files]"
     o = OptionParser(usage=usageString)
     o.add_option("--cachedir", dest='cachedir', default=None,
                  help="Directory in which to cache lex/parse tables.")
+    o.add_option("--only-html", dest='only_html', action="store_true",
+                 help="Only generate HTML from WebIDL inputs")
     (options, args) = o.parse_args()
 
     if len(args) < 2:
         o.error(usageString)
 
     configFile = args[0]
     outputdir = args[1]
     baseDir = args[2]
@@ -46,31 +48,37 @@ def main():
     parser = WebIDL.Parser(options.cachedir)
     for filename in fileList:
         fullPath = os.path.normpath(os.path.join(baseDir, filename))
         with open(fullPath, 'rb') as f:
             lines = f.readlines()
         parser.parse(''.join(lines), fullPath)
     parserResults = parser.finish()
 
-    # Write the parser results out to a pickle.
-    resultsPath = os.path.join(outputdir, 'ParserResults.pkl')
-    with open(resultsPath, 'wb') as resultsFile:
-        cPickle.dump(parserResults, resultsFile, -1)
+    if not options.only_html:
+        # Write the parser results out to a pickle.
+        resultsPath = os.path.join(outputdir, 'ParserResults.pkl')
+        with open(resultsPath, 'wb') as resultsFile:
+            cPickle.dump(parserResults, resultsFile, -1)
 
     # Load the configuration.
     config = Configuration(configFile, parserResults)
 
     to_generate = [
-        ('PrototypeList', 'PrototypeList.rs'),
-        ('RegisterBindings', 'RegisterBindings.rs'),
-        ('InterfaceObjectMap', 'InterfaceObjectMap.rs'),
-        ('InterfaceTypes', 'InterfaceTypes.rs'),
-        ('InheritTypes', 'InheritTypes.rs'),
-        ('Bindings', os.path.join('Bindings', 'mod.rs')),
-        ('UnionTypes', 'UnionTypes.rs'),
+        ('SupportedDomApis', 'apis.html'),
     ]
 
+    if not options.only_html:
+        to_generate = [
+            ('PrototypeList', 'PrototypeList.rs'),
+            ('RegisterBindings', 'RegisterBindings.rs'),
+            ('InterfaceObjectMap', 'InterfaceObjectMap.rs'),
+            ('InterfaceTypes', 'InterfaceTypes.rs'),
+            ('InheritTypes', 'InheritTypes.rs'),
+            ('Bindings', os.path.join('Bindings', 'mod.rs')),
+            ('UnionTypes', 'UnionTypes.rs'),
+        ]
+
     for name, filename in to_generate:
         generate_file(config, name, os.path.join(outputdir, filename))
 
 if __name__ == '__main__':
     main()
new file mode 100644
--- /dev/null
+++ b/servo/components/script/dom/bindings/codegen/api.html.template
@@ -0,0 +1,6 @@
+<table id="${interface}">
+<tr>
+<th>${interface}</th>
+</tr>
+${properties}
+</table>
new file mode 100644
--- /dev/null
+++ b/servo/components/script/dom/bindings/codegen/apis.html.template
@@ -0,0 +1,35 @@
+<!DOCTYPE html>
+<html lang="en">
+<head>
+    <meta charset="utf-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1.0">
+    <meta name="generator" content="rustdoc">
+    <meta name="description" content="API documentation for the Rust `servo` crate.">
+    <meta name="keywords" content="rust, rustlang, rust-lang, servo">
+    <title>Supported DOM APIs - servo - Rust</title>
+    <link rel="stylesheet" type="text/css" href="../rustdoc.css">
+    <link rel="stylesheet" type="text/css" href="../main.css">
+</head>
+<body class="rustdoc">
+    <!--[if lte IE 8]>
+    <div class="warning">
+        This old browser is unsupported and will most likely display funky
+        things.
+    </div>
+    <![endif]-->
+    <nav class='sidebar'>
+      <div class='block crate'>
+        <h3>Interfaces</h3>
+        <ul>
+          ${interfaces}
+        </ul>
+      </div>
+    </nav>
+    <section id='main' class="content mod">
+      <h1 class='fqn'><span class='in-band'>DOM APIs currently supported in <a class='mod' href=''>Servo</a></span></h1>
+      <div id='properties' class='docblock'>
+        ${apis}
+      </div>
+    </section>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/servo/components/script/dom/bindings/codegen/interface.html.template
@@ -0,0 +1,1 @@
+<li><a href="#${interface}">${interface}</a></li>
new file mode 100644
--- /dev/null
+++ b/servo/components/script/dom/bindings/codegen/property.html.template
@@ -0,0 +1,3 @@
+<tr>
+  <td>${name}</td>
+</tr>
--- a/servo/components/script/makefile.cargo
+++ b/servo/components/script/makefile.cargo
@@ -13,17 +13,17 @@ AUTOGEN_SRC = $(foreach var,$(BINDINGS),
 export PYTHONPATH := $(BINDINGS_SRC)/parser:$(BINDINGS_SRC)/ply:$(PYTHONPATH)
 
 CACHE_DIR = $(OUT_DIR)/_cache
 
 bindinggen_dependencies := $(addprefix $(BINDINGS_SRC)/,BindingGen.py Bindings.conf Configuration.py CodegenRust.py parser/WebIDL.py) $(OUT_DIR)/ParserResults.pkl $(OUT_DIR)/Bindings/.done
 
 globalgen_dependencies := $(addprefix $(BINDINGS_SRC)/,GlobalGen.py Bindings.conf Configuration.py CodegenRust.py parser/WebIDL.py) $(CACHE_DIR)/.done $(OUT_DIR)/Bindings/.done
 
-.PHONY: all
+.PHONY: all dom_docs
 all: $(AUTOGEN_SRC)
 
 $(OUT_DIR)/Bindings/.done:
 	mkdir -p $(OUT_DIR)/Bindings
 	touch $@
 
 $(CACHE_DIR)/.done:
 	mkdir -p $(CACHE_DIR)
@@ -33,16 +33,26 @@ all: $(AUTOGEN_SRC)
 	$(PYTHON) \
 	  $(BINDINGS_SRC)/GlobalGen.py \
 	    --cachedir=$(CACHE_DIR) \
 	    $(BINDINGS_SRC)/Bindings.conf \
 	    $(OUT_DIR) \
 	    . \
 	    $(WEBIDLS)
 
+dom_docs: $(CACHE_DIR)/.done
+	$(PYTHON) \
+	  $(BINDINGS_SRC)/GlobalGen.py \
+            --cachedir=$(CACHE_DIR) \
+	    --only-html \
+	    $(BINDINGS_SRC)/Bindings.conf \
+	    $(OUT_DIR) \
+	    . \
+	    $(WEBIDLS)
+
 $(AUTOGEN_SRC): $(OUT_DIR)/Bindings/%Binding.rs: $(bindinggen_dependencies) \
 						 $(addprefix $(WEBIDLS_SRC)/,%.webidl)
 	$(PYTHON) \
 	  $(BINDINGS_SRC)/BindingGen.py \
 	    $(BINDINGS_SRC)/Bindings.conf \
 	    $(OUT_DIR) \
 	    $(OUT_DIR)/Bindings/$*Binding \
 	    $(addprefix $(WEBIDLS_SRC)/,$*.webidl)
--- a/servo/etc/ci/upload_docs.sh
+++ b/servo/etc/ci/upload_docs.sh
@@ -11,10 +11,12 @@ set -o pipefail
 cd "$(dirname $0)/../.."
 
 ./mach doc
 # etc/doc.servo.org/index.html overwrites $(mach rust-root)/doc/index.html
 cp etc/doc.servo.org/* target/doc/
 
 python components/style/properties/build.py servo html
 
+OUT_DIR="`pwd`/target/doc" make -f makefile.cargo -C components/script dom_docs
+
 ghp-import -n target/doc
 git push -qf "https://${TOKEN}@github.com/servo/doc.servo.org.git" gh-pages