diff --git a/www/data/images/program_img/ffsclient.png b/www/data/images/program_img/ffsclient.png new file mode 100644 index 0000000..53e199e Binary files /dev/null and b/www/data/images/program_img/ffsclient.png differ diff --git a/www/statics/programs/__all.php b/www/statics/programs/__all.php index afeb35b..b8e4634 100644 --- a/www/statics/programs/__all.php +++ b/www/statics/programs/__all.php @@ -752,4 +752,23 @@ return 'download' => 'https://github.com/Mikescher/better-docker-ps/releases', ], ], + + + [ + 'name' => 'firefox-sync-client', + 'internal_name' => 'ffsclient', + 'internal_name_alt' => null, + 'category' => 'Commandline', + 'stars' => 4, + 'ui_language' => 'English', + 'prog_language' => 'Go', + 'short_description' => 'A cli for firefox-sync (firefox bookmarks, passwords, account, ...)', + 'add_date' => '2022-11-11', + 'license' => 'Apache-2.0', + 'urls' => + [ + 'github' => 'https://github.com/Mikescher/firefox-sync-client', + 'download' => 'https://github.com/Mikescher/firefox-sync-client/releases/latest', + ], + ], ]; \ No newline at end of file diff --git a/www/statics/programs/ffsclient_description.md b/www/statics/programs/ffsclient_description.md new file mode 100644 index 0000000..820206d --- /dev/null +++ b/www/statics/programs/ffsclient_description.md @@ -0,0 +1,345 @@ +ffsclient - firefox-sync-client +=============================== + +A commandline-utility to list/view/edit/delete entries in a firefox-sync account. +Can be used to access bookmarks, passwords or custom data. + + + +Table of contents +================= +* [Installation](#installation) +* [Usage](#usage) +* [Examples](#example) + * [Get all bookmarks as json](#get-all-bookmarks-as-json) + * [Get all bookmarks in netscape format (same as firefox bookmarks.html)](#get-all-bookmarks-in-netscape-format-same-as-firefox-bookmarkshtml) + * [Get a single bookmark](#get-a-single-bookmark) + * [Create a new bookmark](#create-a-new-bookmark) + * [List all passwords](#list-all-passwords) + * [List deleted passwords](#list-deleted-passwords) + * [Add a new password](#add-a-new-password) + * [Delete any record](#delete-any-record) + * [Query the server without a session file](#query-the-server-without-a-session-file) + * [Create and read unencrypted records](#create-and-read-unencrypted-records) +* [Delete a password](#manual) +* [Request Flowchart](#request-flowchart) + + +Installation +============ + +The latest binary (windows/linux/macOS/FreeBSD/OpenBSD) can be downloaded from the [github releases page](https://github.com/Mikescher/firefox-sync-client/releases):. + +https://github.com/Mikescher/firefox-sync-client/releases/latest + +ffsclient does not have any dependencies and can be placed directly in your $PATH (eg /usr/local/bin). + +  + +Alternatively you can use one of the following package manager: +- [Arch User Repository](https://aur.archlinux.org/packages/ffsclient): `yay -S ffsclient-git` / `yay -S ffsclient-bin` +- [Homebrew](https://formulae.brew.sh/formula/ffsclient): `brew tap Mikescher/tap && brew install ffsclient` +- [Chocolatey](https://community.chocolatey.org/packages/ffsclient): `choco install ffsclient` + +Usage +===== + +Before the first use you have to authenticate your client and create a session. +Call `ffsclient {username} {password}` and a session will be created in `~/.config/firefox-sync-client.secret` + +After this you can freely use ffsclient (see the full [Manual](#manual) for all commands). +Common commands are `ffsclient collections` to list all collections in the current account, `ffsclient list {collection}` to list all records in a collection and `ffsclient get {collection} {record-id}` to get a single record. + +Almost all commands support different output-formats that can be specified with `--format {fmt}`, available are `text`, `json`, `xml`, `table`, `netscape`. If no format is supplied the command uses a default. + +You can get an overview of all commands by invoking `ffsclient --help` and a command-specific help with `ffsclient {command} --help` + +For some collections (like `bookmarks`, `passwords`, `forms`, `history`) are specific subcommands available. +For example you can list your bookmarks with `ffsclient bookmarks list`, this is preferable to the general `ffsclient list {collection}` call, because the bookmark-data in the records gets directly parsed and properly displayed. + +Example +======= + +Here I try to show some common usage patterns: + +Get all bookmarks as json +------------------------- +``` +$ ./ffsclient bookmarks list --format json --output bookmarks.json --ignore-schema-errors +$ ./ffsclient bookmarks list --format json --output bookmarks.json --ignore-schema-errors --minimized-json +``` +*`--ignore-schema-errors` skips records that are in the bookmarks collection but do not contain valid data* + +Get all bookmarks in netscape format (same as firefox bookmarks.html) +--------------------------------------------------------------------- +``` +$ ./ffsclient bookmarks list --format netscape +``` + +Get a single bookmark +--------------------- +``` +$ ./ffsclient get bookmarks "{bookmark_id}" --decoded --format json --pretty-print +``` +The `--pretty-print` flag does format the json in the record payload, the surrounding json (from `--format json`) is pretty-printed by default. +If you don't want to have the envelope pretty-printed use the `--minimized-json` flag + +Create a new bookmark +--------------------- +``` +$ ./ffsclient bookmarks create "{title}" "{url}" +$ ./ffsclient bookmarks create "{title}" "{url}" --parent "{parent-record-id}" +$ ./ffsclient bookmarks create "{title}" "{url}" --parent "{parent-record-id}" --position "{index}" +``` +By default bookmarks are created at the top-level and at the last position in the parent folder. + +List all passwords +------------------ +``` +$ ./ffsclient passwords list --ignore-schema-errors +$ ./ffsclient passwords list --show-passwords +``` +By default passwords are hidden to prevent accidental leaks. + +List deleted passwords +---------------------- +``` +$ ./ffsclient passwords list --only-deleted +``` +Also useful is the `--include-deleted` flag to show both, deleted and normal entries. +Also works with other list commands + +Add a new password +------------------ +``` +$ ./ffsclient passwords create "{url}" "{username}" "{password}" +``` + +Delete a password +------------------ +``` +$ ./ffsclient passwords delete "{url}" +$ ./ffsclient passwords delete "{record-id}" +``` + +Delete any record +------------------ +``` +$ ./ffsclient delete "{record-id}" +$ ./ffsclient delete "{record-id}" --hard +``` +*By default the sync protocol needs tombstones. This means deleted records still exist, without their payload and wit a deleted:true flag* +*If the `--hard` flag is supplied, the record is instead completely deleted from the server* + +Query the server without a session file +--------------------------------------- +``` +$ ./ffsclient collections --auth-login-email "{username}" --auth-login-password "{password}" +``` +This does not use the normal session file an creates a completely new session for this command only. +This is genrally **not** recommended to do. Your request will look like a new client to the server, it can happen that you have to allow it via email and it is also much more inefficient. +If you don't want a session file in your home folder use `--sessionfile` to specify a more secure location + +Create and read unencrypted records +----------------------------------- +``` +$ ./ffsclient create "{collection}" "{id}" --raw "hello world" +$ ./ffsclient get "{collection}" "{id}" --raw --format json +$ ./ffsclient get "{collection}" "{id}" --raw --format text --data-only +``` +Normally records have an encrypted payload that needs to be decrypted before it can be read (via the `--decrypted` flag in `ffsclient get`). +But you can also directly write data in the payload field. +The `--raw` flag in `ffsclient create` skips the normal encryption step and the `--raw` flag in `ffsclient get` skips the decryption. +This is only recommended for custom collections, you should never write invalid data in one of teh default collections (e.g. `bookmarks`, `passwords`, etc) + +Manual +====== + +*(copied from v1.2.0)* + +*If I forgot to update the README you can always get the current version of the help with `./ffsclient --help`* + +``` +firefox-sync-client. + +# (Use `ffsclient --help` for more detailed info) + +Basic Usage: + ffsclient login Login to FF-Sync account, uses ~/.config as default session location + [--device-name=] + [--device-type=] + ffsclient refresh [--force] Refresh the current session token (BID Assertion) + ffsclient check-session Verify that the current session is valid + ffsclient collections List all available collections + [--usage] # Include usage (storage space) + ffsclient quota Query the storage quota of the current user + ffsclient list Get a all records in a collection (use --format to define the format) + (--raw | --decoded | --ids) # Return raw data, decoded payload, or only IDs + [--after ] # Return only fields updated after this date + [--sort ] # Sort the result by (newest|index|oldest) + [--limit ] # Return max elements + [--offset ] # Skip the first elements + [--pretty-print | --pp] # Pretty-Print json in decoded data / payload (if possible) + ffsclient get Get a single record + (--raw | --decoded) # Return raw data or decoded payload + [--pretty-print | --pp] # Pretty-Print json in decoded data / payload (if possible) + [--data-only] # Only return the payload +ffsclient delete [--hard] Delete the specified record + ffsclient delete Delete all the records in a collection + ffsclient delete-all --force Delete all (!) records in the server + ffsclient create Insert a new record + (--raw | --data | --raw-stdin | --data-stdin) # The new data + ffsclient update Update an existing record + (--raw | --data | --raw-stdin | --data-stdin) # The new data + [--create] # Create a new record if the specified record-id does not exist + ffsclient meta Get storage metadata + ffsclient --help Output specific help for a single subcommand + +Usage: + ffsclient bookmarks list List bookmarks (use --format to define the format) + [--ignore-schema-errors] # Skip records that cannot be decoded into a bookmark schema + [--after ] # Return only fields updated after this date + [--sort ] # Sort the result by (newest|index|oldest) + [--limit ] # Return max elements + [--offset ] # Skip the first elements + [--include-deleted] # Show deleted entries + [--only-deleted] # Show only deleted entries + [--type ] # Show only entries with the specified type + [--parent ] # Show only entries with the specified parent (by record-id), can be specified multiple times + [--linear # Do not output the folder hierachy + ffsclient bookmarks delete Delete the specified bookmark + ffsclient bookmarks create bookmark <url> Insert a new bookmark + [--description <desc>] # Specify the bookmark description + [--load-in-sidebar] # If specified the `LoadInSidebar` field is set to true (default is false) + [--tag <tag>] # Add a tag to the bookmark, specify multiple times to add multiple tags + [--keyword <kw>] # Specify the keyword (to activate the bookmark from the location bar) + [--parent <id>] # Specify the ID of the parent folder (if not specified the entry lives under `unfiled`) + [--position=<idx>] # The position of the entry in the parent (0 = first, default is last). Can use negative indizes. + ffsclient bookmarks create folder <title> Insert a new bookmark-folder + [--parent <id>] # Specify the ID of the parent folder (if not specified the entry lives under `unfiled`) + [--position=<idx>] # The position of the entry in the parent (0 = first, default is last). Can use negative indizes. + ffsclient bookmarks create separator Insert a new bookmark-separator + [--parent <id>] # Specify the ID of the parent folder (if not specified the entry lives under `unfiled`) + [--position=<idx>] # The position of the entry in the parent (0 = first, default is last). Can use negative indizes. + ffsclient bookmarks update <id> Partially update a bookmark + [--title <title>] # Change the bookmark title + [--url <url>] # Change the URL + [--description <desc>] # Change the bookmark description + [--load-in-sidebar <true|false>] # Set the `LoadInSidebar` field + [--tag <tag>] # Change the tags, specify multiple times to set multiple tags + [--keyword <kw>] # Specify the keyword (to activate the bookmark from the location bar) + [--position=<idx>] # Change the position of the entry in the parent (0 = first). Can use negative indizes. + ffsclient passwords list List passwords + [--show-passwords] # Show the actual passwords + [--ignore-schema-errors] # Skip records that cannot be decoded into a password schema + [--after <rfc3339>] # Return only fields updated after this date + [--sort <sort>] # Sort the result by (newest|index|oldest) + [--limit <n>] # Return max <n> elements + [--offset <o>] # Skip the first <n> elements + [--include-deleted] # Show deleted entries + [--only-deleted] # Show only deleted entries + ffsclient passwords delete <host|id> [--hard] Delete a single password + [--is-host | --is-exact-host | --is-id] # Specify that the supplied argument is a host / record-id (otherwise both is possible) + ffsclient passwords create <host> <username> <password> Insert a new password + [--form-submit-url <url>] # Specify the submission URL (GET/POST url set by <form>) + [--http-realm <realm>] # Specify the HTTP Realm (HTTP Realm for which the login is valid) + [--username-field <name>] # Specify the Username field (HTML field name of the username) + [--password-field <name>] # Specify the Password field (HTML field name of the password) + ffsclient passwords update <host|id> Update an existing password + [--is-host | --is-exact-host | --is-id] # Specify that the supplied argument is a host / record-id (otherwise both is possible) + [--host <url>] # Update the host field + [--username <user>] # Update the username + [--password <pass>] # Update the password + [--form-submit-url <url>] # Update the submission URL (GET/POST url set by <form>) + [--http-realm <realm>] # Update the HTTP Realm (HTTP Realm for which the login is valid) + [--username-field <name>] # Update the Username field (HTML field name of the username) + [--password-field <name>] # Update the Password field (HTML field name of the password) + ffsclient passwords get <host|id> Insert a new password + [--is-host | --is-exact-host | --is-id] # Specify that the supplied argument is a host / record-id (otherwise both is possible) + ffsclient forms list List form autocomplete suggestions + [--name <n>] # Show only entries with the specified name + [--ignore-schema-errors] # Skip records that cannot be decoded into a form schema + [--after <rfc3339>] # Return only fields updated after this date + [--sort <sort>] # Sort the result by (newest|index|oldest) + [--limit <n>] # Return max <n> elements + [--offset <o>] # Skip the first <n> elements + [--include-deleted] # Show deleted entries + [--only-deleted] # Show only deleted entries + ffsclient forms get <name> [--ignore-case] Get all HTML-Form autocomplete suggestions for this name + ffsclient forms create <name> <value> Adds a new HTML-Form autocomplete suggestions + ffsclient forms delete <id> [--hard] Delete the specified HTML-Form autocomplete suggestion + ffsclient history list List form history entries + [--ignore-schema-errors] # Skip records that cannot be decoded into a history schema + [--after <rfc3339>] # Return only fields after this date + [--sort <sort>] # Sort the result by (newest|index|oldest) + [--limit <n>] # Return max <n> elements + [--offset <o>] # Skip the first <n> elements + [--include-deleted] # Show deleted entries + [--only-deleted] # Show only deleted entries + ffsclient history delete <id> [--hard] Delete the specified history entry + +Hint: + # If you need to supply a record-id / collection that starts with an minus, use the --!arg=... syntax + # e.g.: `ffsclient get bookmarks --!arg=-udhG86-JgpUx --decoded` + # Also if you need to supply a argument that starts with an - use the --arg=value syntax + # e.g.: `ffsclient bookmarks add Test "https://example.org" --parent toolbar --position=-3` + +Common Options: + -h, --help Show this screen. + --version Show version. + -v, --verbose Output more intermediate information + -q, --quiet Do not print anything + -f <fmt>, --format <fmt> Specify the output format (not all subcommands support all output-formats) + # - 'text' + # - 'json' + # - 'netscape' (default firefox bookmarks format) + # - 'xml' + # - 'table' + --auth-server <url> Specify the (authentication) server-url + --token-server <url> Specify the (token) server-url + --request-retry-delay-certerr <sec> Retry delay for requests that had a certificate error (default: 5 sec) + --request-retry-delay-floodcontrol <sec> Retry delay for requests that were throttled by the server (default: 15 sec) + --request-retry-delay-servererr <sec> Retry delay for requests that failed due to server errors (default: 1 sec) + --request-retry-max <num> Max request retries (default: 5) + --request-timeout <sec> Timeout for API request (default 10 sec) + --color Enforce colored output + --no-color Disable colored output + --timezone <tz> Specify the output timezone + # Can be either: + # - UTC + # - Local (default) + # - IANA Time Zone, e.g. 'America/New_York' + --timeformat <url> Specify the output timeformat (golang syntax) + -o <f>, --output <f> Write the output to a file + --sessionfile <cfg> Specify the location of the saved session + --auth-login-email <email> Login with the sync server without using the saved session (enforces a new, temporary session) + --auth-login-password <pw> Login with the sync server without using the saved session (enforces a new, temporary session) + --no-autosave-session Do not update the sessionfile if the session was auto-refreshed + --force-refresh-session Always auto-refresh the session, even if its not expired + --no-xml-declaration Do not print the xml declaration when using `--format xml` + --minimized-json Do not indent (pretty-print) json output when using `--format json` + +Exit Codes: + 0 Program exited successfully + 60 Program existed with an (unspecified) error + 61 Program crashed + 62 Program called without arguments + 63 Failed to parse commandline arguments + 64 Command needs a valid session/session-file and none was found + 65 The current subcommand does not support the specified output format + 66 Record with this ID not found + + 81 (check-session): The session is not valid + 82 (passwords): No matching password found + 83 (create-bookmarks): Parent record is not a folder + 84 (create-bookmarks): The position in the parent would be out of bounds + 85 (update-bookmarks): One of the specified fields is not valid on the record type +``` + + + + +Request Flowchart +================= + +![FFSync-Flowchart](https://raw.githubusercontent.com/Mikescher/firefox-sync-client/master/_data/readme-data/api-flow.svg)