#
# Copyright (C) 2015 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

from __future__ import print_function
import os
import sys

import gitc_utils
from command import RequiresGitcCommand
from subcmds import init


class GitcInit(init.Init, RequiresGitcCommand):
  common = True
  helpSummary = "Initialize a GITC Client."
  helpUsage = """
%prog [options] [client name]
"""
  helpDescription = """
The '%prog' command is ran to initialize a new GITC client for use
with the GITC file system.

This command will setup the client directory, initialize repo, just
like repo init does, and then downloads the manifest collection
and installs in in the .repo/directory of the GITC client.

Once this is done, a GITC manifest is generated by pulling the HEAD
SHA for each project and generates the properly formatted XML file
and installs it as .manifest in the GITC client directory.

The -c argument is required to specify the GITC client name.

The optional -f argument can be used to specify the manifest file to
use for this GITC client.
"""

  def _Options(self, p):
    super(GitcInit, self)._Options(p)
    g = p.add_option_group('GITC options')
    g.add_option('-f', '--manifest-file',
                 dest='manifest_file',
                 help='Optional manifest file to use for this GITC client.')
    g.add_option('-c', '--gitc-client',
                 dest='gitc_client',
                 help='The name for the new gitc_client instance.')

  def Execute(self, opt, args):
    if not opt.gitc_client:
      print('fatal: gitc client (-c) is required', file=sys.stderr)
      sys.exit(1)
    self.client_dir = os.path.join(gitc_utils.get_gitc_manifest_dir(),
                                   opt.gitc_client)
    if not os.path.exists(gitc_utils.get_gitc_manifest_dir()):
      os.makedirs(gitc_utils.get_gitc_manifest_dir())
    if not os.path.exists(self.client_dir):
      os.mkdir(self.client_dir)
    super(GitcInit, self).Execute(opt, args)

    for name, remote in self.manifest.remotes.iteritems():
      remote.fetchUrl = remote.resolvedFetchUrl

    if opt.manifest_file:
      if not os.path.exists(opt.manifest_file):
        print('fatal: Specified manifest file %s does not exist.' %
              opt.manifest_file)
        sys.exit(1)
      self.manifest.Override(opt.manifest_file)
    gitc_utils.generate_gitc_manifest(self.client_dir, self.manifest)
    print('Please run `cd %s` to view your GITC client.' %
          os.path.join(gitc_utils.GITC_FS_ROOT_DIR, opt.gitc_client))
