Skip to content

Instantly share code, notes, and snippets.

@YujiSoftware
Last active November 3, 2024 12:55
Show Gist options
  • Save YujiSoftware/0a3adc5030918469b13894b33c7344e7 to your computer and use it in GitHub Desktop.
Save YujiSoftware/0a3adc5030918469b13894b33c7344e7 to your computer and use it in GitHub Desktop.
WebKit由来のソースコード行数を調べる
package yuji.software;
import java.io.*;
import java.nio.file.Files;
import java.nio.file.Path;
import java.time.OffsetDateTime;
import java.time.ZoneOffset;
import java.util.Optional;
import java.util.function.Predicate;
import java.util.stream.Stream;
public class Main {
private static final OffsetDateTime EPOCH =
OffsetDateTime.of(2013, 4, 3, 0, 0, 0, 0, ZoneOffset.UTC);
private static final long EPOCH_TIME =
EPOCH.toInstant().toEpochMilli() / 1000;
static final class Result {
private long files;
private long lines;
private long webkit;
public Result add(Result r) {
this.files += r.files;
this.lines += r.lines;
this.webkit += r.webkit;
return this;
}
@Override
public String toString() {
return "files=" + files + ", lines=" + lines + ", webkit=" + webkit;
}
}
private final File root;
public Main(Path root) {
this.root = root.toFile();
}
public void run() throws IOException {
try (Stream<Path> stream = Files.walk(root.toPath())) {
Optional<Result> result = stream
.filter(Files::isRegularFile)
.filter(p -> !p.toString().toUpperCase().contains("TEST"))
.filter(p -> !p.toString().contains("/.git/"))
.filter(Predicate.not(this::isBinary))
//.limit(2)
.map(this::parse)
.parallel()
.reduce(Result::add);
System.out.println(result);
}
}
private boolean isBinary(Path path) {
try (InputStream stream = Files.newInputStream(path)) {
int b;
do {
b = stream.read();
if (b == 0x0) {
return true;
}
} while (b != -1);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
return false;
}
private Result parse(Path path) {
try {
Process process =
new ProcessBuilder("git", "blame", "--follow", "-w", "--line-porcelain", path.toString())
.directory(root)
.start();
Result r = new Result();
r.files = 1;
try (BufferedReader reader = new BufferedReader(process.inputReader())) {
reader.lines()
.filter(line -> line.startsWith("author-time "))
.mapToLong(line -> Long.parseLong(line.split(" ")[1]))
.forEach(time -> {
if (time <= EPOCH_TIME) {
r.webkit++;
}
r.lines++;
});
}
process.waitFor();
System.err.println(path + " (" + r + ")");
return r;
} catch (Exception e) {
throw new RuntimeException(e);
}
}
public static void main(String[] args) throws IOException {
Path root = Path.of(args[0]);
new Main(root).run();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment