# Copyright 2016 The Chromium Authors
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Unittest for issue tracker views."""
from __future__ import print_function
from __future__ import division
from __future__ import absolute_import

import logging
import unittest

try:
  from mox3 import mox
except ImportError:
  import mox

from google.appengine.api import app_identity
import ezt

from framework import framework_views
from framework import gcs_helpers
from framework import template_helpers
from framework import urls
from mrproto import project_pb2
from mrproto import tracker_pb2
from services import service_manager
from testing import fake
from testing import testing_helpers
from tracker import attachment_helpers
from tracker import tracker_bizobj
from tracker import tracker_constants
from tracker import tracker_helpers
from tracker import tracker_views


def _Issue(project_name, local_id, summary, status):
  issue = tracker_pb2.Issue()
  issue.project_name = project_name
  issue.local_id = local_id
  issue.issue_id = 100000 + local_id
  issue.summary = summary
  issue.status = status
  return issue


def _MakeConfig():
  config = tracker_pb2.ProjectIssueConfig()
  config.well_known_labels = [
    tracker_pb2.LabelDef(
        label='Priority-High', label_docstring='Must be resolved'),
    tracker_pb2.LabelDef(
        label='Priority-Low', label_docstring='Can be slipped'),
    ]
  config.well_known_statuses.append(tracker_pb2.StatusDef(
      status='New', means_open=True))
  config.well_known_statuses.append(tracker_pb2.StatusDef(
      status='Old', means_open=False))
  return config


class IssueViewTest(unittest.TestCase):

  def setUp(self):
    self.issue1 = _Issue('proj', 1, 'not too long summary', 'New')
    self.issue2 = _Issue('proj', 2, 'sum 2', '')
    self.issue3 = _Issue('proj', 3, 'sum 3', '')
    self.issue4 = _Issue('proj', 4, 'sum 4', '')

    self.issue1.reporter_id = 1002
    self.issue1.owner_id = 2002
    self.issue1.labels.extend(['A', 'B'])
    self.issue1.derived_labels.extend(['C', 'D'])

    self.issue2.reporter_id = 2002
    self.issue2.labels.extend(['foo', 'bar'])
    self.issue2.blocked_on_iids.extend(
        [self.issue1.issue_id, self.issue3.issue_id])
    self.issue2.blocking_iids.extend(
        [self.issue1.issue_id, self.issue4.issue_id])
    dref = tracker_pb2.DanglingIssueRef()
    dref.project = 'codesite'
    dref.issue_id = 5001
    self.issue2.dangling_blocking_refs.append(dref)

    self.issue3.reporter_id = 3002
    self.issue3.labels.extend(['Hot'])

    self.issue4.reporter_id = 3002
    self.issue4.labels.extend(['Foo', 'Bar'])

    self.restricted = _Issue('proj', 7, 'summary 7', '')
    self.restricted.labels.extend([
        'Restrict-View-Commit', 'Restrict-View-MyCustomPerm'])
    self.restricted.derived_labels.extend([
        'Restrict-AddIssueComment-Commit', 'Restrict-EditIssue-Commit',
        'Restrict-Action-NeededPerm'])

    self.users_by_id = {
        0: 'user 0',
        1002: 'user 1002',
        2002: 'user 2002',
        3002: 'user 3002',
        4002: 'user 4002',
        }

  def CheckSimpleIssueView(self, config):
    view1 = tracker_views.IssueView(
        self.issue1, self.users_by_id, config)
    self.assertEqual('not too long summary', view1.summary)
    self.assertEqual('New', view1.status.name)
    self.assertEqual('user 2002', view1.owner)
    self.assertEqual('A', view1.labels[0].name)
    self.assertEqual('B', view1.labels[1].name)
    self.assertEqual('C', view1.derived_labels[0].name)
    self.assertEqual('D', view1.derived_labels[1].name)
    self.assertEqual([], view1.blocked_on)
    self.assertEqual([], view1.blocking)
    detail_url = '/p/%s%s?id=%d' % (
        self.issue1.project_name, urls.ISSUE_DETAIL,
        self.issue1.local_id)
    self.assertEqual(detail_url, view1.detail_relative_url)
    return view1

  def testSimpleIssueView(self):
    config = tracker_pb2.ProjectIssueConfig()
    view1 = self.CheckSimpleIssueView(config)
    self.assertEqual('', view1.status.docstring)

    config.well_known_statuses.append(tracker_pb2.StatusDef(
        status='New', status_docstring='Issue has not had review yet'))
    view1 = self.CheckSimpleIssueView(config)
    self.assertEqual('Issue has not had review yet',
                     view1.status.docstring)
    self.assertIsNone(view1.restrictions.has_restrictions)
    self.assertEqual('', view1.restrictions.view)
    self.assertEqual('', view1.restrictions.add_comment)
    self.assertEqual('', view1.restrictions.edit)

  def testIsOpen(self):
    config = _MakeConfig()
    view1 = tracker_views.IssueView(
        self.issue1, self.users_by_id, config)
    self.assertEqual(ezt.boolean(True), view1.is_open)

    self.issue1.status = 'Old'
    view1 = tracker_views.IssueView(
        self.issue1, self.users_by_id, config)
    self.assertEqual(ezt.boolean(False), view1.is_open)

  def testIssueViewWithRestrictions(self):
    view = tracker_views.IssueView(
        self.restricted, self.users_by_id, _MakeConfig())
    self.assertTrue(view.restrictions.has_restrictions)
    self.assertEqual('Commit and MyCustomPerm', view.restrictions.view)
    self.assertEqual('Commit', view.restrictions.add_comment)
    self.assertEqual('Commit', view.restrictions.edit)
    self.assertEqual(['Restrict-Action-NeededPerm'], view.restrictions.other)
    self.assertEqual('Restrict-View-Commit', view.labels[0].name)
    self.assertTrue(view.labels[0].is_restrict)


class RestrictionsViewTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class AttachmentViewTest(unittest.TestCase):

  def setUp(self):
    self.orig_sign_attachment_id = attachment_helpers.SignAttachmentID
    attachment_helpers.SignAttachmentID = (
        lambda aid: 'signed_%d' % aid)

  def tearDown(self):
    attachment_helpers.SignAttachmentID = self.orig_sign_attachment_id

  def MakeViewAndVerifyFields(
      self, size, name, mimetype, expected_size_str, expect_viewable):
    attach_pb = tracker_pb2.Attachment()
    attach_pb.filesize = size
    attach_pb.attachment_id = 12345
    attach_pb.filename = name
    attach_pb.mimetype = mimetype

    view = tracker_views.AttachmentView(attach_pb, 'proj')
    self.assertEqual('/images/paperclip.png', view.iconurl)
    self.assertEqual(expected_size_str, view.filesizestr)
    dl = 'attachment?aid=12345&signed_aid=signed_12345'
    self.assertEqual(dl, view.downloadurl)
    if expect_viewable:
      self.assertEqual(dl + '&inline=1', view.url)
      self.assertEqual(dl + '&inline=1&thumb=1', view.thumbnail_url)
    else:
      self.assertEqual(None, view.url)
      self.assertEqual(None, view.thumbnail_url)

  def testNonImage(self):
    self.MakeViewAndVerifyFields(
        123, 'file.ext', 'funky/bits', '123 bytes', False)

  def testViewableImage(self):
    self.MakeViewAndVerifyFields(
        123, 'logo.gif', 'image/gif', '123 bytes', True)

    self.MakeViewAndVerifyFields(
        123, 'screenshot.jpg', 'image/jpeg', '123 bytes', True)

  def testHugeImage(self):
    self.MakeViewAndVerifyFields(
        18 * 1024 * 1024, 'panorama.png', 'image/jpeg', '18.0 MB', False)

  def testViewableText(self):
    name = 'hello.c'
    attach_pb = tracker_pb2.Attachment()
    attach_pb.filesize = 1234
    attach_pb.attachment_id = 12345
    attach_pb.filename = name
    attach_pb.mimetype = 'text/plain'
    view = tracker_views.AttachmentView(attach_pb, 'proj')

    view_url = '/p/proj/issues/attachmentText?aid=12345'
    self.assertEqual(view_url, view.url)


class LogoViewTest(unittest.TestCase):

  def setUp(self):
    self.mox = mox.Mox()

  def tearDown(self):
    self.mox.UnsetStubs()
    self.mox.ResetAll()

  def testProjectWithLogo(self):
    bucket_name = 'testbucket'
    logo_gcs_id = '123'
    logo_file_name = 'logo.png'
    project_pb = project_pb2.MakeProject(
        'testProject', logo_gcs_id=logo_gcs_id, logo_file_name=logo_file_name)

    self.mox.StubOutWithMock(app_identity, 'get_default_gcs_bucket_name')
    app_identity.get_default_gcs_bucket_name().AndReturn(bucket_name)

    self.mox.StubOutWithMock(gcs_helpers, 'SignUrl')
    gcs_helpers.SignUrl(bucket_name,
        logo_gcs_id + '-thumbnail').AndReturn('signed/url')
    gcs_helpers.SignUrl(bucket_name, logo_gcs_id).AndReturn('signed/url')

    self.mox.ReplayAll()

    view = tracker_views.LogoView(project_pb)
    self.mox.VerifyAll()
    self.assertEqual('logo.png', view.filename)
    self.assertEqual('image/png', view.mimetype)
    self.assertEqual('signed/url', view.thumbnail_url)
    self.assertEqual(
        'signed/url&response-content-displacement=attachment%3B'
        '+filename%3Dlogo.png', view.viewurl)

  def testProjectWithNoLogo(self):
    project_pb = project_pb2.MakeProject('testProject')
    view = tracker_views.LogoView(project_pb)
    self.assertEqual('', view.thumbnail_url)
    self.assertEqual('', view.viewurl)


class AmendmentViewTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class ComponentDefViewTest(unittest.TestCase):
  def setUp(self):
    self.services = service_manager.Services(
        user=fake.UserService(),
        config=fake.ConfigService())
    self.services.user.TestAddUser('admin@example.com', 111)
    self.services.user.TestAddUser('cc@example.com', 222)
    self.users_by_id = framework_views.MakeAllUserViews(
      'cnxn', self.services.user, [111, 222])
    self.services.config.TestAddLabelsDict({'Hot': 1, 'Cold': 2})
    self.cd = tracker_bizobj.MakeComponentDef(
      10, 789, 'UI', 'User interface', False,
      [111], [222], 0, 111, label_ids=[1, 2])

  def testRootComponent(self):
    view = tracker_views.ComponentDefView(
       'cnxn', self.services, self.cd, self.users_by_id)
    self.assertEqual('', view.parent_path)
    self.assertEqual('UI', view.leaf_name)
    self.assertEqual('User interface', view.docstring_short)
    self.assertEqual('admin@example.com', view.admins[0].email)
    self.assertEqual(['Hot', 'Cold'], view.labels)
    self.assertEqual('all toplevel active ', view.classes)

  def testNestedComponent(self):
    self.cd.path = 'UI>Dialogs>Print'
    view = tracker_views.ComponentDefView(
       'cnxn', self.services, self.cd, self.users_by_id)
    self.assertEqual('UI>Dialogs', view.parent_path)
    self.assertEqual('Print', view.leaf_name)
    self.assertEqual('User interface', view.docstring_short)
    self.assertEqual('admin@example.com', view.admins[0].email)
    self.assertEqual(['Hot', 'Cold'], view.labels)
    self.assertEqual('all active ', view.classes)


class ComponentValueTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class FieldValueViewTest(unittest.TestCase):

  def setUp(self):
    self.config = tracker_pb2.ProjectIssueConfig()
    self.estdays_fd = tracker_bizobj.MakeFieldDef(
        1, 789, 'EstDays', tracker_pb2.FieldTypes.INT_TYPE, None,
        None, False, False, False, 3, 99, None, False, None, None,
        None, 'no_action', 'descriptive docstring', False, approval_id=None,
        is_phase_field=False)
    self.designdoc_fd = tracker_bizobj.MakeFieldDef(
        2, 789, 'DesignDoc', tracker_pb2.FieldTypes.STR_TYPE, 'Enhancement',
        None, False, False, False, None, None, None, False, None, None,
        None, 'no_action', 'descriptive docstring', False, approval_id=None,
        is_phase_field=False)
    self.mtarget_fd = tracker_bizobj.MakeFieldDef(
        3, 789, 'M-Target', tracker_pb2.FieldTypes.INT_TYPE, 'Enhancement',
        None, False, False, False, None, None, None, False, None, None,
        None, 'no_action', 'doc doc', False, approval_id=None,
        is_phase_field=True)
    self.config.field_defs = [self.estdays_fd, self.designdoc_fd]

  def testNoValues(self):
    """We can create a FieldValueView with no values."""
    values = []
    derived_values = []
    estdays_fvv = tracker_views.FieldValueView(
        self.estdays_fd, self.config, values, derived_values, ['defect'],
        phase_name='Gate')
    self.assertEqual('EstDays', estdays_fvv.field_def.field_name)
    self.assertEqual(3, estdays_fvv.field_def.min_value)
    self.assertEqual(99, estdays_fvv.field_def.max_value)
    self.assertEqual([], estdays_fvv.values)
    self.assertEqual([], estdays_fvv.derived_values)

  def testSomeValues(self):
    """We can create a FieldValueView with some values."""
    values = [template_helpers.EZTItem(val=12, docstring=None, idx=0)]
    derived_values = [template_helpers.EZTItem(val=88, docstring=None, idx=0)]
    estdays_fvv = tracker_views.FieldValueView(
        self.estdays_fd, self.config, values, derived_values, ['defect'])
    self.assertEqual(self.estdays_fd, estdays_fvv.field_def.field_def)
    self.assertTrue(estdays_fvv.is_editable)
    self.assertEqual(values, estdays_fvv.values)
    self.assertEqual(derived_values, estdays_fvv.derived_values)
    self.assertEqual('', estdays_fvv.phase_name)
    self.assertEqual(ezt.boolean(False), estdays_fvv.field_def.is_phase_field)

  def testApplicability(self):
    """We know whether a field should show an editing widget."""
    # Not the right type and has no values.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [], ['defect'])
    self.assertFalse(designdoc_fvv.applicable)
    self.assertEqual('', designdoc_fvv.phase_name)
    self.assertEqual(ezt.boolean(False), designdoc_fvv.field_def.is_phase_field)

    # Has a value.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, ['fake value item'], [], ['defect'])
    self.assertTrue(designdoc_fvv.applicable)

    # Derived values don't cause editing fields to display.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], ['fake value item'], ['defect'])
    self.assertFalse(designdoc_fvv.applicable)

    # Applicable to this type of issue.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [], ['enhancement'])
    self.assertTrue(designdoc_fvv.applicable)

    # Applicable to some issues in a bulk edit.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [],
        ['defect', 'task', 'enhancement'])
    self.assertTrue(designdoc_fvv.applicable)

    # Applicable to all issues.
    estdays_fvv = tracker_views.FieldValueView(
        self.estdays_fd, self.config, [], [], ['enhancement'])
    self.assertTrue(estdays_fvv.applicable)

    # Explicitly set to be applicable when showing bounce values.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [], ['defect'],
        applicable=True)
    self.assertTrue(designdoc_fvv.applicable)

  def testDisplay(self):
    """We know when a value (or --) should be shown in the metadata column."""
    # Not the right type and has no values.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [], ['defect'])
    self.assertFalse(designdoc_fvv.display)

    # Has a value.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, ['fake value item'], [], ['defect'])
    self.assertTrue(designdoc_fvv.display)

    # Has a derived value.
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], ['fake value item'], ['defect'])
    self.assertTrue(designdoc_fvv.display)

    # Applicable to this type of issue, it will show "--".
    designdoc_fvv = tracker_views.FieldValueView(
        self.designdoc_fd, self.config, [], [], ['enhancement'])
    self.assertTrue(designdoc_fvv.display)

    # Applicable to all issues, it will show "--".
    estdays_fvv = tracker_views.FieldValueView(
        self.estdays_fd, self.config, [], [], ['enhancement'])
    self.assertTrue(estdays_fvv.display)

  def testPhaseField(self):
    mtarget_fvv = tracker_views.FieldValueView(
        self.mtarget_fd, self.config, [], [], [], phase_name='Stage')
    self.assertEqual('Stage', mtarget_fvv.phase_name)
    self.assertEqual(ezt.boolean(True), mtarget_fvv.field_def.is_phase_field)


class FVVFunctionsTest(unittest.TestCase):

  def setUp(self):
    self.config = tracker_pb2.ProjectIssueConfig()
    self.estdays_fd = tracker_bizobj.MakeFieldDef(
        1, 789, 'EstDays', tracker_pb2.FieldTypes.INT_TYPE, None,
        None, False, False, False, 3, 99, None, False, None, None,
        None, 'no_action', 'descriptive docstring', False, None, False)
    self.os_fd = tracker_bizobj.MakeFieldDef(
        2, 789, 'OS', tracker_pb2.FieldTypes.ENUM_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, None, False)
    self.milestone_fd = tracker_bizobj.MakeFieldDef(
        3, 789, 'Launch-Milestone', tracker_pb2.FieldTypes.ENUM_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, None, False)
    self.config.field_defs = [self.estdays_fd, self.os_fd, self.milestone_fd]
    self.config.well_known_labels = [
        tracker_pb2.LabelDef(
            label='Priority-High', label_docstring='Must be resolved'),
        tracker_pb2.LabelDef(
            label='Priority-Low', label_docstring='Can be slipped'),
        ]

  def testPrecomputeInfoForValueViews_NoValues(self):
    """We can precompute info needed for an issue with no fields or labels."""
    labels = []
    derived_labels = []
    field_values = []
    phases = []
    precomp_view_info = tracker_views._PrecomputeInfoForValueViews(
        labels, derived_labels, field_values, self.config, phases)
    (labels_by_prefix, der_labels_by_prefix, field_values_by_id,
     label_docs, phases_by_name) = precomp_view_info
    self.assertEqual({}, labels_by_prefix)
    self.assertEqual({}, der_labels_by_prefix)
    self.assertEqual({}, field_values_by_id)
    self.assertEqual(
        {'priority-high': 'Must be resolved',
         'priority-low': 'Can be slipped'},
        label_docs)
    self.assertEqual({}, phases_by_name)

  def testPrecomputeInfoForValueViews_SomeValues(self):
    """We can precompute info needed for an issue with fields and labels."""
    labels = ['Priority-Low', 'GoodFirstBug', 'Feature-UI', 'Feature-Installer',
              'Launch-Milestone-66']
    derived_labels = ['OS-Windows', 'OS-Linux']
    field_values = [
        tracker_bizobj.MakeFieldValue(1, 5, None, None, None, None, False),
        ]
    phase_1 = tracker_pb2.Phase(phase_id=1, name='Stable')
    phase_2 = tracker_pb2.Phase(phase_id=2, name='Beta')
    phase_3 = tracker_pb2.Phase(phase_id=3, name='stable')
    precomp_view_info = tracker_views._PrecomputeInfoForValueViews(
        labels, derived_labels, field_values, self.config,
        phases=[phase_1, phase_2, phase_3])
    (labels_by_prefix, der_labels_by_prefix, field_values_by_id,
     _label_docs, phases_by_name) = precomp_view_info
    self.assertEqual(
        {'priority': ['Low'],
         'feature': ['UI', 'Installer'],
         'launch-milestone': ['66']},
        labels_by_prefix)
    self.assertEqual(
        {'os': ['Windows', 'Linux']},
        der_labels_by_prefix)
    self.assertEqual(
        {1: field_values},
        field_values_by_id)
    self.assertEqual(
        {'stable': [phase_1, phase_3],
         'beta': [phase_2]},
        phases_by_name)

  def testMakeAllFieldValueViews(self):
    labels = ['Priority-Low', 'GoodFirstBug', 'Feature-UI', 'Feature-Installer',
              'Launch-Milestone-66']
    derived_labels = ['OS-Windows', 'OS-Linux']
    self.config.field_defs.append(tracker_bizobj.MakeFieldDef(
        4, 789, 'UIMocks', tracker_pb2.FieldTypes.URL_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, approval_id=23, is_phase_field=False))
    self.config.field_defs.append(tracker_bizobj.MakeFieldDef(
        5, 789, 'LegalFAQs', tracker_pb2.FieldTypes.URL_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, approval_id=26, is_phase_field=False))
    self.config.field_defs.append(tracker_bizobj.MakeFieldDef(
        23, 789, 'Legal', tracker_pb2.FieldTypes.APPROVAL_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, approval_id=None, is_phase_field=False))
    self.config.field_defs.append(tracker_bizobj.MakeFieldDef(
        26, 789, 'UI', tracker_pb2.FieldTypes.APPROVAL_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, approval_id=None, is_phase_field=False))
    self.config.field_defs.append(tracker_bizobj.MakeFieldDef(
        27, 789, 'M-Target', tracker_pb2.FieldTypes.INT_TYPE,
        'Enhancement', None, False, False, False, None, None, None,
        False, None, None, None, 'no_action', 'descriptive docstring',
        False, approval_id=None, is_phase_field=True))
    field_values = [
        tracker_bizobj.MakeFieldValue(1, 5, None, None, None, None, False),
        tracker_bizobj.MakeFieldValue(
            27, 74, None, None, None, None, False, phase_id=3),
        # phase_id=4 does not belong to any of the phases given below.
        # this field value should not show up in the views.
        tracker_bizobj.MakeFieldValue(
            27, 79, None, None, None, None, False, phase_id=4),
        ]
    users_by_id = {}
    phase_1 = tracker_pb2.Phase(phase_id=1, name='Stable')
    phase_2 = tracker_pb2.Phase(phase_id=2, name='Beta')
    phase_3 = tracker_pb2.Phase(phase_id=3, name='stable')
    fvvs = tracker_views.MakeAllFieldValueViews(
        self.config, labels, derived_labels, field_values, users_by_id,
        parent_approval_ids=[23], phases=[phase_1, phase_2, phase_3])
    self.assertEqual(9, len(fvvs))
    # Values are sorted by (applicable_type, field_name).
    logging.info([fv.field_name for fv in fvvs])
    (estdays_fvv, launch_milestone_fvv, legal_fvv, legal_faq_fvv,
      beta_mtarget_fvv, stable_mtarget_fvv, os_fvv, ui_fvv, ui_mocks_fvv) = fvvs
    self.assertEqual('EstDays', estdays_fvv.field_name)
    self.assertEqual(1, len(estdays_fvv.values))
    self.assertEqual(0, len(estdays_fvv.derived_values))
    self.assertEqual('Launch-Milestone', launch_milestone_fvv.field_name)
    self.assertEqual(1, len(launch_milestone_fvv.values))
    self.assertEqual(0, len(launch_milestone_fvv.derived_values))
    self.assertEqual('OS', os_fvv.field_name)
    self.assertEqual(0, len(os_fvv.values))
    self.assertEqual(2, len(os_fvv.derived_values))
    self.assertEqual(ui_mocks_fvv.field_name, 'UIMocks')
    self.assertEqual(ui_mocks_fvv.phase_name, '')
    self.assertTrue(ui_mocks_fvv.applicable)
    self.assertEqual(legal_faq_fvv.field_name, 'LegalFAQs')
    self.assertFalse(legal_faq_fvv.applicable)
    self.assertFalse(legal_fvv.applicable)
    self.assertFalse(ui_fvv.applicable)
    self.assertEqual('M-Target', stable_mtarget_fvv.field_name)
    self.assertEqual('stable', stable_mtarget_fvv.phase_name)
    self.assertEqual(1, len(stable_mtarget_fvv.values))
    self.assertEqual(74, stable_mtarget_fvv.values[0].val)
    self.assertEqual(0, len(stable_mtarget_fvv.derived_values))
    self.assertEqual('M-Target', beta_mtarget_fvv.field_name)
    self.assertEqual('beta', beta_mtarget_fvv.phase_name)
    self.assertEqual(0, len(beta_mtarget_fvv.values))
    self.assertEqual(0, len(beta_mtarget_fvv.values))

  def testMakeFieldValueView(self):
    pass  # Covered by testMakeAllFieldValueViews()

  def testMakeFieldValueItemsTest(self):
    pass  # Covered by testMakeAllFieldValueViews()

  def testMakeBounceFieldValueViews(self):
    config = tracker_pb2.ProjectIssueConfig()
    fd = tracker_pb2.FieldDef(
        field_id=3, field_type=tracker_pb2.FieldTypes.INT_TYPE,
        applicable_type='', field_name='EstDays')
    phase_fd = tracker_pb2.FieldDef(
        field_id=4, field_type=tracker_pb2.FieldTypes.INT_TYPE,
        applicable_type='', field_name='Gump')
    config.field_defs = [fd,
                         phase_fd,
                         tracker_pb2.FieldDef(
        field_id=5, field_type=tracker_pb2.FieldTypes.STR_TYPE)
    ]
    parsed_fvs = {3: [455]}
    parsed_phase_fvs = {
        4: {'stable': [73, 74], 'beta': [8], 'beta-exp': [75]},
    }
    fvs = tracker_views.MakeBounceFieldValueViews(
        parsed_fvs, parsed_phase_fvs, config)

    self.assertEqual(len(fvs), 4)

    estdays_ezt_fv = template_helpers.EZTItem(val=455, docstring='', idx=0)
    expected = tracker_views.FieldValueView(
        fd, config, [estdays_ezt_fv], [], [])
    self.assertEqual(fvs[0].field_name, expected.field_name)
    self.assertEqual(fvs[0].values[0].val, expected.values[0].val)
    self.assertEqual(fvs[0].values[0].idx, expected.values[0].idx)
    self.assertTrue(fvs[0].applicable)

    self.assertEqual(fvs[1].field_name, phase_fd.field_name)
    self.assertEqual(fvs[2].field_name, phase_fd.field_name)
    self.assertEqual(fvs[3].field_name, phase_fd.field_name)

    fd.approval_id = 23
    config.field_defs = [fd,
                         tracker_pb2.FieldDef(
                             field_id=23, field_name='Legal',
                             field_type=tracker_pb2.FieldTypes.APPROVAL_TYPE)]
    fvs = tracker_views.MakeBounceFieldValueViews(parsed_fvs, {}, config)
    self.assertTrue(fvs[0].applicable)


class ConvertLabelsToFieldValuesTest(unittest.TestCase):

  def testConvertLabelsToFieldValues_NoLabels(self):
    result = tracker_views._ConvertLabelsToFieldValues(
        [], 'opsys', {})
    self.assertEqual([], result)

  def testConvertLabelsToFieldValues_NoMatch(self):
    result = tracker_views._ConvertLabelsToFieldValues(
        [], 'opsys', {})
    self.assertEqual([], result)

  def testConvertLabelsToFieldValues_HasMatch(self):
    result = tracker_views._ConvertLabelsToFieldValues(
        ['OSX'], 'opsys', {})
    self.assertEqual(1, len(result))
    self.assertEqual('OSX', result[0].val)
    self.assertEqual('', result[0].docstring)

    result = tracker_views._ConvertLabelsToFieldValues(
        ['OSX', 'All'], 'opsys', {'opsys-all': 'Happens everywhere'})
    self.assertEqual(2, len(result))
    self.assertEqual('OSX', result[0].val)
    self.assertEqual('', result[0].docstring)
    self.assertEqual('All', result[1].val)
    self.assertEqual('Happens everywhere', result[1].docstring)


class FieldDefViewTest(unittest.TestCase):

  def setUp(self):
    self.approval_fd = tracker_bizobj.MakeFieldDef(
        1, 789, 'LaunchApproval', tracker_pb2.FieldTypes.APPROVAL_TYPE, None,
        None, True, True, False, 3, 99, None, False, None, None,
        None, 'no_action', 'descriptive docstring', False, None, False)

    self.approval_def = tracker_pb2.ApprovalDef(
        approval_id=1, approver_ids=[111], survey='question?')

    self.field_def = tracker_bizobj.MakeFieldDef(
        2, 789, 'AffectedUsers', tracker_pb2.FieldTypes.INT_TYPE, None,
        None, True, True, False, 3, 99, None, False, None, None,
        None, 'no_action', 'descriptive docstring', False, 1, False)

    self.field_def.admin_ids = [222]
    self.field_def.editor_ids = [111, 333]

  def testFieldDefView_Normal(self):
    config = _MakeConfig()
    config.field_defs.append(self.approval_fd)
    config.approval_defs.append(self.approval_def)

    user_view_1 = framework_views.StuffUserView(111, 'uv1@example.com', False)
    user_view_2 = framework_views.StuffUserView(222, 'uv2@example.com', False)
    user_view_3 = framework_views.StuffUserView(333, 'uv3@example.com', False)
    user_views = {111: user_view_1, 222: user_view_2, 333: user_view_3}
    view = tracker_views.FieldDefView(
        self.field_def, config, user_views=user_views)

    self.assertEqual('AffectedUsers', view.field_name)
    self.assertEqual(self.field_def, view.field_def)
    self.assertEqual('descriptive docstring', view.docstring_short)
    self.assertEqual('INT_TYPE', view.type_name)
    self.assertEqual([], view.choices)
    self.assertEqual('required', view.importance)
    self.assertEqual(3, view.min_value)
    self.assertEqual(99, view.max_value)
    self.assertEqual('no_action', view.date_action_str)
    self.assertEqual(view.approval_id, 1)
    self.assertEqual(view.is_approval_subfield, ezt.boolean(True))
    self.assertEqual(view.approvers, [])
    self.assertEqual(view.survey, '')
    self.assertEqual(view.survey_questions, [])
    self.assertEqual(len(view.admins), 1)
    self.assertEqual(len(view.editors), 2)
    self.assertIsNone(view.is_phase_field)
    self.assertIsNone(view.is_restricted_field)

  def testFieldDefView_Approval(self):
    config = _MakeConfig()
    approver_view = framework_views.StuffUserView(
        111, 'shouldnotmatter@ch.org', False)
    user_views = {111: approver_view}

    view = tracker_views.FieldDefView(
        self.approval_fd, config,
        user_views= user_views, approval_def=self.approval_def)
    self.assertEqual(view.approvers, [approver_view])
    self.assertEqual(view.survey, self.approval_def.survey)
    self.assertEqual(view.survey_questions, [view.survey])

    self.approval_def.survey = None
    view = tracker_views.FieldDefView(
        self.approval_fd, config,
        user_views= user_views, approval_def=self.approval_def)
    self.assertEqual(view.survey, '')
    self.assertEqual(view.survey_questions, [])

    self.approval_def.survey = 'Q1\nQ2\nQ3'
    view = tracker_views.FieldDefView(
        self.approval_fd, config,
        user_views= user_views, approval_def=self.approval_def)
    self.assertEqual(view.survey, self.approval_def.survey)
    self.assertEqual(view.survey_questions, ['Q1', 'Q2', 'Q3'])


class IssueTemplateViewTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class MakeFieldUserViewsTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class ConfigViewTest(unittest.TestCase):
  pass  # TODO(jrobbins): write tests


class ConfigFunctionsTest(unittest.TestCase):

  def setUp(self):
    self.config = tracker_bizobj.MakeDefaultProjectIssueConfig(768)

  def testStatusDefsAsText(self):
    open_text, closed_text = tracker_views.StatusDefsAsText(self.config)

    for wks in tracker_constants.DEFAULT_WELL_KNOWN_STATUSES:
      status, doc, means_open, _deprecated = wks
      if means_open:
        self.assertIn(status, open_text)
        self.assertIn(doc, open_text)
      else:
        self.assertIn(status, closed_text)
        self.assertIn(doc, closed_text)

    self.assertEqual(
        len(tracker_constants.DEFAULT_WELL_KNOWN_STATUSES),
        len(open_text.split('\n')) + len(closed_text.split('\n')))

  def testLabelDefsAsText(self):
    # Note: Day-Monday will not be part of the result because it is masked.
    self.config.field_defs.append(tracker_pb2.FieldDef(
        field_id=1, field_name='Day',
        field_type=tracker_pb2.FieldTypes.ENUM_TYPE))
    self.config.well_known_labels.append(tracker_pb2.LabelDef(
        label='Day-Monday'))
    labels_text = tracker_views.LabelDefsAsText(self.config)

    for wkl in tracker_constants.DEFAULT_WELL_KNOWN_LABELS:
      label, doc, _deprecated = wkl
      self.assertIn(label, labels_text)
      self.assertIn(doc, labels_text)
    self.assertEqual(
        len(tracker_constants.DEFAULT_WELL_KNOWN_LABELS),
        len(labels_text.split('\n')))
