I'd like to get some feedback on an example web API I've put together. It's mavenized and available on GitHub here.
Setup
The only thing you'd have to change to run this locally is line 31 in src/main/java/com.example.config.PersistConfig.java:
String databaseLocation = "jdbc:derby:C:\\Users\\Kevin\\Desktop\\SpringExampleDB;create=true";
Change that to a path on your machine - it doesn't have to exist yet since Derby will create it for you.
The Application
The application is pretty basic: users can register, login, edit their "profile" (which is just a single description text), and view other member profiles.
Registration, login, and authentication are handled through Spring Security. Getting a list of members, information on a particular member, or editing your own information are handled through a web API.
Questions:
I'm mostly looking for criticisms on my overall setup, so I don't have a specific question. But in the interest of being more Stack Overflow-y:
Here is the JSP for viewing a particular member:
<!DOCTYPE html> <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <html lang="en"> <head> <title>Spring Example</title> <script>var baseUrl = '<c:url value="/"/>';</script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script> <script> function getMember(){ var name = window.location.href.substring(window.location.href.lastIndexOf('/')+1); $.getJSON(baseUrl+"api/members/"+name, function(member) { console.log(member); $("#name").html(member.name); $("#description").html(member.description); }); } $(getMember()); </script> </head> <body> <ul> <li><a href="<c:url value="/" />">Home</a></li> <li><a href="<c:url value="/login" />">Login</a></li> <li><a href="<c:url value="/logout" />">Logout</a></li> <li><a href="<c:url value="/members" />">Members</a></li> </ul> <hr/> <p id="name"></p> <p id="description"></p> </body> </html>
- Is there a better way to get the base URL than
<script>var baseUrl = '<c:url value="/"/>';</script>
? This code will be used as an example, so it might be deployed tolocalhost:8080/SpringExample
, or aslocalhost:8080/
, or to a "real" domain, so I want to be as flexible as possible. This is easy in JSP, but passing in the base URL from JSP to JavaScript seems kludgey. - The
<script>var baseUrl = '<c:url value="/"/>';</script>
line happens on the server. Does that prevent this generated html from being cached? - Is this approach of fetching the member information via JavaScript reasonable? Or should I be using a JSP for this?
- Would google be able to index the pages (assuming they were unauthenticated) that use JavaScript to load content?
Here is my API controller:
@Component public class ApiController implements ApiControllerInterface{ @Autowired private MemberDao memberDao; @RequestMapping(value = "/members", method = RequestMethod.GET) @Transactional public List<Member> getMembers(){ return memberDao.getMembers(); } @RequestMapping(value="/members/{name}", method = RequestMethod.GET) @Transactional public Member member(@PathVariable(value="name") String name){ return memberDao.getMember(name); } @RequestMapping(value="/members/{memberName}", method = RequestMethod.POST) @Transactional public Member memberPost(Member member, Principal principal){ if(principal.getName().equals(member.getName())){ memberDao.updateMember(member); } return member; } }
- To make sure a member can only edit their own profile, I'm passing in the
Principal
to thememberPost()
function. Is that a reasonable approach, or is there a better alternative I should consider? - Are there any security "holes" that I'm not covering?
- I know that this might not be strictly REST since the server does have session information, but I'm okay with that... unless I shouldn't be?
My end goal is to create a tutorial that shows people how to create a web API that can then be used by either a website or a mobile app. Is this a reasonable barebones example to work from, or am I doing any glaringly stupid things?