2021-08-31

0831 리눅스 명령어 : cp, rm, mv

 1. cp [-option][source][destination]

옵션들

1) -r recursive. source파일이 디렉토리일경우 하위에 있는 자식들까지 델꼬 복사해준다.

2) -i interactive모드. 복사할때 물어본다. 

3) -v verbose. 복사한 후 내용 출력

4) 주의할 점: destination의 파일이 이미 존재할 경우 덮어써진다. 확인차 -i를 붙이는 것이 좋다. -i를 붙일경우, overwrite할것인지 물어봐준다.

5) destination이 디렉토리일경우 하위에 대상 파일을 넣어준다.

6) destination에 아무것도 없을 경우 새로 생성.

7) destination에 .을 쓸경우 해당 source파일명으로생성해주고, 특정 이름을 지정하면 그 이름대로 복사해준다. 

8) cp /etc/a* . 이런식으로 쓸수도 있음.


2. rm [-옵션][대상파일]

옵션들

1) -r recursive하게 하위 파일들까지 삭제한다

2) -f force묻지도 따지지도 말고 그냥 다 삭제해라. 

3) -rf 이둘을 합쳐서, 디렉토리를 삭제할때 많이 붙이는 옵션. 

4) rm -rf *  이런식으로 정규식을 이용해서 삭제할 수도 있다. 이 디렉토리 안의 모든 파일/디렉토리를 삭제하는 명령어. 사용에 주의한다. 특히 root로 접속했을 경우, 리눅스는 휴지통이라는 개념이 없기 때문에 잘못하면 싹 다 날라간다. 

5) rm -f a* b* c* 이런식으로 여러개를 지정할 수도 있다. a,b,c로 시작하는 파일들 다 지워라!

6) rm -f [^abc]* a,b,c로 시작하는 파일들 '제외하고'나머지 다지워라. 결과- a,b,c로 시작하는 파일들만 남는다.

7) rm -f [a-c]* 이렇게 쓸수도 있음.

 

3. mv [-옵션][source][destination]

파일을 이동할때 / 파일의 이름을 변경할 때 둘다 쓰인다.

1) mv는 특정 하나의 파일을 변경할때, rename은 일괄적으로 변경하고 싶을 때 쓰인다.

2) 참고: rename [어느부분을][어떻게][원본이름]

2021-08-30

0830 static inner class & inner class

 

static inner클래스는 외부 클래스의 참조를 가지지않는다.

따라서 외부 객체의 생성없이 바로 부르고, 메서드를 사용하는 것이 가능하다.


컴파일했을때, 'OuterOfStatic$StaticNested.class' 라는 식으로 클래스가 생성되는 것을 확인할 수 있다. OuterOfStatic.class라는 외부 클래스와 상관없이 따로 클래스가 별도로 만들어진다!!



엥 모야... 일반 inner 클래스(non-static) 도 따로 클래스 만들어지넹..



내부 static클래스에서는 외부 클래스의 static만 부를수있지만.

외부 클래스에서는 static클래스의 것들을 자유롭게 사용할수있다. 

2021-08-29

0829 소켓통신 이해

 

읽을 데이터도 없고 클라이언트도 계속 연결을 끊지않고 유지하는 상황. 에러발생!


-->자원 해제처리를 제대로 안해주었기 때문에 발생하는 에러.


자원해제를 해주는 약속메시지를 보내거나.

아니면 client쪽에서 명시적으로 connection을 stop해서 in, out을 끊어주니까 - 에러가 안난다.

아직도 뭔가 io는 모호하다... 더 공부해야겠음.


----------------------------------------------------


아까 이부분을 주석처리했더니

클라이언트로부터 데이터 한번 읽고, 그다음에 계속 진행되지 않는 상태로 유지되었었다...서버의 메시지가 전송되지 않았던것이다.

0829 thread 이해

 1. synchronized키워드를 이용해서 상호 배제 할 수 있다.

2. synchronized 블록안에서 object가 가지고 있는 wait()메소드를 이용하여, cooperation을 위한 wait-and-notify기법을 활용할 수 있다. 스레드는 notify될때까지 계속 이후 작업을 수행하지 않고 기다린다.

3. thread 는 join()을 통해 수행이 끝날때까지 기다려질수있다.

4. thread는 interrupt()를 통해 방해받을 수 있다. 예외를 발생시키며 스레드가 종료된다.

5. synchronized키워드를 사용할 경우, 데이터의 가시성을 위해서 해당블록 전에 데이터가 실제cpu메모리로 flush된다고 한다. (volatile키워드를 쓰지 않아도 synchronized를 씀으로써 가시성이 보장되는 듯함)

6. 모든 스레드는 스레드 그룹에 속하며, 명시적으로 스레드그룹을 지정하지 않을시 자기자신의 스레드 그룹에 속하게 된다.

7. 스레드 그룹을 이용할 시 일괄적으로 interrupt처리를 하는 등, 좀더 효율적으로 스레드를 관리할 수 있게 된다.

0829 socket통신

https://www.baeldung.com/a-guide-to-java-sockets
<< 위 글이 무지 도움이 되었다!!
1. 여러 클라이언트를 받고자 할 경우 - 스레드를 만들면 된다.
2. PrintWriter는 OutStream을 확장하는 클래스로, char단위로 쓸 수 있다. socket을 열어서 얻을 수 있다. 
3. BufferdInputReader를 이용해서 한줄 단위로 while루프 안에서 readLine이 null이 아닐때까지 계속해서 읽을 수 있다.
4. 클래스 로딩시에 ServerSocket을 생성하고, 클래스 닫힐 시 ServerSocket을 close하도록 셋팅해준다. 
5. 클라이언트로부터 exit신호가 오기 전까지 계속 서버가 대기하도록, while(true)문법을 사용할 수 있다.
6. 소켓은 기본적으로 ip주소와 포트번호로 식별된다. 따라서 클라이언트가 소켓통신을 하기위해 여는 소켓의 생성자에 ip주소와 포트번호가 들어가는 것이다.
7. 통신방법에는 TCP와 UDP가 있는데, 일반적으로 UDP는 잘 사용하지 않는다고 한다. 

 

0829 fork-join task

 1. ForkJoinPool에서 ForkJoinTask를 생성.

기본적인 방향은 - work-stealing 알고리즘, 분할정복 알고리즘을 채택한다는 것.

그래서 추상 클래스인 ForkJoinTask 을 구현한 클래스의 이름들은 : RecursiveTask, RecursiveAction이다. 둘다 compute()를 구현해야 한다. RecursiveTask는 반환값을 제네릭으로 지정할 수 있고, RecursiveAction은 void이다. ( 클래스명이 잘 나타내주고 있다고 생각한다)

2. invokeAll()혹은 fork()메소드를 통해 task를 쪼개서 스레드별로 실행한다. RecursiveTask의 경우 반환값을 받아야 하기 때문에 join()을 통해서 반환값을 받는다.

3. 해당 메서드를 외부에서 부르기 위해서 invoke()를 사용해서 Recursive객체를 전달한다. void의 경우 join()으로 값을 return 받지 않아도 된다. 혹은 그냥 

int result = forkJoinPool.invoke(customRecursiveTask);

이런식으로 곧바로 받을 수도 있고

customRecursiveTaskFirst.fork(); result = customRecursiveTaskLast.join();

이렇게 따로 받아도 된다.

4. ForkJoinTask는 기본적으로 Future을 상속하고 있는데 - Future가 get()하는 동안 synchronized로 블록되던 문제를 다소 해결하여 훨씬 빠른 성능을 보인다고 한다.


0829 Vue.js이용해서 로그인 폼 만들기

 







1 . vue를 이용해서 화면을 작성할때는 : npm run serve명령어를 사용해서 서버를 열어줘야 한다는 것... 이걸 안해서 왜 화면이 안나타나지?? 하고 헤매고 있었다.

2. event.preventDefault();는 jQuery방식이고, vue에서는 event modifier를 통해서 submit.prevent와 같은 짧은 문법으로 사용가능하다.

3. 데이터를 연결할때는 v-model을 쓴다.

4. npm i(install) ~~명령어를 통해서 외부 서드파티 라이브러리를 쉽게 import해올 수 있다. 마치 maven repository같다.

5. axios를 이용해서 쉽게 json데이터를 주고받을 수 있다. 문법이 단순하고 편하다!!

2021-08-28

0828 java.net.SocketException: Socket is closed 에러

 

데이터를 한번 보내고는 죽어버린다...

어디서 닫아주어야 하는거지??

소켓을 끊지않고 계속 유지??


---------------------------------------------------

에러의 원인 찾았다.

try-catch-with-resources를 이용해서

server.accept()를 try()괄호안에 넣어주고있어서

한번 데이터를 받고는 서버를 자동으로 닫아버렸기 때문에

한번만 보내고 계속 서버접속이 끊겼던 것이다.

아아 뭔가~~~ 근데 속시원하질 않네!!


소켓 통신에 관해서 좀더 공부하고 싶다. 네트워크 기초가 부족한게 아닐까 나?!!

0828 Serializable

1. Serializable  : 자바 객체를 파일이나 네트워크 등으로 저장, 전송할때 implements한다.

이것을 implements함으로써 - 얘는 직렬화가 가능한 객체야! 라고 mark 해주는 인터페이스이다.

2. ObjectOutputStream과 ObjectInputStream을 이용해서 객체를 저장하고 읽을 수 있다.

3. 그런데 만약에 객체의 정보가 변경된다면??


너의 시리얼 버전 ID가 변경되었어... 라면서 에러를 뿜뿜 내뱉는다. 


얘는 아까 걔랑 똑같은 객체야~~ 라고 알려주는 것이 시리얼버젼 아이디.

쓸때와 정보가 달라져도 같은 객체로 인식하고 읽어들인다.

but...오히려 에러가 발생하지 않기 때문에 더 무서운 것이다. 정보가 변경되었는데 사용하는 측에서는 그걸 모르게된다!!! 

그러므로 객체정보를 변경했다면 꼭꼭 버전 아이디를 변경해주자.



너가 저장한 것은 1버전인데 2버전을 읽으라고 하고있어....

라면서 또 에러를 뿜뿜. 

룰 : 1) 같은버전으로 저장-읽어야 에러가 안난다( 변경된 객체이면, 에러를 내뿜는다)

2) 객체정보를 변경했을시 버젼 UID도 함께 변경해주자.

2021-08-27

0827 bufferedWriter로 text를 write하기

 

try-catch-with-resources문을 이용해서

FileWriter를 BufferedFileWriter에게 넘겨서!

int 0부터 9까지 쓴다!!

그런데 이상한 일 발생!!


ㅋㅋㅋㅋㅋ이게 뭐람!?!!!왜 이런일이~~우짜~~@!

------------------------------------------------------------------------------


메소드를 수정하였다!!

int는 자바객체라서 제대로 못쓰는듯함!

String의 정적메소드 사용하여 텍스트 형식으로 바꾸어 준다.

이펙티브자바에서 Object안에 아예 null이 들어오는 경우위험하니까 String.valueOf쓰라구 배웠당. ㅎㅎ


이제 잘 나온다!!

0827 synchronized keyword

 1. synchronized : 같은 자원(객체)에 접근할때, 경쟁상태로 인한 의도치않은 결과를 예방하기 위해 사용하는 키워드. 동시성 문제를 해결한다.

2. 메서드에 붙이거나, 블록에 붙일 수 있다. 블록에 붙일때는 lock할 키를 하나 넣어준다. 

3. 메서드에 붙이면 개발자는 편하다(ㅋㅋ) 하지만 !!! 성능을 위해서는 블록 단위로 넣어주는 것이 좋다!! synchronized를 붙이는 순간 다른 스레드는 해당 연산에 접근할 수 없기 때문에- 그만큼 시간이 지연되기 때문이다.

4. 각기 다른 객체를 스레드 별로 할당하는 경우, 같은 클래스이지만 다른 인스턴스에 접근하기 때문에 동시성 문제는 일어나지 않는다.


이런 경우, 동시성 문제를 고려할 필요가 없다.

synchronized키워드를 지우고 다시 시도해보아도 - 의도한 결과가 나오는 것을 확인할 수 있다.

--------------------------------------------------------

여담)

왜 백엔드가 재미있는지 알것같다....!!

설계라는 하나의 예술? (ㅎㅎ)을 배우는 것이 재미있다.

여러 클래스가 협업하여 만들어내는 여러층의 레이어~~ 그것을 읽는 기쁨이랄지~~ 호호

0827 스레드의 join 메서드

 join메서드: 해당 스레드들이 종료할때까지 main이 기다린다.


1 . join()을 사용하지 않았을 경우 : main은 그냥 지할일만 하고 끝나버려서. calculate계산이 이루어지기도 전에 후다닥 끝나버린다;; 그래서 amount가 계속 0이 나왔다 ㅋㅋㅋ



2. join()수행시, 메인메서드가 해당 스레드 종료시까지 기다린다. 스레드두개가 일을 전부 마친후 메인이 종료되는 것을 확인할 수 있다.

3. 한가지 더 유의해야 할점은 - amount의 값이다.!!
둘다 1000번씩 더하는 메서드를 활용했으나 값은 2000이 되지 않는다 -
 왜냐하면, 덧셈연산은 사실
값을 더하고 ->  대입한다 
는 두가지 과정으로 이루어지는데, 
더하고 -> 에서 두 스레드가 경쟁하기 때문에, 대입하기도 전에 계속 연산이 이루어져서 2000보다 적은 값이 되어버린다!!!
-> 이러한 경쟁상태를 해결하기 위한 키워드가 synchronized이다!



synchronized 키워드를 붙인후 - 의도했던 결과를 얻을 수 있음을 확인!
-----------------------------------------------------------------------------------------------------

의문점 : lock하는 key오브젝트는 다 똑같아도 괜찮은 건가?? 아니면 synchronized키워드를 붙인 메서드 별로 다르게 설정해야 하는건가??
똑같이도 해보고 다르게도 해봤는데 둘다 2000으로 잘 나온다. 흠? 무슨 기준으로 다르게 lock거는거지?

0827 다양한 directiive이용하기

 1. v-어쩌구 로 붙는 다양한 기능들을 directive라고 부른다.

2. 원래 jQuery로 써서 하던 동적인 기능들을 Vue에서는 좀더 세련되게 지원해준다.

3. v-model을 이용하여 dom엘리먼트를 맵핑하여, 동적으로 화면을 보여줄 수 있다.

4. {{}}속성을 이용하여 데이터를 동적으로 변경할 수 있다.

5. methods기능을 이용하여 데이터를 method를 이용해 동적으로 변경할 수 있다.

6. v-on:click과 같이, on뒤에 이벤트명을 지정하여- 다양한 이벤트 바인딩을 할 수 있다.

7. event modifier기능 : 이를 테면 v-on:keyup.enter와 같이하여, 세밀한 이벤트 조정 및 수정이 가능하다. 

8. v-bind:기능 으로 dom엘리먼트를 다룰 수 있다. id라던지 name이라던지 하는 프로퍼티를 동적으로 수정하는 것이 가능함.

2021-08-26

0826 router이용하기

 완전신기하다!!

view에서 자체적으로 라우팅을 한다니?!!(여기서 백엔드의 컨트롤러는 그럼 어떤 역할을 하게 되는거지?!! 데이터만 주는 거야?)


라우터 속성을 이용하면 - url로 바로 부를 수 있다!!!


1. view인스턴스에 router를 등록한다.

2. router에 각각의 컴포넌트를 등록한다.

3. 컴포넌트별 path(=url)을 등록한다.

우와... 초간단.

0826 같은 레벨의 컴포넌트가 데이터를 주고받는 방법

 1. 상위 컴포넌트로 이벤트를 발생시켜서 데이터를 전달한다.

2. 상위 컴포넌트에서 해당 하위 컴포넌트로 prop을 전달한다.

(prop이란, 상위에서 하위로 내려오는 데이터를 지칭하는 단어.)


1) 먼저 버튼을 클릭했을때 실행되는 메서드를 등록한다. v-on:click으로 메서드 명을 지정해주면 된다.

2) 상위 컴포넌트로 올릴 메서드를 지정한다.

this.$emit을 이용해서, 매개변수로 메서드명과 데이터를 함께 넘긴다.

3) v-on:속성을 이용해서, 상위컴포넌트와 하위 컴포넌트의 메서드를 엮는다.

4) 상위컴포넌트에서 value를 받는다.

5) 해당 value를, 원하는 하위컴포넌트에서 v-bind를 이용해서 메서드로 받는다.

이때 props속성을 이용, 상위 컴포넌트의 데이터 명을 엮는다.

2021-08-25

0825 event emit하기

 

1. 하위 컴포넌트에서 : 이벤트를 발생시키고, 해당 이벤트의 이름을 지정한다.

method 명과 emit할 이벤트명은 별개. 

2. 상위 컴포넌트에서, 뭔가의 method(function)을 단다.

3. 해당 상위 컴포넌트의 method와 하위 컴포넌트의 method를 연결한다-

4. 아직 알쏭달쏭~~

0825 props속성

 1. Vue.js에서 컴포넌트간 통신을 할때, data를 넘긴다

2. 이때 상위 컴포넌트에서 하위 컴포넌트로 내려가는 데이터를 props라고 부르고,

3. 하위 컴포넌트에서 상위 컴포넌트로 올려보내는 데이터를 event라고 부른다.

4. 과거 mvc패턴에서는 - 데이터가 여기저기의 페이지로 전달될때, 데이터의 흐름을 파악하기가 힘들었다.

그러나 컴포넌트 구조로 계층을 만들고 props와 event라는 문법을 도입함으로써, 데이터의 흐름을 파악하고 변경을 추적하기가 좀더 용이해 진 것이다. 

5. 문법적으로는 - 상위(혹은 root Vue인스턴스) 컴포넌트에 하위 컴포넌트를 등록한다.

6.해당 상위 컴포넌트의 div안에 하위 컴포넌트 명으로 공간을 생성한다.

7. 상위 컴포넌트의 data속성안에 이름-값의 쌍으로 데이터를 등록한다.

8. 하위컴포넌트에서는 props속성으로 공간을 만들어주고.

해당 props를 연결짓는 것 - v-bind라는 문법을 이용한다!


백엔드하다가 프론트로 슉 콘텍스트 스위칭 하느라 조금 해맸다.

Vue를 script로 등록해주는 것을 잊지말기.


2021-08-24

0824 자바 8 메서드 참조

 

자바 8의 메서드참조기능에는

클래스::메서드 명

이렇게만 알고있었는데!

참조변수::메서드 명

으로도 사용할 수 있다.

해당 참조변수가 사용할 수 있는 메서드라면 얼마든지 가능함!

2021-08-23

0823 inner 클래스의 접근 범위

 


이후 @PostConstructor 에서 init메소드를 부를때, default로 설정했더니 메소드를 부를 수 없었던 에러가 있었다!!

public으로 메소드를 바꾼 후 해결되었는데, 그이유는

애초에 지금 inner클래스로 default로 잡았기 때문에 - default 안의 default여서 바깥에서 해당 메소드를 부를 수 없었던 것이다.

중첩 클래스의 경우 접근 범위가 더 좁아지는 것에 유의해야 한다!! ㅎㅎ


2021-08-22

0822 api조회 컨트롤러, 서비스, 레포지토리 생성하기

 더미데이터 넣기


profile.active설정을 통하여 test일때에만 해당 프로파일이 작동되도록 설정. application을 로딩할 때 해당 설정을 확인할 수 있다.



멤버 init이라는 클래스를 작성하여 더미데이터를 넣어줄 것이다. profile이 local일때에만 이 클래스는 로딩된다. 

@PostConstruct를 통해서, 클래스의 로딩 -> 의존성주입 이후에 곧바로!! 실행될 메서드를 넣어주었다.


엔티티매니저를 주입받고. (inner 클래스를 작성할때에는, static으로 한다. 그렇게 해서 외부클래스와의 의존성을 낮춘다.) 

init메서드를 작성하여 더미데이터를 넣는다.

이때 자바8문법을 활용해본다!!(재밌기 땜이다 ㅎㅎ)

나이는 랜덤으로 1~50까지 들어가며, 

홀짝으로 팀을 분배하였다.


쓰다가 한가지 오류 난 것 - 신기하게(?) 저 init()메서드를 내가 public을 안붙이고 실행했더니 - 실행이 안되었다. 처음에는 entitymanager가 주입이 안된건가?? 했는데, 아무래도 init을 부르는 쪽 ( @PostConstructor) 에서 못찾는 거거나. 아니면 - 

엔티티매니저와 public메서드가 관련이있나??

java문법을 더 공부해야 겠다!!

0822 dto로 직접 조회하기

 1. jpql문법 : 조회해서 가져오고 싶은 dto패키지 명을 다 써줘야 되기 때문에 보기에 더러워(?)짐. 

2. querydsl문법: 1) bean으로 가져오기 2)constructor로 가져오기 3) field로 가져오기

가 있다.

1)과 2)의 경우에는 getter setter 혹은 생성자에 유의해서 만들어줘야 한다. 그래야 리플랙션으로 샥 넣어준다. 

3. alias로 가져오고 싶은 경우 - ExpressionUtils를 이용할 수 있다. 


JPAExpressions를 사용해서 서브쿼리 날리고, 해당 서브쿼리를 age라는 alias로 조회.

그냥 alias만 주고 싶으면 간단하게 as()만 쓰면댐.

2021-08-21

0821 서브쿼리 날리기

 

1. 방법

1) 만약 같은 테이블에서 서브쿼리를 날릴경우 - alias를 다르게 주어야 하므로, 새로운 Q도메인 객체를 생성한다. 

2) JPAExpressions를 이용하여 서브쿼리를 날린다. fetch수식어만 제외하고 QueryFactory에서 만드는 문법이랑 똑같음.

3) where 혹은 in조건을 이용하여 서브쿼리를 날릴 수 있다.

2 . 서브쿼리의 종류 : select , from, where

- 그러나 Querydsl에서는 from절에서의 서브쿼리를 지원하지 않는다.

Querydsl은 기본적으로 JPQL를 사용하기 쉽게 만들어주는 녀석인데, JPQL이 from절 서브쿼리를 지원하지 않기 때문이다. JPQL에서 안되는 것은 Querydsl에서도 안된다. ㅜㅜ

이경우에는hibernate구현체를 직접이용하거나, 조인으로 풀어내거나, 그것도 안되면 네이티브SQL을 날리는 수밖에 없다...


3. assertThat의 다양한 사용법

as("~~)를 이용해서 해당 assertThat에 특정 이름을 지정할 수 있다.

extractind("필드변수명").contains()혹은 containsExactly()를 사용하여 해당 값이 포함되어있는지를 좀더 상세하게 검증할 수 있다.


4. EntityManagerFactory에서 제공하는 LoadedUnitUtils를 이용하여, 해당 필드값이 loaded되었는지 아닌지를 true false로 검증할 수 있다. 

0821 join on조건


 leftjoin한 후에 on으로 조건추가할 수 있음. 



일반 join한 후에 on으로 조건 추가하거나. where로 추가할 수 있음. 결과는 동일함.

좀더 익숙한 where절을 사용하도록 하자.

0821 inner join, outer join

1.  entityManager : 스프링에서 ,멀티스레드로 돌려도 동시성 문제 없도록 바인딩 처리해준다고 함.. 우와아아아.

2. 조인에는 크게 두가지가 있다. inner join, outer join.

inner join을 디폴트로 되어있으며 보통 왼쪽 기준으로 left inner join을 한다.

이것을 querydsl 혹은 jpql문법으로 바꾸면 ->

join (= inner join) , leftJoin => left outer join이 된다.


팀과 멤버를 일반 조인으로 했을 때는 team이 null인 member는 조회되지 않는다. 교집합만 추출된다.


왼쪽 (멤버)기준 leftJoin을 한 경우 left outer join으로 전환되어 SQL이 실행되며, 팀이 null인 멤버도 전부 조회된다. 


0821 fetch type=Lazy인 경우

 


Lazy로 설정하는 경우, getTeam을 부를때 한번 더 select를 때린다.


select member한 후에 -> getTeam하니까 (어!! 나 select안해왔는뎅 !!)하면서 다시 select때리고..

이경우에는 4명의 회원이 각각 2개의 팀에 소속되어있기 떄문에

select member -> select team -> select Team

총 3번의 쿼리가 날라가는!! 이것이 바로 N+1문제이다!!!

(사실은 1+N이라고 말하는게 맞는 것 같지만)


따라서 fetch join을 써야한다!

0821 querydsl학습

 javax.persistence.TransactionRequiredException: No EntityManager with actual transaction available for current thread - cannot reliably process 'persist' call


entitymanager를직접사용할때는 transaction에 주의한다. 꼭 감싸 주어야 함




2021-08-16

0816 Vue.js component란

 1. 우선 new Vue()로 Vue를 생성하면 - root가 등록된다.

2. 이 root하위에 여러개의 컴포넌트를 등록할 수 있다.

3. 컴포넌트 : 상위 컴포넌트, 하위 컴포넌트가 있다

4. 컴포넌트 등록방식 : 전역으로 할 수도 있고 지역으로 할수도 있다.

전역으로 할 경우에는 Vue.component('컴포넌트 이름' , '컴포넌트내용')을 적으면 되고

지역으로 할 경우에는 Vue 안의 components라는 속성을 이용하여 이안에 줄줄이 객체를 넣어준다. 

자바스크립트 객체의 경우 

var app = {} 이런식으로 선언하는데

앞에 다짤라내고 {}만 넣어서 좀더 간결하고 익명객체로 선언한다! 굳이 여러 객체명을 만들지 않는다.

실무에서는 전역컴포넌트로 등록하는 경우는 거의 없고, 지역컴포넌트로 불러서 많이들 사용한다 - 왜냐하면, SPA를 제작할경우 아 이런 컴포넌트가 등록되어있구나 하고 한번에 파악하기 쉽기 때문이다.

지역컴포넌트 등록은 마찬가지로

components {

'컴포넌트명' : '컴포넌트내용'

}으로 등록한다. 자바스크립트는.. 저 뾰족괄호로 줄줄이 이어지는게 좀 웃기고 잼나다. ㅎㅎ


5. 지역컴포넌트 전역컴포넌트 그리고 인스턴스의 관계:

인스턴스밑에 지역컴포넌트로 생성할경우, 해당 컴포넌트는 해당 인스턴스에만 바인딩된다.

전역컴포넌트로 생성할 경우, 여러 인스턴스에 모두 기본적으로 등록된다.

그러나 실제로는 인스턴스는 하나만 생성하며, 지역컴포넌트로 등록하는것이 일반적이다. 굳이 여러 인스턴스를 만들어서 혼란을 부르지 않는다...!!!! new Vue는 한번만! 

0816 Vue.js instance란

 1. 즉시실행함수 쓰는 이유

전역변수로 부를경우- 다른 페이지에서도 똑같은 네임의 변수를 사용한다면? 오염되어서 원치 않는 결과를 부를 수 있다. 즉시실행함수로 한번 더 감싸주어서 - 해당 함수내에서만 사용되도록 스코프를 잡아준다. 

(function(){}());


2. Vue.js instance

new Vue();로 생성한다.

생성자 함수로 부른다.

왜 Vue를 사용할때 생성자 함수를 만들어야 하는가? -> 코드의 재사용성이 높아지기 때문이다.

el : 엘리먼트를 뜻한다. 내가 부르고 싶은 html페이지의 요소를 데려다가 여기에 쓸것이다.

이 문법은 제이쿼리와 동일하다. 이를 테면 id="app"일경우

el : '#app' 이런식이다. 큰따옴표 작은따옴표는 상관없다.

data : 넣고싶은 속성혹은 함수를 정의할 수 있다.



생성자 함수 function Person을 정의하고 사용하는 예시.


생성자 함수 안에는 key:value 형태의 다양한 속성들이 들어간다. Vue는 다양한 속성과 기능을 제공하고 있다. 이것을 api라고 한다!! 가져다 쓰면된다!

0816 maven+jenkins빌드하기

 기존 프로젝트를 젠킨스를 이용하여 빌드해보았다.

1.jdk1.8버전을 사용하도록 설계한 프로젝트인데 젠킨스 설정에는 jdk15밖에 없어서 에러남

2. jdk1.8다운로드 후 젠킨스 관리 - global tools에 jdk1.8버전 path잡아준 후 

3. 프로젝트 jdk설정에 1.8로 잡기

4. 현재 에러

INFO] 
[INFO] --- maven-clean-plugin:2.5:clean (default-clean) @ udada ---
[INFO] Deleting C:\Users\dbrtm\.jenkins\workspace\udada-jenkins-v2\target
[INFO] 
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ udada ---
[WARNING] Using platform encoding (MS949 actually) to copy filtered resources, i.e. build is platform dependent!
[INFO] Copying 19 resources
[INFO] 
[INFO] --- maven-compiler-plugin:2.5.1:compile (default-compile) @ udada ---
[WARNING] File encoding has not been set, using platform encoding MS949, i.e. build is platform dependent!
[INFO] Compiling 109 source files to C:\Users\dbrtm\.jenkins\workspace\udada-jenkins-v2\target\classes
[INFO] -------------------------------------------------------------
[ERROR] COMPILATION ERROR : 
[INFO] -------------------------------------------------------------
[ERROR] bad path element "C:\Users\dbrtm\.m2\repository\com\oracle\database\security\oraclepki\19.10.0.0\..\oracle.osdt\osdt_cert.jar": no such file or directory

---------------------------------------------------------------------

의존성 라이브러리가 없어서 에러나는듯. 수정해본다!
아이고 드디어 성공했다.
에러1 - 테스트에서 현재상태 DB와 매치되지않는 상태의 메소드있었던것
에러2 - 한글 인코딩 문제. apach-maven-plugin 에 configuration 의 encoding 항목을 수정한다.
에러3 - 테스트 없는데 jacoco보고 테스트 분석하라고 해서 에러남
드디어 빌드완료! 

0816 Vue.js의 reactivity

 1. 기존의 HTML, CSS, Javascript방식 :

데이터가 바뀌면 그때마다 코드를 추가해서 할당을 해주어야 한다. 코드가 늘어나고 번거롭다!!

2. Vue.js방식:

View 에서 이벤트가 일어나면 그에 반응하여 페이지를 그려주고

데이터 (JS)쪽에서 이벤트가 일어나면 그에 반응하여 페이지를 그려준다!! 양쪽에서 중개해줌

3. Vue.js를 이용해서 오브젝트의 속성을 정의하고, 동적으로 페이지를 그릴수있다


4. viewModel이라는 오브젝트를 정의한다

var viewModel = {};

Object.defineProperty를 이용하여 해당 오브젝트의 속성을 정의한다.

Object.defineProperty(viewModel, 'str' {함수});

와 같은 형식을 띄고 있다.

해당 함수안에 get , set을 이용하여 할당되는 값을 만든다

이때 set함수안에 div태그에 해당 값을 그려주도록 설정하면 - !! 동적으로 값이 바인딩된다!! 우와!! 프런트엔드 신기하다.... 

0816 Vue.js 시작하기

 1. 크롬 확장 플러그인에서 vue.js devtools 다운로드

2. node. js 다운로드

다운로드 버전확인

node -v

npm -v

하니까 새로이 업데이트 되었다고 해서 인스톨함


ㅋㅋ 무지 귀엽다!

요새는 프런트엔드나 벡엔드나 돌아가는 생태계랄지, 구조가 비슷해지고 있는 것같다.

결국엔 프런트엔드 벡엔드 다 잘할줄아는... 풀스택개발자가 답인가 싶기도 하고...

java를 깊이 파면서 + 주변 스택도 두루두루 잘 하는 그런 개발자가 되고싶다!!

그 두루두루스택 (?)중에서도

최근 Vue.js에 관심이 생겨서.

 강의를 들으며 간단한 토이 프로젝트를 진행해 보려고 한다!!

2021-08-14

0814 maven으로 젠킨스빌드하기

 1. maven 직접다운로드한후 path설정해줘도 되고(시스템변수, 환경변수편집)

2. 젠킨스의 download automatically를 이용해서 maven 직접다운로드 해줘도 됨.

3. jdk설정을 해줘야 하는데, 오라클은 jdk다운로드할때 아이디비번인증을 필요로 하기 때문에 automatically download대신에 미리 pc에 다운로드해둔 자바 경로입력한다. (bin은 빼고넣으면 됨) 

4. maven으로 빌드하기 설정을 했으나 

[INFO] Scanning for projects...
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time:  0.113 s
[INFO] Finished at: 2021-08-14T17:38:08+09:00
[INFO] ------------------------------------------------------------------------
[ERROR] The goal you specified requires a project to execute but there is no POM in this directory (C:\Users\dbrtm\.jenkins\workspace\mari-jdbc-jenkins). Please verify you invoked Maven from the correct directory. -> [Help 1]
[ERROR] 
[ERROR] To see the full stack trace of the errors, re-run Maven with the -e switch.
[ERROR] Re-run Maven using the -X switch to enable full debug logging.
[ERROR] 
[ERROR] For more information about the errors and possible solutions, please read the following articles:
[ERROR] [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/MissingProjectException
Build step 'Invoke top-level Maven targets' marked build as failure
An attempt to send an e-mail to empty list of recipients, ignored. 

Finished: FAILURE


에러가발생했따~~~ 

아마 . maven프로젝트가 아니라 gradle 프로젝트라서그런듯?


-------------------------------------------------------------------------

https://miiingo.tistory.com/171<<<이분의 글이 도움이 되었다!!

build를 gradle로 설정 변경하고, 

task에는 간단하게

clean

build만 적고

buildfile에 build.gradle을 입력


성공!!


결국 정리하자면


젠킨스설치 -> 자바path, maven, gradle설정해주기(자동다운로드) -> 해당 프로젝트의 빌드 환경에 맞게 빌드 스크립트 작성하기 -> save ->빌드

2021-08-13

0813 jenkins 설치 및 설정하기

 


1. 현재 jdk가지고 있는 버전이 15인데 젠킨스는 8,11만 (일단은)지원중.

그래서 --enable-future-java 옵션붙임

2. 포트는 뜨는데 자꾸 localhost접속이 안되서

--httpPort=9191옵션붙임

3. java -jar jenkins.war --옵션들

4. 젠킨스관련 설정파일들은 기본적으로 C: 사용자/사용자명/.Jenkins안에저장된다

이 안에 default어드민패스워드도 저장되어있음. (secrets폴더)




패스워드 입력


젠킨스가 추천하는 플러그인들을 다운로드해보자.

0328 fdisk, mkfs, mount, fstab

 1. 하드디스크를 붙인다. 2. fdisk -l로 하드디스크를 확인한다.  - interactiive한 커맨드모드 사용하여 (m) 붙인 하드디스크의 파티셔닝을 한다.  - 마지막에 w를 해야 실제로 반영이 된다.  3. mkfs를 하여 어떤 파일시스...