/*
 *    Licensed Materials - Property of IBM
 *    5725-I43 (C) Copyright IBM Corp. 2015. All Rights Reserved.
 *    US Government Users Restricted Rights - Use, duplication or
 *    disclosure restricted by GSA ADP Schedule Contract with IBM Corp.
 */

package com.acme.apis;

import com.acme.apis.models.Contact;
import com.ibm.mfp.adapter.api.OAuthSecurity;
import io.swagger.annotations.*;

import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.*;
import java.util.logging.Logger;

import javax.servlet.AsyncContext;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.ws.rs.*;
import javax.ws.rs.container.AsyncResponse;
import javax.ws.rs.container.Suspended;
import javax.ws.rs.core.*;

import com.ibm.mfp.adapter.api.ConfigurationAPI;

@Api(value = "Contact list adapter")
@Path("/")
public class ContactListApiResource {
    /*
     * For more info on JAX-RS see
	 * https://jax-rs-spec.java.net/nonav/2.0-rev-a/apidocs/index.html
	 */

    // Define logger (Standard java.util.Logger)
    static Logger logger = Logger.getLogger(ContactListApiResource.class.getName());

    // Inject the MFP configuration API:
    @Context
    ConfigurationAPI configApi;


    static Map<String, Contact> contactMap = new HashMap<String, Contact>();


    @ApiResponses(value = {
            @ApiResponse(code = 200, message = "Success", response = Contact[].class)
    })
    @ApiOperation(value = "Returns A list of all the contacts")
    @GET
    @Produces(MediaType.APPLICATION_JSON)
    public Collection<Contact> getAllContacts() {
        return contactMap.values();
    }

    @ApiOperation(value = "Add contact")
    @ApiResponses(value = {
            @ApiResponse(code = 201, message = "Created", responseHeaders = {
                    @ResponseHeader(name = "Location", description = "Location (URL) of the created contact")
            }),
            @ApiResponse(code = 406, message = "Contact (name) already exist")
    })
    @POST
    @Consumes(MediaType.APPLICATION_JSON)
    public Response addContact(Contact contact, @Context UriInfo uriInfo) {
        if (contactMap.containsKey(contact.name)) {
            return Response.status(409).entity("Contact named: " + contact.name + " already exist").build();
        }

        contactMap.put(contact.name, contact);

        UriBuilder builder = uriInfo.getAbsolutePathBuilder();
        builder.path(contact.name);
        return Response.created(builder.build()).build();
    }

    @ApiOperation(value = "Update contact")
    @ApiResponses(value = {
            @ApiResponse(code = 201, message = "Updated successfully"),
            @ApiResponse(code = 404, message = "Contact not found")
    })
    @PUT
    @Consumes(MediaType.APPLICATION_JSON)
    public Response updateContact(Contact contact) {
        if (contactMap.containsKey(contact.name)) {
            contactMap.put(contact.name, contact);
        } else {
            throw new NotFoundException(contact.name);
        }
        return Response.ok().build();
    }

    @ApiOperation(value = "Get contact")
    @ApiResponses(value = {
            @ApiResponse(code = 200, message = "Success", response = Contact.class),
            @ApiResponse(code = 404, message = "Contact not found")
    })
    @GET
    @Path("{name}")
    @Produces(MediaType.APPLICATION_JSON)
    public Contact getContact(@PathParam("name") String name) {
        Contact contact = contactMap.get(name);
        if (contact == null) {
            throw new NotFoundException(name);
        }
        return contact;
    }

    @ApiOperation(value = "Delete contact")
    @ApiResponses(value = {
            @ApiResponse(code = 200, message = "Success"),
            @ApiResponse(code = 404, message = "Contact not found")
    })
    @DELETE
    @Path("{name}")
    public Response deleteContact(@PathParam("name") String name) {
        Contact contact = contactMap.remove(name);
        if (contact == null) {
            throw new NotFoundException(name);
        }
        return Response.ok().build();
    }


    @Path("/resource")
    @GET
    @OAuthSecurity(enabled = false)
    public void asyncGet(@Suspended final AsyncResponse asyncResponse, final @Context AsyncContext ctx) {

        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(2000);
                    asyncResponse.resume("hallo2!\n");
                } catch (Exception e) {
                    throw new RuntimeException(e);
                }
            }

        }).start();
    }


    @Path("/resource2")
    @GET
    @OAuthSecurity(enabled = false)
    public void asyncGet2(final @Context HttpServletRequest request, final @Context HttpServletResponse response) {

        final AsyncContext ctx = request.startAsync(request, response);
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(3000);
                    ServletOutputStream os = ctx.getResponse().getOutputStream();
                    os.println("Done");
                    os.flush();
                    os.close();
                    ctx.getClass().getMethod("reset").invoke(ctx);
                } catch (Exception e) {
                    ctx.complete();
                    throw new RuntimeException(e);
                }
            }

        }).start();
    }


}

@@ -320,502 +320,107 @@
 ort 
-com.ibm.mfp.adapter.api.OAuthSecurity;%0Aimport io.swagger.annotations.*;%0A%0Aimport java.io.IOException;%0Aimport java.lang.reflect.Field;%0Aimport java.lang.reflect.Method;%0Aimport java.util.*;%0Aimport java.util.logging.Logger;%0A%0Aimport javax.servlet.AsyncContext;%0Aimport javax.servlet.ServletOutputStream;%0Aimport javax.servlet.http.HttpServletRequest;%0Aimport javax.servlet.http.HttpServletResponse;%0Aimport javax.ws.rs.*;%0Aimport javax.ws.rs.container.AsyncResponse;%0Aimport javax.ws.rs.container.Suspended
+io.swagger.annotations.*;%0Aimport java.util.*;%0Aimport java.util.logging.Logger;%0Aimport javax.ws.rs.*
 ;%0Aim
@@ -444,17 +444,16 @@
 core.*;%0A
-%0A
 import c
@@ -3776,1392 +3776,6 @@
  %7D%0A%0A
-%0A    @Path(%22/resource%22)%0A    @GET%0A    @OAuthSecurity(enabled = false)%0A    public void asyncGet(@Suspended final AsyncResponse asyncResponse, final @Context AsyncContext ctx) %7B%0A%0A        new Thread(new Runnable() %7B%0A            @Override%0A            public void run() %7B%0A                try %7B%0A                    Thread.sleep(2000);%0A                    asyncResponse.resume(%22hallo2!%5Cn%22);%0A                %7D catch (Exception e) %7B%0A                    throw new RuntimeException(e);%0A                %7D%0A            %7D%0A%0A        %7D).start();%0A    %7D%0A%0A%0A    @Path(%22/resource2%22)%0A    @GET%0A    @OAuthSecurity(enabled = false)%0A    public void asyncGet2(final @Context HttpServletRequest request, final @Context HttpServletResponse response) %7B%0A%0A        final AsyncContext ctx = request.startAsync(request, response);%0A        new Thread(new Runnable() %7B%0A            @Override%0A            public void run() %7B%0A                try %7B%0A                    Thread.sleep(3000);%0A                    ServletOutputStream os = ctx.getResponse().getOutputStream();%0A                    os.println(%22Done%22);%0A                    os.flush();%0A                    os.close();%0A                    ctx.getClass().getMethod(%22reset%22).invoke(ctx);%0A                %7D catch (Exception e) %7B%0A                    ctx.complete();%0A                    throw new RuntimeException(e);%0A                %7D%0A            %7D%0A%0A        %7D).start();%0A    %7D%0A%0A%0A
 %7D%0A

remove async