B4J Question B4J Packager additional modules

yiankos1

Active Member
Licensed User
Hello team,
I want to distribute an app (with tool b4j packager) that uses additional jar about sqlite connection and encryption.
B4X:
    #AdditionalJar: sqlite-jdbc-3.30.0
    #AdditionalJar: bcprov-jdk15on-154
Do i have to edit IncludedModules at packager code?
Thank you for your time.
 

yiankos1

Active Member
Licensed User
When I try to run after package from temp folder, everything works fine. If I copy to external drive or another pc, if I start exe (debug console) says that can't open sqlite database. I use custom drive for sqlite. Should I wait for 1.41 version of jSQL that will release with next b4j update?
 

Erel

Administrator
Staff member
Licensed User
The answer to your question was given in post #2.
If you encounter any other error then you should post all the relevant information, including the relevant code and full error message.
 

yiankos1

Active Member
Licensed User
The answer to your question was given in post #2.
If you encounter any other error then you should post all the relevant information, including the relevant code and full error message.
When i run app somewhere else (external drive, other pc) i get this error log when run "run_debug.bat":
B4X:
D:\temp\build\bin>java.exe @release_java_modules.txt  -m b4j/b4j.example.main
main._appstart (java line: -1)
java.sql.SQLException: opening db: 'file:data.db?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=****': ? ??????? ??? ???????? ???????, ??? ???????? ????????? ? ??? ????????
??? ????? ????? ?????????
        at b4j/org.sqlite.Conn.open(Unknown Source)
        at b4j/org.sqlite.Conn.<init>(Unknown Source)
        at b4j/org.sqlite.JDBC.createConnection(Unknown Source)
        at b4j/org.sqlite.JDBC.connect(Unknown Source)
        at java.sql/java.sql.DriverManager.getConnection(Unknown Source)
        at java.sql/java.sql.DriverManager.getConnection(Unknown Source)
        at b4j/anywheresoftware.b4j.objects.SQL.Initialize2(Unknown Source)
        at b4j/anywheresoftware.b4j.objects.SQL.Initialize(Unknown Source)
        at b4j/b4j.example.main._appstart(Unknown Source)
        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
        at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
        at java.base/java.lang.reflect.Method.invoke(Unknown Source)
        at b4j/anywheresoftware.b4a.BA.raiseEvent2(Unknown Source)
        at b4j/anywheresoftware.b4a.BA.raiseEvent(Unknown Source)
        at b4j/b4j.example.main.start(Unknown Source)
        at javafx.graphics/com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$9(Unknown Source)
        at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runAndWait$12(Unknown Source)
        at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$10(Unknown Source)
        at java.base/java.security.AccessController.doPrivileged(Native Method)
        at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$11(Unknown Source)
        at javafx.graphics/com.sun.glass.ui.InvokeLaterDispatcher$Future.run(Unknown Source)
        at javafx.graphics/com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
        at javafx.graphics/com.sun.glass.ui.win.WinApplication.lambda$runLoop$3(Unknown Source)
        at java.base/java.lang.Thread.run(Unknown Source)


D:\temp\build\bin>pause
Press any key to continue . . .
my source code:
B4X:
Sub AppStart (Form1 As Form, Args() As String)
  
    DateTime.DateFormat=("dd/MM/yyyy")
            SQL.Initialize("org.sqlite.JDBC","jdbc:sqlite:file:data.db?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=*****")
  
    DB.CreateUserTableIfNeeded
  
    login.Show
      
End Sub
B4X:
Public Sub CreateUserTableIfNeeded
  
    Dim ct As String = ($"CREATE TABLE IF NOT EXISTS users (
    id INTEGER PRIMARY KEY AUTOINCREMENT Not Null,
    username INTEGER (6) UNIQUE ON CONFLICT FAIL Not Null,
    vathmos TEXT,
    epitheto TEXT,
    onoma TEXT,
    hash BLOB Not Null,
    salt BLOB Not Null,
    level INTEGER (1) Not Null)"$)
    Main.sql.ExecNonQuery(ct)
  
    ct = ($"CREATE TABLE IF NOT EXISTS log (
    id INTEGER PRIMARY KEY AUTOINCREMENT Not Null,
    username INTEGER (6) Not Null,
    last_login TEXT DEFAULT (CURRENT_TIMESTAMP))"$)
    Main.sql.ExecNonQuery(ct)
  
    ct = ($"CREATE TABLE IF NOT EXISTS registry (
    id                    INTEGER PRIMARY KEY AUTOINCREMENT,
    prot_tmima            TEXT    CONSTRAINT prot_tmima_replace UNIQUE ON CONFLICT REPLACE,
    date_eisagogi         TEXT,
    epitheto              TEXT,
    onoma                 TEXT)"$)
    Main.sql.ExecNonQuery(ct)
  
End Sub
I use this sqlite driver. I changed my password with ****
 

Erel

Administrator
Staff member
Licensed User
I've tried it with this code and it works properly:
B4X:
sql.Initialize("org.sqlite.JDBC",$"jdbc:sqlite:file:${File.Combine(File.DirApp, "data.db").Replace("\", "/")}?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=YOURKEY"$)
 

yiankos1

Active Member
Licensed User
n
I've tried it with this code and it works properly:
B4X:
sql.Initialize("org.sqlite.JDBC",$"jdbc:sqlite:file:${File.Combine(File.DirApp, "data.db").Replace("\", "/")}?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=YOURKEY"$)
Hello. Thank you for your answer. Now it does not run even at my pc.
Throws this error
B4X:
main._appstart (java line: 71)
java.sql.SQLException: path to 'file:C:/Users/Yiankos/Desktop/WPD/Objects/data.db?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=****': 'C:\Users\Yiankos\Desktop\WPD\Objects\file:C:' does not exist
    at org.sqlite.Conn.open(Conn.java:103)
    at org.sqlite.Conn.<init>(Conn.java:57)
    at org.sqlite.JDBC.createConnection(JDBC.java:77)
    at org.sqlite.JDBC.connect(JDBC.java:64)
    at java.sql/java.sql.DriverManager.getConnection(DriverManager.java:677)
    at java.sql/java.sql.DriverManager.getConnection(DriverManager.java:228)
    at anywheresoftware.b4j.objects.SQL.Initialize2(SQL.java:57)
    at anywheresoftware.b4j.objects.SQL.Initialize(SQL.java:46)
    at b4j.example.main._appstart(main.java:71)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:566)
    at anywheresoftware.b4a.BA.raiseEvent2(BA.java:91)
    at anywheresoftware.b4a.BA.raiseEvent(BA.java:78)
    at b4j.example.main.start(main.java:37)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$9(LauncherImpl.java:846)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runAndWait$12(PlatformImpl.java:455)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$10(PlatformImpl.java:428)
    at java.base/java.security.AccessController.doPrivileged(Native Method)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$11(PlatformImpl.java:427)
 

Erel

Administrator
Staff member
Licensed User
Does it work when you run it from the IDE? Are you using Java 11 in the IDE?
 

yiankos1

Active Member
Licensed User
Are you using Java 11 in the IDE?
Yes i use this version:
B4X:
C:\Program Files\Java\jdk-11.0.1\bin\javac.exe
Does it work when you run it from the IDE?
Now, It does not run from IDE nor external drive. If i change to my sqlite initialization
B4X:
SQL.Initialize("org.sqlite.JDBC","jdbc:sqlite:file:data.db?cipher=sqlcipher&legacy=1&kdf_iter=4000&key=****")
works on IDE but it does not work on external pc.
Do you need something else in order to help me get this working.
 

Erel

Administrator
Staff member
Licensed User
The error happens inside the custom SQL driver that you found. I cannot really help you as it doesn't happen here. It might be a bug in this driver.

You need to make some tests. I've tested it with sqlite-jdbc-3.30.1.

You should also try other paths.
 

OliverA

Expert
Licensed User
java.sql.SQLException: opening db:
java.sql.SQLException:
This may be a clue. In both of your error message postings, it is java.sql that spits out the error messages. Trying to simulate some error messages on my end, they are as follows
'Error message when wrong path is given
org.sqlite.SQLiteException: [SQLITE_CANTOPEN] Unable to open the database file (unable to open database file)
'Error message when supplying no encryption information
org.sqlite.SQLiteException: [SQLITE_NOTADB] File opened that is not a database file (file is not a database)
Notice how in my case it is the org.sqilte driver that is complaining, not the generic java.sql class
Notes:
1) As @Erel, I was using 3.30.1 driver version
2) I've not packaged the test, but it also works from the command line
 

Daestrum

Well-Known Member
Licensed User
It looks more like a permissions problem than code problem. Do you have write permission for the external drive ?
 

OliverA

Expert
Licensed User
It looks like the objects folder of your project. There should be NO databasefile!
Please note, if you don't give the file: URI a path, the default location is File.DirApp. During testing/development, that will be the Objects folder. Quite normal. Plus @Erel's snippet uses File.DirApp (again Objects during development). It's just odd that java.sql produces the error instead of the driver (since the driver is opening the file). Oh yeah, the SQLite driver happily creates a database file when it cannot be found (as long as the path is correct).
 
Top