@Override public String lookup(String theKey) { /* * TODO: this method could be made more efficient through some sort of lookup map */ if ("operationType".equals(theKey)) { if (myRequestDetails.getRestOperationType() != null) { return myRequestDetails.getRestOperationType().getCode(); } return ""; } else if ("operationName".equals(theKey)) { if (myRequestDetails.getRestOperationType() != null) { switch (myRequestDetails.getRestOperationType()) { case EXTENDED_OPERATION_INSTANCE: case EXTENDED_OPERATION_SERVER: case EXTENDED_OPERATION_TYPE: return myRequestDetails.getOperation(); default: return ""; } } else { return ""; } } else if ("id".equals(theKey)) { if (myRequestDetails.getId() != null) { return myRequestDetails.getId().getValue(); } return ""; } else if ("servletPath".equals(theKey)) { return StringUtils.defaultString(myRequest.getServletPath()); } else if ("idOrResourceName".equals(theKey)) { if (myRequestDetails.getId() != null) { return myRequestDetails.getId().getValue(); } if (myRequestDetails.getResourceName() != null) { return myRequestDetails.getResourceName(); } return ""; } else if (theKey.equals("requestParameters")) { StringBuilder b = new StringBuilder(); for (Entry<String, String[]> next : myRequestDetails.getParameters().entrySet()) { for (String nextValue : next.getValue()) { if (b.length() == 0) { b.append('?'); } else { b.append('&'); } try { b.append(URLEncoder.encode(next.getKey(), "UTF-8")); b.append('='); b.append(URLEncoder.encode(nextValue, "UTF-8")); } catch (UnsupportedEncodingException e) { throw new ca.uhn.fhir.context.ConfigurationException("UTF-8 not supported", e); } } } return b.toString(); } else if (theKey.startsWith("requestHeader.")) { String val = myRequest.getHeader(theKey.substring("requestHeader.".length())); return StringUtils.defaultString(val); } else if (theKey.startsWith("remoteAddr")) { return StringUtils.defaultString(myRequest.getRemoteAddr()); } else if (theKey.equals("responseEncodingNoDefault")) { EncodingEnum encoding = RestfulServerUtils.determineResponseEncodingNoDefault( myRequestDetails, myRequestDetails.getServer().getDefaultResponseEncoding()); if (encoding != null) { return encoding.name(); } else { return ""; } } else if (theKey.equals("exceptionMessage")) { return myException != null ? myException.getMessage() : null; } else if (theKey.equals("requestUrl")) { return myRequest.getRequestURL().toString(); } else if (theKey.equals("requestVerb")) { return myRequest.getMethod(); } else if (theKey.equals("requestBodyFhir")) { String contentType = myRequest.getContentType(); if (isNotBlank(contentType)) { int colonIndex = contentType.indexOf(';'); if (colonIndex != -1) { contentType = contentType.substring(0, colonIndex); } contentType = contentType.trim(); EncodingEnum encoding = EncodingEnum.forContentType(contentType); if (encoding != null) { byte[] requestContents = myRequestDetails.loadRequestContents(); return new String(requestContents, Charsets.UTF_8); } } return ""; } return "!VAL!"; }
@Override public void invokeServer(RestfulServer theServer, Request theRequest) throws BaseServerResponseException, IOException { // Pretty print boolean prettyPrint = RestfulServerUtils.prettyPrintResponse(theServer, theRequest); // Narrative mode NarrativeModeEnum narrativeMode = RestfulServerUtils.determineNarrativeMode(theRequest); // Determine response encoding EncodingEnum responseEncoding = RestfulServerUtils.determineResponseEncodingNoDefault(theRequest.getServletRequest()); // Is this request coming from a browser String uaHeader = theRequest.getServletRequest().getHeader("user-agent"); boolean requestIsBrowser = false; if (uaHeader != null && uaHeader.contains("Mozilla")) { requestIsBrowser = true; } Object requestObject = parseRequestObject(theRequest); // Method params Object[] params = new Object[getParameters().size()]; for (int i = 0; i < getParameters().size(); i++) { IParameter param = getParameters().get(i); if (param != null) { params[i] = param.translateQueryParametersIntoServerArgument(theRequest, requestObject); } } Object resultObj = invokeServer(theRequest, params); Integer count = RestfulServerUtils.extractCountParameter(theRequest.getServletRequest()); boolean respondGzip = theRequest.isRespondGzip(); HttpServletResponse response = theRequest.getServletResponse(); switch (getReturnType()) { case BUNDLE: { if (getMethodReturnType() == MethodReturnTypeEnum.BUNDLE_RESOURCE) { IResource resource; if (resultObj instanceof IBundleProvider) { IBundleProvider result = (IBundleProvider) resultObj; resource = result.getResources(0, 1).get(0); } else { resource = (IResource) resultObj; } /* * We assume that the bundle we got back from the handling method may not have everything populated * (e.g. self links, bundle type, etc) so we do that here. */ IVersionSpecificBundleFactory bundleFactory = theServer.getFhirContext().newBundleFactory(); bundleFactory.initializeWithBundleResource(resource); bundleFactory.addRootPropertiesToBundle( null, theRequest.getFhirServerBase(), theRequest.getCompleteUrl(), count, getResponseBundleType()); for (int i = theServer.getInterceptors().size() - 1; i >= 0; i--) { IServerInterceptor next = theServer.getInterceptors().get(i); boolean continueProcessing = next.outgoingResponse( theRequest, resource, theRequest.getServletRequest(), theRequest.getServletResponse()); if (!continueProcessing) { ourLog.debug("Interceptor {} returned false, not continuing processing"); return; } } RestfulServerUtils.streamResponseAsResource( theServer, response, resource, responseEncoding, prettyPrint, requestIsBrowser, narrativeMode, Constants.STATUS_HTTP_200_OK, respondGzip, theRequest.getFhirServerBase(), isAddContentLocationHeader()); break; } else { Set<Include> includes = getRequestIncludesFromParams(params); IBundleProvider result = (IBundleProvider) resultObj; if (count == null) { count = result.preferredPageSize(); } IVersionSpecificBundleFactory bundleFactory = theServer.getFhirContext().newBundleFactory(); bundleFactory.initializeBundleFromBundleProvider( theServer, result, responseEncoding, theRequest.getFhirServerBase(), theRequest.getCompleteUrl(), prettyPrint, 0, count, null, getResponseBundleType(), includes); Bundle bundle = bundleFactory.getDstu1Bundle(); if (bundle != null) { for (int i = theServer.getInterceptors().size() - 1; i >= 0; i--) { IServerInterceptor next = theServer.getInterceptors().get(i); boolean continueProcessing = next.outgoingResponse( theRequest, bundle, theRequest.getServletRequest(), theRequest.getServletResponse()); if (!continueProcessing) { ourLog.debug("Interceptor {} returned false, not continuing processing"); return; } } RestfulServerUtils.streamResponseAsBundle( theServer, response, bundle, responseEncoding, theRequest.getFhirServerBase(), prettyPrint, narrativeMode, respondGzip, requestIsBrowser); } else { IBaseResource resBundle = bundleFactory.getResourceBundle(); for (int i = theServer.getInterceptors().size() - 1; i >= 0; i--) { IServerInterceptor next = theServer.getInterceptors().get(i); boolean continueProcessing = next.outgoingResponse( theRequest, resBundle, theRequest.getServletRequest(), theRequest.getServletResponse()); if (!continueProcessing) { ourLog.debug("Interceptor {} returned false, not continuing processing"); return; } } RestfulServerUtils.streamResponseAsResource( theServer, response, (IResource) resBundle, responseEncoding, prettyPrint, requestIsBrowser, narrativeMode, Constants.STATUS_HTTP_200_OK, theRequest.isRespondGzip(), theRequest.getFhirServerBase(), isAddContentLocationHeader()); } break; } } case RESOURCE: { IBundleProvider result = (IBundleProvider) resultObj; if (result.size() == 0) { throw new ResourceNotFoundException(theRequest.getId()); } else if (result.size() > 1) { throw new InternalErrorException("Method returned multiple resources"); } IResource resource = result.getResources(0, 1).get(0); for (int i = theServer.getInterceptors().size() - 1; i >= 0; i--) { IServerInterceptor next = theServer.getInterceptors().get(i); boolean continueProcessing = next.outgoingResponse( theRequest, resource, theRequest.getServletRequest(), theRequest.getServletResponse()); if (!continueProcessing) { return; } } RestfulServerUtils.streamResponseAsResource( theServer, response, resource, responseEncoding, prettyPrint, requestIsBrowser, narrativeMode, Constants.STATUS_HTTP_200_OK, respondGzip, theRequest.getFhirServerBase(), isAddContentLocationHeader()); break; } } }