2014년 12월 12일 금요일

lattax mac 설치

texmaker의 장점은 바로바로 이쁘게 볼수 있다 강추한다.

1.http://wiki.ktug.org/wiki/wiki.php/MacOSInstall
2.texmaker
  preference
  pdfLatTax "/usr/local/texlive/2014/bin/universal-darwin/pdflatex" -synctex=1 -interaction=nonstopmode %.tex
  check pdf built in viewer

3.한글을 쓰려면 1번을 한후에 아래처럼 패키지를 불러온다.
  \documentclass[11pt]{article}
  \usepackage{kotex}

2014년 11월 25일 화요일

octave head method

0.it is same as r head  use like this head(vector)
   it will display first 6 row.
   if its row smaller then 6 it will display size of row

1.make head.m file at your directory

head.m

2.paste below code

function head =  head(X)
    siz = size(X);
    line = 6;
    if siz(1,1) < 6
        line = siz(1,1);
    endif;

    head = X([1:line],:);
end

3.if you want always use this method check this link
http://resoliwan.blogspot.kr/2014/11/octave-add-load-path-permenatly.html


octave add load path permenatly


1.Add octaverc to your home path

cd ~
vi .octaverc

2.add path like below
addpath ("/Users/lee/util", "-begin");

2014년 11월 20일 목요일

Javascript Closures

원문 : http://jibbering.com/faq/notes/closures/

Introduction

Closure
 클로저는 자유 변수 와 그 변수들을 묶을수 있는 환경을 가지는 표현식(특히 함수)을 의미한다.

클로저는 ECMA 스크립트 중에서 가장 강력한 부분이다. 하지만 정확이 이해하지 않고서는 적절하게 사용하기 힘들다.
하지만 반대로 쉽게 생성할수 있으며 심지어 의도하지 않았을때도 사용될수 있다.(실수로)
그리고 클로저 사용은 잠재적으로 브라우저 실행 환경에서 좋지 않은 영향을 줄수있다.

그들의 단점을 커버하고 장점을 사용하기 위해서는 클로저 메커니즘에(작동하는 방) 대한 이해가 필요하다
클로저는 scope 의 identifier resolution(식별자 해석 후 선택) 에 많이 의존하는대 그말은 object 의 property resoultion(속성 해석 후 선택)에 의존한다는 말과 동일하다.

클로저를 간단이 설명해보면 ECMAscript 는 inner functions 을 사용할수 있다.
inner function 이란 다른 function안에 정의(function definition) 되거나 표현식(function express)으로 표현된 function 을 의미한다.

inner functions은 바깥 펑션(outer funciton)의 파라미터와 로컬 변수에 접근 할 수 있다.
클로저는 inner function 들이 outer function에 접근할수 있다는 것으로 구현된다.
그말은 outer fuction 이 리턴된 후에도 실행 될수 있음을 의미한다. 즉 outer function의 리턴후에도 로컬 변수와 파라미터에 접근 할수 있음을 의미한다. 이 로컬 변수와 파라미터들은 outer function이 리턴될 떄믜 값을
가지고 있으며 inner function 으로 조작할수있다.

불행이도 클로저를 이해하기 위해서는 클로저가 내부적으로 어떤 메커니즘을 사용하는지를 이해해야 한다.
기술적으로 꽤 복잡하다. ECMA 262 명세의 알고리즘은 조금전에 설명한 부분을 조금 이해하기 힘들게 할수도 있지만
쉽게 단순화 시켜 설명할수 없다.

객체 속성 해석(object property name resoultion)에 대해 잘알고 있는 사람은 아래 섹션을 넘어가고 밑에 부분의 보면된다.

오브젝트 속성 이름 해석
(The resolution of property names on objects)

Ecmap Script 는 크게 Native object 와 Host Object 2가지로 구성되어 있다.
native object 의 하위 카테고리에는 Built-in object(이미 구현되어 있는 객체)다

Native object 는 언어에 종속되어 있으며 host object는 환경에의해(브라우저, node.js) 제공된다. 예를 들면 (doc obj or Dom node 같은 애들)

Native object 는 이미 정의된 속성들을 가지고 있으며 필요시 동적으로 정의할수 있다.(구현체에 따라 동적으로 정의 할수 없을수도 있다. 하지만 별 상관없다.);

object 에 정의된 속성들은 value 을 가질수도 있다. 값은 다른 객체의 reference 일수도 있고 primitive 값일수도 있다.
(primitive type 은 String, number, Boolean, Null, Undefiend 가 있고 Undefiend가 값이라면 속성은 정의 되었지만 값은 아직 할당되지 않은 상태를 의미한다. )

아래는 object 에 속성이 어떻게 정의 될수 있는지를 표현한다.

Assignment of values
객체의 속성들은 새로 생성될수도 있고 이미 존재하는 속성에 값을 할당할수도 있다.

var objectRef = new Object(); //javascript object 객체를 생성하고

testNumber 속성을 생성해보자

objectRef.testNumber = 5;
// 또는
objectRef["testNumber"] = 5;

javascript object 는 prototype 을 가지고 있으면 그들은 object 일수도 있다 또한 그 오브젝트안에 속성들이 존재할수도 있다 하지만 이부분은 변수 배정에는 아무런 영향을 끼치지 못한다.

속성에 값을 배정할때 실제 객체에 해당 속성이 존재하지 않는다면 속성이 생성되고 값이 배정된다.
만약 존재한다면 해당 속성의 값을 재설정한다.

Reading of Values

속성의 값을 읽을때 prototype이 영향을 미친다.
만약 속성 접근자에서 사용된 속성의 이름이 객체에 존재한다면 그값이 리턴된다.

/* 객체의 속성값에 값을 할당할때 만약 해당 속성이 존재하지 않는다면 생성하고 배정한다.
그러므로 값을 할당 후에는 해당 속성이 생성되어 있다 */
objectRef.testNumber = 8;

/*속성에서 값읽기*/
var val = objectRef.testNumber;
/* val은 객체 속성에서 읽어드린 8 값을 가지고 있다. */

하지만 모든 객체들은 prototype 을 가지고 있으며 prototype에 할당된 객체들도 prototype을 가지고 있을수 있다
그러므로 prototype chian 이라는걸을 구현한다.
prototype chain은 체인의 마지막의 객체가 null을 prototype으로 가지고 있으면 종료된다.
Object 생성자는(constructor) 기본적으로 null prototype을 가지고 있다 .


var objectRef = new Object(); //javascript object 만들기

위의 오브젝트는 Object.prototype을 prototype 으로 가지고 생성되었다
Object.prototype 의 prototype은 null임으로 ObjectRef 의 prototype chain 은 오직하나의 Object(Object.prototype)를 가지고 있다

하지만 아래를 보자

/*MyObject1 type의 object를 만드는대 사용하는 생성자 함수*/
function MyObject1(formalParameter){
 /*생성된 오브젝트에 - testNumber - 라는 속성을 할당하고 생성자에 넘겨진 첫번째 arg로 값을 할당함
 */

 this..testNumber = formalParameter;
}

/* MyObject2 type의 object 를 만드는대 사용하는 생성자 함수*/
function MyObject2(formalParameter){
 /* 생성된 오브젝트에 -testString -라는 속성을 할당하고 생성자에 넘겨진 첫번째 arg로 값을 할당함
 this.testString = formalParameter;
}

/* MyObject2의 default prototype 에 MyObject1을 할당하며 이때 MyObject에 8을 arg로 넘겨
   testNumber 를 8로 할당
*/

MyObject2.prototype = new MyObject1(8);

/* MyObject 를 생성하고 해당 오브젝트를 objectRef 에 넘긴다 이때 MyObject2 의 "String_value"를 넘겨
   testString 을 "String_value"로할당
*/

var objectRef = new MyObject2("String_Value");

objectRef 에 할당된 MyObject2 instance는 prototype chain 을 가지고있다
chain 의 첫번째는 MyObject1 instance다
MyObject 1 의 prototype 은 기본적으로 Object.prototype 이며
Object.prototype 의 prototyp은 null prototype을 가지고 있다
즉 MyObject2 아래와 같은 prototype chain 이 만들어진다.
MyObject1->Object->null

property accesor(프로퍼티 접근자)가 objectRef 의 속성에 접근할때는 모든 prototype chian 이 process에
들어옴니다.
var val = objectRef.testString;

위의 경우 MyObject2 가 testString 을 가지고 있음으로 val 에 "Sring_Value"가 할당됨니다.
하지만

var val = objectRef.testNumber;

를 하게 될경우 MyObject2에는 해당 속성이 없음으로 객체의 prototype 을 검삼합니다. MyObject1 에 testNumber가 있음으로 찾아서 8로 변수를 할당함니다.

var val = objectRef.toString;
의 경우 MyObject1, MyObject2 모두 속성값을 가지고 있지 않으면 prototype chain을 따라 올라감니다. Object 가 toString 을 가지고 있음으로 해당 함수고 리턴됨니다.


var val = objectRef.madeUpProperty
undefiend 가 할당됩니다. 왜냐하면 모든 prototype chian 을 조사해도 존재하지 않기 때문입니다.(순서대로 조사하다 마지막 null 에 도착하면 찾기가 종료됩니다.)

값을 읽을때는 첫번째로 찾은 값이 리턴됩니다.(체인에서 앞쪽에 있는 객체의 속성값)
하지만 값을 할당할때 해당 속성이 해당객체(prototype chain 제외)존재하지않는다면 해당 속성을 생성합니다.

즉 objectRef.testNumber = 3 를 하게 될경우 MyObject2의 인스턴스에 testNumber 가 만들어지고 값이 3으로 설정됩니다

추후의 접근 모두 My object2에 접근하게 되고  prototype chain은 더이상 검사되지 않습니다.
하지만 MyObject1.testNumber 는 8로 변경되지 않은체 존재하고 있습니다.
위와 같은 상황을 mask 라고 합니다.

ECMAScript 는 내부적  [[prototype]]을 Object type의 property로 할당합니다.
이 내부적 [[prototype]]은 script에서 접근할수 없습니다. 하지만  property accessor resoultion을 할경우
사용됩니다. 또한 object.prototype은 변경 할수 있으며 prototype 관련 접근 문제에는 object.prototype 과
object.[[prototype]]이 두개가 사용됩니다.

Identifier Resolution, Execution Contexts and scope chains
(식별자 해석, 실행 Contexts 그리고 scope chain)

The Execution Context
An executin context 는 ECMAScript의 구현체에 필요해서 사용되는 추상 사상이다(abstract concept).
명세서는 execution context 가 어떻게 구현되어 있어야 된다는 정의 되어 있지 않다. 하지만 execution context 는
명세에서 정의된 구현체(structure)를 위해서 몇개의 속성을 가져야한다.
그러므로 execution context 는 몇개의 공개되지 않는 속성을 가진 object 로 구현된다.

모든 javascript 코드는 execution context에서 실행된다. Global code는 globla execution context 에서 실행된다. 또한 호출되는 모둔 함수들은(constructor 포함)연관된 execution context 를 가진다.
eval 함수의 경우 다른 execution context 를 가진다. 하지만 일반적으로 사용하지 않음으로 여기에서는 다루지 않는다.
ECMS 262(3rd edition)의 10.2 절에  execution context 에 대한 정의가 있다.

javascript 함수가 호출되면 execution cotext 안에 들어온다. 만약 새로운 함수가 호출되면(같은 함수가 재귀적으로 호출되어도) 새로운 execution context 가 만들어지고 함수가 호출되는 동안 새로이 생성된 execution context 안에 들어온다. 그러므로 javascript  code 의 실행은 execution context stack 형태로 구현된다.

execution context 가 생성될때 정해진 순서대로 여러가지가 일이 이루어진다.
첫번쨰로 function 의 exectution context 에 Activation object가 생성된다.  activation object 의 매커님즘은 아래와 같다. 이건 몇개의 속성을 가진 오브젝트다 하지만 prototype을 가지지않는다(at least not a defiend prototype) 또한 javascript 코드에서 직접적으로 접근할수 없다.

두번째로 arguments를 만든다. 해당 함수 호출에 같이 넘겨진 arg들을 array 비슷한 객체에(integer index)로 접근가게 하여 만든다. 이것은 length 와 callee 속성을 가지고 있다

Activation object 는 arguments 속성을 만들고 좀전에 만들어진 arguments 를 속성의 값으로 할당한다

세번째로 execution context가 scope에 할당된다.
scope란 object 들이 연결된 리스트이다. 모든 function object 는 내부적으로 [[scope]] 속성을 가지고 있
다 [[scope]]속성또한 object들이 연결된 리스트로 구현되어 있다 execution context 에 할당된 스코프는
호출된 fuction이 가지고 있는 [[scope]] 의 속성 objects 리스트 맨앞에 activation object를 더한 거다

그후 variable instantation 이 ECMA262에서 "Varible" Object 라고 지칭하는 Object 를 사용해서 일어난다.
하지만 Activation object 가 Variable object 로 사용된다(Actiovation object 와 Variable Object는 동일한 Object 이다.)

함수에 넘겨진 parameter 별로 variable object에 속성을 만든다. 그후 argumnets 의 값을 동일한 해당 속성에 할당한다.
(없을 경우 undefiend 로 할당한다.)

ex) function aa(arg1, arg2, arg3) -> called aa(1,2) -> parameter arg1 = 1, arg = 2, arg3 = undefiend

그후 innerfunction definition으로 fuction object 를 생성하고 fuction 이름을 속성으로 하여 생성된 function object 를 할당한다. 마지막으로 함수안에 정의된 로컬 변수들을 variable object의 속성 이름을을 생성한다.
(이떄 로컬변수들은 undefiend 값이 할당된다.. 실제적인 로컬변수의 값은 함수의 body code 가 실행될때 변수에 할당된 expresstion 을 evaultion(평가)해서 할당된다. )

arguments 속성이 정의된 Activation Object가  함수의 로컬 변수가 정의된 Varaible Object 가 같은 객체이기 때문에 argumnets 식별자를 함수의 로컬 변수처럼 사용 할수 있다.

마지막으로 this keyword에 value 가 할당된다. 만약 object 가 할당된다면 this는 그 object 를 지징하며 null이라면
Global object 를 지칭하게 된다.

Global execution context 의 경우는 조금 다르다 외냐하면 argumnets가 없기 때문에 activation object를 정의할 필요가 없다 또한 scope chain은 정확이 하나의 global object 로 구성되어있다 그후 variable instantiation 단계를 실행한다. Global object를 Variable Object 로 사용한다  이렇기 때문에 global 에 선언한 함수들이 Global object 의 속성이 되는 이유이다. 또한 속성도 마찬가지이다.

도한 global execution context 에서 this 키워드는 global object 를 가리킨다.

scope chains and [[scope]]
execution context 에 할당되는 scope chain은 호출된 함수의 [[scope]]속성 맨앞에 execution context의 Activation /variable object 를 더해서 만들어진다.
그러므로 함수의 [[scope]] 속성이 어떻게 정의 되었는지 아는 부분이 중요하다.

ECMAScript 에서 함수는 object 이다. function object 는 variable instantiation 단계에서 만들어지거나
함수 표현식을 평가(evalution) 또는 Fuction 생성자를 호출할때 만들어 진다.

Function construcotr 로 만들어진 Fuction object의 [[scope]] 속성은 global object 로만 구성되어 있다.

execution context 의 scope chain 을 가진 function declaration 또는 function expresssion 안에서 생성된 함수들은 그들의 [[scope]]  속성에 부모의 scope chain 을 할당 받는다.

global function declaraion 으로 간단한 예를 들어보자
function exampleFunction(formalParameter){
 // function body code
}

해당 함수는 globle execution context 의 variabl instantiation 단계에서 생성된다. global execution context 는 global object 로만 이루어진 scope chain 을 가지고 있음으로 해당함수의 [[scope]]속성에는
glbal object 로 만 이루어진 scope chain을 가지게 된다.

비슷하게 global 에 정의된 fuction expression 을 보자
var exampleRuncRef = function(){
 // functio body code
}

위와 같은 경우 global object 의 named property 가 vaiable instantiation 단계에서 만들어지지만
function object의 경우 생성되지 않고 해당 속성이 사용될때 만들어진다.

?하지만 함수의 생성이 global executio contxt 에서 일어나므로 [[scope]] 속성은 하나의 global object 로 구성된다.

아래는 inner function declaration 과 express 이 function object 내부에서 만들어지기 때문에 조금 상향된 scope chain 을 같는다. 아래의 코드를 생각해보자
내부에 innerfunciton 을 정의하고 outer function 을 실행하는 예제이다

function exampleOuterFunction(formalparamter){
 function exampleInterFunctionDec(){
  // inner function body
 }
 // the rest of the outer funciton body
}

exampleOuterFunction(5)

outerfuncion 의 경우 gloabl execution context 의 vairable instantiation 단계에서 생성되가 이때문에
[[scope]] 속성에 glolbal object 가 할당된다.

그후 글로벌에서 exampleOuterFunction 을 실행 시키면 새로운 execution context 가 생성된다.
그리고 Activaion/Variable object 순서가 차례로 실행된다. 이때 exampleOuterFuntion 의 scope 는 new Activiation object 를 exampleOuterFunction 의 [[scope]](global object 만존재) chain 앞에더해서 할당된다.

이때 outer funciton 의 varaible instatiation 단계에서 inner function definion 을 실행하게 되는대 이때
inner function의 [[scope]] 에 해당 execution context 의 scope 가 할당된다.

이때의 scope 는 outerfunciton 의 activation object -> global object 로 구성되어 있다.

위에 기술된 부분은 소스 코드를 실행할때 자동으로 실행된다.

execution context 의 scope chian 은 함수를 생성할때 [[scope]] 속성에 할당되며 함수의 [[scope]]속성은 execution context 의 scope 를 정의하게 된다. (물런 [[scope]] 속성앞에 activation object 를 함쳐서 )

하지만 ECMAScript 의 with 문은 scope chain 을 변경할수 있다.

with 문은 expression 을 실행시킨다. 만약 expression 이 object 라면 현재 execution context 의 맨압부분에
(Activaion/Variable Object 앞에) 해당 오브젝트를 추가한다.
with 문 블락이 실행된 후에는 좀전에 변경된 execution context를 원래대로 복원한다.

function declartion 의 경우 variable instantiaion 단계에서 생성되기 때문에 영향을 받지 않을수 있지만
function express 의 경우 with statement 안에서 evaution 되기때문에 영향을 받을수 있다.

/ obcjet 를 가리키는 y를 만든다.)
var y =  {x:5};
function exampleFuncWith(){
 var z;
 /* 좀전의 y object 를 context scope chain 앞에 붙인다.)
 with(y){
  /* function expression 을 실행 시켜 funciton object 를 만들고 local 변수 z에 할당한다.
  */

  z = function(){
   // inner function expression body
  }

 }
 ....
}

/*execute the exampleFuncWith */
exampleFuncWith();

exampleFUncWith 는 [[scope]] 로 global object 를 가지고 있다 이때 해당 함수를 실해하면 [[scope]]에 해당 Activation object 를 만들어서 앞에 붙이고 execute context 에 scope 를 할당한다
wish 문을 실행시키면 글로벌 object y를 scope chain 앞에 붙이고 안에 바디문을 실행한다.
그러므로 안에서 실행된 function expressein 의 [[scope]] 에는 y->outer activation obj->global obj가 할당된다.

그후 with 문의 블락이 끝나면 원래대로 scope chain 을 복귀한다 하지만 with 문의 블락안에서 생성된 함수 객체의 [[scope]]속성에는 y object 가 맨앞에 있다.

Idetifier Resolution
(식별자 해석)

식별자는 scope chain 에 대항해서 resolve 된다. ECMA 262 에서는 this 를 속성보다는 keyword 로 분류한다.
이말은 this 가 scope chain 을 참조하지 않고 실행되는 execution context에 따라 정의 됨을 의미한다.

식별자 해석은 scope chain 의 맨 앞부분에서 시작된다. 일단 식별자에 대응하는 해당 이름 속성이 정의되어있는 확인한다.
왜냐하면 scope chain 은 object의 chain 이기 때문이다. 일단 object 의 prototype chain 을 포함해서 확인한다.
만약 scope chain 의 첫번째 object 에서 해당 값을 찾지 못하면 다음 chain 의 object 로 넘어간다.
넘어가면서 찾거나 아니면 scope chain 이 끝날때까지 찾는다.

identifier opertaion 은 위에서 언급한 propery acessor  와 동일하다.
만약 object 가 scope chain 에서 식별 되었다는 것은 해당 속성이 오브젝트를 가지고 있다 property accesor 에서 그리고 식별자는 그 오브젝트의 속성처럼 행동한다.  글로벌 오브젝튼 언제나 scope chain 의 끝이다.


functio 호출과 연관된 exection contexts 는 chain 맨앞에 Activation/Varaible object 를 가지고 있을것이다.

funcito body 에서 사용된 식별자들은 효과적으로 파라미터와 내부 함수 정의 이름 또는 로컬 변수에 대해서 효과적으로 첫번째로 체크할수있다. 그것을 아마도 Activation/Varaible object 로 쉽게 resolve 될수도 있을것이다.

... 뒷부분은 그냥 읽었습니다. :)

다른 분의 번역 http://nodejs-kr.org/insidejs/archives/508

2014년 11월 17일 월요일

mongorestore single collection


  1. 싱글 컬랙션
    • 맨마지막에 파일까지 지정해주어야한다.
      mongorestore -d deployd -c spots spots/spots.bson
      
  2. 전체 디비
    • 디비명 폴더
      mongorestore -d deployd deployd/
      

2014년 11월 6일 목요일

ssh 키연결

ssh 서버 설정하기(리무트)
[서버에서]
/etc/ssh/sshd_config
HostKey /etc/ssh/ssh_host_rsa_key
HostKey /etc/ssh/ssh_host_dsa_key


RSAAuthentication yes
PubkeyAuthentication yes
AuthorizedKeysFile      .ssh/authorized_keys
//RSAAuthentication, PubkeyAuthentication을 허용하며  각 유저의 .ssh/authorized_keys 파일에
공개키를 저장하겠음

PasswordAuthentication yes
위에 실패할경우 패스워드 접속을 하겠음

* 옵션별 상세 설명
HostKey /etc/ssh/ssh_host_rsa_key
HostKey /etc/ssh/ssh_host_dsa_key
설명
Specifies a file containing a private host key used by SSH.  The
    default is /etc/ssh/ssh_host_key for protocol version 1, and
    /etc/ssh/ssh_host_dsa_key, /etc/ssh/ssh_host_ecdsa_key,
    /etc/ssh/ssh_host_ed25519_key and /etc/ssh/ssh_host_rsa_key for
    protocol version 2.

    사용이유
   To prevent man-in-the-middle attacks, each SSH server has a unique identifying code, called a host key. These keys prevent a server
   from forging another server’s key. If you connect to a server for the first time or if the server presets a different key then
   previously, WinSCP will prompt you to verify the key.

RSAAuthentication yes
RSA 인증을 설정. Protocol 1 에 적용

PubkeyAuthentication yes
공개키 인증 설정. Protocol 2에 적용

AuthorizedKeysFile
공개키 파일명 파일명을 지정
디폴트는 유저의 홈 디렉토리로부터의 상대 패스에서 AuthorizedKeysFile 에 설정되 있는 파일을 공개키 파일로 설

서비스 재시작
service sshd restart

로컬에서 키생성
[로컬에서]
ssh-keygen -t dsa
Enter file in which to save the key (/Users/lee/.ssh/id_dsa):  enter
이름을 지정하면 키 복사시 ssh-copy-id -i path/to/key_name.pub user_name@host_name
연결시 ssh -i path/to/key_name user@host
로 접속 해야 한다.



키 파일 서버에 올리기
[로컬에서]
scp -P 포트 로컬파일 리무트계정@리무트주소:리무트파일
scp -P 포트 .ssh/id_dsa.pub 리무트계정@리무트주소:.ssh/id_dsa.pub

서버에서 올라간 공개키를  authorized_keys 파일에 첨부하기
[서버에서]
없으면 만든다
touch authorized_keys
chmod 644 authorized_keys

존재하면 존재하는 파일에 새로 만든 공개키를 추가한다.
cat  test_dsa.pub >> authorized_keys

어떻게 동작하는지 알고 싶으면 아래 링크 확인
http://www.parkjonghyuk.net/lecture/modernCrypto/lecturenote/chap05.pdf

안될경우
  ssh -v
http://stackoverflow.com/questions/6377009/adding-public-key-to-ssh-authorized-keys-does-not-log-me-in-automatically

2014년 11월 4일 화요일

테스트 임베드 2

2014년 10월 30일 목요일

테스트 임베드

주말살이님의 여행 일정 2014-12-24 ~ 2014-12-24, 0박1일
부산 크리스마스 트리 문화축제!
부산에서 즐기는 색다른 크리스 마스!
아침에 거리를 나서면 입에서 입김이 폴폴 풍기는 계절, 드디어 겨울이 찾아왔다.
겨울하면 추워서 짜증도 아니만 그래도 내심 기대되는건 아마도 크리스마스 때문이 아닐까?
크리스마스를 제대로 즐기고 싶다면 아무래도 축제를 가는게 좋을 것이다.
부산에선 해마다 크리스마스 문화 축제가 열리고 있었다.
눈이 잘 오지 않는 남부지방에서 크리스마스 축제를 즐기라니... 좀 아리러니 하지만(?)
이번 부산 크리스마스 문화축제는 정말이지 다채로운 행사가 많이 마련되어 있다.
길거리 공연은 물론이고 보물찾기나 눈 보기가 드문 부산 시민들을 위해 인공눈을 뿌려주는 행사 등!
놓치기 아까운 이벤트들이 많다.
이러한 행사들은 주로 주말에 진행되니 주말을 부산여행과 함께 크리스마스 행사를 즐겨보는 것도 좋을듯!
[부산 크리스마스 트리 문화축제]
기간 : 2014.11.29(토)~2015.01.04(일)
장소 : 부산 중구 광복로 차없는거리 전역
주최 : 부산크리스마스트리문화축제준비위원회
요금 : 무료
[행사내용]
1. 찾아가는 보물찾기
광복로 거리 쇼윈도우,간판,트리장식물등의 일부분을 홈페이지에 올린뒤 축제 방문객들이 그것들을 찾아 
스마트폰을 찍어 퍼즐을 완성하면 소정의 상품을 증정!
* 축제 기간 중 2회 정도 주말을 이용해 실시
2. 트리를 밝혀라
설치된 전기자전거에 차례로 탑승하여 패달을 돌리면 생산된 전기가 트리를 밝히는 체험형 프로그램!
* 2014년 12월 둘째 주말 오후 6시 ~ 7시
3. 소망트리
여러개의 태그로 만든 트리에 소원을 적는 프로그램!
* 11월 29일~ 2013년 1월 4일
* 광복로 삼성매장 앞
4. 스노우 타임
눈이 보기 어려운 부산지역에 크리스마스 축제를 맞이하여 시간에 맞춰 인공눈을 뿌리는 행사!
* 11월29일 ~ 12월 31일 저녁 7시, 8시(10분씩)
* A구간의 눈 내리는 마을
        
여행 예산 KRW 0
항공료 숙박 음식
0 0 0
쇼핑 교통 입장료
0 0 0
오락 기타
0 0
1 일차 (2014.12.24)
여행국가 : 한국 1일 지출 비용 : KRW 0
광안리 해수욕장 (Gwangalli Beach) 자갈치시장 (Jagalchi Market) BIFF 광장, 구 PIFF 광장 (BIFF Square) 남포동 먹자골목 옥천국밥 남포동 나담
AM 10:30 -
1. 광안리 해수욕장 (Gwangalli Beach)

메모
부산하면 먼저 바다가 떠오르기 마련이다. 부산에 왔는데 바다를 안보고 갈 순 없으니 광안리에서 멋진 다리와 함께 바다를 감상해 보는 것도 좋을 듯 싶다. 부산 현지인들 또한 부산 바다는 여름보다 겨울이 좋고 해운대보다는 광안리를 많이 추천하고 있다!

[명소자세히보기]

PM 01:00 -
2. 자갈치시장 (Jagalchi Market)

메모
부산의 명물이기 때문에 한 번쯤은 꼭 들러줘야 하는 자갈치 시장! 남포동에 있어서 크리스마스 축제장소와 위치적으로도 가깝다. 하지만 잘 모르고 사면 바가지 쓸 수 있다고 하니 조심해야 한다.

[명소자세히보기]

PM 02:30 -
3. BIFF 광장, 구 PIFF 광장 (BIFF Square)

메모
부산국제영화제의 상징이라고 할 수 있는 곳! 길거리에는 유명 배우들과 감독들의 핸드프린트가 붙어있다. 또한 씨앗호떡 맛집도 많다고 하니 호떡 먹으면서 구경하는 것도 좋을 것 같다.

[명소자세히보기]

PM 04:00 -
4. 남포동 먹자골목

메모
남포동에서 또 유명한 먹자골목! 간단하게 떼우기 좋은 길거리 음식들이 한가득이다. 부산의 대표 길거리 음식인 비빔당면과 부산어묵, 그리고 씨앗호떡을 먹기위해 많이들 찾는 곳이다.

[명소자세히보기]

PM 05:00 -
5. 옥천국밥

메모
냉채족발, 밀면 등 유명한 부산 음식이 많지만 겨울이니까 돼지국밥을 선택하는 것도 괜찮을 것같다. 옥천 국밥은 남포동에서 유명한 돼지 국밥집! 추운데서 오래 돌아다녔으니 뜨끈한 돼지국밥으로 속을 달래보자!

[명소자세히보기]

PM 06:00 -
6. 남포동

메모
[광복로] 저녁이 되면 거리마다 걸려있는 화려한 크리스마스 조명과 하이라이트인 거대한 트리에 불이 들어오기 시작한다. 본격적으로 크리스마스 축제를 즐길시간! 1.2km에 달하는 긴 거리에 차가 진입하지 못하도록 막아놓고 축제가 진행된다고 한다. 또한 7시와 8시, 이렇게 두차례 인공 눈을 뿌려주기 때문에 이 시간에는 꼭 광복로로 집합해야 한다.

[명소자세히보기]

PM 09:00 -
7. 나담

메모
크리스마스 분위기와 어울리는 카페라서 추천하고 싶다. 아늑한 분위기와 엔틱한 느낌의 찻잔, 인테리어가 크리스마스 시즌에 들려보면 좋을만한 곳이다.

[명소자세히보기]

위시빈, 여행, 여행일정, 세계 여행, 지도, 길찾기, 관광, 자유여행, 맛집, 여행 가이드북, 위시빈 임베드, 해외여행, 일본일정, 일본여행, 유럽여행
일정자세히보기

2014년 10월 17일 금요일

iframe scrollTop

iframe 에서 스크롤 탑을 구할수 있는가? 구할 수 있다. :)

iframe javascript

 function listener(event){
          self.scrollTop = event.data;
          console.log('Message Received : '+event.data);
        }

parent script

<script  type="text/javascript"
    src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js">
</script>
<script type="text/javascript">
      var win = document.getElementById("myIframe").contentWindow;
      $(window).scroll(function(){
          var wintop = $(window).scrollTop();
          win.postMessage($(window).scrollTop(), 'http://localhost:4000');            
      });
</script>


참고
http://stackoverflow.com/questions/24656292/jquery-accessing-parent-document-scrolltop-from-iframe-and-sop

2014년 10월 12일 일요일

몽고디비2.6 샤딩

1.0 컨피스 서버용 디렉토리 만들기
cd test
mkdir log //로그용 디렉토리
mkdir configsvr
cd configsvr/
mkdir server1
mkdir server2
  mkdir server3

1.1 컨피그 서버 뛰우기
컨피그 서버는 총 3대를 뛰운다
컨피그 서버중 1대라도 죽으면 컨피그 서버의 메타 데이터는 읽기 전용이된다.
샤딩용 데이터 목록만 저장하고 있기 때문에 많은 자원을 소모하지 않는다.
옵션 --configsvr 는 --port 27019 --dbpath /data/configdb 를 추가하는 기능만 있음
덥어 쓸수 있음

구성 서버 데이터를 자주 백업 받고 유지보수 작업시에도 반드시 데이터를 백업 받자

mongod --configsvr --dbpath /test/configsvr/server1  --logpath /test/log/config_server_1 --fork --port 28001
mongod --configsvr --dbpath /test/configsvr/server2  --logpath /test/log/config_server_2 --fork --port 28002
mongod --configsvr --dbpath /test/configsvr/server3  --logpath /test/log/config_server_3 --fork --port 28003

1.2 몽고s 뛰우기
컨피그 서버가 뜬다음에 뛰울수 있다.

mongos --configdb 127.0.0.1:28001,127.0.0.1:28002,127.0.0.1:28003 --logpath /test/log/mongos_1 --fork --port 10000

1.3 이미 있는 복제셋 추가하기
mongo --port 10000
sh.addShard('rs0/127.0.0.1:27001,127.0.0.1:27002,127.0.0.1:27003')

sh.status()
--- Sharding Status ---
 sharding version: {
"_id" : 1,
"version" : 4,
"minCompatibleVersion" : 4,
"currentVersion" : 5,
"clusterId" : ObjectId("543a70e0e74f6e2fe12c8638")
}
shards:
{  "_id" : "rs0",  "host" : "rs0/127.0.0.1:27001,127.0.0.1:27002,127.0.0.1:27003" }
databases:
{  "_id" : "admin",  "partitioned" : false,  "primary" : "config" }
{  "_id" : "test",  "partitioned" : false,  "primary" : "rs0" }

1.4 mongos 가 뛰어 졌으면 샤드에 직접적으로 접속 하지 못하게 방화벽 규칙을 설정한다.
1.5 샤딩을 추가할떄는 빈 복제셋을 추가하면된다.
샤드 별로 다른 디비를 만들어서 추가 할수 도 있다.
이럴 경우 디비 별로 샤딩 된다.

1.6 테스트2 복제 셋을 만들어서 샤딩에 추가해보
디렉토리를 만들자
cd test
mkdir rs1
mkdir server1
mkdir server2
mkdir server3

mongod --port 29001 --dbpath /test/rs1/server1 --replSet 'rs1' --logpath /test/log/rs1_server_1 --fork
mongod --port 29002 --dbpath /test/rs1/server2 --replSet 'rs1' --logpath /test/log/rs1_server_2 --fork
mongod --port 29003 --dbpath /test/rs1/server3 --replSet 'rs1' --logpath /test/log/rs1_server_3 --fork

mongo --port 29001
var rsconfig = {"_id":"rs1", "members":[{"_id":1, "host":"127.0.0.1:29001"},{"_id":2, "host":"127.0.0.1:29002"},{"_id":3, "host":"127.0.0.1:29003"}]}

rs.initiate(rsconfig)

use test2
function insertTest(count){
for(var i = 0; i< count; i++){
db.test1.insert({a:i, b:i});
}
}

insertTest(1000);

> mongos 접속
sh.addShard('rs1/127.0.0.1:29001,127.0.0.1:29002,127.0.0.1:29003')

1.7 샤딩하기
디비를 샤딩한다.
> mongos 접속
use test
sh.enableSharding('test')db.enableSharding('test');

sh.status()
 databases:
{  "_id" : "admin",  "partitioned" : false,  "primary" : "config" }
{  "_id" : "test",  "partitioned" : true,  "primary" : "rs0" }
{  "_id" : "test2",  "partitioned" : false,  "primary" : "rs1" }

partitioned true 확인

1.8 컬랙션 샤딩하기
db.test1.ensureIndex({a:1})
샤딩 키에 인덱스가 없으면 에러가 발생한다.
sh.shardCollection('test.test1',{a:1})

function insertTest(count){
for(var i = 0; i< count; i++){
db.test1.insert({a:i, b:i});
}
}

insertTest(10000);
sh.status()
databases:
{  "_id" : "test",  "partitioned" : true,  "primary" : "rs0" }
test.test1
shard key: { "a" : 1 }
chunks:
rs1 1
rs0 1
{ "a" : { "$minKey" : 1 } } -->> { "a" : 0 } on : rs1 Timestamp(2, 0)
{ "a" : 0 } -->> { "a" : { "$maxKey" : 1 } } on : rs0 Timestamp(2, 1)
아래와 같이 청크가 샤딩 된걸 확일 할수 있다.





몽고디비2.6 리플리케이션

1.테스트용 디렉토리 만들기
1.1 컨피그 디렉토리 만들기
cd /
sudo mkdir /cofig
sudo chown lee /config

1.2 테스트 디비용 디렉토리 만들기
cd /
sudo mkdir /test
sudo chown lee /test
cd mkdir rs0

mkdir rs0
mkdir rs0/server1
mkdir rs0/server2
mkdir rs0/server3

1.3 레플리케이션 시작하기
mongod --port 27001 --dbpath /test/rs0/server1 --replSet 'rs0' --logpath /test/log/rs0_server_1 --fork
mongod --port 27002 --dbpath /test/rs0/server2 --replSet 'rs0' --logpath /test/log/rs0_server_2 --fork
mongod --port 27003 --dbpath /test/rs0/server3 --replSet 'rs0' --logpath /test/log/rs0_server_3 --fork

옵션 설명
--port
디비가 시작할 포트
--dbpath
디비가 위치할 디렉토리
--replSert
레플리케이션 이름
1.4 레플리케이션 설정하기
몽고 쉘로 접속해서 최초 레플리케이션을 init 한다.

mongo --port 27001
var rsconfig = {"_id":"rs0", "members":[{"_id":1, "host":"127.0.0.1:27001"}]}

rs.initiate(rsconfig)

*테스트를 위해 localhost ,127.0.0.1 을 지원하지만 다른 ip 와 섞어 쓰는건 안된다.

1.5 복제셋 맴버추가
rs.add("127.0.0.1:27002")
rs.add("127.0.0.1:27003")

1.6 복제셋 멤버제거
/*
rs.remove("127.0.0.1:27002")
*/

1.7 복세셋 멤버 확인
rs.config()
{
"_id" : "rs0",
"version" : 5,
"members" : [
{
"_id" : 1,
"host" : "127.0.0.1:27001"
},
{
"_id" : 3,
"host" : "127.0.0.1:27003"
},
{
"_id" : 4,
"host" : "127.0.0.1:27002"
}
]
}

_id : 복제셋 이름
verstion : 멤버를 추가할때마다

1.8 컨피그 변경이 가능함
/*
var reconfig = rs.config()
reconfig.members[1].host = '0.0.0.0:27003';
rs.reconfig(reconfig)
*/

1.9 세컨더리 접속
mongo --port 27002

2.레플리케이션 상태 확인

2.0 마스터에서 확인
mongo --port 27001
db.isMaster()
{
"setName" : "rs0",
"setVersion" : 5,
"ismaster" : true,
"hosts" : [
"127.0.0.1:27001",
"127.0.0.1:27002",
"127.0.0.1:27003"
],
"primary" : "127.0.0.1:27001",
"me" : "127.0.0.1:27001",
"localTime" : ISODate("2014-10-10T14:59:32.981Z"),
"maxWireVersion" : 2,
"minWireVersion" : 0,
"ok" : 1
}

2.1 마스터 : 예제 컬랙션 insert
use test

function insertTest(count){
for(var i = 0; i< count; i++){
db.test1.insert({a:i, b:i});
}
}

insertTest(1000);
db.test1.find();

2.2 마스터 : 레플리케이션 상태확인
rs.status()

*실제로 레플리케이션에 모든 복제가 완료 되었는지 확인하려면
optimeDate 가 동일한지 확인하면 된다.
{
"set" : "rs0",
"date" : ISODate("2014-10-10T15:04:57Z"),
"myState" : 1,
"members" : [
{
"_id" : 1,
"name" : "127.0.0.1:27001",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
"uptime" : 2331,
"optime" : Timestamp(1412953460, 1000),
"optimeDate" : ISODate("2014-10-10T15:04:20Z"),
"electionTime" : Timestamp(1412951411, 1),
"electionDate" : ISODate("2014-10-10T14:30:11Z"),
"self" : true
},
{
"_id" : 3,
"name" : "127.0.0.1:27003",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 924,
"optime" : Timestamp(1412953460, 1000),
"optimeDate" : ISODate("2014-10-10T15:04:20Z"),
"lastHeartbeat" : ISODate("2014-10-10T15:04:55Z"),
"lastHeartbeatRecv" : ISODate("2014-10-10T15:04:56Z"),
"pingMs" : 0,
"syncingTo" : "127.0.0.1:27001"
},
{
"_id" : 4,
"name" : "127.0.0.1:27002",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 893,
"optime" : Timestamp(1412953460, 1000),
"optimeDate" : ISODate("2014-10-10T15:04:20Z"),
"lastHeartbeat" : ISODate("2014-10-10T15:04:56Z"),
"lastHeartbeatRecv" : ISODate("2014-10-10T15:04:56Z"),
"pingMs" : 0,
"syncingTo" : "127.0.0.1:27001"
}
],
"ok" : 1
}

2.3 슬레이브 : 읽기 시도
db.test1.find()
error: { "$err" : "not master and slaveOk=false", "code" : 13435 }

몽고 디비에서 레플리케이션 셋의 기본 설정은 슬레이브에서 읽는게 안된다.
(슬레이브에서 읽을 경우 예전 데이터를 읽을수 있기 때문에)

어플리케이션에서 예전 데이터를 읽어도 상관없을때는
마스터 > rs.slaveOk()
슬레이브 읽기가 허용된다.

슬레이브 > db.test1.find(); 결과값이 리턴된다.

2.4 디비가 죽을 경우의 마스터 선출 작업
27001 디비를 죽인다. ctrl+c

슬레이브1 > rs.status()
현재 마스터 이며 member 의 27001 이 죽었음을 확인한다.
27001
"health" : 0,

mongod --port 27001 --dbpath /test/rs0/server1 --replSet 'rs0'
다시 시작한다.

슬레이브1 > rs.status()
좀전의 27001 이 정상동작 하는지 확인
27001
"health" : 1,

* 3 대중 2대가 살아 남을 경우 투표를 통해 하나의 슬레이브를 마스터로 승격 시킨다.
투표를 하기위해서는 과반수가 살아 있어야 한다.
ex)3 대 이면 2대, 4 대이면 3대 ...

* 과반수가 살아 있지 않는다면 투표를 할수 없기 때문에 secondery 상태가 유지된다.
why? 과반수 인가?
a, b 데이터 센터에 몽고디비 1,2,3을 배치했다
현재 마스터는 a:1 이다.
a : 1,2
b : 3

b 데이터 센터가 일시적으로 네트워크가 단절되었다
과반수가 아니라면 b: 3이 마스터가 되고 데이터를 받아드린다.
이때 a:1 도 마스터이기 때문에 네트워크가 복구 되면 데이터의 정합성 문제가 발행한다.

2.5 세컨더리에서 프라이머리로 변경하기
(3개의 멤버 중에서 2개의 맴버가 죽었다고 가정 살아있는 맴버를 프라이머리로 만들기)
var cfg = rs.config()
rs0:SECONDARY> cfg
{
"_id" : "rs0",
"version" : 5,
"members" : [
{
"_id" : 1,
"host" : "127.0.0.1:27001"
},
{
"_id" : 3,
"host" : "127.0.0.1:27003"
},
{
"_id" : 4,
"host" : "127.0.0.1:27002"
}
]
}

27001 이 세건더리이고 27002, 27003 이 죽었을 경우
cfg.members = [cfg.members[0]]
cfg 로 멤버 확인
{
"_id" : "rs0",
"version" : 5,
"members" : [
{
"_id" : 1,
"host" : "127.0.0.1:27001"
}
]
}

rs.reconfig(cfg, {force : true})
rs.status()
현재 서버가 프라이머리인거 확인




2.6 아비타 더하기
cd /test
mkdir rs0/arb1

mongod --port 27004 --dbpath /test/rs0/arb1 --replest rs0
프라이머리 : rs.addArb('127.0.0.1:27004')

rs.status()
{
"set" : "rs0",
"date" : ISODate("2014-10-12T06:49:55Z"),
"myState" : 1,
"members" : [
{
"_id" : 1,
"name" : "127.0.0.1:27001",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
"uptime" : 1095,
"optime" : Timestamp(1413096584, 1),
"optimeDate" : ISODate("2014-10-12T06:49:44Z"),
"electionTime" : Timestamp(1413096488, 1),
"electionDate" : ISODate("2014-10-12T06:48:08Z"),
"self" : true
},
{
"_id" : 2,
"name" : "127.0.0.1:27004",
"health" : 1,
"state" : 7,
"stateStr" : "ARBITER",
"uptime" : 11,
"lastHeartbeat" : ISODate("2014-10-12T06:49:54Z"),
"lastHeartbeatRecv" : ISODate("2014-10-12T06:49:55Z"),
"pingMs" : 0
}
],
"ok" : 1
}

stateStr 'ARBITER' 확인

2.7 아비터가 실제 동작하는지 또한 실제로 데이터는 없는지 확인
mongo --prot 27004
show dbs
테스트 db가 없는지 확인

use test
test.test1.insert({a:1})

하게 되면 에러가 발생하면서 인설트 되지 않는게 맞다

2.8 프라이머리를 죽였을때 아비터가 실제로 투표에 참여하는지 확인
27001 을 죽인다.
mongo --port 27002
에서 secondery 에서 primary 로 변경 되었는지 확인

2.9 우선 순위로 프라이머리로 설정 하고 싶은 마스터를 설정하기
기본적으로 priority 1 높으면 높을 수록 우선 순위를 가진다.
만약 priority 를 0 으로 하면 해당 멤버는 절대 primary 가 될수 없다.

rs.add({_id:4, host:"127.0.0.1:27003", priority:1.5})

접속 되있던 창은 primary -> secnodery 가 되고
mongo --port 27003으로 접속하면 우선 순위가 높은 애가 프라이머리가 되어 있다.

우선 순위는 rs.config() 에서 확인 가능 하다
{
"_id" : "rs0",
"version" : 25498,
"members" : [
{
"_id" : 1,
"host" : "127.0.0.1:27001"
},
{
"_id" : 2,
"host" : "127.0.0.1:27004",
"arbiterOnly" : true
},
{
"_id" : 3,
"host" : "127.0.0.1:27002"
},
{
"_id" : 4,
"host" : "127.0.0.1:27003",
"priority" : 1.5
}
]
}

이번에는 더하지않고 그냥 프라이머리를 바꿔만 보자
var cfg = rs.config()
cfg.members[0].priority = 2
rs.reconfig(cfg)

mongo --port 27001
프라이머리 확인

3.0 멤버 숨기기
클라이언트에 보이기 싫은 멤버는 아래와 같이 hidden 과 priority 를
조절해서 안보이게 할 수 있다.

var cfg = rs.config()
config.members[1].hidden = 0
config.members[1].priority = 0
rs.recofig(cfg)

rs.isMaster() 에서 사라지게 된다.
클라이언트는 isMaster() 를 호출해서 복제 셋의 멤버를 확인 하기 때문에
해당 부분만 고치면된다.

보이게 할려면 해당 속성 삭제하고 리컨피그 하면된다.

3.1 슬레이브 지연
컨피그에 아래 두개의 속성 추가
slaveDelay = 60 * 60 *24 (하루)
priority = 0

3.2 인덱스 생성안하기
인덱스를 생성하지 않는다.

buildIndexes = false
priority = 0




















2014년 9월 18일 목요일

ie8 date wrapping (iso date parse problem)

https://github.com/es-shims/es5-shim/blob/v4.0.3/es5-shim.js

<script type="text/javascript">
            Wrapper = (function (NativeDate) {
                // Date.length === 7
                function Wrapper(Y, M, D, h, m, s, ms) {
                    var length = arguments.length;
                    console.log(this);
                    console.log(NativeDate);
                    console.log(this instanceof NativeDate);
                    if (this instanceof NativeDate) {
                        var date = length === 1 && String(Y) === Y ? // isString(Y)
                            // We explicitly pass it through parse:
                                new NativeDate(Date.parse(Y)) :
                            // We have to manually make calls depending on argument
                            // length here
                                        length >= 7 ? new NativeDate(Y, M, D, h, m, s, ms) :
                                        length >= 6 ? new NativeDate(Y, M, D, h, m, s) :
                                        length >= 5 ? new NativeDate(Y, M, D, h, m) :
                                        length >= 4 ? new NativeDate(Y, M, D, h) :
                                        length >= 3 ? new NativeDate(Y, M, D) :
                                        length >= 2 ? new NativeDate(Y, M) :
                                        length >= 1 ? new NativeDate(Y) :
                                new NativeDate();
                        // Prevent mixups with unfixed Date object
                        date.constructor = Wrapper;
                        console.log('there');
                        return date;
                    }
                    console.log('here');
                    return NativeDate.apply(this, arguments);
                }

                Wrapper.prototype = NativeDate.prototype;
                Wrapper.prototype.constructor = Wrapper;

                // Upgrade Date.parse to handle simplified ISO 8601 strings
                Wrapper.parse = function parse(string) {
                    return NativeDate.parse.apply(this, arguments);
                };
                return Wrapper;
            })(Date);
    </script>

2014년 9월 16일 화요일

javascript event wrapper

아래 예제는 jquery 같은 라이블러리에서 어떻게 이벤트를 wrapping 하는지에 대한
가장 기초적인 예제이다.

순수 자바 스크립트를 사용할 경우에 이벤트에 연관된 인스턴스를 event.srcElement 에서
끄내서 써야 된다.
var test1 = document.getElementById('test1');
test1.onclick = function(event) {
      console.log(arguments);
      console.log(event.srcElement);
};

위와같은 경우 불편하다!
그럼 jquery 와 같이 제공해줄려면 어떻게 해야될까?
뤱퍼를 만들어서 해당 인스턴스를 만들고 해당 이벤트 호출시
이벤트 객체와 this 를 같이 넘겨주면 된다.

그럼 어떻게 구현해야 될까?
답은 클로저이다 클로저의 경우 정의 시점에 넘어간 파라미터를 scope chain 을 통해
참조 할수 있음으로 정의 시점과 실행 시점을 분리할수 있다
또한 내가 원하는 argement 를 실행 시점에 넘겨 줌으로 jquery 와 같은 뤱핑을 할수 있다.

var test3 = new DhtmlObject('test3');
위와 같이 DhtmlObject을 생성할 경우 해당 element  를 가져와서 이미정의된 브라우저
(여기서는) 클릭 펑션에 associateObjWithEvent 를 실행해서 할당한다.
associateObjWithEvent 의 경우 최초 아규먼트를 받아 자신의 activation obj에 할당하고
inner function 을 리턴한다.(이벤트 처리 펑션) inner function 의 scope chain 에는  outer
function 의 scope 가 들어가 있기 때문에 outerfunction 이 리턴된 후 에도 outer function 의  아규먼트에 접근 가능 하며 실제 실행될때는 리턴된 inner function 이 실행된다.

     

http://jibbering.com/faq/notes/closures/#clSto
상세 설명은 위의 글을 참고 바란다.


<html>
<head lang="en">
 
    <title></title>
    <script>

        function associateObjWithEvent(obj, methodName){
            return (function(e){
                e = e|| window.event;

                return obj[methodName](e, this);
            });
        }



        function DhtmlObject(elementId){
            var el = document.getElementById(elementId);
            if(el){
                el.onclick = associateObjWithEvent(this,'doOnClick');
                el.onmouseover = associateObjWithEvent(this, "doMouseOver");
                el.onmouseout = associateObjWithEvent(this, "doMouseOut");
            }
        }

        DhtmlObject.prototype.doOnClick = function(event, element){
            alert(event);
        }
    </script>

</head>
<body>
    <button id="test1">testButton1</button>
    <button id="test2">testButton2</button>
    <button id="test3">testButton3</button>
    <button id="test4">testButton4</button>

    <script>
        var test1 = document.getElementById('test1');
        test1.onclick = function(event) {
            console.log(arguments);
            console.log(event.srcElement);
        };

        var test2 = document.getElementById('test2');
        test2.onclick = function(event) {
            console.log(arguments);
            console.log(event.srcElement);
        };


        var test3 = new DhtmlObject('test3');
        test3.doOnClick = function(event, element){
            console.log(arguments);
            console.log(element);
        }

        var test4 = new DhtmlObject('test4');
        test4.doOnClick = function(event, element){
            console.log(arguments);
            console.log(element);
        }

    </script>
</body>
</html>