package com.qy.utils;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;

import com.qy.Interfaces.SmaliApkToolsPath;

import brut.apktool.Main;

public class SmaliUtils {
	//private String str = "";
	public String mainPath =null;
	private int mix = 1000;
	// private String mainPath = "D:\\反编译\\APK\\rx.jar.out\\smali";
	private Map<String, String> clazzList = new HashMap<>();
	private List<File> files = new ArrayList<>();

	public static void main(String[] args) {
		new SmaliUtils();
	}
	public SmaliUtils() {
	}
	
	public void setPath(String uPath) {
			mainPath=uPath;
		
	}
	private SmaliApkToolsPath inter;
	public void start(SmaliApkToolsPath inter) {
		this.inter=inter;
		list=new ArrayList<>();
		System.out.println("开始修改:"+mainPath);
		File path = new File(mainPath);
		recursive(path);
		try {
			System.out.println(clazzList.size());
			for (File file : files) {
				String str = loadFile(file);
				writerFile(file,str);

			}
			inter.smaliPath("ok");
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	private int writerIndex=0;
	private void test(){
		writerIndex++;
		if(files.size()==writerIndex){
			inter.smaliPath("ok");
		}
	}
	private void recursive(File file) {
		String packname = null;
		if (file.isFile()) {
			if (!files.contains(file)) {
				files.add(file);
			}
			String path = file.getAbsolutePath();
			path = path.replace(mainPath, "");
			path = path.replace(file.getName(), "");
			if(path.substring(0, 1).equals("/")||path.substring(0, 1).equals("\\")) {
			packname = path.replace("\\", "/").substring(1, path.length() - 1);
			}else {
				packname = path.replace("\\", "/").substring(0, path.length() - 1);
			}

			try {
				readFile(file, packname);
				/*
				 * System.out.println("开始  :"+file.getName()); show();
				 * System.out.println("结束  :"+file.getName());
				 */
			} catch (Exception e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		} else {
			//System.out.println(file.getAbsolutePath()+"   >  "+file.exists());
			for (int i = 0; i < file.listFiles().length; i++) {
				recursive(file.listFiles()[i]);
			}
		}

	}

	private void readFile(File file, String packName) throws Exception {
		boolean isOneLine = true;
		for (String filter : list) {
			filter=filter.replace(".",File.separator);
			if(file.getAbsolutePath().contains(File.separator+filter+File.separator)){
				return;
			}
		}
		BufferedReader reader = new BufferedReader(new FileReader(file));
		//String str = "";
		String tmp = null;
		while ((tmp = reader.readLine()) != null) {
			if (isOneLine) {
				String newName = null;
				if (tmp.contains(".class public L")) {
					newName = tmp.replace(".class public L", "");
				} else if (tmp.contains(".class public interface abstract L")) {
					newName = tmp.replace(".class public interface abstract L", "");
				} else if (tmp.contains(".class public final enum L")) {
					newName = tmp.replace(".class public final enum L", "");
				} else if (tmp.contains(".class public abstract L")) {
					newName = tmp.replace(".class public abstract L", "");
				} else if (tmp.contains(".class public final L")) {
					newName = tmp.replace(".class public final L", "");
				} else if (tmp.contains(".class final L")) {
					newName = tmp.replace(".class final L", "");
				} else if (tmp.contains(".class L")) {
					newName = tmp.replace(".class L", "");
				} else if (tmp.contains(".class synthetic L")) {
					newName = tmp.replace(".class synthetic L", "");
				} else if(tmp.contains(".class final enum L")){
					newName=tmp.replace(".class final enum L","");
				}
				if (newName != null) {
					newName = newName.replace(";", "");
					//System.out.println("获取到老包名：" + newName + "新包名:" + (packName + "/" + file.getName().replace(".smali", "")));
					clazzList.put(newName, (packName + "/"+ file.getName()
							.replace(".smali", "")
							.replace("#","")));
					if (clazzList.get(newName).length() < mix) {
						mix = clazzList.get(newName).length();
					}
				}
				isOneLine = false;
			}
			// tmp = changeLine(tmp);
		//	str += tmp + "\n";
		}
		reader.close();

	}

	private String loadFile(File file) throws Exception {
		BufferedReader reader = new BufferedReader(new FileReader(file));
		String str = "";
		String tmp = null;
		while ((tmp = reader.readLine()) != null) {
			str += tmp + "\n";
		}
		reader.close();
		return str;
	}

	private void writerFile(File file,String str) throws Exception {
		for (String filter : list) {
			filter=filter.replace(".",File.separator);
			if(file.getAbsolutePath().contains(File.separator+filter+File.separator)){
				return;
			}
		}
		String[] datas = str.split("\n");
		String save = "";
		i = 1;

		for (String string : datas) {
			save += changeLine(string) + "\n";
		}

		PrintWriter writer = new PrintWriter(file);
		if (save.trim().length() != 0) {
			writer.write(save);
			writer.flush();
		}
		writer.close();

	}

	int i = 1;
	private String changeLine(String old) {
		Set<String> keySet = clazzList.keySet();
		for (String clazz : keySet) {
			if (old.contains(clazz+";")) {
				old= old.replace(clazz, clazzList.get(clazz));
			}
		}
		return old;
	}
	private boolean isEncryption=false;
	public void unPack(String jarPath, SmaliApkToolsPath smaliApkToolsPath) {
		File path=new File(jarPath+".out");
		if(path.exists()&&path.isDirectory()) {
			Tools.deleteFiles(path.getAbsolutePath());
		}
		String[] args =new String[] {"d","-f",jarPath};
		if(isEncryption){
			args =new String[] {"d","-f",jarPath,"--only-main-classes"};
		}
		try {
			for (String arg : args) {
				System.out.print(arg+" ");
			}
			Main.main(args);
			File jarFile=new File(jarPath);
			String name;
			if(jarFile.getName().contains(".jar")) {
				name=jarFile.getName()+".out";
			}else if(jarFile.getName().contains(".apk")) {
				name=jarFile.getName().replace(".apk","");
			}else {
				name=jarFile.getName();
			}
			//jarFile.delete();
			smaliApkToolsPath.smaliPath(new File("").getAbsolutePath()+File.separator+name);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} 
	}
	public void bale(String path,String smaliPath) {
		bale(path,smaliPath,null);
	}
	public void bale(String smaliPath,String path,SmaliApkToolsPath inter) {
		String[] args =new String[] {"b","-f",smaliPath,"-o",path};
		for (String string : args) {
			System.out.print(string+" ");
		}
		try {
			Main.main(args);
			if(inter!=null) {
				inter.smaliPath(path);
			}
		} catch (Exception e) {
			// TODO: handle exception
			e.printStackTrace();
			if(inter!=null) {
				inter.smaliPath("error");
			}
		}
	}
	List<String> list;
	public void setFilter(List<String> list){
		this.list=list;
	}
}
