...
[15:08:37 CDT(-0500)] <EricDalquist> and just do new String(byte[], encoding) if the rest API wrote to the output stream instead of the writer
[15:09:12 CDT(-0500)] <athena> do we have expected use cases where something other than a string would be returned?
[15:09:19 CDT(-0500)] <EricDalquist> I don't know
[15:09:31 CDT(-0500)] <EricDalquist> if you wanted to use the import/export rest APIs then yes
[15:09:38 CDT(-0500)] <EricDalquist> oh
[15:09:39 CDT(-0500)] <athena> ok, that's fair enough
[15:09:46 CDT(-0500)] <EricDalquist> well this is limited in a way to
[15:09:52 CDT(-0500)] <EricDalquist> well no
[15:09:55 CDT(-0500)] <EricDalquist> never mind that last line
[15:09:58 CDT(-0500)] <athena> so could we have two versions?
[15:10:10 CDT(-0500)] <athena> 1. sends back a byte[] and encoding
[15:10:25 CDT(-0500)] <athena> and 2. uses Jackson to parse the response and cast it to the provided type
[15:10:43 CDT(-0500)] <athena> it seems like that'd make the API friendly but still let you connect to something more low-level if you needed to?
[15:11:37 CDT(-0500)] <EricDalquist> well 1 would need to return something like:
[15:11:37 CDT(-0500)] <EricDalquist> RestResponse {
[15:11:37 CDT(-0500)] <EricDalquist> String writerOutput;
[15:11:37 CDT(-0500)] <EricDalquist> byte[] streamOutput;
[15:11:37 CDT(-0500)] <EricDalquist> String streamEncoding;
[15:11:37 CDT(-0500)] <EricDalquist> }
[15:11:51 CDT(-0500)] <EricDalquist> then the client would check both String and byte[]
[15:11:55 CDT(-0500)] <EricDalquist> and see which one isn't null
[15:12:00 CDT(-0500)] <EricDalquist> that would be good
[15:12:07 CDT(-0500)] <EricDalquist> since we could then also add things like status code
[15:12:08 CDT(-0500)] <EricDalquist> and headers
[15:12:12 CDT(-0500)] <EricDalquist> if those might be usful
[15:12:20 CDT(-0500)] <athena> oh i see - the issue is we're not sure if we're going to have a string or a bytestream?
[15:12:26 CDT(-0500)] <EricDalquist> right
[15:12:36 CDT(-0500)] <EricDalquist> you get a string if the rest API writes to response.getWriter()
[15:13:52 CDT(-0500)] <drewwills> no to which?
[15:13:53 CDT(-0500)] <EricDalquist> the only consideration on the Jackson stuff is how many exteral deps do we want?
[15:13:59 CDT(-0500)] <athena> yeah
[15:14:01 CDT(-0500)] <EricDalquist> no it isn't a problem,
[15:14:04 CDT(-0500)] <drewwills> good
[15:14:11 CDT(-0500)] <athena> it seems to me like it's probably not the end of the world to have just jackson as a dependency
[15:14:21 CDT(-0500)] <EricDalquist> well I'd go one step further
[15:14:22 CDT(-0500)] <athena> i guess i'd be more worried about relying heavily on particular spring versions?
[15:14:30 CDT(-0500)] <EricDalquist> I'd have two APIs a plain one
[15:14:35 CDT(-0500)] <EricDalquist> and a Spring 3 one
[15:17:06 CDT(-0500)] <EricDalquist> and that dictated the conversion
[15:17:28 CDT(-0500)] <EricDalquist> the HttpInputMessage interface is really simple
[15:17:39 CDT(-0500)] <EricDalquist> and we could create our own impl to wrap the captured output
[15:17:50 CDT(-0500)] <athena> ok yes, that completely makes sense
[15:17:56 CDT(-0500)] <EricDalquist> so "uportal-rest-api-portlet-client" would have:
[15:19:21 CDT(-0500)] <EricDalquist> RestResponse callPortalRestApi(PortletRequest, PortletResponse, String uri, Map<String, String[]> params)
[15:19:40 CDT(-0500)] <drewwills> btw I can certainly work on this vision in the context of my project... if we do it in a way in which I can also get some help from athena, that's even better
[15:20:19 CDT(-0500)] <EricDalquist> I would add this as a module in the uPortal project itself
[15:20:45 CDT(-0500)] <EricDalquist> then we add a BaseRequestPropertiesManager impl which exposes the portal's request context name as a portlet request property
[15:21:10 CDT(-0500)] <EricDalquist> to use callPortalRestApi in your portlet you would have to add the UPortalRestApiProxyServlet to the web.xml
[15:21:31 CDT(-0500)] <athena> do you mean create this as submodule of uportal or include the module in uportal's dependencies?
[15:22:57 CDT(-0500)] <EricDalquist> hrm
[15:23:05 CDT(-0500)] <drewwills> could we combine this utility with uportal-search-api? (though after maybe renaming it)
[15:23:06 CDT(-0500)] <EricDalquist> I was thinking as a submodule of uportal
[15:23:15 CDT(-0500)] <EricDalquist> though we need to move that search-api out too
[15:23:23 CDT(-0500)] <drewwills> yeah submodule b/c it's uP-specific
[15:23:24 CDT(-0500)] <athena> it might be eaiser to have it as a separate module
[15:23:25 CDT(-0500)] <EricDalquist> so maybe we actually get that jasig-portlet-utils going
[15:23:32 CDT(-0500)] <EricDalquist> and move the search api there
[15:23:35 CDT(-0500)] <EricDalquist> as well as this
[15:25:27 CDT(-0500)] <EricDalquist> then down the road we add another "uportal-rest-api-portlet-spring-client"
[15:25:33 CDT(-0500)] <EricDalquist> which depends on "uportal-rest-api-portlet-client"
[15:25:40 CDT(-0500)] <drewwills> seems like either (1) combine w/ search-api (2) move to jasig-portlet-utils or (3) both
[15:25:40 CDT(-0500)] <athena> sounds great to me
[15:26:09 CDT(-0500)] <EricDalquist> and adds:
[15:26:09 CDT(-0500)] <EricDalquist> T callPortalRestApi(PortletRequest, PortletResponse, String uri, Map<String, String[]> params, HttpMessageConverter<T>)
[15:29:00 CDT(-0500)] <athena> and we could improve it from there
[15:29:05 CDT(-0500)] <drewwills> i would probably leave moving the search api as a roadmap item, for the same of triage
[15:29:15 CDT(-0500)] <athena> i can help with some of this, but certainly not anytime in the next week
[15:29:17 CDT(-0500)] <EricDalquist> we don't
[15:29:24 CDT(-0500)] <EricDalquist> I had this working a while back locally
[15:29:27 CDT(-0500)] <athena> i don't think there's any direct relationship between this and the search module
[15:29:28 CDT(-0500)] <EricDalquist> but it never went anywhere
[15:33:39 CDT(-0500)] <drewwills> if I had this I could hit ANY rest api... not just ones I had made interfaces for
[15:33:40 CDT(-0500)] <EricDalquist> so designing a whole new API, implementation and way to provide it as a portal context attribute?
[15:33:42 CDT(-0500)] <athena> it sort of seems like most of the planning is already there? you'd just need to implement the steps eric already laid out
[15:33:46 CDT(-0500)] <EricDalquist> right
[15:34:00 CDT(-0500)] <athena> yes, you could hit any of the existing rest services
[15:34:08 CDT(-0500)] <athena> plus quickly attach to new ones you created
[15:34:14 CDT(-0500)] <drewwills> yeah I was picturing a "whole new API" of 1 interface, maybe 2 methods
[15:34:14 CDT(-0500)] <EricDalquist> this already exists: https://github.com/Jasig/portlet-utils
[15:34:15 CDT(-0500)] <athena> so if you needed a new service you could jsut add it to uportal and go
[15:34:33 CDT(-0500)] <EricDalquist> yes but it needs to be a well thought out API
[15:34:36 CDT(-0500)] <athena> so we just need a small library that's a submodule of portlet-utils
[15:34:38 CDT(-0500)] <athena> yes, it does
[15:38:06 CDT(-0500)] <drewwills> this is about getting all oars in the same boat, rowing the same way
[15:38:47 CDT(-0500)] <EricDalquist> right
[15:39:00 CDT(-0500)] <EricDalquist> so I thinkt he least effort is the rest api proxy code
[15:44:33 CDT(-0500)] <athena> also i think there's a really interesting use case for leveraging the uportal permissions framework for portlet use
[15:44:46 CDT(-0500)] <drewwills> yes, totally
[15:44:59 CDT(-0500)] <drewwills> need discoverable groups & so forth
[15:45:12 CDT(-0500)] <athena> could even create custom permissions
[15:45:12 CDT(-0500)] <drewwills> isUserInRole only goes so far
[15:45:14 CDT(-0500)] <athena> yes.
[15:45:25 CDT(-0500)] <athena> things like the announcement portlet feed permissions could really use uportal permissions
[15:45:30 CDT(-0500)] <EricDalquist> so one thing we'll have to look into is overhead
[15:45:33 CDT(-0500)] <athena> would take some dev to get to that point, but i's possible
[16:16:53 CDT(-0500)] <drewwills> one more question EricDalquist – calling the rest api from a servlet (not portlet) not a problem, correct?
[16:17:28 CDT(-0500)] <EricDalquist> using the request dispatcher approach?
[16:19:00 CDT(-0500)] <drewwills> yeah
[16:19:13 CDT(-0500)] <EricDalquist> right
[16:19:18 CDT(-0500)] <drewwills> fewer steps even
[16:19:18 CDT(-0500)] <EricDalquist> that isn't a problem
[16:19:21 CDT(-0500)] <EricDalquist> right
[16:19:26 CDT(-0500)] <EricDalquist> it is the same as the portlet
[16:19:29 CDT(-0500)] <EricDalquist> just one less step
[16:19:50 CDT(-0500)] <drewwills> whereas the java api/portal context approach could require extra finessing
[16:21:38 CDT(-0500)] <EricDalquist> right
[16:21:44 CDT(-0500)] <EricDalquist> since the servlet has no context from the portal]
[16:47:09 CDT(-0500)] <drewwills> can you stuff GET/POST/PUT/DELETE into a requestDispatcher?
[16:47:38 CDT(-0500)] <EricDalquist> if you fake ity
[16:47:48 CDT(-0500)] <EricDalquist> with a custom HttpServletRequestWrapper
[16:49:57 CDT(-0500)] <EricDalquist> but doable
[16:55:15 CDT(-0500)] Wiki Markup <drewwills> so... any fancy Spring class to turn "/some/url/{p1}?foo={p2}" into "/some/url/with?foo={bar}" given \[ p1:with, p2:bar \]?
[16:55:41 CDT(-0500)] <athena> could take a look at the rest template source code
[16:55:47 CDT(-0500)] <athena> see if that's actually using another library
[16:58:48 CDT(-0500)] <athena> yeah
[16:58:54 CDT(-0500)] <athena> using an internal spring lib - UriTemplate
[17:10:40 CDT(-0500)] <athena> yes, i think we should use normal URL parameter behavior
[17:17:30 CDT(-0500)] <drewwills> sounds lovely... I thought I had seen that the getPeople() method expected differently, but I mis-remembered
[18:36:54 CDT(-0500)] <peterjhart> Here is a mockup of what a Fragment Manager UI could look like: https://wiki.jasig.org/display/UPC/uPortal+4+DLM+Fragment+Manager+Interface