I am trying to make a game with auth system in Java. When I am trying to run it, i can see an exception thrown in the console log but there is no error in the project. I know this is runtime error
The console log displays the following information:
Exception in thread "main" java.lang.ClassCastException: com.google.gson.internal.LinkedTreeMap cannot be cast to Auth$Profile
at Auth.<init>(Auth.java:30)
Here is my code:
public Auth(File profilesFile) {
try {
ProfilesJSON e = (ProfilesJSON)this.gson.fromJson(new FileReader(profilesFile), ProfilesJSON.class);
Map ps = e.authenticationDatabase;
Iterator var5 = ps.keySet().iterator();
while(var5.hasNext()) {
String name = (String)var5.next();
Profile p = (Profile)ps.get(name);
if(p != null) {
if(p.displayName == null || p.displayName.length() == 0) {
p.displayName = p.username;
}
this.profiles.add(p);
}
}
} catch (FileNotFoundException var7) {
;
} catch (NullPointerException var8) {
;
}
}
public class Profile {
public String username;
public String password;
public String uid;
public String displayName;
public String name;
public String playerUID;
public Profile(String u, String t, String id, String d) {
this.username = u;
this.password = t;
this.uid = id;
this.displayName = d;
}
}
public class ProfilesJSON {
public Map profiles;
public String selectedProfile;
public String password;
public Map authenticationDatabase;
}
Line 30 is:
Profile p = (Profile)ps.get(name);
This is a part of my code, my idea is if the player press "Remember Password", the game will generate a .json file to store his infomation..I just want to know what I did wrong, other code i can write it myself
Your ps.get(name) is returning a com.google.gson.internal.LinkedTreeMap object instead of Profile.
try to change it to:
LinkedTreeMap p = (LinkedTreeMap )ps.get(name);
Your code doesn't show you errors because there's no error in compile time, ClassCastException is a runtime exception.
Related
SITUATION
In the code below you can see 2 REST services which both should return a MessageVO. The first service (serviceThatDoesWork) returns a MessageVO as excpected, but the second service (serviceThatDoesNotWork) refuses to, it doesn't even give any output at all.
However returning a Response (java.ws.rs.core.Response) with serviceThatDoesNotWork does give an output. Even when I skip the 'doStuff'-methods and create a dummy-MessageVO that is exactly the same for each service, the 2nd one doesn't return anything.
QUESTION
Why does the 2nd service fail to return a MessageVO? It doens't return anything when I try returning a MessageVO, and nothing out of the ordinary appears in the logging.
The two services need to return exactly the same kind of thing but still one of them doesn't want to return anything, what am I not seeing here?
Could it be because of the path (and/or the amount of parameters)?
CODE
MyServices.java:
#Path("/myService")
...
#GET
#Produces(MediaType.APPLICATION_JSON)
#Path("/myPath/{param1}/{param2}/{param3}")
public MessageVO serviceThatDoesWork(#PathParam("param1") Integer param1_id, #PathParam("param2") Integer param2_id, #PathParam("param2") Integer param2_id)
{
List<SomethingVO> lstO = MyRestServiceBusiness.doStuff(param1_id, param2_id, param3_id);
//return SUCCESS or FAIL message
MessageVO msg = new MessageVO();
if(lstO.size() > 0)
{
List<String> s = new ArrayList<String>();
for(SomethingVO k : lstO)
{
s.add(k.getId().toString());
}
msg.setItem_ids(s);
msg.setMsg("SUCCESS");
}
else
{
msg.setMsg("FAIL");
}
return msg;
}
...
#GET
#Path("/myPath/{param1}/{param2}/{param3}/{param4}/.../{param15}{a:(/a/[^/]+?)?}{b:(/b/[^/]+?)?}")
public Response serviceThatDoesNotWork(#PathParam("param1")Integer param1_id, ..., #PathParam("param15") Integer param15_id,
#PathParam("a") String a_id, #PathParam("b") String b_id)
{
//PUT 'OPTIONAL' PARAMS IN A LIST
List<Integer> lstI = new ArrayList<Integer>();
String aId = a_id != null ? a_id.split("/")[2] : null;
String bId = b_id != null ? b_id.split("/")[2] : null;
if(aId != null)
{
lstI.add(Integer.parseInt(aId ));
}
if(bId != null)
{
lstI.add(Integer.parseInt(bId ));
}
//DO STUFF
String afsId = "";
if(lstI.size() > 0)
{
afsId = MyRestServiceBusiness.doStuff(param1, ..., lstI);
}
//return SUCCESS or FAIL message
MessageVO msg = new MessageVO();
if(afsId != null && !afsId.isEmpty())
{
List<String> s = new ArrayList<String>();
s.add(afsId);
msg.setItem_ids(s);
msg.setMsg("SUCCESS");
}
else
{
List<String> s = new ArrayList<String>();
for(Integer i : lstI)
{
s.add(i.toString());
}
msg.setItem_ids(s);
msg.setMsg("FAIL");
}
//WENT THROUGH ALL ABOVE CODE AS EXPECTED, MESSAGEVO HAS BEEN FILLED PROPERLY
return msg;
}
CODE MessageVO.java:
#XmlRootElement
public class MessageVO
{
private String msg;
private List<String> item_ids;
//GETTERS
#XmlElement(name = "Message")
public String getMsg() {
return msg;
}
#XmlElement(name = "Item ID's")
public List<String> getItem_ids() {
return item_ids;
}
//SETTERS
public void setMsg(String msg) {
this.msg = msg;
}
public void setItem_ids(List<String> item_ids) {
this.item_ids = item_ids;
}
If I need to provide extra information please ask, this is my first attempt at (REST-) services.
As Vaseph mentioned in a comment I just forgot the #Produces annotation in the 2nd service.
I am trying to develop a simple application for android using azure mobile services and database, I have used the following code snippets but can't seem to insert any data into my azure table.
The following is the code I used to add the data:
public void createTable(String name, String userBirthday, String email)
{
userInformationTable = mClient.getTable(UserInformation.class);
item = new UserInformation();
item.mId = "1";
item.mEmail = email;
item.mUserBirthday = userBirthday;
item.mName = name;
mClient.getTable(UserInformation.class).insert(item, new TableOperationCallback<UserInformation>()
{
public void onCompleted(UserInformation entity, Exception exception, ServiceFilterResponse response)
{
if (exception == null) {
// Insert succeeded
Log.e("Succeed", "Insert Succeeded");
} else {
// Insert failed
Log.e("Nope", "Insert Failed");
}
}
});
}
The UserInformation Class is as below:
public class UserInformation {
#com.google.gson.annotations.SerializedName("id")
public String mId;
#com.google.gson.annotations.SerializedName("name")
public String mName;
#com.google.gson.annotations.SerializedName("email")
public String mEmail;
#com.google.gson.annotations.SerializedName("user_birthday")
public String mUserBirthday;
public UserInformation(){
}
public UserInformation(String Id, String name, String email, String userBirthday)
{
}
}
There could be many different error roots for that.
Improve your log using this code, this will give you further information about the error nature.
public void createTable(String name, String userBirthday, String email)
{
userInformationTable = mClient.getTable(UserInformation.class);
if(userInformationTable == null)
{
// Insert succeeded
Log.e("Table problem", "There's no table");
}
else
{
item = new UserInformation();
item.mId = "1";
item.mEmail = email;
item.mUserBirthday = userBirthday;
item.mName = name;
userInformationTable.insert(item, new TableOperationCallback<UserInformation>()
{
public void onCompleted(UserInformation entity, Exception exception, ServiceFilterResponse response)
{
if (exception == null) {
// Insert succeeded
Log.e("Succeed", "Insert Succeeded");
} else {
// Insert failed
Log.e("Error Message", exception.getMessage());
Log.e("Error Full", exception.toString());
}
}
});
}
}}
Most probably a connection issue or less probably there aren't tables with that name.
This question already has answers here:
readobject method throws ClassNotFoundException
(2 answers)
Closed 7 years ago.
I am working on windows application in java:
I just test a button that make function login in my system:
My button action performed code:
private void loginActionPerformed(java.awt.event.ActionEvent evt) {
if(emp.isSelected()) // get the selected radio button
{
Account a = new Account();
Emp e = new Emp();
a.setUsername(username.getText().toUpperCase());
a.setPassword(password.getText().toUpperCase());
e.login(a);
this.dispose();
}
else if(supp.isSelected())
{
}
else if(admin.isSelected())
{
Account a = new Account();
Admin m = new Admin();
a.setUsername(username.getText().toUpperCase());
a.setPassword(password.getText().toUpperCase());
m.login(a);
this.dispose();
}
else
JOptionPane.showMessageDialog(null, "Please select a choice", "Alert", JOptionPane.INFORMATION_MESSAGE);
}
The function login code:
public class Emp
{
public void login(Account a)
{
boolean find = false;
ObjectInputStream in = null;
try {
in = new ObjectInputStream(new FileInputStream("C:\\Users\\فاطمة\\Downloads\\employees.bin"));
ArrayList<Account> b = (ArrayList)in.readObject();
Iterator<Account> i = b.iterator();
while(i.hasNext())
{
Account ac = i.next();
if(ac.getUsername().equals(a.getUsername()) && ac.getPassword().equals(a.getPassword()))
{
find = true;
}
else
JOptionPane.showMessageDialog(null, "Wrong username or password .. try again !!", "Login Failed",JOptionPane.ERROR_MESSAGE);
}
if(find)
{
JOptionPane.showMessageDialog(null, "Welcome " + a.getUsername(), "Login Success", JOptionPane.INFORMATION_MESSAGE);
emp_page e = new emp_page();
e.setLocation(350, 150);
e.setSize(400, 490);
e.setTitle("Products Management");
e.setVisible(true);
}
} catch (FileNotFoundException ex) {
//Logger.getLogger(Emp.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException | ClassNotFoundException ex) {
//Logger.getLogger(Emp.class.getName()).log(Level.SEVERE, null, ex);
} finally {
try {
in.close();
} catch (IOException ex) {
//Logger.getLogger(Emp.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
}
The account class code:
import java.io.Serializable;
public class Account implements Serializable{
private String username;
private String password;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
I have a problem: i receive error:
java.lang.classnotfoundexcetpion:Account
and after searching for error reason i found that serialization is the problem of throwing this error because i test this code before in another function that dont use serialization and its worked perfectly.
so my question is: how to fix this error?
NOTE: my application is not a client-server application ... so there is no two projects created ... just only one.
long discussions about this:
ClassNotFoundException when deserializing a binary class file's contents
ClassNotFoundException during Deserialization of a just-serializaed class
Java SerialIzation: 'ClassNotFoundException' when deserializing an Object
3 advices :
be sure to put the private static final long serialVersionUID = XXX;
be sure to embark your class in your classpath/jar
force it in code with Account ac=new Account(); // See if problem here
it helps ?
I created a database in one of my java class files and was wondering how to access/open that database in another java class file to read through the data. I tried using openDatabase but how does it know the location of the database file? I've searched through many forums and all I could find is having the code in the same class and just accessing the database object.
ex.I created a database at the directory /documents/ in one of my java class files and all my java code is somewhere else. How do I access and use that database in my other source code?
Edit:
public static void main(String[] args) {
try {
EnvironmentConfig environmentConfig=new EnvironmentConfig();
environmentConfig.setAllowCreate(true);
Environment environment=new Environment(new File("user/documents/"),environmentConfig);
DatabaseConfig databaseConfig=new DatabaseConfig();
databaseConfig.setAllowCreate(true);
Database db=environment.openDatabase(null,"mytable",databaseConfig);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
I tried the following and I keep getting this error when compiling.
openDatabase(com.sleepycat.db.Transaction,java.lang.String,java.lang.String,com.sleepycat.db.DatabaseConfig) in com.sleepycat.db.Environment cannot be applied to (<nulltype>,java.lang.String,com.sleepycat.db.DatabaseConfig)
Database db=environment.openDatabase(null,key,databaseConfig);
^
1 error
Yeah since it is related to mysql database , that means you have to have a password and username as it is a secure school system , and you can use mysql connector to access the data you created .
To be more clear you have to have database.java file .
then in that file the main thing to know is the constructor and way to go ...
import java.sql.*;
public class database
{
public static database bDatabase = null;
protected String connection_url = "";
protected String _name = "";
protected String name = "";
protected String user = "";
protected String password = "";
protected Class some_class = null;
protected Connection connection = null;
protected ResultSet results = null;
protected String current_table = "";
protected Boolean error = false;
public database(String name, String user, String password)
{
this(name, user, password, "jdbc:mysql://localhost:3306", "com.mysql.jdbc.ClassName");
}
public database(String name, String user, String password, String connection_url, String any_name)
{
this.name = name;
this.user = user;
this.password = password;
this.connection_url = connection_url;
this._name = any_name;
}
public static void openDatabase()
{
try
{
bDatabase = new database("dbname", "user_id",
"password", "jdbc:mysql://host",
"com.mysql.jdbc.Anyclass");
bDatabase.open();
}
catch (Exception ex)
{
throw new InvalidQueryException("Unable to open database ");
}
}
Has anyone an idea about what is wrong with my attempt to call a method from a C# dll in my Java code?
Here is my example:
Java code:
public class CsDllHandler {
public interface IKeywordRun extends Library {
public String KeywordRun(String action, String xpath, String inputData,
String verifyData);
}
private static IKeywordRun jnaInstance = null;
public void runDllMethod(String action, String xpath, String inputData,
String verifyData) {
NativeLibrary.addSearchPath(${projectDllName},
"${projectPath}/bin/x64/Debug");
jnaInstance = (IKeywordRun) Native.loadLibrary(
${projectDllName}, IKeywordRun.class);
String csResult = jnaInstance.KeywordRun(action, xpath, inputData,
verifyData);
System.out.println(csResult);
}
}
And in C#:
[RGiesecke.DllExport.DllExport]
public static string KeywordRun(string action, string xpath, string inputData, string verifyData) {
return "C# here";
}
The Unmanaged Exports nuget should be enough for me to call this method (in theory) but I have some strange error:
Exception in thread "main" java.lang.Error: Invalid memory access
at com.sun.jna.Native.invokePointer(Native Method)
at com.sun.jna.Function.invokePointer(Function.java:470)
at com.sun.jna.Function.invokeString(Function.java:651)
at com.sun.jna.Function.invoke(Function.java:395)
at com.sun.jna.Function.invoke(Function.java:315)
at com.sun.jna.Library$Handler.invoke(Library.java:212)
at com.sun.proxy.$Proxy0.KeywordRun(Unknown Source)
at auto.test.keywords.utils.CsDllHandler.runDllMethod(CsDllHandler.java:34)
at auto.test.keywords.runner.MainClass.main(MainClass.java:24)
Well, after another day of research and "trial and error" I have found the cause of my problem and a solution.
The cause was that my C# dll had a dependency on log4net.dll. For running a static method from a standalone C# dll the code from the question is all you need.
The solution for using C# dll with dependencies is to create another dll with no dependency and to load the original dll in this adapter with reflection. In Java you should load the adapter dll with jna and call any exported method. I was able not only to execute methods from the adapter but also to configure log4net with reflection and Java
Here is my code:
(C#)
public class CSharpDllHandler {
private static Logger log = Logger.getLogger(CSharpDllHandler.class);
public interface IFrameworkAdapter extends Library {
public String runKeyword(String action, String xpath, String inputData,
String verifyData);
public String configureLog4net(String log4netConfigPath);
public String loadAssemblies(String frameworkDllPath,
String log4netDllPath);
}
private static IFrameworkAdapter jnaAdapterInstance = null;
private String jnaSearchPath = null;
public CSharpDllHandler(String searchPath) {
this.jnaSearchPath = searchPath;
// add to JNA search path
System.setProperty("jna.library.path", jnaSearchPath);
// load attempt
jnaAdapterInstance = (IFrameworkAdapter) Native.loadLibrary(
"FrameworkAdapter", IFrameworkAdapter.class);
}
public String loadAssemblies(String frameworkDllPath, String log4netDllPath) {
String csResult = jnaAdapterInstance.loadAssemblies(frameworkDllPath,
log4netDllPath);
log.debug(csResult);
return csResult;
}
public String runKeyword(String action, String xpath, String inputData,
String verifyData) {
String csResult = jnaAdapterInstance.runKeyword(action, xpath,
inputData, verifyData);
log.debug(csResult);
return csResult;
}
public String configureLogging(String log4netConfigPath) {
String csResult = jnaAdapterInstance
.configureLog4net(log4netConfigPath);
log.debug(csResult);
return csResult;
}
public String getJnaSearchPath() {
return jnaSearchPath;
}
}
In the main method just use something like this:
CSharpDllHandler dllHandler = new CSharpDllHandler(
${yourFrameworkAdapterDllLocation});
dllHandler.loadAssemblies(
${yourOriginalDllPath},${pathToTheUsedLog4netDllFile});
dllHandler.configureLogging(${log4net.config file path});
dllHandler.runKeyword("JAVA Action", "JAVA Xpath", "JAVA INPUT",
"JAVA VERIFY");
dllHandler.runKeyword("JAVA Action2", "JAVA Xpath2", "JAVA INPUT2",
"JAVA VERIFY2");
In C# I have the desired methods on the original dll:
public static string KeywordRun(string action, string xpath, string inputData, string verifyData) {
log.Debug("Action = " + action);
log.Debug("Xpath = " + xpath);
log.Debug("InputData = " + inputData);
log.Debug("VerifyData = " + verifyData);
return "C# UserActions result: "+ action+" "+xpath+" "+inputData+" "+verifyData;
}
and all the magic is in the DLL Adapter:
namespace FrameworkAdapter {
[ComVisible(true)]
public class FwAdapter {
private const String OK="OK";
private const String frameworkEntryClassName = "${nameOfTheDllClass with method to run }";
private const String log4netConfiguratorClassName = "log4net.Config.XmlConfigurator";
private static Assembly frameworkDll = null;
private static Type frameworkEntryClass = null;
private static MethodInfo keywordRunMethod = null;
private static Assembly logDll = null;
private static Type logEntryClass = null;
private static MethodInfo logConfigureMethod = null;
private static String errorMessage = "OK";
[RGiesecke.DllExport.DllExport]
public static string loadAssemblies(string frameworkDllPath, string log4netDllPath) {
try {
errorMessage = LoadFrameworkDll(frameworkDllPath, frameworkEntryClassName);
LoadFrameworkMethods("KeywordRun", "Setup", "TearDown");
errorMessage = LoadLogAssembly(log4netDllPath, log4netConfiguratorClassName);
if (errorMessage.CompareTo(OK) == 0)
errorMessage = LoadLogMethods("Configure");
}
catch (Exception e) {
return e.Message;
}
return errorMessage;
}
[RGiesecke.DllExport.DllExport]
public static string configureLog4net(string log4netConfigPath) {
if (errorMessage.CompareTo("OK") == 0) {
StringBuilder sb = new StringBuilder();
sb.AppendLine("Try to configure Log4Net");
try {
FileInfo logConfig = new FileInfo(log4netConfigPath);
logConfigureMethod.Invoke(null, new object[] { logConfig });
sb.AppendLine("Log4Net configured");
}
catch (Exception e) {
sb.AppendLine(e.InnerException.Message);
}
return sb.ToString();
}
return errorMessage;
}
[RGiesecke.DllExport.DllExport]
public static string runKeyword(string action, string xpath, string inputData, string verifyData) {
StringBuilder sb = new StringBuilder();
object result = null;
try {
result = keywordRunMethod.Invoke(null, new object[] { action, xpath, inputData, verifyData });
sb.AppendLine(result.ToString());
}
catch (Exception e) {
sb.AppendLine(e.InnerException.Message);
}
return sb.ToString();
}
private static String LoadFrameworkDll(String dllFolderPath, String entryClassName) {
try {
frameworkDll = Assembly.LoadFrom(dllFolderPath);
Type[] dllTypes = frameworkDll.GetExportedTypes();
foreach (Type t in dllTypes)
if (t.FullName.Equals(entryClassName)) {
frameworkEntryClass = t;
break;
}
}
catch (Exception e) {
return e.InnerException.Message;
}
return OK;
}
private static String LoadLogAssembly(String dllFolderPath, String entryClassName) {
try {
logDll = Assembly.LoadFrom(dllFolderPath);
Type[] dllTypes = logDll.GetExportedTypes();
foreach (Type t in dllTypes)
if (t.FullName.Equals(entryClassName)) {
logEntryClass = t;
break;
}
}
catch (Exception e) {
return e.InnerException.Message;
}
return OK;
}
private static String LoadLogMethods(String logMethodName) {
try {
logConfigureMethod = logEntryClass.GetMethod(logMethodName, new Type[] { typeof(FileInfo) });
}
catch (Exception e) {
return e.Message;
}
return OK;
}
private static void LoadFrameworkMethods(String keywordRunName, String scenarioSetupName, String scenarioTearDownName) {
///TODO load the rest of the desired methods here
keywordRunMethod = frameworkEntryClass.GetMethod(keywordRunName);
}
}
}
Running this code will provide all the logged messages from the original C# DLL to the Java console output (and to a file if configured). In a similar way, we can load any other needed dll files for runtime.
Please forgive my [very probable wrong] way of doing things in C# with reflection, I'm new to this language.