KeePass is a free open source password manager, which helps you to manage your passwords in a secure way. You can put all your passwords in one database, which is locked with one master key or a key file. This application features:
- KeePass supports the Advanced Encryption Standard (AES, Rijndael) and the Twofish algorithm to encrypt its password databases. Both of these ciphers are regarded as being very secure. AES e.g. became effective as a U.S. Federal government standard and is approved by the National Security Agency (NSA) for top secret information.
- The complete database is encrypted, not only the password fields. So, your user names, notes, etc. are encrypted, too.
- SHA-256 is used to hash the master key components. SHA-256 is a 256-bit cryptographically secure one-way hash function. No attacks are known yet against SHA-256. The output is transformed using a key derivation function.
- Protection against dictionary and guessing attacks: by transforming the master key component hash using a key derivation function (AES-KDF, Argon2, ...), dictionary and guessing attacks can be made harder.
- Process memory protection: your passwords are encrypted while KeePass is running, so even when the operating system dumps the KeePass process to disk, your passwords aren't revealed.
- [2.x] Protected in-memory streams: when loading the inner XML format, passwords are encrypted using a session key.
- Security-enhanced password edit controls: KeePass is the first password manager that features security-enhanced password edit controls. None of the available password edit control spies work against these controls. The passwords entered in those controls aren't even visible in the process memory of KeePass.
- The master key dialog can be shown on a secure desktop, on which almost no keylogger works. Auto-Type can be protected against keyloggers, too.
As the application uses a public logic, there are libraries to manipulate this kind of file with different programming languages, and Java is not the exception. In this article, we will explain you how to manipulate KeePass databases with Java, either to create your own similar application or just to extract the information from kdbx files.
1. Install Open KeePass library
In order to manipulate KeePass databases, you will need to install the openkeepass library. openkeepass is a java library for reading and writing KeePass databases. It is an intuitive java library that supports KeePass 2.x database files. The library offers support so far for:
- Reading and writing support for KeePass 2.x
- Password or Keyfile credentials: openkeepass can open password protected databases as well as keyfile protected databases.
- Android Support: Will run on Android devices.
- Easy to learn API: openkeepass has a simple API with convenient methods that makes it easy to read data from a KeePass database.
- Very lean: openkeepass tries to keep the necessary dependencies to an absolute minimum.
- Backward compatible until Java 6
You can either download the jar file of the package from the maven repository and include it manually in your project or if your project is maven based, you may edit the pom.xml
file and add the dependency:
<!-- https://mvnrepository.com/artifact/de.slackspace/openkeepass -->
<dependency>
<groupId>de.slackspace</groupId>
<artifactId>openkeepass</artifactId>
<version>0.8.1</version>
</dependency>
For more information about this project, please visit the official repository at Github here.
2. Extracting information
As everything in Our Code World, you will learn by doing, so we will explain you how to handle the most basic needs when you try to work with these files:
Printing all credentials
If you just obtained a KeePass database from someone and you only need to obtain the information without worrying about categorization, you can easily print all the stored credentials in the file with the following logic:
package com.ourcodeworld.mavensandbox;
// Import required class
import de.slackspace.openkeepass.KeePassDatabase;
import de.slackspace.openkeepass.domain.Entry;
import de.slackspace.openkeepass.domain.KeePassFile;
import java.util.List;
public class Index {
public static void main(String[] args){
// 1. Open a KeePass database file through a plain text password
KeePassFile database = KeePassDatabase
.getInstance("C:\\Users\\sdkca\\Documents\\Database.kdbx")
.openDatabase("12345");
// 2. Retrieve all entries
List<Entry> entries = database.getEntries();
// 3. Print every entry
for (Entry entry : entries) {
System.out.println(" * Credential: " + entry.getTitle());
System.out.println(" Username: " + entry.getUsername());
System.out.println(" Password: " + entry.getPassword());
}
}
}
This logic will generate the following output in the terminal:
* Credential: Sample Entry
Username: User Name
Password: Password
* Credential: Sample Entry #2
Username: Michael321
Password: 12345
* Credential: Windows User
Username: [email protected]
Password: 123456
* Credential: Wi-Fi
Username: bathouse
Password: 654321
* Credential: Contact Email
Username: [email protected]
Password: 123456
* Credential: Info Email
Username: [email protected]
Password: 123456789
* Credential: Bank Of America
Username: ourcodeworld
Password: 123456
Printing information in a structured way (By Groups)
As a regular user of the Keepass application, i love to categorize the credentials that i store on my file using groups and subgroups. For example, separating the credentials from my personal life with job related accounts:
You can extract the information in this way as well iterating as first by groups and then obtaining the entries inside the group:
package com.ourcodeworld.mavensandbox;
// Import required class
import de.slackspace.openkeepass.KeePassDatabase;
import de.slackspace.openkeepass.domain.Entry;
import de.slackspace.openkeepass.domain.Group;
import de.slackspace.openkeepass.domain.KeePassFile;
import java.util.List;
public class Index {
public static void main(String[] args){
// 1. Open a KeePass database file through a plain text password
KeePassFile database = KeePassDatabase
.getInstance("C:\\Users\\sdkca\\Documents\\Database.kdbx")
.openDatabase("12345");
// 2. Obtain the top groups in the database
List<Group> keePassGroups = database.getTopGroups();
// 3. Iterate over theme
for (Group group : keePassGroups) {
// 4. Print the name of the Group
System.out.println(" - " + group.getName());
// 5. List credentials inside this group
List<Entry> groupEntries = group.getEntries();
// 6. Print every credential inside the group
for (Entry entry : groupEntries) {
System.out.println(" * Credential: " + entry.getTitle());
System.out.println(" Username: " + entry.getUsername());
System.out.println(" Password: " + entry.getPassword());
}
}
}
}
This code will generate the following output in the terminal:
- Windows
* Credential: Windows User
Username: [email protected]
Password: 123456
- Network
* Credential: Wi-Fi
Username: bathouse
Password: 654321
- eMail
* Credential: Contact Email
Username: [email protected]
Password: 123456
* Credential: Info Email
Username: [email protected]
Password: 123456789
- Homebanking
* Credential: Bank Of America
Username: ourcodeworld
Password: 123456
- Recycle Bin
Obtaining a single credential by its title
As there's no indexation through ID's or something numerical, the only way to obtain a single credential from the database is through it's title, for example:
package com.ourcodeworld.mavensandbox;
// Import required class
import de.slackspace.openkeepass.KeePassDatabase;
import de.slackspace.openkeepass.domain.Entry;
import de.slackspace.openkeepass.domain.KeePassFile;
import java.util.List;
public class Index {
public static void main(String[] args){
// 1. Open a KeePass database file through a plain text password
KeePassFile database = KeePassDatabase
.getInstance("C:\\Users\\sdkca\\Documents\\Database.kdbx")
.openDatabase("12345");
// 2. Find single credential by title
Entry sampleEntry = database.getEntryByTitle("Sample Entry");
System.out.println("Title: " + sampleEntry.getTitle() + " Password: " + sampleEntry.getPassword());
}
}
This will print in the terminal:
Title: Sample Entry Password: Password
However, what if you have more than a single credential that has the same name or contains the same string? Then you will need to obtain the entries that contain the specific text and iterate over the result to know which credential match with the search:
package com.ourcodeworld.mavensandbox;
// Import required class
import de.slackspace.openkeepass.KeePassDatabase;
import de.slackspace.openkeepass.domain.Entry;
import de.slackspace.openkeepass.domain.KeePassFile;
import java.util.List;
public class Index {
public static void main(String[] args){
// 1. Open a KeePass database file through a plain text password
KeePassFile database = KeePassDatabase
.getInstance("C:\\Users\\sdkca\\Documents\\Database.kdbx")
.openDatabase("12345");
// 2. Search for all entries that contain 'Sample' in title
List<Entry> entriesByTitle = database.getEntriesByTitle("Sample", false);
for (Entry entry : entriesByTitle) {
System.out.println("Title: " + entry.getTitle() + " Password: " + entry.getPassword());
}
}
}
This will print instead:
Title: Sample Entry Password: Password
Title: Sample Entry #2 Password: 12345
Happy coding !