How to upload file to google cloud storage using java? - google-cloud-storage

I use org.apache.commons.fileupload to upload file
class StorageService is a service that use cloud storage APIs to store file
This is my code
public class UploadFileAction extends org.apache.struts.action.Action {
private static final String SUCCESS = "success";
private StorageService storage = new StorageService();
private static final int BUFFER_SIZE = 1024 * 1024;
#Override
public ActionForward execute(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
ServletFileUpload upload = new ServletFileUpload();
FileItemIterator iter = upload.getItemIterator(request);
while (iter.hasNext()) {
FileItemStream item = iter.next();
String fileName = item.getName();
String mime = item.getContentType();
storage.init(fileName, mime);
InputStream is = item.openStream();
byte[] b = new byte[BUFFER_SIZE];
int readBytes = is.read(b, 0, BUFFER_SIZE);
while (readBytes != -1) {
storage.storeFile(b, BUFFER_SIZE);
readBytes = is.read(b, 0, readBytes);
}
is.close();
storage.destroy();
}
return mapping.findForward(SUCCESS);
}
}
package storageservice;
import com.google.appengine.api.files.*;
import com.google.appengine.api.files.GSFileOptions.GSFileOptionsBuilder;
import java.io.*;
import java.nio.channels.Channels;
public class StorageService {
private static final String BUCKET_NAME = "thoitbk";
private FileWriteChannel writeChannel = null;
private OutputStream os = null;
public void init(String fileName, String mime) throws Exception {
FileService fileService = FileServiceFactory.getFileService();
GSFileOptionsBuilder builder = new GSFileOptionsBuilder()
.setAcl("public_read")
.setBucket(BUCKET_NAME)
.setKey(fileName)
.setMimeType(mime);
AppEngineFile writableFile = fileService.createNewGSFile(builder.build());
boolean lock = true;
writeChannel = fileService.openWriteChannel(writableFile, lock);
os = Channels.newOutputStream(writeChannel);
}
public void storeFile(byte[] b, int readSize) throws Exception {
os.write(b, 0, readSize);
os.flush();
}
public void destroy() throws Exception {
os.close();
writeChannel.closeFinally();
}
}
In local this works fine but error when I deploy my app
Please help me!

Make sure your app's service account has WRITE access to the bucket in question, either by adding the service account to the team with can edit rights or else update the bucket acl to explicitly grant the service account WRITE access. See this question for more details.

Related

Get Exception in thread "main" org.zaproxy.clientapi.core.ClientApiException: Does Not Exist on running form ans script authentication using zap api

public class FormAuth {
private static final String ZAP_ADDRESS = "localhost";
private static final int ZAP_PORT = 8080;
private static final String ZAP_API_KEY = null;
private static final String contextId = "1";
private static final String contextName = "Default Context";
private static final String target = "http://localhost:8090/bodgeit";
private static void setIncludeAndExcludeInContext(ClientApi clientApi) throws UnsupportedEncodingException, ClientApiException {
String includeInContext = "http://localhost:8090/bodgeit.*";
String excludeInContext = "http://localhost:8090/bodgeit/logout.jsp";
clientApi.context.includeInContext(contextName, includeInContext);
clientApi.context.excludeFromContext(contextName, excludeInContext);
}
private static void setLoggedInIndicator(ClientApi clientApi) throws UnsupportedEncodingException, ClientApiException {
// Prepare values to set, with the logged in indicator as a regex matching the logout link
String loggedInIndicator = "Logout";
// Actually set the logged in indicator
clientApi.authentication.setLoggedInIndicator(contextId, java.util.regex.Pattern.quote(loggedInIndicator));
// Check out the logged in indicator that is set
System.out.println("Configured logged in indicator regex: "
+ ((ApiResponseElement) clientApi.authentication.getLoggedInIndicator(contextId)).getValue());
}
private static void setFormBasedAuthenticationForBodgeit(ClientApi clientApi) throws ClientApiException,
UnsupportedEncodingException {
// Setup the authentication method
String loginUrl = "http://localhost:8090/bodgeit/login.jsp";
String loginRequestData = "username={%username%}&password={%password%}";
// Prepare the configuration in a format similar to how URL parameters are formed. This
// means that any value we add for the configuration values has to be URL encoded.
StringBuilder formBasedConfig = new StringBuilder();
formBasedConfig.append("loginUrl=").append(URLEncoder.encode(loginUrl, "UTF-8"));
formBasedConfig.append("&loginRequestData=").append(URLEncoder.encode(loginRequestData, "UTF-8"));
System.out.println("Setting form based authentication configuration as: "
+ formBasedConfig.toString());
clientApi.authentication.setAuthenticationMethod(contextId, "formBasedAuthentication",
formBasedConfig.toString());
// Check if everything is set up ok
System.out
.println("Authentication config: " + clientApi.authentication.getAuthenticationMethod(contextId).toString(0));
}
private static String setUserAuthConfigForBodgeit(ClientApi clientApi) throws ClientApiException, UnsupportedEncodingException {
// Prepare info
String user = "Test User";
String username = "test#example.com";
String password = "weakPassword";
// Make sure we have at least one user
String userId = extractUserId(clientApi.users.newUser(contextId, user));
// Prepare the configuration in a format similar to how URL parameters are formed. This
// means that any value we add for the configuration values has to be URL encoded.
StringBuilder userAuthConfig = new StringBuilder();
userAuthConfig.append("username=").append(URLEncoder.encode(username, "UTF-8"));
userAuthConfig.append("&password=").append(URLEncoder.encode(password, "UTF-8"));
System.out.println("Setting user authentication configuration as: " + userAuthConfig.toString());
clientApi.users.setAuthenticationCredentials(contextId, userId, userAuthConfig.toString());
clientApi.users.setUserEnabled(contextId, userId, "true");
clientApi.forcedUser.setForcedUser(contextId, userId);
clientApi.forcedUser.setForcedUserModeEnabled(true);
// Check if everything is set up ok
System.out.println("Authentication config: " + clientApi.users.getUserById(contextId, userId).toString(0));
return userId;
}
private static String extractUserId(ApiResponse response) {
return ((ApiResponseElement) response).getValue();
}
private static void scanAsUser(ClientApi clientApi, String userId) throws ClientApiException {
clientApi.spider.scanAsUser(contextId, userId, target, null, "true", null);
}
/**
* The main method.
*
* #param args the arguments
* #throws ClientApiException
* #throws UnsupportedEncodingException
*/
public static void main(String[] args) throws ClientApiException, UnsupportedEncodingException {
ClientApi clientApi = new ClientApi(ZAP_ADDRESS, ZAP_PORT, ZAP_API_KEY);
setIncludeAndExcludeInContext(clientApi);
setFormBasedAuthenticationForBodgeit(clientApi);
setLoggedInIndicator(clientApi);
String userId = setUserAuthConfigForBodgeit(clientApi);
scanAsUser(clientApi, userId);
}
}
=========================================================================================
/usr/lib/jvm/java-1.11.0-openjdk-amd64/bin/java -javaagent:/snap/intellij-idea-ultimate/319/lib/idea_rt.jar=43425:/snap/intellij-idea-ultimate/319/bin -Dfile.encoding=UTF-8 -classpath /home/arpit/IdeaProjects/maven-zap-demo/target/classes:/home/arpit/Downloads/zap-clientapi-1.9.0.jar ScriptAuth
Exception in thread "main" org.zaproxy.clientapi.core.ClientApiException: Does Not Exist
at org.zaproxy.clientapi.core.ApiResponseFactory.getResponse(ApiResponseFactory.java:50)
at org.zaproxy.clientapi.core.ClientApi.callApi(ClientApi.java:351)
at org.zaproxy.clientapi.gen.deprecated.ScriptDeprecated.load(ScriptDeprecated.java:146)
at ScriptAuth.uploadScript(ScriptAuth.java:76)
at ScriptAuth.main(ScriptAuth.java:93)
The recommended way to automate authentiation in ZAP is to configure and test it in the desktop, then export the context and import that via the API. If the authentication uses scripts then these will need to be registered with ZAP first.

Curator ServiceCacheListener is triggered three times when a service is added

I am learning zookeeper and trying out the Curator framework for service discoveries. However, I am facing a weird issue that I have difficulties to figure out. The problem is when I tried to register an instance via serviceDiscovery, the cacheChanged event of the serviceCache gets triggered three times. When I removed an instance, it is only triggered once, which is the expected behavior. Please see the code below:
public class DiscoveryExample {
private static String PATH = "/base";
static ServiceDiscovery<InstanceDetails> serviceDiscovery = null;
public static void main(String[] args) throws Exception {
CuratorFramework client = null;
try {
// this is the ip address of my VM
client = CuratorFrameworkFactory.newClient("192.168.149.129:2181", new ExponentialBackoffRetry(1000, 3));
client.start();
JsonInstanceSerializer<InstanceDetails> serializer = new JsonInstanceSerializer<InstanceDetails>(
InstanceDetails.class);
serviceDiscovery = ServiceDiscoveryBuilder.builder(InstanceDetails.class)
.client(client)
.basePath(PATH)
.serializer(serializer)
.build();
serviceDiscovery.start();
ServiceCache<InstanceDetails> serviceCache = serviceDiscovery.serviceCacheBuilder()
.name("product")
.build();
serviceCache.addListener(new ServiceCacheListener() {
#Override
public void stateChanged(CuratorFramework curator, ConnectionState state) {
// TODO Auto-generated method stub
System.out.println("State Changed to " + state.name());
}
// THIS IS THE PART GETS TRIGGERED MULTIPLE TIMES
#Override
public void cacheChanged() {
System.out.println("Cached Changed ");
List<ServiceInstance<InstanceDetails>> list = serviceCache.getInstances();
Iterator<ServiceInstance<InstanceDetails>> it = list.iterator();
while(it.hasNext()) {
System.out.println(it.next().getAddress());
}
}
});
serviceCache.start();
BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
System.out.print("> ");
String line = in.readLine();
} finally {
CloseableUtils.closeQuietly(serviceDiscovery);
CloseableUtils.closeQuietly(client);
}
}
}
AND
public class RegisterApplicationServer {
final static String PATH = "/base";
static ServiceDiscovery<InstanceDetails> serviceDiscovery = null;
public static void main(String[] args) throws Exception {
CuratorFramework client = null;
try {
client = CuratorFrameworkFactory.newClient("192.168.149.129:2181", new ExponentialBackoffRetry(1000, 3));
client.start();
JsonInstanceSerializer<InstanceDetails> serializer = new JsonInstanceSerializer<InstanceDetails>(
InstanceDetails.class);
serviceDiscovery = ServiceDiscoveryBuilder.builder(InstanceDetails.class).client(client).basePath(PATH)
.serializer(serializer).build();
serviceDiscovery.start();
// SOME OTHER CODE THAT TAKES CARES OF USER INPUT...
} finally {
CloseableUtils.closeQuietly(serviceDiscovery);
CloseableUtils.closeQuietly(client);
}
}
private static void addInstance(String[] args, CuratorFramework client, String command,
ServiceDiscovery<InstanceDetails> serviceDiscovery) throws Exception {
// simulate a new instance coming up
// in a real application, this would be a separate process
if (args.length < 2) {
System.err.println("syntax error (expected add <name> <description>): " + command);
return;
}
StringBuilder description = new StringBuilder();
for (int i = 1; i < args.length; ++i) {
if (i > 1) {
description.append(' ');
}
description.append(args[i]);
}
String serviceName = args[0];
ApplicationServer server = new ApplicationServer(client, PATH, serviceName, description.toString());
server.start();
serviceDiscovery.registerService(server.getThisInstance());
System.out.println(serviceName + " added");
}
private static void deleteInstance(String[] args, String command, ServiceDiscovery<InstanceDetails> serviceDiscovery) throws Exception {
// in a real application, this would occur due to normal operation, a
// crash, maintenance, etc.
if (args.length != 2) {
System.err.println("syntax error (expected delete <name>): " + command);
return;
}
final String serviceName = args[0];
Collection<ServiceInstance<InstanceDetails>> set = serviceDiscovery.queryForInstances(serviceName);
Iterator<ServiceInstance<InstanceDetails>> it = set.iterator();
while (it.hasNext()) {
ServiceInstance<InstanceDetails> si = it.next();
if (si.getPayload().getDescription().indexOf(args[1]) != -1) {
serviceDiscovery.unregisterService(si);
}
}
System.out.println("Removed an instance of: " + serviceName);
}
}
I appriciate if anyone can please point out where I am doing wrong and maybe can share some good materials/examples so I can refer to. The official website and the examples on github does not help a lot.

how can I key rotate for google cloud storage service account?

I have written code for accessing GCS bucket to store files thru API in java which takes JSON credential file. I have created that JSON file from google console. I need to automate the JSON file or key rotation for every 90 days. How to regenerate/rotate that JSON file? I am a newbie to GCS.
import java.io.IOException;
import java.security.GeneralSecurityException;
import com.google.api.client.googleapis.javanet.GoogleNetHttpTransport;
import com.google.api.client.http.HttpMethods;
import com.google.api.client.http.HttpRequest;
import com.google.api.client.http.HttpRequestFactory;
import com.google.api.client.http.HttpRequestInitializer;
import com.google.api.client.http.HttpTransport;
import com.google.api.client.json.JsonFactory;
import com.google.api.client.json.jackson2.JacksonFactory;
import com.google.api.services.iam.v1.Iam;
import com.google.api.services.iam.v1.IamRequest;
import com.google.api.services.iam.v1.IamRequestInitializer;
import com.google.api.services.iam.v1.model.CreateServiceAccountKeyRequest;
public class TestServiceAccount {
public static void main(String[] args) {
// TODO Auto-generated method stub
//ServiceAccountKey key = new ServiceAccountKey();
try {
System.out.println("created");
String KEY = "AIzaSyDjHg2u4bwfvncb_YwdjJC_vUPRYLW5Sh8";
IamRequestInitializer req = new IamRequestInitializer(KEY);
HttpTransport transport;
transport = GoogleNetHttpTransport.newTrustedTransport();
JsonFactory jsonFactory = new JacksonFactory();
Iam iam = new Iam(transport,jsonFactory,new HttpRequestInitializer() {
public void initialize(HttpRequest httpRequest) {
httpRequest.setConnectTimeout(0);
httpRequest.setReadTimeout(0);
}
});
//https://iam.googleapis.com/v1/projects/newsampleproject/serviceAccounts/NewServiceAccount/keys
MyIamRequest<String> request = new MyIamRequest<String>(
iam, HttpMethods.POST, "/v1/projects/newsampleproject/serviceAccounts/NewServiceAccount/keys", String.class, String.class);
req.initialize(request);
System.out.println(req.getKey());
req.initializeJsonRequest(request);
System.out.println(req.getUserIp());
} catch (GeneralSecurityException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}catch (Exception e) {
e.printStackTrace();
}
//req.initializeJsonRequest(request);
}
public static HttpRequestFactory createRequestFactory(HttpTransport transport) {
return transport.createRequestFactory(new HttpRequestInitializer() {
public void initialize(HttpRequest request) throws IOException {
}
});
}
}
This what I have written to call the API But i am not sure if this is the way to call it.
try this solution, it worked for me
private static void createNewKey(IamRequestInitializer req) throws IOException, GeneralSecurityException {
Iam iam = jsonAuthentication();
CreateServiceAccountKeyRequest keyRequest = new CreateServiceAccountKeyRequest();
keyRequest.setKeyAlgorithm(KEY_ALGO);
String account = SERVICE_ACCOUNT_URL + SERVICE_ACCOUNT_EMAIL;
iam.projects().serviceAccounts().keys().create(account, keyRequest);
String requestString = BASE_URL + SERVICE_ACCOUNT_EMAIL + KEY;
ServiceAccountKey result = getServiceAccountKey(req, iam, requestString);
String jsonKey = new String(result.decodePrivateKeyData());
System.out.println(jsonKey);
JsonFileUtil.createFile(JSON_KEY_FILE_NAME, jsonKey);
}
private static <T> T getServiceAccountKey(IamRequestInitializer req, Iam iam, String requestString)
throws IOException {
MyIamRequest<String> request = new MyIamRequest<String>(iam, HttpMethods.POST, requestString, String.class,
ServiceAccountKey.class);
request.setKey(API_KEY);
request.setFields(
"keyAlgorithm,name,privateKeyData,privateKeyType,publicKeyData,validAfterTime,validBeforeTime");
req.initializeJsonRequest(request);
System.out.println(request.getRequestHeaders());
return (T) request.execute();
}
If you're using a JSON credential file, you are acting as some particular service account which is a member of your project and has access to the files.
Service accounts can be programmatically controlled for exactly this sort of use case. The IAM Service Account API controls service accounts, and the two methods you want for key rotation are serviceAccount.keys.create() and serviceAccount.keys.delete().
The result of the create() call (if you pass in the private key type TYPE_GOOGLE_CREDENTIALS_FILE), will be a new, valid JSON credential file for your service account.
#user7049946
ServiceAccountKey response = getServiceAccountKey(req, iam, requestString);
CreateNewJson.createFile("NEW_JSON_KEY_FILE_NAME", new String(response.decodePrivateKeyData()));
create new class to convert that conent into new file.
public class CreateNewJson {
public static void createFile(String filename, String content) throws IOException {
FileOutputStream fileOutputStream = null;
File file;
file = new File(filename);
fileOutputStream = new FileOutputStream(file);
if (!file.exists()) {
file.createNewFile();
}else{
file.delete();
file.createNewFile();
}
byte[] contentInBytes = content.getBytes();
fileOutputStream.write(contentInBytes);
fileOutputStream.flush();
fileOutputStream.close();
System.out.println("File Created");
}
}

netty SimpleChannelInboundHandler<String> channelRead0 only occasionally invoked

I know that there are several similar questions that have either been answered or still outstanding, however, for the life of me...
Later Edit 2016-08-25 10:05 CST - Actually, I asked the wrong question.
The question is the following: given that I have both a netty server (taken from DiscardServer example) and a netty client - (see above) what must I do to force the DiscardServer to immediately send the client a request?
I have added an OutboundHandler to the server and to the client.
After looking at both the DiscardServer and PingPongServer examples, there is an external event occurring to kick off all the action. In the case of Discard server, it is originally waiting for a telnet connection, then will transmit whatever was in the telnet msg to the client.
In the case of PingPongServer, the SERVER is waiting on the client to initiate action.
What I want is for the Server to immediately start transmitting after connection with the client. None of the examples from netty seem to do this.
If I have missed something, and someone can point it out, much good karma.
My client:
public final class P4Listener {
static final Logger LOG;
static final String HOST;
static final int PORT;
static final Boolean SSL = Boolean.FALSE;
public static Dto DTO;
static {
LOG = LoggerFactory.getLogger(P4Listener.class);
HOST = P4ListenerProperties.getP4ServerAddress();
PORT = Integer.valueOf(P4ListenerProperties.getListenerPort());
DTO = new Dto();
}
public static String getId() { return DTO.getId(); }
public static void main(String[] args) throws Exception {
final SslContext sslCtx;
if (SSL) {
LOG.info("{} creating SslContext", getId());
sslCtx = SslContextBuilder.forClient().trustManager(InsecureTrustManagerFactory.INSTANCE).build();
} else {
sslCtx = null;
}
EventLoopGroup group = new NioEventLoopGroup();
try {
Bootstrap b = new Bootstrap();
b.group(group).channel(NioSocketChannel.class)
.handler(new LoggingHandler(LogLevel.INFO))
.handler(new P4ListenerInitializer(sslCtx));
// Start the connection attempt.
LOG.debug(" {} starting connection attempt...", getId());
Channel ch = b.connect(HOST, PORT).sync().channel();
// ChannelFuture localWriteFuture = ch.writeAndFlush("ready\n");
// localWriteFuture.sync();
} finally {
group.shutdownGracefully();
}
}
}
public class P4ListenerHandler extends SimpleChannelInboundHandler<String> {
static final Logger LOG = LoggerFactory.getLogger(P4ListenerHandler.class);
static final DateTimeFormatter DTFormatter = DateTimeFormatter.ofPattern("yyyyMMdd-HHMMss.SSS");
static final String EndSOT;
static final String StartSOT;
static final String EOL = "\n";
static final ClassPathXmlApplicationContext AppContext;
static {
EndSOT = P4ListenerProperties.getEndSOT();
StartSOT = P4ListenerProperties.getStartSOT();
AppContext = new ClassPathXmlApplicationContext(new String[] { "applicationContext.xml" });
}
private final RequestValidator rv = new RequestValidator();
private JAXBContext jaxbContext = null;
private Unmarshaller jaxbUnmarshaller = null;
private boolean initialized = false;
private Dto dto;
public P4ListenerHandler() {
dto = new Dto();
}
public Dto getDto() { return dto; }
public String getId() { return getDto().getId(); }
Message convertXmlToMessage(String xml) {
if (xml == null)
throw new IllegalArgumentException("xml message is null!");
try {
jaxbContext = JAXBContext.newInstance(p4.model.xml.request.Message.class, p4.model.xml.request.Header.class,
p4.model.xml.request.Claims.class, p4.model.xml.request.Insurance.class,
p4.model.xml.request.Body.class, p4.model.xml.request.Prescriber.class,
p4.model.xml.request.PriorAuthorization.class,
p4.model.xml.request.PriorAuthorizationSupportingDocumentation.class);
jaxbUnmarshaller = jaxbContext.createUnmarshaller();
StringReader strReader = new StringReader(xml);
Message m = (Message) jaxbUnmarshaller.unmarshal(strReader);
return m;
} catch (JAXBException jaxbe) {
String error = StacktraceUtil.getCustomStackTrace(jaxbe);
LOG.error(error);
throw new P4XMLUnmarshalException("Problems when attempting to unmarshal transmission string: \n" + xml,
jaxbe);
}
}
#Override
public void channelActive(ChannelHandlerContext ctx) {
LOG.debug("{} let server know we are ready", getId());
ctx.writeAndFlush("Ready...\n");
}
/**
* Important - this method will be renamed to
* <code><b>messageReceived(ChannelHandlerContext, I)</b></code> in netty 5.0
*
* #param ctx
* #param msg
*/
#Override
protected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {
ChannelFuture lastWriteFuture = null;
LOG.debug("{} -- received message: {}", getId(), msg);
Channel channel = ctx.channel();
Message m = null;
try {
if (msg instanceof String && msg.length() > 0) {
m = convertXmlToMessage(msg);
m.setMessageStr(msg);
dto.setRequestMsg(m);
LOG.info("{}: received TIMESTAMP: {}", dto.getId(), LocalDateTime.now().format(DTFormatter));
LOG.debug("{}: received from server: {}", dto.getId(), msg);
/*
* theoretically we have a complete P4(XML) request
*/
final List<RequestFieldError> errorList = rv.validateMessage(m);
if (!errorList.isEmpty()) {
for (RequestFieldError fe : errorList) {
lastWriteFuture = channel.writeAndFlush(fe.toString().concat(EOL));
}
}
/*
* Create DBHandler with message, messageStr, clientIp to get
* dbResponse
*/
InetSocketAddress socketAddress = (InetSocketAddress) channel.remoteAddress();
InetAddress inetaddress = socketAddress.getAddress();
String clientIp = inetaddress.getHostAddress();
/*
* I know - bad form to ask the ApplicationContext for the
* bean... BUT ...lack of time turns angels into demons
*/
final P4DbRequestHandler dbHandler = (P4DbRequestHandler) AppContext.getBean("dbRequestHandler");
// must set the requestDTO for the dbHandler!
dbHandler.setClientIp(clientIp);
dbHandler.setRequestDTO(dto);
//
// build database request and receive response (string)
String dbResponse = dbHandler.submitDbRequest();
/*
* create ResponseHandler and get back response string
*/
P4ResponseHandler responseHandler = new P4ResponseHandler(dto, dbHandler);
String responseStr = responseHandler.decodeDbServiceResponse(dbResponse);
/*
* write response string to output and repeat exercise
*/
LOG.debug("{} -- response to be written back to server:\n {}", dto.getId(), responseStr);
lastWriteFuture = channel.writeAndFlush(responseStr.concat(EOL));
//
LOG.info("{}: response sent TIMESTAMP: {}", dto.getId(), LocalDateTime.now().format(DTFormatter));
} else {
throw new P4EventException(dto.getId() + " -- Message received is not a String");
}
processWriteFutures(lastWriteFuture);
} catch (Throwable t) {
String tError = StacktraceUtil.getCustomStackTrace(t);
LOG.error(tError);
} finally {
if (lastWriteFuture != null) {
lastWriteFuture.sync();
}
}
}
private void processWriteFutures(ChannelFuture writeFuture) throws InterruptedException {
// Wait until all messages are flushed before closing the channel.
if (writeFuture != null) {
writeFuture.sync();
}
}
#Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
cause.printStackTrace();
ctx.close();
}
}
/**
* Creates a newly configured {#link ChannelPipeline} for a new channel.
*/
public class P4ListenerInitializer extends ChannelInitializer<SocketChannel> {
private static final StringDecoder DECODER = new StringDecoder();
private static final StringEncoder ENCODER = new StringEncoder();
private final SslContext sslCtx;
public P4ListenerInitializer(SslContext sslCtx) {
this.sslCtx = sslCtx;
}
#Override
public void initChannel(SocketChannel ch) {
P4ListenerHandler lh = null;
ChannelPipeline pipeline = ch.pipeline();
if (sslCtx != null) {
P4Listener.LOG.info("{} -- constructing SslContext new handler ", P4Listener.getId());
pipeline.addLast(sslCtx.newHandler(ch.alloc(), P4Listener.HOST, P4Listener.PORT));
} else {
P4Listener.LOG.info("{} -- SslContext null; bypassing adding sslCtx.newHandler(ch.alloc(), P4Listener.HOST, P4Listener.PORT) ", P4Listener.getId());
}
// Add the text line codec combination first,
pipeline.addLast(new DelimiterBasedFrameDecoder(8192, Delimiters.lineDelimiter()));
pipeline.addLast(DECODER);
P4Listener.LOG.debug("{} -- added Decoder ", P4Listener.getId());
pipeline.addLast(ENCODER);
P4Listener.LOG.debug("{} -- added Encoder ", P4Listener.getId());
// and then business logic.
pipeline.addLast(lh = new P4ListenerHandler());
P4Listener.LOG.debug("{} -- added P4ListenerHandler: {} ", P4Listener.getId(), lh.getClass().getSimpleName());
}
}
#Sharable
public class P4ListenerOutboundHandler extends ChannelOutboundHandlerAdapter {
static final Logger LOG = LoggerFactory.getLogger(P4ListenerOutboundHandler.class);
private Dto outBoundDTO = new Dto();
public String getId() {return this.outBoundDTO.getId(); }
#Override
public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) {
try {
ChannelFuture lastWrite = ctx.write(Unpooled.copiedBuffer((String) msg, CharsetUtil.UTF_8));
try {
if (lastWrite != null) {
lastWrite.sync();
promise.setSuccess();
}
} catch (InterruptedException e) {
promise.setFailure(e);
e.printStackTrace();
}
} finally {
ReferenceCountUtil.release(msg);
}
}
}
output from client
Just override channelActive(...) on the handler of the server and trigger a write there.

Testing Intuit IPP

I would like to create some unit tests for inserting data to QuickBooks Online. I am having a problem with the authentication step:
public DataServices Authenticate(IntuitServicesType intuitDataServicesType)
{
DataServices dataServices = null;
string accessToken = HttpContext.Current.Session["accessToken"].ToString();
string accessTokenSecret = HttpContext.Current.Session["accessTokenSecret"].ToString();
string companyID = HttpContext.Current.Session["realm"].ToString();
// now auth to IA
OAuthRequestValidator oauthValidator = new OAuthRequestValidator(accessToken, accessTokenSecret, ConfigurationManager.AppSettings["consumerKey"].ToString(), ConfigurationManager.AppSettings["consumerSecret"].ToString());
ServiceContext context = new ServiceContext(oauthValidator, accessToken, companyID, intuitDataServicesType);
dataServices = new DataServices(context);
if (HttpContext.Current != null && HttpContext.Current.Session != null)
{
HttpContext.Current.Session["DataServices"] = dataServices;
}
return dataServices;
}
In my unit test project, which has no user interface, how can I obtain an access token and an access token secret? I cannot log into Intuit from that area.
[TestMethod()]
public void AuthorizeWithHeadersTest()
{
string accessToken = ConfigurationManager.AppSettings["AccessTokenQBD"];
string accessTokenSecret = ConfigurationManager.AppSettings["AccessTokenSecretQBD"];
string consumerKey = ConfigurationManager.AppSettings["ConsumerKeyQBD"];
string consumerKeySecret = ConfigurationManager.AppSettings["ConsumerSecretQBD"];
string requestUri = "https://appcenter.intuit.com/Developer/Create";
WebRequest webRequest = WebRequest.Create(requestUri);
webRequest.Headers.Add("ContentType", "text/xml");
OAuthRequestValidator target = new OAuthRequestValidator(accessToken, accessTokenSecret, consumerKey, consumerKeySecret);
target.Authorize(webRequest, string.Empty);
Assert.IsTrue(webRequest.Headers.Count > 0);
}
I'm sharing a sample standalone java code snippet. You can try the same in .net
From appcenter, you can create an app to get consumer key, consumer secret and app token.
Using apiexplorer and the above consumer key, consumer secret, you can get access tokens.
AppCenter - https://appcenter.intuit.com/
Apiexplorer - https://developer.intuit.com/apiexplorer?apiname=V2QBO
You can set all the 5 values in the standalone program(setupQBO method). It will work fine.
import java.util.ArrayList;
import java.util.List;
import com.intuit.ds.qb.PartyType;
import com.intuit.ds.qb.QBCustomer;
import com.intuit.ds.qb.QBCustomerService;
import com.intuit.ds.qb.QBInvalidContextException;
import com.intuit.ds.qb.QBObjectFactory;
import com.intuit.ds.qb.QBServiceFactory;
import com.intuit.platform.client.PlatformSessionContext;
import com.intuit.platform.client.PlatformServiceType;
import com.intuit.platform.client.security.OAuthCredentials;
import org.slf4j.Logger;
// QBO API Docs - https://developer.intuit.com/docs/0025_quickbooksapi/0050_data_services/v2/0400_quickbooks_online/Customer
// JavaDocs - http://developer-static.intuit.com/SDKDocs/QBV2Doc/ipp-java-devkit-2.0.10-SNAPSHOT-javadoc/
public class CodegenStubCustomerall {
static String accesstoken = "";
static String accessstokensecret = "";
static String appToken = "";
static String oauth_consumer_key = "";
static String oauth_consumer_secret = "";
static String realmID = "";
static String dataSource = "";
final PlatformSessionContext context;
public CodegenStubCustomerall(PlatformSessionContext context) {
this.context = context;
}
public void testAdd(){
try {
QBCustomer entityPojo = QBObjectFactory.getQBObject(context, QBCustomer.class);
entityPojo.setName("TestQBCustomer12345");
entityPojo.setTypeOf(PartyType.PERSON);
QBCustomerService service = QBServiceFactory.getService(context, QBCustomerService.class);
QBCustomer qbQBCustomer = service.addCustomer(context, entityPojo);
} catch (QBInvalidContextException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}
public List<QBCustomer> testGetAll() {
final List<QBCustomer> entityList = new ArrayList<QBCustomer>();
try {
QBCustomerService service = QBServiceFactory.getService(context, QBCustomerService.class);
List<QBCustomer> qbCustomerList = service.findAll(context, 1,100);
for (QBCustomer each : qbCustomerList) {
entityList.add(each);
}
} catch (QBInvalidContextException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return entityList;
}
public static void main(String args[]) {
PlatformSessionContext context = getPlatformContext("QBO");
CodegenStubCustomerall testObj = new CodegenStubCustomerall(context);
testObj.testGetAll();
}
public static PlatformSessionContext getPlatformContext(String dataSource) {
PlatformServiceType serviceType = null;
if (dataSource.equalsIgnoreCase("QBO")) {
serviceType = PlatformServiceType.QBO;
setupQBO();
}
final OAuthCredentials oauthcredentials = new OAuthCredentials(
oauth_consumer_key, oauth_consumer_secret, accesstoken,
accessstokensecret);
final PlatformSessionContext context = new PlatformSessionContext(
oauthcredentials, appToken, serviceType, realmID);
return context;
}
private static void setupQBO() {
System.out.println("QBO token setup");
accesstoken = "replace your tokens";
accessstokensecret = "replace your tokens";
appToken = "replace your tokens";
oauth_consumer_key = "replace your tokens";
oauth_consumer_secret = "replace your tokens";
realmID = "7123456720";
dataSource = "QBO";
}
}
For sample .net code, you can refer this link.
https://developer.intuit.com/docs/0025_quickbooksapi/0055_devkits/0100_ipp_.net_devkit/0299_synchronous_calls/0001_data_service_apis
Thanks