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

"""Show the builder layout for CrOS waterfalls."""

from __future__ import print_function

import json
import sys

from chromite.cbuildbot import generate_chromeos_config
from chromite.lib import commandline


def _FormatText(data, out):
  """Formatter function for text output."""
  output = lambda *a: print(*a, file=out)

  for waterfall in sorted(data.iterkeys()):
    layout = data[waterfall]
    if not layout:
      continue

    output('== %s ==' % (waterfall,))
    for board in sorted(layout.iterkeys()):
      board_layout = layout[board]
      children = board_layout.get('children', ())
      if not children:
        output('%(name)s' % board_layout)
      else:
        output('[%(name)s]' % board_layout)
      for child in sorted(board_layout.get('children', ())):
        output('  %s' % (child,))
    output()


def _FormatJson(data, out):
  """Formatter function for JSON output."""
  json.dump(data, out, sort_keys=True)


_FORMATTERS = {
    'text': _FormatText,
    'json': _FormatJson,
}


def _ParseArguments(argv):
  parser = commandline.ArgumentParser(description=__doc__)

  parser.add_argument('--format', default='text',
                      choices=sorted(_FORMATTERS.iterkeys()),
                      help='Choose output format.')
  opts = parser.parse_args(argv)
  opts.format = _FORMATTERS[opts.format]
  opts.Freeze()
  return opts


def main(argv):
  opts = _ParseArguments(argv)

  layout = {}
  for config_name, config in generate_chromeos_config.GetConfig().iteritems():
    active_waterfall = config['active_waterfall']
    if not active_waterfall:
      continue

    waterfall_layout = layout.setdefault(active_waterfall, {})
    board_layout = waterfall_layout[config_name] = {
        'name': config_name,
    }

    children = config['child_configs']
    if children:
      board_layout['children'] = [c['name'] for c in children]
  opts.format(layout, sys.stdout)
