15f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#!/usr/bin/env python
25f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
35f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Copyright 2012 The Closure Linter Authors. All Rights Reserved.
45f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Licensed under the Apache License, Version 2.0 (the "License");
55f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# you may not use this file except in compliance with the License.
65f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# You may obtain a copy of the License at
75f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
85f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#      http://www.apache.org/licenses/LICENSE-2.0
95f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Unless required by applicable law or agreed to in writing, software
115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# distributed under the License is distributed on an "AS-IS" BASIS,
125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# See the License for the specific language governing permissions and
145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# limitations under the License.
155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)"""Unit tests for the javascriptstatetracker module."""
175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Allow non-Google copyright
195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# pylint: disable=g-bad-file-header
205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)__author__ = ('nnaze@google.com (Nathan Naze)')
225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import unittest as googletest
255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from closure_linter import javascripttokens
275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from closure_linter import testutil
285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from closure_linter import tokenutil
295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)_FUNCTION_SCRIPT = """\
325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)var a = 3;
335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)function foo(aaa, bbb, ccc) {
355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  var b = 4;
365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)}
375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)/**
405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) * JSDoc comment.
415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) */
425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)var bar = function(ddd, eee, fff) {
435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)};
455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)/**
485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) * Verify that nested functions get their proper parameters recorded.
495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) */
505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)var baz = function(ggg, hhh, iii) {
515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  var qux = function(jjj, kkk, lll) {
525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  };
535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  // make sure that entering a new block does not change baz' parameters.
545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  {};
555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)};
565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)"""
585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)class FunctionTest(googletest.TestCase):
615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  def testFunctionParse(self):
635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    functions, _ = testutil.ParseFunctionsAndComments(_FUNCTION_SCRIPT)
645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(4, len(functions))
655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # First function
675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    function = functions[0]
685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(['aaa', 'bbb', 'ccc'], function.parameters)
695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    start_token = function.start_token
715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    end_token = function.end_token
725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(
745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        javascripttokens.JavaScriptTokenType.FUNCTION_DECLARATION,
755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        function.start_token.type)
765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('function', start_token.string)
785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(3, start_token.line_number)
795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(0, start_token.start_index)
805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('}', end_token.string)
825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(5, end_token.line_number)
835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(0, end_token.start_index)
845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('foo', function.name)
865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertIsNone(function.doc)
885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Second function
905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    function = functions[1]
915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(['ddd', 'eee', 'fff'], function.parameters)
925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    start_token = function.start_token
945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    end_token = function.end_token
955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(
975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        javascripttokens.JavaScriptTokenType.FUNCTION_DECLARATION,
985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        function.start_token.type)
995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('function', start_token.string)
1015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(11, start_token.line_number)
1025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(10, start_token.start_index)
1035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('}', end_token.string)
1055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(13, end_token.line_number)
1065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(0, end_token.start_index)
1075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('bar', function.name)
1095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertIsNotNone(function.doc)
1115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Check function JSDoc
1135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc = function.doc
1145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc_tokens = tokenutil.GetTokenRange(doc.start_token, doc.end_token)
1155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    comment_type = javascripttokens.JavaScriptTokenType.COMMENT
1175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    comment_tokens = filter(lambda t: t.type is comment_type, doc_tokens)
1185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('JSDoc comment.',
1205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                      tokenutil.TokensToString(comment_tokens).strip())
1215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Third function
1235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    function = functions[2]
1245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(['ggg', 'hhh', 'iii'], function.parameters)
1255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    start_token = function.start_token
1275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    end_token = function.end_token
1285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(
1305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        javascripttokens.JavaScriptTokenType.FUNCTION_DECLARATION,
1315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        function.start_token.type)
1325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('function', start_token.string)
1345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(19, start_token.line_number)
1355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(10, start_token.start_index)
1365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('}', end_token.string)
1385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(24, end_token.line_number)
1395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(0, end_token.start_index)
1405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('baz', function.name)
1425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertIsNotNone(function.doc)
1435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Fourth function (inside third function)
1455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    function = functions[3]
1465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(['jjj', 'kkk', 'lll'], function.parameters)
1475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    start_token = function.start_token
1495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    end_token = function.end_token
1505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(
1525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        javascripttokens.JavaScriptTokenType.FUNCTION_DECLARATION,
1535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        function.start_token.type)
1545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('function', start_token.string)
1565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(20, start_token.line_number)
1575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(12, start_token.start_index)
1585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('}', end_token.string)
1605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(21, end_token.line_number)
1615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(2, end_token.start_index)
1625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals('qux', function.name)
1645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertIsNone(function.doc)
1655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)class CommentTest(googletest.TestCase):
1695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  def testGetDescription(self):
1715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    comment = self._ParseComment("""
1725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
1735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting goog.foo.
1745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         *
1755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * This is the second line.
1765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * @param {number} foo The count of foo.
1775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
1785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        target;""")
1795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEqual(
1815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        'Comment targeting goog.foo.\n\nThis is the second line.',
1825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        comment.description)
1835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  def testCommentGetTarget(self):
1855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('goog.foo', """
1865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
1875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting goog.foo.
1885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
1895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        goog.foo = 6;
1905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
1915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('bar', """
1935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
1945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting bar.
1955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
1965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        var bar = "Karate!";
1975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
1985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('doThing', """
2005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting doThing.
2025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        function doThing() {};
2045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('this.targetProperty', """
2075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        goog.bar.Baz = function() {
2085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)          /**
2095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)           * Comment targeting targetProperty.
2105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)           */
2115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)          this.targetProperty = 3;
2125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        };
2135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('goog.bar.prop', """
2165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting goog.bar.prop.
2185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        goog.bar.prop;
2205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('goog.aaa.bbb', """
2235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting goog.aaa.bbb.
2255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (goog.aaa.bbb)
2275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('theTarget', """
2305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment targeting symbol preceded by newlines, whitespace,
2325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * and parens -- things we ignore.
2335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (theTarget)
2355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget(None, """
2385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * @fileoverview File overview.
2405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (notATarget)
2425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget(None, """
2455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment that doesn't find a target.
2475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('theTarget.is.split.across.lines', """
2515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment that addresses a symbol split across lines.
2535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (theTarget.is.split
2555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)             .across.lines)
2565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertCommentTarget('theTarget.is.split.across.lines', """
2595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        /**
2605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         * Comment that addresses a symbol split across lines.
2615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)         */
2625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (theTarget.is.split.
2635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                across.lines)
2645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        """)
2655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  def _ParseComment(self, script):
2675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """Parse a script that contains one comment and return it."""
2685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    _, comments = testutil.ParseFunctionsAndComments(script)
2695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(1, len(comments))
2705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return comments[0]
2715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  def assertCommentTarget(self, target, script):
2735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    comment = self._ParseComment(script)
2745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    self.assertEquals(target, comment.GetTargetIdentifier())
2755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)if __name__ == '__main__':
2785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  googletest.main()
279