package com.cloudcross.ssp.web.advertiser.main.ad.target;

import java.io.IOException;
import java.io.PrintWriter;
import java.io.UnsupportedEncodingException;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang.ArrayUtils;
import org.apache.log4j.Logger;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

import com.cloudcross.ssp.base.utils.freemarker.FreemarkerTemplateProcessor;
import com.cloudcross.ssp.base.web.SimpleController;
import com.cloudcross.ssp.common.consts.DirectType;
import com.cloudcross.ssp.common.consts.Status;
import com.cloudcross.ssp.common.utils.Common;
import com.cloudcross.ssp.common.utils.LangUtil;
import com.cloudcross.ssp.common.utils.Pager;
import com.cloudcross.ssp.common.utils.AdvertiserSortByDate;
import com.cloudcross.ssp.common.utils.SqlHelper;
import com.cloudcross.ssp.model.Account;
import com.cloudcross.ssp.model.AdGroup;
import com.cloudcross.ssp.model.AdGroupPlace;
import com.cloudcross.ssp.model.Advertiser;
import com.cloudcross.ssp.model.Campaign;
import com.cloudcross.ssp.model.DayParting;
import com.cloudcross.ssp.model.Direct;
import com.cloudcross.ssp.model.Location;
import com.cloudcross.ssp.model.Log;
import com.cloudcross.ssp.model.Order;
import com.cloudcross.ssp.model.Place;
import com.cloudcross.ssp.model.Wifi;
import com.cloudcross.ssp.model.WifiGroupInfo;
import com.cloudcross.ssp.model.Zone;
import com.cloudcross.ssp.model.pojo.CampaignPojo;
import com.cloudcross.ssp.service.IAdGroupPlaceService;
import com.cloudcross.ssp.service.IAdGroupService;
import com.cloudcross.ssp.service.IAdvertiserService;
import com.cloudcross.ssp.service.IBannerService;
import com.cloudcross.ssp.service.ICampaignService;
import com.cloudcross.ssp.service.IDirectService;
import com.cloudcross.ssp.service.ILocationService;
import com.cloudcross.ssp.service.ILogService;
import com.cloudcross.ssp.service.IOrderService;
import com.cloudcross.ssp.service.IPlaceService;
import com.cloudcross.ssp.service.IWifiService;
import com.cloudcross.ssp.service.impl.WifiGroupInfoService;
import com.cloudcross.ssp.service.impl.ZoneService;



/**
 * 广告投放（创意组）相关页面
 * @author chenyou
 *
 */

@Controller
@RequestMapping("/advertiser/main/ad/target/ad-group")
public class AdGroupController extends SimpleController {
	private static final Logger LOG = Logger.getLogger(AdGroupController.class);
	@Autowired
	private IAdGroupService adGroupService;
	@Autowired
	private IBannerService bannerService;
	@Autowired
	private IAdGroupPlaceService adGroupPlaceService;
	@Autowired
	private IDirectService directService;
	@Autowired
	private IPlaceService placeService;
	@Autowired
	private ILocationService locationService;
	@Autowired
	private ILogService logService;
	@Autowired
	private IWifiService wifiService;
	@Autowired
	private FreemarkerTemplateProcessor templateProcessor;
	@Autowired
	private ICampaignService campaignService;
	@Autowired
	private IOrderService orderService;
	@Autowired
	private IAdvertiserService advertiserService;
	@Autowired
	private ZoneService zoneService;
	@Autowired
	private WifiGroupInfoService wifiGroupInfoService;
	
	/**
	 * 投放管理列表页
	 * 前端需要传递三个参数分别为广告主id(advertiserId),订单id(orderId),活动id(campaginId)
	 * 页面搜索的时候是按投放名称进行搜索
	 * @param model
	 * @param paramMap 
	 * @param selectedStatus 选择的状态变量，默认的是全部，为空值
	 * @param page
	 * @return
	 */
	@RequestMapping("/list")
	public String list(Model model,
			@RequestParam HashMap<String, Object> paramMap,
			@RequestParam(defaultValue = "0") int selectedStatus,
			@RequestParam(defaultValue = "1") int page) {
		LOG.debug("请求参数：page=" + page + "," + paramMap);
		LOG.debug("请求参数：selectedStatus=" + selectedStatus + "," + paramMap);
//		//这里没有传值自己设定值
//		paramMap.put("advertiserId", "-1");
//		paramMap.put("orderId", "100");
//		paramMap.put("campaignId", "100");
//		paramMap.put("adGroupName", "电饭锅");
		
		
		int totalRow = 0;
		Pager pager = null;
		List<AdGroup> adGroupList = null;
		
		Long campaignId = null;
		Long orderId = null;
		Long advertiserId = null;
		/**
		 * 对传入的数据做处理
		 * 第一：如果传入的活动id值为空值或者空字符串或者是-1的话则表明这个活动id代表的是全部的活动，这时让它的值设为-1，并且加上一个活动标志它的值设为全部（它用在sql语句的判断上）
		 * 第二：如果传入的订单id值为空值或者空字符串或者是-1的话，这时不能够直接认为它是全部的订单，要对活动id进行判断一下，如果活动id是全部活动的话，那么这时就是全部的订单，订单
		 * id就设为-1并且加上一个订单标志值设为全部，否则订单id的值为通过活动id查找到的订单id值
		 * 第三：如果传入的广告主id值为空值或者空字符串或者是-1的话则，这时也不能够直接认为它是全部的广告主，要对订单id进行判断，如果订单id是全部订单的话，那么这是就是全部广告主
		 * 这时广告主id的值为-1，同时通过当前登录账号得到代理商的id，使查出来的信息是该登录账号下的全部广告主，否则广告主id的值为通过订单id查找到的广告主id值
		 * 
		 */
		if(null == paramMap.get("campaignId") || "".equals(paramMap.get("campaignId")) 
				|| "-1".equals(paramMap.get("campaignId"))) {
			paramMap.put("campaignMark", "全部");
			paramMap.put("campaignId", -1l);
			paramMap.put("selectedcampaignName", "全部活动");
		} else {
			//将前端传过来的campaignId变成Long型
			campaignId = Long.parseLong(String.valueOf(paramMap.get("campaignId")));
			paramMap.put("campaignId", campaignId);
			Campaign campaignObj = campaignService.findById(Long.valueOf(paramMap.get("campaignId").toString()));
			paramMap.put("selectedcampaignName", campaignObj.getName());
		}
		
		
		if(null == paramMap.get("orderId") || "".equals(paramMap.get("orderId")) 
				|| "-1".equals(paramMap.get("orderId"))) {
			
			if(campaignId == null) {
				paramMap.put("orderMark", "全部");
				paramMap.put("orderId", -1l);
				paramMap.put("selectedorderName", "全部订单");
			} else {
				Campaign campaign = campaignService.findById(campaignId);
				orderId = campaign.getOrderId();
				paramMap.put("orderId", orderId);
				String orderName = orderService.selectOrderNameById(orderId);
				paramMap.put("selectedorderName", orderName);
			}
			
		} else {
			
			//将前端传过来的orderId变成Long型
			orderId = Long.parseLong(String.valueOf(paramMap.get("orderId")));
			paramMap.put("orderId", orderId);
			String orderName = orderService.selectOrderNameById(orderId);
			paramMap.put("selectedorderName", orderName);
		}
		
		
		if(null == paramMap.get("advertiserId") || "".equals(paramMap.get("advertiserId")) 
				|| "-1".equals(paramMap.get("advertiserId"))) {
			
			if(orderId == null) {
				paramMap.put("agentId", getLoginUser().getAgentId());
				paramMap.put("advertiserId", -1l);
				paramMap.put("selectedadvertiserName", "全部广告主");
			} else {
				paramMap.put("agentId", null);
				Order order = orderService.findById(orderId);
				advertiserId = order.getAdvertiserId();
				paramMap.put("advertiserId", advertiserId);
				String advertiserName = advertiserService.selectAdvertiserNameById(advertiserId);
				paramMap.put("selectedadvertiserName", advertiserName);
			}
			
		} else {
			paramMap.put("agentId", null);
			//将前端传过来的advertiserId变成Long型
			advertiserId = Long.parseLong(String.valueOf(paramMap.get("advertiserId")));
			paramMap.put("advertiserId", advertiserId);
			String advertiserName = advertiserService.selectAdvertiserNameById(advertiserId);
			paramMap.put("selectedadvertiserName", advertiserName);
		}
		
		
		// 这里的搜索只是对投放名称进行搜索
		String adGroupName = null;
		if (null != paramMap.get("searchValue")) {
			try {
				adGroupName = new String((String.valueOf(paramMap
						.get("searchValue"))).getBytes("ISO-8859-1"), "UTF-8");
			} catch (UnsupportedEncodingException e) {
				e.printStackTrace();
			}
		}

		paramMap.put("adGroupName", SqlHelper.doLike(adGroupName));
		paramMap.put("searchValue", adGroupName);
		/**
		 * 根据状态来进行查询
		 * 设置0-表示全部，1-表示投放中，2-表示未投放，3-投放结束，4-停用
		 * 没选默认时status应该是为0
		 * 实现思想：这里如果是选择的是0（全部的）话那就不用加什么条件，那如果选择的是1的话，就在paramMap上加上一个键值对
		 * key的名字就设置为selectedStatus1，那这样就可以在mapper文件中对key值进行判断，然后增加相应的条件，下面的就以此
		 * 类推
		 */
		switch(selectedStatus) {
		//当所选择的状态是0表示全部时就不用添加什么条件了，只要把所有的都找出来就行
		case 0:paramMap.put("adGroupStatus", selectedStatus);break;
		//当选择的状态是1时表示的是投放中，那这时找的就应该是当前时间处于投放开始时间和投放结束时间之间并且应该是开启的状态
		case 1:paramMap.put("selectedStatus1", selectedStatus);break;
		//当选择的状态是2时表示的是未投放，那这时就应该是投放开始时间要大于当前时间
		case 2:paramMap.put("selectedStatus2", selectedStatus);break;
		//当选择的状态是3时表示的是投放结束，那这时就应该是投放的结束时间小于当前时间
		case 3:paramMap.put("selectedStatus3", selectedStatus);break;
		//当选择的状态是4时表示的是停用，那这时只要在写数据库查询时加上它的投放表中的status字段等于1就行了
		case 4:paramMap.put("selectedStatus4", selectedStatus);break;
		}
		paramMap.put("adGroupStatus", selectedStatus);
		
		// 根据条件查找符合的投放总数
		totalRow = adGroupService.countByParams(paramMap);
		
		
		// 查询符合条件的广告策略
		pager = new Pager();
		pager.setPage(page);
		pager.setTotalRow(totalRow);
		adGroupList = adGroupService.findByParams(paramMap, pager);
		
		model.addAllAttributes(paramMap);
		model.addAttribute("pager", pager);
		model.addAttribute("adGroupList", adGroupList);
		
		return page("list");
	}
	
	
	@RequestMapping("/enable")
	public @ResponseBody
	String enable(HttpServletRequest request,Long[] id) {
		Date date = null;
		if (ArrayUtils.isNotEmpty(id)) {
			//循环得到投放名称
			List<String> adGroupNameList = new ArrayList<String>();
			
			for(int i = 0; i < id.length; i++) {
				AdGroup adGroup = adGroupService.findById(id[i]);
				adGroupNameList.add(adGroup.getAdGroupName());
			}
			date = new Date();
			//如果开启成功，则增加对应的修改记录
			if(adGroupService.updateStatus(LangUtil.array2List(id),
					Status.enable.value)) {
				for(int i = 0; i < id.length; i++) {
					Log log = new Log();
					//对应模块，这里应该是投放模块
					log.setModule("AdGroup");
					//对应的表名，这里是t_adgroup
					log.setTableName("t_adgroup");
					//对应的投放id
					log.setRecordId(id[i]);
					//对应的操作类型
					log.setActionType("开启");
					//变更详情
					log.setAction("开启了投放：" + adGroupNameList.get(i));
					log.setActionTime("100");
					log.setAccountId(new Long(getLoginUser().getId()));
					log.setUserIp(Common.toIpAddr(request));
					log.setAccountName(getLoginUser().getAccountName());
					logService.add(log);
				}
			}
		}
		return OK;
	}

	@RequestMapping("/disable")
	public @ResponseBody
	String disable(HttpServletRequest request,Long[] id) {
		if (ArrayUtils.isNotEmpty(id)) {
			//循环得到投放名称
			List<String> adGroupNameList = new ArrayList<String>();
			
			for(int i = 0; i < id.length; i++) {
				AdGroup adGroup = adGroupService.findById(id[i]);
				adGroupNameList.add(adGroup.getAdGroupName());
			}
			
			//如果停用成功，则增加对应的修改记录
			if(adGroupService.updateStatus(LangUtil.array2List(id),
					Status.disable.value)) {
				
				for(int i = 0; i < id.length; i++) {
					Log log = new Log();
					//对应模块，这里应该是投放模块
					log.setModule("AdGroup");
					//对应的表名，这里是t_adgroup
					log.setTableName("t_adgroup");
					//对应的投放id
					log.setRecordId(id[i]);
					//对应的操作类型
					log.setActionType("停用");
					//变更详情
					log.setAction("停用了投放：" + adGroupNameList.get(i));
					//下面这几个字段目前后端数据没有得到。所以仅作测试用！
					log.setActionTime("100");
					log.setAccountId(new Long(getLoginUser().getId()));
					log.setUserIp(Common.toIpAddr(request));
					log.setAccountName(getLoginUser().getAccountName());
					logService.add(log);
				}
			}
		}
		return OK;
	}

	/**
	 * 批量删除时只是把这些选中的行的状态改为-1，并没有把它从表里面删掉
	 * @param id
	 * @return
	 */
	@RequestMapping("/delete")
	public @ResponseBody
	String delete(HttpServletRequest request, Long[] id) {
		if (ArrayUtils.isNotEmpty(id)) {
			//循环得到投放名称
			List<String> adGroupNameList = new ArrayList<String>();
			
			for(int i = 0; i < id.length; i++) {
				AdGroup adGroup = adGroupService.findById(id[i]);
				adGroupNameList.add(adGroup.getAdGroupName());
			}
			
			//如果删除成功则添加修改记录
			if(adGroupService.updateStatusAll(LangUtil.array2List(id),
					Status.delete.value)) {
				
				for(int i = 0; i < id.length; i++) {
					Log log = new Log();
					//对应模块，这里应该是投放模块
					log.setModule("AdGroup");
					//对应的表名，这里是t_adgroup
					log.setTableName("t_adgroup");
					//对应的投放id
					log.setRecordId(id[i]);
					//对应的操作类型
					log.setActionType("删除");
					//变更详情
					log.setAction("删除了投放：" + adGroupNameList.get(i));
					//下面这几个字段目前后端数据没有得到。所以仅作测试用！
					log.setActionTime("100");
					log.setAccountId(new Long(getLoginUser().getId()));
					log.setUserIp(Common.toIpAddr(request));
					log.setAccountName(getLoginUser().getAccountName());
					logService.add(log);
				}
			}
			
		}
		return OK;
	}
	
	@RequestMapping("/wifiList")
	public String wifiList(Model model
			,@RequestParam HashMap<String, Object> paramMap) {
		//从前端获得areas值，这里自己给定
		Long campaignId = 5l;	
		model.addAttribute("campaignId",campaignId);
		
		Long adGroupId = 1l;	
		String address = (String) paramMap.get("searchValue");
		Double dis = 0d;
		String city = (String) paramMap.get("city");
		if(paramMap.get("dis") != null) {
			dis = Double.valueOf((String) paramMap.get("dis")).doubleValue();
		}
		List<Wifi> wifiListFind = null;
		if(address != null && address != "" && city != null) {
			//找到要搜索的地址的经度纬度
			Map<String, String> json = wifiService.getGeocoderLatitude(address);
			if(json != null) {
				double longitude = Double.valueOf((String) json.get("lng")).doubleValue();
				double latitude = Double.valueOf((String) json.get("lat")).doubleValue();
				//根据经度纬度和距离在规定的城市里找到对应的所有的wifi热点
				wifiListFind = wifiService.findNeighPosition(longitude, latitude, dis,city);
			}
		}
		else if(city != null){
			//当没有搜索地址时，找出所有的城市下的热点
			wifiListFind = wifiService.findAllLocation(city);
		}
		for(Wifi wf:wifiListFind) {
			double lng = wf.getLongitude();
			wf.setLongitude((float)(Math.round(lng*100))/100);
			double lat = wf.getLatitude();
			wf.setLatitude((float)(Math.round(lat*100))/100);
		}
		model.addAttribute("wifiListFind", wifiListFind);
		model.addAllAttributes(paramMap);
		model.addAttribute("adGroupId",adGroupId);			
		return page("wifiList");
	}
	

	@RequestMapping("/create")
	public String create(Model model
			, @RequestParam Long campaignId) {
		Campaign campaign = campaignService.findById(campaignId);		
		Long orderId = campaign.getOrderId();
		Order order = orderService.findById(orderId);
		Long advertiserId = order.getAdvertiserId();
		Advertiser advertiser = advertiserService.findById(advertiserId);
		Long agentId = advertiser.getAgentId();
		model.addAttribute("campaignId", campaignId);
		model.addAttribute("advertiserId", advertiserId);	
		model.addAttribute("orderId", orderId);
		model.addAttribute("agentId", agentId);
		model.addAttribute("budget", campaign.getTotalBudget());
		
		
		//找到所有的场景，并且显示出来
		List<Place> placeList = placeService.findAll();
		model.addAttribute("placeList",placeList);
		return page("create");
	}
	
	@RequestMapping("/edit")
	public String edit(Model model,@RequestParam Map<String, Object> paramMap) {
		Long id = Long.valueOf(paramMap.get("id").toString());//投放id
		AdGroup adGroup = adGroupService.findById(id);
		
		//找到这个投放对应的活动，然后保存活动预算
		Campaign campaign = campaignService.findById(adGroup.getCampaignId());
		model.addAttribute("budget", campaign.getTotalBudget());
		
		//找到所有的场景，并且显示出来
		List<Place> placeList = placeService.findAll();
		
		//获取所有已选择的场景并且用,分割存放到place里面
		String place = "0,";
		List<AdGroupPlace> adGroupPlaceList = adGroupPlaceService.findAll(adGroup.getId());
		for(AdGroupPlace pc:adGroupPlaceList) {
			if(pc != adGroupPlaceList) {
				place += pc.getPlaceId() + ",";
			}else {
				place += adGroupPlaceList;
			}
		}
		// 千次转换
	    adGroup.setMaxImpression(adGroup.getMaxImpression() / 1000);
	    adGroup.setDailyMaxImpression(adGroup.getDailyMaxImpression() / 1000);
	    /**
	     * 把数据库里面的日期转换为前端的需要的格式显示
	     */
	    String activeTime = "";
	    SimpleDateFormat formatter;   
	    formatter = new SimpleDateFormat ("yyyy-MM-dd");   
	    String startTime = formatter.format(adGroup.getStartDate());
	    String endTime = formatter.format(adGroup.getEndDate());
	    activeTime = startTime + " to " + endTime;	    
		
	  //找到所有的已选择的wifi
		List<Wifi> adGroupWifiList = wifiService.findAllAdgroupWifi(adGroup.getId());
		//把找到的已选wifi热点转换为前端需要的数据格式
		String cacheSelected = "[";
		String selectedWifi ="";
		if(adGroupWifiList != null) {
			int index = 0;
			for(Wifi wf: adGroupWifiList) {
				index ++;
				cacheSelected += "{" + "\"" + "id" + "\"" + ":\"" +  wf.getId() 
						     + "\",\"" + "address" + "\"" + ":" + "\"" +  wf.getAddress() + "\","
						     + "\"" + "lng" + "\"" + ":" + "\"" +  (float)(Math.round(wf.getLongitude()*100))/100 + "\","
						     + "\"" + "lat" + "\"" + ":" + "\"" + (float)(Math.round(wf.getLatitude()*100))/100 + "\"" + "}";
				selectedWifi += wf.getId();
				String str = "[" + wf + "]";
				if(index != adGroupWifiList.size()) {
					cacheSelected += ",";
					selectedWifi += ",";
				}
			}
		}
		cacheSelected += "]";
		
		/**
		 * 找到所有的地域定向,排期
		 */    
		Direct locationDirect = directService.findByadGroupId(adGroup.getId(), 1);
		String areas = ""; 
		if(null != locationDirect) {
			areas = locationDirect.getBackShow();
		}
		//批量查询
		List<Direct> directs = directService.findByBatch(id);				
		Long campaignId = adGroup.getCampaignId();
		model.addAttribute("campaignId", campaignId);			
		if(directs!=null){
			for(Direct tmpDirect : directs ) {
				if (tmpDirect.getDirectType() == DirectType.locateType) {
					model.addAttribute("locate", tmpDirect.getBackShow());
				}else if(tmpDirect.getDirectType() == DirectType.timeType) {
					model.addAttribute("time", tmpDirect.getBackShow());
				}
			}
		}	
	
		model.addAttribute("placeList",placeList);
		model.addAttribute("areas", areas);
		model.addAttribute("selectedwifi", selectedWifi);
		model.addAttribute("cacheSelected", cacheSelected);
		model.addAttribute("activeTime", activeTime);
		model.addAttribute("place",place);
		model.addAttribute("adGroup", adGroup);
		model.addAttribute("adGroupPlaceList",adGroupPlaceList);
		model.addAllAttributes(paramMap);
		return page("edit");
	}
	
	/**
	 * 日志的列表显示的，需要传递一个投放id，变量名为adGroupId
	 * @param model
	 * @param paramMap
	 * @param page
	 * @return
	 */
	@RequestMapping("/update")
	public String update(Model model,
			@RequestParam HashMap<String, Object> paramMap,
			@RequestParam(defaultValue = "1") int page) {
		// 查询总行数
		paramMap.put("tableName", "t_adgroup");
		paramMap.put("recordId", Long.parseLong(String.valueOf(paramMap.get("adGroupId"))));
		int totalRow = logService.countByParams(paramMap,"AdGroup");
	
		Pager pager = new Pager();
		pager.setPage(page);
		pager.setTotalRow(totalRow);		
		List<Log> logList = logService.findByParams(paramMap, pager,"AdGroup");
		model.addAllAttributes(paramMap);
		model.addAttribute("pager", pager);
		model.addAttribute("logList", logList);
		return page("update");
	}
	
	
	
	
	/**
	 * 
	 * @param model
	 * @param adGroup
	 * @param place
	 * @param orderId
	 * @param zoneIdString  这个参数是用来做广告位id与对应的投放id插入
	 * @param campaignId
	 * @param paramMap   这个map里面需要添加一个已选择的时间段,变量名为sdayParting，格式是一个josn 
	 * 注意：这里的sdayParting 需要传递的变量和以前的一样就行
	 * @return
	 */
	@RequestMapping("/save")
	public String save(HttpServletRequest request, Model model,@ModelAttribute("form") AdGroup adGroup
			,@RequestParam String place
			,@RequestParam Long orderId
			,@RequestParam Long campaignId
			,@RequestParam String areas
			,@RequestParam Map<String, Object> paramMap) {
		adGroup.setAdvertiserId(Long.parseLong(String.valueOf(paramMap.get("advertiserId"))));
		adGroup.setAgentId(Long.parseLong(String.valueOf(paramMap.get("agentId"))));
		adGroup.setCampaignId(campaignId);
		adGroup.setOrderId(orderId);
		adGroup.setStatus(1);
		
		/**
		 * 在这里做时间定向的功能处理
		 */
		//将前台转换的排期数据转换成需要存储的数据--选择的时间段，以及未选择时间段按照策略的曝光率
		SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
		
		//把投放日期进行转换
    	String activeTime = (String) paramMap.get("activeTime");
		String[] tmpDate = activeTime.split("to");
		String startDateFront = tmpDate[0].trim();
		String endDateFront = tmpDate[1].trim();			
		try {
			adGroup.setStartDate(sdf.parse(startDateFront));
		} catch (ParseException e2) {
			// TODO Auto-generated catch block
			e2.printStackTrace();
		}
		try {
			adGroup.setEndDate(sdf.parse(endDateFront));
		} catch (ParseException e2) {
			// TODO Auto-generated catch block
			e2.printStackTrace();
		}	
		
		//先获得策略的投放周期
		Date startDate = adGroup.getStartDate();
		Date endDate = adGroup.getEndDate();
		//获得前端传递过来的已选择时间段
		String sdayParting = (String)paramMap.get("sdayParting");
		//用来存储转换结果的JSONArray
		JSONArray result = new JSONArray();
		//用来存储传过来时间段信息集合
		List<DayParting> dayList = new ArrayList<DayParting>();    
		//用来存储没选的时间段信息
		List<DayParting> daySurplus = new ArrayList<DayParting>();
		//默认24个时间点
		String allHours = "0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23";
		
		  try {
			    //传过来已选择的时间JSONArray
				JSONArray jsonArray = new JSONArray(sdayParting);
				//当没选一个时间段时，默认从开始时间段到结束时间段都为默认曝光上限
				if(jsonArray.length() == 0){                           				
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(startDate));
					object.put("endDate", sdf.format(endDate));
					object.put("dehours",allHours);
					result.put(object);
				}
				
				for (int i = 0; i < jsonArray.length(); i++) {
					JSONObject object = jsonArray.getJSONObject(i);
					DayParting day = new DayParting();
					
					//如果传过来的dehours是-1或空或者是空字符串，表示全选
					if(null == object.get("dehours") || "-1".equals(String.valueOf(object.getString("dehours"))) ||
							"".equals(String.valueOf(object.getString("dehours")))) {
						day.setDehours(allHours);
					} else {
						day.setDehours(object.getString("dehours"));
					}
					
					try {
						day.setStartDate(sdf.parse(object.getString("startDate")));
						day.setEndDate(sdf.parse(object.getString("endDate")));
					} catch (ParseException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
					dayList.add(day);
				}
				
				//按照开始时间的先后顺序给dayList进行排序，排序后，比较相邻的2个时间段，能够得出未选择的时间段
				Collections.sort(dayList, new AdvertiserSortByDate());
				
				for(int i = 0; i < dayList.size(); i++){
					DayParting dayP = dayList.get(i);
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(dayP.getStartDate()));
					object.put("endDate", sdf.format(dayP.getEndDate()));
					//将已选择的时间段放入result中
					object.put("dehours",dayP.getDehours());
					result.put(object);
					
					//当只选择一个时间段时，无法对前后两段时间进行比较，需特殊处理
					if(dayList.size() == 1){
						//所选时间段在开始时间之后--在开始时间到所选时间段中间有空缺时间段
						if(dayP.getStartDate().getTime() > startDate.getTime()){                     
							DayParting dayS = new DayParting();
							dayS.setStartDate(startDate);
							//减一天
							dayS.setEndDate(new Date(dayP.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
						//所选时间段在开始时间之前--在结束时间到所选时间段中间有空缺时间段
						if(dayP.getEndDate().getTime() < endDate.getTime()){						
							DayParting dayS = new DayParting();
							//加一天
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));      
							dayS.setEndDate(endDate);
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
						break;
					}
					
					//排序后的第一条记录，与开始时间比较，得出在开始时间到第一条记录之间是否有空缺时间段
					if(i==0){
						//第一条记录的开始时间大于策略开始时间
						if(dayP.getStartDate().getTime() > startDate.getTime()){     
							DayParting dayS = new DayParting();
							dayS.setStartDate(startDate);
							dayS.setEndDate(new Date(dayP.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							//添加第一条记录开始时间到策略开始时间的空缺段到daySurplus中
							daySurplus.add(dayS);																
							//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
							DayParting nextDay = dayList.get(i + 1);								
							if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
								DayParting dayS2 = new DayParting();
								dayS2.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
								dayS2.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
								dayS2.setDehours(allHours);
								daySurplus.add(dayS2);
							}
						}else{
							//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
							DayParting nextDay = dayList.get(i + 1);							
							if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
								DayParting dayS = new DayParting();
								dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
								dayS.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
								dayS.setDehours(allHours);
								daySurplus.add(dayS);
							}
						}
					}else if(i == dayList.size() - 1){		
						//最后一条记录的结束时间小于策略结束时间，中间有空缺时间段
						if(dayP.getEndDate().getTime() < endDate.getTime()){
							DayParting dayS = new DayParting();
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
							dayS.setEndDate(endDate);
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
					} else{
						DayParting nextDay = dayList.get(i + 1);				//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
						if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
							DayParting dayS = new DayParting();
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
							dayS.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
					}
				}
				
				//将空缺时间段添加到result中
				for(int i = 0; i < daySurplus.size(); i++){						
					DayParting dayP = daySurplus.get(i);
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(dayP.getStartDate()));
					object.put("endDate", sdf.format(dayP.getEndDate()));
					object.put("dehours",dayP.getDehours());
					result.put(object);
				}
				
				//将已处理的时间段存储起来
				paramMap.put("dayParting", result.toString());					
			} catch (JSONException e) {
				// TODO Auto-generated catch block
				LOG.info("@@@@@@@@排期日期解析错误");
				e.printStackTrace();
			}
		    // 千次转换
		    if (adGroup.getMaxImpression() != null) {
		      adGroup.setMaxImpression(adGroup.getMaxImpression() * 1000);
		    }
		    if (adGroup.getDailyMaxImpression() != null) {
		      adGroup.setDailyMaxImpression(adGroup.getDailyMaxImpression() * 1000);
		    }
			
		    
	    if (adGroup.getId() == null) {	
	    	try {
	    		if (getLoginUser().getOperatorId()!=0) {
					adGroup.setOperatorId(getLoginUser().getOperatorId());
				}else{
					adGroup.setOperatorId(new Long(0));
				}
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
	    	
			adGroupService.save(adGroup, paramMap);
			/**
			 * 新增投放成功后同时会新增地域定向，时段定向,wifi定向以及下面的场景
			 * 所以这里的日志新增记录应该把这些都加进去
			 */
			/**
			 * 先做投放的新增记录
			 */
			Log log = new Log();
			//对应模块
			log.setModule("AdGroup");
			//对应表名
			log.setTableName("t_adgroup");
			//增加对应的投放id
			log.setRecordId(adGroup.getId());
			//对应操作类型
			log.setActionType("新增");
			//对应的操作
			log.setAction("新增了一个投放：" + adGroup.getAdGroupName());
			//下面这几个字段目前后端数据没有得到。所以仅作测试用！
			log.setActionTime("100");
			log.setAccountId(new Long(getLoginUser().getId()));
			log.setUserIp(Common.toIpAddr(request));
			log.setAccountName(getLoginUser().getAccountName());
			logService.add(log);
			
			Direct direct = null;
			/**
			 * 时段定向的新增记录
			 */
			//先得到排期的时间段
			direct = directService.findByadGroupId(adGroup.getId(), 2);
			
			//如果查找到的对象为空且它的排期段没有则说明并没有新增时段定向
			if(null != direct && !"[]".equals(direct.getBackShow())) {
				String dateString = direct.getBackShow();
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了时间的排期段：" + dateString);
				logService.add(log);
			}
			
			/**
			 * 地域定向的新增记录
			 */
			//先得到新增的地域定向的信息
			direct = directService.findByadGroupId(adGroup.getId(), 1);
			
			//如果查找到的对象为空则说明并没有新增地域定向
			if(null != direct) {
				//得到地域名称字符串
				String[] location = direct.getData().split("/");
				String[] location1 = location[1].split("\\|");
				String locationNameString = "地域名称有:";
				
				for(int i = 0; i < location1.length; i++) {
					Location l = locationService.findByLocationT(location1[i]);
					locationNameString = locationNameString + l.getCountry() + " " + l.getCn() + " " + l.getCnCity() + ", " ;
				}
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了：" + locationNameString);
				logService.add(log);
			}
			
			adGroupService.front2dbplace(place,adGroup);//place是场景place把选择的场景存放到相应的数据库中		
			/**
			 * 保存已选的wifi到数据库t_adgroup_wifi
			 */
			String selectedwifi = (String) paramMap.get("selectedwifi");
			if(selectedwifi != "") {
				wifiService.front2dbwifi(selectedwifi, adGroup.getId());//保存已选择的wifi
			}
			/**
			 * 场景的新增记录
			 */
			//这里判断一下就是为了知道是不是有场景字符串有就会插入表，如果没有就不会插入表中也就不会有新增记录
			if(null != place) {
				//场景名称字符串
				String placeNameString = "场景,它们有：";
				String[] strArr = place.split(",");
					for(int i = 0; i < strArr.length; i++) {
						//通过场景id得到场景的名称
						placeNameString = placeNameString + placeService.findById(Long.valueOf(strArr[i]).longValue()).getName() + ", " ;
					}
					
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了：" + placeNameString);
					
					logService.add(log);
				}
			
			/**
			 * wifi定向的新增记录
			 */
			//获得新增后的wifi热点信息
			List<Wifi> wifiListAfterAdd = wifiService.findAllAdgroupWifi(adGroup.getId());
			
			//判断新增后查找的wifi热点信息集合是不是空，如果不是空则说明新增了wifi热点，则添加wifi新增的日志
			if(0 != wifiListAfterAdd.size()) {
				//存储wifi定向的地点名称
				String wifiName = "";
				
				for (int i = 0; i < wifiListAfterAdd.size(); i++) {
					wifiName = wifiName + wifiListAfterAdd.get(i).getAddress() + ", ";
				}
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了wifi定向：" + wifiName);
				
				logService.add(log);
			}
			
			
		} else {	
			
			/**
			 * 编辑成功后如果编辑前的数据与编辑后的数据比较后发生了改变，那么要对投放信息,时段信息和地域定向信息和场景信息增加修改日志
			 * 那再编辑之前要先获得到这些信息，保存下，然后和编辑之后的信息做比较
			 */
			AdGroup formerAdGroup = adGroupService.findById(adGroup.getId());
			List<AdGroupPlace> formerAdGroupPlaceList = adGroupPlaceService.findAllByAdGroupId(adGroup.getId());
			Direct formerTimeTypeDirect = directService.findByadGroupId(adGroup.getId(), 2);
			Direct formerLocationTypeDirect = directService.findByadGroupId(adGroup.getId(), 1);
			//保存编辑前的wifi地点
			List<Wifi> formerWifiList = wifiService.findAllAdgroupWifi(adGroup.getId());
			
			adGroupService.edit(adGroup, paramMap);
			
			//得到编辑之后的AdGroup对象
			AdGroup presentAdGroup = adGroupService.findById(adGroup.getId());
			
			/**
			 * 编辑的日志信息
			 */
			Log log= new Log();
			//对应模块
			log.setModule("AdGroup");
			//对应的表名
			log.setTableName("t_adgroup");
			//对应投放id
			log.setRecordId(adGroup.getId());
			//操作类型
			log.setActionType("编辑");	
			//下面这几个字段目前后端数据没有得到。所以仅作测试用！
			log.setActionTime("100");
			log.setAccountId(new Long(getLoginUser().getId()));
			log.setUserIp(Common.toIpAddr(request));
			log.setAccountName(getLoginUser().getAccountName());
			
			//如果之前的有选择wifi删除之前保存的wifi以便编辑之后保存的wifi不冲突			
			if(formerWifiList != null) {
				wifiService.deleteWifi(adGroup.getId());
			}			
			/**
			 * 保存编辑之后已选wifi
			 */								
			String selectedwifi = (String) paramMap.get("selectedwifi");
			if(selectedwifi != "") {
				wifiService.front2dbwifi(selectedwifi, adGroup.getId());//保存已选择的wifi
			}
						
			/**
			 * wifi定向编辑的日志更改记录
			 * 如果新选定的wifi地点和编辑前的wifi地点一样则不用增加更改日志，否则添加更改日志
			 * 比较步骤：第一如果编辑前和编辑后wifi热点都为空的话，则说明没有发生改变
			 * 第二如果编辑前和编辑后的wifi热点一个为空一个不为空，则发生改变
			 * 第三如果都不为空则逐个进行比较看是否发生了改变
			 */
			
			List<Wifi> presentWifiList = wifiService.findAllAdgroupWifi(adGroup.getId());
			if((null != formerWifiList && null == presentWifiList) || (null == formerWifiList && null != presentWifiList)) {
				if(null != formerWifiList) {
					//保存wifi热点的名称
					String wifiName = "";
					
					for (int i = 0; i < formerWifiList.size(); i++) {
						wifiName = wifiName + formerWifiList.get(i).getAddress() + ", ";
					}

					//变更详情
					log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
							+ "以前的wifi热点有:" + wifiName + "编辑后的wifi热点为空");
					logService.add(log);
				}
				
				if(null != presentWifiList) {
					//保存wifi热点的名称
					String wifiName = "";
					
					for (int i = 0; i < presentWifiList.size(); i++) {
						wifiName = wifiName + presentWifiList.get(i).getAddress() + ", ";
					}
					
					//变更详情
					log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
							+ "以前的wifi热点为空: ,编辑后的wifi热点为" + wifiName);
					logService.add(log);
				}								
			}
			
			if(null != formerWifiList && null != presentWifiList) {
				//以前的wifi热点id数组
				long[] formerWifiId = new long[formerWifiList.size()];
				
				for(int i = 0; i < formerWifiList.size(); i++) {
					formerWifiId[i] = formerWifiList.get(i).getId();
				}
				Arrays.sort(formerWifiId);
				
				//编辑后的wifi热点 的id数组
				long[] presentWifiId = new long[presentWifiList.size()];
				
				for (int i = 0; i < presentWifiList.size(); i++) {
					presentWifiId[i] = presentWifiList.get(i).getId();
				}
				Arrays.sort(presentWifiId);
				
				//修改标志，默认为没有修改
				boolean wifiUpdatedMark = false;
				
				//比较步骤，先判断它们的长度是不是一样如果一样则逐个比较如果不一样则表示wifi热点有改变
				if(formerWifiId.length == presentWifiId.length) {
					for(int i = 0; i < formerWifiId.length; i++) {
						if(formerWifiId[i] != presentWifiId[i]) {
							wifiUpdatedMark = true;
							break;
						}
					}
					
				} else {
					wifiUpdatedMark = true;
				}
				
				//存储编辑前的wifi热点名称
				String formerWifiName = "";
				
				for(int i = 0; i < formerWifiList.size(); i++) {
					formerWifiName = formerWifiName + formerWifiList.get(i).getAddress() + ", ";
				}
				
				//存储编辑后的wifi热点的名称
				String presentWifiName = "";
				
				for(int i = 0; i < presentWifiList.size(); i++) {
					presentWifiName = presentWifiName + presentWifiList.get(i).getAddress() + ", ";
				}
				
				//变更详情
				log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
						+ "以前的wifi热点有：" + formerWifiName + "现在的wifi热点有：" + presentWifiName);
				logService.add(log);
				
			}
			
			
			//对修改前和之后的每一项进行比较，如果发现哪一个字段发生了修改就记录下来，并且让修改标志设为true，
			boolean updatedMark = false;
			boolean updatedMark1 = false;
			
			/**
			 * 对投放信息的修改日志的添加
			 */
				
				//存储修改信息
				String updatedString = "对原有的投放" + formerAdGroup.getAdGroupName() + "做了修改了：";
				//投放名称的比较
				if(!(formerAdGroup.getAdGroupName().equals(presentAdGroup.getAdGroupName()))) {
					updatedString = updatedString + "投放名称" + " " + formerAdGroup.getAdGroupName() + "-->" + presentAdGroup.getAdGroupName() + ", ";
					updatedMark1 = true;
				}
				
				//活动周期的比较
				if(!(formerAdGroup.getStartDate().equals(presentAdGroup.getStartDate()) && formerAdGroup.getEndDate().equals(presentAdGroup.getEndDate()))) {
					updatedString = updatedString + "投放周期" + " " + formerAdGroup.getStartDate() + 
							"--" + formerAdGroup.getEndDate() + "-->" + presentAdGroup.getStartDate() + "--" + presentAdGroup.getEndDate() + ", ";
					updatedMark = true;
				}
				
				//总预算的比较
				if(!(formerAdGroup.getTotalBudget().equals(presentAdGroup.getTotalBudget()))) {
					updatedString = updatedString + "投放总预算" + " " + formerAdGroup.getTotalBudget() + "-->" + presentAdGroup.getTotalBudget() + ", ";
					updatedMark = true;
				}
							
				//单价的比较
				if(!(formerAdGroup.getPrice().equals(presentAdGroup.getPrice()))) {
					updatedString = updatedString + "单价" + " " + formerAdGroup.getPrice() + "-->" + presentAdGroup.getPrice() + ", ";
					updatedMark = true;
				}
				
				//每日预算的比较
				if(!(formerAdGroup.getDailyBudget().equals(presentAdGroup.getDailyBudget()))) {
					updatedString = updatedString + "每日预算" + " " + formerAdGroup.getDailyBudget() + "-->" + presentAdGroup.getDailyBudget() + ", ";
					updatedMark = true;
				}
				
				//曝光总上限的比较
				if(!(formerAdGroup.getMaxImpression().equals(presentAdGroup.getMaxImpression()))) {
					updatedString = updatedString + "曝光总上限" + " " + formerAdGroup.getMaxImpression() + "-->" + presentAdGroup.getMaxImpression() + ", ";
					updatedMark = true;
				}
				
				//点击总上限
				if(!(formerAdGroup.getMaxClick().equals(presentAdGroup.getMaxClick()))) {
					updatedString = updatedString + "点击总上限" + " " + formerAdGroup.getMaxClick() + "-->" + presentAdGroup.getMaxClick() + ", ";
					updatedMark = true;
				}
				
				//转化总上限
				if(!(formerAdGroup.getMaxConversion().equals(presentAdGroup.getMaxConversion()))) {
					updatedString = updatedString + "转化总上限" + " " + formerAdGroup.getMaxConversion() + "-->" + presentAdGroup.getMaxClick() + ", ";
					updatedMark = true;
				}
				
				//每日曝光上限的比较
				if(!(formerAdGroup.getDailyMaxImpression().equals(presentAdGroup.getDailyMaxImpression()))) {
					updatedString = updatedString + "每日曝光上限" + " " + formerAdGroup.getDailyMaxImpression() + "-->" + presentAdGroup.getDailyMaxImpression() + ", ";
					updatedMark = true;
				}
				
				//每日点击上限
				if(!(formerAdGroup.getDailyMaxClick().equals(presentAdGroup.getDailyMaxClick()))) {
					updatedString = updatedString + "每日点击上限" + " " + formerAdGroup.getDailyMaxClick() + "-->" + presentAdGroup.getDailyMaxClick() + ", ";
					updatedMark = true;
				}
				
				//每日转化上限
				if(!(formerAdGroup.getDailyMaxConversion().equals(presentAdGroup.getDailyMaxConversion()))) {
					updatedString = updatedString + "每日转化上限" + " " + formerAdGroup.getDailyMaxConversion() + "-->" + presentAdGroup.getDailyMaxConversion() + ", ";
					updatedMark = true;
				}
				
				//单人点击频次
				if(!(formerAdGroup.getPerClickType().equals(presentAdGroup.getPerClickType()) && formerAdGroup.getPerClick().equals(presentAdGroup.getPerClick()))) {
					/**
					 * 单人点击频次类型1-代表每天，2-代表投放周期
					 */
					//存储单人点击频次类型
					String formerPerClickType = "";
					String presentPerClickType = "";
					if(formerAdGroup.getPerClickType() == 1) {
						formerPerClickType = "每天";
					} else {
						formerPerClickType = "投放周期";
					}
					
					if(presentAdGroup.getPerClickType() == 1) {
						presentPerClickType = "每天";
					} else {
						presentPerClickType = "投放周期";
					}
					updatedString = updatedString + "单人点击频次" + " " + formerPerClickType + " " + formerAdGroup.getPerClick() + "-->"
									+ presentPerClickType + " " + presentAdGroup.getPerClick() + ", ";
					updatedMark = true;
				}
				
				//点击找回的比较
				if(!(formerAdGroup.getRetarget().equals(presentAdGroup.getRetarget()))) {
					updatedString = updatedString + "点击找回" + " " + formerAdGroup.getRetarget() + "-->" + presentAdGroup.getRetarget() + ", ";
					updatedMark = true;
				}
				
				//访客投放期的比较
				if(!(formerAdGroup.getPeriod().equals(presentAdGroup.getPeriod()))) {
					updatedString = updatedString + "访客投放期" + " " + formerAdGroup.getPeriod() + "-->" + presentAdGroup.getPeriod() + ", ";
					updatedMark = true;
				}
				
				//是否全站访客的比较
				if(!(formerAdGroup.getSite().equals(presentAdGroup.getSite()))) {
					updatedString = updatedString + "是否全站访客" + " " + formerAdGroup.getSite() + "-->" + presentAdGroup.getSite() + ", ";
					updatedMark = true;
				}
				
				
				//单人曝光频次
				if(!(formerAdGroup.getPerImpressionType().equals(presentAdGroup.getPerImpressionType()) && formerAdGroup.getPerImpression().equals(presentAdGroup.getPerImpression()))) {
					/**
					 * 单人曝光频次类型1-代表每天，2-代表投放周期
					 */
					//存储单人点击频次类型
					String formerPerImpressionType = "";
					String presentPerImpressionType = "";
					if(formerAdGroup.getPerImpressionType() == 1) {
						formerPerImpressionType = "每天";
					} else {
						formerPerImpressionType = "投放周期";
					}
					
					if(presentAdGroup.getPerImpressionType() == 1) {
						presentPerImpressionType = "每天";
					} else {
						presentPerImpressionType = "投放周期";
					}
					
					updatedString = updatedString + "单人曝光频次" + " " + formerPerImpressionType + " " + formerAdGroup.getPerImpression() + "-->"
							+ presentPerImpressionType + " " + presentAdGroup.getPerImpression() + ", ";
					updatedMark = true;
				}
				
				//位置的比较,因为位置没选的时候默认值是为"0"，所以判断一下位置如果编辑前后都等于0的话，则没有改变
				if(!("0".equals(formerAdGroup.getPosition()) && "0".equals(presentAdGroup.getPosition()))) {
					//当两个字符串不同时为0时，再判断下如果编辑前字符串为0编辑后字符串不0空或者编辑后为0编辑前不为0则发生了改变，否则再逐个比较
					if(("0".equals(formerAdGroup.getPosition()) && !("0".equals(presentAdGroup.getPosition()))) || 
							!("0".equals(formerAdGroup.getPosition())) && "0".equals(presentAdGroup.getPosition())) {
						
						//得到位置的名称
						String formerPositionString = "编辑前的位置: ";
						String presentPositionString = "编辑后的位置:";
						
						if(!("0".equals(formerAdGroup.getPosition()))) {
							String[] formerPosition = formerAdGroup.getPosition().split(",");
							
							for(int i = 0; i < formerPosition.length; i++) {
								if("1".equals(formerPosition[i])) {
									formerPositionString = formerPositionString + "认证" + ", ";
								} else if("2".equals(formerPosition[i])) {
									formerPositionString = formerPositionString + "跳转" + ", ";
								} else {
									formerPositionString = formerPositionString + "上网过程" + ", ";
								}
							}
						}
						
						if(!("0".equals(presentAdGroup.getPosition()))) {
							String[] presentPosition = presentAdGroup.getPosition().split(",");
							
							for(int i = 0; i < presentPosition.length; i++) {
								if("1".equals(presentPosition[i])) {
									presentPositionString = presentPositionString + "认证" + ", ";
								} else if("2".equals(presentPosition[i])) {
									presentPositionString = presentPositionString + "跳转" + ", ";
								} else {
									presentPositionString = presentPositionString + "上网过程" + ", ";
								}
							}
						}
						
						updatedString = updatedString + "位置" + " " + formerPositionString + "-->" +
								presentPositionString + ", ";
						updatedMark = true;
					} else{
						String[] formerPositionStringArray = formerAdGroup.getPosition().split(",");
						String[] presentPositionStringArray = presentAdGroup.getPosition().split(",");
						
						int[] formerPosition = new int[formerPositionStringArray.length];
						int[] presentPosition = new int[presentPositionStringArray.length];
						
						//进行排序下
						Arrays.sort(formerPosition);
						Arrays.sort(presentPosition);
						
						//逐个比较时先比较一下两个数组大小如果数组大小不同则发生改变
						if(!(formerPosition.length == presentPosition.length)) {
							
							for(int i = 0; i < formerPosition.length; i++) {
								if(formerPosition[i] != presentPosition[i]) {
									
									//得到位置的名称
									String formerPositionString = "编辑前的位置有: ";
									String presentPositionString = "编辑后的位置有:";
									
									for(int j = 0; j < formerPositionStringArray.length; j++) {
										if("1".equals(formerPositionStringArray[j])) {
											formerPositionString = formerPositionString + "认证" + ", ";
										} else if("2".equals(formerPositionStringArray[j])) {
											formerPositionString = formerPositionString + "跳转" + ", ";
										} else {
											formerPositionString = formerPositionString + "上网过程" + ", ";
										}
									}
									
									for(int j = 0; j < presentPositionStringArray.length; j++) {
										if("1".equals(presentPositionStringArray[j])) {
											presentPositionString = presentPositionString + "认证" + ", ";
										} else if("2".equals(presentPositionStringArray[j])) {
											presentPositionString = presentPositionString + "跳转" + ", ";
										} else {
											presentPositionString = presentPositionString + "上网过程" + ", ";
										}
									}
									
									
									updatedString = updatedString + "位置" + " " + formerPositionString + "-->" +
											presentPositionString + ", ";
									updatedMark = true;
								}
							}
						}
					}
				}
				
				//变更详情
				log.setAction(updatedString);
				
//				updatedMark1 = 
				//如果编辑前后投放信息进行修改了（除投放名称name之外），就把投放以及投放下级的supdated进行修改
				if(updatedMark) {
					adGroupService.updatedAdgroupSupdated(adGroup.getId());
				}
				
				//判断是否编辑前后的投放信息如果真的改变则添加修改日志
				if(updatedMark || updatedMark1) {
					logService.add(log); 
				}
				
			
				/**
				 * 对时段定向修改记录的更新
				 */
				//重置修改标志
				updatedMark = false;
				
				/**
				 * 如果以前的时段定向和现在的时段定向都是为空的话则说明没有发生变化
				 * 如果以前的时段定向和现在的时段定向一个为空一个不为空则说明发生了变化
				 * 如果都不为空则逐个比较再看是否发生变化
				 * 注：dayList如果大小为0则表示传递过来的时间段是空
				 */
				if((null == formerTimeTypeDirect && 0 != dayList.size()) || (null != formerTimeTypeDirect && 0 == dayList.size())) {
					updatedMark = true;
				}
				
				if(null != formerTimeTypeDirect && 0 != dayList.size()) {
					List<DayParting> formerDayPartingList = new ArrayList<DayParting>();
					try {
						//以前已选择的时间JSONArray
						JSONArray formerJsonArray = new JSONArray(formerTimeTypeDirect.getBackShow());
						for (int i = 0; i < formerJsonArray.length(); i++) {
							JSONObject object = formerJsonArray.getJSONObject(i);
							DayParting day = new DayParting();
							day.setDehours(object.getString("dehours"));
							try {
								day.setStartDate(sdf.parse(object.getString("startDate")));
								day.setEndDate(sdf.parse(object.getString("endDate")));
							} catch (ParseException e) {
								// TODO Auto-generated catch block
								e.printStackTrace();
							}
							formerDayPartingList.add(day);
						}
						
						//按照开始时间的先后顺序给dayList进行排序，排序后，比较相邻的2个时间段，能够得出未选择的时间段
						Collections.sort(formerDayPartingList, new AdvertiserSortByDate());
						
						//编辑前后的时间段进行比较
						if(formerDayPartingList.size() == dayList.size()) {
							//一个一个进行比较
							for(int i = 0; i < dayList.size(); i++) {
								//开始时间的比较
								if(!(formerDayPartingList.get(i).getStartDate().equals(dayList.get(i).getStartDate()))) {
									updatedMark = true;
									break;
								}
								
								//结束的时间进行比较
								if((!formerDayPartingList.get(i).getEndDate().equals(dayList.get(i).getEndDate()))) {
									updatedMark = true;
									break;
								}
								
								//时间点的比较
								if(!(formerDayPartingList.get(i).getDehours().equals(dayList.get(i).getDehours()))) {
									updatedMark = true;
									break;
								}
								
							}
						} else {
							updatedMark = true;
						}
						
					} catch(Exception e) {
						e.printStackTrace();
					}
				}
				
				if(updatedMark) {
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对时间段进行了修改： 从" + formerTimeTypeDirect.getBackShow() + "-->" + directService.findByadGroupId(adGroup.getId(), 2).getBackShow());
					logService.add(log);
				}
				
				/**
				 * 对地域定向的修改的日志更新
				 */
				//重置修改标志
				updatedMark = false;
				
				/**
				 * 如果以前的地域定向和现在的地域定向都是为空的话则说明没有发生变化
				 * 如果以前的地域定向和现在的地域定向一个为空一个不为空则说明发生了变化
				 * 如果都不为空则逐个比较再看是否发生变化
				 */
				//编辑完之后，得到编辑之后的地域定向信息
				Direct presentDirectOfLocationType = directService.findByadGroupId(adGroup.getId(), 1);
				
				String formerAreasNameString = "";
				String presentAreasNameString = "";
				
				if((null != formerLocationTypeDirect && null == presentDirectOfLocationType) || (null == formerLocationTypeDirect && null != presentDirectOfLocationType)) {
					/**
					 * 得到编辑前后的地域数组对应的名称字符串
					 */
					formerAreasNameString = "编辑前的地域：";
					presentAreasNameString = "编辑后的地域：";
					if(null != formerLocationTypeDirect) {
						String[] formerTargetData = formerLocationTypeDirect.getData().split("/");
						//编辑之前的地域数组
						String[] formerAreas = formerTargetData[1].split("\\|");
						
						for(int i = 0; i < formerAreas.length; i++) {
							Location l = locationService.findByLocationT(formerAreas[i]);
							formerAreasNameString = formerAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						
					}
					
					if(null != presentDirectOfLocationType) {
						String[] presentTargetData = (presentDirectOfLocationType.getData()).split("/");
						//得到编辑之后的地域数组
						String[] presentAreas = presentTargetData[1].split("\\|");
						
						for(int i = 0; i < presentAreas.length; i++) {
							Location l = locationService.findByLocationT(presentAreas[i]);
							presentAreasNameString = presentAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
					}
					
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对地域进行修改：" + formerAreasNameString + "-->" + presentAreasNameString);
					
					logService.add(log);
				}
				
				if(null != formerLocationTypeDirect && null != presentDirectOfLocationType) {
					String[] formerTargetData = formerLocationTypeDirect.getData().split("/");
					//编辑之前的地域数组
					String[] formerAreas = formerTargetData[1].split("\\|");
					String[] presentTargetData = (presentDirectOfLocationType.getData()).split("/");
					//得到编辑之后的地域数组
					String[] presentAreas = presentTargetData[1].split("\\|");
					
					//对两个地域数组进行比较
					if(formerAreas.length == presentAreas.length) {
						//先进行排序再一个一个比较
						Arrays.sort(formerAreas);
						Arrays.sort(presentAreas);
						
						for(int i = 0; i< formerAreas.length; i++) {
							if(!(formerAreas[i].equals(presentAreas[i]))) {
								updatedMark = true;
								break;
							}
						}
					} else {
						updatedMark = true;
					}
					
					if(updatedMark) {
						
						/**
						 * 得到编辑前后的地域数组对应的名称字符串
						 */
						formerAreasNameString = "编辑前的地域有：";
						presentAreasNameString = "编辑后的地域有：";
						
						for(int i = 0; i < formerAreas.length; i++) {
							Location l = locationService.findByLocationT(formerAreas[i]);
							formerAreasNameString = formerAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						

						for(int i = 0; i < presentAreas.length; i++) {
							Location l = locationService.findByLocationT(presentAreas[i]);
							presentAreasNameString = presentAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						
						//对应的操作
						log.setAction("在投放：" + adGroup.getAdGroupName() + "中对地域进行修改：" + formerAreasNameString + "-->" + presentAreasNameString);
						
						logService.add(log);
				}
				
					
				}
				
			
			
			/**
			 * 对于场景的修改的日志的增加
			 */
			//重置修改标志
			updatedMark = false;
			String formerPlaceNameString = "";
			String updatedPlaceNameString = "";
			/**
			 * 如果以前的场景和现在的场景都是为空的话则说明没有发生变化
			 * 如果以前的场景和现在的场景一个为空一个不为空则说明发生了变化
			 * 如果都不为空则逐个比较再看是否发生变化
			 */
			if((0 != formerAdGroupPlaceList.size() && null == place) || (0 == formerAdGroupPlaceList.size() && null != place)) {
				updatedMark = true;
				
				if(0 != formerAdGroupPlaceList.size()) {
					formerPlaceNameString = "编辑之前的场景：";
					
					for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
						formerPlaceNameString = formerPlaceNameString + placeService.findById(formerAdGroupPlaceList.get(i).getPlaceId()).getName() + ", ";
					}
				}
				
				if(null != place) {
					updatedPlaceNameString = "编辑之后的场景有：";
					String[] placeIdString = place.split(",");
					Long[] placeId = new Long[placeIdString.length];
					
					//得到现在想编辑的场景id
					for(int i = 0; i < placeIdString.length; i++) {
						placeId[i] = Long.parseLong(placeIdString[i]);
					}
					
					for(int i = 0; i < placeId.length; i++) {
						//得到对应的广告位名称
						updatedPlaceNameString = updatedPlaceNameString + placeService.findById(placeId[i]).getName() + ", ";
					}
				}
				
			}
			
			if(0 != formerAdGroupPlaceList.size() && null != place) {
				String[] placeIdString = place.split(",");
				Long[] placeId = new Long[placeIdString.length];
				Long[] formerPlaceId = new Long[formerAdGroupPlaceList.size()];
				
				//得到编辑前的场景id，并且进行排序
				for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
					formerPlaceId[i] = formerAdGroupPlaceList.get(i).getPlaceId();
				}
				Arrays.sort(formerPlaceId);
				
				//得到现在想编辑的场景id，并且进行排序
				for(int i = 0; i < placeIdString.length; i++) {
					placeId[i] = Long.parseLong(placeIdString[i]);
				}
				Arrays.sort(placeId);
				
				
				//对比一下编辑前后的广告位id是否发生变化如果发生变化就去更新表并且新增修改记录
				//首先对比一下广告位的id数量是不是一样多如果发生变化就说明广告位有了变化否则再一条一条的对比
				if(placeId.length == formerPlaceId.length) {
					for(int i = 0; i < placeId.length; i++) {
						if(placeId[i] != formerPlaceId[i]) {
							updatedMark = true;
							break;
						}
					}
				} else {
					updatedMark = true;
				}
				
				//存储场景名称
				formerPlaceNameString = "编辑之前的场景有：";
				updatedPlaceNameString = "编辑之后的场景有：";
				
				for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
					formerPlaceNameString = formerPlaceNameString + placeService.findById(formerAdGroupPlaceList.get(i).getPlaceId()).getName() + ", ";
				}
				
				for(int i = 0; i < placeId.length; i++) {
					//得到对应的广告位名称
					updatedPlaceNameString = updatedPlaceNameString + placeService.findById(placeId[i]).getName() + ", ";
				}
				
				
			}
			
			
			
			if(updatedMark) {
				adGroupPlaceService.delete(adGroup.getId());//删除之前保存的场景
				adGroupService.front2dbplace(place,adGroup);//保存编辑之后的场景
				//场景进行了改变，将表t_adgroup_place里面的supdated进行更新
//				adGroupPlaceService.updatedPlaceSupdated(adGroup.getId());
				
				
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对场景进行修改：" + formerPlaceNameString + "-->" + updatedPlaceNameString);
					
					logService.add(log);
			}
		}
	    
		model.addAttribute("campaignId", adGroup.getCampaignId());
		return redirect(page("list"));
	}
	
	@RequestMapping("/getLocations")
	public String getLocations(Model model) {
		ArrayList<Location> list = (ArrayList) locationService.findAll("中国");
		LinkedHashMap<String, ArrayList<Location>> hashMap = new LinkedHashMap<String, ArrayList<Location>>();
		// 用来保存省份和对应的编码
		LinkedHashMap<String, String> hashCode = new LinkedHashMap<String, String>();
		ArrayList<Location> tmpList;
		for (Location locate : list) {
			if (hashMap.containsKey(locate.getCn())) {
				hashMap.get(locate.getCn()).add(locate);
			} else {
				tmpList = new ArrayList<Location>();
				tmpList.add(locate);
				hashMap.put(locate.getCn(), tmpList);
				hashCode.put(locate.getCn(),
						locate.getLocation1() + locate.getLocation2());
			}
		}
		model.addAttribute("hashMap", hashMap);
		model.addAttribute("hashCode", hashCode);
		return page("locations");
	}
	
	/**
	 * 投放管理导出excel功能的实现
	 * 前端必须要传递三个参数分别为广告主id(advertiserId),订单id(orderId),活动id(campaginId)
	 *	默认的订单id传递过来的就是全部的订单，这时传过来的值为-1，活动和订单一样
	 * 注：当广告主传了一个-1值时说明该登录账号是一个广告主代理商账号，这时搜索的就是该代理商下的全部广告主的信息
	 * @param request
	 * @param response
	 * @param selectedStatus 选择的状态变量，默认的是全部，为空值
	 * @param paramMap
	 */
	@RequestMapping("/exportAdGroupExcel")
	public void exportOtherReportExcel(HttpServletRequest request,
			HttpServletResponse response,
			@RequestParam(defaultValue = "0") int selectedStatus,
			@RequestParam Map<String, Object> paramMap) {
		
		Long campaignId = null;
		Long orderId = null;
		Long advertiserId = null;
		/**
		 * 对传入的数据做处理
		 * 第一：如果传入的活动id值为空值或者空字符串或者是-1的话则表明这个活动id代表的是全部的活动，这时让它的值设为-1，并且加上一个活动标志它的值设为全部（它用在sql语句的判断上）
		 * 第二：如果传入的订单id值为空值或者空字符串或者是-1的话，这时不能够直接认为它是全部的订单，要对活动id进行判断一下，如果活动id是全部活动的话，那么这时就是全部的订单，订单
		 * id就设为-1并且加上一个订单标志值设为全部，否则订单id的值为通过活动id查找到的订单id值
		 * 第三：如果传入的广告主id值为空值或者空字符串或者是-1的话则，这时也不能够直接认为它是全部的广告主，要对订单id进行判断，如果订单id是全部订单的话，那么这是就是全部广告主
		 * 这时广告主id的值为-1，同时通过当前登录账号得到代理商的id，使查出来的信息是该登录账号下的全部广告主，否则广告主id的值为通过订单id查找到的广告主id值
		 * 
		 */
		if(null == paramMap.get("campaignId") || "".equals(paramMap.get("campaignId")) 
				|| "-1".equals(paramMap.get("campaignId"))) {
			paramMap.put("campaignMark", "全部");
			paramMap.put("campaignId", -1l);
			paramMap.put("selectedcampaignName", "全部活动");
		} else {
			//将前端传过来的campaignId变成Long型
			campaignId = Long.parseLong(String.valueOf(paramMap.get("campaignId")));
			paramMap.put("campaignId", campaignId);
			Campaign campaignObj = campaignService.findById(Long.valueOf(paramMap.get("campaignId").toString()));
			paramMap.put("selectedcampaignName", campaignObj.getName());
		}
		
		
		if(null == paramMap.get("orderId") || "".equals(paramMap.get("orderId")) 
				|| "-1".equals(paramMap.get("orderId"))) {
			
			if(campaignId == null) {
				paramMap.put("orderMark", "全部");
				paramMap.put("orderId", -1l);
				paramMap.put("selectedorderName", "全部订单");
			} else {
				Campaign campaign = campaignService.findById(campaignId);
				orderId = campaign.getOrderId();
				paramMap.put("orderId", orderId);
				String orderName = orderService.selectOrderNameById(orderId);
				paramMap.put("selectedorderName", orderName);
			}
			
		} else {
			
			//将前端传过来的orderId变成Long型
			orderId = Long.parseLong(String.valueOf(paramMap.get("orderId")));
			paramMap.put("orderId", orderId);
			String orderName = orderService.selectOrderNameById(orderId);
			paramMap.put("selectedorderName", orderName);
		}
		
		
		if(null == paramMap.get("advertiserId") || "".equals(paramMap.get("advertiserId")) 
				|| "-1".equals(paramMap.get("advertiserId"))) {
			
			if(orderId == null) {
				paramMap.put("agentId", getLoginUser().getAgentId());
				paramMap.put("advertiserId", -1l);
				paramMap.put("selectedadvertiserName", "全部广告主");
			} else {
				paramMap.put("agentId", null);
				Order order = orderService.findById(orderId);
				advertiserId = order.getAdvertiserId();
				paramMap.put("advertiserId", advertiserId);
				String advertiserName = advertiserService.selectAdvertiserNameById(advertiserId);
				paramMap.put("selectedadvertiserName", advertiserName);
			}
			
		} else {
			paramMap.put("agentId", null);
			//将前端传过来的advertiserId变成Long型
			advertiserId = Long.parseLong(String.valueOf(paramMap.get("advertiserId")));
			paramMap.put("advertiserId", advertiserId);
			String advertiserName = advertiserService.selectAdvertiserNameById(advertiserId);
			paramMap.put("selectedadvertiserName", advertiserName);
		}
		
		// 这里的搜索只是对投放名称进行搜索
		String adGroupName = null;
		if (null != paramMap.get("searchValue")) {
			try {
				adGroupName = new String((String.valueOf(paramMap
						.get("searchValue"))).getBytes("ISO-8859-1"), "UTF-8");
			} catch (UnsupportedEncodingException e) {
				e.printStackTrace();
			}
			adGroupName = SqlHelper.doLike(adGroupName);
		}

		paramMap.put("adGroupName", adGroupName);
		
		/**
		 * 根据状态来进行查询
		 * 设置0-表示全部，1-表示投放中，2-表示未投放，3-投放结束，4-停用
		 * 没选默认时status应该是为0
		 * 实现思想：这里如果是选择的是0（全部的）话那就不用加什么条件，那如果选择的是1的话，就在paramMap上加上一个键值对
		 * key的名字就设置为selectedStatus1，那这样就可以在mapper文件中对key值进行判断，然后增加相应的条件，下面的就以此
		 * 类推
		 */
		switch(selectedStatus) {
		//当所选择的状态是0表示全部时就不用添加什么条件了，只要把所有的都找出来就行
		case 0:break;
		//当选择的状态是1时表示的是投放中，那这时找的就应该是当前时间处于投放开始时间和投放结束时间之间并且应该是开启的状态
		case 1:paramMap.put("selectedStatus1", selectedStatus);break;
		//当选择的状态是2时表示的是未投放，那这时就应该是投放开始时间要大于当前时间
		case 2:paramMap.put("selectedStatus2", selectedStatus);break;
		//当选择的状态是3时表示的是投放结束，那这时就应该是投放的结束时间小于当前时间
		case 3:paramMap.put("selectedStatus3", selectedStatus);break;
		//当选择的状态是4时表示的是停用，那这时只要在写数据库查询时加上它的投放表中的status字段等于1就行了
		case 4:paramMap.put("selectedStatus4", selectedStatus);break;
		}
		
		List<AdGroup> adGroupList = adGroupService.findByParams(paramMap);
		
		response.reset();
		// Content-Type:application/vnd.ms-excel;charset=utf8或者text/xml;charset=utf8
		response.setContentType("application/vnd.ms-excel;charset=utf8");
		// 设置excel文件名称
		SimpleDateFormat df2 = new SimpleDateFormat("yyyyMMddHHmmss");
		String fileName = "report" + df2.format(new Date());
		response.setHeader("Content-Disposition", "attachment;filename="
				+ fileName + ".xls");
		// 需要对excel的列和行的总数进行指定
		int column = 5;
		paramMap.put("dataList", adGroupList);
		paramMap.put("dataSize", adGroupList.size());
		paramMap.put("column", column);
		String excelTemplate = templateProcessor.processTemplate(
				"excel/adGroup.ftl", paramMap);
		try {
			PrintWriter out = response.getWriter();
			out.write(excelTemplate);
			out.flush();
			out.close();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		
	}
	
	
	/**
	 * 投放信息修改记录的导出excel功能
	 * 需要传递一个投放id，变量名为adGroupId
	 * @param request
	 * @param response
	 * @param paramMap
	 */
	@RequestMapping("/exportAmendmentLogExcel")
	public void exportAmendmentLogExcel(HttpServletRequest request,
			HttpServletResponse response,
			@RequestParam Map<String, Object> paramMap) {
		
		paramMap.put("tableName", "t_adgroup");
		paramMap.put("recordId", Long.parseLong(String.valueOf(paramMap.get("adGroupId"))));
		List<Log> logList = logService.findDeliverEffectAnalysis(paramMap);
		
		response.reset();
		// Content-Type:application/vnd.ms-excel;charset=utf8或者text/xml;charset=utf8
		response.setContentType("application/vnd.ms-excel;charset=utf8");
		// 设置excel文件名称
		SimpleDateFormat df2 = new SimpleDateFormat("yyyyMMddHHmmss");
		String fileName = "report" + df2.format(new Date());
		response.setHeader("Content-Disposition", "attachment;filename="
				+ fileName + ".xls");
		// 需要对excel的列和行的总数进行指定
		int column = 5;
		paramMap.put("dataList", logList);
		paramMap.put("dataSize", logList.size());
		paramMap.put("column", column);
		paramMap.put("name", "投放信息修改记录");
		String excelTemplate = templateProcessor.processTemplate(
				"excel/amendmentLog.ftl", paramMap);
		try {
			PrintWriter out = response.getWriter();
			out.write(excelTemplate);
			out.flush();
			out.close();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	/**
	 * 媒体自投
	 * @param model
	 * @param campaignId
	 * @return
	 */
	@RequestMapping("/createbyoperator")
	public String createByOperator(Model model, @RequestParam Long campaignId) {
		Account account = getLoginUser();
		Long operatorId = account.getOperatorId();
		
		Map<String,Object> condition = new HashMap<String,Object>();
		condition.put("operatorId", operatorId);
		//condition.put("position", position);
		List<Zone> zoneList = zoneService.queryZoneByCondition(condition);//获取广告位
		CampaignPojo campaign = campaignService.findCampaignById(campaignId);
		//找到所有的场景，并且显示出来
		List<Place> placeList = placeService.findAll();
		model.addAttribute("campaignId", campaignId);
		model.addAttribute("advertiserId", campaign.getAdvertiserId());	
		model.addAttribute("orderId", campaign.getOrderId());
		model.addAttribute("agentId", campaign.getAgentId());
		model.addAttribute("budget", campaign.getOrderBudget());
		model.addAttribute("placeList",placeList);
		model.addAttribute("zoneList",zoneList);
		return page("createbyoperator");
	}
	
	/**
	 *  
	 * @param position 根据广告位的位置选择广告位
	 * @return
	 */
	@RequestMapping("/zonelist")
	public List<Zone> queryZoneByPosition(Integer position){
		Map<String,Object>condition = new HashMap<String,Object>();
		condition.put("position", position);
		condition.put("operatorId", getLoginUser().getOperatorId());
		return this.zoneService.queryZoneByCondition(condition);
	}
	
	/**
	 * 查询媒体自定义的分组
	 * @return
	 */
	@RequestMapping("/wifiGroupInfoList")
	public List<WifiGroupInfo> queryWifiGroupInfoByCondition(){
		Map<String,Object>condition = new HashMap<String,Object>();
		condition.put("operatorId",getLoginUser().getOperatorId());
		return this.wifiGroupInfoService.queryWifiGroupInfoByCondition(condition);
	}
	
	/**
	 * 查询数据所有场景
	 * @return
	 */
	@RequestMapping("/palceList")
	public List<Place> queryPlaceAll(){
		return this.placeService.findAll();
	}
	 
	/**
	 * 媒体自投保存
	 * @param request
	 * @param model
	 * @param adGroup
	 * @param place
	 * @param orderId
	 * @param campaignId
	 * @param areas
	 * @param paramMap
	 * @return
	 */
	@RequestMapping("/saveAdGroup")
	public String saveAdGroup(HttpServletRequest request, Model model,@ModelAttribute("form") AdGroup adGroup
			,@RequestParam String place
			,@RequestParam String areas
			,@RequestParam Map<String, Object> paramMap) {
		adGroup.setAdvertiserId(Long.parseLong(String.valueOf(paramMap.get("advertiserId"))));
		adGroup.setAgentId(Long.parseLong(String.valueOf(paramMap.get("agentId"))));
		adGroup.setCampaignId(Long.parseLong(String.valueOf(paramMap.get("campaignId"))));
		adGroup.setOrderId(Long.parseLong(String.valueOf(paramMap.get("orderId"))));
		adGroup.setStatus(1);
		
		/**
		 * 在这里做时间定向的功能处理
		 */
		//将前台转换的排期数据转换成需要存储的数据--选择的时间段，以及未选择时间段按照策略的曝光率
		SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
		
		//把投放日期进行转换
    	String activeTime = (String) paramMap.get("activeTime");
		String[] tmpDate = activeTime.split("to");
		String startDateFront = tmpDate[0].trim();
		String endDateFront = tmpDate[1].trim();			
		try {
			adGroup.setStartDate(sdf.parse(startDateFront));
		} catch (ParseException e2) {
			// TODO Auto-generated catch block
			e2.printStackTrace();
		}
		try {
			adGroup.setEndDate(sdf.parse(endDateFront));
		} catch (ParseException e2) {
			// TODO Auto-generated catch block
			e2.printStackTrace();
		}	
		
		//先获得策略的投放周期
		Date startDate = adGroup.getStartDate();
		Date endDate = adGroup.getEndDate();
		//获得前端传递过来的已选择时间段
		String sdayParting = (String)paramMap.get("sdayParting");
		//用来存储转换结果的JSONArray
		JSONArray result = new JSONArray();
		//用来存储传过来时间段信息集合
		List<DayParting> dayList = new ArrayList<DayParting>();    
		//用来存储没选的时间段信息
		List<DayParting> daySurplus = new ArrayList<DayParting>();
		//默认24个时间点
		String allHours = "0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23";
		
		  try {
			    //传过来已选择的时间JSONArray
				JSONArray jsonArray = new JSONArray(sdayParting);
				//当没选一个时间段时，默认从开始时间段到结束时间段都为默认曝光上限
				if(jsonArray.length() == 0){                           				
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(startDate));
					object.put("endDate", sdf.format(endDate));
					object.put("dehours",allHours);
					result.put(object);
				}
				
				for (int i = 0; i < jsonArray.length(); i++) {
					JSONObject object = jsonArray.getJSONObject(i);
					DayParting day = new DayParting();
					
					//如果传过来的dehours是-1或空或者是空字符串，表示全选
					if(null == object.get("dehours") || "-1".equals(String.valueOf(object.getString("dehours"))) ||
							"".equals(String.valueOf(object.getString("dehours")))) {
						day.setDehours(allHours);
					} else {
						day.setDehours(object.getString("dehours"));
					}
					
					try {
						day.setStartDate(sdf.parse(object.getString("startDate")));
						day.setEndDate(sdf.parse(object.getString("endDate")));
					} catch (ParseException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
					dayList.add(day);
				}
				
				//按照开始时间的先后顺序给dayList进行排序，排序后，比较相邻的2个时间段，能够得出未选择的时间段
				Collections.sort(dayList, new AdvertiserSortByDate());
				
				for(int i = 0; i < dayList.size(); i++){
					DayParting dayP = dayList.get(i);
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(dayP.getStartDate()));
					object.put("endDate", sdf.format(dayP.getEndDate()));
					//将已选择的时间段放入result中
					object.put("dehours",dayP.getDehours());
					result.put(object);
					
					//当只选择一个时间段时，无法对前后两段时间进行比较，需特殊处理
					if(dayList.size() == 1){
						//所选时间段在开始时间之后--在开始时间到所选时间段中间有空缺时间段
						if(dayP.getStartDate().getTime() > startDate.getTime()){                     
							DayParting dayS = new DayParting();
							dayS.setStartDate(startDate);
							//减一天
							dayS.setEndDate(new Date(dayP.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
						//所选时间段在开始时间之前--在结束时间到所选时间段中间有空缺时间段
						if(dayP.getEndDate().getTime() < endDate.getTime()){						
							DayParting dayS = new DayParting();
							//加一天
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));      
							dayS.setEndDate(endDate);
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
						break;
					}
					
					//排序后的第一条记录，与开始时间比较，得出在开始时间到第一条记录之间是否有空缺时间段
					if(i==0){
						//第一条记录的开始时间大于策略开始时间
						if(dayP.getStartDate().getTime() > startDate.getTime()){     
							DayParting dayS = new DayParting();
							dayS.setStartDate(startDate);
							dayS.setEndDate(new Date(dayP.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							//添加第一条记录开始时间到策略开始时间的空缺段到daySurplus中
							daySurplus.add(dayS);																
							//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
							DayParting nextDay = dayList.get(i + 1);								
							if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
								DayParting dayS2 = new DayParting();
								dayS2.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
								dayS2.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
								dayS2.setDehours(allHours);
								daySurplus.add(dayS2);
							}
						}else{
							//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
							DayParting nextDay = dayList.get(i + 1);							
							if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
								DayParting dayS = new DayParting();
								dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
								dayS.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
								dayS.setDehours(allHours);
								daySurplus.add(dayS);
							}
						}
					}else if(i == dayList.size() - 1){		
						//最后一条记录的结束时间小于策略结束时间，中间有空缺时间段
						if(dayP.getEndDate().getTime() < endDate.getTime()){
							DayParting dayS = new DayParting();
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
							dayS.setEndDate(endDate);
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
					} else{
						DayParting nextDay = dayList.get(i + 1);				//与后面的一条记录做比较，前一条记录的结束时间小于后一条记录的开始时间，中间有空缺时间段
						if(dayP.getEndDate().getTime() < nextDay.getStartDate().getTime() - 24*60*60*1000){
							DayParting dayS = new DayParting();
							dayS.setStartDate(new Date(dayP.getEndDate().getTime() + 24*60*60*1000));
							dayS.setEndDate(new Date(nextDay.getStartDate().getTime() - 24*60*60*1000));
							dayS.setDehours(allHours);
							daySurplus.add(dayS);
						}
					}
				}
				
				//将空缺时间段添加到result中
				for(int i = 0; i < daySurplus.size(); i++){						
					DayParting dayP = daySurplus.get(i);
					JSONObject object = new JSONObject();
					object.put("startDate", sdf.format(dayP.getStartDate()));
					object.put("endDate", sdf.format(dayP.getEndDate()));
					object.put("dehours",dayP.getDehours());
					result.put(object);
				}
				
				//将已处理的时间段存储起来
				paramMap.put("dayParting", result.toString());					
			} catch (JSONException e) {
				// TODO Auto-generated catch block
				LOG.info("@@@@@@@@排期日期解析错误");
				e.printStackTrace();
			}
		    // 千次转换
		    if (adGroup.getMaxImpression() != null) {
		      adGroup.setMaxImpression(adGroup.getMaxImpression() * 1000);
		    }
		    if (adGroup.getDailyMaxImpression() != null) {
		      adGroup.setDailyMaxImpression(adGroup.getDailyMaxImpression() * 1000);
		    }
			
		    
	    if (adGroup.getId() == null) {	
	    	try {
	    		if (getLoginUser().getOperatorId()!=0) {
					adGroup.setOperatorId(getLoginUser().getOperatorId());
				}else{
					adGroup.setOperatorId(new Long(0));
				}
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
	    	
			adGroupService.saveAll(adGroup, paramMap);
			/**
			 * 新增投放成功后同时会新增地域定向，时段定向,wifi定向以及下面的场景
			 * 所以这里的日志新增记录应该把这些都加进去
			 */
			/**
			 * 先做投放的新增记录
			 */
			Log log = new Log();
			//对应模块
			log.setModule("AdGroup");
			//对应表名
			log.setTableName("t_adgroup");
			//增加对应的投放id
			log.setRecordId(adGroup.getId());
			//对应操作类型
			log.setActionType("新增");
			//对应的操作
			log.setAction("新增了一个投放：" + adGroup.getAdGroupName());
			//下面这几个字段目前后端数据没有得到。所以仅作测试用！
			log.setActionTime("100");
			log.setAccountId(new Long(getLoginUser().getId()));
			log.setUserIp(Common.toIpAddr(request));
			log.setAccountName(getLoginUser().getAccountName());
			logService.add(log);
			
			Direct direct = null;
			/**
			 * 时段定向的新增记录
			 */
			//先得到排期的时间段
			direct = directService.findByadGroupId(adGroup.getId(), 2);
			
			//如果查找到的对象为空且它的排期段没有则说明并没有新增时段定向
			if(null != direct && !"[]".equals(direct.getBackShow())) {
				String dateString = direct.getBackShow();
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了时间的排期段：" + dateString);
				logService.add(log);
			}
			
			/**
			 * 地域定向的新增记录
			 */
			//先得到新增的地域定向的信息
			direct = directService.findByadGroupId(adGroup.getId(), 1);
			
			//如果查找到的对象为空则说明并没有新增地域定向
			if(null != direct) {
				//得到地域名称字符串
				String[] location = direct.getData().split("/");
				String[] location1 = location[1].split("\\|");
				String locationNameString = "地域名称有:";
				
				for(int i = 0; i < location1.length; i++) {
					Location l = locationService.findByLocationT(location1[i]);
					locationNameString = locationNameString + l.getCountry() + " " + l.getCn() + " " + l.getCnCity() + ", " ;
				}
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了：" + locationNameString);
				logService.add(log);
			}
			
			adGroupService.front2dbplace(place,adGroup);//place是场景place把选择的场景存放到相应的数据库中		
			/**
			 * 保存已选的wifi到数据库t_adgroup_wifi
			 */
			String selectedwifi = (String) paramMap.get("selectedwifi");
			if(selectedwifi != "") {
				wifiService.front2dbwifi(selectedwifi, adGroup.getId());//保存已选择的wifi
			}
			/**
			 * 场景的新增记录
			 */
			//这里判断一下就是为了知道是不是有场景字符串有就会插入表，如果没有就不会插入表中也就不会有新增记录
			if(null != place) {
				//场景名称字符串
				String placeNameString = "场景,它们有：";
				String[] strArr = place.split(",");
					for(int i = 0; i < strArr.length; i++) {
						//通过场景id得到场景的名称
						placeNameString = placeNameString + placeService.findById(Long.valueOf(strArr[i]).longValue()).getName() + ", " ;
					}
					
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了：" + placeNameString);
					
					logService.add(log);
				}
			
			/**
			 * wifi定向的新增记录
			 */
			//获得新增后的wifi热点信息
			List<Wifi> wifiListAfterAdd = wifiService.findAllAdgroupWifi(adGroup.getId());
			
			//判断新增后查找的wifi热点信息集合是不是空，如果不是空则说明新增了wifi热点，则添加wifi新增的日志
			if(0 != wifiListAfterAdd.size()) {
				//存储wifi定向的地点名称
				String wifiName = "";
				
				for (int i = 0; i < wifiListAfterAdd.size(); i++) {
					wifiName = wifiName + wifiListAfterAdd.get(i).getAddress() + ", ";
				}
				
				//对应的操作
				log.setAction("在投放：" + adGroup.getAdGroupName() + "中新增了wifi定向：" + wifiName);
				
				logService.add(log);
			}
			
			
		} else {	
			
			/**
			 * 编辑成功后如果编辑前的数据与编辑后的数据比较后发生了改变，那么要对投放信息,时段信息和地域定向信息和场景信息增加修改日志
			 * 那再编辑之前要先获得到这些信息，保存下，然后和编辑之后的信息做比较
			 */
			AdGroup formerAdGroup = adGroupService.findById(adGroup.getId());
			List<AdGroupPlace> formerAdGroupPlaceList = adGroupPlaceService.findAllByAdGroupId(adGroup.getId());
			Direct formerTimeTypeDirect = directService.findByadGroupId(adGroup.getId(), 2);
			Direct formerLocationTypeDirect = directService.findByadGroupId(adGroup.getId(), 1);
			//保存编辑前的wifi地点
			List<Wifi> formerWifiList = wifiService.findAllAdgroupWifi(adGroup.getId());
			
			adGroupService.edit(adGroup, paramMap);
			
			//得到编辑之后的AdGroup对象
			AdGroup presentAdGroup = adGroupService.findById(adGroup.getId());
			
			/**
			 * 编辑的日志信息
			 */
			Log log= new Log();
			//对应模块
			log.setModule("AdGroup");
			//对应的表名
			log.setTableName("t_adgroup");
			//对应投放id
			log.setRecordId(adGroup.getId());
			//操作类型
			log.setActionType("编辑");	
			//下面这几个字段目前后端数据没有得到。所以仅作测试用！
			log.setActionTime("100");
			log.setAccountId(new Long(getLoginUser().getId()));
			log.setUserIp(Common.toIpAddr(request));
			log.setAccountName(getLoginUser().getAccountName());
			
			//如果之前的有选择wifi删除之前保存的wifi以便编辑之后保存的wifi不冲突			
			if(formerWifiList != null) {
				wifiService.deleteWifi(adGroup.getId());
			}			
			/**
			 * 保存编辑之后已选wifi
			 */								
			String selectedwifi = (String) paramMap.get("selectedwifi");
			if(selectedwifi != "") {
				wifiService.front2dbwifi(selectedwifi, adGroup.getId());//保存已选择的wifi
			}
						
			/**
			 * wifi定向编辑的日志更改记录
			 * 如果新选定的wifi地点和编辑前的wifi地点一样则不用增加更改日志，否则添加更改日志
			 * 比较步骤：第一如果编辑前和编辑后wifi热点都为空的话，则说明没有发生改变
			 * 第二如果编辑前和编辑后的wifi热点一个为空一个不为空，则发生改变
			 * 第三如果都不为空则逐个进行比较看是否发生了改变
			 */
			
			List<Wifi> presentWifiList = wifiService.findAllAdgroupWifi(adGroup.getId());
			if((null != formerWifiList && null == presentWifiList) || (null == formerWifiList && null != presentWifiList)) {
				if(null != formerWifiList) {
					//保存wifi热点的名称
					String wifiName = "";
					
					for (int i = 0; i < formerWifiList.size(); i++) {
						wifiName = wifiName + formerWifiList.get(i).getAddress() + ", ";
					}

					//变更详情
					log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
							+ "以前的wifi热点有:" + wifiName + "编辑后的wifi热点为空");
					logService.add(log);
				}
				
				if(null != presentWifiList) {
					//保存wifi热点的名称
					String wifiName = "";
					
					for (int i = 0; i < presentWifiList.size(); i++) {
						wifiName = wifiName + presentWifiList.get(i).getAddress() + ", ";
					}
					
					//变更详情
					log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
							+ "以前的wifi热点为空: ,编辑后的wifi热点为" + wifiName);
					logService.add(log);
				}								
			}
			
			if(null != formerWifiList && null != presentWifiList) {
				//以前的wifi热点id数组
				long[] formerWifiId = new long[formerWifiList.size()];
				
				for(int i = 0; i < formerWifiList.size(); i++) {
					formerWifiId[i] = formerWifiList.get(i).getId();
				}
				Arrays.sort(formerWifiId);
				
				//编辑后的wifi热点 的id数组
				long[] presentWifiId = new long[presentWifiList.size()];
				
				for (int i = 0; i < presentWifiList.size(); i++) {
					presentWifiId[i] = presentWifiList.get(i).getId();
				}
				Arrays.sort(presentWifiId);
				
				//修改标志，默认为没有修改
				boolean wifiUpdatedMark = false;
				
				//比较步骤，先判断它们的长度是不是一样如果一样则逐个比较如果不一样则表示wifi热点有改变
				if(formerWifiId.length == presentWifiId.length) {
					for(int i = 0; i < formerWifiId.length; i++) {
						if(formerWifiId[i] != presentWifiId[i]) {
							wifiUpdatedMark = true;
							break;
						}
					}
					
				} else {
					wifiUpdatedMark = true;
				}
				
				//存储编辑前的wifi热点名称
				String formerWifiName = "";
				
				for(int i = 0; i < formerWifiList.size(); i++) {
					formerWifiName = formerWifiName + formerWifiList.get(i).getAddress() + ", ";
				}
				
				//存储编辑后的wifi热点的名称
				String presentWifiName = "";
				
				for(int i = 0; i < presentWifiList.size(); i++) {
					presentWifiName = presentWifiName + presentWifiList.get(i).getAddress() + ", ";
				}
				
				//变更详情
				log.setAction("对原有的投放" + formerAdGroup.getAdGroupName() + "中wifi热点做了修改"
						+ "以前的wifi热点有：" + formerWifiName + "现在的wifi热点有：" + presentWifiName);
				logService.add(log);
				
			}
			
			
			//对修改前和之后的每一项进行比较，如果发现哪一个字段发生了修改就记录下来，并且让修改标志设为true，
			boolean updatedMark = false;
			boolean updatedMark1 = false;
			
			/**
			 * 对投放信息的修改日志的添加
			 */
				
				//存储修改信息
				String updatedString = "对原有的投放" + formerAdGroup.getAdGroupName() + "做了修改了：";
				//投放名称的比较
				if(!(formerAdGroup.getAdGroupName().equals(presentAdGroup.getAdGroupName()))) {
					updatedString = updatedString + "投放名称" + " " + formerAdGroup.getAdGroupName() + "-->" + presentAdGroup.getAdGroupName() + ", ";
					updatedMark1 = true;
				}
				
				//活动周期的比较
				if(!(formerAdGroup.getStartDate().equals(presentAdGroup.getStartDate()) && formerAdGroup.getEndDate().equals(presentAdGroup.getEndDate()))) {
					updatedString = updatedString + "投放周期" + " " + formerAdGroup.getStartDate() + 
							"--" + formerAdGroup.getEndDate() + "-->" + presentAdGroup.getStartDate() + "--" + presentAdGroup.getEndDate() + ", ";
					updatedMark = true;
				}
				
				//总预算的比较
				if(!(formerAdGroup.getTotalBudget().equals(presentAdGroup.getTotalBudget()))) {
					updatedString = updatedString + "投放总预算" + " " + formerAdGroup.getTotalBudget() + "-->" + presentAdGroup.getTotalBudget() + ", ";
					updatedMark = true;
				}
							
				//单价的比较
				if(!(formerAdGroup.getPrice().equals(presentAdGroup.getPrice()))) {
					updatedString = updatedString + "单价" + " " + formerAdGroup.getPrice() + "-->" + presentAdGroup.getPrice() + ", ";
					updatedMark = true;
				}
				
				//每日预算的比较
				if(!(formerAdGroup.getDailyBudget().equals(presentAdGroup.getDailyBudget()))) {
					updatedString = updatedString + "每日预算" + " " + formerAdGroup.getDailyBudget() + "-->" + presentAdGroup.getDailyBudget() + ", ";
					updatedMark = true;
				}
				
				//曝光总上限的比较
				if(!(formerAdGroup.getMaxImpression().equals(presentAdGroup.getMaxImpression()))) {
					updatedString = updatedString + "曝光总上限" + " " + formerAdGroup.getMaxImpression() + "-->" + presentAdGroup.getMaxImpression() + ", ";
					updatedMark = true;
				}
				
				//点击总上限
				if(!(formerAdGroup.getMaxClick().equals(presentAdGroup.getMaxClick()))) {
					updatedString = updatedString + "点击总上限" + " " + formerAdGroup.getMaxClick() + "-->" + presentAdGroup.getMaxClick() + ", ";
					updatedMark = true;
				}
				
				//转化总上限
				if(!(formerAdGroup.getMaxConversion().equals(presentAdGroup.getMaxConversion()))) {
					updatedString = updatedString + "转化总上限" + " " + formerAdGroup.getMaxConversion() + "-->" + presentAdGroup.getMaxClick() + ", ";
					updatedMark = true;
				}
				
				//每日曝光上限的比较
				if(!(formerAdGroup.getDailyMaxImpression().equals(presentAdGroup.getDailyMaxImpression()))) {
					updatedString = updatedString + "每日曝光上限" + " " + formerAdGroup.getDailyMaxImpression() + "-->" + presentAdGroup.getDailyMaxImpression() + ", ";
					updatedMark = true;
				}
				
				//每日点击上限
				if(!(formerAdGroup.getDailyMaxClick().equals(presentAdGroup.getDailyMaxClick()))) {
					updatedString = updatedString + "每日点击上限" + " " + formerAdGroup.getDailyMaxClick() + "-->" + presentAdGroup.getDailyMaxClick() + ", ";
					updatedMark = true;
				}
				
				//每日转化上限
				if(!(formerAdGroup.getDailyMaxConversion().equals(presentAdGroup.getDailyMaxConversion()))) {
					updatedString = updatedString + "每日转化上限" + " " + formerAdGroup.getDailyMaxConversion() + "-->" + presentAdGroup.getDailyMaxConversion() + ", ";
					updatedMark = true;
				}
				
				//单人点击频次
				if(!(formerAdGroup.getPerClickType().equals(presentAdGroup.getPerClickType()) && formerAdGroup.getPerClick().equals(presentAdGroup.getPerClick()))) {
					/**
					 * 单人点击频次类型1-代表每天，2-代表投放周期
					 */
					//存储单人点击频次类型
					String formerPerClickType = "";
					String presentPerClickType = "";
					if(formerAdGroup.getPerClickType() == 1) {
						formerPerClickType = "每天";
					} else {
						formerPerClickType = "投放周期";
					}
					
					if(presentAdGroup.getPerClickType() == 1) {
						presentPerClickType = "每天";
					} else {
						presentPerClickType = "投放周期";
					}
					updatedString = updatedString + "单人点击频次" + " " + formerPerClickType + " " + formerAdGroup.getPerClick() + "-->"
									+ presentPerClickType + " " + presentAdGroup.getPerClick() + ", ";
					updatedMark = true;
				}
				
				//点击找回的比较
				if(!(formerAdGroup.getRetarget().equals(presentAdGroup.getRetarget()))) {
					updatedString = updatedString + "点击找回" + " " + formerAdGroup.getRetarget() + "-->" + presentAdGroup.getRetarget() + ", ";
					updatedMark = true;
				}
				
				//访客投放期的比较
				if(!(formerAdGroup.getPeriod().equals(presentAdGroup.getPeriod()))) {
					updatedString = updatedString + "访客投放期" + " " + formerAdGroup.getPeriod() + "-->" + presentAdGroup.getPeriod() + ", ";
					updatedMark = true;
				}
				
				//是否全站访客的比较
				if(!(formerAdGroup.getSite().equals(presentAdGroup.getSite()))) {
					updatedString = updatedString + "是否全站访客" + " " + formerAdGroup.getSite() + "-->" + presentAdGroup.getSite() + ", ";
					updatedMark = true;
				}
				
				
				//单人曝光频次
				if(!(formerAdGroup.getPerImpressionType().equals(presentAdGroup.getPerImpressionType()) && formerAdGroup.getPerImpression().equals(presentAdGroup.getPerImpression()))) {
					/**
					 * 单人曝光频次类型1-代表每天，2-代表投放周期
					 */
					//存储单人点击频次类型
					String formerPerImpressionType = "";
					String presentPerImpressionType = "";
					if(formerAdGroup.getPerImpressionType() == 1) {
						formerPerImpressionType = "每天";
					} else {
						formerPerImpressionType = "投放周期";
					}
					
					if(presentAdGroup.getPerImpressionType() == 1) {
						presentPerImpressionType = "每天";
					} else {
						presentPerImpressionType = "投放周期";
					}
					
					updatedString = updatedString + "单人曝光频次" + " " + formerPerImpressionType + " " + formerAdGroup.getPerImpression() + "-->"
							+ presentPerImpressionType + " " + presentAdGroup.getPerImpression() + ", ";
					updatedMark = true;
				}
				
				//位置的比较,因为位置没选的时候默认值是为"0"，所以判断一下位置如果编辑前后都等于0的话，则没有改变
				if(!("0".equals(formerAdGroup.getPosition()) && "0".equals(presentAdGroup.getPosition()))) {
					//当两个字符串不同时为0时，再判断下如果编辑前字符串为0编辑后字符串不0空或者编辑后为0编辑前不为0则发生了改变，否则再逐个比较
					if(("0".equals(formerAdGroup.getPosition()) && !("0".equals(presentAdGroup.getPosition()))) || 
							!("0".equals(formerAdGroup.getPosition())) && "0".equals(presentAdGroup.getPosition())) {
						
						//得到位置的名称
						String formerPositionString = "编辑前的位置: ";
						String presentPositionString = "编辑后的位置:";
						
						if(!("0".equals(formerAdGroup.getPosition()))) {
							String[] formerPosition = formerAdGroup.getPosition().split(",");
							
							for(int i = 0; i < formerPosition.length; i++) {
								if("1".equals(formerPosition[i])) {
									formerPositionString = formerPositionString + "认证" + ", ";
								} else if("2".equals(formerPosition[i])) {
									formerPositionString = formerPositionString + "跳转" + ", ";
								} else {
									formerPositionString = formerPositionString + "上网过程" + ", ";
								}
							}
						}
						
						if(!("0".equals(presentAdGroup.getPosition()))) {
							String[] presentPosition = presentAdGroup.getPosition().split(",");
							
							for(int i = 0; i < presentPosition.length; i++) {
								if("1".equals(presentPosition[i])) {
									presentPositionString = presentPositionString + "认证" + ", ";
								} else if("2".equals(presentPosition[i])) {
									presentPositionString = presentPositionString + "跳转" + ", ";
								} else {
									presentPositionString = presentPositionString + "上网过程" + ", ";
								}
							}
						}
						
						updatedString = updatedString + "位置" + " " + formerPositionString + "-->" +
								presentPositionString + ", ";
						updatedMark = true;
					} else{
						String[] formerPositionStringArray = formerAdGroup.getPosition().split(",");
						String[] presentPositionStringArray = presentAdGroup.getPosition().split(",");
						
						int[] formerPosition = new int[formerPositionStringArray.length];
						int[] presentPosition = new int[presentPositionStringArray.length];
						
						//进行排序下
						Arrays.sort(formerPosition);
						Arrays.sort(presentPosition);
						
						//逐个比较时先比较一下两个数组大小如果数组大小不同则发生改变
						if(!(formerPosition.length == presentPosition.length)) {
							
							for(int i = 0; i < formerPosition.length; i++) {
								if(formerPosition[i] != presentPosition[i]) {
									
									//得到位置的名称
									String formerPositionString = "编辑前的位置有: ";
									String presentPositionString = "编辑后的位置有:";
									
									for(int j = 0; j < formerPositionStringArray.length; j++) {
										if("1".equals(formerPositionStringArray[j])) {
											formerPositionString = formerPositionString + "认证" + ", ";
										} else if("2".equals(formerPositionStringArray[j])) {
											formerPositionString = formerPositionString + "跳转" + ", ";
										} else {
											formerPositionString = formerPositionString + "上网过程" + ", ";
										}
									}
									
									for(int j = 0; j < presentPositionStringArray.length; j++) {
										if("1".equals(presentPositionStringArray[j])) {
											presentPositionString = presentPositionString + "认证" + ", ";
										} else if("2".equals(presentPositionStringArray[j])) {
											presentPositionString = presentPositionString + "跳转" + ", ";
										} else {
											presentPositionString = presentPositionString + "上网过程" + ", ";
										}
									}
									
									
									updatedString = updatedString + "位置" + " " + formerPositionString + "-->" +
											presentPositionString + ", ";
									updatedMark = true;
								}
							}
						}
					}
				}
				
				//变更详情
				log.setAction(updatedString);
				
//				updatedMark1 = 
				//如果编辑前后投放信息进行修改了（除投放名称name之外），就把投放以及投放下级的supdated进行修改
				if(updatedMark) {
					adGroupService.updatedAdgroupSupdated(adGroup.getId());
				}
				
				//判断是否编辑前后的投放信息如果真的改变则添加修改日志
				if(updatedMark || updatedMark1) {
					logService.add(log); 
				}
				
			
				/**
				 * 对时段定向修改记录的更新
				 */
				//重置修改标志
				updatedMark = false;
				
				/**
				 * 如果以前的时段定向和现在的时段定向都是为空的话则说明没有发生变化
				 * 如果以前的时段定向和现在的时段定向一个为空一个不为空则说明发生了变化
				 * 如果都不为空则逐个比较再看是否发生变化
				 * 注：dayList如果大小为0则表示传递过来的时间段是空
				 */
				if((null == formerTimeTypeDirect && 0 != dayList.size()) || (null != formerTimeTypeDirect && 0 == dayList.size())) {
					updatedMark = true;
				}
				
				if(null != formerTimeTypeDirect && 0 != dayList.size()) {
					List<DayParting> formerDayPartingList = new ArrayList<DayParting>();
					try {
						//以前已选择的时间JSONArray
						JSONArray formerJsonArray = new JSONArray(formerTimeTypeDirect.getBackShow());
						for (int i = 0; i < formerJsonArray.length(); i++) {
							JSONObject object = formerJsonArray.getJSONObject(i);
							DayParting day = new DayParting();
							day.setDehours(object.getString("dehours"));
							try {
								day.setStartDate(sdf.parse(object.getString("startDate")));
								day.setEndDate(sdf.parse(object.getString("endDate")));
							} catch (ParseException e) {
								// TODO Auto-generated catch block
								e.printStackTrace();
							}
							formerDayPartingList.add(day);
						}
						
						//按照开始时间的先后顺序给dayList进行排序，排序后，比较相邻的2个时间段，能够得出未选择的时间段
						Collections.sort(formerDayPartingList, new AdvertiserSortByDate());
						
						//编辑前后的时间段进行比较
						if(formerDayPartingList.size() == dayList.size()) {
							//一个一个进行比较
							for(int i = 0; i < dayList.size(); i++) {
								//开始时间的比较
								if(!(formerDayPartingList.get(i).getStartDate().equals(dayList.get(i).getStartDate()))) {
									updatedMark = true;
									break;
								}
								
								//结束的时间进行比较
								if((!formerDayPartingList.get(i).getEndDate().equals(dayList.get(i).getEndDate()))) {
									updatedMark = true;
									break;
								}
								
								//时间点的比较
								if(!(formerDayPartingList.get(i).getDehours().equals(dayList.get(i).getDehours()))) {
									updatedMark = true;
									break;
								}
								
							}
						} else {
							updatedMark = true;
						}
						
					} catch(Exception e) {
						e.printStackTrace();
					}
				}
				
				if(updatedMark) {
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对时间段进行了修改： 从" + formerTimeTypeDirect.getBackShow() + "-->" + directService.findByadGroupId(adGroup.getId(), 2).getBackShow());
					logService.add(log);
				}
				
				/**
				 * 对地域定向的修改的日志更新
				 */
				//重置修改标志
				updatedMark = false;
				
				/**
				 * 如果以前的地域定向和现在的地域定向都是为空的话则说明没有发生变化
				 * 如果以前的地域定向和现在的地域定向一个为空一个不为空则说明发生了变化
				 * 如果都不为空则逐个比较再看是否发生变化
				 */
				//编辑完之后，得到编辑之后的地域定向信息
				Direct presentDirectOfLocationType = directService.findByadGroupId(adGroup.getId(), 1);
				
				String formerAreasNameString = "";
				String presentAreasNameString = "";
				
				if((null != formerLocationTypeDirect && null == presentDirectOfLocationType) || (null == formerLocationTypeDirect && null != presentDirectOfLocationType)) {
					/**
					 * 得到编辑前后的地域数组对应的名称字符串
					 */
					formerAreasNameString = "编辑前的地域：";
					presentAreasNameString = "编辑后的地域：";
					if(null != formerLocationTypeDirect) {
						String[] formerTargetData = formerLocationTypeDirect.getData().split("/");
						//编辑之前的地域数组
						String[] formerAreas = formerTargetData[1].split("\\|");
						
						for(int i = 0; i < formerAreas.length; i++) {
							Location l = locationService.findByLocationT(formerAreas[i]);
							formerAreasNameString = formerAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						
					}
					
					if(null != presentDirectOfLocationType) {
						String[] presentTargetData = (presentDirectOfLocationType.getData()).split("/");
						//得到编辑之后的地域数组
						String[] presentAreas = presentTargetData[1].split("\\|");
						
						for(int i = 0; i < presentAreas.length; i++) {
							Location l = locationService.findByLocationT(presentAreas[i]);
							presentAreasNameString = presentAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
					}
					
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对地域进行修改：" + formerAreasNameString + "-->" + presentAreasNameString);
					
					logService.add(log);
				}
				
				if(null != formerLocationTypeDirect && null != presentDirectOfLocationType) {
					String[] formerTargetData = formerLocationTypeDirect.getData().split("/");
					//编辑之前的地域数组
					String[] formerAreas = formerTargetData[1].split("\\|");
					String[] presentTargetData = (presentDirectOfLocationType.getData()).split("/");
					//得到编辑之后的地域数组
					String[] presentAreas = presentTargetData[1].split("\\|");
					
					//对两个地域数组进行比较
					if(formerAreas.length == presentAreas.length) {
						//先进行排序再一个一个比较
						Arrays.sort(formerAreas);
						Arrays.sort(presentAreas);
						
						for(int i = 0; i< formerAreas.length; i++) {
							if(!(formerAreas[i].equals(presentAreas[i]))) {
								updatedMark = true;
								break;
							}
						}
					} else {
						updatedMark = true;
					}
					
					if(updatedMark) {
						
						/**
						 * 得到编辑前后的地域数组对应的名称字符串
						 */
						formerAreasNameString = "编辑前的地域有：";
						presentAreasNameString = "编辑后的地域有：";
						
						for(int i = 0; i < formerAreas.length; i++) {
							Location l = locationService.findByLocationT(formerAreas[i]);
							formerAreasNameString = formerAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						

						for(int i = 0; i < presentAreas.length; i++) {
							Location l = locationService.findByLocationT(presentAreas[i]);
							presentAreasNameString = presentAreasNameString + " " + l.getCountry() + " " + l.getCn() + " "
													+ l.getCnCity() + ", ";
						}
						
						//对应的操作
						log.setAction("在投放：" + adGroup.getAdGroupName() + "中对地域进行修改：" + formerAreasNameString + "-->" + presentAreasNameString);
						
						logService.add(log);
				}
				
					
				}
				
			
			
			/**
			 * 对于场景的修改的日志的增加
			 */
			//重置修改标志
			updatedMark = false;
			String formerPlaceNameString = "";
			String updatedPlaceNameString = "";
			/**
			 * 如果以前的场景和现在的场景都是为空的话则说明没有发生变化
			 * 如果以前的场景和现在的场景一个为空一个不为空则说明发生了变化
			 * 如果都不为空则逐个比较再看是否发生变化
			 */
			if((0 != formerAdGroupPlaceList.size() && null == place) || (0 == formerAdGroupPlaceList.size() && null != place)) {
				updatedMark = true;
				
				if(0 != formerAdGroupPlaceList.size()) {
					formerPlaceNameString = "编辑之前的场景：";
					
					for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
						formerPlaceNameString = formerPlaceNameString + placeService.findById(formerAdGroupPlaceList.get(i).getPlaceId()).getName() + ", ";
					}
				}
				
				if(null != place) {
					updatedPlaceNameString = "编辑之后的场景有：";
					String[] placeIdString = place.split(",");
					Long[] placeId = new Long[placeIdString.length];
					
					//得到现在想编辑的场景id
					for(int i = 0; i < placeIdString.length; i++) {
						placeId[i] = Long.parseLong(placeIdString[i]);
					}
					
					for(int i = 0; i < placeId.length; i++) {
						//得到对应的广告位名称
						updatedPlaceNameString = updatedPlaceNameString + placeService.findById(placeId[i]).getName() + ", ";
					}
				}
				
			}
			
			if(0 != formerAdGroupPlaceList.size() && null != place) {
				String[] placeIdString = place.split(",");
				Long[] placeId = new Long[placeIdString.length];
				Long[] formerPlaceId = new Long[formerAdGroupPlaceList.size()];
				
				//得到编辑前的场景id，并且进行排序
				for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
					formerPlaceId[i] = formerAdGroupPlaceList.get(i).getPlaceId();
				}
				Arrays.sort(formerPlaceId);
				
				//得到现在想编辑的场景id，并且进行排序
				for(int i = 0; i < placeIdString.length; i++) {
					placeId[i] = Long.parseLong(placeIdString[i]);
				}
				Arrays.sort(placeId);
				
				
				//对比一下编辑前后的广告位id是否发生变化如果发生变化就去更新表并且新增修改记录
				//首先对比一下广告位的id数量是不是一样多如果发生变化就说明广告位有了变化否则再一条一条的对比
				if(placeId.length == formerPlaceId.length) {
					for(int i = 0; i < placeId.length; i++) {
						if(placeId[i] != formerPlaceId[i]) {
							updatedMark = true;
							break;
						}
					}
				} else {
					updatedMark = true;
				}
				
				//存储场景名称
				formerPlaceNameString = "编辑之前的场景有：";
				updatedPlaceNameString = "编辑之后的场景有：";
				
				for(int i = 0; i < formerAdGroupPlaceList.size(); i++) {
					formerPlaceNameString = formerPlaceNameString + placeService.findById(formerAdGroupPlaceList.get(i).getPlaceId()).getName() + ", ";
				}
				
				for(int i = 0; i < placeId.length; i++) {
					//得到对应的广告位名称
					updatedPlaceNameString = updatedPlaceNameString + placeService.findById(placeId[i]).getName() + ", ";
				}
				
				
			}
			
			
			
			if(updatedMark) {
				adGroupPlaceService.delete(adGroup.getId());//删除之前保存的场景
				adGroupService.front2dbplace(place,adGroup);//保存编辑之后的场景
				//场景进行了改变，将表t_adgroup_place里面的supdated进行更新
//				adGroupPlaceService.updatedPlaceSupdated(adGroup.getId());
				
				
					//对应的操作
					log.setAction("在投放：" + adGroup.getAdGroupName() + "中对场景进行修改：" + formerPlaceNameString + "-->" + updatedPlaceNameString);
					
					logService.add(log);
			}
		}
	    
		model.addAttribute("campaignId", adGroup.getCampaignId());
		return redirect(page("list"));
	}
}
