Code Monkey home page Code Monkey logo

fxlauncher's Introduction

FXLauncher

Maven Central Apache License

Auto updating launcher for JavaFX Applications. Combined with JavaFX native packaging, you get a native installer with automatic app updates.

You can see the launcher in action in this Demo Application.

QuickStart projects

Changelog

Check out the changelog for a list of all updates to the project.

Video demonstration

See the launcher in action in this short screencast. There is also a video about customizing the update user interface.

How does it work?

FXLauncher is a 18Kb jar that can be used to boot your application. It knows the location of your application repository where you host all the app resources.

See a manifest example here. FXLauncher will look up the remote repository to check for a newer version of the manifest on each startup.

After the manifest is retrieved, FXLauncher synchronizes every file mentioned in the manifest while providing the user with a progress indicator. After all resources are in sync, a classloader is initialized with all the resources from the manifest.

Lastly, the application entry point retrieved from the manifest is invoked. Everything happens in-JVM, no restarts needed.

Before each run, the launcher will synchronize all resources and seamlessly launch an always updated application.

How to use FXLauncher

See the QuickStart projects at the top of the README for information on integrating FXLauncher in your build system.

Adhoc usage

FXLauncher can also be used to launch an application at an arbitrary url by specifying the --app parameter at startup:

java -jar fxlauncher.jar --app=http://remote/location/app.xml

Alternatively (or in combination with --app...), you can override the uri attribute in the manifest (app.xml) so that both app.xml and all resources are loaded from the specified uri. This is especially useful for testing the complete setup locally or from a staging environment.

java -jar fxlauncher.jar --uri=http://remote/location/

The two parameters also work in tandem, allowing you to load a specified manifest from one URL and override its uri.

java -jar fxlauncher.jar --app=http://remote/location/app.xml --uri=http://remote/location/

Note: All parameters (including these) are passed on to your application. So please ensure that your parameters have a different name if they carry different data.

Include other artifacts

--include-extensions accepts a comma separated list of filename extensions to include of other resources from the build dir. By default it always includes jar, war.

Class-Loader issues

To load the application FXLauncher creates a new classloader fed with the classes of your manifest. This works as long as none of the classes uses the system classloader to load one of your classes or resources which is not aware of the application classes then.

One example is Java's java.net.URL class which uses Class.forName to load a custom handler, which uses the classloader of the callee which is the system classloader then.

To workaround that problem you could setup a special FXLauncher classloader which allows a different strategy how to feed the classpath with additional classpath entries.

java -Djava.system.class.loader=fxlauncher.FxlauncherClassCloader -jar fxlauncher.jar --app=http://remote/location/app.xml

Headless

FXLauncher allows you to run in headless mode and thus be used not only for JavaFX applications, but also for e.g. services which run without any gui at all.

For this to work you could use fxlauncher.HeadlessMainLauncher

java -classpath fxlauncher.jar fxlauncher.HeadlessMainLauncher --app=http://remote/location/app.xml

Notice: WhatsNew is not supported.

File based deployment

The app uri can be a file:// based url instead of a web uri if your application is hosted on a common network location for your users.

UNC Paths

FXLauncher can deal with UNC paths, if you ask it nicely. Instead of \\server\share\myapp use file:////server/share/myapp. Yes, that's four forward slashes; two for the file:// protocol and two for the UNC path.

Native installers

The native installer does not contain any application code, only the launcher. There is no need to rebuild your native installer when you update your project, simply run the deploy-app goal and all users will run the newest version on their next startup. Point users to the fxlauncher.jar or to a native installer if you wish.

Try a native installer

Check out these prebuilt installers for a more complex demo application

Specify cache directory

By default, the artifacts are downloaded to the current working directory. This is usually fine for per-user native installers, but if you distribute your application via a system-wide native installer, or just the launcher jar, you might want to specify where the downloaded artifacts land. See the cache dir documentation for more information.

Installation location

It's worth noting that the two package alternatives for Windows, (EXE and MSI) have different default install locations. While EXE will default to %LocalAppData%, the MSI installer will default to %ProgramFiles%. To write to %ProgramFiles% one definitely does need admin privileges—that poses a problem for FXLauncher which, by default, downloads updates to where it was installed.

If you use the MSI installer you will therefore need to tell FXLauncher to cache artifacts somewhere it is allowed to put them. For an OS-independent answer to this problem, look no further than the two magical strings, USERLIB and ALLUSERS.

Read more about Java Packager in the official documentation:

https://docs.oracle.com/javase/8/docs/technotes/guides/deploy/self-contained-packaging.html

Accept downgrades

FXLauncher will not download a remote version if the local version is newer. This is controlled by comparing a timestamp in the manifest. Specifying --accept-downgrades=true as the last argument to CreateManifest will allow you to make sure that the version you have published will always be used by your clients even if they have a newer version installed. This option is also available in the Gradle plugin as acceptDowngrades.

Ignore ssl errors.

If you are behind a proxy that does a man in the middle attack to snoop on ssl connections, you can use the --ignoressl commandline option to ignore the ssl errors this will generate.

Stop after update errors.

Normally FXlauncher will try to launch the application even if there were errors during the update of the files from the server. Often this will work using the files already in the local cache. You can change this behavior by specifying --stop-on-update-errors=true. The error will be shown and the launcher will exit. Specifying --stopOnUpdateErrors will result in the same behavior, but this variant is deprecated and will be removed in future versions. If both options are specified the value of --stop-on-update-errors will be used.

Show what's new dialog.

You can have FXLauncher show a whats new dialog. This dialog will only be shown when FXLauncher has to download new files from the server. The html will be shown in a WebView. Specify --whats-new=https://whatsnewurl/here

Applications with no default UI

By default the update screen will remain visible until the primary stage is shown. If your application does not show anything on the primary stage at startup, the update screen will stay visible until it does. You can pass in --lingering-update-screen=false to hide it immediately after the update process has completed.

A slimmer alternative

Instead of using javapackager to create an installer, you can embed the fxlauncher jar in a native installer system like Advanced Installer—same approach as above, but without using javapackager. With this approach, you can choose whether to include a JRE or have the installer software preinstall it. Again, you are only distributing the launcher with the native installer, the rest is pulled down on demand.

A note on classloaders

FXLauncher uses a custom classloader to dynamically load the synchronized resources. This classloader is then made available to the FXMLLoader. You can access it via FXMLLoader.getDefaultClassLoader().

Platform specific resources

FXLauncher supports filtering of resources for the running platform. Any resource that ends with -[mac|win|linux].jar will only be downloaded and put on the classpath on the corresponding platform. The manifest enforces this though the os attribute in app.xml.

Native libraries

If you need to load native libraries before the custom class loader kicks inn, specify the --preload-native-libraries= parameter to CreateManifest. It supports a comma separated list of libraries to load. Remember: No extensions, just the library name.

Custom UI

There are two ways to customize the appearance of the update UI. Either you can configure the supported style properties in the manifest, or you can provide a custom implementation of the UIProvider to completely customize the UI. Have a look at this Custom UI Demo Project for more information about customizing the updater.

fxlauncher's People

Contributors

dimonchik0036 avatar edvin avatar fjtorres avatar frknikiz avatar gcstang avatar humpfle avatar imario42 avatar ronsmits avatar terjedahl avatar ttaomae avatar turekbot avatar xzel23 avatar ypenekli avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

fxlauncher's Issues

[Idea] Reworking architecture of fxlauncher

As discussed in #15, reworking the architecture of fxlauncher would allow to bring new features to it such as:

  1. Enabling updates for the launcher itself
  2. Version control of the application and rollback function
  3. Downloading the appropriate JRE (if not present on the system)

All of those changes would result in a small native executable (exe, app, etc.) that would download all needed dependencies on the first launch. The native stub wouldn't be bigger than 1 MB for sure, meaning that the launcher would function as a 'web installer'.

A way to update the build in jre

Hey Edvin,
could you think of any way to make it possible updating the build in jre too?
Besides customizing the updater ui (which was mentioned in another issue) and passing in some jmv arguments, it's the one thing left on my list :)

New Feature: multiple release channels

Once I had dug into the FxLauncher code a little working on the icon issue I raised, I thought it might be easy to add support for multiple release channels. I really wanted this so I could fully test my app without disturbing my current users. So I dug in and got it working pretty quick.

It uses two setting files - one contains a list of release channels (which would be downloaded from a configured URL) and the other only contains a setting for which channel should be used at launch. The app URLs are different for each channel. The app.xml manifest for each channel specifies a different cacheDir folder, so the downloaded files for the channels are maintained separately. The files are consulted prior to launch to decide which app.xml URL (and thus which cacheDir) to use for launching. Switching channels requires editing the second settings file, but with the addition of a UI component in my app, the user could switch easily between release channels by making a selection in the UI and then restarting.

The implementation currently sits in a layer between the native launcher and FxLauncher. But it would be pretty easy for me to move that into FxLauncher.

Would you be interested in including this feature in FxLauncher?

URL resolving counter intuitive

I tried to setup an update repository for my app with github pages. The url (folder) that contains all files is http://sirwindfield.github.io/taskflow/application-support. I added it in the manifest as app.url. But resolving the url for the first artifact, guide.jar, doesn't work as I would have expected it. The launcher checks the location http://sirwindfield.github.io/guice.jar.

I understand that it resolves it correctly (from a programmer's view) but specifying a URL should allow people to be able to use other locations and not only the base url location.

Be able to pass remote URL on command line

It would be really nice if you could pass the URL of the remote app.xml to the Launcher. This would be much easier than trying to replace the app.xml in the fxlauncher.jar file.

Gradle plugin: Local JAR dependencies fail to copy

When running copyAppDependencies from the Gradle plugin, I'm bumping into an issue where the local jar dependencies I've defined are not being copied to the fxlauncher folder, and have no entry in app.xml

So in my build.gradle I'll use either 'fileTree' or 'files' to compile my local dependencies (I've tried testing both)

dependencies {
        compile fileTree(dir: 'lib', include: '*.jar')
        compile files('lib/example1.jar', 'lib/example2.jar')
}

I'm fairly new to Gradle so not sure if I'm missing something obvious.

Cheers.

How to change the icon?

I could not find anything in the fxlauncher docs about changing the icon of either the installer or the installed program. Is there a way?

adding custom files to manifest

it would be cool to be able to manually add files to the manifest that would be updated during the regular allplication start

Support optional --cache-dir program parameter and cacheDir manifest entry

The cache dir option will override the directory the downloaded artifacts are placed in. By default, artifacts are placed in the current working directory. The program parameter --cache-dir or the manifest entry cacheDir can be specified to override this.

If the cache dir parameter starts with the magical string USERLIB/ this string will be replaced with an OS specific path. Consider the following parameter value:

fxlauncher.jar --cache-dir=USERLIB/MyApp

The result will be:

OS Location
Windows ~/AppData/MyApp
Mac ~/Library/Application Support/MyApp
Linux ~/.MyApp

This feature can be helpful in several circumstances:

  • If the application is installed in a placed where the user does not have write access
  • If there is a problem with configuring the current working directory, as seen with some Mac Java Version
  • To cache commonly used library files amongst several installed apps

The program parameter will override any configured value in the manifest, and the default will still be "the current working directory".

Gradle Plugin: SCP + Windows

I'm bumping into an issue running the deployApp task in Gradle from my Windows dev box

What went wrong:
Execution failed for task ':deployApp'.
java.io.IOException: Cannot run program "scp": CreateProcess error=2, The system cannot find the file specified

I've grabbed Putty's pscp, renamed it to scp and have it on my Path. I can manually scp the files from command line, but unsure why Java can't see the binary.

Anyone had any luck with this build task in Windows?

Loading and Updating scene customization

Hello Edvin,

I'm wondering if it's possible to customize the loading and updating scenes.
This is the default loading scene:

loading

and this is the updating scene:

updating

I think right now is possible to do some customization to the "updating" scene via app.xml. Would be awesome if we can provide both custom scenes or something like that.
Again, thanks.

Update dependencies

Hi,
next idea: it would be cool if the updater would automatically update the manifest file so if we update a dependency library or other files that they could be included via a regular update and the application must not be installed completely new.

JNLP file should use the complete URL as href

Not using the complete url as href fails, when downloading JNLP file and double click it. More and more browsers are not supporting java and webstart directly.
When double clicking the jnlp file, webstart tries to find the dependencies locally, where no fxlauncher.jar exists, when loaded from webserver.

As you have the url in the settings, you could easily add them to the JNLP file, like
<jnlp ... href="**http://javafx.ninja/smartcsv/**SmartCSV.fx.jnlp">

Create common build library

As of now we only have a build system plugin for Gradle, but one is sorely needed for Maven as well. I would like to create a common core for all the functionality and have the Gradle/Maven plugins call the core functionality instead of reinventing the wheel for every build system. This would make it even easier to support Leiningen, Kobalt etc as well.

Headless mode

I thought about using your fxlauncher not just for FX stuff, but also for plain java installations. e.g. running headless as windows service.
Having a headless mode of fxlauncher could also allow such a java service update itself.

In fact, I have it already running on my machine, but it requires some additional efforts to avoid code duplications.

I thought about refactoring Launcher into

  • AbstractLauncher for common stuff
  • extending Launcher from it for the current FX behavior
  • extending a new HeadlessMainLauncher from AL. This launcher will run headless and will invoke the main method of the loaded application

Because this leads to a bigger pull request I wanted to ask if you are interested in such a thing at all - or is this out of scope of your library?

Passing application parameters

Hey there!
I've been trying to pass an application parameter into my application on several ways now but it kinda ends like I don't find the right way to do it.

I tried passing it via
jvmProperties=--myOption=myValue and
userJvmOptions=--myOption=myValue
also tried appending an paramfile via
-paramfile file

  • nothing happened...

Would you be so kind to help me out here?

thanks so much for this project by the way!!

best regards
patrick

Integration with Griffon

Hi, I'm trying to integrate Fxlauncher with Griffon. Until now, no luck. Seems there is some issues with threading. Any ideas?.
Thanks.

Parameters are not passed to the launched application

If I want parameters passed to the launched application, I can pass them to fxlauncher.Launcher but it doesn't pass them through.

I solved this by adding this line before the app.start(primaryStage); in Launcher.java:

ParametersImpl.registerParameters(app, getParameters());

I know this uses a com.sun class but I didn't see any other way to do it.

Future plans?

Curious to know if you have a plan for future enhancements for this project? Or do you consider it "done"?

There are a couple of features that come immediately to mind when I consider using this in my project:

  1. Support for updating to specific versions or downgrading to specific versions. Even in the best-run projects. there are bugs or incompatibilities that take a while to fix. Allowing my users to downgrade to a specific version until a bug could be fixed might be very valuable to them.
  2. Support multiple update channels. E.g. Allow users to switch to (or from) a beta channel to get the latest goodies or the most stable release.
  3. Delay updating and expose APIs to the target software for controlling updates. So instead of updating at startup, it would simply check for updates and then allow my software to notify the user that updates are available and ask them if/when they would like to update at the next startup.

Thanks!
Chris

javapacker not found ?

Hi,

I am using tornadofx and built a small helloworld app and I know I wish to create a native installer (I am on Linux MINT Kde), I am using gradle. So I found fxlauncher that seems to do more than I originally wanted. I tried running the generateNativeInstaller but i get the following errors

:embedApplicationManifest
:generateNativeInstaller FAILED

FAILURE: Build failed with an exception.

  • What went wrong:
    Execution failed for task ':generateNativeInstaller'.

java.io.IOException: Cannot run program "javapackager": error=2, No such file or directory

  • Try:
    Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.

BUILD FAILED

Total time: 12.873 secs
error=2, No such file or directory
2:53:53 AM: External task execution finished 'generateNativeInstaller'.

I did the following to my gradle file, placing it here for transparency.

buildscript {
    ext.kotlin_version = '1.0.4'

    repositories {
        mavenLocal()
        mavenCentral()
    }
    dependencies {
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
        classpath 'no.tornado:fxlauncher-gradle-plugin:1.0.14'
    }
}

apply plugin: "kotlin"
apply plugin: 'no.tornado.fxlauncher'


fxlauncher {
    applicationVendor 'My Company'
    applicationUrl 'http://soemthing/'
    applicationMainClass 'com.example.demo.app.MyApp'
    acceptDowngrade false
    deployTarget '[email protected]:fxldemo'
}

repositories {
    mavenLocal()
    mavenCentral()
}

apply plugin: 'application'

dependencies {
    compile 'no.tornado:tornadofx:1.5.7'
    testCompile 'junit:junit:4.12'
}

jar {
    manifest {
        attributes(
                'Class-Path': configurations.compile.collect { it.getName() }.join(' '),
                'Main-Class': 'com.example.demo.app.MyApp'
        )
    }
    from configurations.compile.collect { entry -> zipTree(entry) }
}

Can anyone help, I must admit when it comes to java / gradle I wouldn't consider myself a complete expert :-) Although I love Kotlin!

Enhancement: native installers should log update/startup errors to a log file

When running from a native installer, the end-user won't see anything logged to stdout. Requiring users to run the program from the command-line to capture the output is not a good end-user experience. It would be great if the launcher would redirect all of its output to a log file that can be easily located by the end-user...perhaps even showing giving them the opportunity to view it or save it to the desktop when an error occurs.

README.md has a typo

FYI, in the README.md file, section "A slimmer alternative", you have a typo, "wether", should be "whether/either".

Missing cacheDir leads into NPE

Starting the application with webstart without cacheDir information leads into the follwing NPE (you could test it with http://javafx.ninja/smartcsv/SmartCSV.fx.html

java.lang.NullPointerException
at fxlauncher.Launcher.createApplication(Launcher.java:165)
at fxlauncher.Launcher.lambda$start$0(Launcher.java:70)

How could I set the parameter? As argument in the jnlp file has not worked out.

Thanks for your help!
Kindest regards,
Andi

Gradle multi module projects

I couldn't really figure out how to use fxlauncher in a Gradle project containing multiple modules. I added the needed gradle code to the build.gradle file of the parent project but it doesn't copy the build files from the modules to the output directory. Could you help me out please?

P.S.: I am relatively new to Java and coding in general. Sorry if this question is stupid.

Native launcher on OS X => jars downloaded into ${user.home}, not into bundle

I'm mac user and I'm testing you great FXLauncher. I see that FXLauncher downloads jar files into user.home variable and It would be great to set the target folder. In OS X it would be download into the .app folder in fact, because if you drop the icon app to trash, you don't uninstall all the app because all the jars it's outside. If you want to get the dir to save the jars on OS X the code is:

            final URL myURL = Client.class.getProtectionDomain().getCodeSource().getLocation();
    java.net.URI myURI = null;
    try {
        myURI = myURL.toURI();
                    final String dir = java.nio.file.Paths.get(myURI).toFile().toString();
    } catch (final URISyntaxException e){
    }

Thank you and keep the great job

Download the right version of JRE

Quite often the end user doesn't have JRE supported by the app, e.g. user has 1.6 and we need a 1.8.
Therefore it would be handy if FXLauncher could download packaged JRE along with the application jars. This would make user experience even more seamless without asking users to update their Java or investigating why application uses the wrong version of JRE (if multiple are installed) or why JRE installation is broken. Unfortunately this happens quite often.

fxlauncher.jar not found

Hi seems I am missing some thing - getting following error
[INFO] --- exec-maven-plugin:1.4.0:exec (embed-manifest-in-launcher) @ Turn ---
java.io.FileNotFoundException: fxlauncher.jar (The system cannot find the file specified)
at java.io.FileInputStream.open0(Native Method)
at java.io.FileInputStream.open(FileInputStream.java:195)
at java.io.FileInputStream.(FileInputStream.java:138)
at sun.tools.jar.Main.run(Main.java:261)
at sun.tools.jar.Main.main(Main.java:1288)
[INFO] ------------------------------------------------------------------------
help requested..

Fails to launch without an internet connection

Steps to reproduce:

  1. Download a launcher
  2. Launch for the first time - the app is downloaded and launched
  3. Exit the app, turn your Internet off
  4. Try to launch the app again - exception, part of the content is not loaded

I used the example app https://github.com/edvin/fxlauncher#try-a-native-installer

Stack trace:
java.net.UnknownHostException: fxsamples.tornado.no
at java.net.InetAddress.getAllByName0(InetAddress.java:1280)
at java.net.InetAddress.getAllByName(InetAddress.java:1192)
at java.net.InetAddress.getAllByName(InetAddress.java:1126)
at org.apache.http.impl.conn.SystemDefaultDnsResolver.resolve(SystemDefaultDnsResolver.java:45)
at org.apache.http.impl.conn.DefaultHttpClientConnectionOperator.connect(DefaultHttpClientConnectionOperator.java:111)
at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.connect(PoolingHttpClientConnectionManager.java:353)
at org.apache.http.impl.execchain.MainClientExec.establishRoute(MainClientExec.java:380)
at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:236)
at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:184)
at org.apache.http.impl.execchain.RetryExec.execute(RetryExec.java:88)
at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110)
at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:184)
at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:71)
at tornadofx.Rest.execute(Rest.kt:142)
at tornadofx.Rest.execute$default(Rest.kt:128)
at tornadofx.Rest.get(Rest.kt:96)
at tornadofx.Rest.get$default(Rest.kt:96)
at controller.ContactController.listContacts(ContactController.kt:13)
at view.ContactList$1.invoke(ContactList.kt:23)
at view.ContactList$1.invoke(ContactList.kt:13)
at tornadofx.Component$background$1.call(Component.kt:53)
at javafx.concurrent.Task$TaskCallable.call(Task.java:1423)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.lang.Thread.run(Thread.java:745)

Manifest and .war dependency

I think that this test

if (!Files.isDirectory(file) && file.toString().endsWith(".jar") && !file.getFileName().toString().startsWith("fxlauncher"))

into CreateManifest class is not correct if you have any war as dependency.

In my case, I have a app that runs a embedded jetty with a war (that it's a dependency of the project).

What do you think? Could you create a dependencyExtension param and by default it's only ".jar"?

I'm updating all my projects to use this amazing lib and removing from jnlp, so thank you so much :)

FxlDemo-2.0.exe error

when I run the FxlDemo-2.0.exe ,after it finished. I got this error :
image .so I need put app.xml in some folder?

Bug: Basic auth is not working for domain subdirectories?

Basic auth is not working properly for subdirectories, i.e. if the files are stored in: host.de/subdirectory

Maven App URL configuration;

<app.url>http://user:[email protected]/subdirectory</app.url>

=> With this configuration, an exception occurs: FileNotFoundException: http://user:[email protected]/someJar.jar

It seems that the subdirectory is ignored.

I´ve found out that there is a workaround by extending the maven <app.url> configuration

<app.url>http://user:[email protected]/subdirectory/**any_string_workaround**</app.url>

=> Now the path host.de/subdirectory seems to be resolved correctly

human-readable timestamp

Alter manifest.ts to use a more human-readable timestamp.
Alt 1: a la Maven: Integer: yyyymmddhhmmss
Alt 2: java.sql.Timestamp (ISO-format): String: "yyyy-mm-dd hh:mm:ss"
Question: Is millisecond resolution needed/useful?

Classloader woes

Hi!

I had hard times to get fxlauncher working with my app which uses custom URLStreamHandler which could not be loaded by my app if started using fxlauncher.

It came down to the java.net.URL class which uses Class.forName() which uses the classloader of the callee (which is the URL class). But this classloader is not aware of the URLClassLoader created by fxlauncher and thus is not able to instantiate my URLStreamHandler.

I was able to workaround that by setting my own URLStreamHandlerFactory. But, well, it looks a bit of a hack (see below), because I have to handle a recursive case where (after setting up the URLStreamHandlerFactory) java has to load all the handlers again, even the builtin for file/jar/http/etc ...
And then, who knows which other java classes are using Class.forName .

Long story short, I think we need to create a system class loader and set that up using the startup parameter (-Djava.system.class.loader=myClassLoader) which allows us to add the additional classpath entries directly to this classloader instead of creating a new one.

Basically a URLClassLoader where we unprotect addURL()

What do you think?

`

   // old solution: System.setProperty("java.protocol.handler.pkgs", "my.base.class");

    URL.setURLStreamHandlerFactory(protocol ->
    {
        if (recursiveUrlHandler)
        {
            return null;
        }
        try
        {
            recursiveUrlHandler = true;
            URLStreamHandler handler = (URLStreamHandler) Utils.forName("my.base.class." + protocol + ".Handler").newInstance();
            return handler;
        }
        catch (Throwable e)
        {
            return null;
        }
        finally
        {
            recursiveUrlHandler = false;
        }
    });

`

USERLIB and Windows

Hi!

I wonder if the Windows path construction in FXManifest for the USERLIB is fully correct.
Shouldn't there be a Local/LocalLow or Roaming in the path?
I'd prefer "Local" for now.

`
case win:

                replacement = Paths.get(System.getProperty("user.home"))
                        .resolve("AppData")
                        .resolve("Local")
                        .resolve(cacheDir.substring(8))
                        .toString();
                break;

`

What do you think?

[Question] Notification

Is it somehow possible to notify the user that a new update is available? Like a small Alert in the main application?

Synchronisation problem

Hi Edvin

Thanks for your work

I have a little question

When i try to run :

java -jar target/app/fxlauncher.jar
janv. 28, 2017 5:12:19 PM fxlauncher.Launcher lambda$start$0
INFOS: Using cache dir ${app.cacheDir}
janv. 28, 2017 5:12:19 PM fxlauncher.Launcher lambda$start$0
AVERTISSEMENT: Error during File Synchronization phase
java.io.FileNotFoundException: http://www.myfowo.com/rondoclient-1.0.0.jar
at sun.net.www.protocol.http.HttpURLConnection.getInputStream0(HttpURLCo
nnection.java:1872)
at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLCon
nection.java:1474)
at fxlauncher.Launcher.syncFiles(Launcher.java:159)
at fxlauncher.Launcher.lambda$start$0(Launcher.java:78)
at java.lang.Thread.run(Thread.java:745)

I should miss something but can't find the fix

Could you help me ?

Thanks

fxlauncher does not seem to download all jar

I can give you access to the code if you want, as this code is not public (yet)

ron@frankenstein ~/src/keepassjava $ java -jar target/app/fxlauncher.jar 
Sep 17, 2016 10:24:06 AM fxlauncher.Launcher lambda$start$0
INFO: Using cache dir /tmp
Sep 17, 2016 10:24:06 AM fxlauncher.Launcher lambda$start$0
WARNING: Error during File Synchronization phase
java.io.FileNotFoundException: http://ronsmits.org/ron/slf4j-simple.jar
        at sun.net.www.protocol.http.HttpURLConnection.getInputStream0(HttpURLConnection.java:1836)
        at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1441)
        at java.net.URL.openStream(URL.java:1045)
        at fxlauncher.Launcher.syncFiles(Launcher.java:146)
        at fxlauncher.Launcher.lambda$start$0(Launcher.java:64)
        at java.lang.Thread.run(Thread.java:745)

Sep 17, 2016 10:24:06 AM fxlauncher.Launcher reportError
WARNING: Error during Create Application phase
java.lang.ClassNotFoundException: org.ronsmits.keepassswing.KeepassJava
        at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
        at fxlauncher.Launcher.createApplication(Launcher.java:171)
        at fxlauncher.Launcher.lambda$start$0(Launcher.java:70)
        at java.lang.Thread.run(Thread.java:745)

ron@frankenstein ~/src/keepassjava $ 

Fat JAR support with Maven

I was wondering if it's possible to adjust the plugin so it just updates the main fat jar (made with Shade plugin) instead of copying every possible dependency.

Failure modes and logging

I'm having trouble with the update step when I startup my app. I didn't find any debugging information on the readme....so not sure how to diagnose the problem. Note that the very first time I ran the installer, it updated fine. Since then, the results have not been as good.

Problem 1: My app has 87 jars (most are 3rd-party). When it gets to one of MY jars, it stops updating and tries to run the app. This results in a ClassNotFound error instead of reporting the real problem (which is that the download failed for some reason). I don't understand what is different about my jars.

Problem 2: When I copy MY jars in, it hangs on some of the other 3rd party jars, but in this case, the update hangs. The progress bar goes back and forth (instead of filling in). If I manually copy in the remaining jars from the fxlauncher, then the app starts.

I can't tell if this is some odd network problem, a checksum problem, or something else. Is there a way to turn on some verbose debugging?

Also, how is the checksum in the manifest computed? I tried computing using md5sum and cksum - neither matches the value I see in the manifest.

Thanks!
Chris

Bug: show better error messages when update step or startup fails

I ran into two separate problems where the error shown to the end-user is unfriendly and/or inaccurate.

  1. download permissions prevented download of the manifest
  2. download permissions prevented download of a jar

In both cases, the reported error was a ClassNotFoundException. The download failure was apparently ignored and fxlauncher attempted to run the program even though it had been unable to download the resources.

The desired outcome would be to tell the end-user that the update had failed (unable to get manifest or unable to get required resources) and perhaps mention the HTTP status 403 code when that is the culprit. A stacktrace is, IMO, unfriendly to the end user. Being unable to reach the server at all, as one might get when running offline, should be acceptable if all the resources are present to run the app.

Even when the update succeeds, if the target app terminates abnormally, a stacktrace should not be shown to the end user - they should simply be told that there was a failure and directed to the diagnostic log...and possibly an application-specific URL for getting help from the app developer.

Update if client is newer than server-version -> Exception

Hi,
first i think this is a realy cool project because it is easy to use and seems extremly stable.
Maybe this could also be a part of #16, but we found a problem, our customer wanted to have complete installation-bundles to test the application before our update-server was present, we also implemented some new features, and shipped them with the installer and not on the server, but if the new version now checks for an update and client version is newer than the version on the update server if does something wrong, throws errors and afterwards it is not possible to start the application online or offline. would be realy cool, also a possibility for downgrade and updates for the jre would be very good.

regards

børge

Running demo installer results in a stacktrace

Downloaded and ran the demo installer on Windows 10. Result is:

java.lang.NullPointerException
at no.tornado.FxlDemo.start(FxlDemo.java:31)
at fxlauncher.Launcher.lambda$launchAppFromManifest$2(Launcher.java:104)
at com.sun.javafx.application.PlatformImpl.lambda$null$173(PlatformImpl.java:295)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.application.PlatformImpl.lambda$runLater$174(PlatformImpl.java:294)
at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.lambda$null$148(WinApplication.java:191)
at java.lang.Thread.run(Thread.java:745)

Downloading files to current directory

I'm having issues configuring the fxlauncher to download files into the directory where launcher is started from. I tried messing with the cache-dir setting, and while that worked great, having no cache-dir argument results into downloading everything to /home/val. As I understand it from the documentation, not definining cache-dir should download every file into the current directory, but it does not appear to do that.

Edit: I should specify that I'm using Maven for this project.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.