Set the default parameter value for the report by code - java

all my crystal report are publish on my business object server.
all of them are connected to Business Views Object.
all of these Business Views use the same dynamic Data Connection.
This make that my report have this Dynamic Data Connection Parameter.
I can change this parameter via the Central Management Console.
But now I would like to be able to change it via code with the BO's SDK.
I have this method that I think is near achieving what i want , I just can save the changes.
public static void updateParameter(IInfoObject report){
// get all parameters
try {
IReport rpt = (IReport) report;
int i = 0;
IReportParameter params;
for(i=0;i<rpt.getReportParameters().size();i++){
params = (IReportParameter) rpt.getReportParameters().get(i);
int y = 0;
for(y=0;y<params.getCurrentValues().getValues(IReportParameter.ReportVariableValueType.STRING).size();y++){
IParameterFieldDiscreteValue val = (IParameterFieldDiscreteValue) params.getCurrentValues().getValues(IReportParameter.ReportVariableValueType.STRING).getValue(y);
if(val.getDescription().contains("Data Connection")){
val.setValue(boConstance.conn_EXAMPLE1);
val.setDescription(boConstance.desc_EXAMPLE1);
//save the new parameter ?????
System.out.println("report parameters modified");
}
}
}
} catch (SDKException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Any Idea ? Thanks,

Since you are already setting the parameters you should just need to call the save method on the IReport itself. You wouldn't save the parameters directly since they are data belonging to the report.
So to finish your example after the for loop
try {
IReport rpt = (IReport) report;
int i = 0;
IReportParameter params;
for(i=0;i<rpt.getReportParameters().size();i++){
// do for loop here setting the parameters
}
rpt.save();
} catch (SDKException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

Related

How to use Guild.kick()?

I'm trying to implement a kick command for my bot, but Guild.kick(Member member) doesn't actually kick the specified user. IntelliJ simply says "Result of Guild.kick(Member member) is ignored". Here's my implementation (with non-relevant code removed):
public void onGuildMessageReceived(#Nonnull GuildMessageReceivedEvent e) {
// other code
g = e.getGuild();
// other code
if (args[0].equalsIgnoreCase("kick")) {
// other code
String target = getConnectedName(args, 1, 0); // gets name of target from message
List<Member> nameList = g.getMembersByEffectiveName(target, true);
try {
target = nameList.get(0).getAsMention();
c.sendMessage("Target: "+target).queue();
} catch (IndexOutOfBoundsException e) {
c.sendMessage("No user found with the name \"target\" in this guild.").queue();
}
Member targetM = null;
if (!nameList.isEmpty()) {
targetM = nameList.get(0);
c.sendMessage(targetM.toString()).queue();
try {
g.kick(targetM);
} catch (HierarchyException e) {
error403MissingPermission(); // sends a message that user is missing permission to use !kick
}
}
}
}
Does anyone know why this won't work / what's wrong with my implementation?
SOLVED:
Guild.kick(Member member) has to be queued like TextChannel.sendMessage(String text) , so the correct usage is g.kick(Member member).queue();. Credit to #Minn

Mailjet API v3 update

I have a serious issue regarding the REST API of Mailjet as used with the recommended v3 library.
When I try to UPDATE I am able to do so for the first time without errors, but when I try to do so again, I got NullPointerException. In spite of that, it does update the stat in the Mailjet Server part.
Also the HTTP Response I get is HTTP/1.1 500 Internal Server Error
Code used:
thisUser=cl.createCall(User.Update).identifiedBy(UserProperty.ID, **myUniqueID**).property(UserProperty.USERNAME, propertyValue).execute();
Any thoughts would be more than welcome.
Ok after the comment, here is the function:
#Path("/userUpdate/{propertyName}/{propertyValue}")
#GET
public Response userUpdate(#PathParam("propertyName") String propertyName, #PathParam("propertyValue") String propertyValue) throws ClientProtocolException, IOException{
MailJetApiClient cl=null;
User thisUser=null;
Response resp=null;
StringEntity stringEntity = null;
try {
cl = MailjetUsersRest.createClient();
} catch (MailJetClientConfigurationException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
try {
thisUser=cl.createCall(User.Get).identifiedBy(UserProperty.ID, ___MY_UNIQUE_ID___).execute();
} catch (MailJetApiCallException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
String email = thisUser.getEmail();
String lastip = thisUser.getLastIp();
Date lastlogin = thisUser.getLastLoginAt();
String local = thisUser.getLocale();
String timezone = thisUser.getTimezone();
Date warned = thisUser.getWarnedRatelimitAt();
try {
cl = MailjetUsersRest.createClient();
switch(propertyName){
case "Username":
thisUser=cl.createCall(User.Update).identifiedBy(UserProperty.ID, ___MY_UNIQUE_ID___).property(UserProperty.USERNAME, propertyValue).execute();
resp = Response.status(200).entity(thisUser).build();
break;
default:
System.out.println("Invalid propertyName.");
break;
}
} catch (MailJetClientConfigurationException | MailJetApiCallException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return resp;
}
First of all, thank you for using Mailjet!
After some testing, I was unable to reproduce your issue. You will find below the code I used.
However I strongly suggest that you open a ticket with our support here.
A working code
Please note that it is unnecessary and considered bad practice to rebuild the client before each call.
// Build a Mailjet client config
MailJetClientConfiguration config;
config = new MailJetClientConfiguration()
.setBaseUrl("https://api.mailjet.com/v3/REST/")
.setDefaultApiKey(System.getenv("MJ_PROD_PUBLIC"))
.setDefaultSecretKey(System.getenv("MJ_PROD_PRIVATE"));
// Build a Mailjet client
MailJetApiClient client = config.buildClient();
// Your code (adapted to my environment, ie no 'Response' object
// and no client factory.)
User thisUser = null;
try
{
// Note that the 'L' in the 'identifiedBy' value fi is necessary
thisUser = client
.createCall(User.Get)
.identifiedBy(UserProperty.ID, /*Our user's ID*/L)
.execute();
}
catch (MailJetApiCallException e2)
{
e2.printStackTrace();
}
String email = thisUser.getEmail();
String lastip = thisUser.getLastIp();
Date lastlogin = thisUser.getLastLoginAt();
String local = thisUser.getLocale();
String timezone = thisUser.getTimezone();
Date warned = thisUser.getWarnedRatelimitAt();
try
{
thisUser = client
.createCall(User.Update)
.identifiedBy(UserProperty.ID, /*Our user's ID*/L)
.property(UserProperty.USERNAME, "DevRel Team Mailjet")
.execute();
}
catch (MailJetApiCallException e)
{
e.printStackTrace();
}
Copy pasting the last bit (the update process) so that the update call is executed twice (without the same new username, of course) doesn't throw any error and certainly not a NullPointerException or a 500 HTTP error code.
And the username is changed accordingly.
So yeah, as written above, please contact our support here. This will allow us to better help you.
If this answer satisfies you, don't forget to accept & upvote it so that others going through similar issues can know this helped :-)

Preloaded Ehcache Ignored when using #Cacheable Annotation

I'm still new to the ehcache API so I may be missing something obvious but here's my current issue.
I currently have a persistent-disk cache that's being stored on my server. I'm currently implementing a passive write-behind cache method that saves key/value pairs to a database table. In the event the persistent-disk cache is lost, I'd like to restore the cache from the database table.
Example I'm using for my write-behind logic:
http://scalejava.blogspot.com/2011/10/ehcache-write-behind-example.html
I'm building a disk persistent using the following method:
import com.googlecode.ehcache.annotations.Cacheable;
import com.googlecode.ehcache.annotations.KeyGenerator;
import com.googlecode.ehcache.annotations.PartialCacheKey;
#Cacheable(cacheName = "readRuleCache", keyGenerator=#KeyGenerator(name="StringCacheKeyGenerator"))
public Rule read(#PartialCacheKey Rule rule,String info) {
System.out.print("Cache miss: "+ rule.toString());
//code to manipulate Rule object using info
try{
String serialziedRule =objectSerializer.convertToString(Rule);
readRuleCache.putWithWriter(new Element(rule.toString(),serialziedRule ));
}
catch(IOException ioe)
{
System.out.println("error serializing rule object");
ioe.printStackTrace();
}
return rule;
}
The write method I'm overriding in my CacheWriter implementation works fine. Things are getting saved to the database.
#Override
public void write(final Element element) throws CacheException {
String insertKeyValuePair ="INSERT INTO RULE_CACHE (ID, VALUE) VALUES " +
"('"+element.getObjectKey().toString()+"','"
+element.getObjectValue().toString()+"')";
Statement statement;
try
{
statement = connection.createStatement();
statement.executeUpdate(insertKeyValuePair);
statement.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Querying and De-serializing the string back in to an object works fine too. I've validated that all the values of the object are present. The disk persistent cache is also being populated when I delete the *.data file and restart the application:
public void preLoadCache()
{
CacheManager cacheManager = CacheManager.getInstance();
readRuleCache = cacheManager.getCache("readRuleCache");
Query query=em.createNativeQuery("select * from RULE_CACHE");
#SuppressWarnings("unchecked")
List<Object[]> resultList = query.getResultList();
for(Object[] row:resultList)
{
try {
System.out.println("Deserializing: "+row[1].toString());
Rule rule = objectSerializer.convertToObject((String)row[1]);
rule= RuleValidator.verify(rule);
if(rule!=null)
{
readAirRuleCache.putIfAbsent(new Element(row[0], rule));
}
}
catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Question
Everything looks OK. However when I pass Rule objects with keys that should exist in the cache the "read" method is called regardless and the *.data file size is increased. Though the write method for the database doesn't attempt to insert existing keys again. Any ideas on what I'm doing wrong?
It turns out this was the culprit:
keyGenerator=#KeyGenerator(name="StringCacheKeyGenerator")
The source material I read on this suggested that the "toString()" method I overrode would be used as the key for the cache key/value pair. After further research it turns out that this is not true. Though the "toString()" key is used. It is nested within class information to create a much larger key.
Reference:
http://code.google.com/p/ehcache-spring-annotations/wiki/StringCacheKeyGenerator
Example Expected key:
"[49931]"
Example Actual Key:
"[class x.y.z.WeatherDaoImpl, getWeather class x.y.z.Weather, [class java.lang.String], [49931]]"

QueryDSL simple query will not cast to object

I am testing QueryDSL against the World database in MySql. I can retrieve the data as a List, but I cannot get it to return as a List. I am querying via SQL, nothing else. This is what I have.
private void getSomething(Connection connection) {
QCountry country = QCountry.country;
SQLTemplates dialect = new HSQLDBTemplates();
SQLQuery query = new SQLQueryImpl(connection, dialect);
//List<Object[]> countries = query.from(country).list(country.all());
List<QCountry> countries = query.from(country).list(country);
System.out.println(countries);
try {
connection.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
I get this error:
java.lang.IllegalArgumentException: RelationalPath based projection can only be used with generated Bean types
You need to generate bean types as described here http://blog.mysema.com/2011/01/querying-in-sql-with-querydsl.html under Bean class generation.

Add several contacts in batch

I am perfectly able to add contacts one by one with following code:
ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>();
ops.add(ContentProviderOperation.newInsert(RawContacts.CONTENT_URI)
.withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, null)
.withValue(ContactsContract.RawContacts.ACCOUNT_NAME, null).build());
ops.add(ContentProviderOperation
.newInsert(Data.CONTENT_URI)
.withValueBackReference(Data.RAW_CONTACT_ID, 0)
.withValue(Data.MIMETYPE,
CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
.withValue(StructuredName.GIVEN_NAME, "Hello")
.withValue(StructuredName.FAMILY_NAME, "World").build());
try {
getContentResolver().applyBatch(ContactsContract.AUTHORITY, ops);
} catch (RemoteException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (OperationApplicationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
However, when I try to add about 500 contacts one by one - it takes few minutes, which is too long for my app. Is the any faster way to add several contacts?
Why not make the arraylist a global that can be accessed from any activity I wouldn't insert that much into a Bundle as there more going on when you do, it was only meant to pass small amounts info. I would do it like this, making sure to call this in the manifest too..
public class MyStates extends Application {
private ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>();
public ArrayList getList() {
return this.blueToothAdapter;
}
public void setList(ArrayList<ContentProviderOperation> o) {
this.ops= o;
}
You can use the same function you are using to add multiple contacts in a single batch operation by making small modifications.
You can add upto 500 operations to a single batch operation, you can keep on including the back-reference in Data Uri operation with the corresponding index of the raw_contacts insert operation.

Categories

Resources