views:

568

answers:

7

Ive been reading Liang's Introduction to Java Programming for a couple of weeks, and that question came up when the author said "There is no need for developers to create, and for users to install, major new software versions.".

How does software update work? For example, patches for games, new version of products, and that kind of things. In the book, there's an example that, as long as you keep an interface of a class the same, you dont need to do any changes in any of the classes that are dependent on the one you changed. That's fine, but still a little abstract (for example, how do I create an update patch with only that class?).

Im also interested in books on the subject.

Thank you.

+2  A: 

Have a look at the book

Practical API Design - Confessions of a Java Framework Architect (Jaroslav Tulach, Apress, 2008)

I think it covers most of the aspects you are asking about.

For the topic on shipping new software versions or updates, have a look at the technology Java Web Start for example.

Shipping an update to a web application could be considered implicit in the face of the users as the changes made on a centralized server1 are delivered by the web browser itself.

1 or a set of servers

kd304
A: 

Is that not referring to the Single Responsibility Principle. http://en.wikipedia.org/wiki/Single_responsibility_principle

In practice it doesn't seem to work, unless you have something truly enormous like Windows which you can update pieces of or a game which uses lots of textures which don't need to be changed.

Echilon
A: 

Consider a game that has been architected to have a number of independent modules, each interacting with each other via interfaces only. The initial deployment of such a game could consist of 15 or 20 individual jar files.

Applying updates would then be a matter of connecting to a server, querying for the latest version of each jar file, comparing against the jar file that you already have, and downloading only the changed files.

A poor-man's version of this would be if you were working on a project that has 15 jars, and you make a critical bug fix to one of the jars. You wouldn't have to copy all 15 jars to your customer's system - you jut copy the one that changed.

jnlp (of which Webstart and the new applet implementation are examples) does this using a well defined xml file to define which versions of each library are required. In this case, initial deployment of the application can be performed by reading the xml (served by a web server), and dynamically downloading required jar files to a local cache during a bootstrap operation. There actually is no initial installation at all.

It is probably important to mention that this benefit, while certainly valid and real, is pretty minor compared to the maintainability and ease of coding that comes from reducing dependencies between modules, and using well defined interfaces.

Kevin Day
A: 

The simplest way to update a single class will be to stop the application, override the old class with the new one and then restart. Shutting down the application may not be appropriate for some cases. To overcome this you would need to have a framework/container of some kind and develop your own class loaders that make possible updating a class without restart. This is what Java Application Servers are doing.

For the desktop/thick clients there are available some commercial and free solutions for software updates. See this article for a comparison. It is rather old, new solutions are bound to be available.

kgiannakakis
+1  A: 

I think the concept you're trying to understand is using an interface as a type. In a java program, a variable can be declared to have the type of some defined interface. Classes that implement that interface can then be instantiated for variables of the interface type. However, only methods declared on the interface can be used. At compile time, the interface is used for type checking. At runtime however, the bytecode that actually does the work comes from the interface implementor. An example:

public interface foo {
    public void bar();
}

public class A implements foo {
    public void bar() {
     // some code
    }
}

public class Example {
    public static void main(String[] args) {
     foo aFoo = new A();
     aFoo.bar();
    }
}

In the class Example, a variable named aFoo is declared to be of type foo, the interface. A, which implements the foo interface, will contain the code to do the work of method bar(). In the class Example, the variable aFoo gets an instance of the class A, so whatever code is in the bar() method of A will be executed when aFoo.bar() is called even though aFoo is declared to be of type foo.

So, we've established that all the work is done in class A. The two classes and one interface above can each be defined in their own file. All three resulting .class files can be packaged into a jar and shipped to customers as version 1.0 of the program. Sometime later, a bug might be discovered in the implementation of bar() in class A. Once a fix is developed, assuming the changes are all contained inside the bar() method, just the .class file for A needs to be shipped to customers. The updated A.class can be inserted into the program's .jar file (.jar files are just .zip files after all) overwriting the previous, broken version of A.class. When the program is restarted the JVM will load the new implementation of A.bar() and the class Example will get the new behavior.

As with almost everything, more complicated programs can get, well, more complicated. But the principles are the same.

dcoke23
A: 

In addition to updating individual JAR files (or, in other software environments, shared library files or DLLs), there are binary patch tools that can be used in some cases to transmit a set of changes against the base file. A patch program will take this difference file and merge it with the base file to produce the new, changed file. This only works if the original file is not modified on the installed system, but can work in some cases to incrementally patch particular program components.

Michael E
A: 

I'd actually marginally studied this at university, and upon research specifically for it I actually found it quite interesting. One thing to do to specify updates specifically is recorded versioning where for each version that you release you specify what has updated. Say for example the difference between version 1.0.1 and 1.0.2 is that mylib.dll has been updated. Now say that the difference between 1.0.2 and 1.0.4 is that myotherlib.dll has changed then if someone updates their software to the latest version (1.0.4) and they currently have 1.0.1 then both dll's are included in the update.

I'm not sure if this is practiced though or if more intelligient methods are used. It depends on the software maker really, quite a few different methods are used I assume as some developers encrypt application files and bundle them into a custom format.

Kezzer