Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
# Created by https://www.gitignore.io/api/maven
# Edit at https://www.gitignore.io/?templates=maven

.idea/
### Maven ###
target/
pom.xml.tag
Expand Down Expand Up @@ -90,3 +91,6 @@ local.properties
.sts4-cache/

# End of https://www.gitignore.io/api/eclipse

### VS Code ###
.history/
63 changes: 45 additions & 18 deletions pom.xml
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>nf.fr.k49</groupId>
<artifactId>shielddb-parent</artifactId>
<version>0.1.4-SNAPSHOT</version>
<packaging>pom</packaging>

<name>shieldb</name>
<description>ShieldDB is a simple embedded database with JSON file backend with optional in-memory read cache.</description>
<description>ShieldDB is a simple embedded database with JSON file backend with optional in-memory read cache.</description>
<url>https://github.com/kuroidoruido/ShieldDB</url>

<licenses>
<license>
<name>MIT License</name>
Expand Down Expand Up @@ -37,13 +36,17 @@
<junit-jupiter-api.version>5.7.0</junit-jupiter-api.version>
<hamcrest.version>2.2</hamcrest.version>
<mockito.version>3.5.13</mockito.version>
<guava.version>30.1.1-jre</guava.version>
<commons-lang.version>3.12.0</commons-lang.version>
</properties>

<modules>
<module>shielddb-core</module>
<module>shielddb-demo-app</module>
<module>shielddb-gson-backend</module>
</modules>
<dependencyManagement>

<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.junit.jupiter</groupId>
Expand All @@ -67,8 +70,31 @@
<version>${mockito.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>${guava.version}</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
<version>${commons-lang.version}</version>
</dependency>
</dependencies>
</dependencyManagement>

<!-- Commons utils dependencies -->
<dependencies>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
</dependency>
</dependencies>

<distributionManagement>
<snapshotRepository>
<id>ossrh</id>
Expand All @@ -79,6 +105,7 @@
<url>https://oss.sonatype.org/service/local/staging/deploy/maven2/</url>
</repository>
</distributionManagement>

<build>
<plugins>
<plugin>
Expand All @@ -92,10 +119,10 @@
<version>3.2.1</version>
<executions>
<execution>
<id>attach-sources</id>
<goals>
<goal>jar-no-fork</goal>
</goals>
<id>attach-sources</id>
<goals>
<goal>jar-no-fork</goal>
</goals>
</execution>
</executions>
</plugin>
Expand All @@ -105,10 +132,10 @@
<version>3.2.0</version>
<executions>
<execution>
<id>attach-javadocs</id>
<goals>
<goal>jar</goal>
</goals>
<id>attach-javadocs</id>
<goals>
<goal>jar</goal>
</goals>
</execution>
</executions>
</plugin>
Expand Down Expand Up @@ -141,11 +168,11 @@
<autoReleaseAfterClose>true</autoReleaseAfterClose>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>3.0.0-M5</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>3.0.0-M5</version>
</plugin>
</plugins>
</build>
</project>
4 changes: 1 addition & 3 deletions shielddb-core/pom.xml
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>nf.fr.k49</groupId>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package nf.fr.k49.shielddb.core.storage;

import java.io.File;
import java.io.IOException;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
Expand All @@ -8,13 +9,21 @@
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.stream.Collectors;
import java.util.Objects;
import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;

import static com.google.common.base.Preconditions.checkArgument;
import static org.apache.commons.lang3.StringUtils.isNotBlank;

public class FileStorage implements ShieldDBStorage {

private Path parentDir;
private Path path;
private Path backupPath;
private Charset charset;
private final ReadWriteLock readWriteLock;

private final Path parentDir;
private final Path path;
private final Path backupPath;
private final Charset charset;

/**
* Same as #FileStorage(String, Charset) with a default Charset set to
Expand All @@ -32,29 +41,43 @@ public FileStorage(final String path) throws IOException {
}

public FileStorage(final String path, final Charset charset) throws IOException {
checkArgument(isNotBlank(path), "Path cannot be null or empty");
checkArgument(Objects.nonNull(charset), "Charset cannot be null");
this.path = Paths.get(path).toAbsolutePath();
this.parentDir = this.path.getParent();
this.backupPath = Paths.get(path + ".backup").toAbsolutePath();
this.charset = charset;
this.readWriteLock = new ReentrantReadWriteLock();

if (path.contains("/") || path.contains("\\")) {
if (path.contains(File.separator)) {
this.parentDir.toFile().mkdirs();
}
}

@Override
public synchronized String read() throws IOException {
return Files.readAllLines(path, charset).stream().collect(Collectors.joining(""));
public String read() throws IOException {
try {
readWriteLock.readLock().lock();
return Files.readAllLines(path, charset).stream().collect(Collectors.joining(""));
} finally {
readWriteLock.readLock().unlock();
}
}

@Override
public synchronized void write(String json) throws IOException {
final Path tmp = Files.createTempFile(this.parentDir, "ShieldDB_", ".temp");
Files.write(tmp, json.getBytes());
Files.move(path, backupPath, StandardCopyOption.ATOMIC_MOVE);
Files.move(tmp, path, StandardCopyOption.ATOMIC_MOVE);
Files.deleteIfExists(tmp);
Files.deleteIfExists(backupPath);
public void write(String json) throws IOException {
try {
readWriteLock.writeLock().lock();
checkArgument(isNotBlank(json), "JSON cannot be null or empty");
final Path tmp = Files.createTempFile(this.parentDir, "ShieldDB_", ".temp");
Files.write(tmp, json.getBytes());
Files.move(path, backupPath, StandardCopyOption.ATOMIC_MOVE);
Files.move(tmp, path, StandardCopyOption.ATOMIC_MOVE);
Files.deleteIfExists(tmp);
Files.deleteIfExists(backupPath);
} finally {
readWriteLock.writeLock().unlock();
}
}

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,20 +1,17 @@
package nf.fr.k49.shielddb.core.storage;

import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
import static org.junit.jupiter.api.Assertions.fail;
import static org.hamcrest.MatcherAssert.*;
import static org.hamcrest.CoreMatchers.*;

import java.io.File;
import java.io.IOException;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.nio.file.FileVisitOption;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.UUID;
import java.util.stream.Collector;
import java.util.stream.Collectors;

import org.junit.jupiter.api.AfterAll;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package nf.fr.k49.shielddb.core.storage;

import org.junit.jupiter.api.MethodOrderer;
import org.junit.jupiter.api.TestMethodOrder;

@TestMethodOrder(MethodOrderer.OrderAnnotation.class)
class FileStorageThreadTest {

}
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@

import com.google.gson.Gson;

import org.apache.commons.lang3.StringUtils;

import nf.fr.k49.shielddb.core.json.ShieldDBJsonMapper;

public class ShieldDBGson<T> implements ShieldDBJsonMapper<T> {
Expand All @@ -28,7 +30,7 @@ public ShieldDBGson(final Gson gson, final Type collectionType) {

@Override
public List<T> toList(String json) {
if (json == null || json.length() == 0) {
if (StringUtils.isBlank(json)) {
return new ArrayList<>();
}
return new ArrayList<>(gson.fromJson(json, collectionType));
Expand Down