1658625480
Just a very easy solution for storing settings for an electron application.
Install with npm:
npm install --save electron-cfg
const config = require('electron-cfg');
const downloadsPath = config.get('downloads.path', process.cwd());
config.observe('album', (current, old) => {
console.log(`Previous: ${old.name}, current: ${current.name}`);
});
config.set('album', { name, photos: photos.length });
create(filePath, logger = null)
Create a new config instance with different file path.
get(key, defaultValue = null): any
Returns a value associated with the key.
Param | Type | Description |
---|---|---|
key | string | Key name, use dot in key to return nested value of some object |
defaultValue? | any | Return this values instead if key not found |
set(key, value): electron-cfg
Sets a value.
has(key): boolean
Is key exists in the config.
delete(key): electron-cfg
Removes values associated with the key.
getAll(): Object
Gets the root object of the config
setAll(data): ElectronCfg
Sets the root object of the config
file(filePath = null): string
Gets / Sets config's file path. If relative, it uses app.getPath('userData')
to resolve the full path.
observe(key, handler): electron-cfg
Attaches a handler on keyName property changes. Changes are observable only in the same process.
Param | Type | Description |
---|---|---|
key | string | Key name |
handler | (newValue, oldValue, key) => void | Observer |
purge(): electron-cfg
Removes all data from config
logger(logger = console)
Gets / Sets a logger (object with error, warn and debug methods)
window(options?): WindowManager
Allow to save/restore window size and position. See next section for details
Param | Type | Description |
---|---|---|
options = { | object | |
-- name: 'main' | string | Useful when store settings of multiple windows |
-- saveFullscreen: true | boolean | Whether to restore fullscreen state |
-- saveMaximize: true | boolean | Whether to restore maximized state |
} |
resolveUserDataPath(filePath, appName?)
Return file path relative to userData directory, similar to
path.join(app.getPath('userData'), filePath)
If appName is set, electron-cfg uses its own code to find userData directory for appName without calling app.getPath. Can be helpful in dev environment when app.getPath('userData') resolves an incorrect path.
const { BrowserWindow } = require('electron');
const cfg = require('electron-cfg');
function createWindow() {
const winCfg = cfg.window();
const window = new BrowserWindow({
width: 800, // default, optional
height: 600, // default, optional
...winCfg.options(),
});
winCfg.assign(window);
return window;
}
or it can be simplified using the create
shortcut:
const cfg = require('electron-cfg');
function createWindow() {
return cfg.window().create({ width: 800, height: 600 });
}
Remarks:
useContentSize
to true at creating BrowserWindow instance because it changes how to calculate window size.cfg.window()
before the ready event is fired.Here is a few alternatives which you can try:
A lot of code of Saving/restoring window state is based on electron-window-state
Author: Megahertz
Source Code: https://github.com/megahertz/electron-cfg
License: MIT license
1658625480
Just a very easy solution for storing settings for an electron application.
Install with npm:
npm install --save electron-cfg
const config = require('electron-cfg');
const downloadsPath = config.get('downloads.path', process.cwd());
config.observe('album', (current, old) => {
console.log(`Previous: ${old.name}, current: ${current.name}`);
});
config.set('album', { name, photos: photos.length });
create(filePath, logger = null)
Create a new config instance with different file path.
get(key, defaultValue = null): any
Returns a value associated with the key.
Param | Type | Description |
---|---|---|
key | string | Key name, use dot in key to return nested value of some object |
defaultValue? | any | Return this values instead if key not found |
set(key, value): electron-cfg
Sets a value.
has(key): boolean
Is key exists in the config.
delete(key): electron-cfg
Removes values associated with the key.
getAll(): Object
Gets the root object of the config
setAll(data): ElectronCfg
Sets the root object of the config
file(filePath = null): string
Gets / Sets config's file path. If relative, it uses app.getPath('userData')
to resolve the full path.
observe(key, handler): electron-cfg
Attaches a handler on keyName property changes. Changes are observable only in the same process.
Param | Type | Description |
---|---|---|
key | string | Key name |
handler | (newValue, oldValue, key) => void | Observer |
purge(): electron-cfg
Removes all data from config
logger(logger = console)
Gets / Sets a logger (object with error, warn and debug methods)
window(options?): WindowManager
Allow to save/restore window size and position. See next section for details
Param | Type | Description |
---|---|---|
options = { | object | |
-- name: 'main' | string | Useful when store settings of multiple windows |
-- saveFullscreen: true | boolean | Whether to restore fullscreen state |
-- saveMaximize: true | boolean | Whether to restore maximized state |
} |
resolveUserDataPath(filePath, appName?)
Return file path relative to userData directory, similar to
path.join(app.getPath('userData'), filePath)
If appName is set, electron-cfg uses its own code to find userData directory for appName without calling app.getPath. Can be helpful in dev environment when app.getPath('userData') resolves an incorrect path.
const { BrowserWindow } = require('electron');
const cfg = require('electron-cfg');
function createWindow() {
const winCfg = cfg.window();
const window = new BrowserWindow({
width: 800, // default, optional
height: 600, // default, optional
...winCfg.options(),
});
winCfg.assign(window);
return window;
}
or it can be simplified using the create
shortcut:
const cfg = require('electron-cfg');
function createWindow() {
return cfg.window().create({ width: 800, height: 600 });
}
Remarks:
useContentSize
to true at creating BrowserWindow instance because it changes how to calculate window size.cfg.window()
before the ready event is fired.Here is a few alternatives which you can try:
A lot of code of Saving/restoring window state is based on electron-window-state
Author: Megahertz
Source Code: https://github.com/megahertz/electron-cfg
License: MIT license
1624575120
Key-value stores are essential and often used, especially in operations that require fast and frequent lookups. They allow an object - the key - to be mapped to another object, the value. This way, the values can easily be retrieved, by looking up the key.
In Java, the most popular Map
implementation is the HashMap
class. Aside from key-value mapping, it’s used in code that requires frequest insertions, updates and lookups. The insert and lookup time is a constant O(1).
In this tutorial, we’ll go over how to get the Keys and Values of a map in Java.
#java #java: how to get keys and values from a map #keys #map #values #how to get keys and values from a map
1661805960
This package provides bindings for KyotoCabinet key-value storage.
Pkg.add("KyotoCabinet")
using KyotoCabinet
To open database, use open
method:
db = open("db.kch", "r")
# db::Dict{Array{Uint8,1},Array{Uint8,1}}
close(db)
There is also bracketed version:
open(Db{K,V}(), "db.kch", "w+") do db
# db::Dict{K,V}
# do stuff...
end
Db
object implements basic collections and Dict
methods.
open(Db{String,String}(), "db.kch", "w+") do db
# Basic getindex, setindex! methods
db["a"] = "1"
println(db["a"])
# Dict methods also implemented:
# haskey, getkey, get, get!, delete!, pop!
if (!haskey(db, "x"))
x = get(db, "x", "default")
y = get!(db, "y", "set_value_if_non_exists")
end
end
Support iteration over records, keys and values:
for (k, v) = db
println("k=$k v=$v")
end
for k = keys(db)
println("k=$k")
end
KyotoCabinet treats keys and values as byte arrays. To make it work with arbitrary types, one needs to define pack/unpack methods.
immutable K
x::Int
end
immutable V
a::Int
b::String
end
function KyotoCabinet.pack(k::K)
io = IOBuffer()
write(io, int32(k.x))
takebuf_array(io)
end
function KyotoCabinet.unpack(T::Type{K}, buf::Array{Uint8,1})
io = IOBuffer(buf)
x = read(io, Int32)
K(int(x))
end
function KyotoCabinet.pack(v::V)
io = IOBuffer()
write(io, int32(v.a))
write(io, int32(length(v.b)))
write(io, v.b)
takebuf_array(io)
end
function KyotoCabinet.unpack(T::Type{V}, buf::Array{Uint8,1})
io = IOBuffer(buf)
a = read(io, Int32)
l = read(io, Int32)
b = bytestring(read(io, Uint8, l))
V(int(a), b)
end
After that these types can be used as keys/values:
open(Db{K, V}(), "db.kch", "w+") do db
db[K(1)] = V(1, "a")
db[K(1999999999)] = V(2, repeat("b",100))
end
k = K(1)
println(db[k])
There are also KyotoCabinet specific methods.
# Get the path of the database file
p = path(db)
cas(db::Db, key, old, new)
Compare-and-swap method. Update the value only if it's in the expected state. Returns true
if value have been updated.
cas(db, "k", "old", "new") # update only if db["k"] == "old"
cas(db, "k", "old", ()) # remove record, only if db["k"] == "old"
cas(db, "k", (), "new") # add record, only if "k" not in db
# Updates records in one operation, atomically if needed.
bulkset!(db, ["a" => "1", "b" => "2"], true)
# Removes records in one operation, atomically if needed.
bulkdelete!(db, ["a", "b"], true)
Author: Tuzzeg
Source Code: https://github.com/tuzzeg/kyotocabinet.jl
License: View license
1661299440
A simple key/value store based on Bolt.
In the parlance of key/value stores, a "bucket" is a collection of unique keys that are associated with values. A buckets database is a set of buckets. The underlying datastore is represented by a single file on disk.
Note that buckets is just an extension of Bolt, providing a Bucket
type with some nifty convenience methods for operating on the items (key/value pairs) within instances of it. It streamlines simple transactions (a single put, get, or delete) and working with subsets of items within a bucket (via prefix and range scans).
For example, here's how you put an item in a bucket and get it back out. (Note we're omitting proper error handling here.)
// Open a buckets database.
bx, _ := buckets.Open("data.db")
defer bx.Close()
// Create a new `things` bucket.
things, _ := bx.New([]byte("things"))
// Put key/value into the `things` bucket.
key, value := []byte("A"), []byte("alpha")
things.Put(key, value)
// Read value back in a different read-only transaction.
got, _ := things.Get(key)
fmt.Printf("The value of %q in `things` is %q\n", key, got)
Output:
The value of "A" in `things` is "alpha"
As noted above, buckets is a wrapper for Bolt, streamlining basic transactions. If you're unfamiliar with Bolt, check out the README and intro articles.
A buckets/bolt database contains a set of buckets. What's a bucket? It's basically just an associative array, mapping keys to values. For simplicity, we say that a bucket contains key/values pairs and we refer to these k/v pairs as "items". You use buckets for storing and retrieving such items.
Since Bolt stores keys in byte-sorted order, we can take advantage of this sorted key namespace for fast prefix and range scanning of keys. In particular, it gives us a way to easily retrieve a subset of items. (See the PrefixItems
and RangeItems
methods, described below.)
Put(k, v)
- save/update itemPutNX(k, v)
- save item if key does not existDelete(k)
- delete itemInsert(items)
- save/update items (k/v pairs)InsertNX(items)
- for each item (k/v pair), save item if key does not existGet(k)
- get valueItems()
- get list of items (k/v pairs)PrefixItems(pre)
- get list of items with key prefixRangeItems(min, max)
- get list of items within key rangeMap(func)
- apply func to each itemMapPrefix(func, pre)
- apply func to each item with key prefixMapRange(func, min, max)
- apply a func to each item within key rangeUse go get github.com/joyrexus/buckets
to install and see the docs for details.
To open a database, use buckets.Open()
:
package main
import (
"log"
"github.com/joyrexus/buckets"
)
func main() {
bx, err := buckets.Open("my.db")
if err != nil {
log.Fatal(err)
}
defer bx.Close()
...
}
Note that buckets obtains a file lock on the data file so multiple processes cannot open the same database at the same time.
The docs contain numerous examples demonstrating basic usage.
See also the examples directory for standalone examples, demonstrating use of buckets for persistence in a web service context.
Author: joyrexus
Source Code: https://github.com/joyrexus/buckets
License: MIT license
1660054680
Simple application that replicates a key-value store using the Raft protocol. This application uses the Hashicorp implementation of the Raft protocol.
First execute:
go build
This will create a local executable with name smr
. Then, with 3 terminal tabs open, execute on each one:
./smr -addr=127.0.0.1:8080
Will create an HTTP server on port 8080 and will create a Raft node on port 9090.
./smr -addr=127.0.0.1:8081 -raft=127.0.0.1:9091
Will create an HTTP server on port 8081 and will create a Raft node on port 9091.
./smr -addr=127.0.0.1:8082 -raft=127.0.0.1:9092
Will create an HTTP server on port 8082 and will create a Raft node on port 9092.
Those are the default configuration, that can be found on the file config.json
. Now with the servers available, is possible to execute requests, like:
curl 'localhost:8081/set?key=Fuck&value=Police'
Sending a request to the HTTP server on port 8081 to associate the key Fuck
with value Police
. Now to retrieve a value just execute:
curl 'localhost:8080/get?key=Fuck'
The value defined on server 8081 is now available on server 8080.
Author: jabolina
Source Code: https://github.com/jabolina/go-smr
License: Apache-2.0 license