171 lines
6.5 KiB
Python
Executable File
171 lines
6.5 KiB
Python
Executable File
#!/usr/bin/env python
|
|
#
|
|
# Copyright (C) 2011 Google Inc. All rights reserved.
|
|
#
|
|
# Redistribution and use in source and binary forms, with or without
|
|
# modification, are permitted provided that the following conditions are
|
|
# met:
|
|
#
|
|
# * Redistributions of source code must retain the above copyright
|
|
# notice, this list of conditions and the following disclaimer.
|
|
# * Redistributions in binary form must reproduce the above
|
|
# copyright notice, this list of conditions and the following disclaimer
|
|
# in the documentation and/or other materials provided with the
|
|
# distribution.
|
|
# * Neither the name of Google Inc. nor the names of its
|
|
# contributors may be used to endorse or promote products derived from
|
|
# this software without specific prior written permission.
|
|
#
|
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
|
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
|
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
|
# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
|
# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
|
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
|
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
|
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
|
|
import codecs
|
|
import logging
|
|
import os
|
|
import os.path
|
|
import re
|
|
import sys
|
|
|
|
from webkitpy.common.checkout.scm import SCMDetector
|
|
from webkitpy.common.system.filesystem import FileSystem
|
|
from webkitpy.common.system.executive import Executive
|
|
from webkitpy.common.system.logutils import configure_logging
|
|
from webkitpy.style.checker import ProcessorBase
|
|
from webkitpy.style.filereader import TextFileReader
|
|
from webkitpy.style.main import change_directory
|
|
|
|
_inspector_directory = "Source/WebCore/inspector/front-end"
|
|
_localized_strings = "Source/WebCore/en.lproj/localizedStrings.js"
|
|
|
|
_log = logging.getLogger("check-inspector-strings")
|
|
|
|
class StringsExtractor(ProcessorBase):
|
|
def __init__(self, patterns):
|
|
self._patterns = patterns
|
|
self.strings = []
|
|
for p in self._patterns:
|
|
self.strings.append([])
|
|
|
|
def should_process(self, file_path):
|
|
return file_path.endswith(".js") and (not file_path.endswith("InjectedScript.js"))
|
|
|
|
def process(self, lines, file_path, line_numbers=None):
|
|
for line in lines:
|
|
comment_start = line.find("//")
|
|
if comment_start != -1:
|
|
line = line[:comment_start]
|
|
index = 0
|
|
for pattern in self._patterns:
|
|
line_strings = re.findall(pattern, line)
|
|
for string in line_strings:
|
|
self.strings[index].append(string)
|
|
index += 1
|
|
|
|
class LocalizedStringsExtractor:
|
|
def __init__(self):
|
|
self.localized_strings = []
|
|
|
|
def process_file(self, file_path):
|
|
localized_strings_file = codecs.open(file_path, encoding="utf-8", mode="r")
|
|
try:
|
|
contents = localized_strings_file.read()
|
|
lines = contents.split("\n")
|
|
for line in lines:
|
|
match = re.match(r"localizedStrings\[\"((?:[^\"\\]|\\.)*?)\"", line)
|
|
if match:
|
|
self.localized_strings.append(match.group(1))
|
|
finally:
|
|
localized_strings_file.close()
|
|
|
|
def extract_ui_strings(str, out):
|
|
line_unrecognized = False
|
|
idx = 0
|
|
while idx < len(str):
|
|
idx = str.find("WI.UIString(", idx)
|
|
if idx == -1:
|
|
break
|
|
idx = idx + len("WI.UIString(")
|
|
balance = 1
|
|
item_recognized = False
|
|
while idx < len(str):
|
|
if str[idx] == ')':
|
|
balance = balance - 1
|
|
if balance == 0:
|
|
break
|
|
elif str[idx] == '(':
|
|
balance = balance + 1
|
|
elif balance == 1:
|
|
if str[idx] == ',':
|
|
break
|
|
elif str[idx] == '"':
|
|
str_idx = idx + 1
|
|
while str_idx < len(str):
|
|
if str[str_idx] == '\\':
|
|
str_idx = str_idx + 1
|
|
elif str[str_idx] == '"':
|
|
out.add(str[idx + 1 : str_idx])
|
|
idx = str_idx
|
|
item_recognized = True
|
|
break
|
|
str_idx = str_idx + 1
|
|
idx = idx + 1
|
|
if not item_recognized:
|
|
line_unrecognized = True
|
|
if line_unrecognized:
|
|
_log.info("Unrecognized: %s" % str)
|
|
|
|
if __name__ == "__main__":
|
|
configure_logging()
|
|
|
|
cwd = os.path.abspath(os.curdir)
|
|
filesystem = FileSystem()
|
|
scm = SCMDetector(filesystem, Executive()).detect_scm_system(cwd)
|
|
|
|
if scm is None:
|
|
_log.error("WebKit checkout not found: You must run this script "
|
|
"from within a WebKit checkout.")
|
|
sys.exit(1)
|
|
|
|
checkout_root = scm.checkout_root
|
|
_log.debug("WebKit checkout found with root: %s" % checkout_root)
|
|
change_directory(filesystem, checkout_root=checkout_root, paths=None)
|
|
|
|
strings_extractor = StringsExtractor([r"(WI\.UIString\(.*)", r"\"((?:[^\"\\]|\\.)*?)\""])
|
|
file_reader = TextFileReader(filesystem, strings_extractor)
|
|
file_reader.process_paths([_inspector_directory])
|
|
localized_strings_extractor = LocalizedStringsExtractor()
|
|
localized_strings_extractor.process_file(_localized_strings)
|
|
raw_ui_strings = frozenset(strings_extractor.strings[0])
|
|
ui_strings = set()
|
|
for s in raw_ui_strings:
|
|
extract_ui_strings(s, ui_strings)
|
|
strings = frozenset(strings_extractor.strings[1])
|
|
localized_strings = frozenset(localized_strings_extractor.localized_strings)
|
|
|
|
new_strings = ui_strings - localized_strings
|
|
for s in new_strings:
|
|
_log.info("New: \"%s\"" % (s))
|
|
old_strings = localized_strings - ui_strings
|
|
suspicious_strings = strings & old_strings
|
|
for s in suspicious_strings:
|
|
_log.info("Suspicious: \"%s\"" % (s))
|
|
unused_strings = old_strings - strings
|
|
for s in unused_strings:
|
|
_log.info("Unused: \"%s\"" % (s))
|
|
|
|
localized_strings_duplicates = {}
|
|
for s in localized_strings_extractor.localized_strings:
|
|
if s in localized_strings_duplicates:
|
|
_log.info("Duplicate: \"%s\"" % (s))
|
|
else:
|
|
localized_strings_duplicates.setdefault(s)
|