metatron-app / metatron-discovery

Powerful & Easy way for big data discovery
https://metatron.app
Apache License 2.0
442 stars 112 forks source link

Enhanced search within Data Storage(Datasource, Data Connection) list screen #684

Closed AnnieHwang closed 5 years ago

AnnieHwang commented 6 years ago

Is your feature request related to a problem? Please describe. 데이터소스 목록 화면에서 검색 기능의 강화하는 개선이 필요합니다.

Describe the solution you'd like 검색란의 필터링 기능을 추가하여 검색창의 기능을 개선하고자 합니다. 참고로 현재 깃허브에서는 이런방식을 이용하고 있습니다. image

데이터소스를 시작으로 모든 관리자(MANAGEMENT, ADMINISTRATOR)에 해당 내용을 적용하려고 합니다. 각 부분은 별도의 이슈로 진행하고 해당 이슈는 데이터소스 목록 화면 변경부분 내용만 반영하도록 하겠습니다..

AnnieHwang commented 6 years ago

@kyungtaak 아래의 모습과 같이 초안을 정하였습니다. 기술적으로 문제가 없는지 확인부탁드립니다. image

minjung-cho commented 6 years ago

@kyungtaak @AnnieHwang 데이터소스 화면향으로 작업한 기획서 입니다. 공통 UI라 다른 케이스들도 검토 중이니, 완료되면 추가 정의서 공유하겠습니다. 2018-11-09 8 58 32 2018-11-09 8 58 04 2018-11-09 8 58 13 2018-11-09 8 58 21

koeun222 commented 6 years ago

@AnnieHwang 검색필터링 관련 디자인 공유드려요 가로 1200px안에 다 들어오기 빡빡해서 시간필터링을 셀렉박스로 고르거나 range 입력할수있게 넣었습니다 image

kyungtaak commented 6 years ago

@AnnieHwang @minjung-cho

minjung-cho commented 6 years ago

@kyungtaak @AnnieHwang 먼저 답변드립니다

  1. 필터링 저장 나갔다 들어왔을때 필터링을 리셋하는 것이 기본입니다만... 사용자의 페이지별로 필터설정을 저장하는 것이 있으면 편리할 것 같습니다. 하지만 advanced도 그렇고 다른 페이지에서는 필터 기준으로 뽑을 것이 많지 않아서 현재로선 잘 사용될것 같진 않고, 디자인도 고민되어야 해서... Advanced 진행할때 함께 고려해 보는건 어떠신가요?
  2. 초기 기준값 '글로벌 설정'이라기 보다는, 사용 맥락에 따라 페이지마다 초기 기준값을 다 다르게 정의해야할 것 같습니다. 데이터소스는 상태, 할당, 생성자 정도 생각하는데, 인제스쳔 타입과 디비 타입도 넣어야 할까요? @AnnieHwang 의견 부탁드립니다.
  3. 사용자,그룹 필터 항목 '데이터소스 등록한 사용자' 는, 사용자 중에서 '데이터소스를 등록한 사용자'를 필터링해서 필터 선택지로 보여주자는 말씀이신가요? 그렇다면 결국 데이터소스 권한이 있는 사용자 또는 그룹만 제공이 되므로 사용성이 더 좋을 것 같습니다.
ufoscw commented 6 years ago

@koeun222 @minjung-cho 올려주신 디자인과 기획서가 달라서 문의드립니다. 시간 필터는 created, modified 2가지 옵션이 아닌가요?

deidera08 commented 6 years ago

@ufoscw 처음에는 created, modified 2가지 옵션으로 제공되는것으로 고려되었습니다만, 현재 modified(updated) 날짜 반영이 되는 조건이 큰 의미가 없다고 판단해서 제거되었습니다. (현재 updated 날짜가 반영이 되는 액션은 이름/정보등의 정보가 수정되었을때고, 데이터 자체의 정보(논리정보 등)이 수정되었을 경우 updated 날짜가 반영되지 않습니다.) 때문에 updated 옵션은 more나 advenced등에서 제공하고 전면에 노출될 필요는 없을듯 합니다.

기획서에 해당 내용 업데이트 하도록 하겠습니다.

ufoscw commented 6 years ago

@deidera08 최근 업데이트된, 최근 등록된의 "최근" 은 몇일인가요? 그리고 "최근 본" 조건으로는 검색이 힘듭니다.

deidera08 commented 6 years ago

@ufoscw '최근 업데이트된', '최근 등록된', '최근 본' 의 옵션은 필터라기 보다는 정렬기능입니다. 때문에 최근의 조건에 날짜를 정의하지 않았습니다.

더불어 위 검색필터들은 본 데이터소스 화면뿐 아니라 글로벌 적용을 염두에 두고 있습니다. "최근 본" 옵션은 논의하여 재고하도록 하겠습니다(실질적 의견주셔서 감사합니다 :)

ufoscw commented 6 years ago

@minjung-cho @AnnieHwang CheckBox 타입일 경우는 모두 All 체크가 필요하지 않을까요? 그리고 CheckBox 타입의 목록형 검색 조건은 UI가 통일 되어도 되지 않을까요? 최상단은 텍스트 필터링, 바로 밑에는 All 버튼.

ufoscw commented 6 years ago

@brandon-wonjune DataSource List Filter API 2개가 추가되었습니다.

  1. DataSource List Filter Criteria

    (GET) /api/datasources/criteria

    https://tde.sktelecom.com/wiki/display/METATRON/DataSource+v2#DataSourcev2-ListofDataSourceFilterCriterion

  2. DataSource List Filter

    (GET) /api/datasources/criteria/{CriterionKey}

    https://tde.sktelecom.com/wiki/display/METATRON/DataSource+v2#DataSourcev2-ListofDataSourceFilter

검색조건을 구성할때 1번 API를 사용하시면 되고, 실제 검색 조건 목록을 표시할때 2번 API를 사용하시면 됩니다.

변경된 파라미터로 호출가능한 목록 API는 작업 완료 후 다시 알려드릴게요.

minjung-cho commented 6 years ago

@minjung-cho @AnnieHwang CheckBox 타입일 경우는 모두 All 체크가 필요하지 않을까요? 그리고 CheckBox 타입의 목록형 검색 조건은 UI가 통일 되어도 되지 않을까요? 최상단은 텍스트 필터링, 바로 밑에는 All 버튼.

텍스트 필터링이 불필요한 것(e.g.Ingestion 타입)이 있어서 있는 것, 없는 것 두벌로 가는 것이 좋을 것 같습니다. All에 대해서는 공통적으로 적용하겠습니다~

2018-11-20 11 06 30 2018-11-20 11 06 35 2018-11-20 11 06 42 2018-11-20 11 06 50
ufoscw commented 6 years ago

@brandon-wonjune filter된 datasouce 목록 호출 API 입니다.

(POST) /api/datasources/filter(?page,size,projection)

https://tde.sktelecom.com/wiki/display/METATRON/DataSource+v2#DataSourcev2-ListofDataSourcewithfilter

brandon-wonjune commented 6 years ago

@ufoscw 작업하면서 문의사항이 있습니다.

Q1 초기에 필터 목록을 조회할때 사용하는 api api/datasources/criteria 를 사용할때 criterionKey가 'MORE'일때는 아래의 스크린샷을 표기하는것으로 이해했습니다. 2018-11-21 3 25 11 여기서 'Filter'에 해당하는지 'Criteria'에 해당하는지는 어떤 값을 기준으로 판단하면 되나요?

Q2 세부사항 조회할때 사용하는 api /api/datasources/criteria/{CriterionKey} 는 아래의 스크린샷의 목록을 조회할 때 사용하는 것으로 이해했는데 2018-11-21 3 30 44 여기서 해당 목록 중, 'subTitle(ex.My group)'이 있는지 없는지 여부는 api내부의 'filters'가 있고 없고로 판단하면 될까요?

Q2-1 동일 api의 결과 중 목록의 'search'기능이 있는지 없는지는 단순히 CREATORPUBLISH만 허용하는것으로 하면 되나요?

ufoscw commented 6 years ago

@brandon-wonjune

  1. 기획팀에 문의한 filter의 실제의미는 sorting이라고 합니다. 상단 댓글 내용 참조하시면 됩니다. sorting 기능은 이번 릴리즈에는 포함하지 않습니다.

  2. subCriteria 목록은 한번 서브타이틀로 그룹핑해서 체크박스로 렌더링 하면 됩니다. 구현방법에 따라 filters, subCriteria가 혼재되어 있어도 렌더딩 되도록 구현가능하지 않을까요? 이 부분은 퍼블리싱된 HTML태그에 따라 달라질것 같기는 합니다.

2-1. search 기능 여부는 속성을 하나 추가하도록 하겠습니다. isSearchable

brandon-wonjune commented 6 years ago

@ufoscw 2번에서 답변 주신것처럼 subCriteria가 있으면 서브타이틀이 있는것으로 하면은 가능은합니다. 그런데 filters와 subCriteria가 동일 뎁스에서 혼재되어 있는경우가 있나요?

ufoscw commented 6 years ago

@brandon-wonjune 현재 기획상에는 없습니다. subCriteria의 criterionName이 없는경우와 비슷하다고 볼수 있겠네요.

ufoscw commented 6 years ago

@brandon-wonjune DataSourceListCriterion에 "searchable" 속성이 추가되었습니다.

brandon-wonjune commented 6 years ago

@ufoscw Create time 중 아래 from 과 to가 있고없고는 어떤 방식으로 체크하면 되나요? 2018-11-26 11 44 46

ufoscw commented 6 years ago

@brandon-wonjune criterionType이 RANGE_DATETIME 인경우는 항상 from, to가 필요합니다. UI상에서 Today나 Last 7 days 경우는 UI상에 from, to가 보여지지 않지만 실제 파라미터는 from, to로 만들어서 보내주세요.

kyungtaak commented 6 years ago

@AnnieHwang @ufoscw data connection 까지 고려하여 작업 부탁드립니다. (제목도 변경 부탁드릴게요.)

AnnieHwang commented 6 years ago

@ufoscw 데이터소스, 데이터커넥션 및 데이터모니터링 관련 필터 항목을 올려드립니다. 노란색 항목이 default로 화면에 표출될 필터 항목입니다. 변경이 필요하시면 말씀부탁드립니다. image (아래 파일을 참고하세요) FilterLists-181116.xlsx

brandon-wonjune commented 6 years ago

@ufoscw

api 문의 드립니다.

Q1.

(POST) /api/datasources/filter(?page,size,projection)

이 api는 filter를 선택했을때만 적용되는건가요? 그리고 projection은 기존것과 동일하게 쓰면되나요?

Q2. 만약 데이터소스 초기진입시와 모든 필터가 ALL이나 NONE(아무것도 선택이 안된상태)에서는 기존처럼

api/datasources?size=20&page=0&sort=createdTime%2Cdesc&projection=forListView

이 api를 호출하면 되나요?

ufoscw commented 6 years ago

@brandon-wonjune

  1. filter 선택안했을 경우에도 사용가능합니다. request body 없이 querystring만 보내서 사용하면 됩니다. projection은 동일합니다.
  2. 위의 답변 처럼 request body 없이 query string만 보내서 사용하시면 됩니다. 기존 API는 다중 필터링 조건이 허용되지 않는 단순한 GET 방식의 API이며 신규 추가된 API는 다중 필터링이 허용되는 POST 방식의 API니 필요에 따라 사용하시면 됩니다. 한 화면에서 굳이 2개의 API를 사용할 필요는 없어 보입니다.
minjung-cho commented 6 years ago

@ufoscw 개발 도중에 죄송합니다만, 몇가지 기획 변경사항이 생겼습니다. 아래에 논의 과정과 결과 공유드리니 의견 부탁드립니다.

  1. 체크박스 리스트 > All
    1. 변경 : All 제거
    2. 사유 : ‘All’의 사용 목적에 대해서 다시 논의해 보았습니다. 필터링 할때 a.전체 목록에서 몇개만 선택하고 싶을때 b.전체 목록에서 몇개만 빼고 싶을때 가 있을 겁니다. 케이스 b에서 ‘All’ 을 선택하여 모든 항목을 체크한 후, 몇개를 체크 해제 할것입니다. 하지만 현재 시스템 전반적으로 All을 선택했을 때 전체 데이터가 선택되지 않고, UI에 보이는 목록만 선택되도록 되어 있습니다. 이 부분이 여러 경로에서 사용성 이슈로 지적이 되었는데요, 이 정책(?)이 유지된다면 케이스 b를 완전히 수행할 수 없기 때문에 All이 큰 의미가 없을것이라 판단이 되었습니다. 그래서 All을 제거하여 사용성에 혼란을 줄 수 있는 케이스 b를 차단하자는게 공통된 의견이었습니다. 케이스 b는 advanced 서치로 가능하면 좋을 것 같습니다.
  2. 사용자 기준 (Creator/Updater)
    1. 추가
      1. 내 그룹, 내 그룹 멤버를 유의미한 순으로 정렬
      2. 카테고리 안에서 5개씩 목록을 불러옴
      3. 내 그룹 멤버 목록에서는 me를 보여주지 않고, me를 제외한 사용자는 한번만 노출함
    2. 사유 : 영역이 좁기 때문에 추천 목록 중 선택할 필요가 있고, 불필요한 중복 목록은 나오지 않아야 한다는 의견입니다.
  3. Text search
    1. 변경 : 항목이 5개 이상일 경우만 Text search 제공
    2. 사유 : 기준이 추가될 때마다 Text search 제공을 ‘결정’해야하는 수고를 덜기 위해서 UI단에서 텍스트 서치 기능 노출을 결정하자는 의견입니다.

(1,2 번을 적용해 본 안입니다) 2018-11-27 4 46 39

@AnnieHwang @deidera08 논의한 내용과 다른 부분이 없는지 확인 부탁드립니다.

brandon-wonjune commented 6 years ago

@ufoscw 문의사항있습니다. 현재 more 필터에서 필터를 추가시켜서 api 조회를 하고있습니다. more가 아닌 기존 default로 제공되는 criterion 필터들은 적용시 정상적으로 조회가 되지만, 새로 추가한 필터를 적용하여 데이터소스 목록 조회시 에러가 발생합니다. 아래는 조회 예시입니다.

DATASOURCE_TYPE

// api
api/datasources/filter?projection=forListView&page=0&size=20

// params
{dataSourceType: ["MASTER", "JOIN", "VOLATILITY"]}

// error 
app.metatron.discovery.common.exception.UnknownServerException
    at app.metatron.discovery.common.exception.GlobalExceptionHandler.handleAll(GlobalExceptionHandler.java:149)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205)
    at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133)
    at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:97)
    at org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver.doResolveHandlerMethodException(ExceptionHandlerExceptionResolver.java:384)
    at org.springframework.web.servlet.handler.AbstractHandlerMethodExceptionResolver.doResolveException(AbstractHandlerMethodExceptionResolver.java:59)
    at org.springframework.web.servlet.handler.AbstractHandlerExceptionResolver.resolveException(AbstractHandlerExceptionResolver.java:136)
    at org.springframework.web.servlet.handler.HandlerExceptionResolverComposite.resolveException(HandlerExceptionResolverComposite.java:76)
    at org.springframework.web.servlet.DispatcherServlet.processHandlerException(DispatcherServlet.java:1222)
    at org.springframework.web.servlet.DispatcherServlet.processDispatchResult(DispatcherServlet.java:1034)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:984)
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:901)
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:970)
    at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:872)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:661)
    at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:846)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:742)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.web.filter.ApplicationContextHeaderFilter.doFilterInternal(ApplicationContextHeaderFilter.java:55)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.actuate.trace.WebRequestTraceFilter.doFilterInternal(WebRequestTraceFilter.java:110)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at app.metatron.discovery.common.web.CommonLocalVariableFilter.doFilter(CommonLocalVariableFilter.java:58)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at app.metatron.discovery.common.web.LogbackMdcFilter.doFilter(LogbackMdcFilter.java:59)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:317)
    at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:127)
    at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:91)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:114)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:137)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:111)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:170)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:63)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.oauth2.provider.authentication.OAuth2AuthenticationProcessingFilter.doFilter(OAuth2AuthenticationProcessingFilter.java:176)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:116)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.web.filter.CorsFilter.doFilterInternal(CorsFilter.java:96)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:64)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:105)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:56)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:214)
    at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:177)
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:347)
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:263)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.session.web.http.SessionRepositoryFilter.doFilterInternal(SessionRepositoryFilter.java:167)
    at org.springframework.session.web.http.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:80)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:197)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.actuate.autoconfigure.MetricsFilter.doFilterInternal(MetricsFilter.java:106)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:199)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:478)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:140)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:81)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:87)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:342)
    at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:803)
    at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
    at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:868)
    at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1459)
    at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
    at java.lang.Thread.run(Thread.java:748)
Caused by: java.lang.NullPointerException
    at app.metatron.discovery.domain.datasource.DataSourceController.filterDataSources(DataSourceController.java:891)
    at app.metatron.discovery.domain.datasource.DataSourceController$$FastClassBySpringCGLIB$$8acf3b5d.invoke(<generated>)
    at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204)
    at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:669)
    at app.metatron.discovery.domain.datasource.DataSourceController$$EnhancerBySpringCGLIB$$5ecdbee0.filterDataSources(<generated>)
    at sun.reflect.GeneratedMethodAccessor403.invoke(Unknown Source)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205)
    at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133)
    at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:97)
    at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:827)
    at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:738)
    at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:967)
    ... 88 more

나머지 추가 criterion 타입 (connectionType, sourceType) 도 위와 같은 에러가 발생합니다.

ufoscw commented 6 years ago

@brandon-wonjune API 오류 수정되었습니다.

brandon-wonjune commented 6 years ago

@ufoscw 네 정상적으로 more내 모든 criterion 필터에 대해 조회가 되는것을 확인했습니다. 그런데 테스트 도중에 발견한 에러인데요. datasource를 제거하면 에러가 발생하는데 다른화면 갔다오면은 삭제가 된 상태로 표시됩니다.

// api
(DELETE) api/datasources/{sorceId}

// error
app.metatron.discovery.common.exception.UnknownServerException
    at app.metatron.discovery.common.exception.RestExceptionHandler.handleMiscFailures(RestExceptionHandler.java:95)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205)
    at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133)
    at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:97)
    at org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver.doResolveHandlerMethodException(ExceptionHandlerExceptionResolver.java:384)
    at org.springframework.web.servlet.handler.AbstractHandlerMethodExceptionResolver.doResolveException(AbstractHandlerMethodExceptionResolver.java:59)
    at org.springframework.web.servlet.handler.AbstractHandlerExceptionResolver.resolveException(AbstractHandlerExceptionResolver.java:136)
    at org.springframework.web.servlet.handler.HandlerExceptionResolverComposite.resolveException(HandlerExceptionResolverComposite.java:76)
    at org.springframework.web.servlet.DispatcherServlet.processHandlerException(DispatcherServlet.java:1222)
    at org.springframework.web.servlet.DispatcherServlet.processDispatchResult(DispatcherServlet.java:1034)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:984)
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:901)
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:970)
    at org.springframework.web.servlet.FrameworkServlet.doDelete(FrameworkServlet.java:894)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:667)
    at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:846)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:742)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.web.filter.ApplicationContextHeaderFilter.doFilterInternal(ApplicationContextHeaderFilter.java:55)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.actuate.trace.WebRequestTraceFilter.doFilterInternal(WebRequestTraceFilter.java:110)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at app.metatron.discovery.common.web.CommonLocalVariableFilter.doFilter(CommonLocalVariableFilter.java:58)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at app.metatron.discovery.common.web.LogbackMdcFilter.doFilter(LogbackMdcFilter.java:59)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:317)
    at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:127)
    at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:91)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:114)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:137)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:111)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:170)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:63)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.oauth2.provider.authentication.OAuth2AuthenticationProcessingFilter.doFilter(OAuth2AuthenticationProcessingFilter.java:176)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:116)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.web.filter.CorsFilter.doFilterInternal(CorsFilter.java:96)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:64)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:105)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:56)
2018-11-27 09:49:08.773 at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
 ERROR  at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331)
    at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:214)
    at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:177)
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:347)
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:263)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
[127.0.0.1-admin] [http-nio-8180-exec-2] a.m.d.c.exception.RestExceptionHandler     at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
 :  at org.springframework.session.web.http.SessionRepositoryFilter.doFilterInternal(SessionRepositoryFilter.java:167)
 [API:/api/datasources/550a8af3-01b8-4355-985b-2258b900c1c3] GB0001 null: NullPointerException: , {}
    at org.springframework.session.web.http.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:80)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:197)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.actuate.autoconfigure.MetricsFilter.doFilterInternal(MetricsFilter.java:106)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:199)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:478)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:140)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:81)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:87)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:342)
    at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:803)
    at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
    at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:868)
    at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1459)
    at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
    at java.lang.Thread.run(Thread.java:748)
Caused by: java.lang.NullPointerException
    at app.metatron.discovery.domain.datasource.DataSourceEventHandler.handleDataSourceAfterDelete(DataSourceEventHandler.java:414)
    at app.metatron.discovery.domain.datasource.DataSourceEventHandler$$FastClassBySpringCGLIB$$d36826d1.invoke(<generated>)
    at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204)
    at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:669)
    at app.metatron.discovery.domain.datasource.DataSourceEventHandler$$EnhancerBySpringCGLIB$$be27bb68.handleDataSourceAfterDelete(<generated>)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.util.ReflectionUtils.invokeMethod(ReflectionUtils.java:216)
    at org.springframework.data.rest.core.event.AnnotatedEventHandlerInvoker.onApplicationEvent(AnnotatedEventHandlerInvoker.java:98)
    at org.springframework.data.rest.core.event.AnnotatedEventHandlerInvoker.onApplicationEvent(AnnotatedEventHandlerInvoker.java:59)
    at org.springframework.context.event.SimpleApplicationEventMulticaster.doInvokeListener(SimpleApplicationEventMulticaster.java:172)
    at org.springframework.context.event.SimpleApplicationEventMulticaster.invokeListener(SimpleApplicationEventMulticaster.java:165)
    at org.springframework.context.event.SimpleApplicationEventMulticaster.multicastEvent(SimpleApplicationEventMulticaster.java:139)
    at org.springframework.context.support.AbstractApplicationContext.publishEvent(AbstractApplicationContext.java:393)
    at org.springframework.context.support.AbstractApplicationContext.publishEvent(AbstractApplicationContext.java:347)
    at org.springframework.data.rest.webmvc.RepositoryEntityController.deleteItemResource(RepositoryEntityController.java:440)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205)
    at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133)
    at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:97)
    at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:827)
    at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:738)
    at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:967)
    ... 88 more
ufoscw commented 6 years ago

@minjung-cho

  1. All 정책이 그렇다면 없어도 괜찮습니다.

  2. 현재 Creator는 아래 기준이 필터링 조건입니다. 나, 내가 속한 그룹, 데이터소스 등록한 사용자, 데이터 매니저 권한이 있는 그룹명 상단 코멘트에서 kyungtaak님이 제안해주신 부분이고 @minjung-cho 님이 수용하셔서 그렇게 개발되어 있습니다. 이 기준으로는 리스트 목록이 길게 나오지 않을것 같은데요. 이론적으로 최대 리스트 사이즈는 (그룹수 * 2 + 데이터 소스를 등록한 사용자) 정도 입니다. 드랍다운안에서 스크롤 다운시 페이징하는 경우는 본적이 있지만 서브 카테고리를 넣고 카테고리별 페이징을 넣는 UI는 너무 복잡해보이는데요..

그리고 중복건에 대해서는 사용자는 Me 외에는 중복되는 사용자가 없습니다. 그룹명이 중복될수 있는데 카테고리의 의미가 있으니 중복되어도 상관 없지 않을까요?

  1. 5건의 기준은 드랍다운 세로 사이즈가 5건이기 때문인가요?
minjung-cho commented 6 years ago

@ufoscw @AnnieHwang 님과 논의하신것 같아서 1,2 번은 결론만 남기겠습니다.

  1. All 제거
  2. Creator
    • Users : 데이터소스를 생성한적이 있는 사용자. '나'가 최상위 목록
    • Groups : 데이터소스 생성 권한이 있는 그룹. 내가 속한 그룹이 최상위 목록
    • 카테고리 내의 부분 스크롤 또는 로드 UI는 사용하지 않음 2018-11-28 1 52 38
  3. 텍스트 서치 목록이 10개만 되어도 텍스트 서치가 필요할 수 있을 것 같아서 임의로 정한 것이 5개 입니다. 불특정 목록에 대해서만 텍스트서치를 제공하는게 어떠냐는 의견을 전달 받았습니다. DB 타입은 이미 9개가 있고, 사용자/그룹 은 각 1개만 있을 가능성이 있습니다. 불특정 목록에만 텍스트 서치를 제공한다면.. DB 타입에는 없고, 사용자/그룹에는 있게 되는데 통일성이 없어보이지 않을까 우려가 됩니다. 최소한 개수로 UI 유무가 결정된다면 사용자가 리스트가 많아서 서치를 제공하는 구나... 라고 느낄수 있을것 같습니다. 다른 분들 의견은 어떤지 궁금합니다. @AnnieHwang @deidera08 @koeun222 사실.. 마이너한 부분인것 같아서.. 복잡도나 퍼포먼스 저하가 예상되는 부분이 있다면 모든 기준에 텍스트 서치를 제공하는 것이 좋을 것 같습니다!
brandon-wonjune commented 5 years ago

@ufoscw 데이터소스 쪽 완료했는데요 커넥션 api도 같은 스펙으로 전달이 되나요?

ufoscw commented 5 years ago

@brandon-wonjune 네 스펙은 동일하며 api 주소만 바뀝니다.

deidera08 commented 5 years ago

@brandon-wonjune @AnnieHwang @minjung-cho FilterLists-181129.xlsx default 커넥션 필터 항목입니다. (Security 항목은 문구가 길어서 줄였습니다.)

ufoscw commented 5 years ago

@brandon-wonjune

  1. 날짜 검색시 확인한 사항입니다.

    metatron_discovery
  2. 검색 조건 추가된게 있으니 다국어도 추가부탁드려요. msg.storage.ui.criterion.open-data : Open Data msg.storage.ui.criterion.modified-time : Modified Time

  3. More를 통해 추가한 조건은 다시 삭제가 되어야 하는데 기획서 확인바랍니다.

ufoscw commented 5 years ago

@brandon-wonjune @deidera08 날짜 검색시 오늘, 최근 7일은 기획서에 current time으로 되어 있네요. 명시적으로 날짜를 표시하지 않고 "현재 시간"으로 표기하는게 공통 정책인가요?

deidera08 commented 5 years ago

@ufoscw @AnnieHwang @minjung-cho 아닙니다. 위에 해석하신 바가 맞습니다. 현재의 시간을 표기해 달라는 의미였습니다.

brandon-wonjune commented 5 years ago

@ufoscw

  1. ALL과 LAST 7 DAYS 일때 명시적으로 날짜를 추가하도록 변경하였습니다. (셀렉트 범위 확장 추가)
  2. 새로 추가된 다국어에 대해 메시지 처리를 추가하였습니다.
deidera08 commented 5 years ago

@ufoscw @brandon-wonjune @AnnieHwang @minjung-cho 위의 날짜 표현에 내용을 보완합니다.

  1. 날짜를 Today 선택시 상단 필터값에 오늘 날짜를 표기합니다. 예) Created time: 2018-11-29 hh:mm

  2. 날짜를 Last 7days 선택시 상단 필터값에 7일전 날짜~오늘 날짜를 표기합니다. 예) Created time: 2018-11-23 00:00 ~ 2018-11-29 hh:mm

  3. 날짜를 Between 선택시 상단 필터값에 지정한 날짜를 표기합니다. 날짜를 지정하는것이 필수는 아니므로 미지정시 Past time ~ Current time으로 표기합니다. (from, to 두 값 모두 지정을 하지 않았을 경우 사실상 All과 같음) 예) Created time: 2018-11-23 00:00 ~ 2018-11-29 hh:mm 예) Created time: Past time ~ 2018-11-29 hh:mm 예) Created time: 2018-11-23 00:00 ~ Current time 예) Created time: Past time ~ Current time

더불어 사용자가 그 외 필터를 추가시 Check box에 check시 필터가 추가되며 uncheck시 추가한 필터가 삭제되고 있습니다. 이 부분이 직관적이지 않은 것 같아 기획서대로 필터항목에 마우스오버시 삭제버튼을 노출시키는 방향으로 수정하려합니다. 디자인 요청하도록 하겠습니다.

ufoscw commented 5 years ago

@brandon-wonjune DataConnection List Filter를 위한 API가 추가되었습니다. Request/Response 스펙은 DataSource List Filter와 동일합니다.

  1. Criterion List

    (GET) /api/connections/criteria
  2. Criterion Filter List

    (GET) /api/connections/criteria/{criterionKey}
  3. DataConnection List

    (POST) /api/connections/filter
brandon-wonjune commented 5 years ago

@ufoscw (POST) /api/connections/filter 에대해 문의 드립니다. 기존에 생성한 사람을 표시할때 createdBy안에 fullName으로 표시해주고 있었는데요 앞으로는 fullName없이 createdBy가 생성한 사람이 되는건가요?

ufoscw commented 5 years ago

@brandon-wonjune 기존에 사용하던 projection을 사용하면 기존과 동일하게 데이터가 내려오지 않나요? ?projection=list

brandon-wonjune commented 5 years ago

@ufoscw 답변감사합니다. 데이터소스 projection = forListView 데이터커넥션 projection = list가 맞죠? 이렇게 하면 정상적으로 내려옵니다.

데이터 커넥션에서 새로 추가된 msg.storage.ui.criterion.auth-type, msg.storage.ui.criterion.implementor 메시지 번들 추가하였습니다. 더 추가되는 메세지는 없는건가요?

brandon-wonjune commented 5 years ago

remove 아이콘 추가하였습니다. 2018-12-03 1 41 47

kyungtaak commented 5 years ago

@AnnieHwang @deidera08 @ufoscw

  1. 조건을 추가 하고 나서 다시 돌아오면 없어져 있습니다. 추가한 조건에 대한 액션은 어떻게 정의하나요? (개인 로컬리포지토리에 설정을 저장하는것인가요? )

  2. 검색의 항목을 누르면 바로 검색이 되어야 할것 같은데요. 꼭 "검색" 버튼을 눌러서 해야하는 이유가 있나요?

  3. 생성한 시간 부분 관련 내용 확인 부탁드립니다. image

kyungtaak commented 5 years ago

@ufoscw 고객 요건중, 미리 preset 으로 지정한 필터만 보게 하는 요건이 있는데요. 이것도 적용 되었나요?

minjung-cho commented 5 years ago

@brandon-wonjune

  1. 값을 선택하는 즉시, 필터링 실행 부탁드립니다. 3-1. 선택값이 있을때는 타이틀 레이블이 보이면 안됩니다. 디자인 가이드 다시 확인 부탁드립니다. 3-2. 데이터 피커를 우측으로 뜨도록 이동 부탁드립니다. 3-3. 문구는 아래와 같이 변경 부탁드립니다. (영) Last 7 dys (한) 지난 7일 (영) Between (한) 기간 @AnnieHwang 어떠신가요 ^^;
brandon-wonjune commented 5 years ago

@AnnieHwang @minjung-cho 수정하였습니다

ufoscw commented 5 years ago

@brandon-wonjune 화면 진입시 최초 검색 조건을 셋팅하는 요건에 대한 개발이 누락된것 같습니다. 최초 기본 검색 조건을 알려주는 API를 추가할 예정입니다. 추가되면 알려드릴게요.

ufoscw commented 5 years ago

@brandon-wonjune 기존 API의 response에 기본 필터 목록이 추가되면서 response 구조가 변경되었습니다.

(GET) /api/datasources/criteria
(GET) /api/connections/criteria
  1. 기존 response는 criteria 속성으로 1레벨 아래로 이동함

*AS-IS

{
  [
    "Criteria",
    "Criteria",
    "Criteria"....
  ]
}

*TO-BE

{
  "criteria" : [
    "Criteria",
    "Criteria",
    "Criteria",
    ....
  ]
}
  1. defaultFilters 속성 추가됨 *TO-BE
    {
    "criteria" : [
    "Criteria",
    "Criteria",
    "Criteria",
    ....
    ],
    "defaultFilters" : [
    "Filter", 
    "Filter",
    ....
    ]
    }

실제 Response 샘플입니다.

(GET) /api/datasources/criteria

{
    "criteria": [
        {
            "criterionKey": "STATUS",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.status"
        },
        {
            "criterionKey": "PUBLISH",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.publish",
            "searchable": true
        },
        {
            "criterionKey": "CREATOR",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.creator",
            "searchable": true
        },
        {
            "criterionKey": "CREATED_TIME",
            "criterionType": "RANGE_DATETIME",
            "criterionName": "msg.storage.ui.criterion.created-time",
            "filters": [
                {
                    "criterionKey": "CREATED_TIME",
                    "filterKey": "createdTimeFrom",
                    "filterSubKey": "createdTimeTo",
                    "filterName": "msg.storage.ui.criterion.created-time",
                    "filterValue": "",
                    "filterSubValue": ""
                }
            ]
        },
        {
            "criterionKey": "MORE",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.more",
            "subCriteria": [
                {
                    "criterionKey": "MODIFIED_TIME",
                    "criterionType": "RANGE_DATETIME",
                    "criterionName": "msg.storage.ui.criterion.modified-time"
                },
                {
                    "criterionKey": "CONNECTION_TYPE",
                    "criterionType": "CHECKBOX",
                    "criterionName": "msg.storage.ui.criterion.connection-type"
                },
                {
                    "criterionKey": "DATASOURCE_TYPE",
                    "criterionType": "CHECKBOX",
                    "criterionName": "msg.storage.ui.criterion.ds-type"
                },
                {
                    "criterionKey": "SOURCE_TYPE",
                    "criterionType": "CHECKBOX",
                    "criterionName": "msg.storage.ui.criterion.source-type"
                }
            ]
        }
    ],
    "defaultFilters": [
        {
            "criterionKey": "CREATOR",
            "filterKey": "createdBy",
            "filterName": "Administrator (me)",
            "filterValue": "admin"
        },
        {
            "criterionKey": "PUBLISH",
            "filterKey": "published",
            "filterName": "msg.storage.ui.criterion.open-data",
            "filterValue": "true"
        }
    ]
}
(GET) /api/connections/criteria

{
    "criteria": [
        {
            "criterionKey": "PUBLISH",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.publish",
            "searchable": true
        },
        {
            "criterionKey": "CREATOR",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.creator",
            "searchable": true
        },
        {
            "criterionKey": "IMPLEMENTOR",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.implementor"
        },
        {
            "criterionKey": "AUTH_TYPE",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.auth-type"
        },
        {
            "criterionKey": "CREATED_TIME",
            "criterionType": "RANGE_DATETIME",
            "criterionName": "msg.storage.ui.criterion.created-time",
            "filters": [
                {
                    "criterionKey": "CREATED_TIME",
                    "filterKey": "createdTimeFrom",
                    "filterSubKey": "createdTimeTo",
                    "filterName": "msg.storage.ui.criterion.created-time",
                    "filterValue": "",
                    "filterSubValue": ""
                }
            ]
        },
        {
            "criterionKey": "MORE",
            "criterionType": "CHECKBOX",
            "criterionName": "msg.storage.ui.criterion.more",
            "subCriteria": [
                {
                    "criterionKey": "MODIFIED_TIME",
                    "criterionType": "RANGE_DATETIME",
                    "criterionName": "msg.storage.ui.criterion.modified-time"
                }
            ]
        }
    ],
    "defaultFilter": []
}
brandon-wonjune commented 5 years ago

@ufoscw 혹시 일부 값(PUBLISH, STATUS)이 기존에 오던 filterName과 filterValue가 다른 값으로 대체되었나요?