Some screenshots from some random clicking around by somebody:
Adding a feed: http://cl.ly/image/16183s0h0t2e (clever, it auto-fills the name after a second) (not so clever, the only drop-down option is 'all', and it's not pre-selected)
Having added two feeds, I see this: http://cl.ly/image/321t1J2p461p it persists for a while, the spinner in the corner goes away, it persists... toggled 'all', 'unread', etc, no results.
Some basic key commands I've used in Google Reader still work. The UI takes a moment to load data from the server when you change where you are, but once it finishes it's fast. Minor bugs, some holes things seem to fall through, but as a basic RSS reader it works. Maybe there's more to come?
As long as nobody messes it up for everyone else, "somebody password" is what I used if you want to try it out.
The sources are publicly available, but there is absolutely no mention of a license for the CommaFeed code in the repository. I have filed an issue https://github.com/Athou/commafeed/issues/48
demo/demo for login works. And it looks good: Just a rss-reader with a list of feeds to the left and articles on the right, good performance in the demo. jk-navigation. custom css.
I'm not exited by it being a java-application (hosting that on my own could be a hassle) and the google reader import doesn't work (invalid grant, error code 400, want the eror message?). Importing the .xml seems to have no effect at all (edit: now it does. just takes some time?).
What is the feed-polling strategy? Does it support pubsubhubbub? Will this instance stay active?
What's wrong with it being a java app? As it says on the github, create an account on openshift and its just a few easy commands to get it running. OpenJDK is nice and easy to install on most open hosting environments too.
A lot of us harbour a strong hate of Java due to a decade or more of exposure to abstract factory factories, and obnoxiously slow jvm startup times, and a series of Java applications that are supposed to perform as "native" yet somehow all feel clunky, slow and bloated (Eclipse being the posterchild for all that is wrong with Java...).
I actually have a half-baked code generator to use Ruby to generate Java for some Android hobby-projects because I found that less painful and obnoxious than writing the Java directly.
Are you referring to backend or frontend applications? Java on the backend seems to be very stable and popular. Though I don't have any experience with it personally, my understanding is that it's probably the most popular backend language for web apps in terms of deployment size and complexity.
Perhaps off-topic, but to those that are interested in bloat-free open source Reader replacements, I've had extremely good luck with TT-RSS. It's been in development since 2005, is written in PHP, and is quite slick IMHO. I run my own instance on shared hosting (DreamHost) and it hasn't failed me yet. Open-source Android client as well (though it costs a couple of bucks in the play store.)
http://tt-rss.org/
I like it so far. I think I might prefer this to The Old Reader. Open source is a plus, too. (And thank you for oldest-first! So many forget this.)
One question: I uploaded my opml file, and ... nothing happened. It is processing or queued somewhere? (That's fine, I'd just like to know.) I then added a single feed, which worked fine.
Edit: I'd switch to this from The Old Reader (and gladly pay) if you make a mobile view.
Looking again, it only offers to import a Google Reader XML export file, not any OPML, and I was uploading an export from The Old Reader, so it shouldn't have worked anyway.
Cool. I manually subscribed to all my feeds -- slow day at work, and it let me rename things -- but this will let me suggest CommaFeed to friends and family.
These are some of the features I'd like to see in an RSS reader (I've actually considered trying to learn to program just to build a reader that has these features):
* Import a list of feeds from a simple text file. I find it strange readers don't support this. If I have a list of 50 rss feeds, I don't really want to enter them one by one. Importing from a file another reader has exported is great, but I'd like to import from a text file too.
* Filters. Per-feed and per-category. Again, perhaps naively, I imagine this would be simple to implement but I don't know of a web-based reader that does this and I usually have to resort to Yahoo Pipes or similar, which is a pretty clunky solution. Filters like: Only show entries containing "bar", or don't show entries containing "foo". Bonus points if I can edit a multi-line list of filters, so if I want to filter for 50 separate words I don't have to enter them one-by-one
* Sort-by-newest that works properly across categories. I currently use feedly and somehow in category view posts 12 hours old show up ahead of posts 3 minutes old.
Regarding (1), many (most?) readers support OPML, and you can use OPMLBuilder[1] and similar tools to create a file from a list of URLs. Unless you're regularly import new lists, it seems a decent solution.
Newsblur can filter by tag, author and title keyword(s). I only have a few dozen feeds but the popular ones spew so much content that I honestly could not touch them until I switched to NB.
'r' to refresh was the key I used most on Google Reader after 'j' and 'k', and I'm surprised to see that TheOldReader and CommaFeed both lack this feature.
com.commafeed.frontend.utils.exception.DisplayException: 400 Bad Request
{
"error" : "invalid_grant"
}
at com.commafeed.frontend.pages.GoogleImportCallbackPage.<init>(GoogleImportCallbackPage.java:94)
at sun.reflect.GeneratedConstructorAccessor187.newInstance(Unknown Source)
...
1. Error on Google Reader import
2. Agreed with others it does need at least a single screenshot on the front page (or an About page as a demo).
3. It would be nice to offer a default Google Reader CSS file to add to the styling function.
The instructions on the readme detail everything pretty well. You don't need to know anything about Java or Maven. See the section "Deployment on OpenShift."
Since there aren't any screenshots I don't think I will use this till you fix the landing page. Does anyone have any alternatives that are 'bloat-free' Readers?
Do you mean have all the entries opened and scrolling through marking them as read ? I never used that feature of google reader so I haven't implemented that yet. If it's something people use and want, I'll add it.
Method onFormSubmitted of interface org.apache.wicket.markup.html.form.IFormSubmitListener targeted at [SignInForm [Component id = signInForm]] on component [SignInForm [Component id = signInForm]] threw an exception
Go back to the previous page or to the home page.
org.apache.wicket.WicketRuntimeException: Method onFormSubmitted of interface org.apache.wicket.markup.html.form.IFormSubmitListener targeted at [SignInForm [Component id = signInForm]] on component [SignInForm [Component id = signInForm]] threw an exception
at org.apache.wicket.RequestListenerInterface.internalInvoke(RequestListenerInterface.java:268)
at org.apache.wicket.RequestListenerInterface.invoke(RequestListenerInterface.java:216)
at org.apache.wicket.core.request.handler.ListenerInterfaceRequestHandler.invokeListener(ListenerInterfaceRequestHandler.java:240)
at org.apache.wicket.core.request.handler.ListenerInterfaceRequestHandler.respond(ListenerInterfaceRequestHandler.java:226)
at org.apache.wicket.request.cycle.RequestCycle$HandlerExecutor.respond(RequestCycle.java:840)
at org.apache.wicket.request.RequestHandlerStack.execute(RequestHandlerStack.java:64)
at org.apache.wicket.request.cycle.RequestCycle.execute(RequestCycle.java:254)
at org.apache.wicket.request.cycle.RequestCycle.processRequest(RequestCycle.java:211)
at org.apache.wicket.request.cycle.RequestCycle.processRequestAndDetach(RequestCycle.java:282)
at org.apache.wicket.protocol.http.WicketFilter.processRequestCycle(WicketFilter.java:244)
at org.apache.wicket.protocol.http.WicketFilter.processRequest(WicketFilter.java:188)
at org.apache.wicket.protocol.http.WicketFilter.doFilter(WicketFilter.java:267)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
at org.apache.tomee.catalina.OpenEJBValve.invoke(OpenEJBValve.java:45)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:472)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:936)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:407)
at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1004)
at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
at java.lang.Thread.run(Thread.java:722)
Caused by: java.lang.reflect.InvocationTargetException
at sun.reflect.GeneratedMethodAccessor311.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.wicket.RequestListenerInterface.internalInvoke(RequestListenerInterface.java:258)
... 28 more
Caused by: javax.ejb.EJBException: The bean encountered a non-application exception; nested exception is:
javax.ejb.EJBTransactionRolledbackException: The transaction has been marked rollback only because the bean encountered a non-application exception :java.lang.NullPointerException : null
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.convertException(BaseEjbProxyHandler.java:363)
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.invoke(BaseEjbProxyHandler.java:283)
at com.commafeed.backend.services.UserService$LocalBeanProxy.login(com/commafeed/backend/services/UserService.java)
at com.commafeed.frontend.CommaFeedSession.authenticate(CommaFeedSession.java:54)
at org.apache.wicket.authroles.authentication.AuthenticatedWebSession.signIn(AuthenticatedWebSession.java:65)
at org.apache.wicket.authroles.authentication.panel.SignInPanel.signIn(SignInPanel.java:221)
at org.apache.wicket.authroles.authentication.panel.SignInPanel.access$100(SignInPanel.java:51)
at org.apache.wicket.authroles.authentication.panel.SignInPanel$SignInForm.onSubmit(SignInPanel.java:296)
at org.apache.wicket.markup.html.form.Form$9.component(Form.java:1246)
at org.apache.wicket.markup.html.form.Form$9.component(Form.java:1240)
at org.apache.wicket.util.visit.Visits.visitPostOrderHelper(Visits.java:274)
at org.apache.wicket.util.visit.Visits.visitPostOrder(Visits.java:245)
at org.apache.wicket.markup.html.form.Form.delegateSubmit(Form.java:1239)
at org.apache.wicket.markup.html.form.Form.process(Form.java:921)
at org.apache.wicket.markup.html.form.StatelessForm.process(StatelessForm.java:87)
at org.apache.wicket.markup.html.form.Form.onFormSubmitted(Form.java:767)
at org.apache.wicket.markup.html.form.Form.onFormSubmitted(Form.java:700)
... 32 more
Caused by: javax.ejb.EJBTransactionRolledbackException: The transaction has been marked rollback only because the bean encountered a non-application exception :java.lang.NullPointerException : null
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.convertException(BaseEjbProxyHandler.java:345)
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.invoke(BaseEjbProxyHandler.java:283)
at com.commafeed.backend.dao.UserDAO$LocalBeanProxy.findByName(com/commafeed/backend/dao/UserDAO.java)
at com.commafeed.backend.services.UserService.login(UserService.java:24)
at sun.reflect.GeneratedMethodAccessor309.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:181)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:163)
at org.apache.openejb.cdi.CdiInterceptor.invoke(CdiInterceptor.java:130)
at org.apache.openejb.cdi.CdiInterceptor.access$000(CdiInterceptor.java:43)
at org.apache.openejb.cdi.CdiInterceptor$1.call(CdiInterceptor.java:67)
at org.apache.openejb.cdi.CdiInterceptor.aroundInvoke(CdiInterceptor.java:73)
at sun.reflect.GeneratedMethodAccessor32.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:181)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:163)
at org.apache.openejb.monitoring.StatsInterceptor.record(StatsInterceptor.java:180)
at org.apache.openejb.monitoring.StatsInterceptor.invoke(StatsInterceptor.java:99)
at sun.reflect.GeneratedMethodAccessor31.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:181)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:163)
at org.apache.openejb.core.interceptor.InterceptorStack.invoke(InterceptorStack.java:138)
at org.apache.openejb.core.stateless.StatelessContainer._invoke(StatelessContainer.java:239)
at org.apache.openejb.core.stateless.StatelessContainer.invoke(StatelessContainer.java:191)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler.synchronizedBusinessMethod(EjbObjectProxyHandler.java:256)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler.businessMethod(EjbObjectProxyHandler.java:251)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler._invoke(EjbObjectProxyHandler.java:85)
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.invoke(BaseEjbProxyHandler.java:279)
... 47 more
Caused by: java.lang.NullPointerException
at com.commafeed.backend.dao.UserDAO.findByName(UserDAO.java:19)
at sun.reflect.GeneratedMethodAccessor283.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:181)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:163)
at org.apache.openejb.cdi.CdiInterceptor.invoke(CdiInterceptor.java:130)
at org.apache.openejb.cdi.CdiInterceptor.access$000(CdiInterceptor.java:43)
at org.apache.openejb.cdi.CdiInterceptor$1.call(CdiInterceptor.java:67)
at org.apache.openejb.cdi.CdiInterceptor.aroundInvoke(CdiInterceptor.java:73)
at sun.reflect.GeneratedMethodAccessor32.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:181)
at org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(R
An unexpected error occured
Unable to get write lock on 'subscribe' method for: com.commafeed.backend.services.FeedSubscriptionService
Go back to the previous page or to the home page.
com.commafeed.frontend.utils.exception.DisplayException: Unable to get write lock on 'subscribe' method for: com.commafeed.backend.services.FeedSubscriptionService
at com.commafeed.frontend.pages.GoogleImportCallbackPage.<init>(GoogleImportCallbackPage.java:94)
at sun.reflect.GeneratedConstructorAccessor187.newInstance(Unknown Source)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
at org.apache.wicket.session.DefaultPageFactory.newPage(DefaultPageFactory.java:170)
at org.apache.wicket.session.DefaultPageFactory.newPage(DefaultPageFactory.java:98)
at org.apache.wicket.DefaultMapperContext.newPageInstance(DefaultMapperContext.java:137)
at org.apache.wicket.core.request.handler.PageProvider.resolvePageInstance(PageProvider.java:278)
at org.apache.wicket.core.request.handler.PageProvider.getPageInstance(PageProvider.java:166)
at org.apache.wicket.request.handler.render.PageRenderer.getPage(PageRenderer.java:78)
at org.apache.wicket.request.handler.render.WebPageRenderer.renderPage(WebPageRenderer.java:94)
at org.apache.wicket.request.handler.render.WebPageRenderer.respond(WebPageRenderer.java:244)
at org.apache.wicket.core.request.handler.RenderPageRequestHandler.respond(RenderPageRequestHandler.java:165)
at org.apache.wicket.request.cycle.RequestCycle$HandlerExecutor.respond(RequestCycle.java:840)
at org.apache.wicket.request.RequestHandlerStack.execute(RequestHandlerStack.java:64)
at org.apache.wicket.request.cycle.RequestCycle.execute(RequestCycle.java:254)
at org.apache.wicket.request.cycle.RequestCycle.processRequest(RequestCycle.java:211)
at org.apache.wicket.request.cycle.RequestCycle.processRequestAndDetach(RequestCycle.java:282)
at org.apache.wicket.protocol.http.WicketFilter.processRequestCycle(WicketFilter.java:244)
at org.apache.wicket.protocol.http.WicketFilter.processRequest(WicketFilter.java:188)
at org.apache.wicket.protocol.http.WicketFilter.doFilter(WicketFilter.java:267)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
at org.apache.tomee.catalina.OpenEJBValve.invoke(OpenEJBValve.java:45)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:472)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:936)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:407)
at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1004)
at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
at java.lang.Thread.run(Thread.java:722)
Caused by: javax.ejb.ConcurrentAccessTimeoutException: Unable to get write lock on 'subscribe' method for: com.commafeed.backend.services.FeedSubscriptionService
at org.apache.openejb.core.singleton.SingletonContainer.aquireLock(SingletonContainer.java:303)
at org.apache.openejb.core.singleton.SingletonContainer._invoke(SingletonContainer.java:222)
at org.apache.openejb.core.singleton.SingletonContainer.invoke(SingletonContainer.java:205)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler.synchronizedBusinessMethod(EjbObjectProxyHandler.java:256)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler.businessMethod(EjbObjectProxyHandler.java:251)
at org.apache.openejb.core.ivm.EjbObjectProxyHandler._invoke(EjbObjectProxyHandler.java:85)
at org.apache.openejb.core.ivm.BaseEjbProxyHandler.invoke(BaseEjbProxyHandler.java:279)
at com.commafeed.backend.services.FeedSubscriptionService$LocalBeanProxy.subscribe(com/commafeed/backend/services/FeedSubscriptionService.java)
at com.commafeed.backend.feeds.OPMLImporter.handleOutline(OPMLImporter.java:58)
at com.commafeed.backend.feeds.OPMLImporter.importOpml(OPMLImporter.java:34)
at com.commafeed.frontend.pages.GoogleImportCallbackPage.<init>(GoogleImportCallbackPage.java:92)
... 37 more