Page tree

Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

Code Block
languagejava
themeEmacs
titleimport
linenumberstrue
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.*;
import java.util.zip.InflaterInputStream;


@RequestMapping(value = "/importDoc", method = RequestMethod.POST)
@ResponseBody
public Map<String, Object> importDoc(@RequestParam("file") MultipartFile importFile) throws IOException {
	static String ROOT_PATH = "C:\\workspace\\synapEditorsample\\out\\artifacts\\synapEditorsample_war_exploded";
	static String DOC_UPLOAD_DIR = "uploads\\docs";
	static String OUTPUT_DIR = "uploads\\output";

    String fileName = importFile.getOriginalFilename();

	String uploadPath = ROOT_PATH + File.separator + DOC_UPLOAD_DIR;
	File uploadDir = new File(uploadPath);
	if(!uploadDir.exists()) {
    	uploadDir.mkdirs();
	}

	byte[] bytes = new byte[0];
	try {
	    bytes = importFile.getBytes();
	} catch (IOException e) {
    	e.printStackTrace();
	}
	Path inputFilePath = Paths.get(uploadPath + File.separator + fileName);

	try {
    	Files.write(inputFilePath, bytes);
	} catch (IOException e) {
    	e.printStackTrace();
	}
	Calendar cal = Calendar.getInstance();
	String yearMonth = String.format("%04d%02d", cal.get(Calendar.YEAR), cal.get(Calendar.MONTH)+1);
	// 파일별로 변환결과를 저장할 경로 생성
	String uuid = UUID.randomUUID().toString();

	File worksDir = new File(ROOT_PATH + File.separator + OUTPUT_DIR + File.separator + yearMonth + File.separator + uuid);
	if(!worksDir.exists()) {
	    worksDir.mkdirs();
	}

	// 문서 변환
	executeConverter(inputFilePath.toAbsolutePath().toString(), worksDir.getAbsolutePath());

	// 변환이 끝난 원본파일은 삭제한다.
	Files.delete(inputFilePath);

	Integer[] serializedData = serializePbData(worksDir + File.separator + "document.word.pb");

	Files.delete(Paths.get(worksDir + File.separator + "document.word.pb"));

	Map<String, Object> map = new HashMap<>();
	map.put("serializedData", serializedData);
	// 브라우저에서 접근가능한 경로를 importPath에 담아서 넘겨줍니다.
	map.put("importPath", "uploads/output/" + yearMonth + "/" + uuid);

	return map;
}


protected static int executeConverter(String inputFilePath, String outputPath) {
	String SEDOC_CONVERT_DIR = "C:\\sedocConverter\\sedocConverter.exe";
	String FONT_DIR = "C:\\sedocConverter\\sedocConverter\\fonts";
	String TEMP_DIR = "C:\\sedocConverter\\sedocConverter\\tmp";

	File tempDir = new File(TEMP_DIR);
	if(!tempDir.exists()) {
		tempDir.mkdirs();
	}

	File fontDir = new File(FONT_DIR);
	if(!fontDir.exists()) {
		fontDir.mkdirs();
	}
        
	// 변환 명령 구성
	String[] cmd = {SEDOC_CONVERT_DIR, "-f", FONT_DIR, inputFilePath, outputPath, TEMP_DIR};
	try {
            Timer t = new Timer();
            Process proc = Runtime.getRuntime().exec(cmd);

            TimerTask killer = new TimeoutProcessKiller(proc);
            t.schedule(killer, 20000); // 20초 (변환이 20초 안에 완료되지 않으면 프로세스 종료)

            int exitValue = proc.waitFor();
            killer.cancel();

            return exitValue;
	} catch (Exception e) {
            e.printStackTrace();
            return -1;
	}
}

 
public Integer[] serializePbData(String pbFilePath) throws IOException {
    List<Integer> serializedData = new ArrayList<Integer>();
    FileInputStream fis = new FileInputStream(pbFilePath);

    Integer[] data = null;

    fis.skip(16);

    InflaterInputStream ifis = new InflaterInputStream(fis);

    byte[] buffer = new byte[1024];

    int len = -1;
    while ((len = ifis.read(buffer)) != -1) {
        for (int i = 0; i < len; i++) {
            serializedData.add(buffer[i] & 0xFF);
        }
    }

    data = serializedData.toArray(new Integer[serializedData.size()]);

    ifis.close();
    fis.close();

    return data;
}


private static class TimeoutProcessKiller extends TimerTask {
    private Process p;

    public TimeoutProcessKiller(Process p) {
        this.p = p;
    }

    @Override
    public void run() {
        p.destroy();
    }
}

...