/*-
 * ~~~~~~licensing~~~~~~
 * base-support
 * ==========
 * Copyright (C) 2020 - 2025 EmDev LLC
 * ==========
 * You may not use this file except in accordance with the License Terms of the Copyright
 * Holder located at: https://entaxy.ru/eula . All copyrights, all intellectual property
 * rights to the Software and any copies are the property of the Copyright Holder. Unless
 * it is explicitly allowed the Copyright Holder, the User is prohibited from using the
 * Software for commercial purposes to provide services to third parties.
 * 
 * The Copyright Holder hereby declares that the Software is provided on an "AS IS".
 * Under no circumstances does the Copyright Holder guarantee or promise that the
 * Software provided by him will be suitable or not suitable for the specific purposes
 * of the User, that the Software will meet all commercial and personal subjective
 * expectations of the User, that the Software will work properly, without technical
 * errors, quickly and uninterruptedly.
 * 
 * Under no circumstances shall the Copyright Holder or its Affiliates is not liable
 * to the User for any direct or indirect losses of the User, his expenses or actual
 * damage, including, downtime; loss of bussines; lost profit; lost earnings; loss
 * or damage to data, property, etc.
 * ~~~~~~/licensing~~~~~~
 */
package ru.entaxy.platform.base.support;

import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.Calendar;

import org.apache.commons.codec.digest.DigestUtils;

public class FileUtils {

	public static class FileHelper {
	
		protected File file = null;

		protected String fileMd5Hash = "";
		
		protected String md5FilePath = "";
		protected String currentMd5 = null;
		
		protected String timestampFilePath = "";
		protected String currentTimestamp = null;
		
		public FileHelper(String filePath) {
			this(new File(filePath));
		}
		
		public FileHelper(File file) {
			this.file = file;
			this.md5FilePath = file.getAbsolutePath().concat(".md5");
			this.timestampFilePath = file.getAbsolutePath().concat(".timestamp");
		}
		
		public boolean isReadable() {
			return file.exists() && file.canRead(); 
		}

		protected String calcMd5() {
			if (!CommonUtils.isValid(this.fileMd5Hash))
				try {
					this.fileMd5Hash = DigestUtils.md5Hex(this.file.toURI().toURL().openStream());
				} catch (MalformedURLException e) {
					e.printStackTrace();
				} catch (IOException e) {
					e.printStackTrace();
				}
			return this.fileMd5Hash; 
		}
		
		protected String readMd5() {
			if (this.currentMd5 == null)
			try {
				this.currentMd5 = Files.readString((new File(this.md5FilePath)).toPath());
			} catch (IOException e) {
				this.currentMd5 = ""; 
			}
			return this.currentMd5;
		}
		
		public boolean isChanged() {
			return !CommonUtils.isValid(this.readMd5()) || !this.readMd5().equals(this.calcMd5());
		}

		public String getTimestamp() {
			if (this.currentTimestamp == null)
				try {
					this.currentTimestamp = Files.readString((new File(this.timestampFilePath)).toPath());
				} catch (IOException e) {
					this.currentTimestamp = ""; 
				}
			return this.currentTimestamp;
		}
		
		public String getMd5() {
			this.fileMd5Hash = "";
			return calcMd5();
		}
		
		public File getFile() {
			return file;
		}

		public String getFileMd5Hash() {
			return calcMd5();
		}

		public String updateMd5() {
			String result = getMd5();
			if (CommonUtils.isValid(result))
				try {
					FileUtils.string2file(result, md5FilePath);
					result = readMd5();
				} catch (IOException e) {
					result = null;
				}
			return result;
		}
		
		public String updateTimestamp() {
			String timestamp = Calendar.getInstance().getTimeInMillis() + "";
			String result = "";
			try {
				FileUtils.string2file(timestamp, timestampFilePath);
				this.currentTimestamp = null;
				result = getTimestamp();
			} catch (IOException e) {
				result = null;
			}
			return result;
		}
		
	}
	
	public static void string2file(String content, String filePath) throws IOException {
		string2file(content, new File(filePath));
	}
	
	public static void string2file(String content, File file) throws IOException {
		if (!file.exists())
			file.createNewFile();
		Files.writeString(file.toPath(), content);
	}
	
}
