반응형

쉘스크립트 작업을 하다가 정말 별거 없는 스크립트인데 실행시켜보면 command not found가 뜬다.

그것도 변수명인데 해당 변수명의 command를 찾지 못하겠다니???

 

RECENTFILE : command not found

#!/bin/sh

RECENTFILE =`hadoop fs -ls -R /user/irteam/dmp/demo/data/ | grep "^d" | sort -k6,7 | tail -1 | tr -s ' ' | cut -d' ' -f8`

echo "${RECENTFILE}"

잉??? RECENTFILE은 변순인데...왜 커맨드로 인식해???

 

문제는 RECENTFILE뒤에 공백....(공백을 제거해준다.)

RECENTFILE=`hadoop fs -ls -R /user/irteam/dmp/demo/data/ | grep "^d" | sort -k6,7 | tail -1 | tr -s ' ' | cut -d' ' -f8`

 

만약 처음 처럼 공백을 넣게 되면 bash는 RECENTFILE이라는 명령을 뒤에 있는 문자열을 매개변수로 실행하려 한다.

ex) RECENTFILE = 'foo' (RECENTFILE 옆에 한번 띄고 = 옆에 한 번 띄게 되면 RECENTFILE이라는 커맨드를 '=', 'foo' 두 개 인자와 함께 실행하려 할 것이다.)

 

따라서 변수선언시에는 뒤에 공백을 주어 bash에서 command로 인식하지 않도록 하자.

반응형
반응형

@Controller에서 요청을 받아 특정 url로 redirect시켜주는 컨트롤러가 있는데

정상적으로 요청이 전달이 되지 않는 것 같아 로그를 확인해 보니 다음과 같은 에러메세지가 떨어지고 있었다.

java.lang.IllegalArgumentException: Model has no value for key 'e_e_ttt'
at org.springframework.web.servlet.view.RedirectView.replaceUriTemplateVariables(RedirectView.java:387)
at org.springframework.web.servlet.view.RedirectView.createTargetUrl(RedirectView.java:346)
at org.springframework.web.servlet.view.RedirectView.renderMergedOutputModel(RedirectView.java:307)
at org.springframework.web.servlet.view.AbstractView.render(AbstractView.java:316)
at org.springframework.web.servlet.DispatcherServlet.render(DispatcherServlet.java:1370)
at org.springframework.web.servlet.DispatcherServlet.processDispatchResult(DispatcherServlet.java:1116)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:1055)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:94

 

문제는 리다이렉트 하려는 url에 e_e_ttt라는 문자열을 '{', '}'가 감싸고 있었던 것이다. 

ex) www.hello.com?name=blog&param={e_e_ttt} 

 

왜 문제가 되느냐???

URL내에서 몇 몇 문자는 특별한 의미로 예약되어 있거나, 어떤 문자는 US-ASCII의 출력 가능한 문자 집합에 포함되어 있지 않고 어떤 문자는 몇몇 인터넷 게이트웨이와 프로토콜에서 혼동되는 것으로 알려져 있어, 사용하면 안되는 것들이 있다.

 

URL에서 사용하면 안되는 문자들

% : 인코딩된 문자에 사용할 이스케이프 토큰으로 선점

/  : 경로 컴포넌트에서 선점

. : 경로 컴포넌트에서 선점

.. : 경로 컴포넌트에서 선점

# : 프래그먼트의 구획 문자로 선점

? : 질의 문자열의 구획 문자로 선점

; : 파라미터의 구획 문자로 선점

: : 스킴, 사용자 이름/비밀번호, 호스트/포트의 구획 문자로 선점

$, + : 선점

@ & = : 특정 스킴에서 특별한 의미가 있기 때문에 선점

{}|\~[]` : 게이트웨이와 같은 여러 전송 에이전트에서 불안전하게 다루기 때문에 제한됨

<> " : 안전하지 않음. 반드시 인코딩되어야함

 

근데 이번에 문제가 된 경우에는 {} 문자열이 있었기 때문이다.

 

항상 안전하지 않은 문자들에 대해서는 인코딩을 하도록 하자!!!!

 

반응형
반응형

서버간 통신시 acl체크가 필요한 경우가 많이 있다.

항상 telnet 응답값을 보고 이게 정상적으로 된게 맞는지 헷갈리는 경우가 있어 추후 기억을 위해 포스팅

 

출발서버 -> 목적지 서버 확인

telnet ip port

출발서버에서 telnet 목적지서버IP 확인하고싶은 port로 명령을 내린다.

ex) 10.65.777.23 서버에서 10.62.332.555 80port 요청의 acl 을 확인

10.65.777.23 서버에서 telnet 10.62.332.555 80 로 요청

 

반응 message에 따라 유형이 다르다.

1. Trying 10.62.332.555... 

위와 같은 반응일 경우 방화벽 오픈이 안된 것이다.

 

2. Trying 10.62.332.555...
telnet: connect to address 10.161.241.152: Connection refused
telnet: Unable to connect to remote host: Connection refused

바로 연결거부가 발생하면 방화벽 오픈은 되었으나 해당 서버에 해당 포트로 프로세스가 안 떠있는 것이다.

 

Trying 172.0.0.1...
Connected to 172.0.0.1
Escape character is '^]'.

방화벽 오픈이 정상적으로 되었고 프로세스가 올라가 있는 것이다.

=> 정상적으로 통신을 할 수 있는 상태이다.

반응형
반응형

특정서비스의 로그를 spark으로 분석하기 위해 하둡커맨드 서버로 데이터를 가져와 hdfs에 put하는 과정 중 발생한 내용이다.

 

특정서비스(10대 서버)에서 한 달치의 로그(약 4.4g - 각 서버당)를 커맨드서버에서 wget으로 가져와 작업을 진행하였다.

 

wget으로 network bandwidth 옵션을 줘서 네트워크 대역폭을 모두 사용하지 않도록 했어야했지만 별다른 생각없이 wget을 하게 되었다.

 

문제는 해당 하둡 클러스터가 카프카(KAFKA)와 연결되어 있고 실시간으로 consuming하여 streaming하는 서비스에서 발생하였다.

 

네트쿼으 대역폭을 모두 사용하게 되어 카프카로부터 정상적인 컨슈밍이 되지 못했던 것이다.

 

앞으로는 데이터를 하둡클러스터로 가져올 때 혹은 다른 서버로 데이터를 옮길 때 항상 wget에 network bandwidth옵션을 주도록 하자.

 

wget으로 가져오는 과정에서 네트워크 인바운드가 훅....튀었다.

 

ex) wget으로 데이터가져올 때 limit으로 50kbyte를 주는 예시

wget --limit-rate=50k {데이터 떙겨올 서버주소}

--limit-rate=amount Limit the download speed to amount bytes per second. Amount may be expressed in bytes, kilobytes with the k suffix, or megabytes with the m suffix. For example, --limit-rate=20k will limit the retrieval rate to 20KB/s. This is useful when, for whatever reason, you don't want Wget to consume the entire available bandwidth.

 

주의하도록하자!!!

반응형
반응형

JPA Entity에서 복합키(composite key)를 사용할 떄 복합키에 해당하는 컬럼 모두에 @Id

을 달아주어야 한다.

 

그 뿐만 아니라 class에도 @IdClass(클래스명.class)를 달아주어야 한다.

이렇게만 선언해주고 실행을 하게 되면 다음과 같은 에러를 만나게 된다.

Caused by: org.hibernate.MappingException: Composite-id class must implement Serializable:

해당 클래스에 Serializable을 implements해줍니다.

Serializable을 해주어야하는 이유는 stackoverflow의 설명으로 대신하겠습니다. (저도 JPA를 막 학습하고 사용하고 있는 입장은 아니라서..특정 이슈 때마다 검색으로 적용해 나가고 있긴 한 데 한 번 제대로 된 학습이 필요할 것 같긴합니다.)

The session object needs to be serializable hence all objects referenced by it must be serializable as well. The id is used as a key to index loaded objects in the session. In case of CompositeId s the class itself is used as the id.

ref : https://stackoverflow.com/questions/9271835/why-composite-id-class-must-implement-serializable

반응형
반응형

간단하게 메모리위에 데이터를 올려놓고 사용하고 싶은 경우 보통 ehcache를 많이 사용하게 된다.

 

이때 주의해야하는 점이 있다.

 

동일한 클래스 내에서 호출되는 메서드에 @Cacheable을 적용해도 정상적으로 동작하지 않고 무시되어져 버린다. 프록시 생성방식때문...

 

다음처럼 getSpecificRangeContents메서드 내에서 getAllContentsIdAndLocation메서드를 같은 클래스내에서 호출하게되면 정상동작하지 않는 것이다.

간단히 설명하자면 캐시는 프록시기반으로 동작하는데 프록시 클래스는 모든 요청과 응답의 인터셉터에 의해 생성되어지기 때문에 같은 클래스 내부(internal) 콜에 의해서는 캐시기능이 적용되지 않는다. 관련하여 읽어보면 프록시 동작방식과 ehcache를 사용함에 도움이 될 만한 문서를 첨부한다.

Only external method calls coming in through the proxy are intercepted. This means that self-invocation, in effect, a method within the target object calling another method of the target object, will not lead to an actual cache interception at runtime even if the invoked method is marked with @Cacheable.

ref : https://stackoverflow.com/questions/16899604/spring-cache-cacheable-not-working-while-calling-from-another-method-of-the-s/40340964

 

[ ehcache관련 읽어보면 좋은 자료 ]

Transactions, Caching and AOP: understanding proxy usage in Spring

https://spring.io/blog/2012/05/23/transactions-caching-and-aop-understanding-proxy-usage-in-spring

 

ehcache-spring-annotations - UsingCacheable.wiki

https://code.google.com/archive/p/ehcache-spring-annotations/wikis/UsingCacheable.wiki

 

해당문제가 스프링4.3에서는 self-autowiring으로 해결되었다고 한다.

 

잘알고 쓰자...

 

반응형
반응형

새롭게 구축한 클러스터에 기존 하둡클러스터의 데이터를 distcp를 하려고했을 때 다음과 같은 에러가 발생했다.

[irteam@am~~~server ~]$ hadoop distcp -m 30 -bandwidth 10 /user/hdfs1/20190916 hdfs://newcluster:8020/user/hdfs/20190916

19/09/24 14:02:47 ERROR tools.DistCp: Invalid arguments:
org.apache.hadoop.ipc.RemoteException(org.apache.hadoop.ipc.StandbyException): Operation category READ is not supported in state standby. Visit https://s.apache.org/sbnn-error
        at org.apache.hadoop.hdfs.server.namenode.ha.StandbyState.checkOperation(StandbyState.java:88)
.
.
(생략)
.   
Invalid arguments: Operation category READ is not supported in state standby. Visit https://s.apache.org/sbnn-error
.
(생략)
.  

문제는 신규클러스터의 standby의 네임노드 주소로 distcp를 하려고 하였던게 원인이였다.

active상태의 네임노드의 주소로 바꾸어주니 정상적으로 되었다.

 

distcp를 할 떄는 active상태의 namenode주소로 해주어야 한다!

반응형
반응형

MYSQL 두 개의 테이블을 join해서 데이터를 가져오는 도중 컬럼값이 BLOB로 보이는 현상 발생

join을 할 떄 한 테이블에서는 BIGINT타입의 컬럼과 또 다른테이블에서는 VARCHAR타입의 컬럼을 조인하는 과정에서 발생

select시 해당 컬럼에 CONVERT(컬럼명 USING utf8)로 TEXT로 변환하여 확인하였다.

 

BLOB란
binary large object의 약어로 
BLOB컬럼 타입을 이용하면 일반적인 int나 char와는 달리 이미지나 바이너리 파일을 테이블에 담을 수 있다.
BLOB 필드는 소팅이나 INDEX는 생성할 수 없다. 

MYSQL에서 지원하는 BLOB타입은 4가지

1. TINYBLOB (TINYTEXT)
- A BLOB or TEXT column with a maximum length of 255 (2^8 - 1) characters.

2. BLOB (TEXT)
- A BLOB or TEXT column with a maximum length of 65535 (2^16 - 1) characters.
 
3. MEDIUMBLOB (MEDIUMTEXT)
- A BLOB or TEXT column with a maximum length of 16777215 (2^24 - 1) characters.
 
4. LONGBLOB(LONGTEXT)
- A BLOB or TEXT column with a maximum length of 4294967295 (2^32 - 1) characters.

 

반응형
반응형

JPA 직접 @Query애노테이션을 사용해 원하는 쿼리를 직접 사용할 수 있다.

이 때 주의해야할 점은 from절에 db의 테이블명이 아닌 해당 테이블의 entity로 등록한 모델을 입력해주어야 한다.

 

문제상황

from절의 테이블명(channel)을 작성 

 

다음과 같은 에러 발생

Caused by: java.lang.IllegalArgumentException: org.hibernate.hql.internal.ast.QuerySyntaxException: channel is not mapped [select max(id) as id from channel] at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:138) ~[hibernate-core-5.3.10.Final.jar:5.3.10.Final] at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:181) ~[hibernate-core-5.3.10.Final.jar:5.3.10.Final] at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:188) ~[hibernate-core-5.3.10.Final.jar:5.3.10.Final] at org.hibernate.internal.AbstractSharedSessionContract.createQuery(AbstractSharedSessionContract.java:729) ~[hibernate-core-5.3.10.Final.jar:5.3.10.Final] at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:23) ~[hibernate-core-5.3.10.Final.jar:5.3.10.Final] at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_151] at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_151] at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_151] at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_151]

 

문제해결

entity로 등록한 Java class로 변경

반응형

+ Recent posts