package jp.agentec.sinaburocast.service;

import java.io.UnsupportedEncodingException;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.List;

import javax.mail.MessagingException;

import jp.agentec.sinaburocast.common.SinaburoConstant;
import jp.agentec.sinaburocast.common.exception.ExpectedException;
import jp.agentec.sinaburocast.common.exception.SystemException;
import jp.agentec.sinaburocast.common.util.MailUtil;
import jp.agentec.sinaburocast.entity.AdminNotifyMail;
import jp.agentec.sinaburocast.entity.Enquete;
import jp.agentec.sinaburocast.entity.Member;
import jp.agentec.sinaburocast.entity.MemberNotifyMail;
import jp.agentec.sinaburocast.entity.PointDonation;
import jp.agentec.sinaburocast.entity.Question;

import org.seasar.extension.jdbc.where.SimpleWhere;
import org.seasar.framework.beans.util.BeanMap;
import org.seasar.framework.container.annotation.tiger.Component;
import org.seasar.framework.container.annotation.tiger.InstanceType;
import org.seasar.framework.util.StringUtil;

@Component(instance=InstanceType.SINGLETON)
public class PointDonationService extends AbstractService<PointDonation> {

	public PointGetService pointGetService;
	public ReplyService replyService;
	
	public MemberService memberService;
	
	public static final String ID_SEQ_NAME = "point_donation_id_seq";

	/**
	 * IDを発行して、登録する。
	 */
	public int insertPointDonation(PointDonation pointDonation, String insId) {
		pointDonation.pointDonationId =
			getSeqNextVal(Integer.class, ID_SEQ_NAME);
		return super.insert(pointDonation, insId);
	}
	
	
    public PointDonation findById(Integer pointDonationId) {
        return select().id(pointDonationId).getSingleResult();
    }

    public PointDonation findBymemberId(Integer memberId) {
        return select().where(new SimpleWhere().eq("memberId", memberId)).getSingleResult();
    }

    public List<PointDonation> findAllOrderById() {
        return select().orderBy("pointDonationId asc").getResultList();
    }

    public List <PointDonation> findBymemberIdList(Integer memberId) {
        return select().where(new SimpleWhere().eq("memberId", memberId)).getResultList();
    }
    public MemberNotifyMailService memberNotifyMailService;
    public AdminNotifyMailService adminNotifyMailService;
    /**
     * 団体寄付の処理を行う。
     * @param pointDonation 
     * @param loginId 寄付したユーザーのID
     * @throws MessagingException 
     * @throws UnsupportedEncodingException 
     * @throws SystemException 
     * @throws ParseException 
     * @throws ExpectedException 
     */
	public void organizationDonation(PointDonation pointDonation, Member member, Enquete enquete, ArrayList<Question> questionList) throws UnsupportedEncodingException, MessagingException, SystemException, ParseException {
		// 回答を登録する
		replyService.replyRegistLogic(member, questionList, enquete, true);
		
		//ポイント削減する。
		pointGetService.upDownPointLogic(pointDonation.pointNum,pointDonation.memberId,member.loginId);
		
		Member upMember = memberService.findById(member.memberId);
		upMember.pointNum = upMember.pointNum - pointDonation.pointNum;
		if (upMember.pointNum < 0) {
			throw new SystemException("point is below 0. current=" +  upMember.pointNum + " donation=" + pointDonation.pointNum, "E013");
		}
		
		memberService.update(upMember, member.loginId);
		this.insertPointDonation(pointDonation, member.loginId);
		
		//■メール送信
		BeanMap wehreMap = new BeanMap();

		wehreMap.put("enqueteId", enquete.enqueteId);
		wehreMap.put("notifyMailSendFlg", SinaburoConstant.notifyMailSendFlg.SEND);

		//1件のみのはず
		List<MemberNotifyMail> memberNotifyMailList = memberNotifyMailService.findByCondition(wehreMap);
    	for (MemberNotifyMail memberNotifyMail : memberNotifyMailList) {

    		
    		//ユーザーに送信
    		if(StringUtil.isNotBlank(member.pcEmail)){
    			MailUtil.send(member.pcEmail, memberNotifyMail.subject, memberNotifyMail.mailBody);
    		}

    		if(StringUtil.isNotBlank(member.mbEmail)){
    			MailUtil.send(member.mbEmail, memberNotifyMail.subject,memberNotifyMail.mailBody);
    		}

    		//BCCに送信
    		if(StringUtil.isNotBlank(memberNotifyMail.notifyMailSendBcc)){
    			MailUtil.send(memberNotifyMail.notifyMailSendBcc,memberNotifyMail.subject, memberNotifyMail.mailBody);
    		}
    	}
    	
    	List<AdminNotifyMail> adminNotifyMailList = adminNotifyMailService.findByCondition(wehreMap);
    	for (AdminNotifyMail adminNotifyMail : adminNotifyMailList) {
    		
    		
    		if(StringUtil.isNotBlank(adminNotifyMail.notifyMailSendTo)){
    			String [] bccAdress = adminNotifyMail.notifyMailSendTo.split(",");
				for(int i=0;i<bccAdress.length;i++){
					MailUtil.send(bccAdress[i],adminNotifyMail.subject, adminNotifyMail.mailBody);
				}
			}
    		
    		if(StringUtil.isNotBlank(adminNotifyMail.notifyMailSendCc)){
    			String [] bccAdress = adminNotifyMail.notifyMailSendCc.split(",");
				for(int i=0;i<bccAdress.length;i++){
					MailUtil.send(bccAdress[i],adminNotifyMail.subject ,adminNotifyMail.mailBody);
				}
			}
		}
    	member.pointNum = upMember.pointNum; // ポイントを設定する
	}

    /**
     * 指定した団体の寄付ポイントの合計を取得する
     * @param organizationId 団体ID
     */
	public Integer findPointSumByOrganizationId(Integer organizationId){
		return jdbcManager.selectBySql(Integer.class, "select sum(point_num) from t_point_donation where organization_id = ? group by organization_id",organizationId).getSingleResult();
	}
}