#!/usr/bin/env python
#
# Copyright (C) 2010, 2011, 2012, 2013, 2014 Intel, Inc.
#
#    This program is free software; you can redistribute it and/or
#    modify it under the terms of the GNU General Public License
#    as published by the Free Software Foundation; version 2
#    of the License.
#
#    This program is distributed in the hope that it will be useful,
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
#    GNU General Public License for more details.
#
#    You should have received a copy of the GNU General Public License
#    along with this program; if not, write to the Free Software
#    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA
#
"""The job will do corresponding operations, like create accept tag/notify tag
owner, for SR status changed."""

from common.git import Git, clone_gitproject, GitError
from common import buildservice
from common.gerrit import Gerrit, GerritError
from common.buildtrigger import trigger_info, trigger_next
from common.send_mail import prepare_mail
from common.buildservice import BuildService
from common.iris_rest_client import IrisRestClient
from common.utils import unicode_to_str
from obs_requests.mailer import mailer
from gbp.git.repository import GitRepositoryError
from gitbuildsys.errors import ObsError

import sys
import os
import datetime
import base64
from time import sleep
from xml.sax.saxutils import unescape
import xml.etree.cElementTree as ElementTree

# set default char-set endcoding to utf-8
reload(sys)
sys.setdefaultencoding('utf-8') # pylint: disable-msg=E1101

HIGHLIGHT = '+'
GREYEDOUT = '-'
REPAIR_COMMENT = 'accepted request %s (%s/request/show/%s)\n\n%s'

def request_url(request_id):
    """Get request url"""

    if os.getenv('OBS_URL_EXTERNAL'):
        return '%s/request/show/%s' % (os.getenv('OBS_URL_EXTERNAL'), request_id)
    else:
        return '%s' % (request_id)

def tag_info(prj, tag, event_fields=None):
    """Get git tag info"""

    git_cache = os.path.join(os.getenv('GIT_CACHE_DIR'))
    if event_fields.get('github'):
        github = event_fields.get('github')
        if github.get(prj):
            giturl = github.get(prj)
            gitorg = giturl.split(':')[1]
            git_full_name = os.path.join(gitorg, prj)
            prjdir = os.path.join(git_cache, git_full_name)
            git_cache_dir = os.path.join(git_cache, gitorg)
            print 'org=%s git_full_name = %s' %(gitorg, git_full_name)
        else:
            print 'project: %s is not present in github'%(prj)
    else: # GERRIT
        prjdir = os.path.join(git_cache, prj)
        giturl = None
        git_cache_dir = None

    try:
        mygit = Git(prjdir)
        if mygit.find_tag(tag):
            return mygit.get_tag(tag)
    except GitRepositoryError:
        # tag is not found, try to clone
        # clone gerrit project to local dir
        if not clone_gitproject(prj, os.path.join(os.getenv('WORKSPACE'), prj), \
                                giturl=giturl, git_cache_dir=git_cache_dir):
            exit(1)

    mygit = Git(os.path.join(os.getenv('WORKSPACE'), prj))
    try:
        tag_data = mygit.get_tag(tag)
        return mygit.get_tag(tag)
    except Exception as err:
        print repr(err)
        return None

def obs_git_data(event_fields):
    """Put obs and git data into a dict"""

    obs_fields_mapping = {'author': 'OBS_REQ_AUTHOR',
                          'comment': 'OBS_REQ_COMMENT',
                          'deletepackage': 'OBS_REQ_PKG_DEL',
                          'deleteproject': 'OBS_REQ_PRJ_DEL',
                          'description': 'OBS_REQ_DESP',
                          'id': 'OBS_REQ_ID',
                          'oldstate': 'OBS_REQ_OLDSTATE',
                          'origintype': 'OBS_REQ_ORIGINTYPE',
                          'person': 'OBS_REQ_PERSON',
                          'role': 'OBS_REQ_ROLE',
                          'sender': 'OBS_REQ_SENDER',
                          'sourceproject': 'OBS_REQ_PRJ_SRC',
                          'sourcerevision': 'OBS_REQ_SRCREV',
                          'state': 'OBS_REQ_STATE',
                          'targetproject': 'OBS_REQ_PRJ',
                          'time': 'OBS_REQ_TIME',
                          'event_type': 'OBS_REQ_TYPE',
                          'when': 'OBS_REQ_WHEN',
                          'who': 'OBS_REQ_WHO'
                          }

    mapping = {"Submitter" : 'GIT_AUTHOR_EMAIL',
               "Comments" : "GIT_COMMENTS",
               "Tag" : "GIT_TAG",
               "Git project" : "GIT_PROJECTS",
               }

    ret_data = {}

    for key in obs_fields_mapping.keys():
        ret_data[obs_fields_mapping[key]] = event_fields.get(key)

    projects_list = []

    description = event_fields['description']
    if description:
        entry = {}
        for line in description.split('\n'):
            try:
                key, value = line.split(':', 1)
                mkey = mapping.get(key.strip())
                if not mkey:
                    continue
                if key.strip() in ['Submitter']:
                    entry[mkey] = unescape(value.strip())
                else:
                    entry[mkey] = value.strip()
            except (AttributeError, ValueError):
                print '-------------------------------------'
                print 'key:value  %s' % line
                print 'FATAL: no tag in submit description'
        if 'GIT_PROJECTS' in entry.keys() and 'GIT_TAG' in entry.keys():
            projects = []
            # To be compatible the one or more
            # when entry['GIT_PROJECTS'] is '[***]' executes if,
            # when entry['GIT_PROJECTS'] is '***' executes else.
            if entry['GIT_PROJECTS'].startswith('[') and \
                    entry['GIT_PROJECTS'].endswith(']'):
                if entry['GIT_PROJECTS'][1:-1]:
                    projects = entry['GIT_PROJECTS'][1:-1].split(', ')
            else:
                projects.append(entry['GIT_PROJECTS'])

            for project in projects:
                # Get package name from OBS description.
                # Assume items(packages, projects) are stored one after another.
                obs_req_pkg_name = os.path.basename(project)
                if len(projects) == len(event_fields['packages']):
                    try:
                        obs_req_pkg_name = event_fields['packages'][projects.index(project)]
                    except Exception as err:
                        print 'Warning: not able to find package name from description'

                tag = tag_info(project, entry['GIT_TAG'], event_fields)
                if tag:
                    tag.update({'GIT_PROJECT': project,
                                'OBS_REQ_PKG_SRC': obs_req_pkg_name,
                                'OBS_REQ_PKG': obs_req_pkg_name,})
                    projects_list.append(tag)
        else:
            print '-------------------------------------'
            print "FATAL ERROR: Invalid rquest info: the request might be"\
                    " created by manual"
            print '-------------------------------------'
            exit(0)
    else:
        print '--------------------------------------------------'
        print 'FATAL: package submited has no description, exit...'
        print '--------------------------------------------------'
        exit(0)

    # move the tag info to data, keep the superseded SR in list

    ret_data.update(entry)

    # Database records
    print '########################################'
    import pprint
    ppt = pprint.PrettyPrinter(indent=4)
    print ppt.pprint(ret_data)
    return ret_data, projects_list

def delete_from_obs(prj, pkg, handle_link=None):
    """
    Delete package from OBS.
    Delete project if it's prerelease project
    """

    # Control flag for deleting useless _link file.
    global is_link_visited
    is_link_visited = False

    _bs = BuildService(os.getenv('OBS_API_URL'),
                      os.getenv('OBS_API_USERNAME'),
                      os.getenv('OBS_API_PASSWD'))

    # If selected package have both _link and _service file, delete _link.
    if is_link_visited == False and handle_link and handle_link.get('target_project', None) is not None:
        try:
            for _pkg in handle_link.get('target_packages', []):
                print 'Check link for %s' % _pkg
                viewinfo = _bs.get_source_viewinfo(handle_link.get('target_project'), _pkg, parse=0, nofilename=0)
                viewroot = ElementTree.parse(viewinfo).getroot()
                if viewroot.find('filename').text.startswith('_service:'):
                    if viewroot.find('linked') is not None:
                        print 'Found conflicting LINK %s/%s' % (viewroot.find('linked').get('project'), \
                                                                viewroot.find('linked').get('package'))
                        _comments = 'revision %d is the same as revision %d w/o link. </br>\n%s' % \
                                    (int(viewroot.get('rev')) + 1, int(viewroot.get('rev')), \
                                    handle_link.get('comments').replace('<','&lt;').replace('>','&gt;').replace('\n',' </br>\n'))
                        _bs.delete_file(handle_link.get('target_project'), viewroot.get('package'), ['_link'], \
                                        _comments, purge_comments=True)
                is_link_visited = True
        except Exception as err:
            print repr(err)

    try:
        if 'home:prerelease:' in prj:
            print 'Removing %s' % prj
            _bs.cleanup(prj, "This project has expired")
            return
    except ObsError, error:
        print error
        if 'HTTP Error 404' in str(error):
            return True
        else:
            return False

    if pkg and not _bs.exists(prj, pkg):
        print '[Warning]:buildservice cannot find prj %s: pkg %s' % (prj, pkg)
        return True

    if pkg and _bs.get_package_real_project_name(prj, pkg) == prj:
        try:
            if True:
                print 'Removing %s:%s' % (prj, pkg)
                _bs.delete_package(prj, pkg)
        except ObsError, error:
            print error
            if 'HTTP Error 404' in str(error):
                return True
            else:
                return False

    return True

def request_accepted(data, gerrit, gitprj, targetpackagelist=[]):
    """Do lots of things when request accepted"""

    print '====request accepted===================================='

    message = 'The SR (Submit Request) has been accepted to OBS %s project.\n' \
    '- Package: %s\n' \
    '- Reviewer: %s\n' \
    '- Comments: %s\n' \
    '- Git project: %s\n' \
    '- Tag:%s\n' \
    '- Request URL:%s' % (data['OBS_REQ_PRJ'],
                          data['OBS_REQ_PKG'],
                          data["OBS_REQ_SENDER"],
                          data["OBS_REQ_COMMENT"],
                          data['GIT_PROJECT'],
                          data["GIT_TAG"],
                          request_url(data['OBS_REQ_ID']))
    try:
        gerrit.review(commit=data['commitid'], message=message)
    except GerritError, err:
        print >> sys.stderr, 'Error posting review comment '\
                             'back to Gerrit: %s' % str(err)
        # return 1 if this exception is not caused by invalid commit
        if 'no such patch set' not in str(err):
            return 1

    obs_target = data['OBS_REQ_PRJ'].lower().replace(':', '/')
    timestamp = datetime.datetime.utcnow().strftime("%Y%m%d.%H%M%S")

    # use os.path.join() to avoid '//', which is invalid as tag name
    accepted_tag = os.path.join('accepted', obs_target, timestamp)

    gitprj.create_tag(accepted_tag, message, data['commitid'])
    sleep(1)

    remote = 'ssh://%s@%s:%s/%s' % (gerrit.username, gerrit.host, gerrit.port,
            data['GIT_PROJECT'])
    try:
        gitprj.push_tag(remote, accepted_tag)
    except GitRepositoryError, gre:
        print gre
        return 1

    # push accepted commit to accepted branch refs/heads/accepted/*
    # e.g. changes, accepted for Tizen:Mobile should be pushed to
    # branch refs/heads/accepted/tizen_mobile
    dst = 'refs/heads/accepted/%s' % \
            data['OBS_REQ_PRJ'].lower().replace(':', '_')
    try:
        gitprj.push(remote, data['commitid'], dst, force=True)
    except GitRepositoryError, gre:
        print gre
        return 1

    additional_comment = REPAIR_COMMENT \
                     % (data['OBS_REQ_ID'], os.getenv('OBS_URL_EXTERNAL'), data['OBS_REQ_ID'], \
                        data['OBS_REQ_DESP'])
    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'], \
                    handle_link={'target_project': data['OBS_REQ_PRJ'], \
                                 'comments': additional_comment, \
                                 'target_packages': targetpackagelist})

    # Disable triggerring make_dep_graph.
    # Code remained to enable it in the future
    #trigger_data = {}
    #trigger_data['obs_project'] = data['OBS_REQ_PRJ'];
    #trigger_data['action'] = "postrelease_build_progress";
    #trigger_next('make_dep_graph', trigger_data)


def request_rejected(data, gerrit):
    """When request rejected, give msg to gerrit and delete remote package"""

    print '====request rejected===================================='

    message = 'The SR (Submit Request) has been *rejected* ' \
    'to OBS %s project.\n' \
    '- Reviewer: %s\n' \
    '- Comments: %s\n' \
    '- Git project: %s\n' \
    '- Tag:%s\n' \
    '- Request URL:%s' % (data['OBS_REQ_PRJ'],
                          data["OBS_REQ_SENDER"],
                          data["OBS_REQ_COMMENT"],
                          data['GIT_PROJECT'],
                          data["GIT_TAG"],
                          request_url(data['OBS_REQ_ID']))

    try:
        gerrit.review(commit=data['commitid'], message=message)
    except GerritError, err:
        print >> sys.stderr, 'Error posting review comment '\
                             'back to Gerrit: %s' % str(err)
        # return 1 if this exception is not caused by invalid commit
        if 'no such patch set' not in str(err):
            return 1

    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'])

def request_revoked(data):
    """When request revoked, delete the remote package"""

    print '====request revoked===================================='

    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'])

def request_created(data):
    """Print request created information"""

    print '====request created===================================='

    message = 'A SR (Submit Request) has been trigger to submit the commit ' \
            'to OBS %s project.\n' \
    '- Submitter: %s\n' \
    '- Comments: %s\n' \
    '- Git project: %s\n' \
    '- Tag:%s\n' \
    '- Request URL:%s' % (data['OBS_REQ_PRJ'],
                          data["GIT_AUTHOR_EMAIL"],
                          data["message"],
                          data['GIT_PROJECT'],
                          data["GIT_TAG"],
                          request_url(data['OBS_REQ_ID']))

    print '#########NOTE: post to gerrit is disabled###########################'
    #gerrit.review(commit = data['commitid'], message = message)
    print message
    print '########################################'


def notify_submiter(event_fields, data):
    """Notify submiter obs events"""

    print '====Notify the tag owner===================================='

    status = {}

    _bs = buildservice.BuildService(os.getenv('OBS_API_URL'), \
            os.getenv('OBS_API_USERNAME'), os.getenv('OBS_API_PASSWD'))

    # email notification to mailing list
    data.update({'noreply_sender' : os.getenv('NOREPLY_EMAIL_SENDER'),
                'mailinglist' : os.getenv('MAILINGLIST', '').split(','),
                'bccs' : os.getenv('BCC_MAILS', '').split(',')})
    status = mailer(event_fields, _bs, data, os.getenv('SR_ENABLE_USER'),
            os.getenv('EMAIL_TEMPLATES_DIR'))
    print status
    if status:
        prepare_mail("request_trigger_%s.env" % (data['OBS_REQ_PKG']), status['subject'], \
                status['body'], os.getenv('NOREPLY_EMAIL_SENDER'), \
                status['To'], status['Cc'])

def sub_request_gerrit(event_type, event_fields, reqinfo):
    """ sub request gerrit """

    try:
        data, projects_data = obs_git_data(event_fields)
    except GitError, err:
        print >> sys.stderr, err
        return []

    gerrit = Gerrit(os.getenv('GERRIT_HOSTNAME_EXTERNAL'), os.getenv('GERRIT_USERNAME'),
                    os.getenv('GERRIT_SSHPORT'),
                    int(os.getenv('GERRIT_SILENT_MODE')))

    for project_data in projects_data:
        data.update(project_data)
        data.update({'GIT_AUTHOR_EMAIL': '%s <%s>' % \
                                    (project_data['author'],
                                    project_data['email'])})
        # Update sourcepackage and targetpackage into event_fields,
        # becuase the multiple project have the different packages.
        event_fields.update({'sourcepackage': project_data['OBS_REQ_PKG_SRC'],
                             'targetpackage': project_data['OBS_REQ_PKG']})
        if not (event_type == 'OBS_SRCSRV_REQUEST_REVOKED' or \
                (event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE' and \
                 event_fields['state'] == 'revoked')):
            notify_submiter(event_fields, data)

        git_cache = os.path.join(os.getenv('GIT_CACHE_DIR'))
        prjdir = os.path.join(git_cache, data['GIT_PROJECT'])

        try:
            gitprj = Git(prjdir)
        except GitRepositoryError, err:
            # clone project to local workspace if it doesn't exist in git cache
            if not clone_gitproject(data['GIT_PROJECT'], \
                       os.path.join(os.getenv('WORKSPACE'), data['GIT_PROJECT'])):
                return -1
            gitprj = Git('%s/%s' % (os.getenv('WORKSPACE'),
                                   data['GIT_PROJECT']))

        trigger_next(event_type, data)

        if event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE':
            if event_fields['state'] == 'declined':
                request_rejected(data, gerrit)
            elif event_fields['state'] == 'revoked':
                request_revoked(data)
            elif event_fields['state'] == 'accepted':
                print 'From accept'
                request_accepted(data, gerrit, gitprj, reqinfo.get('targetpackagelist', None))

        elif event_type == 'OBS_SRCSRV_REQUEST_CREATE':
            request_created(data)

        elif event_type == 'OBS_SRCSRV_REQUEST_ACCEPTED':
            request_accepted(data, gerrit, gitprj, reqinfo.get('targetpackagelist', None))
        elif event_type == 'OBS_SRCSRV_REQUEST_REVOKED':
            request_revoked(data)

    return data

def request_github_accepted(data, gitprj, targetpackagelist=[]):
    """Do lots of things when request accepted"""

    print '====request accepted===================================='

    message = 'The SR (Submit Request) has been accepted to OBS %s project.\n' \
    '- Package: %s\n' \
    '- Reviewer: %s\n' \
    '- Comments: %s\n' \
    '- Git project: %s\n' \
    '- Tag:%s\n' \
    '- Request URL:%s' % (data['OBS_REQ_PRJ'],
                          data['OBS_REQ_PKG'],
                          data["OBS_REQ_SENDER"],
                          data["OBS_REQ_COMMENT"],
                          data['GIT_PROJECT'],
                          data["GIT_TAG"],
                          request_url(data['OBS_REQ_ID']))

    obs_target = data['OBS_REQ_PRJ'].lower().replace(':', '/')
    timestamp = datetime.datetime.utcnow().strftime("%Y%m%d.%H%M%S")

    # use os.path.join() to avoid '//', which is invalid as tag name
    accepted_tag = os.path.join('accepted', obs_target, timestamp)

    gitprj.create_tag(accepted_tag, message, data['commitid'])
    sleep(1)

    remote = '%s/%s' % (data['GITHUB_URL'], data['GIT_PROJECT'])
    try:
        gitprj.push_tag(remote, accepted_tag)
    except GitRepositoryError, gre:
        print gre
        return 1

    # push accepted commit to accepted branch refs/heads/accepted/*
    # e.g. changes, accepted for Tizen:Mobile should be pushed to
    # branch refs/heads/accepted/tizen_mobile
    dst = 'refs/heads/accepted/%s' % \
            data['OBS_REQ_PRJ'].lower().replace(':', '_')
    try:
        gitprj.push(remote, data['commitid'], dst, force=True)
    except GitRepositoryError, gre:
        print gre
        return 1


    additional_comment = REPAIR_COMMENT \
                     % (data['OBS_REQ_ID'], os.getenv('OBS_URL_EXTERNAL'), data['OBS_REQ_ID'], \
                        data['OBS_REQ_DESP'])
    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'], \
                    handle_link={'target_project': data['OBS_REQ_PRJ'], \
                                 'comments': additional_comment, \
                                 'target_packages': targetpackagelist})

def request_github_rejected(data):
    """When request rejected, give msg to gerrit and delete remote package"""

    print '====request rejected===================================='

    message = 'The SR (Submit Request) has been *rejected* ' \
    'to OBS %s project.\n' \
    '- Reviewer: %s\n' \
    '- Comments: %s\n' \
    '- Git project: %s\n' \
    '- Tag:%s\n' \
    '- Request URL:%s' % (data['OBS_REQ_PRJ'],
                          data["OBS_REQ_SENDER"],
                          data["OBS_REQ_COMMENT"],
                          data['GIT_PROJECT'],
                          data["GIT_TAG"],
                          request_url(data['OBS_REQ_ID']))

    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'])

def request_github_revoked(data):
    """When request revoked, delete the remote package"""

    print '====request revoked===================================='

    delete_from_obs(data['OBS_REQ_PRJ_SRC'], data['OBS_REQ_PKG_SRC'])

def sub_request_github(event_type, event_fields, reqinfo):
    """ sub request github """
    try:
        data, projects_data = obs_git_data(event_fields)
    except GitError, err:
        print >> sys.stderr, err
        return []

    for project_data in projects_data:
        data.update(project_data)

        git_cache = os.path.join(os.getenv('GIT_CACHE_DIR'))
        if event_fields.get('github'):
            github = event_fields.get('github')
            if github.get(data['GIT_PROJECT']):
                giturl = event_fields.get('github').get(data['GIT_PROJECT'])
                gitorg = giturl.split(':')[1]
                git_full_name = os.path.join(gitorg, data['GIT_PROJECT'])
                data['GITHUB_URL'] = giturl
                prjdir = os.path.join(git_cache, git_full_name)
                git_cache_dir = os.path.join(git_cache, gitorg)
                print 'org=%s git_full_name = %s' %(gitorg, git_full_name)
            else:
                print 'project: %s is not present in github'%( data['GIT_PROJECT'])
        else:
            prjdir = os.path.join(git_cache, data['GIT_PROJECT'])
            giturl = None
            git_cache_dir = None

        try:
            gitprj = Git(prjdir)
        except GitRepositoryError, err:
            # clone project to local workspace if it doesn't exist in git cache
            print "clone"
            if not clone_gitproject(data['GIT_PROJECT'], \
                       os.path.join(os.getenv('WORKSPACE'), data['GIT_PROJECT']), \
                       giturl=giturl, git_cache_dir=git_cache_dir):
                return -1
            gitprj = Git('%s/%s' % (os.getenv('WORKSPACE'),
                                   data['GIT_PROJECT']))

        if event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE':
            if event_fields['state'] == 'declined':
                request_github_rejected(data)
            elif event_fields['state'] == 'revoked':
                request_github_revoked(data)
            elif event_fields['state'] == 'accepted':
                request_github_accepted(data, gitprj, reqinfo.get('targetpackagelist', None))

    return data

def main():
    """The main body"""
    buildmonitor_enabled = os.getenv("BUILDMONITOR_ENABLED", "0") != "0"
    print 'buildmonitor_enabled(%s)\n' % (buildmonitor_enabled)
    if buildmonitor_enabled:
        bm_start_datetime = datetime.datetime.now()

    event_fields = {}
    if os.getenv('TRIGGER_INFO', None) is not None:
        event_fields = trigger_info(os.getenv('TRIGGER_INFO'))
    elif os.getenv('MANUAL_TRIGGER_STATE') and os.getenv('MANUAL_TRIGGER_OBS_REQUEST_NUMBER'):
        event_fields = {'event_type': 'OBS_SRCSRV_REQUEST_STATECHANGE',
                        'number': os.getenv('MANUAL_TRIGGER_OBS_REQUEST_NUMBER'),
                        'state': os.getenv('MANUAL_TRIGGER_STATE'),
                        'author': 'Admin'}

    if not event_fields:
        print 'Invalid OBS event'
        return -1

    # Get event type
    event_type = event_fields['event_type']

    if event_type == 'OBS_SRCSRV_REQUEST_CREATE' \
       and 'home:prerelease:' in event_fields['sourceproject']:
        # do not notify submitter about SR creation from prerelease projects
        # repa immediately accepts/rejects SRs after creation, so submitter
        # will be notified anyway
        print 'Skipping processing of REQUEST_CREATE for prerelease project'
        return 0

    # Update info of request
    build = BuildService(os.getenv('OBS_API_URL'), \
            os.getenv('OBS_API_USERNAME'), os.getenv('OBS_API_PASSWD'))
    if 'id' not in event_fields and 'number' in event_fields:
        print 'Use number(%s) field instead of id' % event_fields.get('number')
        event_fields['id'] = event_fields.get('number')
    reqinfo = build.get_sr_info(event_fields.get('id'))
    if 'targetproject' not in event_fields and 'targetproject' in reqinfo:
        event_fields['targetproject'] = reqinfo['targetproject']
    if 'sourceproject' not in event_fields and 'sourceproject' in reqinfo:
        event_fields['sourceproject'] = reqinfo['sourceproject']

    submissions = []
    try:
        saved_info = build.get_info(event_fields['sourceproject'])
        event_fields['packages'] = \
                    unicode_to_str(saved_info['packages'])
        if os.getenv('MANUAL_TRIGGER_STATE') and \
            os.getenv('MANUAL_TRIGGER_OBS_REQUEST_NUMBER') and \
            'description' not in event_fields:
            event_fields['description'] = 'Submitter: %s\nComments: submission %s \nGit project: [%s]\nTag:%s' % \
                                         (unicode_to_str(saved_info['submitter']), \
                                          unicode_to_str(saved_info['git_tag']), \
                                          unicode_to_str(', '.join(saved_info['projects'])), \
                                          unicode_to_str(saved_info['git_tag']))

        # SR-SYNC: SR listing and its pure git repos.
        if 'submissions' in saved_info:
            submissions = unicode_to_str(saved_info['submissions'])
        if 'github' in saved_info:
            event_fields['github'] = saved_info.get('github')

    except Exception as err:
        print 'Not able to fetch package list from OBS %s' % err
        event_fields['packages'] = []
        return 0

    for var in ['targetproject', 'sourceproject',
                  'comment', 'sender']:
        if var not in event_fields:
            event_fields.update({var: reqinfo.get(var)})

    # add repa_action log for iris
    pub_enabled = os.getenv("IRIS_PUB_ENABLED", "0") != "0"
    if pub_enabled:
        rest = IrisRestClient(
            os.getenv("IRIS_SERVER"),
            os.getenv("IRIS_USERNAME"),
            base64.b64decode(os.getenv('IRIS_PASSWORDX', '')))
        rest.publish_event("repa_action", {
            "project": event_fields.get('sourceproject'),
            "status": event_fields.get('state'),
            "who": event_fields.get('who'),
            "when": event_fields.get('when'),
            "reason": event_fields.get('comment'),
            })

    if event_fields.get('github'): #GITHUB
        data = sub_request_github(event_type, event_fields, reqinfo)
    else: #GERRIT
        data = sub_request_gerrit(event_type, event_fields, reqinfo)

    # Deleting project for SR-SYNC
    if submissions and len(submissions) >= 1:
        if (event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE') and \
            (event_fields['state'] == 'accepted'):
            additional_comment = REPAIR_COMMENT \
                             % (data['OBS_REQ_ID'], os.getenv('OBS_URL_EXTERNAL'), data['OBS_REQ_ID'], \
                                data['OBS_REQ_DESP'])
            delete_from_obs(data['OBS_REQ_PRJ_SRC'], None, \
                            handle_link={'target_project': data['OBS_REQ_PRJ'], \
                                         'comments': additional_comment, \
                                         'target_packages': reqinfo.get('targetpackagelist', None)})
        elif (event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE') and \
              (event_fields['state'] == 'revoked' or \
               event_fields['state'] == 'declined'):
             delete_from_obs(data['OBS_REQ_PRJ_SRC'], None)

    if buildmonitor_enabled and event_type == 'OBS_SRCSRV_REQUEST_STATECHANGE':
        bm_end_datetime = datetime.datetime.now()
        #buildmonitor.sr_accept_reject_for_sr_status_detail(event_fields,
        #                                                   bm_start_datetime,
        #                                                   bm_end_datetime,
        #                                                   data["GIT_TAG"])
        bm_stage = 'SR_Accept'
        bm_data = {"bm_stage" : bm_stage,
                   "event_fields" : event_fields,
                   "bm_start_datetime" : str(bm_start_datetime),
                   "bm_end_datetime" : str(bm_end_datetime),
                   "bm_git_tag" : data["GIT_TAG"],
                   "submissions" : submissions,
                  }
        trigger_next("BUILD-MONITOR", bm_data)

    return 0

if __name__ == '__main__':
    sys.exit(main())

