SMS not received with java smslib library - java

i try with this, but it is some times not working correctly..i used a while loop for loop the code. can i add some listner for this? any one can give me the correct answer for this? in need to get responce real time
while (true) {
msgList = new ArrayList<InboundMessage>();
Service.getInstance().readMessages(msgList, InboundMessage.MessageClasses.ALL);
for (InboundMessage im : msgList) {
if (last < im.getMemIndex()) {
ResultSet rs = DB.getConnection().createStatement().executeQuery("Select * From codes where code='" + im.getText() + "'");
if (rs.next()) {
ResultSet rs2 = DB.getConnection().createStatement().executeQuery("Select * From sms_log where code='" + im.getText() + "' AND tel_no='" + im.getOriginator() + "'");
if (rs2.next()) {
if (m == null) {
m = new SMSClient(1);
}
m.sendMessage(im.getOriginator(), "The Code is Already Sent... Thank You!.");
System.out.println("The Code is Already Sent... Thank You!.");
} else {
System.out.println("The Code Verified... Thank You!.");
if (m == null) {
m = new SMSClient(1);
}
m.sendMessage(im.getOriginator(), "The Code Verified... Thank You!.");
DB.getConnection().createStatement().execute("INSERT INTO sms_log (tel_no,code,status) values('" + im.getOriginator() + "','" + im.getText() + "',1)");
}
} else {
if (m == null) {
m = new SMSClient(1);
}
m.sendMessage(im.getOriginator(), "Invalid Code... Thank You!.");
System.out.println("Invalid Code... Thank You!.");
}
}
}
Thread.sleep(10000);
System.out.println("start");
}

I think IInboundMessageNotification is the interface you are looking for
public class InboundNotification implements IInboundMessageNotification {
#Override
public void process(AGateway aGateway, Message.MessageTypes messageTypes, InboundMessage inboundMessage) {
//add you logic for received messages here
}
}
Add notification class to smsLib service
Service.getInstance().setInboundMessageNotification(new InboundNotification())
From now on, process() method will be called every time your modem receives a message.
As far as I remember, smslib (version 3.5.x) does not delete received messages so it needs to be done manually
#Override
public void process(AGateway aGateway, Message.MessageTypes messageTypes, InboundMessage inboundMessage) {
try {
aGateway.deleteMessage(inboundMessage);
} catch (TimeoutException | GatewayException | InterruptedException | IOException e) {
e.printStackTrace();
}
// your logic here
}
otherwise you will keep receiving not deleted messages every time you receive a new one.
Hope you will find this useful.

Related

Retry the preparedstatement batches if an exception (SQLException | BatchUpdateException) occurs - Java

I had a situation where my code was getting hit by the deadlock issue with SQL Server for some transactions. So, I implemented a retry logic to overcome the same. Now, I'm facing a new problem. The problem is, whenever it retries, the batch which was tried to execute will be empty/cleared after recovering from the exception. This is causing missing data inserts/updates. Please help me with this.
Summary:
Retry the preparedstatement batches if an exception (SQLException | BatchUpdateException) occurs
Current Implementation:
do {
try {
if (isInsert) {
int[] insertRows = psInsert.executeBatch();
psInsert.clearBatch();
System.out.println("insertRowsSuccess:" + Arrays.toString(insertRows));
} else {
int[] updateRows = psUpdate.executeBatch();
psUpdate.clearBatch();
System.out.println("updateRowsSuccess:" + Arrays.toString(updateRows));
}
break;
} catch (BatchUpdateException e) {
conn.rollback();
if (++count == maxTries) {
System.out.println(e.getMessage());
getFailedRecords(e, operation);
}
} catch (SQLException e) {
if (++count == maxTries) {
System.err.format("SQL State: %s\n%s", e.getSQLState(), e.getMessage());
}
}
System.out.println("Tries:" + count);
} while (true);
private static void getFailedRecords(BatchUpdateException ex, String operation) {
int[] updateCount = ex.getUpdateCounts();
ArrayList<Integer> failedRecsList = new ArrayList<Integer>();
int failCount = 0;
for (int i = 0; i < updateCount.length; i++) {
if (updateCount[i] == Statement.EXECUTE_FAILED) {
failCount++;
failedRecsList.add(i);
}
}
System.out.println(operation + " Failed Count: " + failCount);
System.out.println(operation + " FailedRecordsIndex:" + failedRecsList);
}
After execute, irrespective of success or failure of the batch, the batch will be cleared. You will need to repopulate the batch before you can retry.
I think you should just move the clearBatch() outside of the try. If you have to recheck whether it's an insert or update, so be it. If psInsert and psUdate are the same class, or derive from the same base class (and it sounds like they should), you can easily call it in a separate one liner method.
I also think if you submit this question to code review, you'd get some good suggestions to improve the code. I'm not saying it's terrible, but I think there's room for improvement in the underlying model. I'm not familiar enough with Java, though.

Java continue statement not allowed in anonymous inner class

I am threading a time consuming for-loop and executing them inside N number of threads. A continue statement is throwing error
Getting the error "Continue cannot be used outside of a loop"
for (final Message m : messagelistholder.getMessage()) {
Callable<Void> tasksToExecute = new Callable<Void>() {
public Void call() {
if (guidanceonly1 == true && !QuoteUtil.isECPQuote(list.get(0))) {
String msg = "Message From " + m.getSource() + " when retrieving Guidance values: "
+ m.getDescription();
String lcladdStatusMessages = CommonUtil.getLoclizedMsg(
"PRCE_LNE_ITM_MSG_FRM_WHN_RETRVNG_GUIDNCE_VAL",
new String[]{m.getSource(), m.getDescription()}, msg);
list.get(0).addStatusMessages("Info", lcladdStatusMessages);
} else if ("Error".equalsIgnoreCase(m.getSeverity())) {
if (m.getCode().indexOf("_NF") > 0) {
continue; // price not found due to private sku
}
if ("Eclipse".equalsIgnoreCase(m.getSource())) {
String msg1 = "Please check Sold To customer data. ";
String lcladdStatusMessages1 = CommonUtil
.getLoclizedMsg("PRCE_LNE_ITM_PLS_CHK_SLDTO_CUST_DTA", null, msg1);
String msg2 = "Discount information may not be returned from Optimus due to "
+ m.getSeverity() + " From " + m.getSource() + " " + m.getDescription();
String lcladdStatusMessages2 = CommonUtil.getLoclizedMsg(
"PRCE_LNE_ITM_DSCNT_INFO_MNT_RTRND_FRM_OPTMS_DUETO_FRM",
new String[]{m.getSeverity(), m.getSource(), m.getDescription()}, msg2);
list.get(0).addStatusMessages(m.getSeverity(),
(m.getDescription().contains("MDCP") ? lcladdStatusMessages1 : "")
+ lcladdStatusMessages2);
} else {
if (response1.getItems() == null) {
String lcladdStatusMessages = CommonUtil.getLoclizedMsg("PRCE_LNE_ITM_OPTMS_ERR",
new String[]{m.getSource(), m.getDescription()}, m.getDescription());
list.get(0).addStatusMessages("Error", lcladdStatusMessages);
list.get(0).setOptimusError(true);
} else {
if (!QuoteUtil.isECPQuote(list.get(0))) {
String lcladdStatusMessages = CommonUtil.getLoclizedMsg(
"PRCE_LNE_ITM_MSG_FRM_WHN_RETRVNG_GUIDNCE_VAL",
new String[]{m.getSource(), m.getDescription()},
"Message From " + m.getSource() + " " + m.getDescription());
list.get(0).addStatusMessages("Info", lcladdStatusMessages);
list.get(0).setOptimusError(true);
}
}
}
}
if (list.get(0).getFlags().get(QtFlagType.ESCALATIONFORPARTNER) != null) {
list.get(0).getFlags().get(QtFlagType.ESCALATIONFORPARTNER).setFlgVl(null);
}
if (m.getCode() != null) {
String pricingServiceMsgCode = m.getCode();
String pricingServiceSeverity = m.getSeverity();
Map<Integer, AutoEscalationScenario> categoryMap;
if (StringUtils.equals("ERROR", pricingServiceSeverity)) {
categoryMap = getScenario("SEVERITY", globalAccount1, null, true, null);
if (categoryMap.size() != 0) {
finalCategorylist.get(0).putAll(categoryMap);
}
}
if (partnerExclusivityAutoEscalation1) {
categoryMap = getScenario(pricingServiceMsgCode, globalAccount1, null, true, null);
if (categoryMap != null && categoryMap.size() != 0) {
finalCategorylist.get(0).putAll(categoryMap);
}
}
}
return null;
}
};
runnableTasks.add(tasksToExecute);
}
Can someone help me to skip the particular loop for the speicified condition but without using continue statement since it throws error.
What's happening is that you are actually calling continue outside of a loop because the call() function itself does not have a for loop, so it doesn't matter if are only calling call() from a loop.
What can you do to fix this is making the call function to return a boolean and replacing the continues with return true and return false if no return true has been reached.
Then replace the:
call()
on the loop(s) for
if(call()) continue
So the I'm not saying I fully understand you code, but it appears that you are using continue to break out of that thread. On a normal multi-threaded application, it looks like you are launching multiple threads from one one loop. The continue call is inside the new thread, not the loop. As soon as you start writing the call() method, you leave the loop to run it. Looking at the code, I would try replacing continue with return. Normally I would try running it myself before I suggest it, but without the rest of the code I cannot verify that it works.

How to retrieve new incoming data by polling and feed it back

Here the method reads the database which has an unique ID with the sequence number which keeps on increasing, since am a beginner in java,can I know how to implement this repetitive polling and check for new incoming message each time.
public void run() {
int seqId = 0;
while(true) {
List<KpiMessage> list = null;
try {
list = fullPoll(seqId);
if (!list.isEmpty()) {
seqId = list.get(0).getSequence();
incomingMessages.addAll(list);
System.out.println("waiting 3 seconds");
System.out.println("new incoming message");
Thread.sleep(3000);
}
} catch (Exception e1) {
e1.printStackTrace();
}
}
}
//Method which defines polling of the database and also count the number of Queries
public List<KpiMessage> fullPoll(int lastSeq) throws Exception {
Statement st = dbConnection.createStatement();
ResultSet rs = st.executeQuery("select * from msg_new_to_bde where ACTION = 804 and SEQ >" + lastSeq + "order by SEQ DESC");
List<KpiMessage> pojoCol = new ArrayList<KpiMessage>();
while (rs.next()) {
KpiMessage filedClass = convertRecordsetToPojo(rs);
pojoCol.add(filedClass);
}
for (KpiMessage pojoClass : pojoCol) {
System.out.print(" " + pojoClass.getSequence());
System.out.print(" " + pojoClass.getTableName());
System.out.print(" " + pojoClass.getAction());
System.out.print(" " + pojoClass.getKeyInfo1());
System.out.print(" " + pojoClass.getKeyInfo2());
System.out.println(" " + pojoClass.getEntryTime());
}
// return seqId;
return pojoCol;
}
My goal is to Poll the table from the database and also check for new incoming message, which I can find from the Header field SequenceID in table which is unique and keeps on increasing for new entries. Now my problem is
1.Lets say after I poll the first time, it reads all the entries and makes the thread to sleep for 6 seconds, by the mean time how can I get the new incoming data and Poll it again ?
2.Also how to add the new data ,when it does Polling for the second time and pass the new data to another class.
Poller calls fullPoll every 6 secs and passes lastSeq param to it. Initially lastSeq = 0. When Poller gets result list it replaces the lastSeq with max SEQ value. fullPoll retrieves only records with SEQ > lastSeq.
void run() throws Exception {
int seqId = 0;
while(true) {
List<KpiMessage> list = fullPoll(seqId);
if (!list.isEmpty()) {
seqId = list.get(0).getSequene();
}
Thread.sleep(6000);
}
}
public List<KAMessage> fullPoll(int lastSeq) throws Exception {
...
ResultSet rs = st.executeQuery("select * from msg_new_to_bde where ACTION = 804 and SEQ > " + lastSeq + " order by SEQ
DESC");
..
}
Here is some code you may use to get working on. I tried to make it pretty flexible using the Observer pattern; this way you can connect multiple "message processors" to the same poller:
public class MessageRetriever implements Runnable {
private int lastID;
private List<MessageListener> listeners;
...
public void addMessageListener(MessageListener listener) {
this.listeners.add(listener)
}
public void removeMessageListener(MessageListener listener) {
this.listeners.remove(listener)
}
public void run() {
//code to repeat the polling process given some time interval
}
private void pollMessages() {
if (this.lastID == 0)
this.fullPoll()
else
this.partialPoll()
}
private void fullPoll() {
//your full poll code
//assuming they are ordered by ID and it haves the ID field - you should
//replace this code according to your structure
this.lastID = pojoCol.get(pojoCol.length() - 1).getID()
this.fireInitialMessagesSignal(pojoCol)
}
private void fireInitialMessagesSignal(List<KAMessage> messages) {
for (MessageListener listener : this.listeners)
listener.initialMessages(messages)
}
private void partialPoll() {
//code to retrieve messages *past* the lastID. You could do this by
//adding an extra condition on your where sentence e.g
//select * from msg_new_to_bde where ACTION = 804 AND SEQ > lastID order by SEQ DESC
//the same as before
this.lastID = pojoCol.get(pojoCol.length() - 1).getID()
this.fireNewMessagesListener(pojoCol)
}
private void fireNewMessagesListener(List<KAMessage> messages) {
for (MessageListener listener : this.listeners)
listener.newMessages(messages)
}
}
And the interface
public interface MessageListener {
public void initialMessages(List<KAMessage> messages);
public void newMessages(List<KAMessage> messages)
}
Basically, using this approach, the retriever is a runnable (can be executed on it's own thread) and takes care of the whole process: does an initial poll and continues doing "partial" polls on given intervals.
Different events fire different signals, sending the affected messages to the registered listeners, and those process the messages as they want.

How to find the number of vote up or vote down for a youtube comment through API

I am fetching the comments for a video using Youtube's Java API. I want to know can I find the number of up votes or down votes for all the comment. If yes then how. Currently I am using the code given below. I am getting totalRating for each comment to find upvotes but every-time it outputs 0. I know this is wrong but how do I get the vote up and down for comments.Any pointers in the right direction will be appreciated. Thanks.
private void AddComments(YouTubeVideo ytv,VideoEntry videoEntry,YouTubeService service)
{
try
{
//Get Comments
String commentUrl = videoEntry.getComments().getFeedLink().getHref();
LinkedList<YouTubeComment> commentsLinkedList = new LinkedList<YouTubeComment>();
if(commentUrl!= null && commentUrl.length() > 0)
{
CommentFeed commentFeed = service.getFeed(new URL(commentUrl), CommentFeed.class);
if(commentFeed != null)
{
for(CommentEntry comment : commentFeed.getEntries())
{
YouTubeComment youtubeComment = new YouTubeComment();
if(comment.getTotalRating()!=null)
**//comment.getTotalRating() is always equal to 0.**
youtubeComment.setLike(comment.getTotalRating());
else
youtubeComment.setLike(0);
youtubeComment.setSpamStatus(comment.hasSpamHint());
String commentinVideo = comment.getPlainTextContent();
if(commentinVideo != null)
youtubeComment.setComment(comment.getPlainTextContent());
else
youtubeComment.setComment(" ");
commentsLinkedList.add(youtubeComment);
}
ytv.setComments(commentsLinkedList);
}
else
ytv.setComments(commentsLinkedList);
}
else
{
ytv.setComments(commentsLinkedList);
}
}
catch(Exception ex)
{ // This means that "Comments are disabled for this video."
LinkedList<YouTubeComment> comments = new LinkedList<YouTubeComment>();
ytv.setComments(comments);
System.out.println("Could not add comments for video := " + videoUrl);
System.out.println("This happens when comments are disabled for the video");
System.out.println("Exception in function AddComments : " + ex.toString());
}
}
Unfortunately, those values are not exposed via the API, and there are no plans to add them.

How to publish multiple event using EventQueues.publish in zk

Hope your problem is resolved, but my problem is still there
and I thought that you can help me to get out of this problem.
actually I had multiple events to publish one by one as per user
selection for eg: user select Season, Service, DateFrom and
DateTo and then clicks on the refresh button.
When the refresh button is clicked I had used the above logic to
get all the datas using the below mentioned code
public void onClick$ref(Event event){
if(lbox_service.getSelectedIndex() != 0 || lbox_season.getSelectedIndex() != 0)
{
if(lbox_service.getSelectedIndex() == 0)
{
setService_id("0");
}
else
{
setService_id(lbox_service.getSelectedItem().getValue().toString());
}
if(lbox_season.getSelectedIndex() == 0)
{
setSeason_id("0");
}
else
{
setSeason_id(lbox_season.getSelectedItem().getValue().toString());
}
System.out.println("Service Index 11 : "+ lbox_service.getSelectedIndex());
System.out.println("Season Index 11 : "+ lbox_season.getSelectedIndex());
EventQueue evtQ = EventQueues.lookup("myEventQueue", EventQueues.APPLICATION, true);
//evtQ.publish(new Event("service_id", self, lbox_service.getSelectedItem().getValue().toString()));
//evtQ.publish(new Event("season_id", self, lbox_season.getSelectedItem().getValue().toString()));
evtQ.publish(new Event("service_id", self, getService_id()));
evtQ.publish(new Event("season_id", self, getSeason_id()));
//evtQ.publish(new Event("onClickRef", null, lbox_service.getSelectedItem().getValue().toString()));
//evtQ.publish(new Event("onClickRef", null, lbox_season.getSelectedItem().getValue().toString()));
/*.publish(new Event("onClickRef", null, lbox_service.getSelectedItem().getValue().toString()));
EventQueues.lookup("myEventQu", EventQueues.DESKTOP, true).publish(new Event(
"onClickRef", null, lbox_season.getSelectedItem().getValue().toString()));*/
}
else
{
setService_id("0");
setSeason_id("0");
EventQueue evtQ = EventQueues.lookup("myEventQueue", EventQueues.APPLICATION, true);
evtQ.publish(new Event("service_id", self, getService_id()));
evtQ.publish(new Event("season_id", self, getSeason_id()));
System.out.println("Service Index : "+ lbox_service.getSelectedIndex());
System.out.println("Season Index : "+ lbox_season.getSelectedIndex());
}
}
now i had publish all my value and after that my new Controller
run that will subscribe those published values. using the
below code
public void doAfterCompose(Component comp) throws Exception {
super.doAfterCompose(comp);
EventQueues.lookup("myEventQueue", EventQueues.APPLICATION, true).subscribe(new EventListener() {
public void onEvent(Event event) throws Exception {
/*String service = (String) event.getData();
logger.info("Servive $$$$$$$$$ " + service);
//String season = (String) event.getData();
//logger.info("Season $$$$$$$$$ " + season); */
if("service_id".equals(event.getName())) {
setService_id((String) event.getData());
baseController.setFilter_bar(true);
System.out.println("Service Id :" +event.getData());
}
else if("season_id".equals(event.getName())) {
setSeason_id((String) event.getData());
baseController.setFilter_bar(true);
System.out.println("Season Id :" +event.getData());
}
/*setService_id((String) event.getData());
setSeason_id((String) event.getData());*/
/*if("season_id".equals(event.getName())){
setSeason_id((String) event.getData());
}else
{
setSeason_id("0");
}*/
System.out.println("Filter bar :" +baseController.isFilter_bar());
if(baseController.isFilter_bar() == true)
{
String dateFrom = "";
String dateTo = "";
String order = "2";
List TDRetailers = verificationStoreHibernateDao.getTraditionalRetailers(
getService_id(), getSeason_id(), dateFrom, dateTo, order);
//VerificationStoreHibernateDao storeHibernateDao = new VerificationStoreHibernateDao();
//List TDRetailers = this.verificationStoreHibernateDao.getTraditionalRetailers(service_id);
//ListModel listModel = this.retailers.getModel();
ListModelList listModelList = (ListModelList) retailer.getModel();
listModelList.clear();
listModelList.addAll(TDRetailers);
baseController.setFilter_bar(true);
}
}
});
}
but actully my problem is with running the query and with
getting those published values. Based on them I will be able to
run my Traditional getTraditionalRetailers queries.
My problem is
how to publish multiple events values. Is it the right way
that I had done.
as I had done separate publish, everytime
I publish new value The query runs, the result is that i had
mutiple time query execution. for example If i will publish two
values the queries run's for the two times and if I publish
three values the query executes for three time.
I don't know what is their problem. Help me to solve my error.
The event object passed through EventQueue is where you put your payload there. You can just define an aggregate Event class and collect information and publish them in a whole.
If you can publish all information in a whole(using an aggregate Event), this is solved automatically.

Categories

Resources