initial rdf parsing

This commit is contained in:
Marcell Mars 2023-07-30 17:39:17 +02:00
commit 9c7f016f7d
52 changed files with 1929 additions and 0 deletions

24
BROWSE_LIBRARY.html Normal file
View File

@ -0,0 +1,24 @@
<!doctype html>
<html>
<head>
<meta charset='utf-8'>
<meta name='viewport' content='width=device-width'>
<title>Memory of the World Library</title>
<link rel="apple-touch-icon" sizes="180x180" href="static/favicons/apple-touch-icon.png">
<link rel="icon" type="image/png" sizes="32x32" href="static/favicons/favicon-32x32.png">
<link rel="icon" type="image/png" sizes="16x16" href="static/favicons/favicon-16x16.png">
<link rel="mask-icon" href="static/favicons/safari-pinned-tab.svg" color="#5bbad5">
<meta name="msapplication-TileColor" content="#da532c">
<meta name="theme-color" content="#ffffff">
<link rel='stylesheet' href='static/css/bundle.css'>
<script rel="prefetch" src="static/data1.js"></script>
<script defer src='static/js/bundle.js'></script>
</head>
<body class="pl-2 pr-2 monocle:p-0 phone:p-0">
</body>
</html>

94
cmd/build.go Normal file
View File

@ -0,0 +1,94 @@
package cmd
import (
"fmt"
"strings"
"accorder/pkg/calibre"
"github.com/beevik/etree"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)
var buildCmd = &cobra.Command{
Use: "build",
Short: "Build standalone, portable webapp from Calibre library.",
Long: `Build searchable, standalone, portable webapp against the local Calibre
library including all the metadata needed. It creates BROWSE_LIBRARY.html in
root directory of the local Calibre library. For search (authors, titles,
tags...) it uses rendered metadata from static/data{1-8}.js files.
Every time the directory path and/or librarian is provided it is saved in
the configuration file for the future use (therefore: 'accorder build SESSION'
should be enough for the next successful build).`,
Args: cobra.ExactArgs(1),
PreRun: func(cmd *cobra.Command, args []string) {
session := args[0]
for vipFlag, cliFlag := range map[string]string{
"librarian_name": "librarian",
"local_upload": "directory",
"library_uuid": "library-uuid",
"library_secret": "library-secret",
"server_upload": "server",
"bucket_upload": "bucket",
} {
viper.BindPFlag(fmt.Sprintf("%s.%s", session, vipFlag), cmd.Flags().Lookup(cliFlag))
}
},
Run: func(cmd *cobra.Command, args []string) {
session := args[0]
MissingRequiredFlags(
map[string]string{
"librarian_name": "librarian",
"local_upload": "directory",
},
session,
cmd,
)
libraryUUID := ViperValue(session, "library_uuid")
librarySecret := ViperValue(session, "library_secret")
calibrePath := ViperValue(session, "local_upload")
librarianName := ViperValue(session, "librarian_name")
jsonPath := CliFlagValue(cmd, "jsonpath")
bibtexPath := CliFlagValue(cmd, "import-bibtex")
doc := etree.NewDocument()
if err := doc.ReadFromFile(bibtexPath); err != nil {
panic(err)
}
root := doc.SelectElement("rdf:RDF")
for _, bib := range root.FindElements("//*") {
if bib.Space == "bib" {
if strings.ToLower(bib.Tag) == "book" {
fmt.Println(bib.Tag)
fmt.Printf("%#v\n\n", bib)
}
}
}
calibre.RenderStandaloneApp(calibrePath, librarianName, libraryUUID, librarySecret, jsonPath)
},
}
func init() {
rootCmd.AddCommand(buildCmd)
buildCmd.Flags().StringP("directory", "d", "", "A local Calibre directory.")
buildCmd.Flags().StringP("librarian", "l", "", "Librarian's name.")
buildCmd.Flags().StringP("export-json", "e", "", "Path where to render all metadata into JSON.")
buildCmd.Flags().StringP("import-bibtex", "i", "", "Import books from BibTex file into Calibre.")
buildCmd.Flags().StringP("library-uuid", "u", "", "A library's UUID used if part of MotW.")
buildCmd.Flags().StringP("library-secret", "p", "", "A password used if part of MotW.")
buildCmd.Flags().StringP("server", "s", "minio.memoryoftheworld.org", "Server.")
buildCmd.Flags().StringP("bucket", "b", "", "Server.")
CustomHelpOutput(buildCmd)
buildCmd.Flags().MarkHidden("library-uuid")
buildCmd.Flags().MarkHidden("library-secret")
buildCmd.Flags().MarkHidden("server")
buildCmd.Flags().MarkHidden("bucket")
}

88
cmd/commoners.go Normal file
View File

@ -0,0 +1,88 @@
package cmd
import (
"encoding/json"
"fmt"
"log"
"os"
"path/filepath"
"github.com/kirsle/configdir"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)
func MissingRequiredFlags(flags map[string]string, session string, cmd *cobra.Command) {
exit := false
for vipFlag, cliFlag := range flags {
if ViperValue(session, vipFlag) == "" {
fmt.Printf("ERROR: A flag --%s is missing for SESSION `%s` to work.\n", cliFlag, session)
exit = true
}
}
if exit {
fmt.Println("~ ~ ~ ~")
cmd.Usage()
os.Exit(1)
}
if cmd.Flags().NFlag() > 0 {
viper.WriteConfig()
}
}
func CustomHelpOutput(cmd *cobra.Command) {
cmd.Flags().SortFlags = false
cmd.SetHelpTemplate(HelpTemplate)
cmd.SetUsageTemplate(UsageTemplate)
}
func ViperSettingsPrint() {
vipAll, err := json.MarshalIndent(viper.AllSettings(), "", " ")
if err != nil {
fmt.Println("error:", err)
}
fmt.Print(string(vipAll))
}
func CliFlagValue(cmd *cobra.Command, key string) (value string) {
value, _ = cmd.Flags().GetString(key)
return
}
func ViperValue(session, key string) string {
return viper.GetString(fmt.Sprintf("%s.%s", session, key))
}
func CheckProfile(cmd *cobra.Command, args []string) error {
hasProfile := false
// fmt.Println("VIPER:", viper.AllSettings())
for k, v := range viper.AllSettings() {
fmt.Println("VIPER KEY/VALUE:", k, v)
if k == args[0] {
hasProfile = true
}
}
if !hasProfile {
return fmt.Errorf("PROFILE %s should be added to the configuration file.\n", args[0])
}
return fmt.Errorf("MEH! %s should be added to the configuration file.\n", args[0])
}
func ConfigBaseDir() string {
return configdir.LocalConfig("akkorder")
}
func ConfigMinioDir() string {
return filepath.Join(ConfigBaseDir(), "minio")
}
func initConfigPaths() {
err := configdir.MakePath(ConfigBaseDir()) // Ensure it exists.
if err != nil {
panic(err)
}
os.MkdirAll(filepath.Join(ConfigBaseDir(), "minio"), 0777)
}

104
cmd/helptemplates.go Normal file
View File

@ -0,0 +1,104 @@
package cmd
const HelpTemplate = `Command usage:{{if .Runnable}}
{{.UseLine}}{{end}}{{if .HasAvailableSubCommands}}{{end}} PROFILE {{if gt (len .Aliases) 0}}
Aliases:
{{.NameAndAliases}}{{end}}{{if .HasExample}}
Examples:
{{.Example}}{{end}}{{if .HasAvailableSubCommands}}
Available commands:{{range .Commands}}{{if and (ne .Name "completion") .IsAvailableCommand}}
{{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}}
Flags:
{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}}
Global Flags:
{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}}
Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}}
{{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}}
Use "{{.CommandPath}} 'command' --help" for more information about a command.{{end}}
~~~ About command '{{.Name}}' ~~~
{{with (or .Long .Short)}}{{. | trimTrailingWhitespaces}}{{end}}
`
const RootHelpTemplate = `Usage:
{{.UseLine}}{{if .HasAvailableSubCommands}}{{end}} PROFILE {{if gt (len .Aliases) 0}}
Aliases:
{{.NameAndAliases}}{{end}}{{if .HasExample}}
Examples:
{{.Example}}{{end}}{{if .HasAvailableSubCommands}}
Available commands:{{range .Commands}}{{if and (ne .Name "completion") .IsAvailableCommand}}
{{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}}
Flags:
{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}}
Global Flags:
{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}}
Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}}
{{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}}
Use "{{.CommandPath}} 'command' --help" for more information about a command.{{end}}
~~~ About {{.Name}} ~~~{{with (or .Long .Short)}}{{. | trimTrailingWhitespaces}}{{end}}
`
const RootUsageTemplate = `Usage:
{{.UseLine}}{{if .HasAvailableSubCommands}}{{end}} PROFILE {{if gt (len .Aliases) 0}}
Aliases:
{{.NameAndAliases}}{{end}}{{if .HasExample}}
Examples:
{{.Example}}{{end}}{{if .HasAvailableSubCommands}}
Available commands:{{range .Commands}}{{if and (ne .Name "completion") .IsAvailableCommand}}
{{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}}
Flags:
{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}}
Global Flags:
{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}}
Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}}
{{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}}
Use "{{.CommandPath}} [command] --help" for more information about a command.{{end}}
`
const UsageTemplate = `Usage:{{if .Runnable}}
{{.UseLine}}{{end}}{{if .HasAvailableSubCommands}}{{end}} PROFILE {{if gt (len .Aliases) 0}}
Aliases:
{{.NameAndAliases}}{{end}}{{if .HasExample}}
Examples:
{{.Example}}{{end}}{{if .HasAvailableSubCommands}}
Available commands:{{range .Commands}}{{if and (ne .Name "completion") .IsAvailableCommand}}
{{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}}
Flags:
{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}}
Global Flags:
{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}}
Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}}
{{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}}
Use "{{.CommandPath}} [command] --help" for more information about a command.{{end}}
`

30
cmd/mc.go Normal file
View File

@ -0,0 +1,30 @@
/*
Copyright © 2021
*/
package cmd
import (
miniocmd "github.com/minio/mc/cmd"
"github.com/spf13/cobra"
"os"
)
// mcCmd represents the mc command
var mcCmd = &cobra.Command{
Use: "mc",
Short: "A proxy for `mc` minio client responsible for upload & download`.",
Run: func(cmd *cobra.Command, args []string) {
// rgs := []string{"", "-C", ConfigMinioDir()}
// rgs := []string{"", "-C", ConfigMinioDir()}
os.Setenv("MC_HOST_minio.memoryoftheworld.org", "https://klemo:U9@?x$)Kdoq15)J~@minio.memoryoftheworld.org")
rgs := []string{"", "-C", ConfigMinioDir(), "ls", "minio.memoryoftheworld.org/klemo"}
rgs = append(rgs, args...)
miniocmd.Main(rgs)
},
}
func init() {
mcCmd.DisableFlagParsing = true
rootCmd.AddCommand(mcCmd)
}

36
cmd/release.go Normal file
View File

@ -0,0 +1,36 @@
package cmd
import (
"fmt"
"github.com/spf13/cobra"
)
// releaseCmd represents the release command
var releaseCmd = &cobra.Command{
Use: "release",
Short: "A brief description of your command",
Long: `A longer description that spans multiple lines and likely contains examples
and usage of using your command. For example:
Cobra is a CLI library for Go that empowers applications.
This application is a tool to generate the needed files
to quickly create a Cobra application.`,
Run: func(cmd *cobra.Command, args []string) {
fmt.Println("release called")
},
}
func init() {
rootCmd.AddCommand(releaseCmd)
// Here you will define your flags and configuration settings.
// Cobra supports Persistent Flags which will work for this command
// and all subcommands, e.g.:
// releaseCmd.PersistentFlags().String("foo", "", "A help for foo")
// Cobra supports local flags which will only run when this command
// is called directly, e.g.:
// releaseCmd.Flags().BoolP("toggle", "t", false, "Help message for toggle")
}

80
cmd/root.go Normal file
View File

@ -0,0 +1,80 @@
package cmd
import (
"fmt"
"os"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)
var cfgFile string
// rootCmd represents the base command when called without any subcommands
var rootCmd = &cobra.Command{
Use: "accorder command",
Short: "Accorder helps amateur librarians stay in accordance with MotW",
Long: `
Accorder takes care of various tasks which Memory of the World amateur
librarians do in order to maintain their shared catalogs online.
It builds searchable, standalone, portable webapp which one could then
just copy to USB disk and open BROWSE_LIBRARY.html in her web browser.
It uploads all of the books and metadata from local Calibre's library
(together with portable webapp) to the server.
It helps a librarian to maintain and share her catalog at
https://library.memoryoftheworld.org
together with other amateur librarians.
It does all of above in one go by typing: accorder release SESSION.
The configuration file will keep information about one or more SESSION.
Good name for SESSION is the one which reminds you quickly on what
SESSION would do.
Under every SESSION's configuration section there will be information
about the directory path of local Calibre's library, librarian's name,
credentials needed to upload/download the files to the destination
server etc.`,
PersistentPreRunE: func(cmd *cobra.Command, args []string) error {
if err := initConfig(args); err != nil {
fmt.Println("ERROR:", err)
os.Exit(1)
}
return nil
},
}
// Execute adds all child commands to the root command and sets flags appropriately.
// This is called by main.main(). It only needs to happen once to the rootCmd.
func Execute() {
if err := rootCmd.Execute(); err != nil {
fmt.Println(err)
os.Exit(1)
}
}
func init() {
// cobra.OnInitialize(initConfig)
rootCmd.SetHelpTemplate(RootHelpTemplate)
rootCmd.SetUsageTemplate(RootUsageTemplate)
}
// initConfig reads in config file and ENV variables if set.
func initConfig(args []string) error {
initConfigPaths()
viper.AddConfigPath(ConfigBaseDir())
viper.SetConfigName("config")
// viper.AutomaticEnv() // read in environment variables that match
// If a config file is found, read it in.
if err := viper.ReadInConfig(); err != nil {
return fmt.Errorf("ERROR:%s with config:%s", err, viper.ConfigFileUsed())
}
return nil
}

26
cmd/submit.go Normal file
View File

@ -0,0 +1,26 @@
package cmd
import (
"fmt"
"github.com/spf13/cobra"
)
// submitCmd represents the submit command
var submitCmd = &cobra.Command{
Use: "submit",
Short: "Submit metadata to the aggregated MotW Library.",
Long: `Submit all the library's metadata to the aggregated Memory of the World
Library (https://library.memoryoftheworld.org).`,
// Args: OnlyProfileArgument,
Run: func(cmd *cobra.Command, args []string) {
fmt.Println(args)
},
}
func init() {
rootCmd.AddCommand(submitCmd)
submitCmd.PersistentFlags().StringP("librarian", "l", "", "Librarian's name.")
submitCmd.PersistentFlags().BoolP("remove-library", "", false, "Remove PROFILE's library from the MotW Library.")
CustomHelpOutput(submitCmd)
}

101
cmd/upload.go Normal file
View File

@ -0,0 +1,101 @@
package cmd
import (
"fmt"
"os"
miniocmd "github.com/minio/mc/cmd"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)
// uploadCmd represents the upload command
var uploadCmd = &cobra.Command{
Use: "upload",
Short: "Upload local Calibre library to the MotW server.",
Long: `Upload local Calibre library to the Memory of the World server.
It will take care of the differences so files already at the server
will not be uploaded again.
Every time the directory path and/or librarian is provided it is saved in
configuration file for the future use (therefore: 'accorder upload SESSION'
should be enough for the next successful upload).`,
Args: cobra.ExactArgs(1),
PreRun: func(cmd *cobra.Command, args []string) {
session := args[0]
for vipFlag, cliFlag := range map[string]string{
"server_upload": "server",
"library_uuid": "username",
"library_secret": "password",
"bucket_upload": "bucket",
"local_upload": "directory",
"librarian_name": "librarian",
} {
viper.BindPFlag(fmt.Sprintf("%s.%s", session, vipFlag), cmd.Flags().Lookup(cliFlag))
}
},
Run: func(cmd *cobra.Command, args []string) {
session := args[0]
MissingRequiredFlags(
map[string]string{
"server_upload": "server",
"library_uuid": "username",
"library_secret": "password",
"bucket_upload": "bucket",
"local_upload": "directory",
},
session,
cmd,
)
server := ViperValue(session, "server_upload")
// username in upload context comes from library_uuid
username := ViperValue(session, "library_uuid")
// password in upload context comes from library_secret
password := ViperValue(session, "library_secret")
bucket := ViperValue(session, "bucket_upload")
localDirectory := ViperValue(session, "local_upload")
deleteResidue, _ := cmd.PersistentFlags().GetBool("delete-residue")
verbose, _ := cmd.PersistentFlags().GetBool("verbose")
os.Setenv(
fmt.Sprintf("MC_HOST_%s", server),
fmt.Sprintf("https://%s:%s@%s", username, password, server),
)
rgs := []string{"",
"-C", ConfigMinioDir(),
"mirror", "--overwrite",
}
if deleteResidue {
rgs = append(rgs, "--remove")
}
if verbose {
rgs = append(rgs, "--json")
}
rgs = append(rgs, localDirectory, fmt.Sprintf("%s/%s", server, bucket))
miniocmd.Main(rgs)
},
}
func init() {
rootCmd.AddCommand(uploadCmd)
uploadCmd.Flags().StringP("directory", "d", "", "A local directory to be uploaded.")
uploadCmd.Flags().StringP("username", "u", "", "Username.")
uploadCmd.Flags().StringP("password", "p", "", "Password.")
uploadCmd.Flags().StringP("bucket", "b", "", "A remote directory/bucket where to upload.")
uploadCmd.Flags().StringP("server", "s", "minio.memoryoftheworld.org", "Server.")
uploadCmd.Flags().BoolP("delete-residue", "", false, "Delete any remote files not present locally anymore.")
uploadCmd.Flags().BoolP("verbose", "v", false, "Verbose log.")
uploadCmd.Flags().StringP("librarian", "l", "", "Librarian's name.")
CustomHelpOutput(uploadCmd)
uploadCmd.Flags().MarkHidden("librarian")
}

13
go.mod Normal file
View File

@ -0,0 +1,13 @@
module accorder
go 1.16
require (
github.com/beevik/etree v1.1.0
github.com/karrick/godirwalk v1.16.1
github.com/kirsle/configdir v0.0.0-20170128060238-e45d2f54772f
github.com/minio/mc v0.0.0-20211116163708-d0c62eb584e5
github.com/satori/go.uuid v1.2.0
github.com/spf13/cobra v1.2.1
github.com/spf13/viper v1.9.0
)

1009
go.sum Normal file

File diff suppressed because it is too large Load Diff

7
main.go Normal file
View File

@ -0,0 +1,7 @@
package main
import "accorder/cmd"
func main() {
cmd.Execute()
}

View File

@ -0,0 +1,24 @@
<!doctype html>
<html>
<head>
<meta charset='utf-8'>
<meta name='viewport' content='width=device-width'>
<title>Memory of the World Library</title>
<link rel="apple-touch-icon" sizes="180x180" href="static/favicons/apple-touch-icon.png">
<link rel="icon" type="image/png" sizes="32x32" href="static/favicons/favicon-32x32.png">
<link rel="icon" type="image/png" sizes="16x16" href="static/favicons/favicon-16x16.png">
<link rel="mask-icon" href="static/favicons/safari-pinned-tab.svg" color="#5bbad5">
<meta name="msapplication-TileColor" content="#da532c">
<meta name="theme-color" content="#ffffff">
<link rel='stylesheet' href='static/css/bundle.css'>
<script rel="prefetch" src="static/data1.js"></script>
<script defer src='static/js/bundle.js'></script>
</head>
<body class="pl-2 pr-2 monocle:p-0 phone:p-0">
</body>
</html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1 @@
CALIBRE_BOOKS1={"portable":false}

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 978 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.4 KiB

View File

@ -0,0 +1,106 @@
<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
width="1374.000000pt" height="1374.000000pt" viewBox="0 0 1374.000000 1374.000000"
preserveAspectRatio="xMidYMid meet">
<metadata>
Created by potrace 1.11, written by Peter Selinger 2001-2013
</metadata>
<g transform="translate(0.000000,1374.000000) scale(0.100000,-0.100000)"
fill="#000000" stroke="none">
<path d="M6869 11514 c-24 -18 -49 -33 -56 -33 -6 -1 -13 -4 -15 -8 -1 -5 -48
-37 -103 -73 -55 -36 -102 -68 -105 -71 -3 -3 -9 -8 -15 -10 -20 -8 -280 -184
-283 -191 -2 -5 -8 -8 -13 -8 -6 0 -15 -5 -22 -10 -14 -12 -155 -105 -203
-135 -19 -11 -42 -28 -53 -37 -11 -9 -22 -14 -25 -11 -3 3 -8 -2 -12 -11 -3
-9 -10 -16 -16 -16 -5 0 -35 -17 -66 -39 -31 -21 -61 -39 -66 -39 -5 0 -12 -4
-15 -9 -10 -14 -79 -63 -89 -63 -5 0 -17 -9 -27 -20 -10 -11 -22 -20 -26 -20
-10 0 -133 -83 -137 -92 -2 -5 -7 -8 -12 -8 -10 0 -134 -82 -138 -92 -2 -4 -8
-8 -13 -8 -11 0 -133 -81 -137 -92 -2 -5 -7 -8 -12 -8 -8 0 -374 -239 -397
-259 -7 -6 -16 -11 -20 -11 -5 0 -20 -11 -35 -25 -15 -14 -31 -25 -36 -25 -4
0 -17 -7 -27 -15 -11 -9 -101 -69 -200 -135 -99 -65 -184 -122 -190 -127 -5
-4 -22 -14 -37 -22 -16 -8 -28 -18 -28 -23 0 -4 -5 -8 -10 -8 -6 0 -33 -16
-60 -35 -27 -19 -54 -35 -59 -35 -5 0 -11 -3 -13 -7 -3 -8 -174 -124 -193
-132 -5 -2 -33 -21 -62 -43 -29 -21 -55 -38 -58 -38 -3 0 -27 -16 -54 -35 -26
-19 -53 -35 -59 -35 -6 0 -12 -4 -14 -8 -4 -11 -155 -112 -167 -112 -5 0 -11
-3 -13 -7 -5 -12 -95 -73 -107 -73 -6 0 -11 -4 -11 -8 0 -5 -12 -15 -27 -23
-16 -8 -30 -16 -33 -20 -6 -6 -389 -261 -405 -269 -5 -3 -51 -33 -102 -67 -51
-35 -97 -63 -103 -63 -5 0 -10 -4 -10 -8 0 -4 -22 -21 -50 -37 -27 -17 -50
-33 -50 -37 0 -5 -7 -8 -15 -8 -8 0 -15 -4 -15 -10 0 -5 -4 -10 -10 -10 -5 0
-32 -16 -59 -35 -26 -19 -53 -35 -59 -35 -6 0 -12 -3 -14 -8 -1 -4 -50 -38
-108 -77 -58 -38 -108 -74 -112 -80 -5 -6 -8 -6 -8 0 0 6 -6 3 -13 -6 -7 -9
-22 -19 -35 -23 -12 -4 -22 -11 -22 -15 0 -5 -13 -14 -30 -21 -16 -7 -30 -16
-30 -20 0 -4 -16 -15 -35 -24 -19 -9 -35 -21 -35 -27 0 -6 -5 -7 -10 -4 -6 3
-10 1 -10 -4 0 -6 -4 -11 -9 -11 -6 0 -31 -15 -56 -32 -26 -18 -54 -38 -63
-43 -37 -22 -77 -50 -82 -56 -3 -3 -16 -12 -30 -19 -14 -7 -42 -26 -62 -42
-21 -16 -38 -27 -38 -23 0 3 -7 0 -15 -7 -33 -30 -45 -38 -54 -38 -5 0 -16 -6
-23 -13 -17 -17 -488 -330 -510 -339 -9 -4 -37 -26 -61 -50 -74 -74 -100 -190
-98 -438 1 -118 4 -169 16 -285 4 -27 8 -69 10 -93 3 -24 7 -56 11 -70 5 -27
11 -64 18 -112 2 -14 7 -41 11 -60 4 -19 9 -45 11 -57 1 -11 5 -30 8 -41 4
-11 8 -29 10 -39 10 -48 39 -164 56 -223 11 -36 22 -76 24 -90 3 -14 5 -25 6
-25 1 0 3 -7 5 -15 4 -17 62 -187 72 -210 3 -8 7 -17 7 -20 1 -3 7 -15 14 -27
7 -13 10 -23 7 -23 -3 0 6 -20 19 -45 14 -25 23 -45 20 -45 -7 0 64 -136 98
-187 15 -23 28 -45 28 -49 0 -4 7 -14 15 -23 8 -9 29 -32 47 -52 18 -20 51
-49 73 -65 22 -16 49 -37 59 -46 11 -10 26 -18 33 -18 7 0 13 -4 13 -10 0 -5
7 -10 15 -10 8 0 15 -4 15 -9 0 -5 20 -21 44 -35 25 -14 51 -32 58 -39 7 -7
47 -36 88 -65 41 -28 98 -67 125 -87 28 -20 68 -48 90 -63 22 -15 41 -30 43
-34 2 -5 10 -8 18 -8 8 0 14 -3 14 -8 0 -4 18 -18 40 -32 22 -14 40 -28 40
-32 0 -5 6 -8 13 -8 8 0 22 -9 32 -20 10 -11 22 -20 27 -20 5 0 14 -5 21 -10
7 -6 48 -36 92 -67 44 -32 82 -60 85 -63 3 -3 12 -9 21 -15 10 -5 37 -24 60
-41 24 -16 76 -52 114 -79 39 -27 76 -55 83 -61 6 -7 21 -16 32 -19 11 -3 20
-10 20 -14 0 -4 18 -17 40 -30 22 -12 40 -26 40 -32 0 -5 5 -9 11 -9 6 0 28
-14 49 -30 21 -17 42 -30 48 -30 6 0 12 -3 14 -7 4 -9 174 -133 182 -133 3 0
14 -7 24 -16 9 -8 60 -45 112 -82 52 -37 97 -70 98 -74 2 -5 9 -8 15 -8 7 0
24 -11 39 -25 15 -14 31 -25 35 -25 4 0 19 -9 33 -20 63 -51 120 -90 129 -90
5 0 11 -3 13 -7 5 -11 147 -113 157 -113 5 0 11 -4 13 -8 1 -5 26 -23 53 -42
28 -18 52 -36 55 -39 12 -14 70 -51 80 -51 5 0 10 -3 10 -8 0 -4 18 -18 40
-32 22 -14 40 -28 40 -32 0 -5 7 -8 15 -8 9 0 18 -7 21 -15 4 -8 10 -15 15
-15 8 0 113 -71 144 -98 6 -5 24 -17 40 -27 17 -11 56 -39 87 -62 31 -24 59
-43 62 -43 3 0 14 -6 23 -14 39 -31 113 -86 118 -86 4 0 132 -90 180 -127 6
-4 33 -24 60 -43 28 -19 52 -38 53 -42 2 -4 8 -8 13 -8 9 0 67 -38 79 -51 3
-3 28 -21 55 -39 28 -19 52 -37 53 -42 2 -4 10 -8 18 -8 8 0 14 -4 14 -10 0
-5 6 -10 14 -10 8 0 16 -4 18 -8 2 -5 26 -23 53 -42 28 -18 52 -36 55 -39 12
-14 70 -51 80 -51 5 0 10 -3 10 -7 0 -5 25 -24 55 -43 30 -19 54 -38 55 -42 0
-5 5 -8 11 -8 11 0 92 -60 97 -72 2 -5 10 -8 18 -8 8 0 14 -4 14 -10 0 -5 7
-10 15 -10 8 0 15 -4 15 -10 0 -5 7 -10 15 -10 8 0 15 -4 15 -10 0 -5 6 -10
14 -10 8 0 16 -3 18 -8 4 -9 202 -150 223 -158 15 -6 52 13 84 44 9 9 31 28
49 42 18 14 45 36 61 50 57 52 91 80 96 80 3 0 16 10 28 23 12 12 47 43 77 67
67 55 95 79 124 105 12 11 41 35 64 53 22 19 50 41 60 50 11 10 34 28 52 42
17 13 47 38 65 55 18 16 50 44 70 60 21 17 47 39 59 50 12 11 45 38 72 60 27
22 65 54 84 72 19 18 41 33 48 33 6 0 12 7 12 15 0 8 4 15 8 15 5 0 18 8 30
17 41 35 108 91 187 158 26 22 58 50 71 63 13 12 25 22 28 22 6 0 44 33 91 78
13 12 27 22 30 22 3 0 13 8 23 17 10 10 40 36 67 58 26 22 59 49 71 60 12 11
39 34 60 50 20 17 44 37 53 46 9 8 39 33 66 55 28 21 52 42 55 45 3 3 34 30
70 60 36 29 70 58 76 64 6 5 30 26 54 45 25 19 62 51 84 70 23 19 45 38 51 43
5 4 21 17 35 30 14 12 45 38 69 57 24 19 56 46 71 60 15 14 43 37 62 52 19 15
45 37 59 50 14 13 45 39 69 58 24 19 61 51 83 70 22 19 62 52 89 72 28 21 46
38 42 38 -5 1 1 6 12 13 21 12 69 52 162 134 26 24 53 43 60 43 6 0 12 7 12
15 0 8 4 15 10 15 10 0 27 14 98 78 21 18 58 49 85 69 26 21 47 41 47 45 0 4
5 8 10 8 6 0 18 8 28 17 31 30 85 77 117 101 17 13 50 41 75 62 40 35 154 131
219 185 13 11 58 49 101 85 84 71 84 70 215 179 50 41 97 81 106 90 9 9 25 23
36 31 26 21 137 113 143 120 5 5 118 99 135 113 6 4 21 17 35 30 14 12 45 38
69 57 24 19 48 40 55 45 6 6 38 33 71 60 33 28 67 58 76 67 9 10 19 18 23 18
4 0 21 13 39 29 34 32 160 139 242 206 70 57 104 87 131 114 13 13 24 21 24
18 0 -4 15 8 33 26 19 18 49 43 67 57 18 14 43 34 55 45 12 11 41 36 66 55 24
19 53 44 64 55 11 11 36 32 55 47 19 15 47 37 61 50 15 13 46 39 69 58 132
108 133 110 128 165 -5 64 -34 105 -96 136 -26 13 -49 24 -52 24 -3 0 -12 5
-20 10 -8 5 -60 32 -115 60 -102 52 -117 60 -170 88 -29 15 -51 57 -61 117 -4
29 -8 44 -19 85 -5 16 -9 39 -10 50 -1 11 -5 36 -8 55 -4 19 -10 49 -13 65 -7
41 -11 68 -18 150 -4 39 -9 90 -12 115 -6 50 -6 368 0 415 2 17 7 62 11 100 8
80 9 87 20 138 4 20 10 37 14 37 4 0 20 12 38 28 40 35 59 51 108 87 22 16 47
36 57 45 9 8 31 26 49 40 18 14 58 45 89 70 31 25 69 54 85 65 69 49 85 72 85
120 0 65 -34 115 -102 148 -29 14 -93 44 -143 67 -49 23 -112 52 -140 65 -54
25 -137 64 -308 144 -59 28 -109 51 -112 51 -2 0 -50 22 -105 49 -55 28 -103
50 -105 51 -5 1 -84 37 -230 105 -171 80 -233 109 -295 138 -36 17 -67 31 -70
32 -44 15 -70 29 -70 38 0 6 -3 8 -6 4 -4 -3 -27 5 -53 18 -76 39 -146 69
-153 67 -5 -1 -8 3 -8 10 0 6 -3 9 -6 6 -3 -4 -31 6 -62 22 -70 34 -202 97
-302 142 -41 19 -102 48 -135 64 -33 16 -62 29 -65 29 -3 0 -40 18 -83 38
-106 51 -191 91 -197 92 -3 1 -43 19 -90 42 -47 22 -119 57 -161 76 -115 53
-173 80 -291 136 -59 28 -109 51 -111 51 -3 0 -65 29 -138 63 -155 74 -171 81
-181 79 -5 -1 -8 3 -8 8 0 6 -4 10 -9 10 -5 0 -51 20 -102 44 -157 73 -209 96
-219 96 -6 0 -10 5 -10 10 0 6 -5 10 -12 10 -6 0 -49 18 -94 40 -46 22 -88 40
-93 40 -6 0 -11 5 -11 12 0 6 -3 9 -6 6 -3 -4 -41 11 -85 33 -43 21 -81 39
-83 39 -3 0 -49 20 -103 45 -132 62 -147 69 -153 76 -9 10 -94 30 -121 27 -14
-1 -45 -17 -70 -34z"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.2 KiB

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

9
static/css/bundle.css Normal file

File diff suppressed because one or more lines are too long

24
static/css/bundle.css.map Normal file

File diff suppressed because one or more lines are too long

1
static/data1.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS1={"portable":true,"books":null}

1
static/data2.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS2={"portable":true,"books":null}

1
static/data3.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS3={"portable":true,"books":null}

1
static/data4.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS4={"portable":true,"books":null}

1
static/data5.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS5={"portable":true,"books":null}

1
static/data6.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS6={"portable":true,"books":null}

1
static/data7.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS7={"portable":true,"books":null}

1
static/data8.js Normal file
View File

@ -0,0 +1 @@
CALIBRE_BOOKS8={"portable":true,"books":null}

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 978 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.4 KiB

View File

@ -0,0 +1,106 @@
<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
width="1374.000000pt" height="1374.000000pt" viewBox="0 0 1374.000000 1374.000000"
preserveAspectRatio="xMidYMid meet">
<metadata>
Created by potrace 1.11, written by Peter Selinger 2001-2013
</metadata>
<g transform="translate(0.000000,1374.000000) scale(0.100000,-0.100000)"
fill="#000000" stroke="none">
<path d="M6869 11514 c-24 -18 -49 -33 -56 -33 -6 -1 -13 -4 -15 -8 -1 -5 -48
-37 -103 -73 -55 -36 -102 -68 -105 -71 -3 -3 -9 -8 -15 -10 -20 -8 -280 -184
-283 -191 -2 -5 -8 -8 -13 -8 -6 0 -15 -5 -22 -10 -14 -12 -155 -105 -203
-135 -19 -11 -42 -28 -53 -37 -11 -9 -22 -14 -25 -11 -3 3 -8 -2 -12 -11 -3
-9 -10 -16 -16 -16 -5 0 -35 -17 -66 -39 -31 -21 -61 -39 -66 -39 -5 0 -12 -4
-15 -9 -10 -14 -79 -63 -89 -63 -5 0 -17 -9 -27 -20 -10 -11 -22 -20 -26 -20
-10 0 -133 -83 -137 -92 -2 -5 -7 -8 -12 -8 -10 0 -134 -82 -138 -92 -2 -4 -8
-8 -13 -8 -11 0 -133 -81 -137 -92 -2 -5 -7 -8 -12 -8 -8 0 -374 -239 -397
-259 -7 -6 -16 -11 -20 -11 -5 0 -20 -11 -35 -25 -15 -14 -31 -25 -36 -25 -4
0 -17 -7 -27 -15 -11 -9 -101 -69 -200 -135 -99 -65 -184 -122 -190 -127 -5
-4 -22 -14 -37 -22 -16 -8 -28 -18 -28 -23 0 -4 -5 -8 -10 -8 -6 0 -33 -16
-60 -35 -27 -19 -54 -35 -59 -35 -5 0 -11 -3 -13 -7 -3 -8 -174 -124 -193
-132 -5 -2 -33 -21 -62 -43 -29 -21 -55 -38 -58 -38 -3 0 -27 -16 -54 -35 -26
-19 -53 -35 -59 -35 -6 0 -12 -4 -14 -8 -4 -11 -155 -112 -167 -112 -5 0 -11
-3 -13 -7 -5 -12 -95 -73 -107 -73 -6 0 -11 -4 -11 -8 0 -5 -12 -15 -27 -23
-16 -8 -30 -16 -33 -20 -6 -6 -389 -261 -405 -269 -5 -3 -51 -33 -102 -67 -51
-35 -97 -63 -103 -63 -5 0 -10 -4 -10 -8 0 -4 -22 -21 -50 -37 -27 -17 -50
-33 -50 -37 0 -5 -7 -8 -15 -8 -8 0 -15 -4 -15 -10 0 -5 -4 -10 -10 -10 -5 0
-32 -16 -59 -35 -26 -19 -53 -35 -59 -35 -6 0 -12 -3 -14 -8 -1 -4 -50 -38
-108 -77 -58 -38 -108 -74 -112 -80 -5 -6 -8 -6 -8 0 0 6 -6 3 -13 -6 -7 -9
-22 -19 -35 -23 -12 -4 -22 -11 -22 -15 0 -5 -13 -14 -30 -21 -16 -7 -30 -16
-30 -20 0 -4 -16 -15 -35 -24 -19 -9 -35 -21 -35 -27 0 -6 -5 -7 -10 -4 -6 3
-10 1 -10 -4 0 -6 -4 -11 -9 -11 -6 0 -31 -15 -56 -32 -26 -18 -54 -38 -63
-43 -37 -22 -77 -50 -82 -56 -3 -3 -16 -12 -30 -19 -14 -7 -42 -26 -62 -42
-21 -16 -38 -27 -38 -23 0 3 -7 0 -15 -7 -33 -30 -45 -38 -54 -38 -5 0 -16 -6
-23 -13 -17 -17 -488 -330 -510 -339 -9 -4 -37 -26 -61 -50 -74 -74 -100 -190
-98 -438 1 -118 4 -169 16 -285 4 -27 8 -69 10 -93 3 -24 7 -56 11 -70 5 -27
11 -64 18 -112 2 -14 7 -41 11 -60 4 -19 9 -45 11 -57 1 -11 5 -30 8 -41 4
-11 8 -29 10 -39 10 -48 39 -164 56 -223 11 -36 22 -76 24 -90 3 -14 5 -25 6
-25 1 0 3 -7 5 -15 4 -17 62 -187 72 -210 3 -8 7 -17 7 -20 1 -3 7 -15 14 -27
7 -13 10 -23 7 -23 -3 0 6 -20 19 -45 14 -25 23 -45 20 -45 -7 0 64 -136 98
-187 15 -23 28 -45 28 -49 0 -4 7 -14 15 -23 8 -9 29 -32 47 -52 18 -20 51
-49 73 -65 22 -16 49 -37 59 -46 11 -10 26 -18 33 -18 7 0 13 -4 13 -10 0 -5
7 -10 15 -10 8 0 15 -4 15 -9 0 -5 20 -21 44 -35 25 -14 51 -32 58 -39 7 -7
47 -36 88 -65 41 -28 98 -67 125 -87 28 -20 68 -48 90 -63 22 -15 41 -30 43
-34 2 -5 10 -8 18 -8 8 0 14 -3 14 -8 0 -4 18 -18 40 -32 22 -14 40 -28 40
-32 0 -5 6 -8 13 -8 8 0 22 -9 32 -20 10 -11 22 -20 27 -20 5 0 14 -5 21 -10
7 -6 48 -36 92 -67 44 -32 82 -60 85 -63 3 -3 12 -9 21 -15 10 -5 37 -24 60
-41 24 -16 76 -52 114 -79 39 -27 76 -55 83 -61 6 -7 21 -16 32 -19 11 -3 20
-10 20 -14 0 -4 18 -17 40 -30 22 -12 40 -26 40 -32 0 -5 5 -9 11 -9 6 0 28
-14 49 -30 21 -17 42 -30 48 -30 6 0 12 -3 14 -7 4 -9 174 -133 182 -133 3 0
14 -7 24 -16 9 -8 60 -45 112 -82 52 -37 97 -70 98 -74 2 -5 9 -8 15 -8 7 0
24 -11 39 -25 15 -14 31 -25 35 -25 4 0 19 -9 33 -20 63 -51 120 -90 129 -90
5 0 11 -3 13 -7 5 -11 147 -113 157 -113 5 0 11 -4 13 -8 1 -5 26 -23 53 -42
28 -18 52 -36 55 -39 12 -14 70 -51 80 -51 5 0 10 -3 10 -8 0 -4 18 -18 40
-32 22 -14 40 -28 40 -32 0 -5 7 -8 15 -8 9 0 18 -7 21 -15 4 -8 10 -15 15
-15 8 0 113 -71 144 -98 6 -5 24 -17 40 -27 17 -11 56 -39 87 -62 31 -24 59
-43 62 -43 3 0 14 -6 23 -14 39 -31 113 -86 118 -86 4 0 132 -90 180 -127 6
-4 33 -24 60 -43 28 -19 52 -38 53 -42 2 -4 8 -8 13 -8 9 0 67 -38 79 -51 3
-3 28 -21 55 -39 28 -19 52 -37 53 -42 2 -4 10 -8 18 -8 8 0 14 -4 14 -10 0
-5 6 -10 14 -10 8 0 16 -4 18 -8 2 -5 26 -23 53 -42 28 -18 52 -36 55 -39 12
-14 70 -51 80 -51 5 0 10 -3 10 -7 0 -5 25 -24 55 -43 30 -19 54 -38 55 -42 0
-5 5 -8 11 -8 11 0 92 -60 97 -72 2 -5 10 -8 18 -8 8 0 14 -4 14 -10 0 -5 7
-10 15 -10 8 0 15 -4 15 -10 0 -5 7 -10 15 -10 8 0 15 -4 15 -10 0 -5 6 -10
14 -10 8 0 16 -3 18 -8 4 -9 202 -150 223 -158 15 -6 52 13 84 44 9 9 31 28
49 42 18 14 45 36 61 50 57 52 91 80 96 80 3 0 16 10 28 23 12 12 47 43 77 67
67 55 95 79 124 105 12 11 41 35 64 53 22 19 50 41 60 50 11 10 34 28 52 42
17 13 47 38 65 55 18 16 50 44 70 60 21 17 47 39 59 50 12 11 45 38 72 60 27
22 65 54 84 72 19 18 41 33 48 33 6 0 12 7 12 15 0 8 4 15 8 15 5 0 18 8 30
17 41 35 108 91 187 158 26 22 58 50 71 63 13 12 25 22 28 22 6 0 44 33 91 78
13 12 27 22 30 22 3 0 13 8 23 17 10 10 40 36 67 58 26 22 59 49 71 60 12 11
39 34 60 50 20 17 44 37 53 46 9 8 39 33 66 55 28 21 52 42 55 45 3 3 34 30
70 60 36 29 70 58 76 64 6 5 30 26 54 45 25 19 62 51 84 70 23 19 45 38 51 43
5 4 21 17 35 30 14 12 45 38 69 57 24 19 56 46 71 60 15 14 43 37 62 52 19 15
45 37 59 50 14 13 45 39 69 58 24 19 61 51 83 70 22 19 62 52 89 72 28 21 46
38 42 38 -5 1 1 6 12 13 21 12 69 52 162 134 26 24 53 43 60 43 6 0 12 7 12
15 0 8 4 15 10 15 10 0 27 14 98 78 21 18 58 49 85 69 26 21 47 41 47 45 0 4
5 8 10 8 6 0 18 8 28 17 31 30 85 77 117 101 17 13 50 41 75 62 40 35 154 131
219 185 13 11 58 49 101 85 84 71 84 70 215 179 50 41 97 81 106 90 9 9 25 23
36 31 26 21 137 113 143 120 5 5 118 99 135 113 6 4 21 17 35 30 14 12 45 38
69 57 24 19 48 40 55 45 6 6 38 33 71 60 33 28 67 58 76 67 9 10 19 18 23 18
4 0 21 13 39 29 34 32 160 139 242 206 70 57 104 87 131 114 13 13 24 21 24
18 0 -4 15 8 33 26 19 18 49 43 67 57 18 14 43 34 55 45 12 11 41 36 66 55 24
19 53 44 64 55 11 11 36 32 55 47 19 15 47 37 61 50 15 13 46 39 69 58 132
108 133 110 128 165 -5 64 -34 105 -96 136 -26 13 -49 24 -52 24 -3 0 -12 5
-20 10 -8 5 -60 32 -115 60 -102 52 -117 60 -170 88 -29 15 -51 57 -61 117 -4
29 -8 44 -19 85 -5 16 -9 39 -10 50 -1 11 -5 36 -8 55 -4 19 -10 49 -13 65 -7
41 -11 68 -18 150 -4 39 -9 90 -12 115 -6 50 -6 368 0 415 2 17 7 62 11 100 8
80 9 87 20 138 4 20 10 37 14 37 4 0 20 12 38 28 40 35 59 51 108 87 22 16 47
36 57 45 9 8 31 26 49 40 18 14 58 45 89 70 31 25 69 54 85 65 69 49 85 72 85
120 0 65 -34 115 -102 148 -29 14 -93 44 -143 67 -49 23 -112 52 -140 65 -54
25 -137 64 -308 144 -59 28 -109 51 -112 51 -2 0 -50 22 -105 49 -55 28 -103
50 -105 51 -5 1 -84 37 -230 105 -171 80 -233 109 -295 138 -36 17 -67 31 -70
32 -44 15 -70 29 -70 38 0 6 -3 8 -6 4 -4 -3 -27 5 -53 18 -76 39 -146 69
-153 67 -5 -1 -8 3 -8 10 0 6 -3 9 -6 6 -3 -4 -31 6 -62 22 -70 34 -202 97
-302 142 -41 19 -102 48 -135 64 -33 16 -62 29 -65 29 -3 0 -40 18 -83 38
-106 51 -191 91 -197 92 -3 1 -43 19 -90 42 -47 22 -119 57 -161 76 -115 53
-173 80 -291 136 -59 28 -109 51 -111 51 -3 0 -65 29 -138 63 -155 74 -171 81
-181 79 -5 -1 -8 3 -8 8 0 6 -4 10 -9 10 -5 0 -51 20 -102 44 -157 73 -209 96
-219 96 -6 0 -10 5 -10 10 0 6 -5 10 -12 10 -6 0 -49 18 -94 40 -46 22 -88 40
-93 40 -6 0 -11 5 -11 12 0 6 -3 9 -6 6 -3 -4 -41 11 -85 33 -43 21 -81 39
-83 39 -3 0 -49 20 -103 45 -132 62 -147 69 -153 76 -9 10 -94 30 -121 27 -14
-1 -45 -17 -70 -34z"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.2 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

2
static/js/bundle.js Normal file

File diff suppressed because one or more lines are too long

1
static/js/bundle.js.map Normal file

File diff suppressed because one or more lines are too long