using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using EShangApi.Models;
using HZQR.Common;
namespace EShangApi.Helper
{
public class ECodeHelper
{
///
/// 生成电子码
///
///
/// 会员Id
/// 企业Id
/// 是否支持积分
/// 优惠券编码
/// 返回字符串,最终生成的电子码
public static string EncodedECode(int membershipType, int? memberShipId, int? companyId, int isSupportPoint = 0, string couponCode = "")
{
//电子码新规则,共计23位
//2位固定数+2位分钟+9位会员ID+2位小时+5位企业ID+1位固定数(标识是否支持积分)+1位随机数+1位校验码
/* 2位固定数字具体含义:
* 20 企业会员电子码
* 21 驿网会员电子码
* 30 企业会员优惠券码
* 31 驿网会员优惠券码
*/
int ecodeType = 21;//默认驿网会员
Random random = new Random();//创建随机数的函数
int randNum = (int)((1 - 9) * random.NextDouble() + 9);//从1-9中产生随机数
string memberOrCouponECode = "";//会员内码或者是优惠券编码
//判断是否是优惠券码,优惠券码为空则是会员电子码
if (string.IsNullOrEmpty(couponCode))
{
//membershipType=3000,企业会员电子码,首位显示20;否则驿网会员电子码,首位显示21
ecodeType = membershipType == 3000 ? 20 : 21;
memberOrCouponECode = CalculateCode(memberShipId.ToString().PadLeft(9, '0'), randNum, true);//根据随机数计算出虚拟的会员Id
}
else
{
//membershipType=3000,企业会员电子码,首位显示30;否则驿网会员电子码,首位显示31
ecodeType = membershipType == 3000 ? 30 : 31; //30:企业会员优惠券码;31:驿网会员优惠券码
memberOrCouponECode = CalculateCode(couponCode.PadLeft(9, '0'), randNum, true);//根据随机数计算出虚拟的优惠券编码
}
string calCompanyId = CalculateCode(companyId.ToString().PadLeft(5, '0'), randNum, true);//根据随机数计算出虚拟的企业Id
string ECode = ecodeType + DateTime.Now.Minute.ToString().PadLeft(2, '0') + //当前时间的分钟
memberOrCouponECode + DateTime.Now.Hour.ToString().PadLeft(2, '0') + calCompanyId + isSupportPoint + randNum;
int checkNum = GetCheckCode(ECode);//1:校验码
ECode = ECode + checkNum;
return ECode;//返回最终的电子码
}
///
/// 判断电子码是否有效
///
/// 会员电子码
/// 返回结果:100电子码有效;101:电子码无效,102:电子码失效
public static Result CheckECode(string ECode)
{
Result result = new Result();
if (ECode.Length != 23)//电子码长度一定是23位
{
result.Result_Code = 101;//电子码无效
result.Result_Desc = "电子码无效";
return result;
}
string strMin = ECode.Substring(2, 2);//电子码中的第3、4位显示的分钟
string strHour = ECode.Substring(13, 2);//电子码中的第14、15位显示的分钟
DateTime eCodeTime = Convert.ToDateTime(DateTime.Now.ToShortDateString() +
" " + strHour + ":" + strMin + ":00");//生成电子码的时间
//如果生成码的时间比当前时间则表示电子码是昨天生成的
if (eCodeTime > DateTime.Now)
{
eCodeTime = eCodeTime.AddDays(-1);
}
if (DateTime.Now >= eCodeTime.AddMinutes(10))//电子码生成5分钟后则不能使用
{
result.Result_Code = 102;//超过五分钟,电子码失效
result.Result_Desc = "电子码失效";
return result;
}
return result;
}
///
/// 电子码解码
/// 创建人:zhengxp
/// 创建日期:2020-08-11
/// 修改人:
/// 修改日期:yyyy-mm-dd
/// 修改备注:无
///
/// 会员电子码
/// 返回实体对象,包含MemberShipId:会员Id;CompanyId:企业Id;CouponCode:优惠券编码;SupportPoint:是否支持积分
public static Models.ECode DecodeECode(string ECode)
{
//电子码新规则,共计23位
//2位固定数+2位分钟+9位会员ID+2位小时+5位企业ID+1位固定数(标识是否支持积分)+1位随机数+1位校验码
/* 2位固定数字具体含义:
* 20 企业会员电子码
* 21 驿网会员电子码
* 30 企业会员优惠券码
* 31 驿网会员优惠券码
*/
Models.ECode ecodeModel = new Models.ECode();
string memberOrCouponECode = ECode.Substring(4, 9);//会员内码或者是优惠券编码
string subStringCompanyId = ECode.Substring(15, 5);//企业Id
int supportPoint = ECode.Substring(20, 1).TryParseToInt();//是否支持积分
int randNum = ECode.Substring(21, 1).TryParseToInt();//随机数
int EcodeType = ECode.Substring(0, 2).TryParseToInt();//电子码类型
ecodeModel.IsCompanyUser = (EcodeType == 20 || EcodeType == 30) ? true : false;//判断是否是企业会员
ecodeModel.CompanyId = CalculateCode(subStringCompanyId, randNum, false).TryParseToInt();//根据随机数计算出实际的企业ID
string _memberOrCouponECode = CalculateCode(memberOrCouponECode, randNum, false);//根据随机数计算出实际的会员ID 或者 优惠券编码
if (EcodeType == 20 || EcodeType == 21)
{
//会员Id
ecodeModel.MemberShipId = _memberOrCouponECode.TryParseToInt();
}
else
{
//优惠券编码
ecodeModel.CouponCode = _memberOrCouponECode;
}
ecodeModel.SupportPoint = supportPoint == 1 ? true : false;//是否支持积分积累
return ecodeModel;
}
///
/// 根据随机数计算出实际的Code
/// 创建人:zhengxp
/// 创建日期:2020-08-11
/// 修改人:
/// 修改日期:yyyy-mm-dd
/// 修改备注:无
///
/// 原Code
/// 随机数
/// 是否是增加随机数,否则减去随机数
///
protected static string CalculateCode(string orgiCode, int randNum, bool isAdd)
{
bool isOdd = Common.IsOdd(randNum);//判断随机数是否是偶数
string newCode = "";
char[] array = orgiCode.ToCharArray();
for (int i = 0; i < array.Length; i++)
{
//随机数是奇数,则奇数位加上随机数;随机数是偶数,则偶数位加上随机数
if (Common.IsOdd(i + 1) == isOdd)
{
if (isAdd)
{
//增加随机数,生成电子码规则用到
int Number = array[i].TryParseToInt() + randNum;
//加上随机数后>9则取个位
newCode += (Number > 9 ? (Number / 1 % 10) : Number).ToString();
}
else
{
//减去随机数,解析电子码规则用到
int Number = array[i].TryParseToInt() < randNum ? array[i].TryParseToInt() + 10 : array[i].TryParseToInt();
newCode += (Number - randNum).ToString();
}
}
else
{
//不需要加/减随机数则不变
newCode += array[i].ToString();
}
}
return newCode;
}
///
/// 获取校验位
///
/// 会员电子码
///
public static int GetCheckCode(string code)
{
int check = 0;
for (int i = code.Length - 1; i >= 0; i--)
{
decimal val = code.Substring(i, 1).TryParseToInt() * 2;
if ((i + 1) % 2 == 0)
{
while (val > 0)
{
check += (int)(val % 10);
val /= 10;
val = (int)(val);
}
}
else
{
check += code.Substring(i, 1).TryParseToInt();
}
}
check = 10 - check % 10;
check = check == 10 ? 0 : check;
return check;
}
}
}