initial commit
This commit is contained in:
commit
1a324bd91d
25 changed files with 7270 additions and 0 deletions
3
.cargo/config.toml
Normal file
3
.cargo/config.toml
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
[registries.crates-io]
|
||||||
|
protocol = "sparse"
|
||||||
|
|
1
.envrc
Normal file
1
.envrc
Normal file
|
@ -0,0 +1 @@
|
||||||
|
use flake
|
4
.gitignore
vendored
Normal file
4
.gitignore
vendored
Normal file
|
@ -0,0 +1,4 @@
|
||||||
|
/target
|
||||||
|
.direnv
|
||||||
|
|
||||||
|
node_modules
|
3148
Cargo.lock
generated
Normal file
3148
Cargo.lock
generated
Normal file
File diff suppressed because it is too large
Load diff
7
Cargo.toml
Normal file
7
Cargo.toml
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
[workspace]
|
||||||
|
resolver = "2"
|
||||||
|
|
||||||
|
members = [
|
||||||
|
"queryer",
|
||||||
|
"parasite-messenger",
|
||||||
|
]
|
6
README.md
Normal file
6
README.md
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
Tools:
|
||||||
|
|
||||||
|
- "Queryer": Rofi-like tool that just displays an interacts with a "Searcher"
|
||||||
|
- "Searcher": Interacts with the queryer, and fetches results
|
||||||
|
- "Indexer": Provides an API for interacting with the on-disk format
|
||||||
|
- "Parasite": Web browser extension that performs indexing, talks to indexer
|
110
flake.lock
Normal file
110
flake.lock
Normal file
|
@ -0,0 +1,110 @@
|
||||||
|
{
|
||||||
|
"nodes": {
|
||||||
|
"fenix": {
|
||||||
|
"inputs": {
|
||||||
|
"nixpkgs": "nixpkgs",
|
||||||
|
"rust-analyzer-src": "rust-analyzer-src"
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681280529,
|
||||||
|
"narHash": "sha256-WDPFJQpnkFFpWW2OSiR0hfPovmpeP004DIq89q6GyLs=",
|
||||||
|
"owner": "nix-community",
|
||||||
|
"repo": "fenix",
|
||||||
|
"rev": "0d8c62bb906470782a4aa36d93044e660088a3f8",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"id": "fenix",
|
||||||
|
"type": "indirect"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"flake-utils": {
|
||||||
|
"inputs": {
|
||||||
|
"systems": "systems"
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681202837,
|
||||||
|
"narHash": "sha256-H+Rh19JDwRtpVPAWp64F+rlEtxUWBAQW28eAi3SRSzg=",
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "flake-utils",
|
||||||
|
"rev": "cfacdce06f30d2b68473a46042957675eebb3401",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"id": "flake-utils",
|
||||||
|
"type": "indirect"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nixpkgs": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681126633,
|
||||||
|
"narHash": "sha256-evQ3Ct/yJDSHej16Hiq+JfxRjgm9FXu/2LBxsyorGdE=",
|
||||||
|
"owner": "nixos",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"rev": "db24d86dd8a4769c50d6b7295e81aa280cd93f35",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "nixos",
|
||||||
|
"ref": "nixos-unstable",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nixpkgs_2": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1663551060,
|
||||||
|
"narHash": "sha256-e2SR4cVx9p7aW/XnVsGsWZBplApA9ZJUjc0fejJhnYo=",
|
||||||
|
"owner": "nixos",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"rev": "8a5b9ee7b7a2b38267c9481f5c629c015108ab0d",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"id": "nixpkgs",
|
||||||
|
"type": "indirect"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"root": {
|
||||||
|
"inputs": {
|
||||||
|
"fenix": "fenix",
|
||||||
|
"flake-utils": "flake-utils",
|
||||||
|
"nixpkgs": "nixpkgs_2"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"rust-analyzer-src": {
|
||||||
|
"flake": false,
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681234995,
|
||||||
|
"narHash": "sha256-QQxQAG5QZG8z/uRREhWnq4215Asl7Gh6a8zj7swDyP4=",
|
||||||
|
"owner": "rust-lang",
|
||||||
|
"repo": "rust-analyzer",
|
||||||
|
"rev": "7501d3b721560637e27f904d9fce79182c41bef7",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "rust-lang",
|
||||||
|
"ref": "nightly",
|
||||||
|
"repo": "rust-analyzer",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"systems": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681028828,
|
||||||
|
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"root": "root",
|
||||||
|
"version": 7
|
||||||
|
}
|
50
flake.nix
Normal file
50
flake.nix
Normal file
|
@ -0,0 +1,50 @@
|
||||||
|
{
|
||||||
|
inputs = { };
|
||||||
|
|
||||||
|
outputs = { self, nixpkgs, flake-utils, fenix }:
|
||||||
|
flake-utils.lib.eachDefaultSystem (system:
|
||||||
|
let
|
||||||
|
pkgs = import nixpkgs {
|
||||||
|
inherit system;
|
||||||
|
overlays = [ fenix.overlays.default ];
|
||||||
|
};
|
||||||
|
|
||||||
|
toolchain = pkgs.fenix.stable;
|
||||||
|
|
||||||
|
neededLibs = with pkgs;
|
||||||
|
(with xorg; [ libX11 libXcursor libXrandr libXi ])
|
||||||
|
++ [ vulkan-loader wayland wayland-protocols libxkbcommon ];
|
||||||
|
|
||||||
|
flakePkgs = rec { };
|
||||||
|
in rec {
|
||||||
|
packages = flake-utils.lib.flattenTree flakePkgs;
|
||||||
|
|
||||||
|
devShell = pkgs.mkShell {
|
||||||
|
inputsFrom = with flakePkgs; [ ];
|
||||||
|
|
||||||
|
shellHook = ''
|
||||||
|
export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:${
|
||||||
|
pkgs.lib.makeLibraryPath neededLibs
|
||||||
|
}"
|
||||||
|
'';
|
||||||
|
|
||||||
|
packages =
|
||||||
|
(with pkgs; [ cargo-deny cargo-edit cargo-watch cmake pkg-config ])
|
||||||
|
++ (with toolchain; [
|
||||||
|
cargo
|
||||||
|
rustc
|
||||||
|
clippy
|
||||||
|
|
||||||
|
# Get the nightly version of rustfmt so we can wrap comments
|
||||||
|
pkgs.fenix.default.rustfmt
|
||||||
|
]);
|
||||||
|
|
||||||
|
PKG_CONFIG_PATH = with pkgs;
|
||||||
|
lib.concatStringsSep ":" [
|
||||||
|
"${expat.dev}/lib/pkgconfig"
|
||||||
|
"${fontconfig.dev}/lib/pkgconfig"
|
||||||
|
"${freetype.dev}/lib/pkgconfig"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
25
package-lock.json
generated
Normal file
25
package-lock.json
generated
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
{
|
||||||
|
"name": "navigation-tools",
|
||||||
|
"lockfileVersion": 3,
|
||||||
|
"requires": true,
|
||||||
|
"packages": {
|
||||||
|
"": {
|
||||||
|
"devDependencies": {
|
||||||
|
"typescript": "^5.0.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/typescript": {
|
||||||
|
"version": "5.0.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/typescript/-/typescript-5.0.4.tgz",
|
||||||
|
"integrity": "sha512-cW9T5W9xY37cc+jfEnaUvX91foxtHkza3Nw3wkoF4sSlKn0MONdkdEndig/qPBWXNkmplh3NzayQzCiHM4/hqw==",
|
||||||
|
"dev": true,
|
||||||
|
"bin": {
|
||||||
|
"tsc": "bin/tsc",
|
||||||
|
"tsserver": "bin/tsserver"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12.20"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
5
package.json
Normal file
5
package.json
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
{
|
||||||
|
"devDependencies": {
|
||||||
|
"typescript": "^5.0.4"
|
||||||
|
}
|
||||||
|
}
|
7
parasite-messenger/Cargo.toml
Normal file
7
parasite-messenger/Cargo.toml
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
[package]
|
||||||
|
name = "parasite-messenger"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
clap = { version = "4.2.1", features = ["derive"] }
|
10
parasite-messenger/src/main.rs
Normal file
10
parasite-messenger/src/main.rs
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
use clap::Parser;
|
||||||
|
|
||||||
|
#[derive(Debug, Parser)]
|
||||||
|
struct Opt {}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let opt = Opt::parse();
|
||||||
|
|
||||||
|
println!("Hello, world!");
|
||||||
|
}
|
3
parasite/.gitignore
vendored
Normal file
3
parasite/.gitignore
vendored
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
/build
|
||||||
|
node_modules
|
||||||
|
|
3613
parasite/package-lock.json
generated
Normal file
3613
parasite/package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load diff
18
parasite/package.json
Normal file
18
parasite/package.json
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
{
|
||||||
|
"name": "parasite",
|
||||||
|
"version": "0.1.0",
|
||||||
|
"scripts": {
|
||||||
|
"build": "NODE_ENV=production ts-node scripts/build",
|
||||||
|
"dev": "NODE_ENV=development ts-node scripts/dev-server"
|
||||||
|
},
|
||||||
|
"devDependencies": {
|
||||||
|
"copy-webpack-plugin": "^11.0.0",
|
||||||
|
"ts-loader": "^9.4.2",
|
||||||
|
"ts-node": "^10.9.1",
|
||||||
|
"webpack": "^5.79.0",
|
||||||
|
"webpack-dev-server": "^4.13.2"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"@types/chrome": "^0.0.231"
|
||||||
|
}
|
||||||
|
}
|
6
parasite/scripts/build.ts
Normal file
6
parasite/scripts/build.ts
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
import webpack from "webpack";
|
||||||
|
import config from "../webpack.config";
|
||||||
|
|
||||||
|
webpack(config, function (err) {
|
||||||
|
if (err) throw err;
|
||||||
|
});
|
50
parasite/scripts/dev-server.ts
Normal file
50
parasite/scripts/dev-server.ts
Normal file
|
@ -0,0 +1,50 @@
|
||||||
|
import WebpackDevServer from "webpack-dev-server";
|
||||||
|
import webpack, { HotModuleReplacementPlugin } from "webpack";
|
||||||
|
import config from "../webpack.config";
|
||||||
|
import path from "path";
|
||||||
|
|
||||||
|
// var excludeEntriesToHotReload = options.notHotReload || [];
|
||||||
|
|
||||||
|
const PORT = 8000;
|
||||||
|
|
||||||
|
/*
|
||||||
|
for (var entryName in config.entry) {
|
||||||
|
if (excludeEntriesToHotReload.indexOf(entryName) === -1) {
|
||||||
|
config.entry[entryName] = [
|
||||||
|
"webpack-dev-server/client?http://localhost:" + PORT,
|
||||||
|
"webpack/hot/dev-server",
|
||||||
|
].concat(config.entry[entryName]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
var compiler = webpack(config);
|
||||||
|
|
||||||
|
var server = new WebpackDevServer(
|
||||||
|
{
|
||||||
|
hot: true,
|
||||||
|
|
||||||
|
devMiddleware: {
|
||||||
|
writeToDisk: true,
|
||||||
|
},
|
||||||
|
|
||||||
|
static: {
|
||||||
|
directory: path.join(__dirname, "../build"),
|
||||||
|
},
|
||||||
|
|
||||||
|
client: {
|
||||||
|
webSocketURL: {
|
||||||
|
port: PORT,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
headers: {
|
||||||
|
"Access-Control-Allow-Origin": "*",
|
||||||
|
},
|
||||||
|
|
||||||
|
allowedHosts: "all",
|
||||||
|
},
|
||||||
|
compiler
|
||||||
|
);
|
||||||
|
|
||||||
|
server.start();
|
17
parasite/src/background.ts
Normal file
17
parasite/src/background.ts
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
type Tab = chrome.tabs.Tab;
|
||||||
|
|
||||||
|
console.log("Starting background page!");
|
||||||
|
|
||||||
|
chrome.tabs.query({}, (tabs: Tab[]) => {
|
||||||
|
console.log("Tabs");
|
||||||
|
|
||||||
|
for (let tab of tabs) {
|
||||||
|
console.log([tab.windowId, tab.id], tab.url, tab.title);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
const port = chrome.runtime.connectNative(
|
||||||
|
"io.mzhang.navigation_tools.parasite_messenger"
|
||||||
|
);
|
||||||
|
|
||||||
|
console.log("Connected!");
|
15
parasite/src/manifest.json
Normal file
15
parasite/src/manifest.json
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
{
|
||||||
|
"name": "Parasite",
|
||||||
|
"background": {
|
||||||
|
"scripts": ["background.bundle.js"]
|
||||||
|
},
|
||||||
|
"browser_action": {
|
||||||
|
"default_popup": "popup.html",
|
||||||
|
"default_icon": "icon-34.png"
|
||||||
|
},
|
||||||
|
"icons": {},
|
||||||
|
"manifest_version": 2,
|
||||||
|
"content_security_policy": "script-src 'self' 'unsafe-eval'; object-src 'self'",
|
||||||
|
|
||||||
|
"permissions": ["nativeMessaging", "tabs"]
|
||||||
|
}
|
0
parasite/src/popup.ts
Normal file
0
parasite/src/popup.ts
Normal file
5
parasite/tsconfig.json
Normal file
5
parasite/tsconfig.json
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"esModuleInterop": true
|
||||||
|
}
|
||||||
|
}
|
65
parasite/webpack.config.ts
Normal file
65
parasite/webpack.config.ts
Normal file
|
@ -0,0 +1,65 @@
|
||||||
|
import path from "path";
|
||||||
|
import webpack from "webpack";
|
||||||
|
|
||||||
|
import CopyWebpackPlugin from "copy-webpack-plugin";
|
||||||
|
|
||||||
|
const node_env = (): "development" | "production" | undefined => {
|
||||||
|
let env = process.env.NODE_ENV;
|
||||||
|
if (env === "production") return env;
|
||||||
|
if (env === "development") return env;
|
||||||
|
if (env === undefined) return undefined;
|
||||||
|
|
||||||
|
console.log(
|
||||||
|
`Invalid NODE_ENV: ${env}. Can only be production, development, or undefined.`
|
||||||
|
);
|
||||||
|
process.exit(1);
|
||||||
|
};
|
||||||
|
|
||||||
|
const options: webpack.Configuration = {
|
||||||
|
mode: node_env(),
|
||||||
|
entry: {
|
||||||
|
popup: path.join(__dirname, "src", "popup.ts"),
|
||||||
|
background: path.join(__dirname, "src", "background.ts"),
|
||||||
|
},
|
||||||
|
output: {
|
||||||
|
path: path.join(__dirname, "build"),
|
||||||
|
filename: "[name].bundle.js",
|
||||||
|
},
|
||||||
|
|
||||||
|
resolve: {
|
||||||
|
extensions: [".ts", ".js"],
|
||||||
|
},
|
||||||
|
|
||||||
|
module: {
|
||||||
|
rules: [
|
||||||
|
{
|
||||||
|
test: /\.tsx?$/,
|
||||||
|
use: "ts-loader",
|
||||||
|
exclude: /node_modules/,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
|
||||||
|
plugins: [
|
||||||
|
new CopyWebpackPlugin({
|
||||||
|
patterns: [
|
||||||
|
// Copy the manifest, adding in the version and the description from the
|
||||||
|
// package.json file.
|
||||||
|
{
|
||||||
|
from: "src/manifest.json",
|
||||||
|
transform: (content, _) => {
|
||||||
|
const oldContent = JSON.parse(content.toString());
|
||||||
|
const newContent = {
|
||||||
|
description: process.env.npm_package_description,
|
||||||
|
version: process.env.npm_package_version,
|
||||||
|
...oldContent,
|
||||||
|
};
|
||||||
|
return Buffer.from(JSON.stringify(newContent));
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}),
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
|
export default options;
|
13
queryer/Cargo.toml
Normal file
13
queryer/Cargo.toml
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
[package]
|
||||||
|
name = "queryer"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
anyhow = "1.0.70"
|
||||||
|
clap = { version = "4.2.1", features = ["derive"] }
|
||||||
|
iced = "0.8.0"
|
||||||
|
once_cell = "1.17.1"
|
||||||
|
tracing = "0.1.37"
|
||||||
|
tracing-subscriber = "0.3.16"
|
||||||
|
winit = "0.28.3"
|
86
queryer/src/main.rs
Normal file
86
queryer/src/main.rs
Normal file
|
@ -0,0 +1,86 @@
|
||||||
|
use iced::keyboard::KeyCode;
|
||||||
|
use iced::widget::text_input;
|
||||||
|
use iced::{executor, keyboard, subscription, window, Event, Subscription};
|
||||||
|
use iced::{Application, Command, Element, Settings, Theme};
|
||||||
|
use once_cell::sync::Lazy;
|
||||||
|
|
||||||
|
static SEARCH_INPUT_ID: Lazy<text_input::Id> =
|
||||||
|
Lazy::new(text_input::Id::unique);
|
||||||
|
|
||||||
|
pub fn main() -> iced::Result {
|
||||||
|
let mut settings = Settings::default();
|
||||||
|
|
||||||
|
settings.window.decorations = false;
|
||||||
|
settings.window.resizable = false;
|
||||||
|
settings.window.size = (640, 280);
|
||||||
|
|
||||||
|
App::run(settings)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Default)]
|
||||||
|
struct App {
|
||||||
|
search_input: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Application for App {
|
||||||
|
type Executor = executor::Default;
|
||||||
|
type Flags = ();
|
||||||
|
type Message = Message;
|
||||||
|
type Theme = Theme;
|
||||||
|
|
||||||
|
fn new(_flags: ()) -> (App, Command<Self::Message>) {
|
||||||
|
let focus_command = text_input::focus(SEARCH_INPUT_ID.clone());
|
||||||
|
(App::default(), focus_command)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn title(&self) -> String {
|
||||||
|
String::from("A cool application")
|
||||||
|
}
|
||||||
|
|
||||||
|
fn update(&mut self, message: Self::Message) -> Command<Self::Message> {
|
||||||
|
use Message::*;
|
||||||
|
|
||||||
|
let mut commands = vec![];
|
||||||
|
|
||||||
|
match message {
|
||||||
|
InputChanged(new_value) => self.search_input = new_value,
|
||||||
|
Exit => commands.push(window::close()),
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
|
||||||
|
Command::batch(commands)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn view(&self) -> Element<Self::Message> {
|
||||||
|
// Search bar
|
||||||
|
let input =
|
||||||
|
text_input("Search...", &self.search_input, Message::InputChanged)
|
||||||
|
.id(SEARCH_INPUT_ID.clone())
|
||||||
|
.on_submit(Message::Dispatch)
|
||||||
|
.padding(15)
|
||||||
|
.size(30);
|
||||||
|
|
||||||
|
input.into()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn subscription(&self) -> Subscription<Message> {
|
||||||
|
subscription::events_with(|event, status| match (event, status) {
|
||||||
|
(
|
||||||
|
// Exit if the escape key is pressed
|
||||||
|
Event::Keyboard(keyboard::Event::KeyPressed {
|
||||||
|
key_code: KeyCode::Escape,
|
||||||
|
..
|
||||||
|
}),
|
||||||
|
_,
|
||||||
|
) => Some(Message::Exit),
|
||||||
|
_ => None,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
enum Message {
|
||||||
|
InputChanged(String),
|
||||||
|
Dispatch,
|
||||||
|
Exit,
|
||||||
|
}
|
3
rustfmt.toml
Normal file
3
rustfmt.toml
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
max_width = 80
|
||||||
|
tab_spaces = 2
|
||||||
|
wrap_comments = true
|
Loading…
Reference in a new issue