반응형
블로그 이미지
개발자로서 현장에서 일하면서 새로 접하는 기술들이나 알게된 정보 등을 정리하기 위한 블로그입니다. 운 좋게 미국에서 큰 회사들의 프로젝트에서 컬설턴트로 일하고 있어서 새로운 기술들을 접할 기회가 많이 있습니다. 미국의 IT 프로젝트에서 사용되는 툴들에 대해 많은 분들과 정보를 공유하고 싶습니다.
솔웅

최근에 올라온 글

최근에 달린 댓글

최근에 받은 트랙백

글 보관함

카테고리


반응형

오늘은 PDF 파일에 있는 내용을 가져와서 브라우저에 텍스트로 뿌려 주는 것을 공부해 보겠습니다.

저희가 만든 웹앱에 식당 메뉴를 제공하려고 하는데요.
식당을 운영하는 회사에서 메뉴를 PDF 형식으로 그 회사 웹에서 제공하고 있어요.


그런데 회사사람들 대부분이 블랙베리 폰을 사용하고 있어서 구형 BB 에서는 PDF 형식을 보여주기가 힘들거든요.


그 회사랑 따로 EDI 시스템 개발해서 데이터 주고 받고 하는 번거로운일을 하지 않고 그냥 그 회사에서 제공하는 메뉴에서 우리가 필요한 데이터만 추출해서 서비스하는 방법을 고민중입니다.


일단 인터넷 서핑을 통해서 PDF 를 TEXT 로 바꿔주는 소스코드는 구했습니다.

이 소스코드를 한번 분석해 보고 어떤 방법이 있을지 없을지 알아보려구요.




메뉴는 이렇게 생긴 PDF 파일인데요.

왼쪽의 내용들은 필요 없고 오른쪽에 있는 요일별 메뉴들만 뽑고 싶거든요.


원본 pdf 파일과 이 내용을 text 로 바꿔주는 PHP 파일은 여기 있습니다.



original.pdf

pdf2text.php


이걸 돌리면 결과가 아래와 같이 나옵니다.



흠 다 텍스트로 나오긴 나왔는데 이거 가지고는 따로 메뉴만 추출해 내기 쉽지 않네요.

이렇게 모두 한줄로 나오는게 아니라 라인별로 따로 출력이 돼면 좀 더 낫지 않을까요?


일단 pdf2text.php 를 분석해 봐야 겠습니다.


pdf2text.php 파일 안에는 9개의 함수가 있습니다.



이 pdf2text.php 를 실행하면 제일 먼저 어떤게 실행될까요?

함수들은 어디서 호출을 해 줘야 실행되니까 다 그냥 건너뛰겠고...

$result = pdf2text ('original.pdf'); 가 제일 먼저 실행되겠죠?


이건 pdf2text($filename) 함수를 call 하는 겁니다. 거기서 처리된 값을 $result 변수에 담고 그 내용을 echo 함수로 브라우저에 뿌려주는게 이 프로그램이 하는일의 전부 다 입니다.


이제 그 중간의 처리 과정을 자세히 공부해 보겠습니다.


우선 pdf2text($filename) 함수는 아래와 같습니다.


function pdf2text($filename) {
// file_get_contents return the contents of a file as a string
    $infile = @file_get_contents($filename, FILE_BINARY);
    if (empty($infile))
        return "";

    $transformations = array();
    $texts = array();

    preg_match_all("#obj(.*)endobj#ismU", $infile, $objects);
    $objects = @$objects[1];
   
   

    for ($i = 0; $i < count($objects); $i++) {
        $currentObject = $objects[$i];
//echo $currentObject . "<p> end";
        if (preg_match("#stream(.*)endstream#ismU", $currentObject, $stream)) {
            $stream = ltrim($stream[1]);
//echo $stream . "<p> end";
            $options = getObjectOptions($currentObject);
            if (!(empty($options["Length1"]) && empty($options["Type"]) && empty($options["Subtype"])))
                continue;

            $data = getDecodedStream($stream, $options);
            if (strlen($data)) {
                if (preg_match_all("#BT(.*)ET#ismU", $data, $textContainers)) {
                    $textContainers = @$textContainers[1];
                    getDirtyTexts($texts, $textContainers);
                } else
                    getCharTransformations($transformations, $data);
            }
        }
    }

    return getTextUsingTransformations($texts, $transformations);
}

맨 처음으로는 해당 파일의 내용을 받아옵니다. 이것은 바이너리 형식이라서 사람이 읽을 수 있는건 아닙니다. ($infile = @file_get_contents($filename, FILE_BINARY);)

그 내용을 출력해 보면 아래와 같이 나옵니다.



이걸 보면 헤더정보만 사람이 읽을 수 있는 텍스트죠?

이 문서는 PDF 1.5 버전이라는 것을 알 수 있습니다.

그리고 이 헤더정보는 endobj 부분에서 끝나는 겁니다.
나머지는 사람이 읽을 수 없는 바이너리 형식입니다.

그 다음 if 문에서는 해당 파일이 비어있는건지 봅니다. 비어있으면 나머지 로직을 실행할 필요가 없겠죠? 괜히 시간만 낭비니까 그 cost 를 줄이기 위해 비어있으면 그냥 return 을 해 버립니다.


파일이 empty 가 아니면 그 다음을 실행할 텐데요.

(참고로 if 문의 {} 가 없습니다. 그 안에 내용이 단 1줄이면 {} 없이 사용할 수 있습니다.

그러면 바로 그 다음줄까지만 if 절 안에 포함돼 있는 겁니다.)


그 다음은 $transformations 라는 배열과 $texts 라는 배열을 만들어 줍니다.


오늘은 여기까지만 하고 다음에 계속 분석해 보겠습니다.

지금 토요일 아침 7시 40분인데요.

가족이랑 어디 가기로 해서 지금 나가봐야 되네요.


여행 다녀와서 계속 공부할텐데 그 내용도 여기 정리해 놓을께요.



반응형


반응형
그동안 Eric Sarrion 이라는 분이 만든 http://the-jquerymobile-tutorial.org/ 라는 웹사이트에 있는 jQuery Mobile tutorial 로 공부 했었습니다.

Part 2 부분인 JavaScript Programming 부분을 완전히 끝냈는데요.

(관련 글들은 JQM tutorial 코너에 있습니다. 여기로 가시면  관련 글들을 보실 수 있습니다.


앞으로도 계속 jQuery Mobile 공부는 이어 가겠지만 이젠 Sencha Touch 쪽에 좀 더 신경을 쓸까 합니다.


Eric Sarrion 은 제가 알기로 프랑스 사람인 것으로 아는데요.

jQuery Mobile Tutorial 책을 저술 했고 관련 내용을 안드로이드와 iOS 애플리케이션으로 만들어서 보급하고 있습니다.


저는 그 중에서 jQuery Mobile 과 자바스크립트로 프로그래밍하는 부분을 다룬 Part 2 부분을 공부한 겁니다.


Eric Sarrion 에게 감사드리고 여러분들도 마켓에 있는 Eric Sarrion 의 jQuery Mobile Tutorial application 을 많이 사 보시기 바랍니다. 가격은 1불 입니다.


일단 목표했던 jQuery Mobile 튜토리얼도 2012년을 마감하면서 완료 됐네요.

2013년 새해도 기분 좋게 시작됐습니다.

새해 첫날 올린 글에 Daum View의 Best 글에도 선정되고...

대서양 해돋이를 보고 글과 그림을 올렸는데 2000분이 넘는 분들이 보셨네요.


이제는 Sencha Touch 를 공부해 보려고 하는데요.


너무 오랫동안 손을 놔서 다 잊어 버렸습니다.

그래서 일단 제가 예전에 올린 Sencha Touch 관련 글들을 보면서 공부하려고 합니다.


예전에 센차터치 관련해서 24개의 글을 올렸었네요.

그 글을 읽으면서 계속 이어서 할지 아니면 jQuery Mobile 에서 했던 것 처럼 어떤 Tutorial 싸이트를 찾아서 공부를 진행할지 결정할 생각입니다.


제 글을 보면서 공부하고 직접 실습도 하고 있는데요.

만든 소스 파일은 얼마전 웹 호스팅을 받은 서버에 올려놓고 있습니다.

도메인 주소도 받았는데요.



주소는  ...... (잠시 폐쇄했습니다. )입니다.

(Sencha Touch 는 구글 크롬 브라우저에서 실행해야 제일 잘 되더라구요.)


이 글을 쓰는 시점엔 http://coronasdk.tistory.com/88 글과 http://coronasdk.tistory.com/167 글에 있는 소스코드를 실습해 보고 올려 놨습니다.


그 사이에 http://coronasdk.tistory.com/157 부터 이어지는 4회에 걸친 Sencha Touch 로 앱 만들기 예제들이 있는데요.

그 글을 쓸 때도 잘 안됐는데 이번에도 잘 안되더라구요.

뭐가 잘 못 된건지..

혹시 그 글에 나온 소스코드 제대로 실행되시는 분들은 소스코드 좀 공유해 주시면 감사하겠습니다.


그러면 앞으로도 계속 이어지는 Sencha Touch 관련 글들과 또 다른 Cross Platform Mobile Application 개발에 필요한 여러 테크닉들 관련 글들에 많은 관심 부탁 드려요. ^^



반응형


반응형

2013년 들어서자마자 날씨가 추워집니다.

아침에는 화씨로 9도까지 내려간다고 하는데 섭씨로는 영하 12도 쯤 되나보네요.

제가 있는 곳은 한국하고 날씨가 비슷합니다.

한국도 지금 이만큼 춥죠?


오늘은 한파를 대비하라는 아파트 관리사무소의 안내문을 가지고 영어 공부를 해 보겠습니다.



Warning! Freeze Notice


Dear Residents,

입주자 여러분


Due to the predicted severe freezing weather anticipated for this weekend, water pipes in our community are at risk of freezing. Certain precautions are essential in order to avoid damage to your apartment home and those that surround you. Please take the following precautions as soon as possible.


이번 주말까지 한파가 예보되고 있습니다. 우리 커뮤니티 내의 수도관이 얼어서 파열될 위험이 있습니다. 여러분 아파트 내의 피해가 없도록 주의를 당부 드립니다. 아래 주의사항들을 따라 주시기 바랍니다.






1. Run a drip of water from all of the faucets in your apartment home. Run both the hot and cold water at a steady drip. Leave the faucets dripping until we remove the Freeze Alert signs at the entrances to the property.


1. 집안 내 모든 수도꼭지에서 물방울이 떨어지도록 살짝 틀어 놓아 주세요. 냉수와 온수 모두 계속 물이 나오도록 해 주세요. 입구에 한파 주의보 sign 이 없어질 때까지 수도꼭지를 살짝 열어서 물방울이 떨어지도록 해 주세요.



2. Adjust your thermostat to no lower 60 degrees. Open all closet and cabinet doors to expose plumbing fixtures to the warm air.


2. 집안 내 기온이 60도 이하로 내려가지 않도록 유지해 주세요. 그리고 옷장이나 캐비넷 문도 열어서 그 안에 설치된 배관시설들이 따뜻한 공기에 노출되도록 해 주세요.



3. If you know that one of your neighbors is away, please contact the Rental Office so we can protect their home. (It is always a good idea to notify the Rental Office if you will be away.)


3. 만약 이웃중에 장기 출타중인 분이 계시면 사무실에 알려 주세요. 그러면 저희들이 그 이웃분 집에 피해가 없도록 조치를 취하겠습니다. (여러분도 장기 출타하시게 되면 저희 사무실에 알려주시면 감사하겠습니다.)



4. Make necessary accommodations for any pets.


4. 애완동물들에게도 피해가 없도록 조치를 취해주시기 바랍니다.



Please remember, the management company is not responsible for any losses incurred from water, windstorm, freezing weather, etc. We recommend that each of our residents maintain renter’s insurance for coverage of damage to personal belongings.


관리회사는 water, 폭풍, 한파 등과 관련해 발생하는 손실에 대한 책임이 없음을 인지해 주시기 바랍니다. 저희는 입주자 여러분들에게 사유물에 피해가 있을 경우를 대비한 입주자 보험에 가입할 것을 추천드립니다.



Thank you for your prompt attention.

감사합니다.


faucet : : a fixture for drawing or regulating the flow of liquid especially from a pipe
<don't forget to turn off the faucet>



thermostat : an automatic device for regulating temperature (as by controlling the supply of gas or electricity to a heating apparatus); also : a similar device for actuating fire alarms or for controlling automatic sprinklers
<I set the thermostat to 68 degrees.>





반응형