You've already forked LibreTranslate
							
							
				mirror of
				https://github.com/LibreTranslate/LibreTranslate.git
				synced 2025-10-30 23:37:48 +02:00 
			
		
		
		
	Add pre-commit to automatically run formatting when committing
This commit is contained in:
		
							
								
								
									
										28
									
								
								.pre-commit-config.yaml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										28
									
								
								.pre-commit-config.yaml
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,28 @@ | ||||
| # See https://pre-commit.com for more information | ||||
| repos: | ||||
|   - repo: https://github.com/pre-commit/pre-commit-hooks | ||||
|     rev: v4.4.0 | ||||
|     hooks: | ||||
|     - id: check-added-large-files | ||||
|       name: " 🐘 Check for added large files" | ||||
|     - id: check-toml | ||||
|       name: " ✔️  Check TOML" | ||||
|     - id: check-yaml | ||||
|       name: " ✔️  Check YAML" | ||||
|       args: | ||||
|       - --unsafe | ||||
|     - id: check-json | ||||
|       name: " ✔️  Check JSON" | ||||
|     - id: trailing-whitespace | ||||
|       name: " ✂️  Trim trailing whitespaces" | ||||
|   - repo: https://github.com/charliermarsh/ruff-pre-commit | ||||
|     rev: v0.0.277 | ||||
|     hooks: | ||||
|       - id: ruff | ||||
|         name: " ⚡️ Formatting code with Ruff" | ||||
|         args: | ||||
|         - --fix | ||||
|  | ||||
| ci: | ||||
|     autofix_commit_msg: 🎨 [pre-commit] Auto format | ||||
|     autoupdate_commit_msg: ⬆ [pre-commit] pre-commit auto update | ||||
| @@ -33,6 +33,8 @@ git clone https://github.com/LibreTranslate/LibreTranslate.git | ||||
| cd LibreTranslate | ||||
| ``` | ||||
|  | ||||
| Hatch will automatically install the required dependencies in a virtual environment, and enable [`pre-commit`](https://pre-commit.com/), which will run before each commit to run formatting. | ||||
|  | ||||
| Run in development: | ||||
|  | ||||
| ```bash | ||||
| @@ -72,6 +74,12 @@ You can also run the tests on multiple python versions: | ||||
| hatch run all:test | ||||
| ``` | ||||
|  | ||||
| You can clean the virtual environment with: | ||||
|  | ||||
| ```bash | ||||
| hatch env prune | ||||
| ``` | ||||
|  | ||||
| ## Run with Docker | ||||
|  | ||||
| Linux/macOS: `./run.sh [args]` | ||||
| @@ -125,4 +133,4 @@ This occurs when your operating system depends on and manages Python for core fu | ||||
| This prevents pip packages from being installed system-wide. This way, there are no risks of pip packages conflicting between multiple projects or the operating system. | ||||
|  | ||||
| References: | ||||
| * [Python venv documentation](https://docs.python.org/library/venv.html)  | ||||
| * [Python venv documentation](https://docs.python.org/library/venv.html) | ||||
|   | ||||
							
								
								
									
										4
									
								
								k8s.yaml
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								k8s.yaml
									
									
									
									
									
								
							| @@ -1,4 +1,4 @@ | ||||
| # kubernetes deployment template  | ||||
| # kubernetes deployment template | ||||
| # prepare a namespace on your cluster first like libretranslate-prod | ||||
| apiVersion: v1 | ||||
| kind: ConfigMap | ||||
| @@ -41,7 +41,7 @@ spec: | ||||
|           valueFrom: | ||||
|             configMapKeyRef: | ||||
|               name: libretranslate-config | ||||
|               key: ltapikey               | ||||
|               key: ltapikey | ||||
| --- | ||||
| apiVersion: v1 | ||||
| kind: Service | ||||
|   | ||||
| @@ -170,7 +170,7 @@ _default_options_objects = [ | ||||
|         'name': 'UPDATE_MODELS', | ||||
|         'default_value': False, | ||||
|         'value_type': 'bool' | ||||
|     },     | ||||
|     }, | ||||
|     { | ||||
|         'name': 'METRICS', | ||||
|         'default_value': False, | ||||
|   | ||||
| @@ -44,7 +44,7 @@ def get_alternate_locale_links(): | ||||
|     tmpl = os.environ.get("LT_LOCALE_LINK_TEMPLATE") | ||||
|     if tmpl is None: | ||||
|         return [] | ||||
|      | ||||
|  | ||||
|     locales = get_available_locale_codes() | ||||
|     result = [] | ||||
|     for l in locales: | ||||
|   | ||||
| @@ -8,6 +8,6 @@ class Limiter: | ||||
|             return f(*args, **kwargs) | ||||
|  | ||||
|         return wrapper | ||||
|      | ||||
|  | ||||
|     def init_app(self, app): | ||||
|         pass | ||||
|   | ||||
| @@ -18,7 +18,7 @@ def setup(args): | ||||
|  | ||||
|         if args.api_keys and args.require_api_key_secret: | ||||
|             scheduler.add_job(func=rotate_secrets, trigger="interval", minutes=30) | ||||
|          | ||||
|  | ||||
|         scheduler.start() | ||||
|  | ||||
|         # Shut down the scheduler when exiting the app | ||||
|   | ||||
| @@ -12,7 +12,7 @@ def rotate_secrets(): | ||||
|     secret_1 = s.get_str("secret_1") | ||||
|     s.set_str("secret_0", secret_1) | ||||
|     s.set_str("secret_1", generate_secret()) | ||||
|      | ||||
|  | ||||
|  | ||||
| def secret_match(secret): | ||||
|     s = get_storage() | ||||
|   | ||||
| @@ -31,22 +31,22 @@ class Storage: | ||||
|         raise Exception("not implemented") | ||||
|     def dec_hash_int(self, ns, key): | ||||
|         raise Exception("not implemented") | ||||
|      | ||||
|  | ||||
|     def get_hash_keys(self, ns): | ||||
|         raise Exception("not implemented") | ||||
|     def del_hash(self, ns, key): | ||||
|         raise Exception("not implemented") | ||||
|      | ||||
|  | ||||
| class MemoryStorage(Storage): | ||||
|     def __init__(self): | ||||
|         self.store = {} | ||||
|      | ||||
|  | ||||
|     def exists(self, key): | ||||
|         return key in self.store | ||||
|  | ||||
|     def set_bool(self, key, value): | ||||
|         self.store[key] = bool(value) | ||||
|      | ||||
|  | ||||
|     def get_bool(self, key): | ||||
|         return bool(self.store[key]) | ||||
|  | ||||
| @@ -55,10 +55,10 @@ class MemoryStorage(Storage): | ||||
|  | ||||
|     def get_int(self, key): | ||||
|         return int(self.store.get(key, 0)) | ||||
|      | ||||
|  | ||||
|     def set_str(self, key, value): | ||||
|         self.store[key] = value | ||||
|      | ||||
|  | ||||
|     def get_str(self, key): | ||||
|         return str(self.store.get(key, "")) | ||||
|  | ||||
| @@ -74,7 +74,7 @@ class MemoryStorage(Storage): | ||||
|     def inc_hash_int(self, ns, key): | ||||
|         if ns not in self.store: | ||||
|             self.store[ns] = {} | ||||
|          | ||||
|  | ||||
|         if key not in self.store[ns]: | ||||
|             self.store[ns][key] = 0 | ||||
|         else: | ||||
| @@ -83,7 +83,7 @@ class MemoryStorage(Storage): | ||||
|     def dec_hash_int(self, ns, key): | ||||
|         if ns not in self.store: | ||||
|             self.store[ns] = {} | ||||
|          | ||||
|  | ||||
|         if key not in self.store[ns]: | ||||
|             self.store[ns][key] = 0 | ||||
|         else: | ||||
| @@ -103,13 +103,13 @@ class RedisStorage(Storage): | ||||
|     def __init__(self, redis_uri): | ||||
|         self.conn = redis.from_url(redis_uri) | ||||
|         self.conn.ping() | ||||
|      | ||||
|  | ||||
|     def exists(self, key): | ||||
|         return bool(self.conn.exists(key)) | ||||
|  | ||||
|     def set_bool(self, key, value): | ||||
|         self.conn.set(key, "1" if value else "0") | ||||
|      | ||||
|  | ||||
|     def get_bool(self, key): | ||||
|         return bool(self.conn.get(key)) | ||||
|  | ||||
| @@ -122,24 +122,24 @@ class RedisStorage(Storage): | ||||
|             return 0 | ||||
|         else: | ||||
|             return v | ||||
|      | ||||
|  | ||||
|     def set_str(self, key, value): | ||||
|         self.conn.set(key, value) | ||||
|      | ||||
|  | ||||
|     def get_str(self, key): | ||||
|         v = self.conn.get(key) | ||||
|         if v is None: | ||||
|             return "" | ||||
|         else: | ||||
|             return v.decode('utf-8') | ||||
|      | ||||
|  | ||||
|     def get_hash_int(self, ns, key): | ||||
|         v = self.conn.hget(ns, key) | ||||
|         if v is None: | ||||
|             return 0 | ||||
|         else: | ||||
|             return int(v) | ||||
|      | ||||
|  | ||||
|     def set_hash_int(self, ns, key, value): | ||||
|         self.conn.hset(ns, key, value) | ||||
|  | ||||
|   | ||||
| @@ -65,7 +65,7 @@ ltmanage = "libretranslate.manage:manage" | ||||
| test = [ | ||||
|     "pytest >=7.2.0", | ||||
|     "pytest-cov", | ||||
|     "ruff ==0.0.277", | ||||
|     "pre-commit >=3.0.0", | ||||
|     "types-requests", | ||||
| ] | ||||
|  | ||||
| @@ -83,13 +83,16 @@ History = "https://github.com/LibreTranslate/LibreTranslate/releases" | ||||
| features = [ | ||||
|     "test", | ||||
| ] | ||||
| post-install-commands = [ | ||||
|     "pre-commit install", | ||||
| ] | ||||
|  | ||||
|  | ||||
| [tool.hatch.envs.default.scripts] | ||||
| dev = "python main.py {args}" | ||||
| locales = "python scripts/compile_locales.py" | ||||
| fmt = [ | ||||
|     "ruff libretranslate scripts --fix", | ||||
|     "pre-commit run --all --all-files", | ||||
| ] | ||||
| test = [ | ||||
|     "fmt", | ||||
|   | ||||
| @@ -36,7 +36,7 @@ def on_starting(server): | ||||
|             sys.argv.append(kwargs[k]) | ||||
|  | ||||
|     args = get_args() | ||||
|      | ||||
|  | ||||
|     from libretranslate import flood, scheduler, secret, storage | ||||
|     storage.setup(args.shared_storage) | ||||
|     scheduler.setup(args) | ||||
|   | ||||
| @@ -25,19 +25,19 @@ if __name__ == "__main__": | ||||
|  | ||||
|     con = sqlite3.connect(args.db, check_same_thread=False) | ||||
|     cur = con.cursor() | ||||
|      | ||||
|  | ||||
|     with open(output_file, 'w', encoding="utf-8") as f: | ||||
|         for row in cur.execute('SELECT q, s, source, target FROM suggestions WHERE source != "auto" ORDER BY source'): | ||||
|             q, s, source, target = row | ||||
|             obj = { | ||||
|                 'q': q, | ||||
|                 's': s,  | ||||
|                 's': s, | ||||
|                 'source': source, | ||||
|                 'target': target | ||||
|             } | ||||
|             json.dump(obj, f, ensure_ascii=False) | ||||
|             f.write('\n') | ||||
|      | ||||
|  | ||||
|     print("Wrote %s" % output_file) | ||||
|  | ||||
|     if args.clear: | ||||
|   | ||||
| @@ -54,7 +54,7 @@ if __name__ == "__main__": | ||||
|  | ||||
|     messagespot = os.path.join(locales_dir, "messages.pot") | ||||
|     print("Updating %s" % messagespot) | ||||
|     sys.argv = ["", "extract", "-F", "babel.cfg", "-k", "_e _h",  | ||||
|     sys.argv = ["", "extract", "-F", "babel.cfg", "-k", "_e _h", | ||||
|                 "--copyright-holder", "LibreTranslate Authors", | ||||
|                 "--project", "LibreTranslate", | ||||
|                 "--version", get_version(), | ||||
| @@ -80,7 +80,7 @@ if __name__ == "__main__": | ||||
|                     'reviewed': False | ||||
|                 }, indent=4)) | ||||
|                 print("Wrote %s" % meta_file) | ||||
|      | ||||
|  | ||||
|     # Automatically translate strings with libretranslate | ||||
|     # when a language model is available and a string is empty | ||||
|  | ||||
| @@ -103,10 +103,10 @@ if __name__ == "__main__": | ||||
|             print("Translating '%s'" % locale) | ||||
|             pofile = polib.pofile(messages_file) | ||||
|             c = 0 | ||||
|              | ||||
|  | ||||
|             for entry in pofile.untranslated_entries(): | ||||
|                 text = entry.msgid | ||||
|                  | ||||
|  | ||||
|                 # Extract placeholders | ||||
|                 placeholders = re.findall(r'%\(?[^\)]*\)?s', text) | ||||
|  | ||||
| @@ -126,11 +126,11 @@ if __name__ == "__main__": | ||||
|                     else: | ||||
|                         # Meh, append | ||||
|                         translated += " " + placeholders[p] | ||||
|                  | ||||
|  | ||||
|                 print(entry.msgid, " --> ", translated) | ||||
|                 entry.msgstr = translated | ||||
|                 c += 1 | ||||
|              | ||||
|  | ||||
|             if c > 0: | ||||
|                 pofile.save(messages_file) | ||||
|                 print("Saved %s" % messages_file) | ||||
|   | ||||
		Reference in New Issue
	
	Block a user