From 1e2b45545b6c4148736ad87bfd8184c6b0f5085c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20G=C3=BCndling?= Date: Tue, 15 Oct 2024 14:42:19 +0200 Subject: [PATCH 01/28] motis v2 for routing, remove implicit paths (user), (maintainer) --- package-lock.json | 201 +++- package.json | 4 +- src/lib/api.ts | 45 - src/lib/motis/core/ApiError.ts | 21 + src/lib/motis/core/ApiRequestOptions.ts | 14 + src/lib/motis/core/ApiResult.ts | 7 + src/lib/motis/core/CancelablePromise.ts | 126 +++ src/lib/motis/core/OpenAPI.ts | 56 + src/lib/motis/core/request.ts | 374 +++++++ src/lib/motis/index.ts | 4 + src/lib/motis/schemas.gen.ts | 667 ++++++++++++ src/lib/motis/services.gen.ts | 92 ++ src/lib/motis/types.gen.ts | 959 ++++++++++++++++++ src/routes/+page.server.ts | 7 +- src/routes/api/booking/+server.ts | 74 +- .../+layout.server.ts | 0 .../+layout.svelte | 6 +- .../activation/+page.server.ts | 0 .../activation/+page.svelte | 2 + .../completed_tours/+page.server.ts | 0 .../completed_tours/+page.svelte | 0 src/routes/{(user) => user}/+layout.server.ts | 0 src/routes/{(user) => user}/+layout.svelte | 10 +- .../administration/+page.server.ts | 0 .../administration/+page.svelte | 0 .../{(user) => user}/company/+page.server.ts | 0 .../{(user) => user}/company/+page.svelte | 0 .../company/intersects.test.ts | 0 .../{(user) => user}/drivers/+page.server.ts | 0 .../{(user) => user}/drivers/+page.svelte | 0 .../{(user) => user}/taxi/+page.server.ts | 0 src/routes/{(user) => user}/taxi/+page.svelte | 2 +- .../{(user) => user}/taxi/AddVehicle.svelte | 0 src/routes/{(user) => user}/taxi/types.ts | 0 .../{(user) => user}/tours/+page.server.ts | 0 .../{(user) => user}/tours/+page.svelte | 0 36 files changed, 2592 insertions(+), 79 deletions(-) create mode 100644 src/lib/motis/core/ApiError.ts create mode 100644 src/lib/motis/core/ApiRequestOptions.ts create mode 100644 src/lib/motis/core/ApiResult.ts create mode 100644 src/lib/motis/core/CancelablePromise.ts create mode 100644 src/lib/motis/core/OpenAPI.ts create mode 100644 src/lib/motis/core/request.ts create mode 100644 src/lib/motis/index.ts create mode 100644 src/lib/motis/schemas.gen.ts create mode 100644 src/lib/motis/services.gen.ts create mode 100644 src/lib/motis/types.gen.ts rename src/routes/{(maintainer) => maintainer}/+layout.server.ts (100%) rename src/routes/{(maintainer) => maintainer}/+layout.svelte (80%) rename src/routes/{(maintainer) => maintainer}/activation/+page.server.ts (100%) rename src/routes/{(maintainer) => maintainer}/activation/+page.svelte (97%) rename src/routes/{(maintainer) => maintainer}/completed_tours/+page.server.ts (100%) rename src/routes/{(maintainer) => maintainer}/completed_tours/+page.svelte (100%) rename src/routes/{(user) => user}/+layout.server.ts (100%) rename src/routes/{(user) => user}/+layout.svelte (81%) rename src/routes/{(user) => user}/administration/+page.server.ts (100%) rename src/routes/{(user) => user}/administration/+page.svelte (100%) rename src/routes/{(user) => user}/company/+page.server.ts (100%) rename src/routes/{(user) => user}/company/+page.svelte (100%) rename src/routes/{(user) => user}/company/intersects.test.ts (100%) rename src/routes/{(user) => user}/drivers/+page.server.ts (100%) rename src/routes/{(user) => user}/drivers/+page.svelte (100%) rename src/routes/{(user) => user}/taxi/+page.server.ts (100%) rename src/routes/{(user) => user}/taxi/+page.svelte (99%) rename src/routes/{(user) => user}/taxi/AddVehicle.svelte (100%) rename src/routes/{(user) => user}/taxi/types.ts (100%) rename src/routes/{(user) => user}/tours/+page.server.ts (100%) rename src/routes/{(user) => user}/tours/+page.svelte (100%) diff --git a/package-lock.json b/package-lock.json index 094b5abe..1fcd655c 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8,6 +8,7 @@ "name": "prima-test", "version": "0.0.1", "dependencies": { + "@hey-api/client-fetch": "^0.4.2", "@lucia-auth/adapter-postgresql": "^3.1.2", "@node-rs/argon2": "^1.8.3", "@playwright/test": "^1.45.2", @@ -30,6 +31,7 @@ "zod": "^3.23.8" }, "devDependencies": { + "@hey-api/openapi-ts": "^0.53.11", "@sveltejs/adapter-auto": "^3.2.2", "@sveltejs/adapter-node": "^5.2.0", "@sveltejs/kit": "^2.5.18", @@ -80,6 +82,24 @@ "node": ">=6.0.0" } }, + "node_modules/@apidevtools/json-schema-ref-parser": { + "version": "11.7.0", + "resolved": "https://registry.npmjs.org/@apidevtools/json-schema-ref-parser/-/json-schema-ref-parser-11.7.0.tgz", + "integrity": "sha512-pRrmXMCwnmrkS3MLgAIW5dXRzeTv6GLjkjb4HmxNnvAKXN1Nfzp4KmGADBQvlVUcqi+a5D+hfGDLLnd5NnYxog==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jsdevtools/ono": "^7.1.3", + "@types/json-schema": "^7.0.15", + "js-yaml": "^4.1.0" + }, + "engines": { + "node": ">= 16" + }, + "funding": { + "url": "https://github.com/sponsors/philsturgeon" + } + }, "node_modules/@ark/schema": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/@ark/schema/-/schema-0.2.0.tgz", @@ -663,6 +683,119 @@ "@hapi/hoek": "^9.0.0" } }, + "node_modules/@hey-api/client-fetch": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/@hey-api/client-fetch/-/client-fetch-0.4.2.tgz", + "integrity": "sha512-9BqcLTjsM3rWbads3afJkELS86vK7EqJvYgT429EVS9IO/kN75HEka3Ay/k142xCHSfXOuOShMdDam3nbG8wVA==", + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/mrlubos" + } + }, + "node_modules/@hey-api/openapi-ts": { + "version": "0.53.11", + "resolved": "https://registry.npmjs.org/@hey-api/openapi-ts/-/openapi-ts-0.53.11.tgz", + "integrity": "sha512-PaO+o0jDhfHVS5SjtonP5CzP/NYoW8dVZUn8WthSgzpgPts8AiWYXplOyk5uEnM4ZxbkZbeTiREwaNLnJmXlTQ==", + "dev": true, + "license": "FSL-1.1-MIT", + "dependencies": { + "@apidevtools/json-schema-ref-parser": "11.7.0", + "c12": "2.0.1", + "commander": "12.1.0", + "handlebars": "4.7.8" + }, + "bin": { + "openapi-ts": "bin/index.cjs" + }, + "engines": { + "node": "^18.0.0 || >=20.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/mrlubos" + }, + "peerDependencies": { + "typescript": "^5.x" + } + }, + "node_modules/@hey-api/openapi-ts/node_modules/c12": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/c12/-/c12-2.0.1.tgz", + "integrity": "sha512-Z4JgsKXHG37C6PYUtIxCfLJZvo6FyhHJoClwwb9ftUkLpPSkuYqn6Tr+vnaN8hymm0kIbcg6Ey3kv/Q71k5w/A==", + "dev": true, + "license": "MIT", + "dependencies": { + "chokidar": "^4.0.1", + "confbox": "^0.1.7", + "defu": "^6.1.4", + "dotenv": "^16.4.5", + "giget": "^1.2.3", + "jiti": "^2.3.0", + "mlly": "^1.7.1", + "ohash": "^1.1.4", + "pathe": "^1.1.2", + "perfect-debounce": "^1.0.0", + "pkg-types": "^1.2.0", + "rc9": "^2.1.2" + }, + "peerDependencies": { + "magicast": "^0.3.5" + }, + "peerDependenciesMeta": { + "magicast": { + "optional": true + } + } + }, + "node_modules/@hey-api/openapi-ts/node_modules/chokidar": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.1.tgz", + "integrity": "sha512-n8enUVCED/KVRQlab1hr3MVpcVMvxtZjmEa956u+4YijlmQED223XMSYj2tLuKvr4jcCTzNNMpQDUer72MMmzA==", + "dev": true, + "license": "MIT", + "dependencies": { + "readdirp": "^4.0.1" + }, + "engines": { + "node": ">= 14.16.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/@hey-api/openapi-ts/node_modules/commander": { + "version": "12.1.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-12.1.0.tgz", + "integrity": "sha512-Vw8qHK3bZM9y/P10u3Vib8o/DdkvA2OtPtZvD871QKjy74Wj1WSKFILMPRPSdUSx5RFK1arlJzEtA4PkFgnbuA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + } + }, + "node_modules/@hey-api/openapi-ts/node_modules/jiti": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/jiti/-/jiti-2.3.3.tgz", + "integrity": "sha512-EX4oNDwcXSivPrw2qKH2LB5PoFxEvgtv2JgwW0bU858HoLQ+kutSvjLMUqBd0PeJYEinLWhoI9Ol0eYMqj/wNQ==", + "dev": true, + "license": "MIT", + "bin": { + "jiti": "lib/jiti-cli.mjs" + } + }, + "node_modules/@hey-api/openapi-ts/node_modules/readdirp": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.0.2.tgz", + "integrity": "sha512-yDMz9g+VaZkqBYS/ozoBJwaBhTbZo3UNYQHNRw1D3UFQB8oHB4uS/tAODO+ZLjGWmUbKnIlOWO+aaIiAxrUWHA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14.16.0" + }, + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + }, "node_modules/@humanwhocodes/config-array": { "version": "0.11.14", "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz", @@ -830,6 +963,13 @@ "@jridgewell/sourcemap-codec": "^1.4.14" } }, + "node_modules/@jsdevtools/ono": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/@jsdevtools/ono/-/ono-7.1.3.tgz", + "integrity": "sha512-4JQNk+3mVzK3xh2rqd6RB4J46qUR19azEHBneZyTZM+c456qOrbbM/5xcR8huNCCcbVt7+UmizG6GuUvPvKUYg==", + "dev": true, + "license": "MIT" + }, "node_modules/@lucia-auth/adapter-postgresql": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/@lucia-auth/adapter-postgresql/-/adapter-postgresql-3.1.2.tgz", @@ -3980,6 +4120,28 @@ "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", "dev": true }, + "node_modules/handlebars": { + "version": "4.7.8", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.8.tgz", + "integrity": "sha512-vafaFqs8MZkRrSX7sFVUdo3ap/eNiLnb4IakshzvP56X5Nr1iGKAIqdX6tMlm6HcNRIkr6AxO5jFEoJzzpT8aQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "minimist": "^1.2.5", + "neo-async": "^2.6.2", + "source-map": "^0.6.1", + "wordwrap": "^1.0.0" + }, + "bin": { + "handlebars": "bin/handlebars" + }, + "engines": { + "node": ">=0.4.7" + }, + "optionalDependencies": { + "uglify-js": "^3.1.4" + } + }, "node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -4794,6 +4956,13 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, + "node_modules/neo-async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", + "dev": true, + "license": "MIT" + }, "node_modules/node-fetch-native": { "version": "1.6.4", "resolved": "https://registry.npmjs.org/node-fetch-native/-/node-fetch-native-1.6.4.tgz", @@ -4916,10 +5085,11 @@ } }, "node_modules/ohash": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/ohash/-/ohash-1.1.3.tgz", - "integrity": "sha512-zuHHiGTYTA1sYJ/wZN+t5HKZaH23i4yI1HMwbuXm24Nid7Dv0KcuRlKoNKS9UNfAVSBlnGLcuQrnOKWOZoEGaw==", - "dev": true + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/ohash/-/ohash-1.1.4.tgz", + "integrity": "sha512-FlDryZAahJmEF3VR3w1KogSEdWX3WhA5GPakFx4J81kEAiHyLMpdLLElS8n8dfNadMgAne/MywcvmogzscVt4g==", + "dev": true, + "license": "MIT" }, "node_modules/once": { "version": "1.4.0", @@ -6384,7 +6554,7 @@ "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "optional": true, + "devOptional": true, "engines": { "node": ">=0.10.0" } @@ -7264,6 +7434,20 @@ "integrity": "sha512-UsUk3byDzKd04EyoZ7U4DOlxQaD14JUKQl6/P7wiX4FNvUfm3XL246n9W5AmqwW5RSFJ27NAuM0iLscAOYUiGQ==", "dev": true }, + "node_modules/uglify-js": { + "version": "3.19.3", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.19.3.tgz", + "integrity": "sha512-v3Xu+yuwBXisp6QYTcH4UbH+xYJXqnq2m/LtQVWKWzYc1iehYnLixoQDN9FH6/j9/oybfd6W9Ghwkl8+UMKTKQ==", + "dev": true, + "license": "BSD-2-Clause", + "optional": true, + "bin": { + "uglifyjs": "bin/uglifyjs" + }, + "engines": { + "node": ">=0.8.0" + } + }, "node_modules/undici-types": { "version": "6.19.8", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.19.8.tgz", @@ -7959,6 +8143,13 @@ "node": ">=0.10.0" } }, + "node_modules/wordwrap": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", + "integrity": "sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==", + "dev": true, + "license": "MIT" + }, "node_modules/wrap-ansi": { "version": "8.1.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.1.0.tgz", diff --git a/package.json b/package.json index 7d133dee..3f4647d2 100644 --- a/package.json +++ b/package.json @@ -17,6 +17,7 @@ "test:unit": "vitest" }, "devDependencies": { + "@hey-api/openapi-ts": "^0.53.11", "@sveltejs/adapter-auto": "^3.2.2", "@sveltejs/adapter-node": "^5.2.0", "@sveltejs/kit": "^2.5.18", @@ -45,6 +46,7 @@ }, "type": "module", "dependencies": { + "@hey-api/client-fetch": "^0.4.2", "@lucia-auth/adapter-postgresql": "^3.1.2", "@node-rs/argon2": "^1.8.3", "@playwright/test": "^1.45.2", @@ -66,4 +68,4 @@ "tailwind-variants": "^0.2.1", "zod": "^3.23.8" } -} +} \ No newline at end of file diff --git a/src/lib/api.ts b/src/lib/api.ts index ded802f0..16fed9c4 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -141,48 +141,3 @@ export const getRoute = async (query: RoutingQuery) => { return await response.json(); }; -export enum Direction { - Forward, - Backward -} - -export type oneToManyResult = { - duration: number; - distance: number; -}; - -export const oneToMany = async ( - one: Coordinates, - many: Coordinates[], - direction: Direction -): Promise => { - const dir = direction == Direction.Forward ? 'Forward' : 'Backward'; - const response = await fetch('https://europe.motis-project.de/', { - headers: { - 'Content-Type': 'application/json' - }, - body: JSON.stringify({ - destination: { - type: 'Module', - target: '/osrm/one_to_many' - }, - content_type: 'OSRMOneToManyRequest', - content: { - profile: 'car', - direction: dir, - one: { - lat: one.lat, - lng: one.lng - }, - many: many - } - }), - method: 'POST', - mode: 'cors' - }).then((res) => res.json()); - const result = response.content.costs; - if (result.length == 0) { - throw new Error('oneToMany api did not return any distTime-object.'); - } - return result; -}; diff --git a/src/lib/motis/core/ApiError.ts b/src/lib/motis/core/ApiError.ts new file mode 100644 index 00000000..9cf09496 --- /dev/null +++ b/src/lib/motis/core/ApiError.ts @@ -0,0 +1,21 @@ +import type { ApiRequestOptions } from './ApiRequestOptions'; +import type { ApiResult } from './ApiResult'; + +export class ApiError extends Error { + public readonly url: string; + public readonly status: number; + public readonly statusText: string; + public readonly body: unknown; + public readonly request: ApiRequestOptions; + + constructor(request: ApiRequestOptions, response: ApiResult, message: string) { + super(message); + + this.name = 'ApiError'; + this.url = response.url; + this.status = response.status; + this.statusText = response.statusText; + this.body = response.body; + this.request = request; + } +} diff --git a/src/lib/motis/core/ApiRequestOptions.ts b/src/lib/motis/core/ApiRequestOptions.ts new file mode 100644 index 00000000..2c83c55d --- /dev/null +++ b/src/lib/motis/core/ApiRequestOptions.ts @@ -0,0 +1,14 @@ +export type ApiRequestOptions = { + readonly method: 'GET' | 'PUT' | 'POST' | 'DELETE' | 'OPTIONS' | 'HEAD' | 'PATCH'; + readonly url: string; + readonly path?: Record; + readonly cookies?: Record; + readonly headers?: Record; + readonly query?: Record; + readonly formData?: Record; + readonly body?: any; + readonly mediaType?: string; + readonly responseHeader?: string; + readonly responseTransformer?: (data: unknown) => Promise; + readonly errors?: Record; +}; diff --git a/src/lib/motis/core/ApiResult.ts b/src/lib/motis/core/ApiResult.ts new file mode 100644 index 00000000..84b9f9da --- /dev/null +++ b/src/lib/motis/core/ApiResult.ts @@ -0,0 +1,7 @@ +export type ApiResult = { + readonly body: TData; + readonly ok: boolean; + readonly status: number; + readonly statusText: string; + readonly url: string; +}; diff --git a/src/lib/motis/core/CancelablePromise.ts b/src/lib/motis/core/CancelablePromise.ts new file mode 100644 index 00000000..f0face19 --- /dev/null +++ b/src/lib/motis/core/CancelablePromise.ts @@ -0,0 +1,126 @@ +export class CancelError extends Error { + constructor(message: string) { + super(message); + this.name = 'CancelError'; + } + + public get isCancelled(): boolean { + return true; + } +} + +export interface OnCancel { + readonly isResolved: boolean; + readonly isRejected: boolean; + readonly isCancelled: boolean; + + (cancelHandler: () => void): void; +} + +export class CancelablePromise implements Promise { + private _isResolved: boolean; + private _isRejected: boolean; + private _isCancelled: boolean; + readonly cancelHandlers: (() => void)[]; + readonly promise: Promise; + private _resolve?: (value: T | PromiseLike) => void; + private _reject?: (reason?: unknown) => void; + + constructor( + executor: ( + resolve: (value: T | PromiseLike) => void, + reject: (reason?: unknown) => void, + onCancel: OnCancel + ) => void + ) { + this._isResolved = false; + this._isRejected = false; + this._isCancelled = false; + this.cancelHandlers = []; + this.promise = new Promise((resolve, reject) => { + this._resolve = resolve; + this._reject = reject; + + const onResolve = (value: T | PromiseLike): void => { + if (this._isResolved || this._isRejected || this._isCancelled) { + return; + } + this._isResolved = true; + if (this._resolve) this._resolve(value); + }; + + const onReject = (reason?: unknown): void => { + if (this._isResolved || this._isRejected || this._isCancelled) { + return; + } + this._isRejected = true; + if (this._reject) this._reject(reason); + }; + + const onCancel = (cancelHandler: () => void): void => { + if (this._isResolved || this._isRejected || this._isCancelled) { + return; + } + this.cancelHandlers.push(cancelHandler); + }; + + Object.defineProperty(onCancel, 'isResolved', { + get: (): boolean => this._isResolved + }); + + Object.defineProperty(onCancel, 'isRejected', { + get: (): boolean => this._isRejected + }); + + Object.defineProperty(onCancel, 'isCancelled', { + get: (): boolean => this._isCancelled + }); + + return executor(onResolve, onReject, onCancel as OnCancel); + }); + } + + get [Symbol.toStringTag]() { + return 'Cancellable Promise'; + } + + public then( + onFulfilled?: ((value: T) => TResult1 | PromiseLike) | null, + onRejected?: ((reason: unknown) => TResult2 | PromiseLike) | null + ): Promise { + return this.promise.then(onFulfilled, onRejected); + } + + public catch( + onRejected?: ((reason: unknown) => TResult | PromiseLike) | null + ): Promise { + return this.promise.catch(onRejected); + } + + public finally(onFinally?: (() => void) | null): Promise { + return this.promise.finally(onFinally); + } + + public cancel(): void { + if (this._isResolved || this._isRejected || this._isCancelled) { + return; + } + this._isCancelled = true; + if (this.cancelHandlers.length) { + try { + for (const cancelHandler of this.cancelHandlers) { + cancelHandler(); + } + } catch (error) { + console.warn('Cancellation threw an error', error); + return; + } + } + this.cancelHandlers.length = 0; + if (this._reject) this._reject(new CancelError('Request aborted')); + } + + public get isCancelled(): boolean { + return this._isCancelled; + } +} diff --git a/src/lib/motis/core/OpenAPI.ts b/src/lib/motis/core/OpenAPI.ts new file mode 100644 index 00000000..8f77483d --- /dev/null +++ b/src/lib/motis/core/OpenAPI.ts @@ -0,0 +1,56 @@ +import type { ApiRequestOptions } from './ApiRequestOptions'; + +type Headers = Record; +type Middleware = (value: T) => T | Promise; +type Resolver = (options: ApiRequestOptions) => Promise; + +export class Interceptors { + _fns: Middleware[]; + + constructor() { + this._fns = []; + } + + eject(fn: Middleware): void { + const index = this._fns.indexOf(fn); + if (index !== -1) { + this._fns = [...this._fns.slice(0, index), ...this._fns.slice(index + 1)]; + } + } + + use(fn: Middleware): void { + this._fns = [...this._fns, fn]; + } +} + +export type OpenAPIConfig = { + BASE: string; + CREDENTIALS: 'include' | 'omit' | 'same-origin'; + ENCODE_PATH?: ((path: string) => string) | undefined; + HEADERS?: Headers | Resolver | undefined; + PASSWORD?: string | Resolver | undefined; + TOKEN?: string | Resolver | undefined; + USERNAME?: string | Resolver | undefined; + VERSION: string; + WITH_CREDENTIALS: boolean; + interceptors: { + request: Interceptors; + response: Interceptors; + }; +}; + +export const OpenAPI: OpenAPIConfig = { + BASE: 'https://demo.triptix.tech', + CREDENTIALS: 'include', + ENCODE_PATH: undefined, + HEADERS: undefined, + PASSWORD: undefined, + TOKEN: undefined, + USERNAME: undefined, + VERSION: '1', + WITH_CREDENTIALS: false, + interceptors: { + request: new Interceptors(), + response: new Interceptors() + } +}; diff --git a/src/lib/motis/core/request.ts b/src/lib/motis/core/request.ts new file mode 100644 index 00000000..3d09b2f4 --- /dev/null +++ b/src/lib/motis/core/request.ts @@ -0,0 +1,374 @@ +import { ApiError } from './ApiError'; +import type { ApiRequestOptions } from './ApiRequestOptions'; +import type { ApiResult } from './ApiResult'; +import { CancelablePromise } from './CancelablePromise'; +import type { OnCancel } from './CancelablePromise'; +import type { OpenAPIConfig } from './OpenAPI'; + +export const isString = (value: unknown): value is string => { + return typeof value === 'string'; +}; + +export const isStringWithValue = (value: unknown): value is string => { + return isString(value) && value !== ''; +}; + +export const isBlob = (value: any): value is Blob => { + return value instanceof Blob; +}; + +export const isFormData = (value: unknown): value is FormData => { + return value instanceof FormData; +}; + +export const base64 = (str: string): string => { + try { + return btoa(str); + } catch (err) { + // @ts-ignore + return Buffer.from(str).toString('base64'); + } +}; + +export const getQueryString = (params: Record): string => { + const qs: string[] = []; + + const append = (key: string, value: unknown) => { + qs.push(`${encodeURIComponent(key)}=${encodeURIComponent(String(value))}`); + }; + + const encodePair = (key: string, value: unknown) => { + if (value === undefined || value === null) { + return; + } + + if (value instanceof Date) { + append(key, value.toISOString()); + } else if (Array.isArray(value)) { + value.forEach((v) => encodePair(key, v)); + } else if (typeof value === 'object') { + Object.entries(value).forEach(([k, v]) => encodePair(`${key}[${k}]`, v)); + } else { + append(key, value); + } + }; + + Object.entries(params).forEach(([key, value]) => encodePair(key, value)); + + return qs.length ? `?${qs.join('&')}` : ''; +}; + +const getUrl = (config: OpenAPIConfig, options: ApiRequestOptions): string => { + const encoder = config.ENCODE_PATH || encodeURI; + + const path = options.url + .replace('{api-version}', config.VERSION) + .replace(/{(.*?)}/g, (substring: string, group: string) => { + if (options.path?.hasOwnProperty(group)) { + return encoder(String(options.path[group])); + } + return substring; + }); + + const url = config.BASE + path; + return options.query ? url + getQueryString(options.query) : url; +}; + +export const getFormData = (options: ApiRequestOptions): FormData | undefined => { + if (options.formData) { + const formData = new FormData(); + + const process = (key: string, value: unknown) => { + if (isString(value) || isBlob(value)) { + formData.append(key, value); + } else { + formData.append(key, JSON.stringify(value)); + } + }; + + Object.entries(options.formData) + .filter(([, value]) => value !== undefined && value !== null) + .forEach(([key, value]) => { + if (Array.isArray(value)) { + value.forEach((v) => process(key, v)); + } else { + process(key, value); + } + }); + + return formData; + } + return undefined; +}; + +type Resolver = (options: ApiRequestOptions) => Promise; + +export const resolve = async ( + options: ApiRequestOptions, + resolver?: T | Resolver +): Promise => { + if (typeof resolver === 'function') { + return (resolver as Resolver)(options); + } + return resolver; +}; + +export const getHeaders = async ( + config: OpenAPIConfig, + options: ApiRequestOptions +): Promise => { + const [token, username, password, additionalHeaders] = await Promise.all([ + // @ts-ignore + resolve(options, config.TOKEN), + // @ts-ignore + resolve(options, config.USERNAME), + // @ts-ignore + resolve(options, config.PASSWORD), + // @ts-ignore + resolve(options, config.HEADERS) + ]); + + const headers = Object.entries({ + Accept: 'application/json', + ...additionalHeaders, + ...options.headers + }) + .filter(([, value]) => value !== undefined && value !== null) + .reduce( + (headers, [key, value]) => ({ + ...headers, + [key]: String(value) + }), + {} as Record + ); + + if (isStringWithValue(token)) { + headers['Authorization'] = `Bearer ${token}`; + } + + if (isStringWithValue(username) && isStringWithValue(password)) { + const credentials = base64(`${username}:${password}`); + headers['Authorization'] = `Basic ${credentials}`; + } + + if (options.body !== undefined) { + if (options.mediaType) { + headers['Content-Type'] = options.mediaType; + } else if (isBlob(options.body)) { + headers['Content-Type'] = options.body.type || 'application/octet-stream'; + } else if (isString(options.body)) { + headers['Content-Type'] = 'text/plain'; + } else if (!isFormData(options.body)) { + headers['Content-Type'] = 'application/json'; + } + } + + return new Headers(headers); +}; + +export const getRequestBody = (options: ApiRequestOptions): unknown => { + if (options.body !== undefined) { + if (options.mediaType?.includes('application/json') || options.mediaType?.includes('+json')) { + return JSON.stringify(options.body); + } else if (isString(options.body) || isBlob(options.body) || isFormData(options.body)) { + return options.body; + } else { + return JSON.stringify(options.body); + } + } + return undefined; +}; + +export const sendRequest = async ( + config: OpenAPIConfig, + options: ApiRequestOptions, + url: string, + body: any, + formData: FormData | undefined, + headers: Headers, + onCancel: OnCancel +): Promise => { + const controller = new AbortController(); + + let request: RequestInit = { + headers, + body: body ?? formData, + method: options.method, + signal: controller.signal + }; + + if (config.WITH_CREDENTIALS) { + request.credentials = config.CREDENTIALS; + } + + for (const fn of config.interceptors.request._fns) { + request = await fn(request); + } + + onCancel(() => controller.abort()); + + return await fetch(url, request); +}; + +export const getResponseHeader = ( + response: Response, + responseHeader?: string +): string | undefined => { + if (responseHeader) { + const content = response.headers.get(responseHeader); + if (isString(content)) { + return content; + } + } + return undefined; +}; + +export const getResponseBody = async (response: Response): Promise => { + if (response.status !== 204) { + try { + const contentType = response.headers.get('Content-Type'); + if (contentType) { + const binaryTypes = [ + 'application/octet-stream', + 'application/pdf', + 'application/zip', + 'audio/', + 'image/', + 'video/' + ]; + if (contentType.includes('application/json') || contentType.includes('+json')) { + return await response.json(); + } else if (binaryTypes.some((type) => contentType.includes(type))) { + return await response.blob(); + } else if (contentType.includes('multipart/form-data')) { + return await response.formData(); + } else if (contentType.includes('text/')) { + return await response.text(); + } + } + } catch (error) { + console.error(error); + } + } + return undefined; +}; + +export const catchErrorCodes = (options: ApiRequestOptions, result: ApiResult): void => { + const errors: Record = { + 400: 'Bad Request', + 401: 'Unauthorized', + 402: 'Payment Required', + 403: 'Forbidden', + 404: 'Not Found', + 405: 'Method Not Allowed', + 406: 'Not Acceptable', + 407: 'Proxy Authentication Required', + 408: 'Request Timeout', + 409: 'Conflict', + 410: 'Gone', + 411: 'Length Required', + 412: 'Precondition Failed', + 413: 'Payload Too Large', + 414: 'URI Too Long', + 415: 'Unsupported Media Type', + 416: 'Range Not Satisfiable', + 417: 'Expectation Failed', + 418: 'Im a teapot', + 421: 'Misdirected Request', + 422: 'Unprocessable Content', + 423: 'Locked', + 424: 'Failed Dependency', + 425: 'Too Early', + 426: 'Upgrade Required', + 428: 'Precondition Required', + 429: 'Too Many Requests', + 431: 'Request Header Fields Too Large', + 451: 'Unavailable For Legal Reasons', + 500: 'Internal Server Error', + 501: 'Not Implemented', + 502: 'Bad Gateway', + 503: 'Service Unavailable', + 504: 'Gateway Timeout', + 505: 'HTTP Version Not Supported', + 506: 'Variant Also Negotiates', + 507: 'Insufficient Storage', + 508: 'Loop Detected', + 510: 'Not Extended', + 511: 'Network Authentication Required', + ...options.errors + }; + + const error = errors[result.status]; + if (error) { + throw new ApiError(options, result, error); + } + + if (!result.ok) { + const errorStatus = result.status ?? 'unknown'; + const errorStatusText = result.statusText ?? 'unknown'; + const errorBody = (() => { + try { + return JSON.stringify(result.body, null, 2); + } catch (e) { + return undefined; + } + })(); + + throw new ApiError( + options, + result, + `Generic Error: status: ${errorStatus}; status text: ${errorStatusText}; body: ${errorBody}` + ); + } +}; + +/** + * Request method + * @param config The OpenAPI configuration object + * @param options The request options from the service + * @returns CancelablePromise + * @throws ApiError + */ +export const request = ( + config: OpenAPIConfig, + options: ApiRequestOptions +): CancelablePromise => { + return new CancelablePromise(async (resolve, reject, onCancel) => { + try { + const url = getUrl(config, options); + const formData = getFormData(options); + const body = getRequestBody(options); + const headers = await getHeaders(config, options); + + if (!onCancel.isCancelled) { + let response = await sendRequest(config, options, url, body, formData, headers, onCancel); + + for (const fn of config.interceptors.response._fns) { + response = await fn(response); + } + + const responseBody = await getResponseBody(response); + const responseHeader = getResponseHeader(response, options.responseHeader); + + let transformedBody = responseBody; + if (options.responseTransformer && response.ok) { + transformedBody = await options.responseTransformer(responseBody); + } + + const result: ApiResult = { + url, + ok: response.ok, + status: response.status, + statusText: response.statusText, + body: responseHeader ?? transformedBody + }; + + catchErrorCodes(options, result); + + resolve(result.body); + } + } catch (error) { + reject(error); + } + }); +}; diff --git a/src/lib/motis/index.ts b/src/lib/motis/index.ts new file mode 100644 index 00000000..0a2b84ba --- /dev/null +++ b/src/lib/motis/index.ts @@ -0,0 +1,4 @@ +// This file is auto-generated by @hey-api/openapi-ts +export * from './schemas.gen'; +export * from './services.gen'; +export * from './types.gen'; \ No newline at end of file diff --git a/src/lib/motis/schemas.gen.ts b/src/lib/motis/schemas.gen.ts new file mode 100644 index 00000000..8d744eed --- /dev/null +++ b/src/lib/motis/schemas.gen.ts @@ -0,0 +1,667 @@ +// This file is auto-generated by @hey-api/openapi-ts + +export const DurationSchema = { + description: 'Object containing duration if a path was found or none if no path was found', + type: 'object', + required: [], + properties: { + duration: { + type: 'number', + description: 'duration in seconds if a path was found, otherwise missing' + } + } +} as const; + +export const AreaSchema = { + description: 'Administrative area', + type: 'object', + required: ['name', 'admin_level', 'matched'], + properties: { + name: { + type: 'string', + description: 'Name of the area' + }, + admin_level: { + type: 'number', + description: `[OpenStreetMap \`admin_level\`](https://wiki.openstreetmap.org/wiki/Key:admin_level) +of the area +` + }, + matched: { + type: 'boolean', + description: 'Whether this area was matched by the input text' + }, + default: { + type: 'boolean', + description: 'Whether this area should be displayed as default area (area with admin level closest 7)' + } + } +} as const; + +export const TokenSchema = { + description: 'Matched token range (from index, length)', + type: 'array', + minItems: 2, + maxItems: 2, + items: { + type: 'number' + } +} as const; + +export const MatchSchema = { + description: 'GeoCoding match', + type: 'object', + required: ['type', 'name', 'id', 'lat', 'lon', 'level', 'tokens', 'areas', 'score'], + properties: { + type: { + description: 'location type', + type: 'string', + enum: ['ADDRESS', 'PLACE', 'STOP'] + }, + tokens: { + description: 'list of non-overlapping tokens that were matched', + type: 'array', + items: { + '$ref': '#/components/schemas/Token' + } + }, + name: { + description: 'name of the location (transit stop / PoI / address)', + type: 'string' + }, + id: { + description: 'unique ID of the location', + type: 'string' + }, + lat: { + description: 'latitude', + type: 'number' + }, + lon: { + description: 'longitude', + type: 'number' + }, + level: { + description: `level according to OpenStreetMap +(at the moment only for public transport) +`, + type: 'number' + }, + street: { + description: 'street name', + type: 'string' + }, + house_number: { + description: 'house number', + type: 'string' + }, + zip: { + description: 'zip code', + type: 'string' + }, + areas: { + description: 'list of areas', + type: 'array', + items: { + '$ref': '#/components/schemas/Area' + } + }, + score: { + description: 'score according to the internal scoring system (the scoring algorithm might change in the future)', + type: 'number' + } + } +} as const; + +export const ModeSchema = { + description: `# Street modes + + - \`WALK\`: Walking some or all of the way of the route. + - \`BIKE\`: Cycling for the entirety of the route or taking a bicycle onto the public transport (if enabled) and cycling from the arrival station to the destination. + - \`BIKE_RENTAL\`: Taking a rented, shared-mobility bike for part or the entirety of the route. + - \`BIKE_TO_PARK\`: Leaving the bicycle at the departure station and walking from the arrival station to the destination. This mode needs to be combined with at least one transit mode otherwise it behaves like an ordinary bicycle journey. + - \`CAR\`: Driving your own car the entirety of the route. This can be combined with transit, where will return routes with a Kiss & Ride component. This means that the car is not parked in a permanent parking area but rather the passenger is dropped off (for example, at an airport) and the driver continues driving the car away from the drop off location. + - \`CAR_PARK\` | \`CAR_TO_PARK\`: Driving a car to the park-and-ride facilities near a station and taking publictransport. This mode needs to be combined with at least one transit mode otherwise, it behaves like an ordinary car journey. + - \`CAR_HAILING\`: Using a car hailing app like Uber or Lyft to get to a train station or all the way to the destination. + - \`CAR_PICKUP\`: Walking to a pickup point along the road, driving to a drop-off point along the road, and walking the rest of the way. This can include various taxi-services or kiss & ride. + - \`CAR_RENTAL\`: Walk to a car rental point, drive to a car rental drop-off point and walk the rest of the way. This can include car rental at fixed locations or free-floating services. + - \`FLEXIBLE\`: Encompasses all types of on-demand and flexible transportation for example GTFS Flex or NeTEx Flexible Stop Places. + - \`SCOOTER_RENTAL\`: Walking to a scooter rental point, riding a scooter to a scooter rental drop-off point, and walking the rest of the way. This can include scooter rental at fixed locations or free-floating services. + +# Transit modes + + - \`TRANSIT\`: translates to \`RAIL,SUBWAY,TRAM,BUS,FERRY,AIRPLANE,COACH\` + - \`TRAM\`: trams + - \`SUBWAY\`: subway trains + - \`FERRY\`: ferries + - \`AIRPLANE\`: airline flights + - \`BUS\`: short distance buses (does not include \`COACH\`) + - \`COACH\`: long distance buses (does not include \`BUS\`) + - \`RAIL\`: translates to \`HIGHSPEED_RAIL,LONG_DISTANCE_RAIL,NIGHT_RAIL,REGIONAL_RAIL,REGIONAL_FAST_RAIL\` + - \`METRO\`: metro trains + - \`HIGHSPEED_RAIL\`: long distance high speed trains (e.g. TGV) + - \`LONG_DISTANCE\`: long distance inter city trains + - \`NIGHT_RAIL\`: long distance night trains + - \`COACH\`: long distance buses + - \`REGIONAL_FAST_RAIL\`: regional express routes that skip low traffic stops to be faster + - \`REGIONAL_RAIL\`: regional train +`, + type: 'string', + enum: ['WALK', 'BIKE', 'CAR', 'BIKE_RENTAL', 'BIKE_TO_PARK', 'CAR_TO_PARK', 'CAR_HAILING', 'CAR_SHARING', 'CAR_PICKUP', 'CAR_RENTAL', 'FLEXIBLE', 'SCOOTER_RENTAL', 'TRANSIT', 'TRAM', 'SUBWAY', 'FERRY', 'AIRPLANE', 'METRO', 'BUS', 'COACH', 'RAIL', 'HIGHSPEED_RAIL', 'LONG_DISTANCE', 'NIGHT_RAIL', 'REGIONAL_FAST_RAIL', 'REGIONAL_RAIL', 'OTHER'] +} as const; + +export const StopTimeSchema = { + description: 'departure or arrival event at a stop', + type: 'object', + required: ['mode', 'time', 'delay', 'realTime', 'route', 'headsign', 'agencyId', 'agencyName', 'agencyUrl', 'routeColor', 'routeTextColor', 'routeType', 'routeId', 'tripId', 'serviceDate', 'routeShortName', 'source'], + properties: { + mode: { + '$ref': '#/components/schemas/Mode', + description: 'Transport mode for this leg' + }, + time: { + type: 'integer', + description: `The offset from the scheduled arrival time of the boarding stop in this leg. +Scheduled time of arrival at boarding stop = endTime - arrivalDelay +` + }, + delay: { + type: 'integer', + description: `The offset from the scheduled departure time of the boarding stop in this leg. +Scheduled time of departure at boarding stop = startTime - departureDelay +` + }, + realTime: { + description: 'Whether there is real-time data about this leg', + type: 'boolean' + }, + route: { + description: `For transit legs, the route of the bus or train being used. +For non-transit legs, the name of the street being traversed. +`, + type: 'string' + }, + headsign: { + description: `For transit legs, the headsign of the bus or train being used. +For non-transit legs, null +`, + type: 'string' + }, + agencyId: { + type: 'string' + }, + agencyName: { + type: 'string' + }, + agencyUrl: { + type: 'string' + }, + routeColor: { + type: 'string' + }, + routeTextColor: { + type: 'string' + }, + routeType: { + type: 'string' + }, + routeId: { + type: 'string' + }, + tripId: { + type: 'string' + }, + serviceDate: { + type: 'string' + }, + routeShortName: { + type: 'string' + }, + source: { + description: 'Filename and line number where this trip is from', + type: 'string' + } + } +} as const; + +export const VertexTypeSchema = { + type: 'string', + description: `- \`NORMAL\` - latitude / longitude coordinate or address +- \`BIKESHARE\` - bike sharing station +- \`BIKEPARK\` - bike parking +- \`TRANSIT\` - transit stop +`, + enum: ['NORMAL', 'BIKESHARE', 'BIKEPARK', 'TRANSIT'] +} as const; + +export const PlaceSchema = { + type: 'object', + required: ['name', 'lat', 'lon', 'level'], + properties: { + name: { + description: 'name of the transit stop / PoI / address', + type: 'string' + }, + stopId: { + description: "The ID of the stop. This is often something that users don't care about.", + type: 'string' + }, + lat: { + description: 'latitude', + type: 'number' + }, + lon: { + description: 'longitude', + type: 'number' + }, + level: { + description: 'level according to OpenStreetMap', + type: 'number' + }, + arrivalDelay: { + type: 'integer', + description: `The offset from the scheduled arrival time of the boarding stop in this leg. +Scheduled time of arrival at boarding stop = endTime - arrivalDelay +` + }, + departureDelay: { + type: 'integer', + description: `The offset from the scheduled departure time of the boarding stop in this leg. +Scheduled time of departure at boarding stop = startTime - departureDelay +` + }, + arrival: { + description: 'arrival time, format = unixtime in milliseconds', + type: 'integer' + }, + departure: { + description: 'departure time, format = unixtime in milliseconds', + type: 'integer' + }, + track: { + description: 'track/platform information, if available', + type: 'string' + }, + vertexType: { + '$ref': '#/components/schemas/VertexType' + } + } +} as const; + +export const TripInfoSchema = { + description: 'trip id and name', + type: 'object', + required: ['tripId', 'serviceDate', 'routeShortName'], + properties: { + tripId: { + description: 'trip ID (dataset trip id prefixed with the dataset tag)', + type: 'string' + }, + serviceDate: { + description: 'service date', + type: 'string' + }, + routeShortName: { + description: 'trip display name', + type: 'string' + } + } +} as const; + +export const TripSegmentSchema = { + description: 'trip segment between two stops to show a trip on a map', + type: 'object', + required: ['trips', 'routeColor', 'mode', 'distance', 'from', 'to', 'departure', 'arrival', 'departureDelay', 'arrivalDelay', 'realTime', 'polyline'], + properties: { + trips: { + type: 'array', + items: { + '$ref': '#/components/schemas/TripInfo' + } + }, + routeColor: { + type: 'string' + }, + mode: { + '$ref': '#/components/schemas/Mode', + description: 'Transport mode for this leg' + }, + distance: { + type: 'number', + description: 'distance in meters' + }, + from: { + '$ref': '#/components/schemas/Place' + }, + to: { + '$ref': '#/components/schemas/Place' + }, + departure: { + description: 'departure time, format = unixtime in milliseconds', + type: 'integer' + }, + arrival: { + description: 'arrival time, format = unixtime in milliseconds', + type: 'integer' + }, + departureDelay: { + type: 'integer', + description: `The offset from the scheduled departure time of the boarding stop in this leg. +Scheduled time of departure at boarding stop = startTime - departureDelay +` + }, + arrivalDelay: { + type: 'integer', + description: `The offset from the scheduled arrival time of the boarding stop in this leg. +Scheduled time of arrival at boarding stop = endTime - arrivalDelay +` + }, + realTime: { + description: 'Whether there is real-time data about this leg', + type: 'boolean' + }, + polyline: { + description: 'Google polyline encoded coordinate sequence where the trip travels on this segment', + type: 'string' + } + } +} as const; + +export const RelativeDirectionSchema = { + type: 'string', + enum: ['DEPART', 'HARD_LEFT', 'LEFT', 'SLIGHTLY_LEFT', 'CONTINUE', 'SLIGHTLY_RIGHT', 'RIGHT', 'HARD_RIGHT', 'CIRCLE_CLOCKWISE', 'CIRCLE_COUNTERCLOCKWISE', 'ELEVATOR', 'UTURN_LEFT', 'UTURN_RIGHT'] +} as const; + +export const AbsoluteDirectionSchema = { + type: 'string', + enum: ['NORTH', 'NORTHEAST', 'EAST', 'SOUTHEAST', 'SOUTH', 'SOUTHWEST', 'WEST', 'NORTHWEST'] +} as const; + +export const StepInstructionSchema = { + type: 'object', + required: ['relativeDirection', 'absoluteDirection', 'distance', 'streetName', 'exit', 'stayOn', 'area', 'lon', 'lat'], + properties: { + relativeDirection: { + '$ref': '#/components/schemas/RelativeDirection' + }, + absoluteDirection: { + '$ref': '#/components/schemas/AbsoluteDirection' + }, + distance: { + description: 'The distance in meters that this step takes.', + type: 'number' + }, + streetName: { + description: 'The name of the street.', + type: 'string' + }, + exit: { + description: 'When exiting a highway or traffic circle, the exit name/number.', + type: 'string' + }, + stayOn: { + description: `Indicates whether or not a street changes direction at an intersection. +`, + type: 'boolean' + }, + area: { + description: `This step is on an open area, such as a plaza or train platform, +and thus the directions should say something like "cross" +`, + type: 'boolean' + }, + lon: { + description: 'The longitude of start of the step', + type: 'number' + }, + lat: { + description: 'The latitude of start of the step', + type: 'number' + } + } +} as const; + +export const EncodedPolylineSchema = { + type: 'object', + required: ['points', 'length'], + properties: { + points: { + description: 'The encoded points of the polyline.', + type: 'string' + }, + length: { + description: 'The number of points in the string', + type: 'integer' + } + } +} as const; + +export const LevelEncodedPolylineSchema = { + type: 'object', + required: ['from_level', 'to_level', 'polyline'], + properties: { + from_level: { + description: 'level where this segment starts, based on OpenStreetMap data', + type: 'number' + }, + to_level: { + description: 'level where this segment starts, based on OpenStreetMap data', + type: 'number' + }, + osm_way: { + description: 'OpenStreetMap way index', + type: 'integer' + }, + polyline: { + '$ref': '#/components/schemas/EncodedPolyline' + } + } +} as const; + +export const LegSchema = { + type: 'object', + required: ['mode', 'startTime', 'endTime', 'departureDelay', 'arrivalDelay', 'realTime', 'distance', 'duration', 'from', 'to', 'legGeometry'], + properties: { + mode: { + '$ref': '#/components/schemas/Mode', + description: 'Transport mode for this leg' + }, + from: { + '$ref': '#/components/schemas/Place' + }, + to: { + '$ref': '#/components/schemas/Place' + }, + duration: { + description: 'Leg duration in seconds', + type: 'integer' + }, + startTime: { + type: 'integer', + description: 'leg departure time, format = unixtime in milliseconds' + }, + endTime: { + type: 'integer', + description: 'leg arrival time, format = unixtime in milliseconds' + }, + departureDelay: { + type: 'integer', + description: `The offset from the scheduled departure time of the boarding stop in this leg. +Scheduled time of departure at boarding stop = startTime - departureDelay +` + }, + arrivalDelay: { + type: 'integer', + description: `The offset from the scheduled arrival time of the boarding stop in this leg. +Scheduled time of arrival at boarding stop = endTime - arrivalDelay +` + }, + realTime: { + description: 'Whether there is real-time data about this leg', + type: 'boolean' + }, + distance: { + description: 'The distance traveled while traversing this leg in meters.', + type: 'number' + }, + interlineWithPreviousLeg: { + description: 'For transit legs, if the rider should stay on the vehicle as it changes route names.', + type: 'boolean' + }, + route: { + description: `For transit legs, the route of the bus or train being used. +For non-transit legs, the name of the street being traversed. +`, + type: 'string' + }, + headsign: { + description: `For transit legs, the headsign of the bus or train being used. +For non-transit legs, null +`, + type: 'string' + }, + agencyName: { + type: 'string' + }, + agencyUrl: { + type: 'string' + }, + routeColor: { + type: 'string' + }, + routeTextColor: { + type: 'string' + }, + routeType: { + type: 'string' + }, + routeId: { + type: 'string' + }, + agencyId: { + type: 'string' + }, + tripId: { + type: 'string' + }, + serviceDate: { + type: 'string' + }, + routeShortName: { + type: 'string' + }, + source: { + description: 'Filename and line number where this trip is from', + type: 'string' + }, + intermediateStops: { + description: `For transit legs, intermediate stops between the Place where the leg originates +and the Place where the leg ends. For non-transit legs, null. +`, + type: 'array', + items: { + '$ref': '#/components/schemas/Place' + } + }, + legGeometry: { + '$ref': '#/components/schemas/EncodedPolyline' + }, + legGeometryWithLevels: { + description: 'Like `legGeometry`, but split at level changes', + type: 'array', + items: { + '$ref': '#/components/schemas/LevelEncodedPolyline' + } + }, + steps: { + description: `A series of turn by turn instructions +used for walking, biking and driving. +`, + type: 'array', + items: { + '$ref': '#/components/schemas/StepInstruction' + } + } + } +} as const; + +export const ItinerarySchema = { + type: 'object', + required: ['duration', 'startTime', 'endTime', 'walkTime', 'transitTime', 'waitingTime', 'walkDistance', 'transfers', 'legs'], + properties: { + duration: { + description: 'journey duration in seconds', + type: 'integer' + }, + startTime: { + type: 'integer', + description: 'journey departure time, format = unixtime in milliseconds' + }, + endTime: { + type: 'integer', + description: 'journey arrival time, format = unixtime in milliseconds' + }, + walkTime: { + type: 'integer', + description: 'How much time is spent walking, in seconds.' + }, + transitTime: { + type: 'integer', + description: 'How much time is spent on transit, in seconds.' + }, + waitingTime: { + type: 'integer', + description: 'How much time is spent waiting for transit to arrive, in seconds.' + }, + walkDistance: { + type: 'integer', + description: 'How far the user has to walk, in meters.' + }, + transfers: { + type: 'integer', + description: 'The number of transfers this trip has.' + }, + legs: { + description: 'Journey legs', + type: 'array', + items: { + '$ref': '#/components/schemas/Leg' + } + } + } +} as const; + +export const FootpathSchema = { + description: 'footpath from one location to another', + type: 'object', + required: ['to'], + properties: { + to: { + '$ref': '#/components/schemas/Place' + }, + default: { + type: 'number', + description: `optional; missing if the GTFS did not contain a footpath +footpath duration in minutes according to GTFS (+heuristics) +` + }, + foot: { + type: 'number', + description: `optional; missing if no path was found with the foot profile +footpath duration in minutes for the foot profile +` + }, + wheelchair: { + type: 'number', + description: `optional; missing if no path was found with the wheelchair profile +footpath duration in minutes for the wheelchair profile +` + }, + wheelchairUsesElevator: { + type: 'boolean', + description: `optional; missing if no path was found with the wheelchair profile +true if the wheelchair path uses an elevator +` + } + } +} as const; \ No newline at end of file diff --git a/src/lib/motis/services.gen.ts b/src/lib/motis/services.gen.ts new file mode 100644 index 00000000..8de6f499 --- /dev/null +++ b/src/lib/motis/services.gen.ts @@ -0,0 +1,92 @@ +// This file is auto-generated by @hey-api/openapi-ts + +import { createClient, createConfig, type Options } from '@hey-api/client-fetch'; +import type { OneToManyData, OneToManyError, OneToManyResponse, ReverseGeocodeData, ReverseGeocodeError, ReverseGeocodeResponse, GeocodeData, GeocodeError, GeocodeResponse, TripData, TripError, TripResponse, StoptimesData, StoptimesError, StoptimesResponse, PlanData, PlanError, PlanResponse, RailvizData, RailvizError, RailvizResponse, InitialError, InitialResponse, LevelsData, LevelsError, LevelsResponse, FootpathsData, FootpathsError, FootpathsResponse } from './types.gen'; + +export const client = createClient(createConfig()); + +/** + * Street routing from one to many places or many to one. + * The order in the response array corresponds to the order of coordinates of the \`many\` parameter in the query. + * + */ +export const oneToMany = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/one-to-many' +}); }; + +/** + * Translate coordinates to the closest address(es)/places/stops. + */ +export const reverseGeocode = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/reverse-geocode' +}); }; + +/** + * Autocompletion & geocoding that resolves user input addresses including coordinates + */ +export const geocode = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/geocode' +}); }; + +/** + * Get a trip as itinerary + */ +export const trip = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/trip' +}); }; + +/** + * Get the next N departures or arrivals of a stop sorted by time + */ +export const stoptimes = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/stoptimes' +}); }; + +/** + * Computes optimal connections from one place to another. + */ +export const plan = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/plan' +}); }; + +/** + * Given a area frame (box defined by top right and bottom left corner) and a time frame, + * it returns all trips and their respective shapes that operate in this area + time frame. + * Trips are filtered by zoom level. On low zoom levels, only long distance trains will be shown + * while on high zoom levels, also metros, buses and trams will be returned. + * + */ +export const railviz = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/railviz' +}); }; + +/** + * initial location to view the map at after loading based on where public transport should be visible + */ +export const initial = (options?: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/map/initial' +}); }; + +/** + * Get all available levels for a map section + */ +export const levels = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/map/levels' +}); }; + +/** + * Prints all footpaths of a timetable location (track, bus stop, etc.) + */ +export const footpaths = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/debug/footpaths' +}); }; \ No newline at end of file diff --git a/src/lib/motis/types.gen.ts b/src/lib/motis/types.gen.ts new file mode 100644 index 00000000..2ecf658e --- /dev/null +++ b/src/lib/motis/types.gen.ts @@ -0,0 +1,959 @@ +// This file is auto-generated by @hey-api/openapi-ts + +/** + * Object containing duration if a path was found or none if no path was found + */ +export type Duration = { + /** + * duration in seconds if a path was found, otherwise missing + */ + duration?: number; +}; + +/** + * Administrative area + */ +export type Area = { + /** + * Name of the area + */ + name: string; + /** + * [OpenStreetMap `admin_level`](https://wiki.openstreetmap.org/wiki/Key:admin_level) + * of the area + * + */ + admin_level: number; + /** + * Whether this area was matched by the input text + */ + matched: boolean; + /** + * Whether this area should be displayed as default area (area with admin level closest 7) + */ + default?: boolean; +}; + +/** + * Matched token range (from index, length) + */ +export type Token = [ + number, + number +]; + +/** + * GeoCoding match + */ +export type Match = { + /** + * location type + */ + type: 'ADDRESS' | 'PLACE' | 'STOP'; + /** + * list of non-overlapping tokens that were matched + */ + tokens: Array; + /** + * name of the location (transit stop / PoI / address) + */ + name: string; + /** + * unique ID of the location + */ + id: string; + /** + * latitude + */ + lat: number; + /** + * longitude + */ + lon: number; + /** + * level according to OpenStreetMap + * (at the moment only for public transport) + * + */ + level: number; + /** + * street name + */ + street?: string; + /** + * house number + */ + house_number?: string; + /** + * zip code + */ + zip?: string; + /** + * list of areas + */ + areas: Array; + /** + * score according to the internal scoring system (the scoring algorithm might change in the future) + */ + score: number; +}; + +/** + * location type + */ +export type type = 'ADDRESS' | 'PLACE' | 'STOP'; + +/** + * # Street modes + * + * - `WALK`: Walking some or all of the way of the route. + * - `BIKE`: Cycling for the entirety of the route or taking a bicycle onto the public transport (if enabled) and cycling from the arrival station to the destination. + * - `BIKE_RENTAL`: Taking a rented, shared-mobility bike for part or the entirety of the route. + * - `BIKE_TO_PARK`: Leaving the bicycle at the departure station and walking from the arrival station to the destination. This mode needs to be combined with at least one transit mode otherwise it behaves like an ordinary bicycle journey. + * - `CAR`: Driving your own car the entirety of the route. This can be combined with transit, where will return routes with a Kiss & Ride component. This means that the car is not parked in a permanent parking area but rather the passenger is dropped off (for example, at an airport) and the driver continues driving the car away from the drop off location. + * - `CAR_PARK` | `CAR_TO_PARK`: Driving a car to the park-and-ride facilities near a station and taking publictransport. This mode needs to be combined with at least one transit mode otherwise, it behaves like an ordinary car journey. + * - `CAR_HAILING`: Using a car hailing app like Uber or Lyft to get to a train station or all the way to the destination. + * - `CAR_PICKUP`: Walking to a pickup point along the road, driving to a drop-off point along the road, and walking the rest of the way. This can include various taxi-services or kiss & ride. + * - `CAR_RENTAL`: Walk to a car rental point, drive to a car rental drop-off point and walk the rest of the way. This can include car rental at fixed locations or free-floating services. + * - `FLEXIBLE`: Encompasses all types of on-demand and flexible transportation for example GTFS Flex or NeTEx Flexible Stop Places. + * - `SCOOTER_RENTAL`: Walking to a scooter rental point, riding a scooter to a scooter rental drop-off point, and walking the rest of the way. This can include scooter rental at fixed locations or free-floating services. + * + * # Transit modes + * + * - `TRANSIT`: translates to `RAIL,SUBWAY,TRAM,BUS,FERRY,AIRPLANE,COACH` + * - `TRAM`: trams + * - `SUBWAY`: subway trains + * - `FERRY`: ferries + * - `AIRPLANE`: airline flights + * - `BUS`: short distance buses (does not include `COACH`) + * - `COACH`: long distance buses (does not include `BUS`) + * - `RAIL`: translates to `HIGHSPEED_RAIL,LONG_DISTANCE_RAIL,NIGHT_RAIL,REGIONAL_RAIL,REGIONAL_FAST_RAIL` + * - `METRO`: metro trains + * - `HIGHSPEED_RAIL`: long distance high speed trains (e.g. TGV) + * - `LONG_DISTANCE`: long distance inter city trains + * - `NIGHT_RAIL`: long distance night trains + * - `COACH`: long distance buses + * - `REGIONAL_FAST_RAIL`: regional express routes that skip low traffic stops to be faster + * - `REGIONAL_RAIL`: regional train + * + */ +export type Mode = 'WALK' | 'BIKE' | 'CAR' | 'BIKE_RENTAL' | 'BIKE_TO_PARK' | 'CAR_TO_PARK' | 'CAR_HAILING' | 'CAR_SHARING' | 'CAR_PICKUP' | 'CAR_RENTAL' | 'FLEXIBLE' | 'SCOOTER_RENTAL' | 'TRANSIT' | 'TRAM' | 'SUBWAY' | 'FERRY' | 'AIRPLANE' | 'METRO' | 'BUS' | 'COACH' | 'RAIL' | 'HIGHSPEED_RAIL' | 'LONG_DISTANCE' | 'NIGHT_RAIL' | 'REGIONAL_FAST_RAIL' | 'REGIONAL_RAIL' | 'OTHER'; + +/** + * departure or arrival event at a stop + */ +export type StopTime = { + /** + * Transport mode for this leg + */ + mode: Mode; + /** + * The offset from the scheduled arrival time of the boarding stop in this leg. + * Scheduled time of arrival at boarding stop = endTime - arrivalDelay + * + */ + time: number; + /** + * The offset from the scheduled departure time of the boarding stop in this leg. + * Scheduled time of departure at boarding stop = startTime - departureDelay + * + */ + delay: number; + /** + * Whether there is real-time data about this leg + */ + realTime: boolean; + /** + * For transit legs, the route of the bus or train being used. + * For non-transit legs, the name of the street being traversed. + * + */ + route: string; + /** + * For transit legs, the headsign of the bus or train being used. + * For non-transit legs, null + * + */ + headsign: string; + agencyId: string; + agencyName: string; + agencyUrl: string; + routeColor: string; + routeTextColor: string; + routeType: string; + routeId: string; + tripId: string; + serviceDate: string; + routeShortName: string; + /** + * Filename and line number where this trip is from + */ + source: string; +}; + +/** + * - `NORMAL` - latitude / longitude coordinate or address + * - `BIKESHARE` - bike sharing station + * - `BIKEPARK` - bike parking + * - `TRANSIT` - transit stop + * + */ +export type VertexType = 'NORMAL' | 'BIKESHARE' | 'BIKEPARK' | 'TRANSIT'; + +export type Place = { + /** + * name of the transit stop / PoI / address + */ + name: string; + /** + * The ID of the stop. This is often something that users don't care about. + */ + stopId?: string; + /** + * latitude + */ + lat: number; + /** + * longitude + */ + lon: number; + /** + * level according to OpenStreetMap + */ + level: number; + /** + * The offset from the scheduled arrival time of the boarding stop in this leg. + * Scheduled time of arrival at boarding stop = endTime - arrivalDelay + * + */ + arrivalDelay?: number; + /** + * The offset from the scheduled departure time of the boarding stop in this leg. + * Scheduled time of departure at boarding stop = startTime - departureDelay + * + */ + departureDelay?: number; + /** + * arrival time, format = unixtime in milliseconds + */ + arrival?: number; + /** + * departure time, format = unixtime in milliseconds + */ + departure?: number; + /** + * track/platform information, if available + */ + track?: string; + vertexType?: VertexType; +}; + +/** + * trip id and name + */ +export type TripInfo = { + /** + * trip ID (dataset trip id prefixed with the dataset tag) + */ + tripId: string; + /** + * service date + */ + serviceDate: string; + /** + * trip display name + */ + routeShortName: string; +}; + +/** + * trip segment between two stops to show a trip on a map + */ +export type TripSegment = { + trips: Array; + routeColor: string; + /** + * Transport mode for this leg + */ + mode: Mode; + /** + * distance in meters + */ + distance: number; + from: Place; + to: Place; + /** + * departure time, format = unixtime in milliseconds + */ + departure: number; + /** + * arrival time, format = unixtime in milliseconds + */ + arrival: number; + /** + * The offset from the scheduled departure time of the boarding stop in this leg. + * Scheduled time of departure at boarding stop = startTime - departureDelay + * + */ + departureDelay: number; + /** + * The offset from the scheduled arrival time of the boarding stop in this leg. + * Scheduled time of arrival at boarding stop = endTime - arrivalDelay + * + */ + arrivalDelay: number; + /** + * Whether there is real-time data about this leg + */ + realTime: boolean; + /** + * Google polyline encoded coordinate sequence where the trip travels on this segment + */ + polyline: string; +}; + +export type RelativeDirection = 'DEPART' | 'HARD_LEFT' | 'LEFT' | 'SLIGHTLY_LEFT' | 'CONTINUE' | 'SLIGHTLY_RIGHT' | 'RIGHT' | 'HARD_RIGHT' | 'CIRCLE_CLOCKWISE' | 'CIRCLE_COUNTERCLOCKWISE' | 'ELEVATOR' | 'UTURN_LEFT' | 'UTURN_RIGHT'; + +export type AbsoluteDirection = 'NORTH' | 'NORTHEAST' | 'EAST' | 'SOUTHEAST' | 'SOUTH' | 'SOUTHWEST' | 'WEST' | 'NORTHWEST'; + +export type StepInstruction = { + relativeDirection: RelativeDirection; + absoluteDirection: AbsoluteDirection; + /** + * The distance in meters that this step takes. + */ + distance: number; + /** + * The name of the street. + */ + streetName: string; + /** + * When exiting a highway or traffic circle, the exit name/number. + */ + exit: string; + /** + * Indicates whether or not a street changes direction at an intersection. + * + */ + stayOn: boolean; + /** + * This step is on an open area, such as a plaza or train platform, + * and thus the directions should say something like "cross" + * + */ + area: boolean; + /** + * The longitude of start of the step + */ + lon: number; + /** + * The latitude of start of the step + */ + lat: number; +}; + +export type EncodedPolyline = { + /** + * The encoded points of the polyline. + */ + points: string; + /** + * The number of points in the string + */ + length: number; +}; + +export type LevelEncodedPolyline = { + /** + * level where this segment starts, based on OpenStreetMap data + */ + from_level: number; + /** + * level where this segment starts, based on OpenStreetMap data + */ + to_level: number; + /** + * OpenStreetMap way index + */ + osm_way?: number; + polyline: EncodedPolyline; +}; + +export type Leg = { + /** + * Transport mode for this leg + */ + mode: Mode; + from: Place; + to: Place; + /** + * Leg duration in seconds + */ + duration: number; + /** + * leg departure time, format = unixtime in milliseconds + */ + startTime: number; + /** + * leg arrival time, format = unixtime in milliseconds + */ + endTime: number; + /** + * The offset from the scheduled departure time of the boarding stop in this leg. + * Scheduled time of departure at boarding stop = startTime - departureDelay + * + */ + departureDelay: number; + /** + * The offset from the scheduled arrival time of the boarding stop in this leg. + * Scheduled time of arrival at boarding stop = endTime - arrivalDelay + * + */ + arrivalDelay: number; + /** + * Whether there is real-time data about this leg + */ + realTime: boolean; + /** + * The distance traveled while traversing this leg in meters. + */ + distance: number; + /** + * For transit legs, if the rider should stay on the vehicle as it changes route names. + */ + interlineWithPreviousLeg?: boolean; + /** + * For transit legs, the route of the bus or train being used. + * For non-transit legs, the name of the street being traversed. + * + */ + route?: string; + /** + * For transit legs, the headsign of the bus or train being used. + * For non-transit legs, null + * + */ + headsign?: string; + agencyName?: string; + agencyUrl?: string; + routeColor?: string; + routeTextColor?: string; + routeType?: string; + routeId?: string; + agencyId?: string; + tripId?: string; + serviceDate?: string; + routeShortName?: string; + /** + * Filename and line number where this trip is from + */ + source?: string; + /** + * For transit legs, intermediate stops between the Place where the leg originates + * and the Place where the leg ends. For non-transit legs, null. + * + */ + intermediateStops?: Array; + legGeometry: EncodedPolyline; + /** + * Like `legGeometry`, but split at level changes + */ + legGeometryWithLevels?: Array; + /** + * A series of turn by turn instructions + * used for walking, biking and driving. + * + */ + steps?: Array; +}; + +export type Itinerary = { + /** + * journey duration in seconds + */ + duration: number; + /** + * journey departure time, format = unixtime in milliseconds + */ + startTime: number; + /** + * journey arrival time, format = unixtime in milliseconds + */ + endTime: number; + /** + * How much time is spent walking, in seconds. + */ + walkTime: number; + /** + * How much time is spent on transit, in seconds. + */ + transitTime: number; + /** + * How much time is spent waiting for transit to arrive, in seconds. + */ + waitingTime: number; + /** + * How far the user has to walk, in meters. + */ + walkDistance: number; + /** + * The number of transfers this trip has. + */ + transfers: number; + /** + * Journey legs + */ + legs: Array; +}; + +/** + * footpath from one location to another + */ +export type Footpath = { + to: Place; + /** + * optional; missing if the GTFS did not contain a footpath + * footpath duration in minutes according to GTFS (+heuristics) + * + */ + default?: number; + /** + * optional; missing if no path was found with the foot profile + * footpath duration in minutes for the foot profile + * + */ + foot?: number; + /** + * optional; missing if no path was found with the wheelchair profile + * footpath duration in minutes for the wheelchair profile + * + */ + wheelchair?: number; + /** + * optional; missing if no path was found with the wheelchair profile + * true if the wheelchair path uses an elevator + * + */ + wheelchairUsesElevator?: boolean; +}; + +export type OneToManyData = { + query: { + /** + * true = many to one + * false = one to many + * + */ + arriveBy: boolean; + /** + * geo locations as latitude;longitude,latitude;longitude,... + */ + many: Array<(string)>; + /** + * maximum travel time in seconds + */ + max: number; + /** + * maximum matching distance in meters to match geo coordinates to the street network + */ + maxMatchingDistance: number; + /** + * routing profile to use (currently supported: \`WALK\`, \`BIKE\`, \`CAR\`) + * + */ + mode: Mode; + /** + * geo location as latitude,longitude + */ + one: string; + }; +}; + +export type OneToManyResponse = (Array); + +export type OneToManyError = unknown; + +export type ReverseGeocodeData = { + query: { + /** + * latitude, longitude in degrees + */ + place: string; + }; +}; + +export type ReverseGeocodeResponse = (Array); + +export type ReverseGeocodeError = unknown; + +export type GeocodeData = { + query: { + /** + * language tags as used in OpenStreetMap + * (usually ISO 639-1, or ISO 639-2 if there's no ISO 639-1) + * + */ + language?: string; + /** + * the (potentially partially typed) address to resolve + */ + text: string; + }; +}; + +export type GeocodeResponse = (Array); + +export type GeocodeError = unknown; + +export type TripData = { + query: { + /** + * Service date as specified in the source dataset. + * Can be taken from an itinerary leg or stop event. + * + * Not that for GTFS the first departure time can be greater than 24:00:00 + * which means that the service date is shifted by the offset (first departure / 24h). + * A valid use case for this are stay seated transfers expressed by `block_id`. + * + * Example: a train with first departure at 25:00:00 on 9th of Oct 2024 + * has the 8th of Oct 2024 as service date. + * + */ + date: string; + /** + * trip identifier (e.g. from an itinerary leg or stop event) + */ + tripId: string; + }; +}; + +export type TripResponse = (Itinerary); + +export type TripError = unknown; + +export type StoptimesData = { + query: { + /** + * Optional. Default is `false`. + * + * - `arriveBy=true`: the parameters `date` and `time` refer to the arrival time + * - `arriveBy=false`: the parameters `date` and `time` refer to the departure time + * + */ + arriveBy?: boolean; + /** + * Optional. Defaults to the current date. + * + * Departure date ($arriveBy=false) / arrival date ($arriveBy=true), format: 06-28-2024 + * + */ + date?: string; + /** + * the number of events + */ + n: number; + /** + * Use the cursor to go to the next "page" of stop times. + * Copy the cursor from the last response and keep the original request as is. + * This will enable you to search for stop times in the next or previous time-window. + * + */ + pageCursor?: string; + /** + * stop id of the stop to retrieve departures/arrivals for + */ + stopId: string; + /** + * Optional. Defaults to the current time. + * + * Format: + * - 12h format: 7:06pm + * - 24h format: 19:06 + * + */ + time?: string; + }; +}; + +export type StoptimesResponse = ({ + /** + * list of stop times + */ + stopTimes: Array; + /** + * Use the cursor to get the previous page of results. Insert the cursor into the request and post it to get the previous page. + * The previous page is a set of stop times BEFORE the first stop time in the result. + * + */ + previousPageCursor: string; + /** + * Use the cursor to get the next page of results. Insert the cursor into the request and post it to get the next page. + * The next page is a set of stop times AFTER the last stop time in this result. + * + */ + nextPageCursor: string; +}); + +export type StoptimesError = unknown; + +export type PlanData = { + query: { + /** + * Optional. Default is `false`. + * + * - `arriveBy=true`: the parameters `date` and `time` refer to the arrival time + * - `arriveBy=false`: the parameters `date` and `time` refer to the departure time + * + */ + arriveBy?: boolean; + /** + * Optional. Defaults to the current date. + * + * Departure date ($arriveBy=false) / arrival date ($arriveBy=true), format: 06-28-2024 + * + */ + date?: string; + /** + * \`latitude,longitude,level\` tuple in degrees OR stop id + */ + fromPlace: string; + /** + * The maximum travel time in hours. + * If not provided, the routing to uses the value + * hardcoded in the server which is usually quite high. + * + * *Warning*: Use with care. Setting this too low can lead to + * optimal (e.g. the least transfers) journeys not being found. + * If this value is too low to reach the destination at all, + * it can lead to slow routing performance. + * + */ + maxHours?: number; + /** + * Optional. Default is 15min which is `900`. + * Maximum time in seconds for the last street leg. + * + */ + maxPostTransitTime?: number; + /** + * Optional. Default is 15min which is `900`. + * Maximum time in seconds for the first street leg. + * + */ + maxPreTransitTime?: number; + /** + * The maximum number of allowed transfers. + * If not provided, the routing uses the server-side default value + * which is hardcoded and very high to cover all use cases. + * + * *Warning*: Use with care. Setting this too low can lead to + * optimal (e.g. the fastest) journeys not being found. + * If this value is too low to reach the destination at all, + * it can lead to slow routing performance. + * + */ + maxTransfers?: number; + /** + * Minimum transfer time for each transfer. + */ + minTransferTime?: number; + /** + * A comma separated list of allowed modes. + * + * Default if not provided: `WALK,TRANSIT` + * + */ + mode?: Array; + /** + * The minimum number of itineraries to compute. + * This is only relevant if `timetableView=true`. + * The default value is 5. + * + */ + numItineraries?: number; + /** + * Use the cursor to go to the next "page" of itineraries. + * Copy the cursor from the last response and keep the original request as is. + * This will enable you to search for itineraries in the next or previous time-window. + * + */ + pageCursor?: string; + /** + * Optional. Default is 2 hours which is `7200`. + * + * The length of the search-window in seconds. Default value two hours. + * + * - `arriveBy=true`: number of seconds between the earliest departure time and latest departure time + * - `arriveBy=false`: number of seconds between the earliest arrival time and the latest arrival time + * + */ + searchWindow?: number; + /** + * Optional. Defaults to the current time. + * + * Meaning depending on `arriveBy` + * - Departure time for `arriveBy=false` + * - Arrival time for `arriveBy=true` + * + * Format: + * - 12h format: 7:06pm + * - 24h format: 19:06 + * + */ + time?: string; + /** + * Optional. Default is `true`. + * + * Search for the best trip options within a time window. + * If true two itineraries are considered optimal + * if one is better on arrival time (earliest wins) + * and the other is better on departure time (latest wins). + * In combination with arriveBy this parameter cover the following use cases: + * + * `timetable=false` = waiting for the first transit departure/arrival is considered travel time: + * - `arriveBy=true`: event (e.g. a meeting) starts at 10:00 am, + * compute the best journeys that arrive by that time (maximizes departure time) + * - `arriveBy=false`: event (e.g. a meeting) ends at 11:00 am, + * compute the best journeys that depart after that time + * + * `timetable=true` = optimize "later departure" + "earlier arrival" and give all options over a time window: + * - `arriveBy=true`: the time window around `date` and `time` refers to the arrival time window + * - `arriveBy=false`: the time window around `date` and `time` refers to the departure time window + * + */ + timetableView?: boolean; + /** + * \`latitude,longitude,level\` tuple in degrees OR stop id + */ + toPlace: string; + /** + * Factor to multiply transfer times with. + */ + transferTimeFactor?: number; + /** + * Whether the trip must be wheelchair accessible. + */ + wheelchair?: boolean; + }; +}; + +export type PlanResponse = ({ + /** + * the routing query + */ + requestParameters: { + [key: string]: (string); + }; + /** + * debug statistics + */ + debugOutput: { + [key: string]: (string); + }; + /** + * The time and date of travel + */ + date: number; + from: Place; + to: Place; + /** + * list of itineraries + */ + itineraries: Array; + /** + * Use the cursor to get the previous page of results. Insert the cursor into the request and post it to get the previous page. + * The previous page is a set of itineraries departing BEFORE the first itinerary in the result for a depart after search. When using the default sort order the previous set of itineraries is inserted before the current result. + * + */ + previousPageCursor: string; + /** + * Use the cursor to get the next page of results. Insert the cursor into the request and post it to get the next page. + * The next page is a set of itineraries departing AFTER the last itinerary in this result. + * + */ + nextPageCursor: string; +}); + +export type PlanError = unknown; + +export type RailvizData = { + query: { + /** + * end if the time window (unix timestamp in milliseconds) + */ + endTime: number; + /** + * latitude,longitude pair of the upper left coordinate + */ + max: string; + /** + * latitude,longitude pair of the lower right coordinate + */ + min: string; + /** + * start of the time window (unix timestamp in milliseconds) + */ + startTime: number; + /** + * current zoom level + */ + zoom: number; + }; +}; + +export type RailvizResponse = (Array); + +export type RailvizError = unknown; + +export type InitialResponse = ({ + /** + * latitude + */ + lat: number; + /** + * longitude + */ + lon: number; + /** + * zoom level + */ + zoom: number; +}); + +export type InitialError = unknown; + +export type LevelsData = { + query: { + /** + * latitude,longitude pair of the upper left coordinate + */ + max: string; + /** + * latitude,longitude pair of the lower right coordinate + */ + min: string; + }; +}; + +export type LevelsResponse = (Array<(number)>); + +export type LevelsError = unknown; + +export type FootpathsData = { + query: { + /** + * location id + */ + id: string; + }; +}; + +export type FootpathsResponse = ({ + place: Place; + /** + * all outgoing footpaths of this location + */ + footpaths: Array; +}); + +export type FootpathsError = unknown; \ No newline at end of file diff --git a/src/routes/+page.server.ts b/src/routes/+page.server.ts index f7519135..0e04b6f2 100644 --- a/src/routes/+page.server.ts +++ b/src/routes/+page.server.ts @@ -3,13 +3,16 @@ import type { PageServerLoad } from './$types'; export const load: PageServerLoad = async (event) => { if (!event.locals.user) { + console.log("redirect guest to login"); return redirect(302, '/login'); } if (event.locals.user.is_maintainer) { - return redirect(302, '/activation'); + console.log("redirect maintainer to /activation"); + return redirect(302, '/maintainer/activation'); } if (event.locals.user.is_entrepreneur) { - return redirect(302, '/company'); + console.log("redirect entrepreneur to /company"); + return redirect(302, '/user/company'); } return { user: event.locals.user diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index 6232ec8d..bcf01033 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -1,4 +1,4 @@ -import { oneToMany, Direction, getRoute } from '$lib/api.js'; +import { getRoute } from '$lib/api.js'; import { Coordinates } from '$lib/location.js'; import { db } from '$lib/database'; import { Interval } from '$lib/interval.js'; @@ -9,6 +9,9 @@ import { MAX_TRAVEL_DURATION, MIN_PREP_MINUTES } from '$lib/constants.js'; import { sql } from 'kysely'; import { getFareEstimation } from './fare-estimation/fare_estimation.js'; import { covers } from '$lib/sqlHelpers.js'; +import { oneToMany, type Duration } from '$lib/motis'; + +const MOTIS_BASE_URL = 'https://europe.motis-project.de' const startAndTargetShareZone = async (from: Coordinates, to: Coordinates) => { const zoneContainingStartAndDestination = await db @@ -31,21 +34,30 @@ export const POST = async (event) => { const toCoordinates: Coordinates = to.coordinates; const time = new Date(timeStamp); + const coordinatesToStr = (c: Coordinates) => { + return `${c.lat};${c.lng}`; + } + let travelDuration = 0; try { travelDuration = ( - await getRoute({ - start: { lat: from.coordinates.lat, lng: from.coordinates.lng }, - destination: { lat: to.coordinates.lat, lng: to.coordinates.lng }, - profile: 'car', - direction: 'forward' - }) - ).metadata.duration; + await oneToMany({ + baseUrl: MOTIS_BASE_URL, + query: { + one: coordinatesToStr(fromCoordinates), + many: [coordinatesToStr(toCoordinates)], + max: 3600, + maxMatchingDistance: 100, + mode: 'CAR', + arriveBy: false + } + }).then((d) => d.data!) + )[0].duration; } catch (e) { return json( { status: 1, - message: 'Es ist ein Fehler im Routing von Start zu Ziel aufgetreten.' + message: `Es ist ein Fehler im Routing von Start zu Ziel aufgetreten: ${e}.` }, { status: 404 } ); @@ -174,7 +186,7 @@ export const POST = async (event) => { console.assert( Math.max(...[...mergedAvailabilites.values()].map((availabilities) => availabilities.length)) <= - 1 + 1 ); const availableVehicles = [...mergedAvailabilites.entries()] @@ -226,18 +238,44 @@ export const POST = async (event) => { return new Coordinates(vehicles![0].latitude!, vehicles![0].longitude!); }); + let durationToStart: Array = []; let durationFromTarget: Array = []; try { - // Motis-one_to_many requests - durationToStart = ( - await oneToMany(fromCoordinates, centralCoordinates, Direction.Backward) - ).map((res) => secondsToMs(res.duration)); - durationFromTarget = ( - await oneToMany(toCoordinates, centralCoordinates, Direction.Forward) - ).map((res) => secondsToMs(res.duration)); + durationToStart = + await oneToMany({ + baseUrl: MOTIS_BASE_URL, + query: { + one: coordinatesToStr(fromCoordinates), + many: centralCoordinates.map(coordinatesToStr), + max: 3600, + maxMatchingDistance: 100, + mode: 'CAR', + arriveBy: false + } + }).then((res) => { + return res.data!.map((d: Duration) => { + return d.duration ?? Number.MAX_VALUE; + }); + }); + + durationFromTarget = await oneToMany({ + baseUrl: MOTIS_BASE_URL, + query: { + one: coordinatesToStr(toCoordinates), + many: centralCoordinates.map(coordinatesToStr), + max: 3600, + maxMatchingDistance: 100, + mode: 'CAR', + arriveBy: true + } + }).then((res) => { + return res.data!.map((d: Duration) => { + return d.duration ?? Number.MAX_VALUE; + }); + }); } catch (e) { - return json({ status: 8, message: 'Routing Anfrage fehlgeschlagen' }); + return json({ status: 8, message: `Routing Anfrage fehlgeschlagen: ${e}` }, { status: 500 }); } const fullTravelIntervals = companies.map((_, index) => travelInterval.expand(durationToStart[index], durationFromTarget[index]) diff --git a/src/routes/(maintainer)/+layout.server.ts b/src/routes/maintainer/+layout.server.ts similarity index 100% rename from src/routes/(maintainer)/+layout.server.ts rename to src/routes/maintainer/+layout.server.ts diff --git a/src/routes/(maintainer)/+layout.svelte b/src/routes/maintainer/+layout.svelte similarity index 80% rename from src/routes/(maintainer)/+layout.svelte rename to src/routes/maintainer/+layout.svelte index ec48ff64..7bdef212 100644 --- a/src/routes/(maintainer)/+layout.svelte +++ b/src/routes/maintainer/+layout.svelte @@ -6,13 +6,15 @@ const routeLinks = [ { name: 'Freischaltung', - href: '/activation' + href: '/maintainer/activation' }, { name: 'Abgeschlossene Fahrten', - href: '/completed_tours' + href: '/maintainer/completed_tours' } ]; + + console.log('Hello from maintainer layout');
diff --git a/src/routes/(maintainer)/activation/+page.server.ts b/src/routes/maintainer/activation/+page.server.ts similarity index 100% rename from src/routes/(maintainer)/activation/+page.server.ts rename to src/routes/maintainer/activation/+page.server.ts diff --git a/src/routes/(maintainer)/activation/+page.svelte b/src/routes/maintainer/activation/+page.svelte similarity index 97% rename from src/routes/(maintainer)/activation/+page.svelte rename to src/routes/maintainer/activation/+page.svelte index ae874111..d759590d 100644 --- a/src/routes/(maintainer)/activation/+page.svelte +++ b/src/routes/maintainer/activation/+page.svelte @@ -6,6 +6,8 @@ import type { ActionData } from './$types'; export let form: ActionData; + + console.log('Hello from maintainer page');
diff --git a/src/routes/(maintainer)/completed_tours/+page.server.ts b/src/routes/maintainer/completed_tours/+page.server.ts similarity index 100% rename from src/routes/(maintainer)/completed_tours/+page.server.ts rename to src/routes/maintainer/completed_tours/+page.server.ts diff --git a/src/routes/(maintainer)/completed_tours/+page.svelte b/src/routes/maintainer/completed_tours/+page.svelte similarity index 100% rename from src/routes/(maintainer)/completed_tours/+page.svelte rename to src/routes/maintainer/completed_tours/+page.svelte diff --git a/src/routes/(user)/+layout.server.ts b/src/routes/user/+layout.server.ts similarity index 100% rename from src/routes/(user)/+layout.server.ts rename to src/routes/user/+layout.server.ts diff --git a/src/routes/(user)/+layout.svelte b/src/routes/user/+layout.svelte similarity index 81% rename from src/routes/(user)/+layout.svelte rename to src/routes/user/+layout.svelte index d5ca4ab3..f657caae 100644 --- a/src/routes/(user)/+layout.svelte +++ b/src/routes/user/+layout.svelte @@ -6,23 +6,23 @@ const routeLinks = [ { name: 'Taxi', - href: '/taxi' + href: '/user/taxi' }, { name: 'Stammdaten', - href: '/company' + href: '/user/company' }, { name: 'Abgeschlossene Fahrten', - href: '/tours' + href: '/user/tours' }, { name: 'Fahrer', - href: '/drivers' + href: '/user/drivers' }, { name: 'Verwaltung', - href: '/administration' + href: '/user/administration' } ]; diff --git a/src/routes/(user)/administration/+page.server.ts b/src/routes/user/administration/+page.server.ts similarity index 100% rename from src/routes/(user)/administration/+page.server.ts rename to src/routes/user/administration/+page.server.ts diff --git a/src/routes/(user)/administration/+page.svelte b/src/routes/user/administration/+page.svelte similarity index 100% rename from src/routes/(user)/administration/+page.svelte rename to src/routes/user/administration/+page.svelte diff --git a/src/routes/(user)/company/+page.server.ts b/src/routes/user/company/+page.server.ts similarity index 100% rename from src/routes/(user)/company/+page.server.ts rename to src/routes/user/company/+page.server.ts diff --git a/src/routes/(user)/company/+page.svelte b/src/routes/user/company/+page.svelte similarity index 100% rename from src/routes/(user)/company/+page.svelte rename to src/routes/user/company/+page.svelte diff --git a/src/routes/(user)/company/intersects.test.ts b/src/routes/user/company/intersects.test.ts similarity index 100% rename from src/routes/(user)/company/intersects.test.ts rename to src/routes/user/company/intersects.test.ts diff --git a/src/routes/(user)/drivers/+page.server.ts b/src/routes/user/drivers/+page.server.ts similarity index 100% rename from src/routes/(user)/drivers/+page.server.ts rename to src/routes/user/drivers/+page.server.ts diff --git a/src/routes/(user)/drivers/+page.svelte b/src/routes/user/drivers/+page.svelte similarity index 100% rename from src/routes/(user)/drivers/+page.svelte rename to src/routes/user/drivers/+page.svelte diff --git a/src/routes/(user)/taxi/+page.server.ts b/src/routes/user/taxi/+page.server.ts similarity index 100% rename from src/routes/(user)/taxi/+page.server.ts rename to src/routes/user/taxi/+page.server.ts diff --git a/src/routes/(user)/taxi/+page.svelte b/src/routes/user/taxi/+page.svelte similarity index 99% rename from src/routes/(user)/taxi/+page.svelte rename to src/routes/user/taxi/+page.svelte index ec7ae3d7..b6d5147c 100644 --- a/src/routes/(user)/taxi/+page.svelte +++ b/src/routes/user/taxi/+page.svelte @@ -41,7 +41,7 @@ $effect(() => { const offset = value.toDate('UTC').getTimezoneOffset(); - goto(`/taxi?offset=${offset}&date=${value.toDate('UTC').toISOString().slice(0, 10)}`); + goto(`/user/taxi?offset=${offset}&date=${value.toDate('UTC').toISOString().slice(0, 10)}`); }); onMount(() => { diff --git a/src/routes/(user)/taxi/AddVehicle.svelte b/src/routes/user/taxi/AddVehicle.svelte similarity index 100% rename from src/routes/(user)/taxi/AddVehicle.svelte rename to src/routes/user/taxi/AddVehicle.svelte diff --git a/src/routes/(user)/taxi/types.ts b/src/routes/user/taxi/types.ts similarity index 100% rename from src/routes/(user)/taxi/types.ts rename to src/routes/user/taxi/types.ts diff --git a/src/routes/(user)/tours/+page.server.ts b/src/routes/user/tours/+page.server.ts similarity index 100% rename from src/routes/(user)/tours/+page.server.ts rename to src/routes/user/tours/+page.server.ts diff --git a/src/routes/(user)/tours/+page.svelte b/src/routes/user/tours/+page.svelte similarity index 100% rename from src/routes/(user)/tours/+page.svelte rename to src/routes/user/tours/+page.svelte From 6a18b4658fe532fa1ca476f1cdfd45a7f2db2ee7 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 24 Oct 2024 15:46:12 +0200 Subject: [PATCH 02/28] basic andriod app setup --- .../.gradle/8.7/checksums/checksums.lock | Bin 0 -> 17 bytes ...rariesForLibs$AndroidPluginAccessors.class | Bin 0 -> 920 bytes ...ForLibs$AndroidxCoreLibraryAccessors.class | Bin 0 -> 918 bytes ...ibs$AndroidxEspressoLibraryAccessors.class | Bin 0 -> 932 bytes ...riesForLibs$AndroidxLibraryAccessors.class | Bin 0 -> 1911 bytes .../dm/LibrariesForLibs$BundleAccessors.class | Bin 0 -> 765 bytes ...rLibs$JetbrainsKotlinPluginAccessors.class | Bin 0 -> 937 bytes ...riesForLibs$JetbrainsPluginAccessors.class | Bin 0 -> 1175 bytes .../dm/LibrariesForLibs$PluginAccessors.class | Bin 0 -> 1504 bytes .../LibrariesForLibs$VersionAccessors.class | Bin 0 -> 1435 bytes .../accessors/dm/LibrariesForLibs.class | Bin 0 -> 4000 bytes ...nPluginsBlock$AndroidPluginAccessors.class | Bin 0 -> 962 bytes ...nsBlock$AndroidxCoreLibraryAccessors.class | Bin 0 -> 2218 bytes ...ock$AndroidxEspressoLibraryAccessors.class | Bin 0 -> 2232 bytes ...luginsBlock$AndroidxLibraryAccessors.class | Bin 0 -> 3448 bytes ...orLibsInPluginsBlock$BundleAccessors.class | Bin 0 -> 891 bytes ...Block$JetbrainsKotlinPluginAccessors.class | Bin 0 -> 979 bytes ...luginsBlock$JetbrainsPluginAccessors.class | Bin 0 -> 1259 bytes ...orLibsInPluginsBlock$PluginAccessors.class | Bin 0 -> 1630 bytes ...rLibsInPluginsBlock$VersionAccessors.class | Bin 0 -> 1477 bytes .../dm/LibrariesForLibsInPluginsBlock.class | Bin 0 -> 5631 bytes .../metadata.bin | Bin 0 -> 99 bytes .../gradle/accessors/dm/LibrariesForLibs.java | 313 +++++++++++++++ .../dm/LibrariesForLibsInPluginsBlock.java | 369 ++++++++++++++++++ .../8.7/dependencies-accessors/gc.properties | 0 .../8.7/executionHistory/executionHistory.bin | Bin 0 -> 1062082 bytes .../executionHistory/executionHistory.lock | Bin 0 -> 17 bytes .../.gradle/8.7/fileChanges/last-build.bin | Bin 0 -> 1 bytes .../.gradle/8.7/fileHashes/fileHashes.bin | Bin 0 -> 74915 bytes .../.gradle/8.7/fileHashes/fileHashes.lock | Bin 0 -> 17 bytes .../8.7/fileHashes/resourceHashesCache.bin | Bin 0 -> 19483 bytes driver-app/.gradle/8.7/gc.properties | 0 .../buildOutputCleanup.lock | Bin 0 -> 17 bytes .../buildOutputCleanup/cache.properties | 2 + .../buildOutputCleanup/outputFiles.bin | Bin 0 -> 22007 bytes driver-app/.gradle/config.properties | 2 + driver-app/.gradle/file-system.probe | Bin 0 -> 8 bytes driver-app/.gradle/vcs-1/gc.properties | 0 driver-app/app/.gitignore | 1 + driver-app/app/build.gradle.kts | 55 +++ driver-app/app/proguard-rules.pro | 21 + .../de/motis/prima/ExampleInstrumentedTest.kt | 24 ++ driver-app/app/src/main/AndroidManifest.xml | 26 ++ .../main/java/de/motis/prima/MainActivity.kt | 13 + .../res/drawable/ic_launcher_background.xml | 170 ++++++++ .../res/drawable/ic_launcher_foreground.xml | 30 ++ .../app/src/main/res/layout/activity_main.xml | 6 + .../res/mipmap-anydpi-v26/ic_launcher.xml | 6 + .../mipmap-anydpi-v26/ic_launcher_round.xml | 6 + .../src/main/res/mipmap-hdpi/ic_launcher.webp | Bin 0 -> 1404 bytes .../res/mipmap-hdpi/ic_launcher_round.webp | Bin 0 -> 2898 bytes .../src/main/res/mipmap-mdpi/ic_launcher.webp | Bin 0 -> 982 bytes .../res/mipmap-mdpi/ic_launcher_round.webp | Bin 0 -> 1772 bytes .../main/res/mipmap-xhdpi/ic_launcher.webp | Bin 0 -> 1900 bytes .../res/mipmap-xhdpi/ic_launcher_round.webp | Bin 0 -> 3918 bytes .../main/res/mipmap-xxhdpi/ic_launcher.webp | Bin 0 -> 2884 bytes .../res/mipmap-xxhdpi/ic_launcher_round.webp | Bin 0 -> 5914 bytes .../main/res/mipmap-xxxhdpi/ic_launcher.webp | Bin 0 -> 3844 bytes .../res/mipmap-xxxhdpi/ic_launcher_round.webp | Bin 0 -> 7778 bytes .../app/src/main/res/values-night/themes.xml | 16 + driver-app/app/src/main/res/values/colors.xml | 10 + .../app/src/main/res/values/strings.xml | 3 + driver-app/app/src/main/res/values/themes.xml | 16 + .../app/src/main/res/xml/backup_rules.xml | 13 + .../main/res/xml/data_extraction_rules.xml | 19 + .../java/de/motis/prima/ExampleUnitTest.kt | 17 + driver-app/build.gradle.kts | 5 + driver-app/gradle.properties | 23 ++ driver-app/gradle/libs.versions.toml | 24 ++ driver-app/gradle/wrapper/gradle-wrapper.jar | Bin 0 -> 59203 bytes .../gradle/wrapper/gradle-wrapper.properties | 6 + driver-app/gradlew | 185 +++++++++ driver-app/gradlew.bat | 89 +++++ driver-app/local.properties | 10 + driver-app/settings.gradle.kts | 24 ++ 75 files changed, 1504 insertions(+) create mode 100644 driver-app/.gradle/8.7/checksums/checksums.lock create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$BundleAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$JetbrainsKotlinPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$JetbrainsPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$PluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxEspressoLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$BundleAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsKotlinPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.class create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java create mode 100644 driver-app/.gradle/8.7/dependencies-accessors/gc.properties create mode 100644 driver-app/.gradle/8.7/executionHistory/executionHistory.bin create mode 100644 driver-app/.gradle/8.7/executionHistory/executionHistory.lock create mode 100644 driver-app/.gradle/8.7/fileChanges/last-build.bin create mode 100644 driver-app/.gradle/8.7/fileHashes/fileHashes.bin create mode 100644 driver-app/.gradle/8.7/fileHashes/fileHashes.lock create mode 100644 driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin create mode 100644 driver-app/.gradle/8.7/gc.properties create mode 100644 driver-app/.gradle/buildOutputCleanup/buildOutputCleanup.lock create mode 100644 driver-app/.gradle/buildOutputCleanup/cache.properties create mode 100644 driver-app/.gradle/buildOutputCleanup/outputFiles.bin create mode 100644 driver-app/.gradle/config.properties create mode 100644 driver-app/.gradle/file-system.probe create mode 100644 driver-app/.gradle/vcs-1/gc.properties create mode 100644 driver-app/app/.gitignore create mode 100644 driver-app/app/build.gradle.kts create mode 100644 driver-app/app/proguard-rules.pro create mode 100644 driver-app/app/src/androidTest/java/de/motis/prima/ExampleInstrumentedTest.kt create mode 100644 driver-app/app/src/main/AndroidManifest.xml create mode 100644 driver-app/app/src/main/java/de/motis/prima/MainActivity.kt create mode 100644 driver-app/app/src/main/res/drawable/ic_launcher_background.xml create mode 100644 driver-app/app/src/main/res/drawable/ic_launcher_foreground.xml create mode 100644 driver-app/app/src/main/res/layout/activity_main.xml create mode 100644 driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml create mode 100644 driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml create mode 100644 driver-app/app/src/main/res/mipmap-hdpi/ic_launcher.webp create mode 100644 driver-app/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp create mode 100644 driver-app/app/src/main/res/mipmap-mdpi/ic_launcher.webp create mode 100644 driver-app/app/src/main/res/mipmap-mdpi/ic_launcher_round.webp create mode 100644 driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher.webp create mode 100644 driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp create mode 100644 driver-app/app/src/main/res/mipmap-xxhdpi/ic_launcher.webp create mode 100644 driver-app/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp create mode 100644 driver-app/app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp create mode 100644 driver-app/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp create mode 100644 driver-app/app/src/main/res/values-night/themes.xml create mode 100644 driver-app/app/src/main/res/values/colors.xml create mode 100644 driver-app/app/src/main/res/values/strings.xml create mode 100644 driver-app/app/src/main/res/values/themes.xml create mode 100644 driver-app/app/src/main/res/xml/backup_rules.xml create mode 100644 driver-app/app/src/main/res/xml/data_extraction_rules.xml create mode 100644 driver-app/app/src/test/java/de/motis/prima/ExampleUnitTest.kt create mode 100644 driver-app/build.gradle.kts create mode 100644 driver-app/gradle.properties create mode 100644 driver-app/gradle/libs.versions.toml create mode 100644 driver-app/gradle/wrapper/gradle-wrapper.jar create mode 100644 driver-app/gradle/wrapper/gradle-wrapper.properties create mode 100755 driver-app/gradlew create mode 100644 driver-app/gradlew.bat create mode 100644 driver-app/local.properties create mode 100644 driver-app/settings.gradle.kts diff --git a/driver-app/.gradle/8.7/checksums/checksums.lock b/driver-app/.gradle/8.7/checksums/checksums.lock new file mode 100644 index 0000000000000000000000000000000000000000..3d91ceb22ee1f2f86f01854347be44b4af3eced1 GIT binary patch literal 17 ScmZP$+sGNIyh~ey0SW*iz5<;9 literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..0e55e2b9966b9fa80c88d12163743a88c5b25fa3 GIT binary patch literal 920 zcmbVLO-~d-5PiKM!>$Vm2#TLE*~6lSz8EhO2(85B5#V+n(N#LV(narF@bCRmi zQky`|s9Yv0sN809F!jNyB)tDx|2U+AOiCs>A92*W^WJe@X4=e70!#ba=x`vA^v8|j zg|lZmB`1$(&MYZz0)7|bL0zkEYH$e^=q8R-pgJz_wm<%&&XmlR z$>bzBZL)Z`*~YbgV}Zq?O-W#FtPLHNr&DsD)HLVFYDQsj)qp^+f2)G+iO!4)rQ;e$ zw@BHaXIWfmCreMV?(9n5_<-4VCbo15jdaCut2wN_Y6Lu*55|xi=E{5W5q1Oy^W*-n ztrA$N3C&g{!V`i1eA!EBZcSg7>1uHvw!#bp_b2@##4h_yMAquU`Lz_|C4t zJ+>79Vx8?eHaMvUSIHH4Bl>~%w+46zn;dE3KEGQR-Zmcaw@Po}As(U4EFR-2+W!Eo CG!DQ3 literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..8756f5836d35130fb019844c0478ba2a5fbadfb8 GIT binary patch literal 918 zcmbtTO>Yx15Pc3I+k`-AY56Rzka9?i6kiaRRF$I8NQe|61@(+~*Q^X1I~sed^wrJv(@&C)%dkCbI#19nD&!BL2fEP}?`wgad&=d-&gX zba#(eup+RgY)a0g(@x?@cix9-0}Wh@&}`y5ZU`JMUX>);dq-ZTV>vW2DKgp*9I@_O zz4J_cPIPuS>&*dNeL`9VE%3BGe5X#7%$3dLD3GyPcX#Mb3S#V=OF;IQt5X!rTjt8kBc^1m@;Q}9 zE-iBXo4f7-*WDPof)YJ2Wv!dbZR?cH5NJNPR#QJ$-fJJ>oRX@Jk@UF4(}zrg1fk1t#c6%@DTN1)8`Ld literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..bc2da5db48b709b721964615505c3f2aa9eda632 GIT binary patch literal 932 zcmbtT&2AGh5dIuOwh4jK(w6@MQVwY=#TUdSRi!92Ql%6j1@(+~*Q|^-b~N@@%~NpY zG2j9c2OfZjLd>>_h(aYQICwlWo^L#!Z~Wuux9&n^yL>WQ|gw#jtBUPsf`sEGe?3e@(EHQ_*D&>sHx z9o?Oi6|4wsDVvfr=~+kn32EgLD_7Uz2^cK7SPZK4uaoJ2o zcqGtX%s!{-GHwN){*7Hc*dJxuI^nC{*@*o zi6;I4f0S{qyV*$*|be>g`u3S z{Iiez+=hZahSG5)O%tx`NLSVCYQ?NcE=}Q<9Z739Q?PaEnEGzfk)o~KD+C5{B+#!Q znZzXwFci854FfX7oR7AU48{MDYXS;-{1`7Mk-`;*8H;NgC3aR$49`!v4sz|fIC%xb z469w&q~tcF{~qDmB#>@rGn<TxXaKWpkP#!>jHyIt?t}hcSi}KkSMH-e_n}y}`W% z)%j);6PToy)uiB_U|7mlw)qZMEp8iX)sv=eB3AxT|7M&yw;T3{77&6&&xL}A^O~dA1Qxd|~IZT$radYXJ z?}@sux<(AGb1Pu>nxi)@aYW_(N}i#Qf_&LdM4_cmC+d!n--|aJLqDMgug0);5#+!; z+Yx15Pc45mWGruge`ey?Dw8$#{Tx>%U1v|@vw^)Ze?iquz`-jX^^oU3zZdHnmFrx zV)0bjf)Z6>Z2NgkLPdJ_aei>b6ZR$hVmj2_Ak)3KjaT*}GU&W^-laFjboNJU;&mvw zvZwha7iob%T*pi#T)C3Po-Lfe0dHh_#23_5>6|6H;0N>kZ|E;+l#;l-NgVBQT{nsH ziu=pGf8I)x+=X@^+A>ylKoiPc<l7(|)19l2ac z9LHf0_2Z(O{cDUtd!Su2*d960CrzERe3+$b(0v~oDR}5+!J~DdgG;(1gWj?CEQ5+- zfgc5Ph4Lx(O+TLZN&WA?1+rk-Y#HSCyiaARsE0f_mTBgSExojds@+{a0`S zi32}?AB7mliHK5!Dr9*)JDxXsZ)W!AukSwqJi~SaH7rF~ZsHPF1m0Pf$;_!VC#l9- zY7@vAmCHm0mD@~qM?N@}gqNSHANw>Wlafi!`W&_HtaX?dnKsjtz{;*RI_wD~?ZHCv zv9qT-B_|K3&J+|cCZ1!lPajl~ha+-cThpt!#XCodfwhXzbXOwW6KKzuosH#hlN8wg_bl;{ccjKw18hZkC)lp@=>eAb0is8b zpL~P(!mhwowq*juQ?}Qz!JsO+1eeJh(O1+zFC;(5b&k|440*W4{0!(9u@Y2{gjIHP;G8BCk zDxFHJMG{6L6^V(%X4j=wMCsFa!;2l+m%1l)bkb(6u_x92WDqMok_a=8l~(B!LR9PI zg7>XCRy}FM{Sh;AYUB;iRIwuu#UM!!q;<;Z*08q5_JM~>glE5}i6ZHou`cW#g&ozk z!Yb+7#xn1!&t=LQrQM!M6QzfhH^(kMO1SJH2r!E|Li69l<^mG@@sk~4JO9e@-5EHt zLKXsC!6L&M8GWc?!o$4#IYBDHLotiE9N-$R6E^!IiWreUgF)DxNH_-R0=PB^Q!Uez zg!zur^2Ok&EA4C1O<3c{G95O9uveRe=>JldUYUW7WLsrvmh+=<|E)L{gkV=|Xv0AI9>C5>+P>3iYZ9xfIQ3`(C+-<|kbua8)iv3p# zmV$ymz@MZj&XG%LuLjb7xShGZnP;APcJ_Y${q_UEV?45vL*7Ec!2~7=Z$i^`yGHnd zbVX0OO2^V@5xAa+MG$t~W+#e`@Z!x+gAW_BC$%rNcd*5~p*dLE4*FfC(>KE8Go@Ah zoZ!{k8StJ7_mwY=yPY~|QX?C9hQ)^575yOIktR~1ZVk9KmUk>%BD^?R#`9zpg(h8awKhJipzOs4*s(**|q5c&`eo9BUeu!z_s+`!md5HNhoItq4YZ(Pz|1jJy z%;7gy*(WZ(n8H`t5=Trh-t=d725CukP{QOMmUvB=oD7}Mh9=G2=b#)O;33;ZuA4&* Ubrkt>uV9U>&32t_g{_O?KT58^+5i9m literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..903d941f68f3cdadca775ec6ff6e5c4d596acd4a GIT binary patch literal 1435 zcmbW0OK;Oa6ot>EZS16>Ers%i@(7SVsCfy2QdNr5MuG-ZDX9C2Ggwocu{Cz8_Sdjx z2SNe~3ARY=ShHr$KR{e3PGyo=R4CHq`p*44=ghtS{^#>o01xq?h#V#?OqMW(Ji|_) zJ;&3$;|qs}(vd0_T5;cTdCdL5b877<*4&M^4h9>WA{444lzZ5qY@iRzyFy1YQ0XH> zeqAaVZ!ox(=E&Pa9qh}F(9TX8q)>IVa7@Ogc*T2uoSs!5h^sE`+OQcWxEB^t#I%J{ z2`4ba@FaV(>xw7}bmVlpPE)ou*HT1{KvNtI<=2Kq3`I{24`O&!Y3}iT?)Y4JPAk?@ zdDW#+xnsVnHs%-#JPh5S8}iu3JcH#1T5QJ$Hcm5?L=@^oR-KYI&M-{v_2}MgoTJTt zn3}b5fiCrR5c^WuxWr(0IrTzvpJB2dbOgg}Q!4SI*KG^^lDB=z=y1ZRI=|K zPLXNU80J#^XxMO##x_S^CQty40P?h6rl&2@P^h!TqSf+ zoa<+;<$3EP3hzdW-_j|d((6=o!vxJ5pbr_SY=TZ2pf4HdrU^P_fWBp*TPA410R6~7 zw@uJl1N1WkRZP%%1N18cEt#N;2I%(@l*4lW@>j4*|MS#_9PYrOb{BCM_fhx@xEf8Z literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class new file mode 100644 index 0000000000000000000000000000000000000000..34a5842efa753171490776dca19bb18610d73fa3 GIT binary patch literal 4000 zcmb_fdsiDp6#q>NETmi8qNQLT6pNOokJXBOg+9^%6$%tfMeDPh%@7ASyK#0?;e+@+ z^c*SY=sA7>Ka|Jc=G8JuAo2Le=I+ki_x;VCo4^10<1YZyh*CI&!xs8%^kYCE8|tD{ z)Na9-j$2la3Sy}P*LOTOcKxvEWb;w1T`!*7s%^~5vJ46`@V4i<8tQF{yN6M zT$~cP-EAEv>*#FeASvjWjdyWcV5osjmg|yPrp8_iZW9e>ZJfh6kBb)u8>%R9(-d#1 za{JSg!U!gklDsG2wUnfz5C73x4bPJ{-p2<5r(V|TWu{1A@7dh9PNp#HGbM1V>-s#b z1ngIP%9FNn8CL|Xu-Xe)oJlj@cD*90%QYJgJ`_0dx+0 zKE|}bsMn!o2t4R)rn{z-!bRLjAaS!@7j751Y4QJtjj6xK#B~<$E+IA4-nMZE8G(^} z4YdYv1n%syvoB~3Sz`8XFPL5RD@7GFF`L2+CK7Z!u#v?>x>&BcXz=yqq9L0Z#4PWW z%?fYl6ivT&)6QPb)#JN^)IAD!FTepng^Ic%H19-r~TK+}+MXm9SKUMHw$9 z9`giGb>R#<@|r3JZd}o{_@WDunLRb<%;Pp8wah`Lk zGxp@Gad!#K8Rqu|R71?XaqBkfO_Hg)+l$tg-YSryk2UmC*-S6WOw8AG)nL}EE)$&8 zwH8*iC+Agym6PT)bS;6Vz-hBuD`Buw@%?OBF;VtHz=0{}yHOR#MV^SVrR6|mW3aAr*$1qJ)151 zN7`>#2m}^-)xI?sm31-{o995_e50J5SS{OBa)+OO0jHt9(A%#V0$s#qF6lB<}6t{%-!G?FY&mA2IeBnw{Z;%4DYPVdG17}B^QO_ z$^_|*&^#4EXq)q7?1K|&c=M_Lu`3H{GHKG&K1HoN?dG=M{nIy%tz)LK4&W*5Q@7(^YnvW*lDcvoOU@G++NqNw$U4sO zsyjRsCxUBXay|-9nLOT{ZR%3@F~fY%W|CoLsEphzkH^w|5Mxb|9PiSUplm@a!R)V~#GSpT!ectRW0pgRMythy{@SLn2XIeLKT z+4C3Qz`l^naD!|G02`3KiB(Ff!BuhvUX8w@`FRHX9%~e7;1<2N&%AZqp>LJmz+K!& LlUO{!BQ$>l>)9XX literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..230a2e82e7bf8c871486d4fe456c88a7c8f328d6 GIT binary patch literal 2218 zcmb_e-&Y$&6#fPxOJcMoR{LT+@?X&9xMP>1(qaDM}zPA8Nm64ulS*ugq}< zfhm<4?h3Q-MXpqV+4X#TuUbF>FB>Qp@d{pLxRHtR5Ccc_wIDa-&7u_3e#>`Vp&3f) zyl9ABK9GJy#%`tch!42saphX=P*be6g)9OmdEcZ2xhoox^cA6Q|)TVKsVRcJ+ z2WAwAG~Wb>G{*#plK?2;H3JulcpbA0FEm7k!ebfk)}4X01;f^h#iUk132zi}5pOcg zK9-)>5cfsT9|&hdttVVwX4tNr1@`YK{1ke+{s*!rJgEd>e~Dpf&kt$TaRRS%$N{I5 z;@uhFLMLHb0ax(00kepAaFyZPQxNT6R5&IkhPfE*?S5RwVm*?MXbU?gEyK0S#?$C{ z#L%toBU)QCP-eJ$#?X8_>IoGl^-{n*-Yeo7Dh!6=?sgDY%w#1l%Qr0>IWO@-l(n{aaot^W4~+UcC_?h zq#3lGM9J2Ihs4O6CowYC!oKzg1g5s`jXO1l+?wyu{&OuN!#7c{EA#{2^~f^iitui@ z&rtp+?~Zd+NZBPEhJ0JPiieRVN8dlk{*`RC#wTzc%7>)Kfwf7p+v8p;*PFf*d4kRw zi+1f6C2{e7q(Wl!jtnFPUsuW>-5NnOo8ik*h_tEDCVjI-Q^wiOKl>W0F~Jy$8%hbi z=J6m9fdP69>e*}kU(XH0g{M6@2I>sU8Skf)SrYTZWHVwucWlYcBr{pY8)y=*G7+4D zwhWh^MO;#jC3?2w&jeWfaMSM%8eO4rY@b@Z{wvr|)MNNC9#aeaK))Z+o1aV8u3|E= zmP^KO$d}FyG4lkaA?D6cm);uU@)OJt@$O=2VTkKL9(s!ZE&xB{GJe4))B|qPcLJZ{ zGiu{=mZ{C*^Tb*kugT7>(99ymJb^FpWiC(By^03%6#FXHsGX z_$EWM);jYZ_1T>XOfY=e@O@#eRG}NmuHi-s>uTe66GaJF_rB3RcOZ5+_g8^J*Of??~~Vp1=mf>+A8gjX4+9?2+L z5qCsS4@9t`)-x_IGHln*0{cA*KZl-<|E}zbNGd_tzs@lKP{;Jv32f9kd9A$oo7zy{Zm8P_#l4c&cC|5dzBcrIFn#Yp zJjey9lWzo%iJCV~qGl?JeWM42s_||QJ9UP!RUOd!b1h=U*GaD{%w67%$l`<|UZq?Z zs()qRah^&!&qTm5*_NT=agwh8_CKs&D%Nef12?g}Ps(h)O%mW9k8_W#IxK)Q;iP%vvALDUL1C$Q;Eyg3s{z*dz)0GFC82u`gql+8JtZQ9F+{tYh*|N3F)0 literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..484959aa81aa850b65a8df51948053fd4b27b263 GIT binary patch literal 3448 zcmb_eTUQ%Z6#fnb2GX&m5lgGBjwRASD`RUd(jXEjAT$(8xQJEL$;@duFqz4kOMoAs z&-$!CqOR3am#*dNvp>q^o+JYyCQu9y$v(H)m+yT0?EUvYfBXgDF7znc&@Le&qXV4` zYqpbD^NwbiT-Ay~6_&>xOEXnn^EA`WtErspIhyWG?^ZS*@FKSiZs~h7v}!wh@rnbv zQAP}JGxVF9u2ay*MaZyv#B>;Wi@+r%yu+~GB3{#O(FyLc9=9lZE0JE7aRu)(+^CDR z*@p}ptw!5Sb+QXr8Rje05msI?L)s~}qvU*xvdC4QId(xQamN+5rBu_%RfMH@n_MYY zXsP4^UJgg`K0c73$oLS~8E)5Ld60+(CxA!|X;UfB!g1Qp=L1&7!hJr;H?@+meOk;V z(py?dQ%%jvs~OKBUz3BisGOvIfv!Z$^GRQr26y72-9sA$MVw(`(K7cG-{oPvZU96W zV;P8(02sgx2?-g47-Be67a5{E!rM$4C82Xl?6bur8N~o@$@mz<43~Cw)GqgmE)&FldOjBJQ^wt5TMGSi~C zgHI*gmGK$wF+4s6(dwws#3zQn0PNLbP)qo%FASdHdO%vr+{9cXIvz4~F}Fo$={@I6>nlAE@U&wK1 zMa!AABImi63jJV+A7xHs6GZWlAKYN*&WOCFdA>vHp1#5NW3~AfSkN3#JfpJistZ)T z3z`{L{RP|bO-{C|wLdwYWVo{ITOM(8O}K(WNLiL$!QG{dsJZb&7wMxe3Uj^!g+#-k zB2y8mbM~w%6vH{P5kBV(Pg=JVDyy$o6k0SxkFU;WL~xz`l>^OMlHq{;bm?;z^#)U> z=DOUKu+EUG;s5_@$QXJXwPX^$Au88ue{+->t{&fDTn@MEVPR0ht!Btc$TE!9ICi?? zM0tEbu$mIs*Yu&fSl+39C#d=cZ87K<3)(6g#e$}TWCy5$Lnr-D)9fom%ID%kH(!Ab z{RwGf=mol8;lfMw(6qNYz4Q`&ztMT>e#^Qd^uJAdHmRu*=%+EmY*|~Nbpq`)2ja2! ze#f;~|2{r?je&jK?CFZB`?&oYBl{Q~ihZ$G?5)zyeQLVfu!gTA-89<369gUj2EHZPOY%FC1Na_KN!}r;ksKkJ GL-)V&T_^Iv?+gp*(;)KM3 z58$H^vm_0n6;xtZ_RM(ZJ=@Rr_a9%s0eFdrZ8UHrL9>Gmv;UQ((BRM3zwq&NH%6#|6>I|BXn zjsDkt64?6VMkRP4@M@j*LXGS7W1$vYD+Tcg3BQ2)6a4cV;C_>%J@#5`JJ0r?A9S1D vjV}Yx15PeQdw+ShQ@>RZy5ILlP;tS%Es!~XaRESEYK=01(uyVVxBimcie+3ti zIPe4bQHa@WBBE3(6$rjyf%n#>GIc7+NUE`x z+5~b&WinPlWj2+ap$|^Q;mzmrV2{RR5;E~wkE7O|H4d{p)n>XASlQ7=hh2fV*!;fS2q)^tm5?d_vgtO{%%Qy4m>jc=XUkZIFWCUI6L zHPmo5LcNYPTod>>PbZGad+WSRMzXIN?lk$Hb?p0nQ}*OvXEr`*yq%SQH>qBpb!G(w z>aimgsEiA|YW9!Ssgjv8sT>5SP1@dG?C{(u+5*d6n~=bIUmH5eM?-QS)G*^nEv3*Y zTM}qAFIB8M(5X=&cZ@%{1Y~EP;dmmc%st7ntG}wZcbREzU~?B!PZ#W-UOc{5F$^Bk zzA@ywnev`|gnI&=c{%>;>Itls^rrVH!b2YaeA$^u|5jOG>tdbpgl|)Y9}(D!;`Ojy z=iOs0@drfDp1=4G@s(YH>uiez2x5B!8w@Iw3viLV5q(4T%R=%9H#t(lE&gv$ygRtd RYXPrd6ZcVN77y?U)j#?HCk+4q literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..a4118f6539525518602efac84b9a52c83b1fb207 GIT binary patch literal 1259 zcmb_cZBG+H5Pr4=&Z`F~qCypXp%|#f`(iY)#-tXTppBBKRlb;Px65Vq*ll*NME;c~ z8WK(X0sbiCoP9}q7)0WSyP4gYd7ioFX7|U>uipXO!HoiP$a|OwFo`LK=f*~1WO+N5 zA@8VA=|o!1<52K~$0iD^Etgm>lE)uy**8UT>B4riW7uuSRKvkj@$F!uD?1 zP%X=?lCEwn`EFD9dUcOtBi@&u$b{lbyQe0JRX$U;oF%f1awe&8{^PJDr2%_Oq?c(ghb1hNEfP=;SExCkM)*2PWD8_h G;r{}3&V;uB literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..6f1f3eeaf1196e10266cfbb3fbad07908cc58516 GIT binary patch literal 1630 zcmbVMT~8B16g|@dYu81zB32QR4;9MC8Wnx0F)76+kg5<2iI3CWp&4Cfo0%<{CzB+oly*E<#fI4DtsvSH+Q?8<+O?Gy_bgmtc-x)E^Mo;>Hm-l* z)?{6CErqFun&xIxwQDu&LFj#+FDqY%(r>SoJApaaxN5<1Fp6so6#7q~j?X2)Q>YBN z4tv9}m?qrWJEu%s&2bG!^?E|CH1mlAsZv!axj703{y?+dBpHyCFpjX zNz@1Xivdd(?xe0L-54sjf|>gsueK7-1|dGL*X?(?H#ZVYFRa(mE_GGrZ`Ay}Y6f6Blbrr7AHOP^<>PxuHVYPaSsJJ5Z-?etvMa@<tPgoy|-;twl>;yND zF-}W`uBE%jnEXZo3=e3`V~D0})U=<{D|$w}*Jx)3vkCkZSw?=tgg5^6G%U^zR-$nZ t^EAelbh}QbUDt`oLvqUC5gwDBrMwv|poko`k0q>-waKoMEs%AQ`wQ17@K68% literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class new file mode 100644 index 0000000000000000000000000000000000000000..b4504975e5c69d72f167ec21228539ac65c84075 GIT binary patch literal 1477 zcmbW0T~8B16o%g^(A|~_h@bd{3Tj)B^()4tgrpWQNHruF?x)*vGq9c6%x($%E4|Ug z3x9yOUVH7e*CxiZ?Ut_$c^uT~i@ene%>#tcJ&2Z5_Q0gr6VGFYxQVmmsrah{TJXnuL(&Wh}bC*)tQ- zR1s}%_e3*HlKtvLba7XAjVm@~EOg=T*Siv59@Vv_lrRmShoJ~9tT5EmjvU!%hYfw`jm~^oD@~XgrXo^*VjcV~l=)Rb5*C2=<;#h8wiT z0l-&U=W&zJesHemwW_n$2Nd271%IO~pwQbCw2%c&XF%Um&|(&JHUs*Rg6?EN=Q5z5 zDd=t%bYT=?6DjCk7IY~CnodFGENCtRnoB{IEa++mv~U9DQ0+B;3Cr|9OV^OYeK>U8 KMLfVG6n+Ba;?Z+F{_G#+@q3v}nobhhrv8xJnR)Z>^4;&fd*A%??;n2wcm%)1u@38F*r1^W ztpa_vlTYOxJ!i_4UNlmMH+RrQ;g5H4qp{N2e7Xd&bB~Cv~QLQMOg{V!_TyGj%$1 zMP|K5?^Ht4J6q4 zXLQGvPI~`jJKE45LtMjc&;$-wW0K8E*R>t$D5OS>jH5e-bO&vR*Y2=&#`N=s<@TF) z_NqXOea(`Nz(5q9N<=G8QaXm)1x`2TNmrkhb8I6w8#p}I7X}f>Mr>9@+9EKxeD0T} zQW?8DG~9{11a_NxHcM<8nHP9^2{NHu%VXOxBI2}7V5mu)%B-&7qlnO{;cjdfXb(B< z3hZCvHdkFZR>OCtVW);&*v(~@wXJC*FYs7&dJP}yud+C{VvkDKJp$R9bT#y$No&D6 z=+ba6?i1KH6XY@qk-+d0{j11fR26gAO&&IxyMEu|9=IfRJsR%E0fCrZ+FzKst|h)Q zarO2em9s+{Qg}dM%i^9>-d_ZcMU_<2xA^j{HYlb4Aq@}X5rK|ugKbFQcw;jw+sNYB zhr^04kJa1R>qQ>5_s(+QhHJ-jQKmtY|(eMP)0$Vcyqa(x-cxs8ARS-I&iF|&t zc|HfFq{8Poda*|_=eUMG^wa%f;C|%2HMk$qly1Wbfsw!i!^$Vku-qkWCz&ZNH#a%$ z*oEXw&oZ4io4F38iCIhXWZ8OG}>Ai@|+Kr9EqI8MiKM#IxMD^N|dHM=Mfzh-!s`*Jfz zRi|1l^Uc(D`kxj-bh!&wj1D{w971-yC zs_~XXK3m-hHn8+sU|;ueJvuHjG-!6YIb0GrwMN(MtY45;(7whog^Y$Qa;$ikoe5>vl+eOv&oNh2f3`lz!lYxI8ygWmcz@DMI9_^Y5@~t3bYld!ZCDSZWv%Q zFR*EpSsV8Y8R?u;9lAj0S>N)Q&Pl^HRLgEz<&K*b`K}UJvplz`BS31nB)B`b<)t^G zJZ8~eN~`+LkpCfhBmrojF!Gk}`3}urTEYC@>cyxm=#`Q(#=}uTH^cMOn4R-YNn7Pp zRQjl@B~>Y3bb|x8F^sVaLh3GTh6N@feyyU?gi4|fec58Uvm(5wnzvEYo)KdD9~3#N z9%){6v`_|`gZi^J&4G?e)g&JA2^NX095fUY_XdD9IWw6Z z&$*XZdB8?vrH9_G5$W+z%ro$*(uN%gPGHxqUx?wW=8w4*)iqW-8V$wpt-x55v6eGm zV{L2wff&9QxUe=`vnO3PMf?I0UHJmZkcf?5iQy-1I%~8)U^}wb_KwhYy6u5Y z=TB_B*mDE1o7gmu1aG&h+YbJA+(dF7d--UedbB@$OnH#M2XErhc|6YH-l`c#=W*;e z8WOPhzl&}FNxIyD&FI8#eh7F7+u6MBK#oD#9Bt*h#nOzI;9x_^-Q!r#r$AR?;CGx% zoLa!x-xy!O#OAidg#}#v8&eC=dlGU1`Cm(Ol{NKU4>*XOI0TnhfXClD_!T=dycf8( zYCBi!*h$k)?=9`jVvcbr_>Y$3x#!mL+(054%^YV zmm#G$lA`aTogZl0@E+wp%J(UIDL$AHD5oetrTmQJUr>HY`8DM?l-DW0 Nqx^yLN6Mek{vRR52owMS literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin new file mode 100644 index 0000000000000000000000000000000000000000..0b6bada853bcb777c24bfd1907b45a75177e7fc7 GIT binary patch literal 99 zcmbPTS(RK^l4z7sT$Yw*o>^v+l#*YNXku2Lk}A;0&Cv1a#^k@+_y7Ibx%bZHjm%6P z$vKI|#i_-N0uMe)gq}}1@sLmb#SG0GDHA%1^Gl18K{7cFsTT3s-(G literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java new file mode 100644 index 00000000..726833de --- /dev/null +++ b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java @@ -0,0 +1,313 @@ +package org.gradle.accessors.dm; + +import org.gradle.api.NonNullApi; +import org.gradle.api.artifacts.MinimalExternalModuleDependency; +import org.gradle.plugin.use.PluginDependency; +import org.gradle.api.artifacts.ExternalModuleDependencyBundle; +import org.gradle.api.artifacts.MutableVersionConstraint; +import org.gradle.api.provider.Provider; +import org.gradle.api.model.ObjectFactory; +import org.gradle.api.provider.ProviderFactory; +import org.gradle.api.internal.catalog.AbstractExternalDependencyFactory; +import org.gradle.api.internal.catalog.DefaultVersionCatalog; +import java.util.Map; +import org.gradle.api.internal.attributes.ImmutableAttributesFactory; +import org.gradle.api.internal.artifacts.dsl.CapabilityNotationParser; +import javax.inject.Inject; + +/** + * A catalog of dependencies accessible via the {@code libs} extension. + */ +@NonNullApi +public class LibrariesForLibs extends AbstractExternalDependencyFactory { + + private final AbstractExternalDependencyFactory owner = this; + private final AndroidxLibraryAccessors laccForAndroidxLibraryAccessors = new AndroidxLibraryAccessors(owner); + private final VersionAccessors vaccForVersionAccessors = new VersionAccessors(providers, config); + private final BundleAccessors baccForBundleAccessors = new BundleAccessors(objects, providers, config, attributesFactory, capabilityNotationParser); + private final PluginAccessors paccForPluginAccessors = new PluginAccessors(providers, config); + + @Inject + public LibrariesForLibs(DefaultVersionCatalog config, ProviderFactory providers, ObjectFactory objects, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { + super(config, providers, objects, attributesFactory, capabilityNotationParser); + } + + /** + * Dependency provider for junit with junit:junit coordinates and + * with version reference junit + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getJunit() { + return create("junit"); + } + + /** + * Dependency provider for material with com.google.android.material:material coordinates and + * with version reference material + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getMaterial() { + return create("material"); + } + + /** + * Group of libraries at androidx + */ + public AndroidxLibraryAccessors getAndroidx() { + return laccForAndroidxLibraryAccessors; + } + + /** + * Group of versions at versions + */ + public VersionAccessors getVersions() { + return vaccForVersionAccessors; + } + + /** + * Group of bundles at bundles + */ + public BundleAccessors getBundles() { + return baccForBundleAccessors; + } + + /** + * Group of plugins at plugins + */ + public PluginAccessors getPlugins() { + return paccForPluginAccessors; + } + + public static class AndroidxLibraryAccessors extends SubDependencyFactory { + private final AndroidxCoreLibraryAccessors laccForAndroidxCoreLibraryAccessors = new AndroidxCoreLibraryAccessors(owner); + private final AndroidxEspressoLibraryAccessors laccForAndroidxEspressoLibraryAccessors = new AndroidxEspressoLibraryAccessors(owner); + + public AndroidxLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for appcompat with androidx.appcompat:appcompat coordinates and + * with version reference appcompat + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getAppcompat() { + return create("androidx.appcompat"); + } + + /** + * Dependency provider for junit with androidx.test.ext:junit coordinates and + * with version reference junitVersion + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getJunit() { + return create("androidx.junit"); + } + + /** + * Group of libraries at androidx.core + */ + public AndroidxCoreLibraryAccessors getCore() { + return laccForAndroidxCoreLibraryAccessors; + } + + /** + * Group of libraries at androidx.espresso + */ + public AndroidxEspressoLibraryAccessors getEspresso() { + return laccForAndroidxEspressoLibraryAccessors; + } + + } + + public static class AndroidxCoreLibraryAccessors extends SubDependencyFactory { + + public AndroidxCoreLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for ktx with androidx.core:core-ktx coordinates and + * with version reference coreKtx + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getKtx() { + return create("androidx.core.ktx"); + } + + } + + public static class AndroidxEspressoLibraryAccessors extends SubDependencyFactory { + + public AndroidxEspressoLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for core with androidx.test.espresso:espresso-core coordinates and + * with version reference espressoCore + *

+ * This dependency was declared in catalog libs.versions.toml + */ + public Provider getCore() { + return create("androidx.espresso.core"); + } + + } + + public static class VersionAccessors extends VersionFactory { + + public VersionAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Version alias agp with value 8.5.2 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getAgp() { return getVersion("agp"); } + + /** + * Version alias appcompat with value 1.7.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getAppcompat() { return getVersion("appcompat"); } + + /** + * Version alias coreKtx with value 1.13.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getCoreKtx() { return getVersion("coreKtx"); } + + /** + * Version alias espressoCore with value 3.6.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getEspressoCore() { return getVersion("espressoCore"); } + + /** + * Version alias junit with value 4.13.2 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getJunit() { return getVersion("junit"); } + + /** + * Version alias junitVersion with value 1.2.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getJunitVersion() { return getVersion("junitVersion"); } + + /** + * Version alias kotlin with value 1.9.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getKotlin() { return getVersion("kotlin"); } + + /** + * Version alias material with value 1.12.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getMaterial() { return getVersion("material"); } + + } + + public static class BundleAccessors extends BundleFactory { + + public BundleAccessors(ObjectFactory objects, ProviderFactory providers, DefaultVersionCatalog config, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { super(objects, providers, config, attributesFactory, capabilityNotationParser); } + + } + + public static class PluginAccessors extends PluginFactory { + private final AndroidPluginAccessors paccForAndroidPluginAccessors = new AndroidPluginAccessors(providers, config); + private final JetbrainsPluginAccessors paccForJetbrainsPluginAccessors = new JetbrainsPluginAccessors(providers, config); + + public PluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Group of plugins at plugins.android + */ + public AndroidPluginAccessors getAndroid() { + return paccForAndroidPluginAccessors; + } + + /** + * Group of plugins at plugins.jetbrains + */ + public JetbrainsPluginAccessors getJetbrains() { + return paccForJetbrainsPluginAccessors; + } + + } + + public static class AndroidPluginAccessors extends PluginFactory { + + public AndroidPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Plugin provider for android.application with plugin id com.android.application and + * with version reference agp + *

+ * This plugin was declared in catalog libs.versions.toml + */ + public Provider getApplication() { return createPlugin("android.application"); } + + } + + public static class JetbrainsPluginAccessors extends PluginFactory { + private final JetbrainsKotlinPluginAccessors paccForJetbrainsKotlinPluginAccessors = new JetbrainsKotlinPluginAccessors(providers, config); + + public JetbrainsPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Group of plugins at plugins.jetbrains.kotlin + */ + public JetbrainsKotlinPluginAccessors getKotlin() { + return paccForJetbrainsKotlinPluginAccessors; + } + + } + + public static class JetbrainsKotlinPluginAccessors extends PluginFactory { + + public JetbrainsKotlinPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Plugin provider for jetbrains.kotlin.android with plugin id org.jetbrains.kotlin.android and + * with version reference kotlin + *

+ * This plugin was declared in catalog libs.versions.toml + */ + public Provider getAndroid() { return createPlugin("jetbrains.kotlin.android"); } + + } + +} diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java new file mode 100644 index 00000000..19c6b8a0 --- /dev/null +++ b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java @@ -0,0 +1,369 @@ +package org.gradle.accessors.dm; + +import org.gradle.api.NonNullApi; +import org.gradle.api.artifacts.MinimalExternalModuleDependency; +import org.gradle.plugin.use.PluginDependency; +import org.gradle.api.artifacts.ExternalModuleDependencyBundle; +import org.gradle.api.artifacts.MutableVersionConstraint; +import org.gradle.api.provider.Provider; +import org.gradle.api.model.ObjectFactory; +import org.gradle.api.provider.ProviderFactory; +import org.gradle.api.internal.catalog.AbstractExternalDependencyFactory; +import org.gradle.api.internal.catalog.DefaultVersionCatalog; +import java.util.Map; +import org.gradle.api.internal.attributes.ImmutableAttributesFactory; +import org.gradle.api.internal.artifacts.dsl.CapabilityNotationParser; +import javax.inject.Inject; + +/** + * A catalog of dependencies accessible via the {@code libs} extension. + */ +@NonNullApi +public class LibrariesForLibsInPluginsBlock extends AbstractExternalDependencyFactory { + + private final AbstractExternalDependencyFactory owner = this; + private final AndroidxLibraryAccessors laccForAndroidxLibraryAccessors = new AndroidxLibraryAccessors(owner); + private final VersionAccessors vaccForVersionAccessors = new VersionAccessors(providers, config); + private final BundleAccessors baccForBundleAccessors = new BundleAccessors(objects, providers, config, attributesFactory, capabilityNotationParser); + private final PluginAccessors paccForPluginAccessors = new PluginAccessors(providers, config); + + @Inject + public LibrariesForLibsInPluginsBlock(DefaultVersionCatalog config, ProviderFactory providers, ObjectFactory objects, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { + super(config, providers, objects, attributesFactory, capabilityNotationParser); + } + + /** + * Dependency provider for junit with junit:junit coordinates and + * with version reference junit + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getJunit() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("junit"); + } + + /** + * Dependency provider for material with com.google.android.material:material coordinates and + * with version reference material + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getMaterial() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("material"); + } + + /** + * Group of libraries at androidx + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public AndroidxLibraryAccessors getAndroidx() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return laccForAndroidxLibraryAccessors; + } + + /** + * Group of versions at versions + */ + public VersionAccessors getVersions() { + return vaccForVersionAccessors; + } + + /** + * Group of bundles at bundles + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public BundleAccessors getBundles() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return baccForBundleAccessors; + } + + /** + * Group of plugins at plugins + */ + public PluginAccessors getPlugins() { + return paccForPluginAccessors; + } + + /** + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public static class AndroidxLibraryAccessors extends SubDependencyFactory { + private final AndroidxCoreLibraryAccessors laccForAndroidxCoreLibraryAccessors = new AndroidxCoreLibraryAccessors(owner); + private final AndroidxEspressoLibraryAccessors laccForAndroidxEspressoLibraryAccessors = new AndroidxEspressoLibraryAccessors(owner); + + public AndroidxLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for appcompat with androidx.appcompat:appcompat coordinates and + * with version reference appcompat + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getAppcompat() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("androidx.appcompat"); + } + + /** + * Dependency provider for junit with androidx.test.ext:junit coordinates and + * with version reference junitVersion + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getJunit() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("androidx.junit"); + } + + /** + * Group of libraries at androidx.core + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public AndroidxCoreLibraryAccessors getCore() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return laccForAndroidxCoreLibraryAccessors; + } + + /** + * Group of libraries at androidx.espresso + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public AndroidxEspressoLibraryAccessors getEspresso() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return laccForAndroidxEspressoLibraryAccessors; + } + + } + + /** + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public static class AndroidxCoreLibraryAccessors extends SubDependencyFactory { + + public AndroidxCoreLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for ktx with androidx.core:core-ktx coordinates and + * with version reference coreKtx + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getKtx() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("androidx.core.ktx"); + } + + } + + /** + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public static class AndroidxEspressoLibraryAccessors extends SubDependencyFactory { + + public AndroidxEspressoLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } + + /** + * Dependency provider for core with androidx.test.espresso:espresso-core coordinates and + * with version reference espressoCore + *

+ * This dependency was declared in catalog libs.versions.toml + * + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public Provider getCore() { + org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); + return create("androidx.espresso.core"); + } + + } + + public static class VersionAccessors extends VersionFactory { + + public VersionAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Version alias agp with value 8.5.2 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getAgp() { return getVersion("agp"); } + + /** + * Version alias appcompat with value 1.7.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getAppcompat() { return getVersion("appcompat"); } + + /** + * Version alias coreKtx with value 1.13.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getCoreKtx() { return getVersion("coreKtx"); } + + /** + * Version alias espressoCore with value 3.6.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getEspressoCore() { return getVersion("espressoCore"); } + + /** + * Version alias junit with value 4.13.2 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getJunit() { return getVersion("junit"); } + + /** + * Version alias junitVersion with value 1.2.1 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getJunitVersion() { return getVersion("junitVersion"); } + + /** + * Version alias kotlin with value 1.9.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getKotlin() { return getVersion("kotlin"); } + + /** + * Version alias material with value 1.12.0 + *

+ * If the version is a rich version and cannot be represented as a + * single version string, an empty string is returned. + *

+ * This version was declared in catalog libs.versions.toml + */ + public Provider getMaterial() { return getVersion("material"); } + + } + + /** + * @deprecated Will be removed in Gradle 9.0. + */ + @Deprecated + public static class BundleAccessors extends BundleFactory { + + public BundleAccessors(ObjectFactory objects, ProviderFactory providers, DefaultVersionCatalog config, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { super(objects, providers, config, attributesFactory, capabilityNotationParser); } + + } + + public static class PluginAccessors extends PluginFactory { + private final AndroidPluginAccessors paccForAndroidPluginAccessors = new AndroidPluginAccessors(providers, config); + private final JetbrainsPluginAccessors paccForJetbrainsPluginAccessors = new JetbrainsPluginAccessors(providers, config); + + public PluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Group of plugins at plugins.android + */ + public AndroidPluginAccessors getAndroid() { + return paccForAndroidPluginAccessors; + } + + /** + * Group of plugins at plugins.jetbrains + */ + public JetbrainsPluginAccessors getJetbrains() { + return paccForJetbrainsPluginAccessors; + } + + } + + public static class AndroidPluginAccessors extends PluginFactory { + + public AndroidPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Plugin provider for android.application with plugin id com.android.application and + * with version reference agp + *

+ * This plugin was declared in catalog libs.versions.toml + */ + public Provider getApplication() { return createPlugin("android.application"); } + + } + + public static class JetbrainsPluginAccessors extends PluginFactory { + private final JetbrainsKotlinPluginAccessors paccForJetbrainsKotlinPluginAccessors = new JetbrainsKotlinPluginAccessors(providers, config); + + public JetbrainsPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Group of plugins at plugins.jetbrains.kotlin + */ + public JetbrainsKotlinPluginAccessors getKotlin() { + return paccForJetbrainsKotlinPluginAccessors; + } + + } + + public static class JetbrainsKotlinPluginAccessors extends PluginFactory { + + public JetbrainsKotlinPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } + + /** + * Plugin provider for jetbrains.kotlin.android with plugin id org.jetbrains.kotlin.android and + * with version reference kotlin + *

+ * This plugin was declared in catalog libs.versions.toml + */ + public Provider getAndroid() { return createPlugin("jetbrains.kotlin.android"); } + + } + +} diff --git a/driver-app/.gradle/8.7/dependencies-accessors/gc.properties b/driver-app/.gradle/8.7/dependencies-accessors/gc.properties new file mode 100644 index 00000000..e69de29b diff --git a/driver-app/.gradle/8.7/executionHistory/executionHistory.bin b/driver-app/.gradle/8.7/executionHistory/executionHistory.bin new file mode 100644 index 0000000000000000000000000000000000000000..3bffa4c5330c15c7b6fffc55131d2062698daef7 GIT binary patch literal 1062082 zcmeEv2Uru$^FIgnii*8rZlX!}~nEl4EBx^V!+inc3OBAP0vk&VPyj9Q6NH)c;!WTLA(E z2oxYtfItBP1qc)%P=G)I0tE;ZAW(on0RjaG6d+K5Kmh^;2oxYtfItBP1ql5Afy8VNdgD$7e`F;J7_IZiyy1M7d z-2F$gD%_o|eO@@hQTIG${edsL+wvA^pO-lqt$Ut|T-vlK{rp9|ec^+;=j#ef)5nkb zyj=UdZ1WPj=R2=QA)i=X#^LQ}?$SNq7u?QOl6DH`v+S>By60JE9oIhUJjO}e-XXY? z?)mvj6-N&drJln3X?a%nJXcUe&|*oOT#Wdu^gj z(!I8`_IcTH!*tK@*P8maqU(oC+UF$>?;xLVUq7kxk_i*F&kN61>7GAb(xA!@Wyh8H z^Kk=p&)=48^Lf|WfRlJX3J=}$PaU=|{CN9#QM`Tq&AR75e7>KJZ|?I``@HO{dAjE% zmdu#nzt7_*+UL%!G~M%x{9i63^Ioy>ex`iVJ+D+~SIvOt2is|%mpH4@J?FHkH6UO^ zmBrfU4&CnRp10Y=sd_c^4}!OsgpwQ4YMD3QA$a>!U3AZb z8&sLYAM<%K-hWJY-SeI!azB_EUak zXrC9Z?XP=2G`z~BwcUCL;?Ji)&^_nf?of5zq!^sf60**^=h0K&KI!W&Z;SVTVuS8^ ztfP|Gv-J*Q+H`KGdp^=(nfH=WW#jSonZ0z+b^kgzI1SYPt>AwJ2oxYtfItBP1qc)% zP=G)I0tE;ZAW(on0RjaG6d+K5Kmh^;2oxYtfItBP1qc)%P=G)I0tE;ZAW(on0RjaG z6d+K5Kmh^;2oxYtfItBP1qc)%P=G)I0tE;ZAW(q7{}2HVC|;fqer94nOC>QvVT3e7 zf_jU?RMJ?rSP&T@;YWFSq0ZvGi3iKw|CIVHt!R-Mt?mYtGI-)}K%kJh^W;L6LLzkM zM@pnZ_b?StC`H{hJavTHy%Q=&RXh#a9{W?ELN1boaf48S0(&NO&iFkt!0Y>nGfw@k z4e<7PJ{9?o`ztYvr&LNM0-i>qkarO}%@(5WGKEH>c2}w-GTtmL!+m0vXb+wYb&40F z{K&BB+W&{~_)-*^E|T)16e{gs$FI-q`p%UIu zqVVXAf^U#Y;xPGI#waxoHMCz)N2F57>S*z(gVDFBqlH1^Pz3K6w5u!DXp}8HJXjo0 zcR!9h%g5WD&0@9i^YrtqJ5?&-t9Ytd#{@YBhLR^hnPAU|LRA=AfeIm72xvE=d!R*k z63g8aNtB_gFjN@KlS@RXTBCMA64i=Gl>qG-sZmC1f+Q-33y6nUAwxaX8dM}gEVJ%lO=_zE{L;vU$KRu+#iLjQywcu)9aToFCAB05YIq7Ly|t#F9f_Jqu#!0(PB z?BM)##E`(gKf3QhPA_ji%jQjKZV@}NbZ40Yc73p3ST>%9aJkD*>&xY zTOn}j!f6SZod_5F^v8b8&CaP?7iYa_@jKY}%-g%6t2f0sI2%0KZ>VKPXJ;=|-49a~ zwb{A(pY}#f7a(M!LN~goK%-E_I-LE-W2{2e9^eO;1s`63bI&V>@&<5{%1tiDN%!tB zXC{U-A_O=${RMtLVL#?@uDWmbm6(^8qURJ2zS?&G=z#jp%qI>f5tBemAWzd z?sL4KJDB@(fy_#Y6zwgH(EVXLu@bm(yp{tSk9NncLJ+Es3cyjV~+i$s3V4r4uy_DMs=n8 zj&#FAEOQW;X9MOO6c_;x$4}rT^kxe<0C8^thb3g8 zejGl_m%+41#S6oheE_t#yVt+bliZ)dPg=$eTUVVuBXOUq$OK1Qc=i*aekj|A=gIc* z^!4);3B7#y91-7#?d=0p2<6a$7HA|<5=|`N*$<*}__0{14@=}L%wea)v_F{pV=_eEjJ$;2N7N6~f zdirvNY)=}~s7w(qVY@|1&}g-r7?lE>0Ql$pJItRvsuQ~FGv6t1XiAr<<7cjOykmoI zqe6d?w@@VX6p8$WKK?9Ef1V$oE#$FTUMzu-?`@3z|DNLqHgN2Vdb3!5BB4Jp-aH;# z;N#=t>o4&15&HXjark^5jbp9Bmtb*)c0T?qyKSH*w{75>@68r@0d{@8JozGjk*ANy z-=F924IX$3MSMRm8rNFg{vYV|3mX^~3I%LWA1|OAd=baj2Pm|+A4}-%&-Um0@%=eM z8pBc$2?$~ZQq)ZfynD=Ja$~#uxU>JwtTa$-TV^H8%U8f>0me};FM*erm#-Jg*H7r< z>&F7@`}oplrJj3iV#+|QBK;q*|J(-fIlx2<1fG07t_V)Al zF#$gCG6bkv{Xby-tqsh3`SHAjY#*>*dJ0g~mnZN7OFP?_#o>uOJ=sE2%#)g<)&Bop zeQd#>=j-psVS#0y?*-`A_xJPhV}nn=Y+t?!{8f>14M;cq5AgqD3;uk8uaBRf zkOP(@p~&CMN9fBDuzNzd~rXv7taqkyT0Du zKBy+LBJ^5{z{PcBygq_G7GjREcemaWq8q+qr3`gdM|!D{u)1{Lx~f!6!7czhm+F?>Z{ zs2^}|d_-(-jz5ZmC6}iE!0L!V@FkH0m61vbkLF)FWCrj*wS{*U$B)NBeRx9DQ^02P zSiXGlE1LyAi2Qu~=^+MSS*3|oy6I*vSakoL<`_8bcWq#u&++Da3cUQ;LJ_byJP{js zIBb6azK;(Z6)>Cx;Mxd4tPV8A^WSNT@?9BGNZg?E?|jDuzWDH_x#J@nSO&`y;8lc* zglrCQ7=YGzdh$R#>gfxXE^kjGevJ-lHkhRU${#b(lDf7;qHv;rgW%s5rv`TH@65C* zw%`pX@;6}FmKYjJ-0#e^Apd`J3?)xtpcS?#GMp@h0n4@+4%j&gXQrvn=NSqEer<7D zA>}6w6eNFVCkoj8U*>)a&@Dih+;J*Uh5}_MPzJl?+zqDM|DlY#fzxA)hY361{{I*A zwxp`zZWS2dZcCyxKWr2j2w)5LaJLBzSpPq|Nnjv{EzuUFEdm3cZPEMuut8w3QvILV z9x#CZ|H|foL1r(%Zw)vzcLx4XYz!FahjY$5*Te_M(gvP$4}NoX+^o~{u);;DR1u8| z+o?fyC004;fXo+0%4D%*4Kq>Y`qIWKS8XAw3>8Yi?x`B90p#jx0J)$7Q4oQbyLxDU z55fxB+v!UfO%%a4LpTnF#`FX~ov5f7E&G+v~gDA70q4h%@tv!y!-+ zXznOLFi+WATPoNa)r9agVztHE*Z;c5Vu@gIbSDyopy;_2;`E;u8!sfw%|qm2YI4M# zPTDxuWH(qfvxgG&g^z9``3Jx}D2M-Vxt}kQ3sfk+O&qMP#K*qkk&V35^_0>jp`hSw zKm;!g)v73v0xuq2q^P1uMUoLiBk}ynycTGe8&*re^xh)2?-8P$Pi>Q_Rj?ywp#zy zj-~E<0m5oYn4HU3Xfz5LS1m?S4OcCd2vM#??j9qPIysk!t90>haLJ`p8|TjYnBqAY zNyRv|NO&nzAZP@aS(j9LyR9v>_ly3siM zaYpLMeS3Gb* zY{30D^FS(*qgt4SD5&h0N#tO`=3)<7TrsHk2Ka-=N(DHSpitqu^vQpHL)L@&Pco31 zSA(0Bb3k@$C9<`nd?l)eCy^Qvwd?3&LqB)=9-CO{%;MniCW9@DYP6$#Br4m~sQwwh zLM5D2cmA7GS=++9Zu7Jxs)>&Bm8eDs!^v4OXQ)@U{P+I)rE2wkFm{obWl@cGlw)@z zBjcD`udWHkblv8B#<53=oT066 zA#2RYKv12AAp~{;Qz7SyKuH}JR4Sr`ZQQ)*i~Eq1P5)j{O;kje++G`5q2u2uf&JGh zpba!mVkCrzux|bCFyXAVNxfe8^>I~p98RoLCfeKI$pMV0G4Blb)U=Ruu~WcYDJmjF zn7|udblUlGA*+yYFMoEQJdJR2EK**Ap+LrkQAxtYgfyN@{MUxc5fZNS1vm68PYI#A@i0#Z!FFK`33w_Y7fZIO)J8nbpH;T^sMq}1Ch@y( z-T1wnhwE&YCCX3s4%pqI*enE@hABSw>lJ&?QtV4D#^6rQS!cRu)EyC3ylm!_fYO1i z{m4cg#}KMHy3vCbe|N=dWc-ILcO*z- z7+#W-vnKrF!AIOu6&<~V9fD_{`GWh2R*+uK52HkgLm8sz+h6x*{rb_TO5dEUrz1MA zL^hZjA|@@Q@iF0T=n|J}zF%1zE=XzXrdZYY)S(AUsN-Xn6w>&Z;EA+!`xfp&yL@cc zNjV0&c>QQ#ed_p_r?tDUg5@j;Uj_Ts?to%ns&h9)JU&;91+YZ;tyZD}JfHe9;a7)> z;~W-j+|pp>i#DL)VBPV%}35BL`OAE6)qT(RnfRW#%OQZ+azgG z29}?%k#kWg8U>QyLhT3bv0sn}S8KSK`N2o3Sx~w5uj9j(#c-5a`-Ht3AnDlOZ0W=9 zu^^Q>qcV+tdTz^8-r=(?JF)hKtn|pkV?hgK*I|v5Hi#kz%BVn}vroMV_~Dw+_$#+c z#lWsU$QJ4#S?s{>VXh8pEoVk0`Z(+3=c5_3&klMrukr#(otb!;Yl#k?AYzGI13n@6S9M?LZ)wNynpu0u= z>X$^Poh@cYG-Dk=^Gj&cieXbRg~t67_0&p*u78+!F}hz|T6ijYi|&_L(}&&DL-=ge z#tXppVn~Kd_0;j{l>6_7OCxJ;+3|AB!bN!fjYUF8W2F-%QchZZqf$-0Hh-^tU+D+U zpWUt9h5uwYb*!xG!|wSnJ>;f+l)(8lhqr2$dgr>Lr?_?1*Q@aSmt{(r!kApuvxADX2mnsg)R3m z{4XaiW5vMCC%zWW)I>Y+YaYIMa7gtAi<4&zL3WrKKoh+{G_|IaU-x*Mo8~O<*1U2B z^{Ya2Ly3J){kma_60$JHl*q|BZF6*Y7P|2gZ{E)2USR{{nd=57j4?`E&XfGd>W8sJ z-Uh9`e~qZHAp=2uqH?-(-$gmy@|uiJ*ndAM!<&cfr7NNJec5ud&0Yc%3x!_XwZaP1 zMkIep=smSCtMciZvB(}P#bxyL&E8w|*zCdfe-LD*j$`a26eFkIhazh2!9CVkMYjp_ zjFI!%o$O`36*jdh5Z{)1+C5qCe& zN=LR*$H&8B5AW@%Nx%SLyC?D5f9+c9s{KaYz6oCu12jgZh|uPybn7AOV&7+yF~3_s zA8>#7iznlJkYtNQN9?H?G;UCpO2>E0DplvCUOH8{c<8aGAI=5LL>3xvc>)@<5&y8?ZB*u+ejcqh()668IR7uL+XdXAe`LOwwnkBAkc_?c# zvcXzfyC!ywGG#bw$Mib#<6*8YjB2H7j@ zy*Bvlzm?LIdu>;q`0s;E&W6)-oRKXybpTZ~@Ol%}jA+p zNuO2@b38K+op2q{)S>FE%H={sjcSe=#ykqS`S=&QaH(R*ZJ&~E4;L$u zjaC!GS&;-hDcB#x&IN+k#Bqri90|D^kY>a!!_c@Nw=(^U4VlyRSeca{XKbddNET@A zTBSw8OlQh)O-juSb^BVg*spKXuP^Rd`Jp?q-bzxt9-*S}1d7R-1_~dUs3V)F2Hbw!Fd8UnVa(ruqk^O#4~>(SxPq!c(rGt7pANz^fWTgpVc5wDB^% z{WT~H8E}*$xI$FKit16b_F;zU0_p^?}>f~n+DzC5BuFg#)jTFQRdb{Q| z%`v71FSNuwL#k*FS2L>j+&$JOn(unibxo_f$X45WfMcz+sEfgYTPb$v7SzJ&z1t?v z7al$l`})tg6jJ3wwbH*R*2*LmoW+k|N3NlGgSf@L*Q(LBG)2T>{=+vVYyK7aD&*2wTo^%wxcuytiDSl27GGTbxPAa7!(y2nPQ+o!9@MXtF$dvy^tNn9%Ey1iaS`T#1Ekkr9zI_!V3ZBu7<7ld&hB9Cqck zd~~A7l9fyNRnK%o_Wskp?0U%!$)s`bsE=$wnXa>+2O*kOL=@$O4)E6+j{%ds*&s`QAv z?puB9uN#SNvffg*7_I35&VtS4OlwZ`Q*vDSa?17V>NY$)?rE9pC%)CCEZAl#;RG#A zmZ-Xjk5SR9b$9Pio1A+ra>~rxZz|2A1TB_`;RG#AuITwMC+DF)$3rg-K2$6>d|S@K zGg;1*pv62XbPK7{-oa^kRd_pOQ9#e(ZC&4Wos(5^Lcd?eEu?k5+4U5nG2>>EO}Zs_ za_+gj;^Du+++jo3rPK`gc%&_o`7gS&YbmHnKB=>ju`-0dDZSxb9bQ7`$n>q-2P__r z?6AETyB>fh*;6W%kxFnYc_i0JMVhZXwIR1e)wKEppL^bJUeW_uYYiQog}_2a?t$-t z-QFABvz7=FD~!m?YDQTI%u>P`6%|h?Q4k>;@sEB@EAt^_@$JkrU$|)t`|cZ4B$F~K zX6WDxLd+k%Ahk|j&3V%4m%{NCxA9kp&$mnn!l1L|#k&8UmxvddVRxuvA+$;%HJ6EN z$$CGvJ1h8x&(#UTCKMT86xl`28yot8Qwyn<$gsL5t)ED>c)0%&)qHkz>(YO_X&N3F z{k?%GoKg#Eju4JX(B6-);_?IdmaH!(T4B6gnn`ViL?! z!tvovvIH(J4dV%jjR#r7d7;Zy9anW(BXjFeJ!%WZhqtB!NGgZD$3O)NRiz3dEkzZH zw>EsqpT}X!RR^9wT03V!S*psJA%s(iMt}^ir8l8;3r}X3|GvpFdu5ZYKj*zg&rk}{ zEYQNq_nKjfrg-eQ#PaJ(^qbOkXt!!NnoJpr=<~hSb#Vqt#)IHZBaW1Ti$(Oc_$Tjw z{nKmOL)TMl$5tD8xkhJXmEMBmO2;69YT+on&<3UBhRO@7<(`+Ws5LU}&CYi|h8E5^ zC7faqHOQ_B#9W*uy_fKK%gUZ1!^GYryFbk7fXtXgDF!i00hf90BBN*CvyXelzSW}! zPCat)@Q7i9g+`dCQNT$)Yj}Kc$uG7|K$!y3SIg(Ts?x-{?D{zmYnN}kmy&!o(jJcf zGZ+C;84v>OuoJ6cM9ji0?&Pbp=kHkF=Fc$n5JmsZQo>OoElY+j*NWJ!?7T%AqvaKs zY;$S0TSHMHqZDu!J_A;mW3i_*yVT>&FY9Zj&UpHz^Ta`vh0g*l#5uvtR<&FC{8_m= z!NO&47p`$181BuS6ZG~F=Y*aS<~YQ6++TfPDP&Zq6Ol)K`mvic=Y%OrI5`+CH@ZOB z{NbM>Rrf#t(d2ipV*M{pdWbx9qvT+$?ghS(X7|LMoIgh=O)R&&=;R+!>Oik^f4L@v zG}{ZD+C1tQP>mcTlO_!O`8@n;;@;h=K7s=sE6k?U=2_JPJmEwVR0<9`;Ct@IcUXEA z3ZCAveJ5APH#;7@nmK4MLpX~)z$w(haK~BG?|f>^cYY{c-}oPDdWS2@qd0_ zq7>>_CWo^#LFG#s30?uhC}i*Fcu6`sv&MszlvdIqBCleUoeA@#aLPmVJmIN$%HX_m zh= zC1OZkxgKhPQ~}bTOo`5%NY)H^J~!5LLdoxf>`8T~Ub%T%yWU$!CSNEpgHxVL>;?tn zOYOlHJt9st_Rk!)KiQ{+$K4bp-PS(flv5cI&~S1UIXQCWhTVeL_@%QN9IRXB6Q!KW z3VJwa!HqD+R7THkf8AAb&7)2ogPu&=QS>O~EVxB#IOPBow#d{2KF0{VZ#Z_*J~Inf zS~xzXQ=P1OkH0=DK`95Yxi>gvr54#_j_Z!(ivdM7HPCL0z23|$|JILER%&Bk(3f+J zUr+#u`HO}gN`q_Xz6>4s>df-{0c9f#h2Jv1oSW$al6VR^54?ZP@LB^#XtwO6q{x+J zSqO16h6DDb3xK%o4=$E(XZfL-L z#VfVNFPjHG?bk>6`Q(a4J(rMfm1W|)5O$4>bA`&3Vjj2`3A{BW3~XY=Dp6dxMx#G< z-@h#2?oxim1-!eiB4j7wh}hB%3}?#%e=<}ki6mY$vUo`L)Wqi>HuOC@b-U_*-_({E3ywRH+3@$fKnb#*{`bo+qv;-!!cG z{E{Vtq$A%hHa1%3`+!jaVFYthK&mdDI9PVm`I|!p113MdhYnA>K~_Lm*8yZjR7a{r zJOQdZQYyr4h)30NH==3>D$$qccEve0ENe^=jZs2YL>)`yI5A9Pmt_+(9(VoP{JO9s zD`raL+Qt;od>@b%(SSLsB04+Q2{?UpT7a)-P^}MNKQ%X|h-Nx~QLjgtB0A1+FBezC zU0;UWJ6ZB*-?RNTG%DBpTnDmV&nz8`Qyn^nl;G{Pm}?4N6(i(oS7yV*^8t63pE~(m ze*azJ5(`S?B)uh1by(jCi~~y6aR*`*aM7fi@I_X6NF*QGC8r*l^d2$aEKis=Vr8y$ckpqk%!lwRUq#2BkjFCgEPR;|r)vK5{bljLn zZRJZF&uChROfy*9#l!qEt_<<$L)tK5{fHvzKY|;y;xBk}`C@YFRZU5my&8 z5K9i82PGmZ%H1fhk6cL!4pqHhH?vv#q#Lt5kt2vX$*t-&-z>m7ZnY^;L)jgx{+;1m zl*OsgEc9=iO}}rOUx3Ya2Ggw~s%CXH&S0mLD+6~*sj2C;D*G??y<|8Lg~$C zIUBfDmOFv51EVuC4DOg`2RH+j*QQshiEcmjAmHoUCJ)FR7^~=E`u2oi`eJ*0N$vb? zN;#)=j~!Qw)?F=la4_7!w>L@$GyO&|q%XBMs)kK6I+U-jIQHqBdzk9!9!^t(^qV!^ zz$hwWD3V@GrYe3P>TqLPdDV|cCvL9oxX*1nSyW_Y4=~PrFj%8hq2t>4eDWdAsc~b3 z#f#snGVAh`9^{!1^Mo)R8_G_WLCps))Qn+If9KSncIHm}`-u@>caJe}Y%FyFquN6U zxFK)U%)s&2KU|Jpsg?ApVxwbghRx0;t39kChdH|_Vi_-xaG8qZJQC$wZdVUMO+mtOiXCr>aNq&1Ip5pk&ja^lC^D?NMR=2C`ii`LX?Lo;(yGy*$6~+ER&a4H9nVJAkn$WADSm-sR2@!(AuFj%)m$$|bkvZe5x* z_UXn;w`SEO7iF__Ft%BB3>nrt4D9l4XO)@33zeSEgZC8@wI{b(O_9K;l+y7+-P31` z1=8U~$l}Ej2d>wBwC#thFovv@vPcVK&ghuZ#vx`jEHObn@YwwMo@4gkzB7G5(lm0; zSl0o}u_8q?)VZdCMJ^Oy(rd3MYhu^{r^rJFV`Y*S#`X^lYF#df`dX7MRX6PjQ6R!m zueSI*G}E*qw|^{9!r1S}ShDo;g3Yn6KfR~j&z?K@Oj@;j%?6YE{g#PgjSndjetsY9 zCaAEN(BrG=)IGf?yDyJ<_vYcjp>b0~@@V5@h7v}NH4ZU&8$*-?jW)P&ZfVo_p5-IGn%c`EMa+tQ>7$bqT z?wh&xbnwcOwH_|0tx9XU%V(}V4;)N2sEotTkm^0M{jY{h+PwId zW}q-LWYfOPQFL`OK?dVuYOQ)>{OGnlwPqMss79=c+#bdAS_!*Met7)s^+n{x)TW7G zoF65*(XMS2{+%YeTzev$92Ga9Xsw8n0}7GnM@>+`h%#|j6cSMRU{bxEoD(w_w^H<6 z7a}e^wb9WfPwtUXrZwa+0x>3EhMtPM+v$vLrB2U%IJc2+m4^;h$w15!DU7TQlP9L8 z1&#eaFXYs%Knm>-yVyqxIg&^_Zmcp>wN zEeTpXSStl~wXlf@v9R31(V@_u>eC;JE{^Umx=dRsOwz%c;uu5t5+lm@yp$-yX*`+KG75$HE8+ zj5C~=tsxMl<{@w|+~Wc4vrDff?J7eH%Q1nfF>?8;BQYL%^hdPRGYvGA(GTp z@`Oc~+|lDS@5>x1j3abL&^8>aoqLhz8o$u)@hKmwq}NmjkVojOpw0*L%*^f7PGcX; zPWq&ZVnq*Ey?%0|p{aRhvI|(bN{Sw7d1J)LgMP;IHmnLhHDpYMQK~lAm(p^TW@%xi z_n1sE!vF(`bZ?Jk=pa5BNly@4=N>=`1whtfMhcdnmzz4L!l~_W+B!G>4%9nHB$WMydN>GQ%z?D{r6^KwJ7G1b6(Y z@b|LlWm(~wRN`f|XLrlpC~|+`v5+dXyn!Wh*yBRG0n*9&#Fbs@J~E%+&x2zZrA96- zXLMX>G_YJ7?Zth%xX5rVxftf&bM{JEW&Vlz?K>{)GnnSun5BgkE@+w3PIj$SjD^2< zUQNMZ#iu@47|#A;@g4c_1Iy z|Hu^i)gCe8HI%fL&eyN!Ne1-H~(|p_HeP3?eD&#sM z=Voj)ae>i4=*#{mO08g$e)13(`E8wL302C^d$Q}fo6Ay{jakHr(tp&O{rv-@Y#M(% zXvW~x6|T>}zUk+%ZR{g!d_xKU!0I0CU)^bfH6!m2EpxV4UX^C5D$U1_sZpuL>Xk%w zr?nl}{~)DN&ZzTIcQFR#JmJJiDb3E_AO6R&!O@dW>(&d1gOs*+W&guW20VfnM@LGD zD<^3gNqkZs-;kE$Jbgs5w=qR#?~Lc2Bn~s#*3Esp=UC12XUzJnzpQM=o|IPqsY2BGk8n*8ba{Or|W@m!*F?R9G(!`ytN`+`WQ7_b9Rb zX;UxoRzMXh;wpJkRHFfx3K2e!9E}9wk(9;8t;%cZd*7RlK40maRO#Hz6|e3vRzQnA z`BFGGF>;;uT~4~wGp*vn$wzWJ`sT)2 zFC5-O{uIs&AGy98nm51xdxxZC>viqcm-ansgK*j&;5lYyW(*yEwSfm#3jc9Y+Ocy1U+f_rQA5v>oJ2mGmQwiAUO-hK?uu zJ=}d+lb-ZqyRY>siT98%h4Uwj$v$4^?tAh|G~{(;uRJGqI%K_Ycn|qgIAX%d`XB82 zrv1*!rz1W`kGM2>xDCQ-d&r-{5mWBZ_p<2`eh#9x55us(nrNwgpXhE>9Tx4}{hBl&^)=xoFbBRr@Cfxs=~E zrmUxbg}Ex*g~fZy-@+1BwsZRc(Vx4wu`FmC||3v&c#cc z-;4JpCtgyh@{F^WoBhbPU4`+U^0lx!m+wj~(RoeM;7RA_m-$+!b*XQ*3yb%Zzl9|x zY~4vN)k^x`9eQ#03QwPjl^Xm5VYNNwZ()fkdvejc@S?eMW?Y?eb=1I9jz9i^u=#(^ z>RiNeWtP@T{0G8nUByrK+z%D1c+ot*6h)9}x?k;jY*_cD9=s?a zxEWc9f;6F89j#CicaE2K=$sSvd{L|YmAhZ=xxVNdWTkluc+9KCif9J&m$r>MnVEe} z+^G7@*O3d31~Hg7ps?$4FA_%~s+NSwx!74i{Y$LysONU#{s&om7meJ|U>|F+XKoK< zjb$pkmS8j40bA)&619XckxDeg+n48$2wa}`x{Tt?NX7hfiQxhy*&>l$i+#;C}elB@^Bwsa6r%wQh{bk!~t;(OBY+lB9>x_$` z4c8&7Ez#Ju29wE*S`J?Ji=Db-PK@}AyPpJ|YS8=6X4gqKpQTJk)>}zx*Taw`PheW` zR4QPfFgdts6maH*mKE&fhdSnkN_=K#Ke*-7Fy;P=#26$kB-8H^Wlor& zfu=+eXe?jB1K0L2W#FvqGMN=y{z!%Q0ZHAz%veBIA`@h%?O6gqRccUprM=$+lxPYf z@ImO|RH^df=a*-%N=r&y!;v>cR+uHQ>)95QoPcA%0*MMt30#J0&w~2B9(cwjdUVF2 z5Z7(sY>Rc2@W%nWwFj4>Q9{7!A6+MgPw(rMy$$W3Y+@XA1kh%J46EDL>JMWO#Em|5 zIF-RJUHRvW_P$TIbfV7$6J&4}IbdA~ez2R9u(<$a(avmqET)HNmh3%w%J*;S$=mMM zSwEDr$eAa#Yjp@s$MI32h(nzpEBvdb-%mTrNVTsv?j)5MZy(1jkANK=}%dMj_*>#VD%b0&NfDig|KyXav_MzgjE0wb~GSyjtvIZsAQ;_!KK; zf%X&>e+n>V80Uo_u23EQTw*$FZQDM-4>s+AEGK8Rk@j|d!vc*Fg)&kpL*t$dt#c*u4lKX_~IwY6p_IA3b|4v;%pnf=If0gH7?{_6$L!l z)vr0S*#>erX&&;V6!9)#9mDweOrG$#RhG-x{mCv-uj)3~Se%mPF-Hh#2I&rcVR0&` z?v#ULEadX83vbierUkb=9jllJO6_vg>IvYj{*)2SN?TbJxhw zJF6?yy`YYI|K{4Ngr3OWf7+K_Pox-SQoBUsV=GidgBKML`9IxkoDp5EMP!X?FY9u7 zts?4=ZG-Im2i@59RaTbxi&Pp2nNwnH>n>#-68k!}@h-fx$3A4c&7DB9rdTM7JG~}+ z-mqG)q=$}up5Co>ds%i+*IcSKwLlCh5W%BskTT&bVz~H0XM6$ozOrst`(`&>B|%H? z4-~%GNDV|x5J8$>Mz|rfK#_7HAA}3#vNfW9@S(I$)wUK@IzFm0h&sQl?gma0MW1og zkCgWIS6s46Zwudwl+WCk_OV;Qo#D%-Qj#cUDed~!PW?PL1~z_C2$8;{r5tb(Uv}9w z_}e{Y*t4277wmXAayoM0-}DD*^|L5ALu2zgisx^r|2u~hx@WQQWXC7e)z7xR^4mz$ zMp!pt@sVzj9-8@iRG-o8*9St6I0xifHPR;gdjTh%U~+Wmj55ai%7;0RhYPMO%>3=_ zF{j1U_sAhDl-x{@`AyA9ap@yoc;v3o!+YP3o6~4sYPlt{n^vj0(Z2HAXzQ7zjS{Zt zLti%j96$5(m_Wb8k8ZPrFIY9&W_rv=E3lqR+6pXIogaL;?ZiRnk1q?|HrI2Jr4`s{ zH;~d%*o+oRcv3|eCC!EpWZ%Zwt3M5|F?t2-`y6pxm;2Oolu0r;`}bORK&VnEwGoIm z7{O)e)z8me-kN))L*H&6=JOj4bMx6Wzv zW^w^4#RuWWDbA&U#;UdL85)yxzn zL^U(U61WcvRjX0rc!oG6pncaNkA(+z#a8^5IOPaa%`Ei*(c&3pjj@I$Wqwgbf+hO=+J15E z&ML1~G${H}bm7Xlh3(C%qLCi*iz@0^W2oZ9JL@lg`15xtH@QgXNk=CQHmiz8`+&6X zj5*GgJR7`hESI2yi)SY?>D`xckb9Tl~vr52}1)J##bF z3^7C#p)K{&-GB=sBWlswm)s(CM5PbTef4Eo-PA^5`>3TUn0YZx3nwh31XHL?sfnfR zH_olHJE``#!b#VfAIxxPH!nsB3r$jegK;3(Es729NS>*S8nBO0(#O~rW0!4e$Cw$q zg>&X6vqQLzL)vtHpIfK(QGNQ@3>lPpi}RzaqcU3hm$T2cf`60dwM)0S{dU-`g`@QI z)*`W8Z+@q$gog~9e-zC%nLPM*e(<%-Q?))$**#TJ>hc*B51L0qnnznTFz{E7?R`h5O0aruS!W%;$Y%}v(3_2wy|6p!jyQlnB-ppk%g zdV!a=Yg7s;@eW&DB$pO~kQ>7So*zB=X1gk9pF&?eY7IRsgQXoMqXx^p+wB^zCpHw< zOo+<5c-g-K&0v`#v+H|XD6>+}kM=bdN}dV@ckVK6u%pZD8x2xdT=xh$9lpH=>oc;= z#xCr7^)8(^%y?POrAZfMXK#GSo?Btr`2%M!rxinX*xrj>4VOd?jw&e?QmpJB7%u8Z zyM`3hFUAa)I#$hC!FOOy3cw!8J*=mr_7!v!xV)t(!}wls-Kmo)$JXENUVElO{b-d#Q<2P6}$rM0WmZ-yzg6x`&Z z6Q}5~_{HKWb0zMA}^86iD&RVLq~JGJ*N! z*13tFgu=IeJ)$y3cep*j{p8=@kX`?zpO>(fAq;p+f-=?*C+FFcA1xwM=iT4Sk!Ifd zQ#KqqjMyqPqtE;;KYcNAa#pI*%iBFv(wROs<^R}jmUzM{9-_-9vzqOnm_*tUQgR9Oo!DtT7=#uBU zt$EUT+PKu^dwU1R&q6jC>aHp3d@x$ZeJ>~Hi>3K{U01z4JKcHZ(-AELQ%sGParzJT z^xeRvBp{wakSX{tc6EgDuk;}9iY0Eaq3ru$1*5o4FW&al&9hfkd%rDJkE+?X=wxJr zwX}9E2{+0VaXeXjRt1+v9{sAw8rG%_m51L-*`9Yi2}!kz(5|PF=^WvoxVo!LaWR6g zJQCFn-6B}m_FB!nzJWK8WQ#<0-6l254TyCG(nukZHr*V(7j05)_0Jv&Ry?OBH1a%tz1 zU#9OGG=jO3n5MPsg;jJtVKSvg!M>^f{;h`V+MWINIjV? z(h=D;HEdF2Nb`ovQF3Yg!Nw~aziH?(H*Zw&j~|hB)=@(A!>~01EcZ%~wgQTMgc0jWJ>VvXK-(>1p7sMx)2|V=tmzM28W-oJjQkHfJ4t3 z6(?tcB~rVde%52F#@w_HT|OS0xZ?JM&o9X2HU?X^+sxHvA zOblhRlj@}%6(y>YD1=;%A}ma2v~JbuIIG*PQB{^+zB*`|dxuQ@WVb*H!@Ht`EaC}J zF19R3NziCq)2f~GxS2cY&CA@A?CiVZSg`SKFkdhr3@D*2hctk-Ea?S#>TtjH*s*=ce=hUX}b! zx`^fpVFbS_CmRKW^p-KsO1p_hr2M5jbu28e#^wW`Nw=VET+{xhABCTCt=fTu@ zObl=gPD0$r^2cLIv%2M$49VU7A?)^x@a@P7vjlcM4`!4T?O@;&{Q9DO;o$+7r3v5r zbQ(Hm)IwyXc?#&vQ`P6Z^Yk0r)5>+?I_<9Oacyywapv_DP$#rr_h~^!sn*5T?YiV6 zFJJfb@ZPykTns0)Q9`?J>l;%E998XdfzNH4htjTOO#j=D96aM{JPNzkcv(jz-PS(r zTDqlU4%^x@j03$j)3z-==KnhT^@5vU(J&>l++2GoUN4hzdMudKs_!hG!_%B;>1(HQd!7F0K3W_C4?2{>x zMfSS0&Uzr*Z0rJxT{DF_c6tLG+@i?$JRoDnlu2{mB)z?~y+!3-8G5^BZ68nqF)efE zlN4_w#Oa|G`aN89_i~ReYd?I@2Vxe9p_yv(bqqpXWbCr_=<^rz$KLO7r1r?NvzoM{ zn`&lzXr`LV2zdJ`HyTBW^ZD!Jo}^B0(L>tpRJn!clCuubO|>aHD2@%L7gUDSbV))E zi~82R^0AhCMd#a}f<7ec9UHTRc0JBWHBO``VueZ)2aaj-hzkpsN0yoV?LrZs;+%Hz zA){JGAt_dnLGhDmz{-FKV%*7p*63tCMQmsr=j8K`do`Kus`rzPQ$R^Y7_!2Z^7!CX z6>%P?&#K{nhD}<&@@ny9wfEDMA^KE=c}i#omsBY2NKnp?6NBLH*-k8F>l&-(&vRukU&YN(s%(czXE=XZi0_) z>A3T0Y|68)Kl1wR7&p1MKAmck2uk{a#!W1F2Ji97{WEfhHhLv5QRC6<#tla5(+@@o zpeYY-H5oNqOJYv63w;#2ptRek_m_IawWBMK5fUg_UkpeFFZ6n?iW%2W_PqPDj?2r? z(EELUCFrxh7D%DFAe0gg6;A^0izRCto40fqtqmGqXyw^y?NaY_eL;6YOwmDG@Q6eN zZS%AB-9f_b)lL*zK5Ss8zstT{p)Yub6wszK!3uTPd0p0(`KZ(0*%i@Jvm1ST`hz~5 z4G5qaQ-Tvwq*SUFs8E#H_MgmJbZ}#0-h;Do{hmy^ajzQPm>MO5HU|i9@ERXlR_@ZH zQ-^{stExtqsa&}FiRc^jIbezoTC#!85OYW}*UWC$Ip$!?*5^+jD|Yd9Cwj8M9IahT z+NoYOohkkGDcDv5?mi7_*&{x1?2p||*Bm}`L{r%vNwbAMpNy0?xuwma;zF%D^7Z5X z)9d!k{I%hFp)qaK%#9SCHlNHP>Q1QJ8t>?%8h=emY0mql!r)!z=8&EaTI@ln9HlHt z2(||Cak)2ouxIe)OqJ*PH4|g|wChNZJxo)=o<9s>z@-IduX!!NIQ)>8M7*VzB;rZDULbe}6E3S;ox}S6b*w(ZHo-`6wg9D-XFTd?Mi1=4} z;Q!!w_20dDaQaqJYu{3#zV*h8&OzoHH2Q3R7TtIv1WCX-0ly!$r)?s?mB0ynKMvK2 zcR8UCHaWJ+eLtp#TPMStK<~1qCn_2^dj7n3_<3@`c`Wyf!t>88p%{gslgR(G&_`z-WjL{SdU~v?{;-CN)M*@Z*L8` z)&KjP*VRIh6f4N=dTSWTk6P8NJ5M7Aw}vqv*|pAs`Q>_C2?lXs2YTHtUS!byIVI+~ zHv9I>1=LwsMF?Yp^HKc-=c6ztI3FcZB=TTB%e{YncR2cE&5^ZtPCUEbnw;RwrceM2 zqW~5L1+Xv@urOTT0;^1U*u>*$M)w1Q9@gLZiK_>U(G&_`VAkr^T)rF%U~&>LVn?it z$BO-zlO7Jgm;3ruweJbn^?)&&LII58r0}6QDSXoN;1f>D331<%ClVe#?3MB;@7js8 z>3YBzO<@2g;OR9?z=NS-0-jF81jMx-2Tnh%8T)+Ew)5);Um9I$jUx#dvndq7C>kb! zqG1A3Z3KjdjVb-)Yl|kIS#RGrz4LcRzlM6i7)@aSCZuSX5Q>HgNevSc8aD1+?!rbx z;u;;^@inXBt-%5kFlJLIfKl8EAr!YlNV*le3!Gg24!n-r*#4|K?ftJ|?)ww;fH9iF z01TDtZ5S$rVZ%_V&W7n;3tn`*xKUA!_r?<`0U7FA2LegJm`%S!2((bSo2pZL1ery+ z*7#?;R?^YFnFLSE7w(sh`*3*t3>Wq9?`_6*ocpQs4P=!C5-6HSSqxApivdbnc$8QS zE|j{~bZDE0?u#EMBsMEM@`qmY7)_yQp4v^-w>L%ew4b49p7xtb&C`A|5!#cQXMzNZ z=7BpUb&&z8fnxJCBzQy()6B%By&bOq{5-aQk7eEZSG=LuJVsL}fJIUOi-ZDLBncRC zY1Njl1B>*o^DKBuykEP8QKk3m0b?|U0hoy5w~3(mZ6eZd6A^yfczILzYD+qbQjV9L z;h_3BnFNg46bfJxy@rV-Ff>dg(P@}Sg4?o}ebeK4s(Hfr%B*Qe{l@BJPi9jnfKj$! zL{PS1MC87Th}eSZmQuFv)3#|P%KaWZXX&Q3e7%M-n!;E;MJhK{U_1TliGPN%dg9+q zYMYiXT;tTojvwy2_I^oW-@?R5RJ2-o5c*y@ac>Un{e#$w4-+?u9pt*ZI$&A z*=}igXL#+NrQsAexHq!|d z_`Up0z)$}J6!_^ZkjT*=U)J}h9)5ajGo3(z-`m@S@uB|# z3jA~yNaW~`ari%;4|tp&w5WWO+TRLsWbUDQ`01_9bOK|s6jK5LF_b_+Oa=mCA`r;v zo^|EItZ{Fbj;>p|M(LgN$;Fb{6bfLJKtK#75D=5zy_g6D?%X?b7U?r%(VB{!`9te3 zS*Zt%(G&_`6n9Jv#T^rqK9-np$4YEzICJ}_*fx8Mex6rtMU&Zjz!*)T02Zr{&Bd`W zVsmjUX{Cs3Plx>2=J|KtK%e11u8r(3@844o7^5i+z$BE)0|}JM0|{A9pnGkm|M9`1 zur}Eh;<8!ycXjAkiv*0>6bfLJtpEv>tpEv`-p#T=Gw_%cK7&c52 zt+Qbg;zHfZI}VlY(r4MP>3hRJ{#yHWnI14kQy74SQ!?1$P%_xzWClB&$Y8Iy-~QLg zmHWK8Dvnp%?bnk@z?e;802V<3ECLE(5hP#{1Ypm9>~HJdczR^c;d;S60$dJ|fH9jw z0W3m4B_kqWOv#7{-IRp#VlXrV;_=m`VhB z_9TKhrov6~-gcvN-O)iOwsu||Gum4Z7^5i^z$kuL1Qb6kg7m{8hzii#cV<1TySQ+V zX$LNk+UP2b(F4Y43I#9)WlAcbOi2YfC5hKGq;8n;`qZ7SLmwZ1T}<+_W1=1~MpGz& zQ9`2#D4|gV8Sg|8q0zm+b+|JQXMU+3SvN!e{qtZwV2q}Ay-a|}d=r-mP(Io9CI-s) z>hw&1ZNS#%;oeobl0pw;o8G zJ3RdubS*ic+=L_7Mf;t;;Lg1 z2li`nJ=rN&&a3FPFG|-5$@@T_@i9*b!#YYS%ZU`qav~+y2r03gxW3vuB(dV?v_+3v zA88SEBbv01%%)HPqlEQRC}F*njMb$?Sl_0~&4{y0HYy)ymH3kvP2qoILrulJXkx5G^j7^5i+z+{x5O9mzAl97>=j0n2k zyc)FWWks%U(`#P)7ri-@M*_xd3I#AqwTlc&wTq0bc99X)E`xiuQjOjD)4RE>V7$xYEK?%BKWF#dcf-av8=XzfcxNxfGt;9bk3X7iV0b?|U0vKfjPX=WJ zPe$&_$%qZS!>zfoBd?0jw)V-&uH*YoA44#kLII4jTOfn7TOcF10A$2&K@ZOgZ&vN^ z67&AfopL9R&hMkwFh)}-fKj4U8I&khMuwg;B1)BA<8|!YqHE+#el5Q@XKrWc0b?|U z0hpYxcPr$47;c4}uX8KpeB7-NY*})>$I2pOw@#~HC|Et@C!E<+dMHTOLqWJ6>l3%l_?cW;*o0eZ$6CQC{ka}yQy73LDVuys zD4Tpra+6Oq!P-MRFYFtNleKgG;;NuzaaCj%S4CuTA3R;q*lk|M^6wE_U-c={dI4$km`$MoMkz2=K`Ag* zkyWEAqQLa`_OHUAh-10QjXy4&b0B=P9xz5z7=WoMHQ#C|HQ#Eo=37nFd>5a*VZe?` z=|S@%20F}>R&7NB#%u}&FiI9z4JC`KCbPI|B8ywst#-_zUhfVbxVfcHPRW;EdcYV> zp#Vm4L)1{*5H;zBs0lYj^P_9hoI<@eG}y3}@AA6Xc|Bl^rZD1DwTvePyP}k>X5AAQ z@u}{+b!({ZGro#`Yqs>~>S^A_Pb?oEfwW6zSTNt%luZ4`JPynOEr)ntishW&W)kJ){Avbya3&GO~eby9h z-_|F$vmP);Qz(E@_CwWB_CwX=Ca0R%4{ekizzp(?ib5S`1_AGdOY4N5alfEdof0H8{ttN({ml{fR?xjFEN9}4L8oV|Y(3lc`uxM!+O#Jp zGP5ZZz{GlIL?edbjA+EV*{XXvwbQh(qxT+u+;oy_czbr4XJzz&F`7aFj1og=pu`Xw zGBD5(F~rbf%UVRof4oyWBk0`lQW6(EV2q|v0Hb(s8YteIhIGj^g!gu$^Vx@`9$o&- z`IL~6T}jqV4;Z5<48S5OVSOZ&us)KE)gy_pURZB=?y=?#N}X!CaLdwLAEuCiF`GgG zjG|$YP&6!(RGUab!xjX0sPN{LIGGn9h!(G{{8j$ZirEdW`f=aJDE4s0AMY#cbSar8)VaM#scTr$tHiiQmsH4%t<_8Bh zKRs-IIBe4bp3be7JSwS%<2L{8`y<{^U}H9h0vm^F+c+#JuyORZjYHVBT=ny7g|a(I zUp;6g>d}5#4LxiIjp4vXounK%la!;McN}7p9&=snd*fDPRnh~`_-h;6$tbWf8^drt zq9~huQBXGdqR36YC}NY(v46Pod-K-y-)<~jqvvrqA?bQBo5Hw=EE>NB(eN5R#vfo@ zM8;r2XZaY9aVt1$bHi>sBU{GIcA47pPsxoAYa&2$0oBr@#5_Ix^wwrNfdW7N!fPYOhyDjB@Y7i!k)uDx;omoh&;2y* zPno_K{3a}N-I1$@pWfO`CoqcF;>6&x>K^*yHT*M-;x+u6b@1SyaA<3kD0XG!$COK4 zQO)#-CRf^$#cQTWU;){=8y(2b-CzOPxf>P8&fRbzT{`XYtW{;vNN&=nqm`RoctHcw z7zr#O`}C&+*{44&Ap7*E0@@)t)`2kx21>ap!!@2ZOzdi7GKrMDpcU}jTWcAVLsEKiOP-`h{*BV_ygv3Whj5d|ywthepMdt3?Wx3>A9tluCg@rsRRTS5&QtR0&YE8_V6--O~en_7JLg z(LBBsZ1GLg{d&=cMBM*?6AvC=z>Pu$8ik6hLDj@r`3*a_Zp^N-f7;z;5&Kj3s%|06 zb?h2zZ_8~L|DgzYq7Xr*;J?^%|H^;P1u={9>3f*d`f`=`-1PISTw=m&Y`=!g#W|!j zvc>YDJYQdtH;c#O^Zfa!mp4Zw68MPN0+E1?@;RO?n*IqCay8ILiCiP)#VR5-Zfti? zca~Q97Hxhx(vQ;g7=n`jCT(@?ECN`L_?kZRRR zfk>^_tFgP^GCUZ%{xjmwxi;u}C@(0g8ngjd-5#Se6R7Y^(Wo^M8Ud`*!&sfJn^g2y zaO9x+H5z#MKi|R#gqGskQ)r#(jVN@5qfOVV-n-p>%jUs76d6BbF2s)sehe+4>Wh)y z0^-#=nO3d}N1X-nSxavTyEt%HqG`Zw`*`t z>Pydcu;@xs|HES)Fx$4cj3P7Ia^zqkP(>&d)M3__Iq_g}>>`&}PglCVXqC4S+Glr| zZOC~A+|US>(a9Zf?C~>?Z?0DL{;7`=)w_Oi;X|QgRxNf^;Oin}x)A~alD&}GnAEF< z0gYc~#Z(=$IeXQ^=N>1a;|17WfW#+7$aovB$#9#~B!BJAw8}Gj1(yx^^5xr1=s*ER z+mQ4Kh_PCsM6Nb0+-j**pww#>0*P8LKn^y@F~VR6X~}LjX`ir0MhX7+HZ5n2A5kI! z+JhVFu$0F|#7HEH4;7#*E5*u+v$kd2&Se!VbGY02&}zv-Xs;bBZHakS^vpC)TZ*kC z%e?Q=$!pfcfWb}brTNJxL5Cc()l!x-1+v090~jI&!tGQA`0m>S=h{^KFxZ2abAI6T zHjht0yRBGiUkK>=iD_rc95Zjefi-Sy{CohLqC6RFj^W(;a4V9j?Sy`$1DCo$a zOQSVTcV10};XW`lm(WJSQ+I9YTG#FT>kkJjpAUnM{s(b40gbicXlC#^Bx=>e(RzVt zbWszVuU(NDaL)NvGmBTN<*KXqYSAHRKVhL0f@nQ3IHe&z8Vt7` zO|E?SDQ*gtX195nvvwR8I`C(bXw87zP|?aH4Avz5)v#`#iUZ4jns{Vkx8=|#M|quj zsro+$kp(G58nC_feWfXTk8~XJdzWi^jo+EjW`~(+O*9i)>0qH&EE7Z^$2r5wk1qIU z_J`hHU+Zh@s+pCw+4+JnXq8=tJ7AU#9gO6XknjUrIIK8W{RLOUv?cfhYOh&)-}f&s z5wwMDhkb59dzUSvNKQ88z_5c8p+(yKPnkQ97F%4FymuAIehJK2=?%dnp0YJ8@TjNB zv;l9FrM3u0ZYVds;qYgCXe}{9)_G_x5Kxqnz*1p^={pb;w`SiQU;j7n=%R!{GwG zEJBH0_pF>YW?<)9?EB9)Nc{)Q?-fd3ldLd+bQ7J%SkFK`JiPh2*U*q5C3$6g`0Rh* zFW$mUNYu`B4;HqY=%VC$WFtU&e#F>$u2}&KtjS?}~Z=2K`5#Z{;**XUnc zOez@s#9Fkd5p~V;sIz~5y+g%ae&5{v3|f!cV4siH<`R1fkyibT%QsaclTX0%rM?UI zuE}T)ZE%RunU2oFaVZbuE5dO`?F>KDA88w&ismp#hf|SSD}l8NSf{gg#N{lT^=ZSZ z+zpD8dxrF4EgOzS+D=OX0ypw%F%CBe2;3Ye;XZz5YGvlor@uGFl^O|u@;*(#?VKd~ zgEYh=ELF6UGkF%jzWDAR{hP0-?Cte7>e+EDNOO#x{(u_S%Q$V3Twkcnxc1;{D!Q2o zql@($wZ(hE%P#vP=Jx5L!2)WBxar>=aJ8&Qk_@*erP5h6f0eoY*Zv0|r#wG;R<&{mwA!@rqHbz5oy0+Zh+(cgIlN@Jxk-}7 zE#30G@Afx)U)0v>+G8PxZI;V`v8P6*eG>wja^dHb&ggEZ&fHjfACzbXesd`v}JII=(>%*F3yj>({lb0E8}8= zm)3%k1;E(8gI3&iGNA^``mo+rmc)C0o7}HQQhuDU{#Yp4K~}JChBgtHyV=&db>@d{ zt`3b1o6~vMS{3;LITX8cRytKyQX1*d8 ziUg!mHIin8wJM}6Eeb`a&iYQS(>}btvGu^Vyd^bq6n{foonWW6&}UCCq&b=riI*zZ zt5Mv2Rg)ZmW01(@KFoxbW+3> zkmiXMNNtERN)4kw`?f3}u=VAps{>Ta+G(M6REsRRXg$qR)d^K2JuAi%mrx_87<2bX zsdg*nB8I*XzHY-rq zGmerv64pu;$TDFbHar}5(r0S=?JUiWnVx4wd61>++2#hfE17`S2z7ecn(yU5IaIw^ z?TGZ-0gt1*-5%b8vMUw9e-GqpXT%$AZ$rNHVc~+GyVp)WetKNo=-8ynuX#=GLEEWo zgm>K9&VRKDa-IelAY0y2zQ)mu8l`ZRvb=1pr(H^)T{^ zG|@>aLz)apy<8zxmkmg`@b3AjSIc$JSl%(zRnQ(czzx`%TBJ(dJI_AD@;U{&j$f>K z?On3tZ0ZJVmz~zPc+BRyLarnA_mT$9crA(C@Isz|GJe_qpBhKSzwP2$y!4GX0*#G{h5*%u)_;(+q0q+4l~2;ta@xc^^oEDd4m$Jr@OabN!j-7F@xJDw8$G) zs!$PfCX=fqa0zb+=QIG&|*)>A50t_-w;#y|| z=X8WV#xJcEG&<(7mOW;0v6i8BWpFuTCl`NSPmWdGfA}e#hR8Z9zP=_N-Yd zBNHm57FK+GaEDQnS9-rfZQP3lac3Y9cyN?Y|l&{@LtE=8dx!T2LC}mNw%?i%Vj7?VJ z2(8W{?3o}=E_KE`Q6L}C!>42Zt~839*E`yLBe`hJ zecr`xO;7DFsnoPu;o(X;3Kqay1jdpuh;;pswXrt|y zkk+0%Gp|F-^`;9u&>`&I_d)p3^L>@ClZWMgYj^Y#w59+SFf~?#I}z#|t{uVN_@~@V zF)!v&w-RZqN|w!CI3%fG$b&lab(tGcT<`)K^&;S-?M z_Bnu$jmqps7|PiElUu!33w3w6$GYeelfUJ}S|1xbBEUrDhWm>J3OEu*Za2U#T1H3b z{@~~nZAQHOQ0Zqtv(4*Q_>rP=8$4j9zUi_zsaB|jN%{5*J6&(~n|!x<#@5zNva@`; zk*2mA0CYu*C%Z2U^1Dgky|4V{4DYG3b(OWXX$147o(uvP75ijCbGOy z6SI<)n|gflzE-_#m0}YzHNBiN5fxH2OhkhKQUHLD;_#Cz1@-PXx<0FhdP#7dD~;@! zXiG>@HPJMRk9uVUJRH9H#fBHdN@mBG4RgvwR0xnXo@u?qd(KUb`$Qav3?q}}iLE-~ zs8qrFwv!jIl_mQwKBK8Yr16}SRD_LXu}#L-D}AtL#nE zIP|oGd1sTI-8LpJtrgWMXeo1AkTk}|?rBd*5t)HzCZZ=I%*I$=F_zbi%T*+M&JFb* z-z(1E474SM*4y@MI~jhtAa(~BIv34G^!@##NB2GOpIEH;%`ugHpIn5F{s(a{i^lx4 zVYb;QN8f0%lUGCfpxn2mn$KJP&p;_o+f9;3>)oAJ6*V@?BF9ikI2?nVL{&(t#kjdB z4cF^np8dJ>pi)O>^xgJp#n{c?!qa|12meqMt=HOF)e-%G3b}}F*h$I8vd_i8h*j1( z*W})_+HD!b#zFi4ND%l4Nhj7uh(t)RfLyPo*Qyo7bGOCp-+9xvNa?Ga;QibeqxeSZAWF@J9mw zUzm<%BZB$|dEQ_AxZRK|DYsg*E7kGOO*aYzf6T*2-E`-qWo&#pqxskEZlzYw&@8@j zt(!z{lh zgK2uL3fqr%w45`yW%o0|QToQC)Pv*PZN$rVWPlGQO=%dk*~{WMmoUR`{)BT|T?dcQ z@{4sS{>Vl!X;%vP6gQ=N#lp(c+Vk4AYc}Qzec=}AA5Ns%NO9X213suQ_O+nFqd+E9 zNsvo(6|fY2dk)P3*W2D~%IaGl*Zb`n7rdezyR?mltzLmC%;G`N5`4Cr{|lJ8Xs&~?Mr9{zW4NWgj2X13- z6v)9)8k-WV4TkAoKn{jUhk^&=O!EkJDR%`L2Tie#ew~YUKSrkl)mYfwv>qXiYz~eSU&~n@VNb4t(Y^zc5 zxJ*73TKwJSAIq-to>bZMB{T~<^5@dPw6>v(t66Is_9rmse(d2!=nHCXyEV1UfhO7o z-MNwP+AO+Vd=Tl}@3BzR7g=Z(bN>> zzBuGo-tV2z#efzsXS@h3@05ukTid7uV5=*Q;WlsT>JrmfPj%5$&%(|2P`Ul62-POGI&xa6lk3PP^IVA~9>`PYBq1LvP z&+czS#=lA(Cw(<1|8<>pq}bOO$JpdF3jHllLA=){gGsh!xxPgLDde6$UN9gqd4 z7D67CKW}YwSPGcdHVgHvwYEK&cv&=2Fr@)wbMZ1UEjIi`YHf3XA55vvLNV)YX$-g1 zQMFR)d2KB->R8{6?bkHjNh;MjC4phFjl(J^Xv#N`x=2>d~o7iRe|NYNW*|+L8jMwar338$DjekLO|u z{~l?TWbHnBK8*d>rH)6e{4lAt&3SQPTH74e(`=L*)z`HgG~<2i<@;~{72Ha6h1A;i z2lBw=Fv*HK(%QD=RMnL?>wgwJ|6OtT#P`2`lX95Oi2_rFChJ&mYg_m25&I528Zc?K zic#n4@ZZHqRcL1ffsc^zHW+)YZBINuj)6B!d_4F@UW+@;eaqX3kQ|T&roW3kBo<2A zY;Eh(eA&XAt|>QLKP&zh=W?%2r2eiy5%~YYbgZ?lcGkstvo22Y9}`+;Bwy zfURv-2g!D8+wB26RXbvD4?F9we|^Mr?^_$kJlub5NdnW_X4P0*t!*x~a%87V)~h$F zY1rpY(gr0-t!+-o0Us~hEpTRy@Qv%AUJBx^>#`(Z;h4HM;$=HBzz372G>nbbw&>p_ zKU~kdHZ5}D-&gugzTVPCFlko`_!PJOo-~G=NAICmi#7IJa-ziF+O}B zBqZOm5iS-i3VaUHijLIQwv3SNN4J0470_zun9EyxbVa^;Z#9Qlpd>KGTJok~P_f|F zwyGgl6Yjb`t@CPd&x!8e7B3HVG~C&KKN`cW>YUT*4Uebxhz<^4FUiaqZpWSN zivrWyW_?f!>_TI>^~ru;qQ;SdX=9?Ft%_0n6+~`r`$M5%THEX@YrD1WNX9{R=S!^? z)Jb|g&Ua<%aZ+pBA4$vua=DA~^TxCBB?lHS?~fq|B1PkLQt2rcTNNa>KHRNl9b<8+l1vYiJZUyS?}RvUtyJT}wAC|K@eQ z3EvtnAg=W;kQvBDTDVpcxlo}F#jPP-cZ*&;RWI0m^xB*+O{;n}=&@>5%Q?hFS`LZ; zatkT0o8hCc*1o!ZW9s$^H|Ou|z2t81^zn@<*CB2pEr1os)t$Ib=7l3O53D%l$jjhv znz8kJo#zh@4y!_3-B~aARL~+;?I6?oy9tl_jO2 zoR9-1OJk;>{qD8oo{^g_{&lY3gn?6g);_vRM9R`QETzaAY3h9Xls{|nwPR%k8&5P^ z%v;+w#5p5TDMiFc%l0nQ6?^M*H_zCEn&sG@8x z(Z`mcC=v7i!JwN<^g^FH&qAv?ZLUcam?V_hkT}%IRuy{q{U)!Srr~OTRV&WRBvKN} zSz$%MWC!}skhi-2S(m%@ZuZkh%_>)H91+a1WwHapz!V0|2FCnQV)4$q#YJtzwXTkf z0rKrD4@>>5^|P%x@?5ZP`I`+>8r8bAW6hUt#J8^;5&)*(%hEJk9c`6EyLj%(J1}}< z{Dv;xQ43p<`n?<#QUrEWd+lgQ*WP9ocT~6R+7lVghJ;2>xMyoOwI`*h%tTxLXbiW< z^{=0d{u-b4t=^_?NRNYX>(@_M;2Foj3@PX z{ee6%ogoe@YS!77czx!8S>4O|y^Z^*DBnGH6sa@hPXvNVGn;AZNN?MK$gb5J-i`9e z{Pts_`_^6@QkvOGSzxM_W=a;^-BzjhSia^wax9ga4 zaHbE3U{`S%uWmb?uio$WdE7Ox#gfcUEt^fZ6*V~^3{3ILY*Z|?wAtad{g~(c+Y`m# z(!HAg`}^4K`lRC3A4&ZGVLaC3=AQN=OE@B;!rvcz&D?hN2f1?Rtno&PMc@#KkG!qk zG=|&ueye;1;ag72zu(Hc_$%UqtwUgeqQE3~t&fbYKDX7a4}3e{Wx>>SQJz<(a6jxP zC3l?>R0QH^J6&oFw}ZcyRJvYqNVPZnUp-j%uGdCeakL#FMIgj9C2MT-x;>lKKeK|@ zoW#TjowsgjARB8d#I!4>2qeYrx2ZAQF4a;-tQ}cl!mt>Vg1g=(B$W=n zG-7OtwXf=HM>Jg7nsgP0)6$BFQ`>J=W4LAi+vISm-*3tv$=dwrN9nvDwoXQdLAEdJ z9gwSwY>bNoop0r<%v{j-qTdAR@b(YOK4=yIogyxE`%|fJiXaBId*4>3ZN2qS(0}%f z2VWZb$1J!Hop2NZTQb3PF+`h&i`>P4{}E82YtqS~O8V|G7uTl7j@&g>P;9f9|1*&s z=sFFM?D{L}=&O$P zhKxwpmwNo%^@@{bqGABW0~V9YbiT4tQ@_&lc~A^%4X;G2&rwevm3>8y2b_~tqzyKe z!WnL{>tj`8g`1jgxmf;WGmlRloHy7c3s9JAHYyI))rUUa>XQ8;t;~wU?Xtb+_HL=>A=G6b2|uYNlnuwf5X`m1iu<{M$n`C~sEpv7f(_v!qUm zDhiPlUNy8=Z6EE|`PI!y-74Oy-6CiBrKUe@Mp6z)1C%f`8yE{UZPwdsXyS4n-k2V; zpw!(CEi!B8n~Sy${peZO=WZLB=&sp%WZOI>VLA|D6=RW67li3U3IVR zUgyoE;OQ%-?5W%-dF%8}HV=sf$^ul_v+kU>>h9dlrRon*Y=Un7cpCB~J>U(wu;+}V zq7Y%*DVj6f4oP~n-qeMCc2;za+Cy@qOWKUE?MNvKp{FUSW25%|@s!ts4m@tw&Ii%E zuf1-UWHa=%E2k(V((PBx8E${Q(yyw&vfuCA=Ax7?(^j9dnMk)Us3?RUR?4cB`up+f zM>73dw9EWAuhXy(y=%X<8F~~Xswf1PR&=ze!24GHQR7KYrvo`Zq0WQeuHxDZE(;b` z6gD0!T2gE9Up*PYS7n{UYB7%ae|&y6$>zpWpe!(#j^b4~V;Rh#WWiPVxFao^T^={8 z#Ksv7DxMxK%phGl>b$t3;@b9W=M1;*OZHz~6E`&`?#$x;$3psSvg_LRg}pBVNjqYs z9jL^28;};fCuDGkRn0;#xn@UQhf+y(XtQ|339(@A;j!hQ7z(!P<_tIQot1Q*|9$^5 zK{m9}rHwuBkniF7L!rOHywi?r3qcD>30c!Pf(n;R&o?ea_KVa5r?!7mW%u$*8`@l7 zKetBH%4Xq`!*YtSp{BxS$mG<={{4nLW1lTH|HI}>dS?wq{VZY?G*&ArAu zcVzOCevcoE+Hma~YD-QLHq=(iw3u6_^N5XN zb>A0N4t_b7f92zC)$P90uX$#hrgOrIw#lXvGs7)uZsJ^zaTRqNPwbGF@rdsC2PT_@ zf!ZO>1_n=vrS(wr9rBNa{(nILOTRs1_`>Hw27AL6ry1hf5<@sbH<~yV(LEp-1xF8yAvyY$@4bN5?znJw}d- z0hPKi*Dp$r+_ogJm2|uNTe-34(DCg~>6h-?e~x|7EOp_yAW#WLGY#!$R~T-a=0AD8 zH*3-D*{edg!A*umnI#yVkOb-!Z>}P8sukG%=6$a^W2Uuzbf!nw@NY`tf)Z!VPVr93 zDiYgNfw=~TTdxw&29%4Ko^a-$>Y5t&!5vijEVi_zB$3I7}k|VcG8m`(TGYFXI4ULISJ}-Fo;8~Zb+>E;mT-!~9 zPD5m}Ka~6b2nQC5L#2j;OY|FB=6b{DJp<2VDeL}c9E@^577c%hQ2iH=IBUlvoRIwg z3JY6a@!zp9N~X1>YcZdRv#V5!1ypv|h!PoB`q%AO_V~`~^AdV49n~8t>HbHVw6^Kk z(N*(ab(; zOrPjX8!Ch`h|Ul+4gKL7o$#TLMBmRL?yJ_z^$J)ZM{cb~5sWE4>_cGlbAE2K!-osX zU2P1lcZBZ-ctavI0>hbFC`XP~s44vUA15elbSa(5oz*wE;5i8U> zbdKZKo1?}|?eVtJOHQA|WilEc?{TlxDQJgt5!9X@J%ID92U5UVy#Tw>S`?wzW1mPc|6oAMXa7jAkP4hy2R__R3#hRh+UcYSU`|Lj&)lXR zdy=|;Xt0Of=&v0EuT^}o(%cDc@zHvtzAcc^c);A8kE4!H`+Bg`wU2ka!?%CPPK35N z&Q0rgDoARHg*vfNB3B__bbwV6#sJ4`Ki%J9$e7sdyTM2IXU-nhp!{)Yv%}1w91fdF z)<&qVZ&v$*`5B#VeDd~BQCygA=5RLot^(Rv;b@IeB{3v*3`2wBj;`KWyxEdz?|ssH zhqb6XFS1e!ltda8TWp}>HRCc(c$YCRfuyWZOIj`+I{NY=3MunYR7TY& zVk&1jw86SX6h=^{AQfpCRvFLEuu6|)QpAb~35+`1t966BK0e!Z-{!Cw*$Qr+*31;! zjA?*I1=C0;S85cP1vUGAg)3?YjtrS93moa^vJF~E8Vn11T0gsEOA&!O64oOBD8Rld zW;lPM!}0H)-;c6Z{8ewRYxgw=qL*)jb~!8KJlK)ZtJMnpB(39Zt2c(5**$ac`24KH z`7&sgr8Oi5P^TDEE2CDek*K4P%99~8W7r;b0=5E4Hlafkv{vC?D(m~kiDRo?q>m;eKB(9-Qnlx$3M>bD-@`2>_8+GB-_!oPd$JV$C-8mj>UUV#~VJ zZn`6NLCzgEo>p>D0*D1!7opLpk)#s3#S2WYsY%F-Gdh)&?dC1Ha%f+>I;VbQE;)8F z3}28P6_HDST?qLyoeu=fL|x4A3xMRk;jzXV5f&Vgc3_5E^)UxKdG9VhYxIi9E0ueD z)HWsW?J)fS03-e-JP4YHfrzuN@tLTKNZ6X(FKKS zG_!bYyHoMuqxMx^`RdWrc7PMsFKmGd!3`jxK|0lD5O9DLl!L@FdY!U zbU0u-bV`<0XU&fni*F8o$5>pW1AhPk7=;uFV6h~?Vu1h_ivt#m0+!bACimRrpUvln zY&p}Tcg7S&yJ|A8}u#k^%uN zlmu8P5Wqrlz(P@f`||eYoWby@vkS8-cMfY7xP$1 zMj-_Om{>@7m{BHvowsSmmMh>kmP5u+SR) z{UU&b5c*^sJfmJHfGNH2=l`0UyLjL2v?+_rJlYMdF;mu(1r(40e&#?1_<;g4z>kbd zfS&_ET4MnPWT3w}kb(Z7fDH5}0~zS=0Fc&LKmpmUmpPE#dVvD6TQ4$@-Fi6yq%{^$ zKn@Hr2XbHlC?E$0kbxW+fC5>cU7<@{(#WObhV(yFsk3XY*&1n$1<3A93YcLa0W*w8 z!7vsuSNk@sW@zO8y0^AB)~78RUyj(FDWpI=Pv@cS{}0LYjK2f%JmZsb&olmpdfq#Q zjMJ#uWN&W8p+oM)m&+nN&jt$+&qH4BG-Xdv)Z(W=2jSXEa zZ~KApJPIigz#>S1MF0UT0tYMt1bUbt;=89U77(5nO3JE) z0?Dd`;#rkYEUU77OWQK#Q}i3U%%0XKZ^VXJ-1DfUKma4{o}oZ?&rp0z48?ZO&0jx0 zcnKYOTTK>G|NP&Lrx1WqNCC7=dB}KdrbOcr$>Kn!4k^;#ZURV05gM7ME%6t0>b7b4 zw2?b|%-Kg#-&*YOoV^W7#?n#*p>@{p0P=h?iAL@b$%UYJlalBkXl-RRe>4sbstF3} z(txe(^on0^bZ@Zz+Jq;in?Q*LGJ%-jGE(p&0}{N*@Q6f)1ur*?#|@~+o&MrW*&<2gw=mcFc4&t-~urD}ArzT(VIeO!7IfKf<+07lBX$$@0ulxYodT3Grji?-1Lk) zrpNE5+MJU)1Yi_W5P*e|vTk8OvTk8`)-4Rnx^+1t86i?vTD5OEyFuI0?Nf2UsH7kO z3nu{<4g|1p9I$WAS zQVnEEs_`kQMyI4^?5(g#D|o31d9Rnf$&A}Z07fAN0vPFN6b|HQ6po*F!m*=Kxw-?c zZicUpt~YK@m@9u}djc>D=~n>RG6ixE8U)S4Qcs58&H+e48lG$NGsDlQr?p?*Pw_Et z)%8j{!&Y~{5wRFrK~j@So(}{(Z76KaHO|E~L;phSwOy2F6Ud;tpkQ{Lt=V^MK$#Se zQJyajDRoDnBnQ|)yt}24DD+z7eSQ}4?iT(h5bti`565veDTo5=Q@dJ+^uF20n@T-r z-ff&b27h{;=gnMjtE2bagZE1CmMFa_Caxhb|>{=(_x9#*tQQ&iMY!3VwR{ z?z(UsFe)h!z(^H(C6Efe60guJu?qdWcEVa6{4TN&w+@N=xF%>H0T_i82woHe5D+;{A~O>1&u7fAg5F%e)Lpgr_?Djo?VcMadw?)u>`KgR=gWmi9SX3P`M`!UHfB7OS1ox4Cg-(BUz=D|N5=BKj_IlLM6$1Ym}5V47au zPy-1))Ob9h#zGJ8{BNDhH=2JyR5v6eKkgxMSs9fS1YjCckxv7p$fv=Jd>X9CcVxx) zSFMJ&?ijwKv`_rsK|ArClu8N&Fw&IN0GW~+d`fDtDcOHdYR4hkAIhv{74vp}nj1s_ zMj-`}AUE9hN+ie)zkx`Q8=h<03=BV`8v$o&wUxi0KIsnK8t^e$v}iY;Ah$*i#M?;u zGYydZnTCK31MN}^&l=|*ahKg#JKW{mwA3Mlw^2wzyvU)^duaXp5wAg_zk_&@1AQ{? zb4I;Tud@KqbV-3N7EnO;2{s3^PcSGT`vjAL>=TRv*)6Z+g{1h65nJCb8{hd^kMsB& zF$N&5v4EJuT2jqG3#4YC#cKvytY*-<7khJNwTAa+R$^|My8Y)Hd+N7m?BeE`&zM>LyKNkIUnBfVju1M-G}4u8WyhrMACaNA?v zj`JE`rR}x%dBp8ri+dQA6bN9Xnt={T%|M6O40Kq{px0{HU$mh_O71t8ucL+~RU-hS zkOBdW6!hwV1id;ulGR~BZ_=-nuL*CejM&|1bUkq;k(L0ALJ9=1k;FMvHxfj?O*hiC zW9mktyXEq??LM8C>EmKP9k`ovde|faFbXLUz(@yo9gu^&4nMf-Of`cse(;Kt)qakB zk`y$4U*qBgU=&gyfRPHtIv|B&9bWy_VTIxujOJU%ulx`iEs`XsC$3=tkiA^ioQIZGGi!^GdTU4S(^k^V^Q zcVR6bk1ub8n&>(wsS-7L?1@gd4lT>B-%!_c4Yb)|W)Oac{3v{)o;mmG^|C^r_vHR88CZoqcg;5< z$4eyz0+@^lM)Wce!H8aFnyq>nI!T{SRn;DIW5>G2yIBva_Fxj%8&gSv07eRT^+3X1 zJs!jAv2eFZkL}l1Kdv#({fYm=HeHw1!?y}5DG0sYW!9g1rRw4kSkb(d#f^-6n0CED2z>k#?*a`Iby!6zW`$vV2_6d_T+br_O0i%)v z0gU8f5kNdF0(YAT%)`1g_~&ZbDwQ|9DJ7{54;nC#0E|Kk1TfMkPa=SP@+1QPj!6Xe z$&)ET89w7%9!w4OI`s2-9Rcw|EtQnkFZW^5VI<4&5jFtG6n*!U=Ht4|%u-Q2f9NakA?ziO|)h)J+fiGjdoc&i16jm-iA z8=Hm0#%7_gZFh~x)2X()HoJ0g&B&ph+7hr?5QBk@O@@sP1~xVU8ykh~P$O5y``zoZ z^L61r`mOT(OoEL{3&E4M9C_v8EpD*uPbyA=jYFtB+Ouz91fePM6N zYP6u<&c|I6)<2)R@)HR*Dlr(?$Z;Fn2MlaP+{VV@w#ZMdD~KL$&HR}xn)fm7WMdL+ zRAMl&kpmDmm;i)L#1w2S09jbQb$?dC&Yp3(V~0FZ2o929qY{HSRz;F(?U6ug?U8t` zJrb+6w_cZ6d&P`SB4s03d~^QRuJ}2WN($m_Wc;(;#M{XDpFq5gj6dA8&f$MRSG#3P zTqUn#*SjWebm?+5apN-lZDgFzDkDf}NiTYvlw^T~77vecZBS@uk6`vuZ92rdAJpcw zFe!421+>-~K|mX=5Snf#Fn#|N{}Tvk@rRq75B~!S?T+M4-_9m~p6D}N@o%$3zF|1D zIGt5S5RHYgGUTdl(zj;N-$67MqE9vfgZ_rXSvGP)cX8J{Git=AJ?VYt>TnZSm)-! zHXf@+Jlwde@#?o@L#9`qiU&tj($7w`STMyfj{{4^Y>|}16Z`l`q&%ru3^VysCYQyN z_Mf}m+=GS`{@j>394=4PmW{oN+2 zXX>}-_b+$4o?EQy-{VYItCNU6H~|m`7D|L14qwcbc(cVEu9)vF=CC9zn9mWhcv8L@ zKvJzRR0*r}2t3}NTq8U}l^nSnZi?YQ&fMr;7?1TbsUwgIb$Wq1LN9=$k?|Dh6zV8} z>Gs(NzwaFETavZ8%l+BX>D}t=gEkp-b%fU$KPwD-(3^l}7}PWTnC?Vbqp%+D2rLY@ zRv&vO#ot|8wJE3Vz<-X{I0$Vs>FfwU-LMMvhIb8(uo`~6L^G_0XA-c86>1$UK&B9k zl_nE?Q*S)&F=Jkj?*1V)v}t#sL<5#~nVi}03d1q1DidwGd$%G(SoXxwgxbo5;whCL zE*b`{wP^sx16F^jP+~R!In)0Ri24+`#WSn_)N4(rKe492InM>49)#+G!+)nu_8IZj zFEv*-_&xV-mFnG~HJ0$3v4BNit$|f!_pd)F!S6EZoTj2;5Jfg=$rF^MIY4# zM}NpIzo+B9TL|DbrKgsfB|KvdeKVGiG;Ymkz=B6E&YaHw>#~79niP^S+)_Gqu9JR0 ze_`Ozq~7<+by#U7ZgB=2z7*!eY#$+$?Zf2pnNkVYN5qkeeAwPTY$glln8htZv0ff2 z*T*1n3*UNJ=L|T7^Jp`0#M?s_O@CRXbNK8o6|<7y16IKKz&SuEIxCFMytzFc3C zw^SnJBfrBwQkd<{&s!~2MsP;uky{H3{8zPRwkS?gDBLhRPsTc@6>cE}1q&P+NnQ{*caOE^9}E{`J=`AEcU zt~au;dGq;vo&*+|0i=b+F=7R*HLT#qNoUoSoSAfm_jogqB7}MJv#--GR$E>pKR4L# zgB6gnod^O%-fSrsaUUL+DU$k1nLbiqU!kuz@&~3wD&lj^Kr#jaqyWIMQVB&0K~Qd5>DG z(l436;E};Qk{<0G^Eb5Fx)oNK&x0Kcy<7p~UQ~WuseZ$Hw7;6M{#Lswy3^C4MC)dd zn4Gz*tx!h8L#T=|en!#IO1aRaAL*}G=mwPZY%jT3AQmbV0wjHo#5AajZ>w@5s&YW^ z>P)xAO)s|a847K*qO}#y8%4(u)7)dYJ)5*DJXomw(D&k~>0WSt1hl1KV@%w)ijYB( zatVyxCZZcOH&b=G<&N=QOsQX@Y7JTJ)20Z&eUQ4 z*QS`@Ww<50Z>gNDD8FHpY|5kU>%-qeTOBaR#GXfY+~a|NTX!C=CiW+15~zg(FZN*E zO|T_bqY7oX3Br%1{rIjK@-)mpQF6WKekh5muN5}>o!z<##^JSY2I1`XS!s`vOrAl3 zRe&y&Mq|oto_2LY#{t?l(e7WCxlQ*ZVx$6@oq1LNf9YJPImGx_n6$kBH!~ODOwsLs zW0q-sG!9U5QfyY!^?~E2eA_zQf8zX9XuVBqNPO35-~Xttk10b8i-jSZ3NpmRdk>f~ zlvABSA%O~Mzz`}teLaoCb4e)6-IKmDdO+O9x3l8PML@ePtSU&zzeUPC4bn)WgC!>W z7>j(DEvvSBa*4w(&+81DHXYjIkbP!Sz%3M1=*`Ej?}5~T?vL|>gG%?=Ikqx95VBk- z>QS30@w(YE|LBXrERWI%MBc+p->kH8w_|5vpJXvc{0INoJdx~AXWr^eTr1|6_&YC)3dk5U!J`~dP27ZIgmf1*E1#U4zFi%@5hpAtU$+AZ_* zbobq^r39lIkfK!EZ1hK|)^#y$nG81zGl(eFJ}doEsttWeQK~v;+}ntanFj}EFD*W4 zY^xchD77GF`ZphY8WH1TVG^-uwpl}|Gg$In$XVjq}3k96+0WgA%l z{pWuBT2asaDVwqu9Jr#Mv>3|TxVd4lf^_b8MiBi+VKeOtI>0jAF3+#IW5e~%L4h8p zN7bKw=pN}P?3AP&+6y+u&uGua5AIIBKvOtLXXK&gO(=%OV=GM*k`~9xL*1ftN1QpJ zoZe!B7TQVH+W`^IynIuUNN{ky#B$yP(-C2yXLRaeh!@**lZDtqPy z9ch=h!$yuA-=eXUb%=p1#<8P|((-=MvgPFSEAfJ+8dH*%!QaGO?qNQcimTLnQ;b=H3T z!JG|QSu*TNpg)MT=~mWiTMReXPCr7bOnJHgL2RerEBbECBn6R9NqP*}Ned2_vvV7i zTlcPu^p^r!z2a+4HgwR2qZTB}nYSqlDWEeA1q3Z1ls5elz_w(1G-bO)3rOyQUpW=( zOP`cY*wXH${L*3awq%D9z_w&V8)93sFom=&6~Ih?XJ51}jYx4_;^f8QH&@?`TOZRa ztK{k3dQxX!!R*f5a!|;QPjNK!xQyXuVHR;nvu~DZsOfLdw$zIhqA}d!MY)TD`Y(yf z%UV!I-3l5^YR|UI3E(tg;dU0$orN((d$vtuOd~^oD}OYu6S*~m4#tME5Cy>=&y2GQOs=N{jSZe6EkaX&f+QD z&10gzX-KX7_E|w}_!jfQV(GOohiK)uZH{S#-_w;DMqeIAuD?KkaOMTi{}gDTkMj~o z==5r(Kq40^)Yz+w9aR^V!)E-rpMB|q;>n8`S7@m%TH0I~Q$VgnUX2qXHxubJ3b|gO zhmrfVOqXV$uXf2B=DSBQ)I-0t9sO{{`(|t?*+Ev?)=!c?Iv9C%Q6kjF*tTcHfS%nW zm!5eXxI`2as=8Aa+U5-ZS-MW9m{Mlx0JNxp4$GS8fos1mXzcmGNBn>_?#>-(wS5lS zvfQ@S5Fpb+gv<@odrpsi69V_N`a0y}t+>z%I-hp;j*t%d~2hS_$K~ul2w2OE%=#-sh6;^=c12J2?>A?X(cu0^Wi( z(<93`I$%>-Tiy28ek5J>W46n{pFPe)TO8+h=AxlO*eKCk4`-tK8Gdo*g0Dh)zO{-g z3gq&(v-@o4FRuDweb0FVb7w_E>j*_{anZcv88EY^3U!?=epH?q$n^ZD{gngFzeP{! zYufP~#aJa&*aU^XQgQTBwssDnz|3#>7A|XJ)}wfPP6JCS~+=stgDr4RGhhJ?msOt zsCphkDe+xbq4YOhCm{Uk*fleV9_XresCUxA<0-Em*82CG=t8sM5Ads&g;H};+JQpu z5{@&et)v|&C2qYE1uDJqryGo(LD}Q`e=A%2Uc^WOC<-aQ%&da_~RVRyL*TVsbNF6V%&6_{)}rzwUZ;^7XCDdIk!A;9ncT>8vu+?Rz59 zhvG#r-M%NnKN2s(j!*Tzet&y!jZ4>dyYoKsFW;Pn`yQ2)cA!Fu)l3vhJ5Zsxw_v%B z{a3f* zEy{NOLI6b}r5z~J{wSh-e-z=Ho(S6?@2%U)cX9K25ZbrG+$R~?5&|d+DcwMcg@i|m zg>-wASZMMnu@LpB*cFRQxGx(s_)OzrsV|0da&e%jq_hJ?@+dLw9wo-zM2vaVFG1fr zV?GH^j7#h1exkvR-ULt-Qo4bXkUUC4yGKcIkCI>>Rqn#WX9w;kci54utox+&l+HL% zR8rc3B83MM+QS109v(=r@F4YgM)!T6bz!CAwzlrjeR6jKC<-avK*0)Pje-?)uTikV zv_`=SbdCBpr-Rp^Pu=Rd?mc#D3jbVf94IQOGnfAsMnVQwd1(Fm6CV;oe|P5g_QKNw z2hFGx3fzp)lhq?V?!0=jVhF6i6q$g3L=08bk_7~S0e8s5Ew8jDgz(9X<00aF&02t^`1~Aay0S~ms0s_Epq_0yNW=6MO zAOP&viwt15UJd|gjRgdN0|U%Ga9{uk00#z;0UQ{B0yt-e_(Zi8dq$Ni-5_3mWI=%0 z6t>1f`)*4LbYa>9UHsF89xxW@9?T39YqmCC*<)5Y0eqlC6=Ju=16`Dqc2CoJX#4*| z@-*Y`w0oNIsko;Ze?vV@cW`N^=bN`T3z%F(m3?{sV#3pGu+Z*ldQx1cr#-II(DW$z4DaFf-Qmi6* zIBG&}@!X;LSFQxLKRbNtH3BFKDc!rFREvC8opf|Uf2VslM4yU#mr*Cw!?KmD7e>Q@ zy3?^UsxYAUUifZki-m4a3ngVaLTS%(gyLC_P%O)FE@?}4-F@zorJsD?Bvw3r4)-)F zDeXX!cEeEGcf(M8iwnhe!`Un5WNzsEX!7UTiR(_!Wv3B9QAp_qN=91bWwbByGJNHh zVT*j+?TIa;m-q}`Qfip*zjXxJI8anl+JPc1@-o^Nc^STP%dkbhNqUUC3p~`POG_b} z8Sy@g0E$9NJ5Z#lC!>Ap$?*9k!=|45jESp+``2ju1?^{Xx_ccVfTEDn4pa;gU&&(V zj;~}frX5fggYJH+*O$uN`}+5-DW%GfyzBe82>}#^ly0Epq>8qj_KLO~FH_60iuOhI ztfu$<)>OMCsh)L}y=Ec~6qS^Aph#&MIqhi~Ii72gV`-W5Noud7k3#d8ym(yP_ip)t z1W*)G+JPcv738#M736rT!1N{gVd3pJJ?vKBJ7bb^$>H6*mlHryNNEQuidduMQFO0S z@+i|9CC9!bc=$}4i?jEpxt~tttdH=!d6fW)LP|GKVWg}=80}ewFg&XehGi9Q1`off zV^w(8=+oMnuRGOkjRQp`r5mVl5>Vl^0~L+~6^;Sry20;5ttJom=M+!c>h(FgA`TRl zly;!PiK!PJPWRLc4>wJ{@NhId=rKQ}MXGCHa`OlINAu43wIhI{kkSqmsdGM@_Rjfm zyd6Fq>zuFLC_amolk@xLpc;L;Ms)WkfTEDn4iqVl3a34e3diH9a4e3hqU|-Zb;e`X zhtRB}&9?8oO8`Y7r5z|WY3iwIpL%M1>R}(R#!@@pDNyc7z$Tx>EMX64#>^pTGEN>q&J20ThLlZlDw-k5bU?Q3~8m6qrX{ zyM5?F$@QL>!dm9`URk>SDI6#&DeXX!B69`pk+}j7w-s2uZ~Wx3hc^uQT6#9O?(K_T z7)17fN=iFWk;EFMh@^XsQbd~8C`BY19-J*PIqQXFMZea)Yh3>Mv!_4dQ4~_Tfl`v< zC?)N2loAh)lvo_4nsJ{|M)%bJZySm4eO+@!Hm6Ud%NO6>s_Bcw32S-XQj{5XNIJf!Sf9ko6KX9eNzoYvS z9z`Lg9Vk-HTuFP*T!|;bl~~UFM)I|P>W7@Dkg}smnxIz+qFhBKr5z|z;!a6>;!cTY zPdJMg_L%nNCBsk_JC7~N0CY_;H*2dXRxSw6;4XY zN_()+>Kr!q}l!_LN@eEaDl?om`y z+JPdyVWFb^4GR_i+Jxy&sGv*NbUR$yl^r!=amnPwDHW`tJr%6MQ^6W66}<7#{r7IIAGA-K@OeY!`44{MKv79)2Z}WH zG_+4W4L+YV*wkaU@ICW;z5h9dGO$zf*q`$VpeUrY14YUnXlTzKXz=WT2Fo4{X!L1O z+ifitd(YTZcLchK36kz^%cqeXzv> z0>D1O<^c8y1_5B7U^0Mxf>8jQWKX>_X5+yDFJtaE|Gnwab-b0)0H8G%x~Hm^lo8d^ zo)OjJ8Br~k5smr=-lGIHv8qls4_Y>p8$$NN;gnCQY)j5_Ett6-pZ)MS{Ys6^jX%f%#+v;3s)IxHi)$!lo2Hk(rYQp?3fwVU?qJ^>Vkly;y_)9(JkzDwzO^LP|SOBZ+K-ZY15=2Hi;04yYT6?tZN&u54O& z$mI@Gq>u2a0qy)X{!6)Zu4C9dF~BY z9oC^&%l$}R=9^^?O3!lP{aCzU8UYlAly0E(q-=wp_H2V5&o=0>Y{RF$Q%mmB&h%AH zQ{;9OzkG=UMJ1&jC{jjLPkTmGkEc2H*qt*sJES#ST72J?zU}+eyq$4`xRQ=aN;^<8 zV%O8l=-&18GSjZ7m!Z4fu(}WraiFNAv;#%*s0i9U zDgt+t2+X7Q?m0jD?8x$Gt4E#e*Wp73QQo4G(hd~q65t5hF9D9gZ}yGAE&*Ouuld!V zKFhLCO862F|J>w`eVBTXA0q6)h6F$OKJRC!zP zUzhazLbplQ9)_0LB&OT1B1u`PNZPYfk$6@r63a@hm{Om=dn9MgjUj`2)c6b9hWizj zls))tw53yLO;!bge{Cngs z#gN?5RkCzliGn_r)S0j1N+e=7(}(LVk&2`oo{xyl_2#oA-o9*K5ntrXk$CB~$k$}0 zYONBMcq!ykSR5l(z#a;DBrFl?g&u5AA5XTI7Qe&{`Aj3aSvm7%y~0)kb2rq_A_5X3 zcc)IT(K3Z~uSXE0ww2Gw{BYt!E-WrjEMg&8!CbDG%jNR8EFNFt!{f6M#C&*68-PX1 z;V7kA0xN7I=FHSAbS=yvJ3a|M`6IOawUbA3$0qT|ZLtEGGvB%AFj=rz%oO=@VPC0G z$dmXm`CM-ymnrsTd-HvLY(S>bs>QHQXB)6HPQ+@3tb-X`4tSU|A1&qbgErxmgeW^grd+v*!K<@&OkeP;)07qw_; zWnwzBif~0@o)4cd;V}6UiPV?tBjItxEN?M~!xeM9rM5hcSj%)mWE;@wk*{ak#?G1V zD*i7OG6T|qDf`)pO@YZme2gpP^QAsKZ*L!%$@2APahX!&e_65w(@yLI zg{y+IU^x@_OISQEn=eKn;6iWDPGd~jxwGzWxhJeJh?pV$Q zhK2KJGjQs!dN}7x!=HZt{4ACyYuvQHl}YH#sj_f1L_RahA*akZ&UjMcsel1x&<2h3 zSAQv4N2afJP}P1+!|0qdUr1Rq4u#m6FO7M#ID8=o_7O^8rkKqZvUnooM>Y%jMauW_ z<(qjFGV8SZ2#tp+pkR3-|7UH*N_A%T6{ZGe{v~`r|5Zr6^rcI-eyW?~Gr#$N^e-f+ zm-0DMSSn$2kW(eHYB8BYE(d1vkig%Y$u)z@7^RwUVk7&Y)s@|uJ*My;Zw8VB%X#xR zPHfjgU*zbB9DRf$9>+(*lJZ4Dt~U>fAf(9uN_@kM>UG4AiJ4XC|BvR?*St~ptH(t5aTRE-_T80=hn|r1Fqek?#wv&uzAS- z05g3!5-y9wWlCTXpCb{9*c>Tx-jbS6Yyt`b0OgFoDsRtN{pqxb|7dN7XUzA zuOzu#E|)|w$M^StpU;aA!p+>w?(FWgonb$+56XFIRlC}AGv4k5^F@3oU|>3nTpWc! z*#{Pr6IaBA-JJwnHxlb&1wR;3z`(m*?3|I!j5B=I$WMyYiD7e3j7hsXC&BiA<=yUL z*d2Cs0w=M+)zQTjEDYF5XVm#Zl_W}{iUoYT<02pOa#pL0BRXB& z{_SG{0B6UjJ5LgN{a6pF>J_ckmo|++du*gFUJdGj;vDic8>cMsJ;JXVPMSMrDGgl}Q z=vo0d8HV3%PETwP7lErQSmYi+XNCnL2ayNZd7PXbJ)E47|8zGTk%Au$EAY)mbA)q- zJx}Y~+E-C;;BGj2NTbHv%`p(gPVO$Qd>2=)hX-)2x;wi&I64Sjzz_iSLLh*3ITy<1 z3Xw#{SILP)pywmUVbIN+arSdFlGl}w>u41?(VR`k4F=|@yIAA_&L2J>m=3@a^AI|? ziagw$0Tp~5@kjl>64VGo7C!d&{Mo}F229Hv;JExsOwQnYZOoYh!~rN2ihu>^?B>K5 zxB|zsvkMS>7k77eH?aBYyj_9$nH9Kt4it2B zP;dA-*B>6Acj1LcyZck$*Qixim69lx3;EJOwWF-zLHiJSIBc&}!D2BivloKg5BmrZ z%HrFL6d-vKnm`xOjrMSjdWm|iOF6fZ4#k1>bKH>6(vC+u?Qv-6j!&?yv_3t zmvZh=H{gr^8G!+UbiuOzXs9v!9^@-wKji({Fk`^>YG)A-nMrJH@AmPtt9mnS^1-^J zoV!+NRTEll=-HEh_Udp+L^wafmM@DHMMyv##1(?(>V0>mh;S3-0pqXk^&1i1W9Oy# zOi%y*5n41HO4WNg8R*tuAcjW}XFZbAXi3t7W*3UE5HS7_G!uUp^4o<%rRQtuoKW~ z1B4Ku3OB;xIwOqyR=5#HFzAgKn{(;vM(fl?(v@v~F74lwXH}pXVan$VH^O9;gt20C zn$_60;QYV~L;c!egWuXGfRPceGt$q{w z`=uhlsW)dG&pXpOr+P5bE`wx{G3=2?~rE&#c zzO~jdpJCg_AE{hE_*K^0z;d@VSqj>RPW{<1;x7ZyWr-|U-R0@7qv&&!UFSyZ?YOYk zz;PF$Wc{ZK$D1ky4p+DO{@JgTjMHq%WqE)5$gbU!1sdM85B=f3j!|tZlLUu=GIFzs zzvdQZv@neJTKd?WuvaH5m)erC_~E`DV++R4RA???p)V&qy6=w^^_XyQ;d%=AH|Njj z29WlM;S(9bQ$$MDBfr_lYwU?;OU7Tje0o95chx3nKGk!7cmyJ-kn0gVI0ghJKpBKGd>Wlk%a|IR(re&%I8%NLr5q#S}Ykq}>C&w`cI9sCNB)3yzpt%692 zRAdj*J7DCJi3DW4DDAOy6P^-Q@estotctM5NCH23A+!ad2`NFa${+k)X^)U#3;t%O ziczsRFOG~Y@$JVE*@9}Lr7cd|f4j9I{_`fs_svT{tPl6f1WbF7dkwPvJ z*`ci9u5>$;BN<<6r{XKaly(F7QVEa=SmPq-2fpTc!64QTz7=sYevR(p{B7hJ_JFGc zU0k0{gZ?6J_8d({j~zO!m05R8V8jcKfMp_BCXCfE;RzCiBEifxRez(ImtHdP2O9q7 zX-No%WiUDj43LqiB?GbD8K8ijswDxP3_DEvy(AzC4srk_u#&Y-`-o<+C>~p-eGGL( z=pm~9hw8KmZXq`3|Ase-K}XPk&Kj_T6C7GZbs5)B!9iI#(;u;OiFob)4>(r}HzH)8 z0zM-D)6S4T)Z5hNkpUt3Uw2*n=Vs7Z`UI2rKZgM77a?wpgwZLSy{k3T*_{8+ZF$Bl z@Bd#-XQ*gQXO48AyZygd^k%6>9X}C0*+=&*+uG zAX+TqX>@p=_8s6$E`4K9|%B;gCSi4FXq#uJjFLqrK7-Qz_Y!tH{i0muDh_e&j zLDDq1ufcWVx`4Y+2|{qyNf_cU3${u|97EkCGLYdN>@7or{UWP)v6LUIWKT?1&#cG` zmMKB@HLR>qiajkR2Hl<6afqtMj*}w)PE~)0=ql`Z^nt125?PQatOSe2s+l0;121C) zUkI}kMX+7CTm|~rqX`H};F2g(SV1EwR`Vm2aHL4?gJdwkN;Od$vlJMjO20^zQX+x_ z<#Lt3LLLeXQ}AsC)?AISsvQB9O>$e%coJwNK|_&J{Wd$z`x*0NXiakpqBQf#fL}rD z44@#4Azuf@4C0#{jEfyKGg1k6#r$alS&O4k7f4WK1hW14NCXPLBDTL0ESY5FY5-{& zm0hMl{8I|0P$7v>^-z12fS?0mWo^>Pie@}e_blPCvzOmDAM*+A~^B4u-e|{!5=Z~_M{_``zXcf(3n-o+yuZjT|!vAy1aE;4KUN;8>LnA)fmwlBDy$=g@;D*Lc>>HA0d5H(=y?)=pQnnA zfI;SkFbtHPz@1L`ZzP`+fMByYewPmw40KAa99PC^yNh?ytP*o2GNA&bIU#ksa7rJV zoV`Pp5JJF5M-Q}22oe&ITo6q{2=I1*3I>QPg~eHUC}nz5mCVSeCq~Vh?P{OAa2t{r zl3JTJBOLKYiR?tcQo{?Fs;hz{+3qaP`)?J#rf$vNX@9KRTHlIo?2=K)*QF8W(;NQ& z)oHoS+a+C|u$uV=vgTlm7R!{fjdF+Pk-orCzH;$id~N#W)zwG54C?azv|>Jra!N^n zG8rCjBbqk$<_VuW$KKoSx(B`rmF0i0KQBE~_^{Hhz@C-HLKw-Y3eDoM2aEUQ{0{p) z``hpu-1dFzEkbe4c4W;$lG`F8FxDt$3Va2%nCLm)=kB2>mFmbO7gdXaV6-ZQPs1Ap`70Ik|#RaJ5%1ODg}_r2T*{gA!au z|758%UJ*OQHp&@FBH%>zDVE-af_)e_ zda49#j#{6j83J-d_XvisqG1ZiIpfDrh`joM0;NsC+4;dgKM!{QQu4TC`7~CNngUem zF)#>Zt@b2}@K_DQB#<+yPooe^>;MU#hf{XPCr@cRp=w}PjUeJKWCJvi^Okc_ zj8p0xrh%MVd=7=U-vQ9j?%K5bcW1w9%4#|M`}vjw-xkLWm4)P!LP_MbP!@-r7Wxrg zVz=4Q67;O3%I9S1DGNVPp!FrdV7$EFtySjXSsC$VPhT8wwWtpGD(HkfY2l=8XS_-j zoXcGplY)d^YDI(43wt&AEJZ$ap_jO%!x@$LG@aL@{f>G4D!iOjfb<}Wl1B<;N zemoGn0Z8e2KqCT2meQ`NLuJ-(paYOnGWih_JN!vINjT{IJ%9+- z3w)!Of4Ni-vz>sig!_W93OgRn(*tceNbk0Tv49Rl0W6M`N(sQL^ntNs7YQVy&mjY2 zizNi|Bf?S)J>L(gYGsa5%s7$f0YpkM*L5VwxCD`^rr5|KSf&Q`>f6J|d%6Cb@Tiuj zTm&P*CCKn2DCJW?y&e`c3+D%QsTWdFMYK9hV0qZ|gN$HIVsX6!$OOouMU_*saI0lo z3C+hSvJHn-pa2?ZT^Fj9%UGQ7pZ7d^w_aBI!zk6WZ!3NYx1-9_K?tnXT(?doF1%g& zac8Y|jhZ{gWFl*ood(t_bP#;@ARoH5Y8A5T_};Z~?OwDBJaP3$UJS$`f5SScFRWN) z8$4~;8_OW~g5d}si7ZTMG;6qs5n4?J`czlG!fL*H#Qmips2G9;N-DCTIWm3}BC|?$ z>;y^#-$;T{>FNyz7$TS3G&3r$LB>O-3!iU%Bi0NHI`j707vocVw`B9WO%I3$KRtJS z(YEvDg7>0RYlTcBbQDaZjScuzLOyiUII6wl;M@ucVP8*%%zQiY{Ma`Thx`>Qhhhcd z6RAlA2d+Omf4)Kq)3T(2Z+;zwb zSa@K=)o=h}Q}th4#8?3L=k@N$pDvUYY^s@}d9zNMRFT}NXOaP3d+86OS>)Ov=B;s) zX8`k2XfExO%cTF+w-)Y_{};$JpcjdHf0 zQ4X0}bbwq5>+jBj+6ab7jsbFO3yV;pBM1f(@YPpmal-XL$VLAxPB_6c!q)SQXs+5) zkWT=#tPH4KF&Y`bzp$(f;4jsiP>T8sY8fyDVp$oWpn@=!6jdA4*RAOR$wlD)t{`h% zQ4rZbM()^U89FG$fb5imR;m4H6pIPuDGuKz_EUj({bQ zA|63V&rxYv4M9T*aYPLT{ncfL3=L6K8eAmE-fB&C94)naf|OSb$k!1HvI8C3pxz@WStr0+$kf7OmYRAV7LrBmtvU@j z$e~wFjSTEr#E`Ji5sJM~8`p)%kzNa#@gzF%(bCX`nO5ZRGPK47uxFMzfso(}TGFF% zRU%Aw8-VxyaS0G|tDe8479k`W3^AFXk7Aj?yFL=Job?C9>~&UJASi^UEuLeQne5p+ut3AnJf>^taA8;D$RVsrjk?wsWp zR@FD(?s16C{h$aa9{s~#ey`qZIkmnv@wJq2?z@k9$o4pE1aX&OhGe0n}t%RoRIp?|Q`FoAq?8ghT#@ zMHQgZiF1HkMaZS3uG(OrI&MRAAqe_Qcq=dFi$uhG9*Fcx1fbA~6@9pJJ`y7Im5V@~ zA#~`2k^5b&8A$jFgh=qaS&e6kL9i-Pfrj~5OG0H55D!p-TP;3tFkcw!kEUIL+hK-6 zF0;e=G1{0YOFu+PbN5Rgfdu_PQWi#mvI4t|&P6>m$b%+BDeTk}fZo(oI5zDii;{VEzFyvaJ$rcv&A|^1KM>PYfE#V(fb&d{FNWlfArohn z1p2uJ!z%4yvnM+_PX`5xRDNL5SUF_+~fmUQ%4xTJf%i~X#-^ki9P)U6|$|as4fi;2<#8dqj;={-o_!n zOz%`!9F9kCky!vfePl00>o~Cz)PGU7GN+Asp_-~uj0BtG^&#R!sY@R&4SoE@M#0KG zNjYF-#~IyORz$7WD2e^idcf+tey`V6@XVK;P54lcl2~%8C>^my(V&fz(r&%thqjwk z>czl8nPHtqUf4`YsW~%Ws5WktBrdGYnOgE}z1dmZLBktueB((;BKhE^8_dErd!wW= z^H)$ixLU-b-kelHrCjbuN*c+^H64wGX$eP3;go)?x`7+E$9+kx!u>~-LM@W!P*|Ae zZIl!~{&uvjV<&N7Ks8UriO`vED96woQ7lx8H%b!g-Ar%LOjvjL%%4MUEtoO%2PKK- zY(hoU2#%82-9GzA21yoQuDeL6TA#Ll5+$+ZTo5{${PT8kl=NLWbVEMX`J_-a?qOD? zQK?NR=_5y!>F6tLQ#nd1mkzeRy?2FIbD8tcwN0>b4lF}s-jpKA6(!D$_{Ac3iNK!M-k~XO-X6P3RSOl z+WLWx}A&Mkk0XR1k=#jcTvlSb=uE9`6axe$I2eL^C;;gM-u4i7Q6+-|0+AvN>C+NWd3}_^v{civ#HT3VL6H9;BdYkkAF@I)PTSy3H4*a?s%# z>G^4pzOI5H5)Bn5LfP7K$}v{D2LFT-M+B>D=8O!ozp|h9$WLh#x%Eq z&X0dtU!tVaoGsMF+1=d%G_`dSf-aw+v8up9C9OI_4CK=87aw&AJ%j2&&*Mkw~mnQlQxmHrXuBd{ z=SaQB_q!Z3Z1~PMZMUuO$xZ&}(|bx<&C%zIs3{!fz}61!-Xqzk*RSY0m8=&n8Vykr zYmO#TB(38pNuAzt&i>me)rF3aRpmEMTGgGBRCCVGB5W{6N${~!S8Os$ue^}H+-Y-~ z{qhQw1e-IqMbd_jl2rFwF+Z;yJ?P!+-S)-h7ffD5NoqbRyh^wHi@sSMCEaOhBa*gG zZR*;t*2EiEFGj7Rq}!aWwQw!%C~3T0BOdx%BeDG8&Z(KlCB4!qX*5S}i?Hz>CBbP= zHVzx{Iz6-3kukS>9hm-#lHh+yK1(`b@NnXbg|L&e*oo`T_izA;AKz6BPJGa^4hE;c zt}Z2vR475UbP=e>Mz5djD1Z7@i$4C#``mtAu<03ZI3=0pX#GXe#gB48``*8rws6wV z1H6|P6!m{S5K>ZVj+>+~z5XaE945ZOtr<3K6T3;lQ4u$K7$t?~C{hkWzLTRP*abu` z?m{r(?l5qLdvHZgZhS`v4}q?Vg5I5okb@wioK_>P*0SxPUpzt5z%i8?oo*LJZ9SQD zvciZW>fq`DyNX=7P9hgB2swIqxVj6tPHrxa&Q3a703HW`MIh)Vgr!LA0JWUB)M~)h zfh!OH>QO8FLmq#KN8I=NltY?r#+F(HO%^HV9^xcCiEQPUWs|omyJ>P2YM043GnTu+ z$pvVn&K`~;vAdHiU+f4v(K~v;?#`~RjmRTZn1CAUgR|f&t#aRUM48*SPLJuIWB4@71L7+=6sH7=V(T%3_ z>Sb-Ktxdj=njbdqSM$Z+DMzz|IW}@p$GG%DT;^<#e=nNFAqTU}Ij8?p+=@dETbVO& zMIE8ykONd^DY3xY;{=O^j)-k5bafSp!MP@c9o)qZ&RjQhq}xW-=dCcamYa}bGDto7r)|=!&m0GSBo@K#UTf( z%+X)|LQIN74oR8gm-t)JCk{FIWX>j7UO}4g#@<*uhoo;lcNC0be+PSR={# zg(eDstOh4LN+%+R9QOQ=kpD&mw4n9H6RXjs^WTX4HzNP-BZb{ri$(4ThnzZMj@RVx zWr=XeNg~CREOT5Ie=ALeL(Wn$#~}Z^2`L6mi-Ihn)3cj=laD5!`$W}G;*Vls2Y z>CvV)wCqH*E)A256O{IcPhaOQlMoVd65tgEB=!N*}OdbsE_g*T3qAfz!DfA8dnWO zR));v1MOTxu7?h)7$D^|^r@#vP-AiW`DHu4NnWU2_a(Ys_F!cVjMQA45;HJ{u;C`< z`57Y}XauGNk8N5G4b_(n=q63~0q z+@d6Z7r&8?35JV*B;qsDlP?oVVMS$DHpMs)y9S`05{S$rltE7kwNk?Pk;B$Iawzj-8K+Z^O#QN6E5q?qLOr;C>h5WH zv+k#6o}0Qtf+`sz&GD|J)J`x>hH?n?5BIe@ks@EYHqaszFUJ{qMLf}`20BxtDd3;EC;&9##D<;Af| zJx^V5xZTb5^J-Xg$ltKCz@i}a?$Id|)|(&2_gBE4SV1kLeKU#{-EzK6CRd?1`Ed(4kfv)8*S9P&4;Lq?>*7unT<{BT*c9YGNSKj@?BSpzk`g1%=vMxh5L+dIJqD!%)MxR5qhKl8;cSLX zuBOi#N3_p_{xHLk=uD zonQ0cu~XTPhrBv>IK3Q){1qz$yq)g&MK@ecDN)*;w#ZObjYqav$I7h3CWw|2RzyjF z=fkcm0)y_KG*r$;G27u*4m;7^&czPgb>TX3T|8VI5`>CKnJ~m3RN_oVDm!$;8YO#U zJ^rlX#ZrE-lD*hJ(9hF5D2O+}+q0ivAkQnX>pw_A%b?_7SO$Y8d$7n0bXb%i9f&KG zVo$@1l(XZIt`O`vDe~`BtmZd64ry?}jz=2|OvO4MBGOpXuuY$YpXZu6f#ydj;Yg7j zt6r*96PpTF8hWrGQVh-?B`AFvD3`0i*&Yh?RPb#D)?D>7N<{QQu~Xn8IAy|^dud8s zYN${npc#7&MVhzSY2I&#x`!&W?iB9rP1W>hR0LxJu}(vRngaq+n)zgauvK(~AqE}; zG*QeTC^0SpO9jTo4w@OMgmI7KK-OZc$W#zk3JLFl2g=@xtdfzNW~Aj+c9{Z}A-a(e zG_Y3nP_HF0r9fC&oAk#6Z3#$xPTi0&P5)WVR1%B)vgjTJ@71bpYxFUyi#w~8QRQpv zx1^(-?yhX1E_VWIfVwUThoCs*f9FZI!e4(c&^MGo`{fDbDo{^|rwoB%6;BBy0S4XV zvHG*+M%B1*$Jcu4w3hj^Kdf;W0J zXuT0$a7c5)X+fu$&KuKu;A^~^1tv=$J<^(U@6Ugn0nNJN+p03?CyR1qE}~+^s){d>Qn1>4Y?)!7 zdVGtWQ{&8H-_TY=jI&CKs2H*8XlPb{Ph74LB{iP^`c(F|(B9h|jIn9}QL$o`ax&N) zdD1ZF9NDk^P0QEse}DWUXXC6=A|m%}`um$qxD(xZbyYa7_cqQMtG?yJBA5Iu=mn*s z>yi$L++v6+7Bsu1Thx*?VaB%Q$4acdoja`KO=vX@4>*)LIfF%WMu8y>mm|edd1BxS z%cHG#G=PBr6`WFr04#q_ktvCh;2OgEv^~M1*=v&n zU-frw6w!SIeoh&9-ttNgAOtZ0aZL>!a-LWLR5vLs##xxeA6t6*xe5L&p|3A~_{2@e zl^mmx7cGA18YD>}2@b)zX|!i>WvlfukKN$>yn)Xy6{8&@_M4+|jp5+hdzT-hS;P2;_`V z?_I_q$=!JW`U!3u<;aDg>4@MXKVG)Kk z%2R@{8HFY%Nm*o5LX>Rc@r@|un1-l1iP@YNR@1NCUp{RAk><@^f7bRd4Q-f{ z*Avy^Lu8AjC9yfG&>4_$QUSedQBMq~@k`;aH%l_=2-}}|< zpPT(;WX~1Q218RshGl4e3}_o_H}dLlm)C|0*L1d(uk3&7(ETOE`Jn}6XnqXPq}k~* z7w(07eQ47oVjOhg+ELG@#QC9zwYaW=RN%#R734>Y4=D0dwYmXX8t_680~YrjC?jAY z<}-Ma@YB2c1lEF$TbiwS-YNV5HlU`!GR}}PL>{frQ0FRJHXk{c5FOQeooK<(?CR7E zQNfb0NBs4J107|sB?(kA9xR2UkkB{!ixT9_A%1YBiid1J*i5zYs@&~WeDJaur-?%>MA{Xh!1M!H?(JERZyug_*g= z;Fx11L=wTHWW>=;)_KFfBO0tL`#A7ji0v8@BL?6Y6E=;U2@O!j=4=V`e75fD(4cml zc&_8hK`FYzW)#6Qrq&TiJU}uPM8JV9;0Z(cvS8p@m5hRULb+7R2kAKayZVx?a`r|yVbJIz}Yz#s1V2w(xU~{sk@9y0-b?}|i?oF-X z>1WH(uttS|F}*}*S&{ZsW4*-oF!9@cUMA(A??BT zM>rW$XJ~1qK8D$xOy7tKe;=K2F^8zm`~kun#boNKPj=Pv{QFI<+#210 zK0EgfJhmL#Ml;h?D2fYvREIO0<8i0S*#W{y?P9l8zTEp8s}wDJR48s2li4F}t;qI? zorSYh(QHAz!xs(?tdc|gPMQfcfQ7-W*0A&IE`M|D+>}0TZK^6?mY5rW$33;@ zh9O9XnV}LQHYa^^v=0~Fc#%JES88DJpm_4RfiOb_`H(sBLr4Nmt7J;CT!A%w#xra* zhM?9_IfK)GQEs1tR$~+P-%HML;Y0g$h0t_d_lqIJ_(7p%cde-E^pUBb6N09dwaEBZ!t+(aOc0TQE-hoQbH^?As>(Eq7q+^>$$2HxBA{P6@= zDAgzsx$wnbjVsWiH0Jb{3VfsAIt;Za!`wkI6W1r zKMH^9_2gb-pMoZXa+(~1Hk$!%QMajD zi#+Hc7X!I%MLA_7ra!G->1@_T)$6d*jw4k^piQPjpSAp{19m?FCW_$7Y=rKzVkJ3b z96HfxU~5*b**2B^S3s-CtdLl&?SsV;&_aMqn+PrKK5W zU83~Qq;**VwqNR%`T2FmwZ(om5A2{c6G1I{g^EBENG2z5P}s~w9oam!Ag)@4buD`P z^cwf}JG9z36uDHB1$1Mu@X=@jc?q*QEj-6h+f{N|ddFJZ7yam&Jri1?%K#aILE`o0 zXm@NGg{+iN1f4ms$V~BXGgo-8^b$Pv$>}X2o z$peVHk|8LD7B)f-d5>Xp)-FAhRk?i7v<36}M)tmxREfB-sUR36p1jAfIZyHveM7_@ zzV<($JU-wow-K3mGK59%rRs_^S^T}$O#e~k;r*o(Lf2e|SIvF}rO-Wpl@SdVC`w^G z5iI6|vYNP39-#nLK95trWR*tE1hv;+%i*IK<6k=0*RS z?`v21N!YCnLNRmr;pE6v1Z@!8aqo6$u`OL5wpj4swROE;qGN=^&kztZ9u|}u;(Afr z8$7v88jCR_3=64}xMuRW@o^y+Ry}Ikh2UW^4$h3lVQfEWS|it^VCjqHDQ!;(CQlu; zj9_ulgEC{}>e58D3j_^XZnG+@cclQhVb_e^pGFXjTw}n@%n;bH1v)1^$!cFXx?=d1 zy!cW(M;+T(>zv@}mgmq*b+@eV! zniB+>By_mR9Fb;A&sVw4OcV^WN4Dlk?CJR{DcGY$!HlJ8WQqMspD-ln!s54iHL?a@ z-!(p)U}@4qS~O!qD@PJ3;srykW!!QG$`B|H1d3)-I%7{fKHP}k{^5yIOI9oq)H>4# z+V`ipEL!A7LnO6!)GvHs#omd}yr8kCn`g9CU4WL;0x)Atgn$sHo=$XNcddBGwj&o8 zoFDr&?fsWA1Y?5Yd1j0WqI97@qk~J@4UR+y$b;it?0O!WJG<(K{UHQn!UXt7j95w9 zrc%I1fP0psC8`im4MQXmB1tRQ%F_C81`F)AJ+`Yb;{eCLU86VBcqmgNXyzh&TwGa} z@&&Mz5O7}#ceY##P71b$_M5}AF1B06foY;Eg(Sr`3$HY?+L(04c4qn7 zxvEZVXon$Q4I*JC#7K}nG(bXDO)#V7SjE0I`;NNiR%h$a>vK9~zafMeO+moSfla0i z-A=Siazd5L5ozliH$Ob#NyTd?zBVQt*tC$$7%gOyh+>4zQRyp<_v}xP%Rd%5b=Ixd zHD(ix7GuE77%gO~$o{fnuEzr|4mngNKXhB}!ZX<%g3&?`%J>ecKx=R!@kaVn;my!R zUHnFLZuGWyQnvM^0Y9mCNYk)c^cEu3=4Oyg-JP7x@k^0}6aU139BLw-Wf$n9Hq3|u?{+G#!(i(Y`%kQX73 zh>Qq_Wsy9Jj5Igdy5_ucwbGjodggGet+hS0))Y8q4gw<{x%+Mh_PA`c%U&X!Q*~rP zb{oP$KnuyttSI;*i5xfC@c(Jgw2JTj7vIV{^O={vuz%*bQdxvqp@Czb5q$k<8L5Br zO77zxKjl_0c`d)NKHW6H2np^kBU&PsXol2KMNDXgTuSGOYtMZ*&4=rI-Sx_(;gd>D zEDi0}tQ#}%Fp~?ZL|RgUs`ALeM%?i*{UfSvVsys}|MpQeKQQ)NGjS*(7m^N;nJodW zkFVhIg(^uDj9eQLh7lvxeU5K`_U_7!>?iUYVTovYF}?Pbr_`e_nL;{3^Ut0CPAu@$Z$|tM4O9$^4^! zyOKD6XG*8v!{I{&`KN_sMubq3^i{6qv0EJr7Hy1{RbR5LTAMv8f(TJUFmv$fkwTt} zy*(YvKid4FscPEHC!c#x9!xm+jKDIuCdl5Zt}C8Bt=!O8wCv5o)pmnIUC3)f_jv}_ zgq9HUJj8e3UnjFXG^WRi$fK?U9NUuDgds>~d@v|AYD1X*@=vK+`=5Pp^((NLBBek*1A&qH{q|7Bcz{tRXsQSCE|Xe#6Ayzb+CIb&P{E6PX~=1zK^Usjo!+ zXMoj3>Da8g_t&iHARQ`pE<=b+(1S9Q9;&4YbHx)T=OruZ*~b0ryU$-;dhW@)|Gp-q zhZ=-p=3;@C9CC^`o73RJ%a%u2u1!ve#`j$LD9crOe4&0w)j?SD& zRSkSLH`Za2^*3S8l!ipDoF3Mqbqh7l7s4=uTb>a}1qJG(_F%idVJBL8WDVb+>e|l! z&KhXDxj2|fr=nm`e{q#MIeNv0J;K=drL&tIY+UgpA)U$ucxLW`QxHZLMu$HC+9_nJ zhdsJ`J)XX^^ijfHaHG)7qyrGh(zqV5HHPo|`g0fUI;&)jg%j8GXqesP(U*ti2`tJK8k7H?5kXux#E%MC(awDo*4pr7c|$>odu zmT1%}F(i?T=Y`ahZ5rNozI8b->F76$sb-5F2NM|( z6l1PokSL2M4p!Q9?#3|Tz_>?u;SuTAH5m}5Az)Y#m5~ZDUkIzOl!~xD#J<*q>ro9n zBj6W#yGOB`SE3R`DoBO}QB9I&o=96`uVs@n9`*jx_L`_WH)d+f22_GbkAq=B)FX~4 zh#XGCE~k%9@8ag*Rsa2$k8P<0kp=-1`FeyUqNWVfaxpR7{dwr!lh#N3pB=EFMdh}6 z-kN+pS~w}dt0*Hf^xaZZ#1_$Oh>}R z1trs{1GWk%G^xaOk(Krm$p=U4X-B4f&cAkISb^q(lKIG(h?G%MiE2|k^?8Muo|v#& zb^kEu^Nx$9wwxbRz1D_v%`}lRGq5n>R4|b|-H9Dw^L_Qyk^8L1-ujqjm&<>kaVq=) zHYW0GX~@*|t6+26`!ozM8n}D?afj;L`yQFsMU!7^7M`aJ+73D!6DGpCjOxzso?%Yu z$*23g`)=nGm2L$+gAS042($1p;bx$m8H!7+Y|fysO{y0Rn=tNSXW7!0Gh3I?xEV}E z@u0ZOD~UbbDQ%vRHnPFGOBB_WZNLn_@qWEnX z>-zL6iti6k+*sQ^({_g@smMeOOx*b(kw(Zu$E5LD+##n^6UK?kmc3bX_NA$PHFrMf z0hv^62$3wkoDYntnZuv_%56IR%BCwugGa^=Tt|29Ce_UhU}R z`pF-ww>Y+Xcw)XL+rt!aCRZ1ME$Re`YBSda?R?wcuUbr{8~f~&s_CsRBN&*-ZKD`; zlsUw+h>2p=$q8*c++j~U5K%!g`q8=zn%p*HpiDa42qPUX7s2={)84f>mEU6_@8qE{ z>81Jo*Os5tS<8|wb~a%Y-_Tm)~22Qa!54h8dmjsz4=X}^O_uM zIxwcr8?+w-$_BOrV5-f$Gc6`gNDTUSnnS{}T6r}O>zp@KAWWV6G-XeRtgx>CU_k># zdh2DjpRcssqI2#Wgkwyckb3e!!Bm3GIOGngRwLX0a_E%Ji*Kq1iL(4RWoC`h6(<8= zOcbU@#T%hV9ri@GVN9S}aI5qBmM!QY>J|6k_}OcVG=-@R12J)bR6`AVwh`!OPp)?L zad=$RsDY*HhglCSp}9Y50D=iC6C*_~0htd5#hcBUleM^m+;6>qNXcm}jxKq8S7T+G z0?vdXMy5+&Q?au>ow2R_>A4T)ws5QYfK^Llh#3QA!fQjOi7aVe2*QpC&BYp$l@-OR(4gP*RMoVNJqFLHIlG3= z5;q3Ulp=!ArN6XGC*__E8#4EMUeKJwkrN|=brcaQ5T)6G^)ie$U%25C_tFF!-?!Q_=pny5SSM7 zBxU@9HOIpjiDI_yacS;3Qgers28t<#(C{_kQe_TadiyNyX^)N5{CLa5{s8fj)fJRRQq?|fZ8BHr%l^UF$8XVrSbE}{B`vy(8`a$E>Hx&gFnN&2i>2G9X zw(prR_rU%$k54`>sCZ^9OOr`u1{S8YFVY;6=C1LWPM%f$CF@qo5*A&wgOBTIUv!{M zT%n^FZT-30wGVoxau4u{U-Q1^_Ik=Lnk#fBKo^5`MpK=dJ^p@T@<&A!H+qEP)#K~U z4XrbSD46n9666S_jbtMa{t?gLu+sO`&~a7AC^}tRs^hDqg=NaUM<$AF2Iz65?jB2$ zL2NN+3_D{mcREoD>!SQe1&cMojUp+4J1=u8@#tP-sMDlEJLHxMkajhA-nN< zQG;5^JtpdSZK#2mGVe6h=xcq0LssnZT;Q|4&eCMtby;O*>zH>2;g}LE+FH_+dcAS+ z3;34D_ECOz8XmAxN3duhnR0aK)D|S|*&BXZ?SAUNmQ#f_qlvs`UYw4j!!RHd7f6vk zSBE0)5|Q42$~_Q#Ald6yaO}Q&mE@WWqy}M_@*AibKvSPYpvIqquR=;OYk67jkX-IX z?WcDtUoUlU&@um-I(`FV;7repP6bFd=fvgR%6{RlzMqD~E?O74v@+$q=)f?g+MtE| z)OL~nS#lxR&M$FAxQ*b%{BGSB_8X$3+R(x>WiFsZp^F{migfS?71R?Bk$>D<&2!(i z1YYOiI_3f$C{voXA)3^-EaqB>Uy!hO;LkO?%a!BC9RB@au#RSJ3JN9?xR5;xr41_; zZCG3DDR}yHx0_GO`|!(CO8SbzH3?iMVqj`>K$+8DQ@57a+L)5jc`TIo@@)HEaYrd6af%Z%7yom64FC?T}}$T$Do)Y-I+fq#eWL*(JGy;22>#jwmC4~FEbbQ(S;QPm(<4>kLSi3bof9wlxfSQfzljWCCloJ<%60p?+eztr8BU|uRqzREI zR>lvP2zh8bX5D_jL{9*ALb|PPyDcvB^Yxo08jZ}o5gUycF!}>rmcLPI0+G5m4>6YC zG+dTYv&y{3yPw%sTUu>nHh!b@kFZ%@KcFO&x;tpbkX2Q$&A+zk$M9{AM^?K9;QE2d z7%ZRNX@E3}{-G7m1{Tz8qo~<-;<&ms+O1lFXLp*4!15O3Z1n(}Gd!o$LPl_0HS6rEpW< z1X#<5KgmQH*2lBH8hNvpzr0O40gYlPp3J#n%>CnHAzYYN_l>a>1 zF=MV7%%K>HC3BAW%=O5;lziJSz52qqBe~t(@<*A@9EPEIGUtrVT>lMi+g|&%Q)1n5 zeb=-KZb!{v4#mKnVn(xKaNbsOvR}4OT=%%nJNL2eXK(63Qp}7YD3+|bV$*hENQ=); z0!mwr@y)VpbnESX(^*3i6ibnG$2SxE^w-U;P7Zjm=aOoB^79>Tri&zop;$8Kfo~?6 z{GL903(7U;cXwQo7s5VdI&&C?;>jGo;KKho*!y+2T{fq~K1Gkb7&pQU=1>g9lR13J z{k~MD?WOHoplUm&MFp*SP|^(Mitn29aL4wOp6hOoJ$~8hUZ<~lAIsNnInNB{Pz(%s z^l%pw%`VQ1;)ANhGL>2dn|rU)=k5M&JbPDK@a&8K(ot%Up1GKcH?#OID&!rq4(`yc zp5wL!t#_p)4EqCSQB1{}S+$BL^<24svRAb#yT?^>@TfXhVLr1MrsB;kzRULP)BqC7(&n>@A}ZD*tXA>T=LhmX=f+D)*vve8sm=Es^FHMV zn^}Cxo?P@cv~+&b%qvr`j2U#w>iZusTm09oT1A{Nv2o6Ur=xaN8*rv$#ijM<`~kD5 zs`$~8@lcV1AI%p?VF;S8{?Ve>hSe{%=SPV^Wn>Wy+=NPHv|NGL9IwFYnH%+NQHT9D zK9~H`O239y&_ggsyfQ={O(Oo{wlOEOa;}E7s59$T+h5!~Bt+ zDFv@8%Fm3J&(E6^Duhyv0$DWKmzElyTr9@ecpPPQ^mgX5=T6dT&9_@8yo1)61ZdH` zF)~H!rObn4@fsz`5Bz&~XgyWY?c&y%7Xq5EhgKPbv1kq^nHZ%EH2Xzv-H{hY{DnP_ zy-qa?y1lv4lp9ai%z)BN1hwd8NDWP3S@0DKusY znr@|>kq50Y0gRb#7O)|d!pL;!a4;sn=8;nCv*zFEc7zx6^HMXyHcJV?%$h(+L7E?` zi5Ep+D?8`@P1ojY?k%4a1Eu?Cxj!VV2?H>U2~ijvE0FU+*&Z?vPV0Ncabv3-srs%< zvd`z43v`9Z0N80urT`Fy8YEt!^*um}rZ5bfgud(=HjAHKN?e(qJZH6&tU0ut7Qmu+ zTMSYHt^o@r3a}(F9;QF_8t`h+nQGBvGY*SHY)^ni0fmyN3HGG zCzaltR_zk6!_b^4XoIP+%q@2xitK`V`bFk@eUst_>f;TR4IV1pDEr3&2q z5@HOTj(BuKx#eWSw3RtKPWZg7N3bsp0Wre@IQ0w|+4)yoYfKqB{l4%XFKE<{ais_> z7y@FH1wF%=&6&LU&Vx4xgEF#fd}`(VCh4|53wl7z>{4Jr1#*>29?nySz_5x3q&=7y z!k2+dBbYq7*I(YJ!-m-7wPPRgN^YttAnZ~`U{5ikPXVIz?Yz*#RqMc?%FW=e?cDFz z!Pb4D6wRupc;2EN7IX-aM?^-1!?H+%fya}BR#l**H#Qshsx&*9)AQWH@ZQ^dRSG!M z14=gso*DH7j4*a5O(H|O1dAj>zDlmZ__-Ui;zr^C{uJ*fQOiEc%1tMzCx*c+dUuOB zzSvDNc_i3;MLa15JKILA{&M|$-SfFu#9i+19?%xrYz8342d?z3&)R=^OFfp@+5T1r5q!);Jh2FP9V+>+^TC{@cEseorE?0UvVxAW&9y3i{2J9g+>K(AyjWZcaILZy{c;C^UA1qudl95@PqdKDK3lNNTDPW zJ)*I>70IJPqXOLjr(TUSqieT|tXuma#!C>XouNI7}`w{QxsEr4d}eV^vwl+bG?zoYw5i~qURflhKKv7Z06k7ci;010|7@kUGhzu zX@mHlGviJ$I6Jz8lIHvJ`=m!BgqIg){o>dswVU=1I%I;7(_k!aVyl86!TKOT+T2tVdNmxTiRhN-SJeOkB ziP|G-KW{KH>EoW0E$TIH_PeL7$MN&f zGQCL<^3{(s6UI}IBDy)D?UpgpLz^sFxjG;}x6G6&%8X-C0zw#%8iXO|E3&B|qmHP{ zh(VyU$==Oe-K}%x&QAxUZ;KW_e#Rv_UugiDiQelBE5eFq%g47Rr=TZ_wS&qwNEma~ z>A}6%gy=mz=m|#G1EC#CY3>)ViPfb!`v!&IYPexzIJ8u6IcT0{b|<1xQLM(OYVl(S zyPu9(xn_f6R5Zm-qz7fux@Nj#NvNic6LNcMc z|7!0}Y4?V`1T`7V!@x{}C%Q4I>*R(+h6^yk8(;G1v#Z%1%XVB?89J0VqctJHlM;eK zF(VSMd$=f*SMC4o`fShkpGW3(bUwClq>bUApxi`bczO zcWm{qbEY04i;|hr57s4I7mN#cj*?k;w$&V0P>D!97k~xMV(o*9c?$W z%pSjw-8#L#K5p|nUs_QlKo%EK#7WX!Upp?W-Bt7D@@Az!h|gc1u&^7gC{kc3E~2O= zjUL>&|NGxzywp-XryQL!gjN(OaWE8jMighAbwXmS-?Y)&?T4uc&0SZ=EiN;rVMtdXFZ~ns;z#4J-m|tGzBVxB_*dE)qr_4C7{mn&JC zwL1{sjd=*t*TlY*f{wRoey?+TD6H{N}nsuuFhpBs}$xB^T9e{TK2_B}Ff|Kr2aAHKQ2LtYeECtYEKqAL-PVk1W zm;lMo_v!cP?8A%>hlca>Dun=vd1Ddw06mqE!OV!#5{jU%2 z^6coz*ETFnsz%1Igg|I5M z^q_4lBKQgz)Z8WS!B*80uQyw_{F=T0>Chc@xu2kIW}>iY>0Mpgkj=}uFHO2ACuidW z$GKIPojY*$QhFI^r}!4)c`~ zSuhW%MCW$u+{U$P*x$(6<@Z2d7{I1rxxSAVwSTSr#tr@x4g#0VP>+ei_W4) zm+|RAuBhGvG9_;?gxw&lDtr79xKh|9erJDn9QCFLB!oY<`teoA#RJVr(R*V^NE6R= zN%xp|CgYv^qV1iw`^bjo0%wA$uohMNX^2uvK_wS8JEe!mFAkYHcZ#&+tp@crKB@(+ zHx1IFmqqnSBJPwvqbGW&uBs@tKivC>wbvCMltTAB!(xRIjtZ8}JRFU99d;;w>bi^? z6Xv&D=6{$!$zA?r4W)=&fX3im=~!>e8hc8@`txiW>)P5w7oiwO&Dg&+AaCQ6P(k zNolD8wysbbDZ<^Ro1^!^t!j_B$ASBw4z($@6541oF!QqlfV}d0-Qg1<|YDNYzn2B2+H7$Q0~7s8b+oaeg5O)%gIl?o*yhV zkvt<5Kn$KFBx-meFkb}Y9`u}SCC{&-WBa8&tv}D$J$NMfBryzY(SlXFazZ9b34^$) zw*FT0^U%6|9&tv3ylK|KsPBfxPV0o?YWni%1z%z4F&_6=;Xc>mJ;kf~+&A0_Ky1^^j6 zYX}qpe}Dq81rl7aiE**3SigVy#y#>Hl^9Y^7=*oNynT! zA+aFvuD4#0fzX3w#$meT@Q^gb9RCFo>e3;f!m%+Sy-m!t{b`t=x=G-e^Rf*yi#;)&vOjx*!>j`Yes zc+%BnQ}G$JVfaW(w~O$lhxus)SYV55p2 z7ued?(NMZt$NY2aAcj!Nx&w7$u`_b{4c26F(&}zMOaEzScdIS;d!Cf0K)-C68 z@cKgAl)&p>`_ASz1y3*u+vZmFKPC1%wdPKj%T+V7W3&gKF<6V< zlhK!RU53IVrJzMjh+HDX<5s;3D%5T$PCU6LveZ61?pb?io0%vW+1Ct>IdXdgT-+k? z_pD3C%&Ak7UMIh~xTBp-V1{;IGZhCTh8Rj5y_4ciSjhH(sskP@x^t;-ueI;rYYj1@ zz>ICxnsy8#wPjpw>(OV==a0YVeWbzYO0!#a)!nMe&oj1F6A1y`PkGTWjNi{s8})cy zT)V!~KBp=#%uCHapu1HYf@4InLF9r+kW!Zu|HI<`jW2(wZ&#gj>!a8ERIOq|3uw{n zjKs}J!%B!;AsGd(Y4Y)cg(;C0h850n6m2@kewl5)0|#GL3F@GxM(|D*0I zz@lopzt^=3RP4kKdP!R_5L;2~b(3A#a)T7>H8H?Iu@ylP8~a5p3=Aw(Y{9}-6cxny z-`(4HgI!<$JABXcJ>Sb-&zyVCZ_dn|Ip@sWn)ZbS*+U|FQ;kPY6ChDv4UjZhsP$U) zj@&&z^zoaPHgARx&-4EgO+Dz4ejb zYpM%ks2#8c4-G_6lAqllkK?5_K38G=q_O>fulst7y5Q-y05+UaQOH^6ZKrO<@fk;B z>hWvDv@gp4P94rV4S-Fis3ZclSghnK_#}7>z_);ZlAga>7 zwSB7gb6mM1yWIX`C)J0>>m5G^+XJc5(zsIC=e4m5D1J?R7yN5!;>dc1USq?OtG6X; zv~;O0`V9o~Y=jC;WTPFQXWMs}8t^HnZ_UMre&5~;tusRY&GN@@?8Wd+7!b4wkxKi^ zq8|<WJ|H1q~>1%SW$?J zI|MC6(T9HkNUFkzaorI}sX;{qQBi%jDmUYHTpCsJ^aplltEN~|)mSTw9taI#i`9H3 zd>|D0B@n=rIACb5X2$DvQ~k~>WB~>x~DG4?NQ=#7|+E4qmu#wjO14EfVdSr+^xVaaI*DGe;1MBeObAy;Kw9~ zv}gh_8Yu|C_+nxXN~Bg*FKJ~&`>(qaG`Exy!V z(cc?_mY}XR^4p@7bd)#a;A!PT{IVIJPR?9pqx@OiV|u@3g}(QoO{FveVtJ&+fDdFb z;NvqqA6*Qt*SOPZVvnZ|tDi^5cD9QAPFNm|6o}<1?G>X&k}OaA8;Ip;-;7(H_LqUJ zJ#KjhngFpp_)bY|XTVnhne$XQcxVmN;@Gt#%iS&cGCg3(x`6@p?h%$pBLxDOngo~{ z2w-X)F!a)@-F{;$jcoaH@VvR6y;p_QOd|lJk%9nBK=RuJK>RiV?zah0zipa&ytxgW7i4%&C-$Cn zQXqhlQZND_DHs8sR}r8on1P8_t@3;Bs#g2w_@!%iByk7}qmhDGJp~GTg->r{^+bMy zSUr(9+;20~1cc=Ul6DM%Kz0m)_>LhEJ(u@- zW{ZnMt*Uk`&t+eK^Ds|@TOOSh2wyeqi@) zL;yx3Jq@6IK*)5_R9neq3KddvwF=$7(Eh=qb%^>!z(z4mGGsVIlV+WHz98fAKgr@T z9^FoThEmOD0tS9}4g8vVN;>?Me*gnNMFawV%3}on_EGG&IUcXv?tMMH&vD)CSQ7jc zY9ma5!0+m50DkH}0D+$>0*)N@F#>=8EwT&M&sF$QYtzGj@+6~52>7YgMwkGB-_6ay z%XqM&SQ^wb%1~ed6nMY*AE!DRCH1z)z(%!UV)(DI{$Kgg`a|LVP12 zL^lFQ2A#TfeaVauYol5yJNVBy5x zTo?{wZ!QeSXDRgB(+S`AI{jWT)_wB#JCOm>fT09nG*S?NiAa?PA|RCqBD|ac`)sDy z+3|wF9vACITy)Mm*tcJE956a55Wq;O01=Q>fC!K8i_lcS$FE7*JsX~nkaw-`_My9SPG_V&(ymKIAC;A5P$`f01E~JSTGJ)FbdeK?`b_9IxJLYooqdLNH3do956a5 z5Ws?oAsHMDVn_xDV?#0+y>jit=z{&tW=>oF&TVsp-?`T&5P;E0fdEE2rV=K3Is6H z)+iXr)+iX??*yY;quk#uS&L2{``Sd^>WH-X%Xk7X8mUDu6F?*1=w$+=UlzTIf%IO? z&WLLR_Sglv4T!3jk>>ewd%uNq@}YG`$U&U(5wjJ6eESer;*1aW1jHF1?A-*Ah;&H! zvCo}^UbSbPz8jg)_GYz|;ji&CKE|4XIO8McDO6%O&*4Fw@xdQ~IOBuA9LE(C5CQgE zLTgE;E%R+?((9Tnhu!{!pYbu?5X9^#CM_poAj^puUn9ima$@`T=!DpMQM=-wbwAyu z&%IE5cBGR60gSY*7X#VWi}Ag>7~R(QXm~&P@|qO+^HbG+$3FYkg8+<13Iwna!eJ4I zfN)sEA^12AK?dkSyFC*;h3zN$*uP7wwPL?L0T_)G1Yi=BtSM@5_~5mK{s9Q+pmng+v|E}vj?%i&Q%oT6M)f3fdEEI;7Nca@FaLv zPJ$-zPIhO7N9G7GcXvN^v8BgHVh=$l1p*i;TOa|FEs)?T0128c7~)j-{id`5VFiyK z)jpRI=TBG|jT8uAq+O~6$SzfaZ#^aGE>&`e-EUMEKlNfxbINjW|w<>-+7wTII_a(@1ZE?K=3 z8CS(b3WiP!;+TqDWv}oaK^#*-euFrsg1i}95|CfWf-pP&bY@-A8_7OicjvD?ZV<;* z3^f4-6Kki+~z0XfW{4CF9>1W1Q%b3XNrR#ymW8ocjwx7sW5^FA6N^)&%8gcYPH zt^!CDSAj=y6=)RqN&dMfO`m6{ZTW*E8 zQ8yegIw=sqNKsrRkSMMakK!uPC~hnJ7GWnwd_10he|O8Q>Tg^Lz-XjE03*2}N+52C z5_dzCs2igC?zentg%R7^Zr{VPc~|8s0T_)G#Qsz%VT<9cC@Iy9Jpr*l#omprq1bO^ z6)oz#wq)~y6})9${SVw2oU|I>pJHVCngOxGDMVOFIR!*mNjU|_VhRG@w6@C%x4jF0 zUbT5>;=DCop zF^5+^&tAQw((JGD)FLUAVsc{;cBvu-np8jnO)5Olq(TEt6Du6*ku$}oXJW+&58jw8 z;=BT#6bN9X41@|u2113W6|hf*W&Lw++=WFOyT{nxjXQa#hc`Zu>7+ma6B5pdN(jOk zQ3bIVq%qbT|(!6 ze$?VfpDUAVh-?VJXrw>@BYAHsAl{n_cga+!_jbDC6xaJ zH9krJMkBT8H@i^pFvP_f{$>~P<1B#dkYE|Gg%bV~ac6tATVvhp<@+;_Yd^}kUQ*Nx zT0_W4BL)K-lMEXZ3~WpS2_^#DVlc450XM?hT*1KR zO2Fod28lv?Htta|;mu>l+t)j0@eYz;qZ5OH4X&dhVDkh6ncaL zBM(w0m_f=U#vKzKq-Shbd)#}_L9zUa)7(2Ly(J{r=)@pgj}TIlF9b-EF9c8Wg`i2k z@&Q5eV!Q5bKBUxaI`phP4|hH2q#!OL3q@{0)V+p}_75N~BBP0b&3v@S$Sk;IXS;z1 z)Lp}3Z02|URXwE~ei0ds+6WUc@M|v#)V+iOTO1pDF^59Q82*|G!H)tilDqYK^+?IV;|F|1|=BDzy7}( z0_i&t6p+3H$w2xJM1ZvEf7q#c!}v(n^1_S;ov**90I9DDC?Nd+z+Ocnv-#MadLKIx^vt-1@1f-FHaYDSFR`1mC5(u3%DE)Cl^PRf-O}F zWC{tN=g5}JxiX2I4cEQ$l`^%0%U9YvJ9s!aIl{jkc?xzYn-K51{p!xccbLx$WXFs(=IvA!r`* zhdKAJ{BiG z;|M${U=f3r7@};c2)>?dj^;ln%|Pg{yjMH81Z*Ckh23^~)2YVib@Lc~Uoc}w#t$z{ zhT=4W(dkZs6BITv#OTu|ICra%czSDS?8mzIdgfe#R#GKJ3C+2Q=I>z|sE~!SP+(aC zg-pWY$W$sBdiPtdJwrKaLCkq8Ti>HaexVJZt+?pM8k#eJ{+=pwnOrSr@uez0nx`8e z;FR+Z8QZdvt-bg29gP0aYFv66tvR(3e_h}(?0VI^w+8M=88=9r`!oDvOqBm)D4s4a zN_rEBRV#%Gku(@F7T9KWttIH{%<0W@aWfj#NS zY-o+H)F|-rjKSYg`O` zN<7;$W6u=Fb8i=_N4K9B8L*9H*L321iyH?=C1r7id~PsD7RFM^kiYpn*uukLH$}=< zuq1r=!aN>JV;pRiNQT~3v*g?UrM=EuZH^H!HEIg6Yp#J^S1w84y5z)aDpyPTqHkIM)GNif|0u~&-5E>ZN z8`(Z>Ugn3_k4pKt;o)=pQ_zW0bT5VDlQN{d0n=nyFKJt{IXly4!4Ur%0bjlpFN6-4 zqO<`{kANtvVDm&W&BQGe2v`!8Ld@dHR4jO718*ZVdXT2<_WvAYH_EN#`MqnW1v4gB zii7s!iki&jaT!q(_TmFs$jnO9vd*GixwpPLm#_ZsfD3^QlG)G!BU&0_^Q`QtsU5a7 zU8hukKd6u6qFFxU+P28-E&2yKYMQRPyv#|E{hd94##127PFjlXzCC=tYn>0{>^%xE zjG5o{@kuCEkEX_%fF7TybcRfhVQtfDalrSWhbb3scMx?O-Vo9|K1<>96tLmyil=L9 z3~RgQfz!A3_L!5O-}GTXO{E`n#Bgtt@X}>fV9D4aS0>inL^N0X-xrnyTKh(ASdhc! z25TmFDUZcv!>cb#2*-k1O1>D0@x#+SUm;?{ivU}JR>pU-PVg)IapU6Fy3e|W?Ruw-? z#lm_QQL)43b@{cIcH7a`_2+}+6{+4(GD$^aO>@AgqqS5xkH$ys7t@Ahs|S|nue9!< zZjl{y;FR~?#EZ~QLZwoh-zj5ik*u-i=0!d``v?Y}u#wDkZEl|r?J_|xynP-R#pDXu zdsKuYrpFU0HJMG8Oezk??U2-SH};Gxys%+mg$7Nmlr3JZJPI8mG&F;eMK=s)Nr?9b z!+KBKD<6Jx+d zS2;%xw1cdN@z#LWE<;L@jBL)~iAQEZD-|W5^7bApzp4g#?JBkTWiWlE(m0QJ$W}AK zBbFvq_`H!+*}Vel!3zOg^TS2=bM0;I*zMBWB+WRxx5b$)PEVmtG*h8B zxn}vf1rtGIC;GfaImfrizS*H=Esj>G`a3)I8I*+RV7#40i%X0NM4I(;v$CaAl27tQ ztG!kn*p%A=+G+oonMX;py+~(N(7KKe?SD z;5Ltw<()LxB6LO66Ek@hlT;z~$EXhLY}_2*hCVxiI%%dgx4c7*%cUK*aI7y-sGWQ8 zITcyV*kR>IMDB1~{<7a8b?mTya@3(VskP--2V5-uo+QKiNtK-NjNgw2@BiH_uIB5|We?QFFx(^yF!pq>baB>YS=K>tv~8UOkE#V!bv4O4Qc_H0QR^ zlGz;W$OGxHhD8H%*!%G{n&b*$K@((p4^w=)^7VZ|rYPiFomIPw;-T%Pwza5T=m>=r zhfsAnGQc2DV?QYG{ipkbe2Tx|4s;u;#75tttt--D%l) zJ^f;!twj?`Isl{V4w7+K3fXcr>f`**h8N>dJbT2T#FA)s%V|)uiA}+p8B#<*HM5<~ zn=K1UX$VaTTGDsl<4(SM%uKf#STm!_Lo&0r50{LoG!jqvdU_(X%bfNW^~EWIiMTAZ$7l*gRT}=(ioaR7;P{*0`EFew zK}n{xyKhNx zHIu~^km_;8aBhg!ORd5_dv&Viv-9QltD~iBx+|b9bd7XdS#&o`7bj2#*Q{t$Tx_|B zrp%qRD&5!j_Isk5*I{DJh3_??9j3PiH{-!0NWzz@;eri0oFLcKVX`GGwpcDiZzXCmrTf3V0}i6tX0`*H4eJ%@t-wvv`s5j&b9M`-&w|EU16+XhiABoPy>l2gv8Ydf zs~M~0uiYy5T1;PnjW)OFDIUsL7mJjn`d(6}X|E*_X%6JEX#Mxm`%|0Hn793`8n)_u zBjChy=)`~H_y*VlV6yV0ex7sn%ewtlQn@py2T77T&0|0(p+8d}=Ls$@K-Hht%}yED zhBLZcT*r)hn%ljw+Gko^z(`wg%bp&gaF`j^=Va4b$i`19DHZ#qcEogbzvWFt<9VW`{I; z7dJM&-@JcE_go7d{xeP%t&63KsDg(V5;=7B#3F~BW$N0|=fnNWrMFW5tZEYrZ7!{i zMQhe{g%PsF0v#<19^7VB_Ncb*bJ4g*O)odO32im0p*dIC{pTbzRU$M`OerTsW`-3V zIOEUQt&47c^g^0fz>BxgHq%;yn-o-VpxuzC@UEcM$y!ZYE0hhpN;X!lI)OGR7;XyA z%(O*TT(v@}^3#;W$MSgUbJno(bizb4qn->xy(hIiiS@TYNEKv*r_?_$KKtp>EELI->9w@tXGo8 zj?tDDz0Ct3&U!_H?>!(c;y~il)H@IOg)iS#bUX3o#nF_mspW+N==gtP2xcotQJtzU z(vvGU-S@aOpxx<1l_m1d>+G#aTftJ=mVv$`6e3+eq^~beRsF3lxVz-y(}ZNN-6H}z z8R|mC{E5;{|u<;}1SWRPL(Rw_6P$POFos&~?{n@I_?)CQ#bvYI@ zZqiI>qwyBN`$kH+5r)<`BfmCm(or^$KWIx>rP;-W5&HYa2n#S?x#s?2mY5&Hhi^AP zFIq-==l-~`lU*mj{80C&Py3Xlb-hVmxq&udhCX)Ln?S*q@JaFZi+ioIN6fy{A$Mn& zwjcA|2atxo{w9F%M{nap#3zOAzAyM*Z_0xXUoK}gai~>W_??Wu{x&~A6nfeVd2*3` z2>ex~rI`I-k1Tqt5&h-b0#JBU09WF{sX)0lRG_UN(B=cZ9OTkKhBaf&5!YYIOSc|5 zaOYOLF7MNz1AoBAqL=*Wl@IquwDS|XbT~OVAxiEHIsCKI(<`oR9Qz8g>|R7dsb(`N zt13FXAu8r4OSTXC;&!cJje6y0=E;Ycr6R(lY^aDh0VD?i@5M={*0WmNZ+(4HBU!wE zvn#EQsAz~uSyd71#YaPOeI8Cqd9n4y#L6FIY6O|3BEken7!RB8@S1b1aG&tw;BIts zc0gwxZfFK8soU)3E|SW_SDlqNBEop)aVo>gI=f)Xwy1Wbahn-!1c&dA@p6vt{MuY) zF-{h}J5KKeNvpoqmZ|EjD8rV!RJ-5lj{2Xxuah5m@7@F*{Zn4x6^1LA;LmbMM4C)F zQB_E&tX)EDKN*!V^W~zIszv?BN=vGoHlVNxyexW?oZep1rb2n55cuwIINL}lijG^^ z{Fn!G*3E8RebcSU)ziOrh4!1z1xP&`Wm?fHDUfm1N;qt#Nq%D^HNnsJS5ljf$NI!c zSKT6H=rfC@Q@tyxLQ%DSA7 zc@ZILcE0W1XHB~?CQgSA{ShPZ9+Hx)P;)r2vjAVOrBcYm#C6fg83nC}^q%1rS&#Q3 z{Y(2p2ac%*mN(!bnZOH3T7k00>IeyMRk4XyYt#6Cb>_o>h5M=xJsZ%c=YR#Rj`t6$KA(YNx#{#dzD^)uDX^X_-!8E>)4%>y1wz5+z#J%TUXh* zK)&k6wE;Ylfo)!?oGkkB2EDTmE~55!C_USN3NPJ%P2-k7H2T7~>O;1Ev4Rf%2_NwO zGFEtmbS8GJ3SE!(bXpSIY2aD^P*s~q*|=ys1OBoR9^joxEDVDbd+BWF;uiE?HuL;W zt8tSRp5=R1cx1qtG|B~hh?`cuqN8Os#RbLYP20Y*z4#q-KAg-n5aKq@2E0?Dt!qJ? zN0yK+<-wQciunTM^c)fcZn3-loQ*f_uaDR_-G5z8mud!_iqaT?cNg_YC=u~A8f!)> zqHOo`9sAa8NEkr6pyOlWIeBVM`Td)34$ktsgACOzRB zSX@fw^c?seNFyRr48`WEL?LiFE>b##o@qrV-|T)*GmlU4x8^24A6#`Mb29X=-WA3a zW@W>i5tS)7WFQVQs_^p><=Soxs5c{Zi@2Jq$838e=4_nR+cMO{SkTl+M=x$x>*aT! z4n1nb+&xsze$fi(6n?6P;w2M3T`E%`XR3?~Yq;OfjLwnE$AogzMtqx;HRbsh;!M?_ zam)bH{bHU%B}N5y_JE*xe6&*k1p`r^#0huu6^iQQJqF<_wD;NOKN+E6w5J_mqkCLNk<*m7=qRq z{5LS(5(*ZHnm>^DT?xPx6+`WoFTfv~_^Tb%vm|hX2u`pGYz+ zM(O=B`*dK1cPT&CT=jTTZ~vFTd?@YDxq&HdLnc>BX&d?o%)TFexfc4;O51MEt$w(z zV);PVkat~I-l{N`wC^{a4VauKSw7>XZFj?Ov|U^^t8eFnmuPm<8;@}#um`&cU2zdH#8fPf~bGBJ3f-G&L_aYVzHBj1icx^zKyRbpuO&Ost zr)FEtAVq4-;shovWs-S)h$fY` zrGK`28!+Ql#&p4}B_*$$Z6W!-X7U2BunFa84C~1@C7hFc=4AA7sc^FX)(TS%C~N{R zFu4$Nul#vwo5@_jl(y-Jr?0f_!K^IKEY=)bMoNY1;T^Y@BbBz9&>l>xPDe2PWoZoS zGoek=TR85l9(jEDwjP_>?Ioq^OymK6^)yzM#<0$L{&?fB?wyvdz53CSG3~M3!0Ks? zNf{Y|SgnNi(jiij62p4;4FB;+krnF5*JOede+K=a= z0sldnb%osv93Dp8tJ=&yLi8`Gw9R~WU`pFem6OuTty?NPja~4*%i2S?%K3NZTp^XV z{Q*BPF-)?crj)krI9-2zcFWJK=fCSrn)UwIZ&D1?JXT<`&}11)FKrvRTYd2GqtX9t zlroxKo%FjrDGO~5Bk&#)UIt^VwC#yQK@@-MtjFVS6m`7a!K;=556J{xVCuWbU7{nT z!P2&V9oDSKwo1?L@~lERX4a7Hr24KuVfa6xI$GM+H2>1lMVIDyM+G)JQ0-dimOob= zU}>A)PBL8Dc5C!r>7IyN6VKVHUZ*)6cxzyrhue=KPGCyg^eStpw5@8BLgAUpEm}mj z3;MiWU|X3~+GYkH@cy#V1ZVzaujo-ZRUnTo{o;LAL^U_yFB{~+wA=6-NTCQ4LB90F#_){>XA^Vw2jlBx$oZCNgowmcH6X# zOTKBqT`Zjy_!y!d8R?~MxdFS6?f$gSr}N&Ztet~=;jiB7jUkrG2~4tV_4T;awezMiHt#E{=rGSyuwLF%-J|A zFr{t!JEhbrG=}xCkMAorN*j|I74~dHxVW4jxwP#MnSv>8Gb*g%(zdkRBeK4iJ1=jR z_;|Y4`iv8#(zZY1SOny97wzYb7vobB{1eR16#K}rrfL?x8%ujHH0^46>a~K8j@B${ zTyN9TtLf>BMDJrfNIO$Ac>%d$*&Y*8oBxInX)82^!j#*4@2`n**yUTTRjoI#Tg)tO zwVb%tyVS-&F4DrK;)&Q|Ss<AG9w;;9z?c2hSOerZ?V(RR>=4V{({7ipQu0>~|- zxNMq_zUuqx_Kmr_XJ#)uFf{(o(3}~qZJH6cke1RE$km;=Ow_~?#RBWhNqgx(Kt8SI zkPDvU{DbNdS9g})8q{|9@tQ(b7jz0DbOc)A#yGgZcc1gm-oPBGy9lSU{waTMKHArD7Gx&gs z(oh66UcHt)IAr^!a_2|P95Z)t(_{NMq$rKaT*|DHSmo2Fl0~bo9k0RKcCz&YB*X5s_sueS2$I2R{J-d0V%Cfpd9b25Z zQuzA^W3%H`Z1-l*0vnjEF2)K>5Q@?zCRMW4haP^<_UJBewb5JJnfWr26ofLDSs75- zg!(i1RM*HYUw7X5`1DbGn>uaO{!BwEo4^cAVt~>y)J=)bnRlIw+K6jiO=kn-+gJ9w z^69H*+m!a4wPo#_t#ev8xx8o7mjT4LuS{Y9rrt|eHA59`Hi7*d_7xqTx-DjFKex~o zok{gxrZOo5tEsVaG`MOnMd}(k;A7KSjP~OL!)D$!w3-^@QdUNyp?Wli_2ZV;PlbJp z$uDlP{o1K`8H1Ff)9pz^Y{1la>B?t9U0ZssJwxpqjGPy{m_4O}v>=95-}MLlz*L5q zEGVV2E#dmY(TfJw?EN;nKwN8JL?o#)o_l%)Bw~bv67hmYNeD0P|hbwbjKO7};9_FI8UwX%&lZi!tL?ZXA>l#aojYuW z(+s(oM%k2spt$ieHHP)&CKC1LDYduVuC(xmZD5sRLqT!le9C~Ep{JIKR__*dTGXKC z>;q%cXM5LvA0VG;$jvB?QyFj~^@ylb@pd73`S*_(eG{WSd*wX(eUw~9PnnHM=T!!l z8a+bNYu;8*eV7oO>)y8fty79t*SQQsOHHY)z+8o)(fsBVx+FxvcUjT+g2gWJlKwMu5CPiiE~< z>CI0%gnc^ov|-)C46m7-sw>G}pvi2?u9{d5c0BL*t=rvqKHOit$^J60d%BrwB5cZv znuapr4C{-XSG@GyGNoqhjcF&Ao)m31s-__}WmiqCH+_GF9(&cR#rVlNsw$74TU{|z zO@s{~e?VtYVf!lsIrS@ppZkS7Z}OSrN{Q>iMm1%{sR5-&rA}K;TjlI3y zj!U&pwYUG&(|m<7UVz+OO0SrdSD)~7XVs4{GOMrqw^qUJ423met%ns_EBp~0cwRSha_0yjWm2uk0Sl3VXGIQaP3m+7@Xyg$s~4!s{m4nvsE z=N=e;R#!lM+4Z?gm>FM|4*j=z2b-!NB6D^?dx#=RQ#b(1J?n~QD8GJ48M1cTgP=o` ze%i50?jGlobI+!7DGRHsvD`Sr`t7dTtwtw~+0p-@-NU-y26r^Lx*B6sW=5o;Nhx{uI*K>e3-0WTt=)M2;JEeC+sLW8Kj8={6-yD-luY}0|XgiCHG41Vy-dUjsMf6`yevn*^9@%}fQb#H3d?9D&^^ViMUZ__7v z=lnhfH;JY40+iU(Z=8nm?yf0ST84S15{^M;(*Glx@I@UV>}%^B85d4sxa z@8@!EQCOp<C#d2 z*_9R3Hl90YSPzUpbahko-0drvLtcaXmM* z54>#kG4wi=LCQl@{0%eMg1Lvskb$Bo7|NS7tljq3RrbC2{$-qSLhH-h2Hz&%!}Ets ze}g&Gj!O$cD@XxZtRF$SOW6Ch6Or*G^_aOmp43ZSTX$>M>q)VV+SyRtC6oD-VMVdT zX29%>$KE5xKXW-(e%XhV%PMmfMfj8%MGa+`8P*+Vt^Rt=<9yoe_z{mEbGo`3SJV)n zGOQ@pqb}#H&OEn1dTqnTIQ7dPlw-FS$~1OL}X# z;9C)8(KL@)*;W}#F*B?aV-sTSr`J(#JGn}JNdQa|`_2xystN)J-I zOD>X1`3miKvsrA~7w)-i`{X+}E++5UQQ3A+uiMlbBU9Oc3SCg;3l+h)EwKy*-R}IB zY#TgbM)%XI)dvrqcR4}{U6{@YRDh8pq4DSn!+QI&C$A6Wue`N*L*Ooc+lir+0HYb4 zK<(nGBEq{`meFtC4`~)PuiK-ugM5RFCG6#u&QW&pX7MT$%T%ec28Q*JO3y~uRL_q) zJF=m?(fwd2!^>2u%q)5Zok*(UE95dUTP0J#SJ07vez4@Wn*3r%e7C}pg|WCoJ~tTu z9KBQo-!`eaYLnc6<%HbOn9%m~@@Eg8^$Y!)duO>-_j%A6h)ni}eE)}Va7J*b+iF~; z5fiFkZ}og||Fij$=KmQ7E#HE&VGnBQf3b*jMl8Y%&i_+b7_y50j)j)9MN_&u}|L-Zt&{Jp>Rs~Kk~F_nT`=zrGKRUiT}ni3)rL}U@KKD znHu&)#IjI$IY6eqj;Bv2*+k5kSHWt79q*gndnkdTpT0()EEzTwv%_JTA!r`*$2CjB zhrALwpF`YNtrDrke3l5lwHiS%yxPPM{X3lRZM`^n607FbHc*l&?QVcqL@j4&_S9?< zytP79@my9gQ_`qkwLI5F!~HAYybo>DuL`{-U}dyrXPORSA>ty+tXoyH>bm}|kGDB< z)V|Wf%oKgf=xb@w5vq%?RwS|>vGGUB-E5hA^uhJG8zt2@M?wjuHo6GbxFj+jUvsrP z(hm(wYD9YO_U#oOGv*?ZbhCoLA0jfF$ktgPTJJRP`!ELwT-5)+CKs!utZPD*kki_D$m0UJYB!$1| zz?Z7E4i05KJ=Al2RK&+S{>KjGEuLsw>jacya$`^ihmItDJ=EMQzsHf1+&(uxxp}9H zFV3eJoWXWi0WGZjFgaVw(*$)iU4!6`%-;DPi+S_jyXOoI>ezf~NZoWOk<=@Ont}4y zw9_9l&(2NfyOlGt%-3pgy6AB!YcuM3EPBGjfjq zzBahQ&^I$rmnhdjTS#4EpcSYQLKBBxMVo~0!ZuPyh{1NCMhHzH zZIlD)j=|&kQwDJRe_ocv+Bklm?NiDKG1Tl1AfrN#lW2#Ckk979j+)NCCZm48q@z9x z?)#*c+xlf+YzplnnOCXpuY*@iN28KO-(x=oRDZ~+E*++x%Ula>)vpn)At+Vgj5MDw z)$X17QWYFY;fmEfK4NUIwv6+Ae9re^N>I3PookVTqKe^$nSgo)l}IU)$i=7zjfa2Z z*HMg_5-?ZTe@gGFyP)-?&d{N^=x28f3Br3a_!(9M}l0;lSEkJg+chiNzy}w*K zGP~;R`inj-fp(k407O`cs+tns0mEZOpKdN+Y>T1tYx*^9w3?)hTrSVse9_-%i^pCvw(g1=1X4nYeM z6Vvl;%&=}4b)=75YK28p*M(fM8EW4Y3*H-P^aB8l_?Pe?XekON z{>Y*gMf8^=$v1NR&tO<|Ti}?&^Nk-C?T@UytAJ@IgZ}+vW)`jEE?r7}@hi@yHa*wR z{UN`6bxM-j&*m3&@K5+yG?g2|7OVM6IF*b1VbL!tBCm8r{)5bSotTa>-+Fa&nsuO1 zz(31d3oX+j`eMnUh`imNEr6hC{O=4)I$8KzQJi2|5U8d)Rfy<*Iwm;spw0SM_a;t< z;th}j0Zc*yOacTj2@V)q6VP_rwBL6Vs`b7;v8Mm3XMQ6Hz-XjE0D}t`aSKxb0Zf4d zh9-%F-_)KncLSqd?tp>Kj+J-4N&rS91p*j6Y2kn=fdHn&0aGGFvW6^wSqzt(J?8 zS*hqeh^>;s{ulj`MMDPkmt!d60wQ46iFKKB+GqNf$oNJR^GZg|gtnU05QHsq_=GKT z_#kYN!^crXV_$)dmpI+MT7SsvSsm64@;hIE+ajG52w;IEzyg5)7Kj5Dh}hegx7ka^ z@gvWz$hYYm)V_Z_0T_)G2w?E2#g+$-6bN8a956Hosj`=!zujs+R5a4As(Rn$X9Qq0 zQXqhl)>96U^^}7zk{onB?G%@w}J=6 zt>EEq1(xlUx9uh$>b@eYe$>fHYnOGdPXIJ2nZo>#=+Cdg#eg7^nS^& z*srS&-pZV_s`{f;XcI+P-6o)b^yy6n(x*2lAbon1QSs?*0+9NefC93=HxzqbiM>T3cD$N@vBKn@rJ3djLN$UqJlVgiu*nt%dwj1LvaF+QMx9OFXoj&E0KO znJZ`1Bvxk{DG6y{!P<+m2scaqr2YpB#RQ zo-iGM$R6Q<(Mf>-CL%0MAOc}w0ug3m0uf?iBl=}GT$O(Atn-zjLYEScdIVrJQXqhl zGO7X~8C3zECKaF=)z~bno9~3F6QCQl?+I^upCbUHk%Cw~1qyowc}s@;2C;e~Z^o@n zD;HvM3v)+Y{qX2V{`AcOKb5XaE90xDp(Y?KFOU>f2?P>V3B;o+foN1^?T&8MYo)8U z_FFt}SkdII5xC{iNr3=HT0H}Ste%1Rk{F1to+;l79=wFo-Zl`bTVANxW)1-ujTAu1 zl)ccy#fc}k4{>HfScMenSvG)h6d@5dY>6kx(CymlX=^)|sB@1(i#zUdSiB2LM#EAB zq5h`d0mS))Jh{j|#1(>KFd>l#7A<9^z8VJykpuyCwa-qMoI2lb47A;SZRV3|ZJ~rx z8-W<$LXz_$1me61agRiZIxpE3qDR+po&VxX$gi6TlM=t+1Ds9@1Td2GA_U^R2yu@@ zh&nI(8R5!^Z@HNzE5~vBbzb$60E|Wo1TfMPA_TI82=R46h%O;jc0g^W?-)0=|BuLo z`x!Ot2*7BhKmZFT_7lQz5c>&XI6kF?BeU6tw0Z}79l789*}84phaTA3k^qcG3IZ?@ zsiH&#q@qNGmx*8(g{c}tPu|pRyMkfUV7%6-y0usIy;W0@O8oq4N zqUs#(dg)YuRh@->hE*L(07fGP0vIXkCIS+56XBsW5gK)q_MBnYy7%|a8FOqajQV~u zngEPO3IwoFVh$69f|$cZq1YTILT_$z%5ys~X8SYOs6oHmDGE;&5`fW2K>!v+in;{> ziMj>hQMVv8>elZpZ!$+#cf-N8F1FpK_Q=2iqmzOFESLmXFc83kalnF6z=Ssrj40nE zbz7+ma3nqqSa4?7=861oa$>3nbt?;ire~frpLT>Z0(CoWa8h61h zj7|y!Fw#kxU?3-Dg7M=o!RSeuiK#21Ygh9PJnR;DsB*iZlL^3Rq(A^8`C-98{IFo$ z4+};sdyf`b_4T)@)xV&@M6cLJZDa&sG*Tdd$w)&|24qOe@F6KfhNOJj&7gnQd1S;D zyyJNV5F^4Fp#ZLFuvajMz=;an~%Pl!oNDT#q=dXR-Ws75P;E0zX6Dr ziQ#+DAZQU9deZzl4#=c!xS(jm^}2h5HV(X@UIncqiAg6f0Ro;P zkgtt3#^RD8Pb_+E7wz2yGKee)n7)hU2ak`go^BuM@ZzXMnFb}A&0M1LFf^NF99xX`gyy>jh&wT%<|K8aWi~~j|1p*i;LoWf6p_kwpdI_4L zf7hMeq-XC-F8_832rby;caQ*#MhXNl(xyuSWYZyJNV5Dq;1W2|( zf~No^XtqE)^-`-f^Jm=;xSzAhDYuq00T_)G2w&1EQ|6TO%Eddyf6a-*W4&hcvIUw8$DF<^aq#VSpIFRlCbVkUyI6)&(%rn(#q6mRb z3Is6HaY`wW()t1}1iRLk7h4km3G>40S!+N{ai|YQ5|*r+Gkb zN%TYFvNAd;2*Bi|B%d5el248&`Q&JlFKylTSDhzx=@q=EntMz|zrFZMN+$&Z7->k# zfecAGJ|yMnkQ}u?qt|%F4@v%-Iz@Xw#rhF|(MUlA$ThdU5&?3}FAxE8&3m!MK=U`U z5HMFaSpWO!lY!99(FMtzm8p1uTpu|QYa_+aq`*)UP(Tjzrvf?59~6+o z{K-HL^GARjP*nM1V$3%6&bMo3^nEty0)8S!1EjttAcnAllrvBO$r&i{oPh$(8FU%q zl9Jb;)%}Haop#LK{qqezgz2O}03($%D}a$UW-rZhFu@I(0K{VRTX;fRSnb<+IqgZJ-;9H8DiDCtNPz%GN)#)BB#M=I_E(7} ziWe|C?3}UwL-gYD9}4f(m`L3BMkfUV7^z@h38Y|NiC4iZ(Smu%;o!c5>R~s|4a(>};YZ)Lgfl`X1p*i;HKPKO zno;4Y85Meg_SqKsfzJoK{;b@;o=fbeVj{*%Cj|nSkZ?v+LJ-b~N{EeCl@J-EPv=UT zM%~!6rA?~ygZhJRdqr2@H7)R^ zf=&tqFp~GC0^+@?aFE;e$6P)#{Ib8_wiR^=z-Xi(08^88plTpHP&K}- zRHHl46H9Y479NTWoa!FLYoEgL#sQ;~0s)L$nu(>!RuM!)Fp~bYd{D!FP-i*2V+_8}u&rvpV+q^V;HQysI=u}+LQ6X6 zjS1-t5?b6n#-%}^T|C)om~{J5=lgzL&#)6icIZH>zaa={!^CXtW&-T{r}!ff(Bd!0 zj1PZ+K)WY-d-1vC&$HYoiSM;P>J@}Ti___C2%@ksLI_{AP5Rah@*6~9A@XJn7~~fM zXN{1V1G&Dp7c`2=d@}U*)wOtGp`j+Afb<7zzf%Fdm1*Crf8A$&C1W5NwYqmYCvvzN>n|IpsS#u^( zfYjFngmV-@s@#kKQn?v{S8hh2m77Pp+HaWraNE8%8{bX~m|uS`?i|rcKbuiv;l$;8 zF!=(m3rE28;JUl>1Req|m+#~$aB_9_;CVT!6l|$dAX7;A@U=W5eyE%s$XB@7J3BZz zI5{ftPYXfNJS3QFPJPGUdO2!lh<#P;8ag;KG(mNuU~OGcC|W*=z|#mG5KsB zo5}R#y7JsyxJ*~BryG~)%yZ^@GC9s30#6D+0tGuz!k4OGc-$OZweYZ|BKU5&Ihy~N zbEEs;c&#HQ4okpRs#r3$ip39u`;(;<%R*V$?XwSl-##+DvU5tm`-=th2Q)hfZP&~H9U+yt~hBcA5Z95d1yf9v(8z{0TZTre~-=FaN+?U>!hj6Bik2($~6*_8H{ zhLx?-oHf+Ks`>M>g<;jalYoUQmMQrxcnI;))MSEJ#*L?g7Aze!&^w@!BJ(zspuy5; zBXicfzhM}9g$cv%-mSx6*El&LuBl`NcTU}hDwUv^!1QIGyBvHuuB$*F`qVaH(MM##(I0=a_tP0}9a;RY)#g@N#6GJJeM*x8 z3ogxw!-9J*=IqY@>$HKqn&gr&tke7SZI*MtWJUi8i9_$!?73c#-(n6po&vrn-^HEn z^t6@Lk+oU1?q~SEk_G z2dlzhaGaSA&ib5QbG{z*m)=c*N9_|AlA1BUQKxk0yMz1~P4&QIUI)5)IC*-yxjH*J zJ9+ZBJSPvHvopuVmG9)iqKx$S&8vDVmeHCotY`{l|TRo64%%;`h{)6>nJ?dI<6<>lq#<>~6_7yA=0LRTm z;0l|MhpQ7u;3aT!7kGKGz1-jjPCNm})0F~})(Idv0GgSK%@M-~I2K@ko-t!u`YZ2t zl*&{hfr!i27&nU(h{V6{-l{W*6MxPAP_$j0JA>wBLF+LA_0ea77Mcaeq7cFJw|wfr zzFB_s{@Gi0e5!n4Ahg+#;8+`T@>l;4h>N%y*xB6RK!r?=-BdoPiF37=PQUn5{P!e2 z+8b37O3|-{p2ioz_Jv9$=HpgWYkHLt69@IUnwxa9`yAz&`A~v>HAs!jxvTB3^oBiK z8m|3}qNbE`1tuTq=@m-@N_w}Wh|A)##bOp5K8Jl8#Kd>iI~i)@_02M*P>6`fM{g5Rj*ZQe zp6Rq_hT{y$fnU|yL%U2+32%R=tSN<|&9I*P_0*%`yo{H2-CAdE@@?S+?K4#|jE6aQ zAO7vpjgJT(pDPw&mq^~d<2&(pU+aPu8#X+Miw!;lB^%R;)YP0j%>TD47`zPYxc8kT zv&FTxMhfRV+MN{q9@=SwI#}}}OZz?c__uYJ;$otY%n6|W9eB|f<7R?RxpHYB!(KXEO%NpzX4up?XYGZSb>i>Tl7orZ)KRPPyF2&5K49rQo{r{+i&5zm+N=}T( zZdE0k5+$F9>Bm^0^{zHq?}b@D)l?1fQiXqGcg__CRD1a@{k2 zDdQaNhcv0@`l3f>bLgmXO%3yU1XkH_mYgl+i{Uwj6iuS2dgDc?cc)5e=aub>-)F=$ zn+F}%uWD(WEbpa?webP?5EtR4qK_=^rJ^sU`9+8^iB7X0eH)PXdA?n$RTWmGEy+tY z+|2S`s(x9pC6i&TqXyxn8gFWOFV%oNBrjD~IQ^}9Ti%f|A6HlSXIke4BrmnJ#+F}v zj7dcFkB&;j;$sQ}%X_JGsYu=?!}|J_Hou0q>=oBCN1n7gxz-+%mujS)<-Jq`!Vuk} zqX^-pmeSVpGpa;)MnxZ4env%KtanD`Oqf0Sr}NJnH{RWRf2_>{F=<9M+|2Sbs(x7r z)6h|am{E;4wfu}~KpxVJ>XuhKYt!l5;-_J=T5qi8)SWb=me$zvGpaF(i2l)0iI`DM zVPN?gl`a)!Mzvww^ACb{k4hWwneph>%2T8n)kr(b&!`53A-Y9J5n@IyrLE=n{g^-$ z|C^kwbfs-z8P-|L8t>V9y{}(?`!kU(7azS#+6tS+ zsnFsH8|`Pb7vmduGY`=GouD)PQfd*3rtnx#5e2W~@mkP;u&_jC$KI^hHI9GtWSXpDUfUO;$)O(?UR07+c_ZyCzsegB zhFIlw6d_jmQrcR+pu&(qB==bMBF)>ea<7uBZ&E~UudvpT3Mxu%ecR$OM57`ReWat* z9-ZMqGg4}1EDOA16c^dLmVBjELdonC-?QT0W!<-hwi?!l)X?(VF`fQFr6IaTM-{wO z&Azn8mUkm@iRf;YuABUQWzXF&$JDoatg7PSR{X6E$&ECb%YATWr%yqeqrCLM!zSOF zHJGqOR(RIxQgktNK-UOMWdm@^pvy+~bQ#w3Dva;>d2eSwD74w;f*($cAw5%uF%Fh@ zA`P0AzT6hW+N#fwfO>OY9(oYb=l8nd+ww?Gq*$-26o1K~!@2^3mJ>o_4*@Jo*sE#FC6Yk0WBn?u-BR$RM%<3>FGZLC zB`-@x8Uk3B3`j#POFF8MmZee}TfVX{%#cJRzb;|+s^IL6+0jYiL-H%1NmY?5`$}(a z&MgOj+3;zGM)k`W);ektn>6EUVO?$c@@!qXNG=+~I)?LgrQfLd(4ze1)n%QbaisEW zqb&jKCUneB$Gg)}hA7WAs0`LKmM`TG!(}3u@)J)%*oqFuNP;A9WOAxkVKpd>M8P+<=kZq-u)|M~jC#*v6423L+9k}-4?fSQhyW&^>>yAOT z7fGf3CbYMFDSs(K5q+hj7*Wb^A`i=FIrRuenRve|zBUVAbf9q69M_bn&|*2Ml;3z$ z5DUJ}c+i=8b<`nB`3Rd={EJ@y7%o}pkx!9T5SF#$)n`MM;Cc)MYv&oCXXIGFl6=F$Nl3u;epcs zWA9zyq1@X3@tH&_)#!XK6&)RCFgi(;ibPaOr8zRppc#kgAVMNi=_FJ-QFK&Ph(bA) zLJm>rs3f7Hr2m?G&D{4rv+H@cclXTx{Xd`g^S=9ew)?rR@4D7^U2Cmtt#!>>Pn3vB z-O_r`&&Jp$UKdfWam&m*4y``X>PXy^}2lQUaS{l}KAEZp_*c50bp7H*kzRdP% ze#h@`$6MEQ%Ybu7cc;4(J;&_U`pvT4y zf1_%W5Hbt4rS6)OS$@JVE}HY7ep|;*b-c;$@i$@u_W2C>#WgD3xoGYm4KdI>bs8Ic z*OkWpDXSF_TDs_(8DIw-)ov_1m3lk9p=MN72R(oC`fBv5Wg1&jROUp1yM#l;X7glD z6c4RE4-!>AspYZU(k0E?S9BIJxTyQ>dx(>HlF?C+3_ik^Y?E&G87|9N>t`V z;hrI-`N*6o^a)a$=n2ww4W?w&7zOMwFDO%zh&x8kgwP1^nseG4WbJ!& z^pSYFX!$hm>$k?rVSk+#n z@>K;PW2PSQF2RVB5|ueopm&M`3A&5SiE=@Sa)BK&a(1>)$=IQG_lHkzo2s3e_q zj7*is%P^v(L}g7B6X#J(nR^ry^(dyuqx$97yiBQxH@x_TH@3b{-~yB=X;GOIg$oau zG7k@!Xn4RBg$H+U*P2~x6*wt|B+fK63oyfok`k3QQ7kStMzOfE9-~-X@fgM8!ZE5N z+)#6M%i?hZk~8iEQtypMiINuW&gH*xp_}sFYb78##4`*oRiWz z8zV|eRMteXacfVu%-5c5bnVF&tvxC7Qy%wN}yB?bZyWUsTuTLMgKFU@IUK}(0&FxH#C@E2y6NNjGWXt?Sl8qiSvPCD7H@*D6 z^!&2+`-2Bd=H{*sD#nPC5|#CA$mWA*)p1KF__wTQLs%;6U5HK4!GzZ)+hl9*_IULYk4hPXL$GubMo5x<8!93Dp@IG$f?R%)FNsG#y zDBNu5AoJPK0iEI;M6+R7ba>sF1{YOHBpYZLEcg3gS;a;ayyC! z`H(XIX`2q~tvRf?&Y)_HeKSgww5ZI9!VU6{G9Tm}(UIFxG{~!#d(Y_2TC2Bk8cj#b zqv;Jsl$5B&N-amt5B-n`z#{h>{YOIZ@tNeC6mZ z>-fsiTRa0gdc)bzI?*n0 z-L3Z2==iWw=I}QUb&mU^L`jRvoG9G33`geMG8}ZTg(KRQ$vfq$nfA=#`{CEmdm2>q zx5bE(5|ueoxLpN~%y$(y=vIOFCHZyEa}#P7kJqi;!8?5O%9W!SQBtBZC&~*Oqc~o& z9-}y3;xURNdP(qR&a8s4=WCqmzujGc)RB`qpzqMUI=Im?_VXOt*s5m5uq7=0Y2T64Xv=cz=^)=dLZ zqNGJ-PLwm&^_-n$-SwQE#a++Y8HNYu`&Lc8JHRx4O7-`&_8g-*7*SH9GA9a`Iqxj< z%z0-t9o|`#IX`&fo;TWUZ9hv^kFZ?iVWx`_B_%3zqHuAPv&`ctXEcs-7R6CR_!b*y z);`z%=w2y-?|QCi*AqQnsh^OPm+3iI#d1x4#6FeM85mJg zqB186w}f$)`4Yw%U6(kEmM~k74Ql?R@W|^>UO`J@mg@nGC@E1{6UD`O6j$aR#YNqO zEApt~vK#rmPHPl8P5ZJerqB30C{fa)GA9ZbnR8_xnRC%_n=3l++a9p(<{7)MeZnYX z%L+crVY>&?qB1AS6C0zrp0XaJxSrxMit7o(gItAxH?Nt|%V#bdQS{@-()pN2Nr}pu zC>}13;>kRY;-SG2PZUSF?0PEKSMXxKyo=H5IVO`Hp+rfG%A6?N;Q~+QhYLLPaDgW} zT<9^+prUs_Tf6DaR>#Z(6R_-MX;GOIg^QzjGLNHpXmG?6#ZfJtw1_DY*5i6_PkEqH zwZ#haC@E2y6NTF|=gEA}oQH0N^F({*kK>E2$FIs%PQR#n-`+w2JFb!zl{rzkjXR#q zH|}`oZX8dvakr$|aNmLa-flZrr+rCaw=BgxN=j7bMBxHXp3DPI9vVgRL;>g6(4{u? zDMQHVy#`%vZivCsyro5DO_U2A3lCiAvJMYi=;H9eg$~1miE~z1rkeCs8{m}dlhxQ# zfO?d)sLYAN{ldaU=D)CTL4P(Oz7uLmVX@$1?>S1FHyr8}9~VCjBT7nC=0xGb0~eWx z2QFxM;35hS#u%vjna#+}yHXx0nj_6S-> zd!PQ?e%!r0`IRv!QPQHaCdv)B73?PStzb8FE7(o66@2!_(bdv*TF(sLSN#(u zN?KIrMB%!go6NhO8`_`TL|sp3szJ`r)AR3fd8Q`u+kWiDh>{YOIZ?RX12>uP9=M^q z2X3O>gOw9o4$e-RdPsLy!jMc0cNL5%DN$Kx;<>r2^XD(e^3vhovd+YVrHVrZ_!kTp z{zBYw(X|i1Q~5Utw6u{V(9-7LAkfkVPoSj@Bv7?E=*iZzsVm=lKb`V3;n^cJl~G9G zuT*5+Rr$CbQNGM~MEU5BC||TA>eaz|ymQRtht*f3tafZQE&#VNZ7+$vPLv}y>$yA1de(Dy6wi9@j&Rmn*SvIgWN0J%%O)c`zq%_}cpxn* zbE0r@l)KF1D0ehCau>x>6V|MHB`R~GaN&Ww%)63ywlqhLYnG=QcC=Z!?ln3f29wLuQzM8iscVqwD;a*wG4L{am$6L~(GA9am39yIE zF9G&IZ}#;NT>>0CZpy%pR=}?ZARJ7l_1A?2jy2JqUyq zDW3R%DRAbKTYYHI;G|_;h3?lJl9(rM5~F@AENj2=#O+FX%6wPK6Wx{a6zxhy2acy+ z*+@SA*lxA?2m&z)^($#nS?{R(ID*RoEU+DQ__wTg)M2S&2ZMh>A6xUmcQLcKdZlYo z$zZF4T5{-)`tMZ!4FVULNfNlo?B5`8kr|%AMP`t|=)Kh>Pm9JLOZvY1@N)O+JrV@| zO6A`m&}Nk+fi|oD4FYXe;R&=^1qlopv^V@soUUQxN56Johl`&j2>g|btj9VZ+);&( z%#SL3(DMf$(NV>do?Om1&&yo9FI$GZ5iG(E^rc0+^C~Wr$cayRH_9>xbeuiOnDF)dxY(tL^B=wCb|)7g!OT(l|r47xVpibbI? zC=`l5MO&ZB)YGSG1IG09wSGgGCx_+5b7iu)zh|sFUGtAyAwk*g9jvTQhyKM`x4vvU zMfE-Z3(C6l&OKR6o5f&g(G4gp12&DO&(zbRQgmq)Erx-PF4aKqHYT^THa;P-^( zbR$;#!!}6J^*21MJCBx9s5A;wM~_TpXfaqUeHw$JuS?g_*Cx~0T3R~H-_eD3Nro$* z^?T9^xo0(AT31VJ`Wl9fO74pu$6??ia4 z^5;jt@U-rXX*vuY8jYpRAnSqAA8^EEYLRtW6dkg@t`>ty)0OC$G#BtpF3p|e>Y~ot z^-qEfWA z^w>JOWCIpUhauTX!JNtFa9JD|&?&iG79Vg%{1k2OS~MnAN5an-G(J-}mI0Eqe(hM@2@L;C(Guj0kF5#+JmH6t z^^YFyj+4~J|DqFiXI1%UECkPtlJQ$+Zg+a$pR_>2zi3VS8di-fKXN#+W$Y=veN+CSe}SN$O(nBgY^DwwtSZ5% zrKLrqkXc&#An@1KqDWAMM5$t)bih3L%aOf1bIhMBUV@~*F`Q3%-;L>-W&oCsVCh4n z>y!1E+H5MFM$y#=5d<6jCsR*yh~k0JiqApjK5Y?2q>rX67roo@>U^JheKjTxTHU`p zLx7H!wibwqbwQxQ1k;I*9)&?AgC^2vu^DuIEy==ZZf*=$o*ND1*s=t!9(=GG14E@g zY$?*PJ<$_pWQ{7)*gf!CncYc2cXsYsG<|)xt~O1ZPBWmhD7s`en*pXY2AiS7qJyQH zl&65%j8EgZxQpHc21LMKMOrPFE9X9eBp6frWAn=5vf%EtgPx8)m>*bLdSoU=n@rJS zvglMYlSbDev%z|cE!nX#Dlh_gy9k3X)E;ZercZT27{$V1#`W&KGQ&g0O1_vMsr~Cb+DO=G*p!_{>rjOxmTLj`HekB4u02-(#b3u zlST#$ObSz1hXI0puwo)>GqqV%GF@9=s_JY$%|RG|fwFZqD8j*vwEo1#&-^$)=Y6?b z;wvIT)c^ldHkHkyvUK!lS~_}K`cy48lcGl_v*~&|x_Y2vu*edu(-`g?Pma4cs5e#Q z@{WyRQ%g3?ExFv$qf4PkwKy_3 zI=gQIWowJ#H&S+9`1x(2f;B};9(9y{{CK=O-JU8OTc}iB5IJgtwH|}1rO(vX2Ah3g zY$h{xBsZ;CJXa@3VvglN*4TnMG%6F%7`TL#F5$kjcXTmmF}I ze3}=FFB)vnDV((KUA)D#rTj6r*H~V5DibbuXMxBjQ+4%dx_a6M24HKIN}+1$XfbpF z1t7ej(^--=XSllZnH(3IyDQ!ZWPT)Rt*)*P)ZCZ4|BO=LoF2>lx-;nLv%qqc%4QmX z`G-aWO9!wLGhk@xF%9%7zzUj#`y>0l9AptD?D(+s;_&q^t%4t{)QK(Ml)t8KdUu*Y zxB3q1)%ol~{AV5b39@-PDHzs8*HiNFO zT^4DR?euS#|E3$x|4$y8BCU++GtB(aZVSe>#p&nY8VUZdU=0U8jmc$cGH47(aQc8A zQwY>4n*T?&9^1fxW}r*c0U;%uPW?sbjhk8i&$<4uJISm&wRL02{A1^W|0sC+b7yU& zXOT&V7o`(E)$wNCoK4fT>P`&zUo@jTk<6buNc&5ZbZ1ZW&mK(u#gy*w@u!Y^NE&ey zV`^tOeW1(^%zM>HFX_(K$A9JAzC)WJOCnBV`D{m`~y3eqPyEb@joA$h$-SLk< zyUG6-BD%BH@rU-#|6)UT*4+Pa*OlZmEYw?fxav{k3w<8!Dl9qCogMi>hBt)Royh+WYz+Q|ep1!ToXE%T4QAHwY#BPDw|mT4bdSs!?3sChZ95Gf zhrxF>a&unJ5}0tniUzFbya~yFl|#R1fMt+}g9hAd6RU7o0zxV(f`X%8G#pqiEI!yL zWd1_&Dk}C1MIP8w`>W27N~sx|0n%19-M}dvO_Rw7c|Ux0up6c+{71lNXbM4)9d6;O znMMZ@Ifr4-rFpo3u$*sCr!kxz_^uuet=ZNDwr|_rIqJjq5KsLLwLfVP z$Yf&S4GJ7RH!?9YQ-NYS+Ul!i0sS`yNvb{g-!TMt6g0&fOZEu=n|NF~QmxrCjX~A% zJ2FQ5P>lLb9Zo#*JK6I8UC}&_8;|CuPIK{Qx^cjni5|X{VAG7Qdg``dYh;Z1uB2~m z#KY@}asQ)I&40lddz`oY#iaQEXcDIS_#YYO2so19$BRXGlOy>iY2{ArF>vPyjWyRN zA33_47$dUgm+}>V)C5u0pds;-;;YTG>_^5=uX*0n!#S6D@;8RywEh_*yk9d?T5+y# z++ptV>77ScEVA$M1ZCux^8btxX-Hh%uTqVEcnk^i7o@{by5 z(=Qucjug(BuQX17(Q2jigaYbPrx;?asBM0&@V^||eupVR%8Ah&ua{Y_k=bjCzn2-` z*-Je2H`Gf187sf8r5s6vd2{wO?Lii#XiMc{iY=9ROl-@qHLCuw84|=K#)VdPJ$*0V zdgrLg9{IGX#M8eu2B%l{4^8@YMde7nc}sp2EXx~qeC}Qat!Yhh#N((nzgBtrrwzeX zQjXO8;@x$t?wP8$Uml4?|$>k3T|qlNqFXx%WOqJL61br+6}z_Xbt--k=Q&vIb`6SP@Fk%O9X~X*`y>tHUx6 zcd#H>=*k5O1nITo?~9{*aJWoOaO}+zCf{>FgfGzKvG@)wrag%2?Gbc)HiD{&EF9qf zY9d@iEEgZxYr1;46L#@DxbDKRk9Y(DkQC8y61ch$NbinYHSwNQ9vjuA+M)X?+XJF&QdW}MD*EGV+LuDg zKHwz9rKcPC@q?JYA7|-M5M9Ghu@@VUi4* zsPv#$)yMnSvH1P&Mm<=syfd>7!Ng07F>}tSZq}OdXi(SB*19AWm82JlWHW}z6k|Ri z?lj|W7XF0lX&Y)@Ba%3GVTxJOOew6kYTztV+GK5*81b%F)BqSJiz~8o;_)Rm zX4iVX2vdF5m~9=fphj$`X#7@Zxv2AvR*0lWc+Vg6vcB@iAQQs_bsmg4&}A})ibs1y z+So`W{cX~Y!og#1+n*UV&nZUv%;L8Qwv@E#e37(so!6L(T@RwyjoU%F+mSW&6(apf zR|0#ng-DtizOiCYdX`A#I`jSNv}yuJ{>vOv~&l<%QBdhQD2W>2M)uq zk%#R?(o?pQJFGKL>fA_8(f%~SROIfvFmD8-GwkcB0iDG^{g$|nvD?2(P1B{h0l|HP zdt* zwJtGQGTa%lcXdyY)&UDpt2#br_B_k4O?P~=7GL`644XJj9;c=!RO8ZI zm^if_FV3HRU^w{Qp-msUs)MFXhoi(b1xyX(82nW&NRE>D%H&*ILt(&%^eWQZ41{{T zny&6Ij9i`5xueRN7gv&hecHx{Rt=B^VB{fj-Sm;VVbw}nxMnm{MgC2ny!@y7b2<{&4+*?nQv}6xo#g%W^0Wd= z(;*ulr+k3btHoh@izKah!`>H`r0MHj)$e?@;nWW}>{McsU`GvN8cfl=FknN_fOVZ0 zs#O*5(x9EVSqeNW2_+lL7H*7H{17jfzr98eqMm(mtGk$9wbiHnC?Uj&Q)mgl2 z6%LisT?{-d2r=J8HH~i z+e80L!6d=ca!}GUquxDZiH7}7>Mg4RKZYIjohqE9vq*B&oG}^m2uCN_Znp2;f1u}K zINjhnICxwPVs3xqFge@qIHmH&;%!5wu^(q4H3A)6JiLI{wV>ody`$UJGF9e|tTd|e z&Zc<4sR7p!on1weFFF(^tlz!*l|{mU4K4n?x5IY7jKdVS=K6qm<;Y#refRpCbUKfz zcY^T&@TI*XClz)&5o+$IMVYI@wjF+1Sb|Ffp_#g;*rP3PQ+sT& zK6`!W?sa)e)J#4X5XP-1!_S z9XEl2S0bR~dgj2JoTfV|^CBl`R5pGngm%8bl`i(1lN$E=b(a^_$vwS!@KflLHIOA- z=mXvffS6VmBsYa+8d>IU)gi89+ZEt+Uw~nPi}InQntpsrLd&PS(FN)*YN1tYpd^@* z#IY)}UQ_p^isbWNcpdKl)2Z_NjNVJ`jhOoyjv8fS(VhctmWRm6j_Tnq2j|8r&cZrEe34jZ<8)`S}** z51*$8G4?-GKm`+ck;sJoH=WIo){A}D+78AF02OEtU}2TzD&cV zt=l~=ew=l5>4Zu1;lz$>18~nMl;oM$2RwYa>;Qj7gi_^dIUC3VCKTCby%w8jkdMYsDi=?lJov z*(q-F%^ki*S$le1heW z87wZD^kigoqD>nqw`1u}@BMvh;N%cOLYoX+Xa~Vvo?Z7H5IwqS?~CBZuDSab!c_}! zTyf)q8{MF!Z+$~b|10a;-#HQor+GJIz^;gETyUislpL>BtgJYBTXF2-vO8L~9{O;y zeTc&pH(AT%R6@(F!R+_ioo)BZFU^Lf<1xj=hJRk^sQ%q5+kWP!DKRshe!^i3*A>C7 zPOx-x{s3*eO>>g1x5e4yZ(HdB=>l#bt`WG_2ui*PUie{?#ok9HqkY~l^;>ZQc7f+O zN%0c9>j%YYZEIuE^|a1!`iyBxuyi09A!-6oZ9Nfa#4fE{&C9Qv3D#}X^HqIv4qj5d+-4NFKv30tN^R)jK|#=4 zLUE|*40~X^d*QPo4Cm=uH}4JZHS!SbgpZeFs5&|#TfbX74^3?xr@Cm$mClHeqnC|N6q?v zI8j}ZXz#K66tBp+?QQkfHomL(eF*fFw|E1@ycRw+tz4P4d#${kN&TJdC!e6J>`}m> ziphFnl^J0Aer}lGwcaW*M|ban9lK^ACQ25EBR{xovkqT{r`LCM1-v&uvI^RoH3KIq zu2vV9VAmA!u6gW~Pao`5wXVU*xJnuID{xy6^eeXSz*;Xi*LA)86UwR+9LB&F09{+W zM)HDdB&o&Dd{xgw6$94H_9pbc`Y4Uq3&sTn*c!=;jI5EQmR6rW>ois8g^j10xOQIW z=go#yIE}55yeP=%Af;BLb~tD4v8x?4LeM7S%**FsX?Qg_s7M)kZ19(fj~y?BHoLf- ztvXMq!QKVdNaD>SFPb~U5d?f%A~G~oYYJxtA3F5lkiWI*tS1G~yym|uh?}Gx0gPC|;3VEs5lVyWZ=m$!i3a6+9gZDVaq-h;&$>JhT3;k74eok@ z(oU`4E^nChJm-EaOWA70AO#rQ0%`Hk11>p%l7o`Y_RUir(>K&s=RIp$Xg2IluXKsK z;ea9%JK040aUqj9`}xx`700w~%3#$#rz^=3NKpwZ_~o@lhi_y}JJ{;c?=4}c0Brbk zS^sJGQ*c4|iS8u9c-KA5amBtZ6xezp!vWmppG>twKVusUw$$!7o3%a!e0r5|!v0Xi z%b!2icP!X3<&;m)W5WID`5YIJw(nq0^9Gx)i(S~RVB=S`>nr_x?(XgSBAeZGhz@cq zgz)wpfN$^a?Z&c4wsimV4lpozSs55e$@`T970H)%7wiq|c?iuLu>_|fz*MkD4RTHh zfB&=tZcw8zNEV12z=F2?s?2>H7X}|3hX{YpEn=qrZy!7SYCjx@_j?A2(ZZjxfuBXI z3x6A}4iX_W!0)8N&syAtxizFP1+(0?QT7WrA29c`dv;9kJu=yx8A%9*yX_iGz>4Tr z8}U_f!juUDY3%w6lk7smJDu>&i9;^*xA>SO+%kXgT^rPWv3vHT*L4>)DuOu&uUS-9 z5JE%~B8^Q9NBXG{mlyJ5u5mF);ltvP@hvex$Pg@;U1bm;B5@!p(A z7z_`CL7wU+ke7#UYyn|6te#&{0oPH+)Q?UZTXm2yVB)H$PaUq+rH2na%7K7nq zFvz8b1X5R^v##m;*3?7Qr%h@GQwzEfm}Xl5qbToDRNi~Y-N9*3sIjK>0T_$`gF#N# z2&Ct4vz}C!?ajV>w)RH3+D+wVEW1Lx_4meX}>^fIInI|Y92uxNQk%f(ak3D2S~Tw zW{;I4^*>gxtzOl!_rplb>j>m49ROKbncL^(n398!s-KhC%})ae;++8cbkWW~x*kKn zK+tc#eXk!(x>h*X>DFw&z1)L85Z2BM?WEhOtvMOjcC{(ec!BBi(T~yU(phMA!9fAy zQtiW3!QOYn*ioUi^?UAf+Jh0>n(Y8g-RoJ;$7voNcJ7JwR=_$uFTS1HgWnD6ox@VtpSG<2sacvRzo@b0M z8Tv&aFwvF(=3?Hsf$!~B>T1sMKSpi;B*0)WYZxMHG~O*T7JRF`zhI>;<$BJw(?<{( zKOu}u$LW9>n-+fD$X;8!q%3bU3d6*#0mmAMHTnDVDvz&jz7V>Rt#Ev=#^V?SCU7Z$ z*_&Np9sKct#f;dst$F%;zhf|1gM%{<1m;7Z#l1t9b7HMkZf)LgIeb$r0uw9bCZ;3E z`dL(+!{d%=UroO*{)WP^xF|Q^Km>t#cEoNU)rP&NX}OAL=cc7!5)hcewE*S-U#`cc zpPs$r?u5^qvSi!=f_V6WM0srBr*UJ`J|MiOw~NCko0CFrUCc@S$*i>sxV;+(bl&;hE1aHea5+CNib zzH3fP^O`4UXGy@B&X<4#XD$fbjZ=px!=I)4s+3RJckIW$p2mHlXNFUvlo?0U?*gil+`YSJa(Y>g%0z^M%a z*EikT=z`MZdB;phSu^$ZH(o*De(-^H%Xs@+^e%sh&h4eYO)a4OCDx*to5CY>0;wdv zmNiR3^WKl!mp809np|`qfoT#thIh|^5SxMLt2DMNW(4G|oq}0~90y@m!P6ncs)YGB zw4OfqnR}c)bIK#lsAJm^xMCq(Xtv_K`8G={Ri+k9Qtx5<4717|^E2cPFal}T?Eb4g zo!_j9ed}u(vtdwlA_8;90>ErLLz}O3i*W0!U|(#-o}q3Sj0XmT++{}~wck#?Is3GRr1B87#oz%J+G3*fECkN2=dm{36uYqPsrzQ$oRBj9 zECN?5gzH}@S0LYyUb;54{6f%y+p4Hl4%o;5j<67zD$e=7X)pHLT)y71>-;=ANK{ z$4VNDemc7?E$Gi>1XXP@zzUE&M8gV@{0<8+J?Wa)H@9bJ|Kl|~>Ub-@2OJ;ADN0AZh)YV=?ZU57fNpCIh42`?tj(Ak>%%&TMSMUAkeD8z1mA?$*; zCU28{d|7P8Subl%GA0nj%Qa#4BiJuQmxiLhA>a|?M4j@1Umu&PTqyRd@1qKb=h7Yk zFn9Eg*{SpWH>`G>y5O73%` z#y#5N@b=-A#sth7Z*-_}M4nhCkQh1_TKe2mxOU3=xk{kc!`Bd|Q5anJTN4(UYxb2I zv^;0`j#=ZYQ5X&un1SO(#2T;d59_b{u(ZrSj4Y2?Y7qig3^~FP%VMRA%@M6Z+H+pF zuAe%9i3MgHY>okEj|hyL?qpB>$EER4*avGN{!nO#lP_O4V62I~yYqR#Lom8jtn%=Zl=9xOe2 zt?$r72+Y^j0H&_v-GH6*4O25VP2qkjt_&lHwttX32y_n;IiE!;<`C5<$!^b)Jf(vf za@0WyBjA`5I1E6g`Q|oIc9amh?gnY~d;^a}*l8$Hah+^YGu8e1c@ zVp9CpuSi$9Bphtj=C7a+b(q>`Z5%txz-Fx_4pemTivtxO1tXRJ8aI)5UxnQ0b^2Yu z@s>|o;KYCoxZY{|cNpJnitIm|ke$3bm4`M57i(2;PK?0RM)AmwU;GBUZhvjCdZf9= zF{C-J38(l4gI4NaJ~^Y{)q#iWJZR|z3Gz>^^)2y|j-L^025;q$d>U)>Rx#GqZrjiYo+lA&@`XOu zwa&SGhg;*U!Ocgu>tz--VK7(}1XCduY_Kbwk6`i-I%9x8-iSfWU+aS9M$V?JTy7nUK)Lsx;l&y3+-N z!4}l;$$0|lu8N|=>j_0$rv%pf$E{2Hd=Y^OVF8%Z7mH25K9qN_%MLupbNQl)js)Vf zb#x>Ue}I;CJTJJIGyHLIO3yj^XIfLNA!N{00LhWd9YwEJ^imp@aCrK*e%mn1Fdu?% zyc0-AC%02BS00E9Szi~vGsm$9T&*MvN6i7ZbyJ*HeJ|TldDxLSc6J*I1D;|u8kRl4L|UeY69ux#)Cub zuT0z5==$=}Xj)ke3>)u_0WgX`TYbhAcvva;U6;3cWj_*Kg~7Z6bQLB_GeC@TxI5Qy zpUReomp&mkZ>nWhz}+HbUvJADxw@r6Jx&>%^qY3{^mr2qIPjdZI0lE06vM`gSpR;G z|Iu|8Gq}6o&J5Z7EC690S%z;b%OK6!>YsdQ@WngCg3=7MlHhS+apS@FeF>!4%Lf+A z36y5DGOTA!Oj>a?2!V+ZvOb_wA;-=z$ou>qgH>1hq()*eSWpXJzXjW!Pq&YFtpA|l zbLIX}?%>=LI}w=e!fnEB3I+7$32U|tQ@gumcrZ8&6YpPxhiS#uz_($+4tm!amFZrY zzFc|#$_E}vy5R^+xo|jIrlfZ3=PU1Z4GS9m-&5y5z+kYU8or!LAO!?zWY_GbeJ2Q} zk8?a2QLqPr2^LnWjx}Z9J132YS#3K9?8v|W5QD)y622=696NT)_Qvl=&k6htU&$Sd z+yP-83!_o8;oQhhwF!B7@f4NmwPxPv03c3)KnDQv2iR)u(~o{Xu`80f&%iYK@zT>r zV3(^Fu4tATE)9D5ZBr4UcdEzreFsf2%Qj*>ArEeqIUR1B7yX&=je;)Ro85E2qpILxp6i4AX2Gf;iyJ-a+~h| z{mo^C5&MUAE(~=dh))u6c^PO5DefC2J!9>0)6&QQ@B2MI+iQ<%-wA#EdtU%N*sje! z&wX0iNS*6fM|WBzqV|Dj5yj34UnT@Gzf1E4vc(?5r87)sd@l_thCyb$aOMs<6YbD{ zhxN?76YR;WHdyz=V6bTgzS~D2wH4_lC1fcSU(H#TUVLff8n{ZnDV*ev-w50vlvve2 z$7Y1{aDHko2IGiXgS=`-AZh4~>qGK6Z@;_IZI^Bjy}m~gwtlV$FzXbaj~ZWgu(y&$ z{{AT?>uN9<%*WxIZv>KOQGgF?a+t2`)Y)pAoj>J7BQQUNo^+~`Kbrrc#b4gEeGB8v zbUFruc@lgPjX=6{rT?iXw|4gO`|(-*HbR?Xkr_|+ju)zd5vu_j^-fN5;cZD^E}OFyu9)J8LFV+IC; zSp#3w0%6@QJ?2?kg?NL&S^exv!`oq~7AagR#fLxZv+_g6`t@6Lc$`32Y;5$vPK@AN zQ^1;KkChv?=#(8h)Kl+P*1*Fs#>x;@>RVOzT6up%|LfTad$`2K5d`$*Cv7YdOqj8P z4E>J1%RebaU#CuUF`3cPGK+H1~*+44ru0vX=mEQ%*q^R&Wf)-G+;gs3HvFKC&-jRs&-@I0J)|s zC!4+&%1h` zi*TQBzc4Z2z>U3MQ0H@d&I;(5gag7d5j=HtA<$=?GjAsDA9v~b!ULyY1;w<$ zs-2euKr8F$$&(iqto?k+rt{m-URgLGoFD0k{K&IqrZT-IvF=Aaeeb9HS(D(#pkFTl zG_0a&@WkY&8HzpMYQ`vyvcv)5nqNoM{8ic(r?&8Bz0i6%`aqPT-)=Y}UKs#@mc7cD zyRv+@fibmdMcL3Z$1or=uKhuF57KJIf`*Eo`KH{)`q^xY`O%|yBdwNFDQy3A+KO%J zDtnWjcD&knAN~7)c%qtFvd64Vdj<#3>gs!r(1EPGlZAcRwbjjazZPY) zfs?aFOGV}sTmceUMYsYazQY38tOs*HCrsc8R<)&H={)nXWadx8omwCFt;bY*mh@rnhbZ!L5? zi|$OIDNX3k1o{PHMjal&eCKm|K-}5h3)AAxMztceUl+2%>CwwYuuJPMb>|-QF-qgE z{{>Y0FQ6jt4cnk)>5_0m`{|Nd*|bxh=OJjFys#}T6{2=nUv|#nAAdkg9O{jNqN!0R zDEb9jdNDqsBR9U)UvE9PYVr*OCpe?l348nfDc)a0SmaYThd6GWb2|Mn8t23GDKyR( zWm6$NtTN|Nqu;L1hwoE{#72BCS$Y|9=r&=$uvQCGdFWD9mXT@U9P6fVM*Sy8D4ox@EO%tB*9q z9$T}0^Ve&d2Z=DhMzpFerL4$0vv3;YVXZoA$Ep#g7cUBPX(B^C31PyYV!OG4`)xoX z4#1JlWCEXV+0@VueHXlMqkT(WUh&4IX9!4<66G`1{i6gU><731A-^a=e2ImEBl_BdTUng%?mc;No%Qfmxa{~wjur+L-O7k5r*OW6>bSVx6N`meYaQA z<>KZFh%tm1E6NS~%MCLk#VbFL4-e5kyje@jyY%#D_VhQ1VuT#=tmrrX*!?j0ng~0H z2*G5ceeSw}JrXJ`zKr2#&ES@=N!TE~`b1HceLDiP)OzC`i$Fw)AndkRDlRVR)M zjvh%IwsiEH4SkPpHTrZ_*bLRf(DH>Bhy1R5k5;nEB6Ty~IAgM_QWB>DDwisvu_#6IMvr5vX5*;7^uq#6A z-wq%qi0^9npBYf+ElaI5`CR6ay|`B|<0v0!LB%-imXQBwLhOdRLv}mQQJS|tqeZZ5 z%bp+=$R0*KCpO_P>VIY7q{m&uFkQPz%3JHzE0|vmVP}Zf#9heo7ZeSgBmDS0C1vpQ z@-fU+yBt@gco)4!j0hMBKGQ?Z+xuXFU`gXT-ZW(b&%De_Q79$srix=R}lf9Z_Bg(q2js5$necAp0$XM3 z?E3V|dW5$2MQA1HEL5L`FMk@daO||fKKtgR^4jV*hMQbM%5S#B6dh1S2fX4vg*RJM zthI{2cKW2x+?&C;fGAeu6kSk77rbKEvHsCFpT7Fh!m0f@|DDU}7R1yq;;O9W|gIK}hJTZmKZx40K)78NOV9?IK| zn0jderihjZ65())RD*$En)a->YH_f0(yu-j5RWK!VkI)s5<%)4PSIw-LBnz8w(bwI z`oGI)bK25{C?;a=&qSL8B)j1hr>`N8RUDYtHFd)1d6f^ItbB|pW@9C?xZ*m3^fsKL z`XbHKQ&(t(ui87|Mq%go{czR@SWY}6@*|khhAP7=0B`_>zP+ZtyjR0E(ANHWC4KSh zbfn~fArb(_MtA^_!iEEQ_#%Du!HE{d$`=AA_#~c7f?a;QB!KCBJOD^q!vW;HU9&u) zCG{HjrWV!^{Xn_8sh;# zVj2!$CTE=O=*Nnh_FKa;%g1ZK+=WaYom|WUBx?)>fH`D1fEN*OlgXo>v>!=u5}bVY z%IZJQzSp$ridNn_8?qmXxhTsWRdmOj9CeU*eznEL z14i$>Z^SZrpD!YHE;PnU^gtCo@QUxJJ>PtETT)oXnnd;IN2?nHk-DD3JdKU|Hb^PM z)zKnvZ%T&Rr(4WyTaRTm2h&QB5+kt@n#~cH2$INfiZSyIJ#JKYo|(9T?hz5XXiExI zG)CEl8D6L|A3PH+;bFHXFWWJ!=){<6pPcp^aVrKtLICb#gB%;38$jL}uH@q%YU0&Z zwteWal)A2Dz$sEQGQ=li>^h*m3Z#bN6e*9~=R^gmMT`&9-fFgd(!6S<#A=)($}UI- z!zr%zx~Dd$YgU>ANoCdtg~7cbNiSCrQ$@`$mFFd{wA5!jALU2jN%CUTs zM=9c4(LHdG5~*Dnq{L@Dq=R{Q%SMZ7bv2yZx?hKk`3h%^!wMLrWHJ{DDft->xx$5T zQ&L24C~$ zPGu?0SOUYUYB{vKIik)Fa@1w( zPws<VhC23#aH8GPQA%(@N5fg>%-tshRod6{47p z`L3fkT2XJjVsNwd-Ah5GFC3??O4AK^s8|CX%>u0>2c6kL&K0giQic1Js-@59U!Sk- zztF{o2}^9mW<3r%`hhGfoT8KbtOW%z4+|)}`W(!%-yit{DG{%Tj(#Ao3a9wSs%b{; zMe{{*xhX~b=)SseyuE~x!|@W=5oA)~6q{C#J=xEkX*MY7tKqw(n&4Wb#JAW`;)ITV zAa@F}{)j4Fa`DV*Z##o;GB&SC<4FmyD`ry8uNF6iRVkNqwrn=%4 zqqTl4O}exGRe!yX#Ccq6?K&7rW0R3H>T)2@30Gpj95*GV!oj+!?^nR$ykfDTAv^jBXNxO&FE81>N z*39*mXYvunwiRg8anYUxa*}Y0Ydhr}90N7g`lv?tIIQL4ejibMyAV_KL@oBjD-K#7 zb>Eily|CDO?w2#%C83vL(_tYG5A|!1cZ4hPh3$xpm4}mdvWAR4SAIJp#2*G**f7IG zCuOk5f>S*CEb-px$7TI?ZTFZRoO5VT1Hy6S2Gmp@>enE*2&d>UNMRWFcJbnizScML z!dD)K!F4sZMC74kFvuptDQ-CWdaFf8@#R+u^UBY%ay3hlI-XjIm52^(Ab$v_Xn)qH zsA*C`O~&y(t<1e=tiXtJMVkiX`rs5f<}}LEk(sKu_0JmVJ^vI9>l?5H zEzu1fk3n`1PI3H)rdr;i_|zqjR3u9_(=^ zn7?2R++m7XfR0tdtQ|2)NCpp1d1RY&-UX)T*t?F_^)oaQ8lWe&5z!bJ=GUO=;C;dQ z%kic6n=}4h#!7R==pj4w*7NK_QlZ(V5&)JqcmQzE2hM{1=T00k>65eI(&KB_W*1NX z@Btazi?ROdh8Zt0LL_Ul&flD5b$*4_eZIws7j7{A>>P{|#z)5_kcxvVv8zc>@54Y> z?VH=ey_cMM$O=JBK8{V9d^Caq$u~Gf9aG)AeAjI`v}H~WI+^QAcOZ(}u`LDx8f<}d z8=T^!S1r%3&Dni-xu9ReAnoVNt|5w%Sbr6uV-iTP!6_=Ylr zrOJLfx#u2vAA!B+B{u2{Hlpeq@rnVDANDDp|9xU-T+a%9TWWP0QhFK|1_{vK0}^F$ zW*^$$l+yp|p}no)0n_Y1EDwiEvNUWA7NDa(NR7cMUU8Z<{c(TCs)Uc#`4i`@YUn^p ztesE1B$}{sDJ!VWxEn`sP~VOe+sAV*EpXyL@33qSxBdbns(z?n3D6i0;jRjZY%Mis;HVz+?^EO+lH$0lx3Fm=Rm_xdwEejG?aEc?G4Z&l^+48%m{wr|3QqM1m0Ymsph0JO_V6xd`Q_Gs=9d9-Ak^;iw)5_j%JCN55;(_WTSZcr!eEe+*&8@3DUoZx(fm(6bXalYWxr6Z>CX_z zQhCfu$;1p4Qt~t2%H{I*ch+2Jo7s^#X`XY3uNK@RE5<=eredIwlArOAv3{zSjwY(J z{h9lF{un>?7>w{EvE>(SB_qHP>|Ca&(v!U zD@OWL@_k)m6gXr@p54J;$Syjt9CCVsTixqh`4)yVT+8K6PQmm4-9+L^q0(=!R2ON7 zTe9Z7A*j6O7V^mDZ5M0c(M75-g=%ZNQ(15FyO_Q22pb(Hygt^GNa$JFMkWw?kib8R z!heo(HZhsbTxSkT*U^E`^%giXJe)anPYQ)a8j-&xJvoX(j*C^FwuqcRp77T%`9yGs ziw4*r;k$B}8pu^Jq9+SAkQ>rnXj~0dIts z!EHf3_HsFNV^bg!4Eq)=cM>EWQBz*^@vZ43`V1ySlm?b7=wrc#qwY z5X=z%E4aNT1o;=_8!-Y+dJ(-f_0Mh{0=Mh4_<&b?;jKCLz)E{2Ym+^V&u|2fK#4B- z0ZB0e4+k0_xlvx4_Fv@c0LLKo81nzI_Z(nNY|UoDUbwOMj$I(V*ik`6P^{Q*fBN`+e`d&-c8zGt8WsGiPSb zoEe}P&~ET26aC{#F{&TS>3!+=rfKVj$+py(e`6Sn?eG)oq6~KbO%zu7p_T&8ri> z)30xtF}3QXqm$de@nREy!rJF_bDQ_Hd2vmP(-pDw)H1l-(Rq#0Ydj3c8iTa)tQ2*m z77P&!1l!MO2#1a6CNUJvHxXwJmt;Y1*<(O zZXjw**&1=c9lefW7D*4#s?m*W-K?gcnzm|)RvoIAn}4|hoe|+=uR`~Ln8PZ9KPAyW zuEe~%NxAzg4XTB0#Z&5znl(P6G@JMn)=A1nymb_!h;9=Xt5GX}$u`+N3TFJ@#m_>m zcN|zl^boO-Bz;AwE_5|Vm!kmF-=zo)gE91C5g0b2Q1Ey>v4STQC?tFZVjp6SD8XDk zpjc{H;|B&c^ZYq}`Z%po9fNqY4-6S{|7*_4psM|Ji)(136QH?HKK(+2G$A69%B2Fi zNWn$q2$&cRDYd0Z)1B$7%LDnzN2OXYG7n0bv`Nrg@eDoDYYLZi7n z(hn@BKi9sX0lRvxUplB@c;wdi_Yb!kpu%cqFSfv!fh#W^+yc!u43r8Y)9*{H#E9o{Fwfn4l(fUW7%%q%|*H{Tqs`t=}W#6lG@j(_e*U6`JjEkJ7lu8g#tpLk~ zDzQkwlfVdH3aknbfq};HaBGId=mw~Hey9=|{Gt#IXwwL&!;PmM7w^1t zz24A-jY0FkkN^vXxbKLgpj>STsT`=C7?$%9u1YCTDpaskz>#pdFgR0$BDoMp6k3js z=q=U`h!`v3AD8m|(QHq`mWJv#ea}1%sQ}G){`Dss=7f(Z_TgLYo}8MIarWn?OJUFwHz0H@AFLGe zB_bt9BI2rGCCpdC5|}Gih!q?$Um`&yxU~c)ht{A*<1&+Z!O)m8qHv34zc%ctrQ1+T zs(7&gN_F-vt)q>A<+4S@?(Addz%gj^s(lyU_h5lF=nrBWzR0Sm3- z63!1(L~4B|0p`%61S3k+{$O`@$kZ>TOHN!a7@zSY5MB~^3}k<(0KTU|wn8CLNflr( zDHRF{2T&_g2o)+0S1JImm|QBxtuNuX6R4e3c73@A8)tu8`05rr@w~PZw9wV}zi1H2 zQ_6XOHkc#la=3h@KnlDZn9mn*_+qh8!ND7I4H5|}68#KuvFJstpUGgy8PysCSY4bp z>|WQf?f41o^qjp<-km&oWg4`aA}Af}DV9rs_<=XU6H634kpMWha&Q9ir78|Ep)g)8 zG&(dYBGP%h=eRf8gT-cUnVOpTZuR#SPzu?1bPh)$S1FMQ#3CSKp@hTX3*|z&k|P(R z6bWF$rn31jM7mlG?X@#-SiRFr*k08>XBNK>@^e&S^!wyTNV5K+;SPXLoKnD?6 zAd)Cyo}4S;gPn!9n_!4|qC$h{(ccSxC2sGGI(UaID9>3rzf|Hw$-WY|q500greiH7 zBH*b4>nN7;K(};0PX&XZMa~r?A|Y5%2_Ls%6mbTlE{2S}ahr!`rwl7|xWkb{xs96L zoD8Kp`}P@~jlu(FN2HX(2uG|0?hepBiJT{qaD@V3;bFWfH|-3tYB-N)SjMpu?Q0KP z1GmiGJ*ZZjUeGL(&py*2NiGo!5QHO?0Fx~Qdl!u10^62{2oVtQakzK`u2F*@q9XOv zfTS9lfd$ct$e(9-V(<7bRouREyxpf3fzZO_=wxWAI~Y2y8BjZLrl5X}g0JH9cnYbQ zqmqE-gki3TqrzK5`!7ZX9D^n>iPZ9gei~miYtS!9nlbCz+ZpYkWp07!I2j;QC6$Xn z_zV_PE&`DOU&@gR5U`IGa-N8T_k!%d8Dy?NR?R>pcE;3pQOVZ@Ad`Y$s^FomKbnbgZjbA_mTrhzGnV zImi?Mzk~(!U6_G4A`CNGz_Y$BaD|O zQ33Z@ECu->t_oOurJN%~IN)#se^mkR$;k?XS7s&(Wb<8dm7^&A2rreQTQ?&@#6`bdChELZsp<5V=S!2U|)3 zPI{#j*jtelM3-`KM&QkI z^S<%GN4=`TwNlR(mRwhX2d$(8_>P9d0%#Tr$7W*6cZ;G!}%ps48HDiw198Z}#3ra5K$Ltbj|bvn^t6{t`3e~Cs3>5)(&F9Y zLd&oRt2vV%H03qyv%FTJ1`iHFbI8A>6B!8*z5?tY9&qkNT)t2U%f-Oe=gEZ%kUkWP z@O#}<1Q4qOJr;Bh@njQa?UY)R;=e5xbyu9*lT-Q7n;*LCQnK5g~{Im`{#EBoN@qRp`LhG3%r$&h%yr5{E}@ z%nCX3RUkDdRpH$W>-D(RpCt(O=!Aw1zLgo!rvBzerEhkaT?AU>65s_5G9@5n zQz^i~!sAPTxds__iI~rm^Z7i1m>FZj( z5&5&Z9|y1MH}%)jOlZFIub}6;bcJ~!Dg=MQ>zPKUfHiVGNbD(KgE0oyqPK=bN(Y<{3%UPs$FGC8K8?8C zGdu@cP63QgUPumH1&IPpyGW!U-^Z88IZBWj5&{oLD3q)4B97IA^MFX==C|iloA&V1 zS8NnI_e9M`OQBgLpV3K-sz44vA`~dW4iNG{4S+<9fbbP$d8Hu0;tKG$U>HBZ8m0in z>)Rv3OW!=FqC}}qP>1@KfKtf5qq9zYsay%0F1q+ag^(|l2t{J95L|ol1S*wMfp=N) z{|2p$C9hA(ZVb&L`HYUQ#}}!<#VRmld=a>c2KPrCjzX#8fkO+_ zA^ItS1M_uYH{PAnvk*AZfKyzt|92`TP`^L zVX;6UR&ar2K{}ZOGJZUvSiq6}!8YF7&Dd`KVEx9u@#I`JDi>MsHUq!d=No^5STAT039Iz&BeQ!8nwY_u9P&N_vq&IX3Os(?RV_Ip**`y-G1ar!%%Q9 zK=K`(gI)l3OQ7T7<3xopaESoIqIcjd~0qz zz2w@}H)ns=EK_?Fw8$kuD4qL@yr>*)~W>gH{I5Sv&YM8`hlVeJo_So%XpCV5fX z!zNbt&~c&jq=1J_tlyy%I_5!@4x3n{^Pl?t|GXH8O{@i?qk?%+^TQ^V{LnEAd0W}T zCKmS4IbZ&9)ef6jv_r=i$fNQcHnBQ~&ecs`R^YIS1vqpJQ=ZhYx4eBKs-vWfMd9z+VAP&zN` zOxeUTQ#t`;-dB;biAAJz)+H~iL)paQP>-nnWD`q2>G*AVQq0LF)^gIxh~`1XrbEFd zojshlg_#a@nRIMyo)%rQi8YsW)FMwRDjfX1z=I`jk@=veZ+EpB8J zYa8j*G5n*#MTfdYI(9QpsuUfH6zNnb5 zV2_T+l83c<4yAc?Hbfqk-Z^-*bWWvzR9)v#Tt`O%|8XguLnR%Z6DjX%=GerNIriW8 z56wFNOxiei+}pAh3L6(fDayE*n8Z%jVVgJN(6(=q@2C<1hVjXhc zBhB0kFWmf?IUH6*gVJhc80e*;LJUSXtqi^XEyS$HBm~2;X!l>ES_S$V`Kx2VY=QRL zK&=wUv5gvZB>-=95<7u6Z>HyOU66rsfd2O2E8o^=TQMzo2<5BRf}Sg|Mm-oY^~Uq% z`f?rmcCw&kbDulw8W_C36P^Lk(+o@3JW#Z5T2gDeZ{=V%xfeQN0#z{j{w?3n+!`JBVlt|1~n%*^#r8<^<_e#LtzVuAk~s&e04^k2Pz% zb+rvFV!;VL>MZD#GAg1D*6A&qjZ~a02dQs0HRC;1j(lNR?A#rPg8Q6!ck@rb^uD3Z znpJt9iOvoE3mr9`m{cS6@W}P;iY9K_v8-UR{b;MreEood$^QcUd4T?LWni?t3bWG= zbq}b=>tN`8VZf0hY~oK?IV9UP5{fuSGec@1$xK zr-%lvHqkz~>?xp+rXEp-!+JQzP=a;(H<|J6ib3O|kLX+Y}>u0Eqs(Kj=(s`7F6(V7K-?f@ERcL%X$a6V!7t?)SuiUWMS>P*B|7 z+SC}h1nW*-FzOpdMC^j~J+4Xej|ERH!F1}FusDrT4HyK+Qe+%>9oi)hG_5T<9}n%& z&$#e-00Pbe18cVJIJUIZG`0R@rJxU-Y(1P4!E%7FS<@pmIytQAny58KAx5>rz*=eQ zlnZ`2`aRgG;KQ!wezl!qLBCA(U~^05&3Jl<>)?+zcWsMk&AmNMEU-4X0WtS`O|($W z%5?L2oB`2W*Qx`8#0CR;SvzR};T9OzD)!1hI`n`bEUu5~_ycWW(Zxnpot4BP@p)KD zT(X~z;*x$mitFTS9yt;|`HuzUKNgbxIEfT>5-H{+Qp8E*ctxbYO-%Yz3F%LzBtHc| znqJs&y#ELOj_vH6BNGefpNLxh{BO|)%X7e=Y3LtUR{#FhL)%x)l#bfmbjFc44~8GE z&nEtab(pgK=mDHA;4C0rL7QVLrvKl<445W&{)u&k^iF;-ZN;;IICc%-hmcM(Cm4NoEyqTait(8FQzl;WNqH%r9p?~HB zgI^)DI<*$b4brQP;Jg4<3$s80;6uCj3*2}Ra~RPM-R$M5)xQ6_*{a#r=MRq*+4#Nu zk8P+6CNT;25)iCcd+;X^{o_ioL6z1I;DvX8R-tnKPiYTJ1s7)%f5JLXS+EwJGoSdD zl`}-3Z0X$!`hW3T3M89fl3_=UjwgSonR@BkC|3qhti2sT_S z;y+k%g1v?5e-B+D^oOFi`3<-|F9W2Y0~V}do?V43)Z#@EV1f2CTMR!dv?;1$v3n~H zG$}ImU2^Kgku~Z~n)rOmc2uMOL^aB*BcJ8HekS-c3H{?rqYf0Tz2xr=!+U2pF1O07 zmALy~1=z$Nu`W_jDbOOpKUA%a2AjduLLIPaiA1|tTXwrus{hUJsWcY#y?7;9*%a6U zK2*FK#Nz&eD2ypH;KGHSYQpSq5tR2dlYR2za`~XSjgXUy{%fF8Y3l6?YfK>p0ydkW zXfkY$?L%O_=~t9s?RN0$EmfTMn8~udRv4FL*@e*aHxA>J_ z6G3ZN1Wfx-AjD55+5Sc8HA$;OlO{mkhN9EValD}&pda+TDM1>Rp{bd8FsA_4S~4>j z6*2jzAV~v~1{NF+IhUpQ-(f{%1~T~ja!RnaIxd#OFYRHbzzl|_ejI*Ly1QTGj}Fi1 z2-e7ZtSK;C;}*bdzm$-B)T%g*27`K|Th!(cP@moeHWfX1OjP;9vC-=&f|~-!gCyGk zyL`BnGg~Oj+!)_ZCdr{##&vDqv2AG3dbhvWvNu}mln5GMLzE#*Y=U#0lMIg40U)K< z$|{Y~fcJ?&A3Ld3U_u5f8T{2WxWi1Vp*U-*5sc$8Z7h`3GLVDllMAeS!OCyYvpP9y z5;0X_P=G@nWEa841*2*LEjdRNv2S=_>kff!gWAZ#0z0-34(i&i>-6wio8#VIWP7n# z33^u3e}cV)_|Eg&vv%(CVtI$M3ZcO#x*|qa$jLK6Om6Atq@nU%aX3&Wnksw2BWbr})f&hy(3@}fW0lz)Kn%WJp z{r1)t7{ElnXth>pWcg8r?EpS+k`Oyw&*D%d*Vp>nfX15s2h1h`OXY*Eyg$0~{y`vj zg#E`@Bdd7(j@^Q~gax%}AJ{FZD^M;W#ova~=i8=zm!Q_&I(6x#2;Eptll6JEd4U_! z!11GTxZ&{EB`Z+K*jPY7WpkGYAYp5(C4+xZOsp{x)rM5vk+ZAr{K+$aJ;ewVI?!NN zDDMfa0=ovu0>eAZ1xW?4t*l2FnpQC7F1#j#e+Wi(uD#OWH4FSl7|5r`z#7{Z&=l}P zkSGCNsK6&s(Rt`$7!0P@fRiK9nq@`JnSnJOhV@p5-kh76PdFc~`7UtwLA&tti7cmL z02pT#V9gjAtQzIV7g+!5KLFNyvyYGSo4EN@v9t1sJ=2$rOX%$NPtZAFW1o6mBRTir z`d+8~!(Lt)IrZ2gAiY??qtcdV0#7VhvA-wG6{|@43}pkOJ#4% zKG;8Z!l`rLOTHZeZKS{@7R4<_*^J@4m17;h5>KwzIyyez?Xl(W4gIwcT5IFbE%a>< zWDdLd-t63LLESI2*7RN2tJH%?neQxUog413;LNHhSbYP!>&!b4wBADWGL;@|Ne!aH zs%W40)jDKw7whi!|EpkDyH>?8DoPE-eWs;I&Zb@+8HMFjwlkj`+FNQ!1LK=fUHvYE zL7T9mq=Ms)Co!6!Hp+}TqA+`ey`S5*Qu*(F8cw|0Zhe(Y(0XS~lEL5gKn96oob*h1 z=-KIBwPfRX(Pf5rhM)~@IK(4hScXPD7;@_7WSlfDWc99U2lcmeH%;Fu+5H_WL-+6u z%g_mdShMKOo|Y=UHRkBBzSmakW_q>M^u)@L0s_X)M5?~cvWb;i>*T3}My)xTJMq(p z@#Zs;8Z={Pq6_ly()(lA&!9`8tH-o?z5Gz>?CF*>ks|m-rc8{LK7$sNWXNGX-W%0~ zUTA%`ep3C;yShzXSccOOT8df~S1^}6h7r7U%AD{?9Wz;#Gip)Q7rVUAC4dQrWSn4u zUNXiCIz!eZ3MHDs1mlB2I1UDXY7wq13W1eCM&QSm?#LLg`cnEh`RjrYHhC`ZkyI`a>iiy%sa>Cfz0zkB=DR+;vL2xM9zGD91jA zR=eN|3woJJw$LjcomK|=iXt*o5Q(wF=`$aE9FwwTS-u^Lne)Aut%cI8965(#?%V|G zgCh$>Kp0;1uQs+w@4n(gx%Q);O}llgtmWKv1;m`I2B;zrSP8LxvnvNfN)J`?);zEC zXl3dRojH9WqXy1csN|eJd@Se99xJ&Wxg(@iF@w*(BkMO$ZfFjbsKVc1a$jNPM;42F zvv1b>m{qE->X-M%y~iTIii<*Pth>t{>`f12j3~D9UWX@aeF$wh{Auap&?7nHp>!9V z;ei>HnUlyAm(~8e*z^vEQ$njvx%;x!#*ODES!L!PmO+_0Ar5;4d9zcY+()k~on5xL z+Sg@&Zid%bWkvy*K|6_3hfZ{nX>?$+u)J*7=$MWIbsl>@d9D3LX4=mV>rqy+wq zsoiFp8H2fU0TASn4&0y5ww;^=hf=;m~*aJwZaPuvnDF{Ec$Y*UV~a8&<^WI z*xMTls2(xSHaNy8(CN+Ivz&eXTl<8bocRSGZR@vv7LC$JlLX2(|-_lD@K~%Gw$+?zurE3^xXT~OC+fo zw9Trvv=A|NVw&{M!m@KN5#GBhTQ9%M=+tBPY}vZFedZIB3hYCsWobHCY{GQT;(_Z6 z*B!rDY1pvDVfUZaSDc5oUTz-J)&-NvwJ`Z zn0eNs)Um`<6SEKh`V5y}6w13d^LX-+U1v3I2&}mRW?V&W+Np3wrZ;=QnSFsH+H*!7 zO`UUM+=xr5con6F1!KDT;4$t+T2ahsC;hhIQ)wh}f0B`luBtW!V8n>{YoA0E#VAd%X#=R-r)+8KG=-Gp@;_cq0oT~8YmTz?OgfrXMA3lforYIv~?C#lo zl$xS#;6f63#qc@5M(|W_M3s;E8vI(a^6%Xu^W8HwXolr!WiC!@J8+!ynJ7B|6<$*` z-KZa(JY7_<3|5{r5HXgUuuH^^XEg_^{?~zX=e<+ww_?@Zh|7XC$Q(*^Z2y3 zL;kg`7IpPI-u&$3?Thm{u;&W=GqZ;*s%JRMLBr`Nd9}lU&0Cu6+_nDQ=k_7I{LmrH zLHqlN8Fs>467IrB@Md@I|Mh;m0&^PmAAI3Ng@S|GI4A6P(LVMt{cz!Yl<)F**Y{D? zsx|TN@MGwKGJBz|b|2J%eW!RljbW#*gEt#t-M)LRCHv^BCAaI%3;Yz}l3}NK7)`#) zVjLtxIIvJNjX9j}`wpEyA-=idb85ZD8=|=*?8#S}s64=~yU9iN7!(n3w`W{TffwJ> z8ZFfgBiePB;2y%BQ?2u6zY9z$zx8wZu7eXJR@W{%_XZhzPQl+WZ|5P}~+P6LQOo3*^?hoU!1c7w^vzgQ8Drp}lzfL=)jF4_*SxIYn52on^cV?w&sN zj;M6-!KlvlK0~`HE&v(27fi4ZM61*LY0Gsfm#I^B1V**0;MtF`K(3aMo?;rk@wt~QPsP?8RzqTzgGZUd|pWi zyd-z4JkHQDV(!fJ#`C%8Wr;FT3&*GxG9|2!26t&H7&L!Evx24>+~A5-pC~f|M;@~P z>9?L%z196r%FP}b8OtkPxeM+6M+o0Bx8L0_fdK)nA;8i&EW(}W!ddav>*k+3vbSPG zy=4a>wATTu2EUDykxOIeG)Dnjs6p)^NE#CqV1LV3vX4hwtQs*YtB&8((x;)!-$27i zHqaHFTB8gc_(-H)7pGNX)Lk8Uf8@HO0riuPRammXR}c+tp^xRYXX&`9D}_a;WlFUH zeKRc6X*G!$wojJHTAlwxzNE{n4h7*=m7hU-oU`p7-*eAd04gSKalgtLii^c2WH$O< zx>4HOBG689=H26Bq>`Efu}%%!oTsh1Lo&K`*?C}82(t6A6593q*cf?jO-il{YnG2+ zM!?@+VfcmU!ZZI?cdQI$(8It;X^0aNo!PKL4+4A&YaUPO{!8CB;=%<#Xag+-jARl> zDRggXyx9pob)|<@XqqV>zUwV-RGqHSj^9MZ{E4hbRI*rDgBU^8n$=O$B5@!()o^(j zV_k7T{>z6RZ0jD=pes{qZ(ZNwmz*qFW?S!b}?u?n_U4$x|QlZEY-02TtR16!=|Ejn#VNQ zwWDF)y>zkZ>|}bg7tHB>JSFGPz1e5<^*^K!X+&@@DPi$wWhgkfds*Eep#f@~7*^Y+6L5|Sz1Qo9Lc29RriQ`^=us|?6qIJ?EM96a`U&){WsXhT5P}Jp*4?9+b8J%Wb!c1 zl_%eRgMB-?{{;IO57C>Q^2e%tZ0$16_KvOjUWvO4(q|uo?!Upl-4uJXzijCf^L29T zsY6RnNc&~X?(!S#+tD$f_@S`(?c{p1Z~d`&?B3e*j*l4msaVhYV~P?IKeVv@Cz!V% zOWy1{tD5U-`bppYJ?O7y)31EqLZ5j%w*Q3UV?0c6wxQL-`y;N8eUQ7OPtw$^)ByU5 zk3sjJU?1agdb3Lx{rtK3&hgWZtS-oX*ZIIn`s`!S{WsXhZv28F+*yzJ{@Hl&=7&Mt zxy=o~!M+{ce}jGdX7y(O%s+L)A?4rW>s2lIx!k$fSHHo&9o>I}eY=P1&CUwGoU-g= ztxEdboVE#NvNXTJz8xJSty4_dUF$PYxh}y{qG7(o#<=u1Hr!g+GAOX`q><_UHvRo1 z4q8PG@(g2lS5~ILd<9&s99LKR>g5_&l9xA;-W#$aVjQ#p#|i%P3yhPm26yP7k_J~r zk)SU5Wb>27K7+>hyH`3bGYDFOW5E%GLDjOqf<{MOXy8N#)v8u$X3n?PjbAixz%3h6 zr+ctfwcJ56cXx!Ae!vC;XiE*AgMl}Gwgq?KO?0k7&?&jr%aMwE8+9(eVbl~1EIClp&9A#Y9kNVEmNt7BW2)W9~cwi zz#{9ju>HoA>fE)b`k$_S*ZV%Si7pQ2GR&q2-R9CeIcQI4F3&J?C^LY^FzDn_jFFc> zAAR>1&VI4J)%UNN#!}#+nw?duSUiGRdo7A{X2Xicg~rc5#wxYz^5UMwvJN^j>mCau zotTL-0sU0a4u#G+U0!LJrq`&ilh&l%zVV^Ml$y{+nkcR@cM1YCWT_<7tHGEU$L(2Y zrG5)scK~<#mbbIUaF<3yVB#cNf9D2}x#|ihl#%Vn9Yw#~zS*)?^}g>e)eRJW9CT7zx zJcUlq$j7JF41~`NGfp`dK?k$Am+r_Ub61OC)vEVzU%HR z=>>^Wpw$#XiG$1jC$l8*v^g;-dmnEd`}gSlTOQ_{_Udi>hz8Jd3Sb_j+l<2Bv6i=n9B3{f8R^G^S#%HwSz;oz;@QEC z7Ol?*-zoN2m(!a@v?@Gu?iOebRak~CAR6Eioo9?9)|;_0?buo`p?2T#lTY3#dSfl1 zOHhVQ21=U~3%ERP{M7SrSnqEfPhI$f^Y$**WH<%$0Cq@C8JGxEapt44C0?q2{y17Z zW>dQ-M0QBQ7-=Vq-w~wSs9W6!i9vB=0y)J`-Y7hD%p+)-Tc8JwdhgVq#uQDzT)#%C zt8H)mcpO`5^8WJBW*ci%kuX;xf%@bmR64B`e{^hg#XCp(P7RJIu%+FsPJde}Lg=Ak z)-sydbx|Ac6T}Ko7r0SWaw_P>*&i_#FqY9ZD6_}2g*Io^;EUk0W%6B`RHkiEc$;-| z)>Ok}D_ue|o9!}@My39{_v%wOF4y1Lq3?_np<8PtUc+R&DB@r?BBS&O4~~i1AzY=X zuAcd}>fFd@nV5)-0z9*+13ZCF?MvO6ygrYP?%%g_)PZdyKYn_INgYtaz^oL((;zv{ zJ0Z)C6iBPP!FNEh&PQ`DPVYLf`BRJ(DZn$kA8n0@O!o&a+{^q)YZl9>_>_?7-`*MJGoIonxsMGkxZgROC_jJ-`Vh;H-5n8^ZD!hKwxyTC6`A7kB2Z! z%$krfyz6+O;fH$F9QY(;^pNp2Uiy+T>>dxZ(K?l_T50p4&6mp-ANKv1ce4^dHeJO; z>+Zpsd*+RLV_=jqn22h=;O>zfT9I$4b19Ea+A_goR)Sx<4$8ufmtb%v-5jd zo_YT+LPjQa*!G?aAFtY-dEdvDE~->_DK&bwv3oBl%{>&ep;Z*PO2=e0F_C=YQT@Ui zy20fOwypCca^uA}n9#}@5VN6`DKCc2kvUbz(O2{j9}IqWo()x8*7)Y&!kEyCDw4O1 zMv+=LUL9#}Cu5qihTbR)QX8W{<9($X4Cn?IK4e+KI?YS3&#E5&VqLvc3)3H5uL`ih`09hZFHFR5WH zUoLTPN6gJOWh~746htz~_IB(0n?e@WDN=oXf8p51+t1y__!REJnT_Fy^kMZ5Bgbv` zL=y_7l{$GdU-|f(eVXpZ#Bh`_FdM@WNhD2Y=2i&Z$PG?B)^y?C3*~3{zrn{GTFauGs?NFg2|Nc3+d7Ok=K!bboZ+wT`{gc&gi|;-@Xm7U-j5WYmF8 zR|T z>nb+?qYCCAau3d|j-1$g*{9Q*zq`Re1a$(4C?n&&LJs>{GcFqE+{tf*#LM!_1LB}?eQR#7)g3gmm7NwDfU)YXRP{pp1>bI_?+w~-EbE`P2yPXo_YMw2QQLXA;zF<{6MdhLR-sYB1@&Z+jHxbVB6 zPnV+2&n7@CZ2p@IIFGQV7=|1L_jr}M#;fvMca6BVK|ieczWx~3&5mJ$BRF&=zn4DV4nrmHr2WL22=6m9LzJ=F&%mYcKS#juA0?m)%CmQOUZWL zN~=V|jw2Yew+u#D4u-;_PxpvhNi-&;_>w;rbw@`wFaAdS>=@>j!5I*<`-ngl@IC=s zpcVvsUXPkl|9Hfh+%}bubxBH|)ae{%AGrr-R`E>qIdLWLdRN&uqs;8cI`ZfD9-R2V z!YH0|FlLWt2f9e*_3pa=p6ExN((iuAF25{(H5YRCMH0F0FZF zoO$=#Vij?3kpOwX-m+6gDy!&Km8OL)NIul7_J^Nsl-o8C_m)d=X7gbt(yZwP3hxh_ z{`f9q_f{0(nXTKl6KKAbAqw#7 zuyEE{(YD0F1&*}pR-$_nrf%CcD6=n+?6i?S=eBaC$AirS@c`~^UZeFDzxh%HX@;bfVtsM=p7113gDT0EZXG8#TFfU6Zugt zE;{AuTUCq0X>|)*hCk6o#BA*$3Cm74X~SbBAKX13*^oE#t7L$@RAWr-Ayp*Iw%H(| zl60H){JZqJM0Mv6Uz1x)Vxs$h#I)I}L&cu-`E zI>Jues+*VjyDMPx|W&JA6-l z@r_z)EW_0CFnQZ!9nh$V(;GnLG%*0U*S5gthhfLw{2ITyb>rT3H`#7`T*5KgB*;pb zQXOx)LML)`&cDO;BFmRN;|IJ@KWux9{`)+k%y?S1Emh?`{~5%BL`ETm(nJ082A2Y)G;#kb%%w?f>_Khvyy4{=P}9~ zo#65a*P_zV_C0q!iQICgIPp<`a>zdC%*=zV%yB|Lp( z9~i9Hq)aV|67((`%l+Q^=!QztZ`FJYj;aLhw?4c2eXLBTZ%Cu6#+JUJg@?JJW^PlAm8>sOUFNpamdS7OGgI{laIp)bYdQ;V0HM= z+I|66%m&@%CQj8$b8ZAB&FF3Prw^53`jkQO4m3yA;Eyi+Y~n+d@O159sL^ zqMj79BtEyW!!D(QhRH%u5}BCTMKiw`1s?VGP@zG{nYWvZ1y1{`WaM32At)tyPe^}a z1QDZCB9`4sc!D*gP~zdJW1@MzD_5yItE}LLL;8~f7AD;WqaIxE8^Kj-q}c%^yVozz zX>j-FyWM5hMP<|pt5mMI&24ZG%;aUhl{zQoIaR)vSMTq?G&$x)xq;AFd8q9&-z6NA zC4*MNu=OTn@>+Xy#>2=>6x$Gw)bdY@dSC=n02D53|j;Bt#7*=qyo-lEec8>rBO$|Bd6!EGv-a*^|MOB@F`ob*lJNI zVqjW^HYUx|1NTUJSR08w?@w1bRAbTCQkISEMWvz7{$Xu))eiBoJ&Tt=^7lPG6(75E; zwy_azAenp|ZzIig@De%7nc8DU^N*8HwOOLfxlwOme%s@CS71y=>SnrhYEZf3dWU$k zmvILDF*oGe{!#_1Mz1P&{4ZOiP8kQ2p(~L{C;nD)?duDD8uXcdcEX84N&9=(u!XLa z;F-*z5eX#K&szDOJPP(JvNWv0&>LwZXBD(%&?rEkV(@YcB@aJ@+?&1Cd*!X$`>S0E z4!e?g`q{Or&^)t~8RPgd(veBU_Xh&>PV9WW;+U=KkS;2w zy-I?d$>bZexTWD@+Fth0+-(={%QGTyUZq=jCSUrJ2*ZgyFZJo$AuHuEzjjXH*VAW* zb+EnkrHaCX_N%*L5~bADd0Pv#uiG=I?AeC1ek^ykUtQy2I{%DOJQJa0nTK;R@fpvT zC3|%&ka9FUARz&le|C?6=>#p2Leiip`9Ouo)h~ug2d3VfUwQf43|xYi0)|%%2Sy-Y zgsVS8?@sKDl6m7x5^jI%b8Ae!=ap{Hdiu6_CbS!KsM1Bpv>yxTwI-OHn5L-l;cIlK zf7}=(?Rlrz->bwpKh_;M(-|~foKXYjs#&J35gdmdb4J%b;?-RS2e1b%&f9u^Sf(}d&enQofw=+xi zX^P9wP{QFUvUBWu?9HxhxFm=6Y#7n7)%OSS=Ot}PW#ulb`>5xi*wN2BVamsGErzUBW4eTq(UHSW6RDvcg_qlT$^$_j6LZcE_iYa z&vaDbj6iEX0F%P$@#f{I!WY7V$G$G`=F@whF1V^KKx`p7WF z4(@}98s6=)S7eS&Z+hWD?4)n~=irVEN;nuvJu3C^AXu(J{Nj0BQ+qkIE4{s&3}!zj zO)0ed@QLUXbKc$>^0WTV!_XS4u#AMgc;c+3ww88A)_=sX7kpZhkpFT4o}|E&iXDEA zuL)&XKQb?kI}D7xa>bK~8VXE+ZkvKjD$cZ!f!nLz{cz>&9qx>CHET71vVI#GBQXYs zT0W|{*imC<1B4Oo!{t3^Uun})8C?3Bw)kXKQ)nFxa7LbO5$SU_&`%eE{ zocpYJt%DPMpF*2yBVpPEnIvgC3P^Rf>Dku_r8UIDdIZcECuQKpLdz+DG0%=6N;im%om%xelpOLXrmy~@UkShW2Q>tC$iW!7Gqx?W z5;3SFwKB8f)D$?<#3_Bzi+@ zsY5doCK1WA8VMPah%Fy4G%kC{fvDv2U+>;%vmz}a0$NE4kdf2{kun1q_ZN-&ounJ= z@Z$!7om4FjP3+L*dbr4V6AWf6m`j9y&l*?lrx!JgZ^Kh0Hcn|{pSxYX*cy{ zw~mVj2k(uZZ1+vv!7^*)0b>dcf{M(Mr!K`W-uvLc_r#me{56IVd{Dn@6PR-_X7`qf zE*(Zh%2yRSAdMGUNn*@*P#y>tU|(Z6(0I+a2D@a zGhv^!88c$V2l1-s3idJ+cePj@0)d;U&{`3ND55cf+L7>wU_-5IC0Lhd#q6!OU@?^D z9*WU06y4-FX22DtLahf|3&Yirn%{4oeD_DjvDb&X+&g;nf;|kS0PZ=mLLX*exT+c= zomH;zl8|5BH>Io@Uh#<&S>d1<-%+NrXp`2F3F^d3VeyEUaHP>lx-4rU1{#Ef8+=J22?5&yr#* zP4yWRCNGn}Mazq?SAu7vv=A_FNbD?{9zi)U$T}#STB=T=ufO^&8&mwj-B|=f;u@Th zQe>SAPuCwG`or_$pk;1>7|rIRE+WO0XxjRp9W`x5+Y(k+V?~JbSF~sIDI;Ol$pWmJ65eRJ z9%wbGR4ZU3Zoub+RgWtV=IW1fv}ND)_5Ru)<7BykW#md2t6ApTYF!*K{Ysfr21VVE z3{9LHnz``AjbE}J$USHiT^!6N;bPp~d3v)20qZjMx7+sap0;?VI&&a43Fj7?;hkt@ z4h{Ta4T8=qx49&^@OqeEU}2wpD{3CkIahFCc#C`3ok$T0qc`C8?yV@RxLgm8&(XbN zp2m00R(G7QsGgGA+{=CgP7MRY=O9KDU^EK2T(jh}a6Gm+HE3bU`h!Lleq@NAu=#Qj z_8g>ufRUEIcB6rz(3aIPXC*a=$_dBy_H+>!FY>l>_}hN!qNO_Zf%g0pe2mOpqe8GA z%mH$;0@~7Fv}gCNZ27cM30+L@+lQgO{|F%?{Xa=5jzP3>maMc=HwbhtBh&bC-6v&L z-6!r)`D1z6m~8>Gpq;;qi;hS$@rPjtU`Y0{k!-F>Q-@As@XCVk}|oROIdcH==N3vrcH`!u@u=x*7Kn znm-DA9RCJFPgMt;8d!HeMjhVu8P00=t#gxU_v-}4j#M6|rVg&Leq!`G&*|1hqkl|_ zluRi;7kJm>k4NX1eeBgBV(IDp@z6mko5LMmPu(826(G@zGWp_X4mZ~i zn?z}QI7jHIDq*J>Cq&E!8S*Vuwm3dEYhG6H#r4Rodel_H9bOOg3hX31dIdolKQ51X zA^A0XNKkN2l7BmQUV(F53?~Co%dS+z8eJrLZ4fvXzm)2=`S16~H8&O&%hF?$fv#bh ztv4|lJ*8e3Yl^^3!8k^TD+Kvw#0_4)y8YaSbEmJb0G_jLP8pcl5>S)0@T|pQ>x0@C`cfeO=ix1QXWu>h znI3)^Qv&K5^dj>ouPKkIRUjISpq_HGyleD&UG=Q*MI6@wNp{xqYZ*SE40t2XPq|0Sl{gaZ5p zkJwklUW-@!YNhQ6PB@;Od~n%ZLDR|55{GSt2k{K6=giX@`Rdx^ndx1-e=2>dNn2ya zbrP#b4$8XS$BhRJrf*_-hu0#kbJ9Lxih6Uz?CVb}8J(bpBe)EN`d zAtEBG6YC&RIbDK#fO3-22ii>`1_Oe9>@_ue04H2>Zqw3fS*?xZ#`YsBCnYo%CR$gDh&)Y!9VI*M=c0$T!n9W-UJv~BEm*zSr2-Sd zJxzfv^pWgS>4M6K8?LXnZQRutY1t<$2f9>XXJ|Z4fvt3sDKKj%C$z;ceS}YepJ6?A zTrcTTft@2_xCR1^HgH>wjMchta%w2X=_R6F9Y%y-8aEGH13>|Sr%BbuB8eLR+9eMk zKDYbXo%6<=xRe<@-KA8WBl299Et-gN95gTTCpXD1KBDWf!tGWTn3YA5Wg;RE@{G_< zR2T*e9!Z`pzm+Iws*W4*HLf+ghY6%zgEG=QMy&Ipc<53qgB2jL zihyQ;*oSY8%EybcYj>zqrsmaWd-iU>2pxj*0`Y%iMSul!T#;XQzpv~#_Wh1WzxH{x zp4@55@2m(3Vn)tiYNAAozhOPbh$98tjV@T_R^_#Sg>Nay{&OL;?Y9sy(!YforQnGZ zS}cu?cMaS&y;k0g96j2bckt8NGO^H(-$eD%bFG1uZE{=C{BDW-nukYx)|K@7#Y03@ zpaT?bfh)BCh1DS0uHNit%~}=6NV|Qfvas#q2i`lb(_ak|w2ZtLaMWWoL{h;9qYN}& zHog4-?*`P^+tCGE#El9SEP8ItUQG+}{*x`C&9sp)GULDvl?Dyyet~0jQ$Wp~FDn|S zoZs$yeM!*V%g{!eC_G4_W;DD2C&%gQ(e}qv+^qy&3?v7G&OP&?_dijikuckb`=yiMY-&_Hd zgR|tngVgg^g2dc2P&f0 z@2Wno){CN@yr6Y7z!`b&??|76RbD-@&D7JcrH?W<=d0iR(Jc|Q%q@_ID5DF{(3`#5 zf8nYS|qBlbIo73LM(JQT!I#L>C7mmopY3<9Q-W>oaRFhZvpK z7=;m~VTjk1`@go{|GxWWg^djl?}AoS1ZCt1vB=4ypq36lm`fydL?MQ`U7f^}x*xCe zdJn5dh4h7$k3kz~Az-9Pnv_DzGiTFF5e$D#eM3?36stR~0}Dl~CQ>;>63!P}Ar4y&%b zYPI%VwRTUEtj7dZ44xx7a4k)|?DhYd6|$*+w}aZ$%7+#Y8*gwTIR{A3VhWv1gV|@f zmwyx(Iw+(u@A!kivZ~Gra={c1l97i9_?=?vhGClA3M)((*kHy2jA5-sozWfYJ^9f; zdycHs#Y4zLXgwWx50IL3>)&nHtNJrDL$2CTHlAfPq^5LI7mhkN_hK+QB#{K#c+1-MQc^efh{k0wCZ?ide6ZNpmj9BJ;1*- zjbKx2W5J~@==DZC%;SCP>pFXVDe3jJ+oNsOBbE^TOIOeyaQ0!y0|{?ED80isTrt*J zyhc;?*ta6D)hlNQdvzn8eXijdd4y-tE^uoJ0y@Bv`SCbLAq&l!bhY+}l6w#NPOCP! zLCPU$i5n0G!&CGs2FnJxJ3w6&1BM;s+}Nu(7mRuo7Sl%-Flk6PYk2Awl#%!EzDgB+jbNsct&1X+n3&e&Zu${X=`%2-ng~2qUijiF4A*lFP4N> zP=RBlV}X@0Yg)c?O!^!49;&9y zx>9Y31$1NhDzfLzx00PIKZvVRa^L%FGC!NY;Rce)^Z_|(z`(}?wZtaTdA%2CEAJfN z^6L7dlG_(g1lrOE6frPrMr=yycqf99-EK;w-bwNo#!RO{YdR+8O(%bbvtK95h zbA~BEGnrDbk%zjo=5v7ba_;=M8dpa8^%|Zt<7C;}Z-%jLDFtc>7#YMvJg!j2z=Jn6 zwtG#>ZP&W*{W)c5)3H;}2To3I4W+qsHN5H)$RI=gsHIaA;%zW?y2GYmJ`!<@4I-t z`{?mIrH-b;IW!|Bv1B@Ax$L%E4M#t#!oV37rkK;$EprRRsK-xag(RN-Fn&}#96V(7-seBJUiOpB zuzUP&ff@BX9H=A4)Rp`$d>+Xkm-MdPmudN$z{Bl+hZ|5vk7he<=1JxjQ$h@@?=1SG zR!Y}%4VHe6Xw&UkN*DXlObG!aW4;}?3ZBIn@D^6Bh|;MQ*t^m0#)$)GEvTzJxvpF0 z^QQ6yXzTCbVbq2?6AAimRD(EhtQ`NT#_aGhr%KK^KmXHtjofZSX(3`XbTv^*Aw6_| zPnjwK-=6kJ$@%o~&XY|Nd+16H1LFsUZ6t~kmv1P>c`^0u@O!sn6Z@t27*?}2{-7WQ zV*H@MQUzv6%LX9`wx7VUC3Pf6BN{&}*fe5a=W+9%;13Fyz>K+qcz` z8Yf=A-nPnDd*;WNdv^ECJv4(AmV`>KD4kwC7*un?*w&WM*KUQ3*2M@!sHNU0$ z4Cos&b7@ACZS6njbRV|do&=%*&bYa^?J<+IWcF)PjQ@zIW@4F{MXjb>Aw( zn|t>d7`+d06aw~Ms#B|DOKxe~4D@d`uF8|E+Sm5`09SB~Ce3k##e>U3FnSJaI(l48 zNc&+}oicpjtu5k1O$*tR=B^9_gKAcw6`m1k|6M~y=Z>7h>_y#J2&z_yLbCaFV=?%Ro0)2bF~)LRc7DYw% z68Ix%@uL#lPGgw+yhFcodZMPst)PxA>UYX6h>y+OfP2b5B(Mj(6Ky1x$#?a`1Likx zGIGLeS@}s-g5QzuL)SQ-G7Q?2ZWckx??8tpZZ zPCyu$Q-U>m7B&dA6d7+>A%7nDoWA;VR)I;eFSO87cQABZEP;y4S4nsx4wo-hAp%6e z7xH*=m3NQkNF{pI<7(^KWo-6BhYGr~y92<+)0K!Ip(B4}Yr&l0`09%WB zSgw%8BMQ(t5g0=Q*5;QR+tk42%;lZ@$*x1 zy6s1$j|&Dui)?I=0UTkF@&q+jhw5-^ZSNe_uTt39*@p`jNoxu%BodDOo=(~%&$P%8 zrB`dC&3c4(og-JIeLw5fXjD4mV&xr3)#-3jF0{eM2o(e;nUIJ%^{ZnG{m+<&>qgPzc0 zNAj@{r=QowhGBG{6oO8#+dQ$Ua--HfEC8LUhQ9T%jBZB%Q?1p4 zjwdmQJ`xP-MpXtzU+Q2Ex>i%9i~A|&R-RXW+`~>e-^zflcqYyI2S`0?0l>y~y#PL~ z8m}JheRSD?O~|v#y8F3Q7QhWsI*(WXRShsr^45Y(BdO?L73}BNcIKDkHP|ca%zhcT z4a#yUc~{8jbbS9;IJQr_prrL5hMn_X-y&GB_2k9SiXSVK0v&xxd8dW;<^TG?Ans8+ zwdRSFAli#^wfDV8F0S4DcEpogjYsh|er=QkW)izu1uA&ybVK@=b-|U&db1^*7k%rT ze>v;7k<2(fMEG7Q_*eXp>`L;Za72XIp_sZGwAFf9ExJW8d`N`@fHc zcDi8KB`!LZnExAoO?#V+>Dm)c-q#+hnbph7FTZzo`d`pqYD_ypNGD_eFL17aaGR=1)jnQ+J_mKwRod-HmE`$z32N zkTeO_Qlsu}wA76j>Pp>}mby|`>ZL}7zMDW!lDm+j?H%v)eE)c#-?#ZObD!Cnot>ST z-OWJg)DXG67yO&CkqM`l#1*a_-1%jFFVZ>e3M)D{`u;o3;-sapKrXLrwK3~-n^#UQ zt4xeE)`P}y4p8eibAC*&Pinm`<24#flG3_fTYdqtxJqvX$3u1CsYPr33B7d^7n(1S zl%4Zo=eHx%gYTSu>>FB@v;Pm+u^}}$drn{K%7x;*G~GyGlotVosqT0egs z_@9}~e&2n}Rk8Mu-=jKhS~jp^{lf1#TZrOi%7RXL=kH1f&Rc>kl5JlNsR-9V>@HSd zaqOLD^W)}fQVVaX~3Ix`gEmI07#;j-K8$?4lL~$PR=Gza}=isa%5yOG*61#GkKFZ1+;~*(pmq zPYqvxE3i~vQ?1>ck(_lTl8{icY*{9QHPeJsN#{JjS`@1`sp;WBk3P8zAUsmbvL~Zc zm;MJc9{(gEPL#7JAo}D%=)j$lfL2t z2$oau;9@8>1h(wJO#^q9-q!<4ytb7HG*1}uM@OQTPTI9=g`aZSl`6ptcZIog4s)z> zW}PRKnLzqbtqT`U%?XJIdv2^2F>q;)yN_2l?^pui}wG#<7vhoC~NGPtnpLmhH9dY`B^nCcYNjTZH|ORbjyD{fU}7f z13Gub{UaMjC9_xIof}{F{VxBdRHJ?4nzw=1F57VS`U{umU|#~aUGmIKIC+P$hLbP;nzUdcqB5tJF*VFlg%@i z7uaz|@iC(tUjNj&;NJarQpxg;jgOZseGW`?zBxiIV$*kr;vQOsno|lxyd=9Sg z>$-ovf)}q}?S%JaR8%Zlko^`Jq{F9gKYLVC^+mUV?~8XYGrpRG1=*7@p0B}XGR2Ns za?&SY#+-IDgX4pmbzVMvUq-$r6FSE8fl3>EOOl2%M0KALTR`2$TX1pGr@EWQ-i*%3 z2f9McWEXGxJSCUNe)XuhW_rqu!6zT{8XUd(Ji6F>&PLa%nXC=lI@mq^VT0B)L~J!6 z@VJG^A3T?!G=Mxvdi@a68T=tHg_j}7&r73&%v@erul|$6T6Uh(>0tAzeIu_9XcJ9l@+HA zF7Kma`!4s82*a+3)*%O9Y?siI6~~FmECA&!v$QbuN zn+6kLS|B7yeW9jjw4nRXUu)()ir78=#w@y06WB4?w?nENHCT*PSUMhb zXj3gn)8%2i*PMP)zva2u3-yNHIm0>lM+{k)T&uQRIv=RD6dtT+{UC!DFFUpryPrB+ zdGEuz2?M%M{4!OwW(kGlt}GVN<25@weRLWiB-wd2Rw9%{aU$uGWtsdKvvnxxCSYL&$mW!7%y+nvN-0w=w ziOCPz)~mIH|6#h{K|RGPoGGX5F-r-urf-7q!mbWkJ;J~LMNQp%w|hlh7(C6{EOp9? z$wDZ#>7fqd&Zwfa5{4eTAAvhn*%E+~ZlDbv>sCb4K^byWPfCL;=V z9y|EpoZ&vZhV}Ma#yLuV1njvo*>6cY1lD)3z{VI3K*GV^I0(_DuTGX5T?tNmV2NRQ z8&(;7u;}}a$0vO|zMFI4PxvueX(Yv&eqa|Dg;}2tc96RGunUVPpZI)!%gc#(q91Xd zarR}M8|%>*xLPP!r2>8NpcY~_>UG!&f%H@e7JVhxntUOqUCv#578?rt_v<=^BKmTb zA(JP8NcH0Y6daGR`DUx)iJ1}TIIqLmQ%x3JeB5JX_4E6mfs;Ug&i4Od5b!CJ;J^yv zhh=>#4PM;nY4eI&;U5eF#+LORCu#|{3cOYQj;X*o5O3J|plJT40Aw`mam_@r<8+N3 zlV|^&8>+PvjcWgKphm88u%xZO1;jhd%C;KXN{8SC+RM!6$HRB#`NL$Y`Er#sh* zt~qf(5w0_)%ds2PDdO|Y7_lC++OkHL9z!b4K3n!$=q6vV@>9Uc4c&&Vnn)3|X3mQB zJihg<=^z+fcWSwqhGO#O9^0hswr7X)*ZK8uaf!)~#1wga7kIHAr&wF{GA`Tq2N(B% z)+imK0j>4m_9I+=`$6MdZfkB`2#kxE|ej${w-s^0_90==d7yA2hZBe10aznlTiaSb`z+$L)MAFLfxpZi%sZ)%tb7`TW1Ymz9~I zgNdR`4vbsdJZgBp+0*LQX^)!;S>VT_+=15a1efLhKDp6= zs4s60wjQ`n{X#u>u!G#R__30UNY_tTdRvCef}fk%=XUh!88tVwS{*UmgL4^|i^vK? zR@S==pmat5K6p&ft)SsOj*s!LS+~^k1l)R;C5}vPvuKv1p&$7*B`DYE1^Kctb`s}i=)P$}fF7I{BsTZ#r zjkzYevOQ)|&nrLZN=;zLN&tpej_XZG)vJxW5>|Y9+N802+!{{lY{ms(Sz*Y!SU)jc|F1wR@j5Kdz+PP(&sxo?jW~Y?eA@#Yz*BgXy{2gp?Qd@=>H-%GvR?`9bT$ z4@%>kkg~{>l_n%tu{tV#IXoVxk^I(!pSR=Kj01jB=Mxd}<1tJ2tn zs9{w)CLPVyeAE&yE(w+eeykMt@Hky;LQ)hd6fv@YbW6jAlaIT$ZOO$I_h@rtJ^DgB zCNgb8+8(^6fA0D{tIqgr2)*{W@(GIQ%TlWhjj(t11S6u6e@p1m`N`KVP)I$i@{jRvekt2iJr|ml^Bv zdFIuu0gdDCv`9GKdF!B4s;}*gPblK^%owpAv)ZyoPMeTwPb~H0_klBaBL+7(Gks1Z zMa-HxE7tS)E;J5tdDZep<(?Q2E{u@&n|!bIiQ5!;d>44J9;aA}>KRwXDV;PS)qgPc zN1Z`4Yrn2=CiYXYF25+^6qmTM9+Q%wByU1;n_Z{E@EX6R8$RFaF|6t+Pl}k-MSiTW zO(Zx;n~>Tx*{oa`QzeJ`+OKHa-4@Hrqy&}=`QeNr3r~#L#{RwH<+ zn}!Gl=@*264m5D=9y~s3ee@lFK-+d(817oo=FjIm2ZcYpe3^gff)!6ahJ?)I>~xUO1wKq(>*|2da={kmn*sTcPU^+^v~lHx$pMM_B0ZMPFTD4+n6rf@3s&}sA;R?c z0Bk8R%qme!#mU&T-Gh;kZ?a$R69*P7x>c(LZjVTZ5i7fhPzcZ2rn!ohAm5Vl?np5Lbx32HcU#?vqw+qYyziccw zp5rl_M*;Yl4=DAvHKzNOCs%>DiP) z6A}Nz8*3fBp?%e=FD`dYlUEWON6j2DQnrD0nCdmHU6;HAlCOQZP${5BAZI(efpD1% zE8S6!=$tl!O1pOE)$y-hOE@z2tZwI3TqkI`sq~N22H`d%aczE z4-0YiH~Q?@kI2v-7F$jXeZAWLZmQR<7pJaN?eQA2dd$$s(f7wvMP#mWWTp5*P>};t z=Z#^qh;qkXf0(}GNU^ceuMUSL;EOL==lg##3|J2rm$xsr1NIknqE_fzdhUE{|}c9`5+owkRS6|^1e|3&+7 z$HRFegVRbL#$|_Tb7Mbl&#bSD%WM67X5G>Ku5CRUm=@`78i2oAl_+oeTbmj8hdADM z#eO7f%Pl!;5xe!nu%_A5zV#aqzOO%VDC#@azB6-P>}UR6Xzb$hq9zpR7^Hz#4w-qk zfpA!X(^Q#%7nrdhxsdewklj_)VdkkW^C$e^4+=c8ZEo9cbEqO0m)Nl%sgl4XZxkD~ z8FC-KO+34msM#1@Y|ulhNYzD#?5|WLKuKH08kTrgp!VyND#bTV<#K60lq;2M{8+if zg5YZ{I9+TOOT3hSeXrhyBI?gx6TZ1uw^sN|EV9NkdlTrN*2s#m2^omvNn zjOu)_`o33lY08V^l}+SzTAt_fMsr0G+E#NCb=B5R4u4;{x>I?b^2)aI;&j609sm9! z=JUu_DSjRNw*}TLC7>xUju$&?xWk;Y?V_Aj`=hpT?w8ozVX0=(^wztI|L%!j!?VCJ zJ4;Te&x6~V){Po5x##lTZB|R>N#@Mt)0dpUke#rVpd!~R{v8K@o&BoJ`TjYY-ts;s z9QA+@wq}WEHW1&{5fb((wHydL7!2Pe;&Xc8`?+)e$6R<^O2F)aUzWzU22zD0ksT{}y>UJFv>X%WT*w zhdaV^TKnJsd0GB9o1(7n7{zP3!8aeF0g)D~Y_LveTC(Tzeq5O*Q11wSIWKR8Z-$n| zx>Bywnexgmv({=cCw za9!>KnER&t28A$wNxjJfUk2s=mIGfD&I(6%lB)!yF7^RHbL!U&@%#RLq%PuC&6Qmw z_%a}Ue%T;QL+h29b^ei%(N?j7&a-=Gp8JBDxjIHP&997VQdyWY zH@==on_V^t=reB$*fwDDxK}k6MEYD$?pc0_n>W6{l_+s0T>;r3z_lfzoV5kKd7gB* zTeH-Y7pip*oc1`p8fAc+IkRj~E^wii4{nc{Qew*8fdhQ+AG^I^gn4KJWx2owZrLE1 zAt~*WwFdOAS84H**_#WmEnT45+a@w&mS%GG`T2&f!{4#09F`or|C&iRcGWCsV2=FpWG$1J-@?6la;@Jh0EJ%o+vbpjsFoJ->&zWN?p?EN{nO1((2|g^=w-WXT|g710p`$ zZp`l&Tvg*`+_tSfVRg#_$80S-q1w&m8Di!i7$3J}`QyqVBX3Fj{>*~x1dc2%Wdtpu znHXDY(s^#Km{-T<9jh0wR_AK!wNd3}rVy91taJW9844_k#^v=)n*L#_M_zfZ1uajN zKhmz^pA7}ZnWc&(QFoanS-8BHk%jW-9wOabyy1xE6}Bz-OsGiG;>A+>f`~Cx3odn1 zI?c%qzn3pxt(}2oc9aeOIlFITZ$kQlCO4K6kpz@3WLdbpiLG_Nrw_|H>U`7cb$<;k zHIMi?>b5R-}Q8oE(Xj&Ds5H-C7qTh>#sH`9lT-C)nvqsgsg^*E#%c zku+ZlZ^tU^B1>23S+&6QT^z~vsxO;wKl(Y2Q)%sx#*^aDO?pORffTf?S|AaVy#?N= zvY?^7iFd+^yKhc3X@!tkpfd({*zy&29kSXWaN%eWq*JQ=a8?+)aD-30=r`jgHfq>% z&Np2=XDh*HxWI#rr}3;a#15NTZy0E;G5xmIgsX zE;x>3xlol%GSAqDxqWIxNQ$q&eWm*SumPM61l2hsX5$)T>u_5@8IAf-C2R!hO0S@( zbQS@HV%UJQ%ge)lO$mGR!9Dy?vjuJ5eoVx!F{Z=kGK-p1>kx4LHi?t;>+rB=-Mqp= zy#`e_9$5T1jkDffZxp0#TwZJ&Z9hGDGXpY$trBF=l1X*`^2Vy+hw^W#pW^Y$M?BOA zyS&&%7OeS6V3XF?Jhk2sZg=HCSfI{Jql3&`-u4UIrnEy0t!E6Iq)6N`tAm}Nbb$wJ zkqC+{*qkAr&fpK>=34CaX|E~?-{}L6Me!291b4BEL^7dg(<-fc(}y5NjSlz}lDSqt zx_{Z;>*7ldS~j6Wn16LaGiAZvicSVC{iFf5qL11&pj$%Jhb3PJ=dFFeVBM1T zD|+TU*f?5Y^$FIqKIo|u+=B}sjU8mtTHk&l)95k;jy0UvXI}4voRa067=}Aq@dtd_ zXs@OR*IxCZ2lG$i$;xay=Q+KTbk>ROxc2HlVa!?%gJ=(Anjdh!c;8ADqqNeQH^s%z zSDb8@Mazr4&HGC6VZMKx33G!A+u38L99WCzOb8NSu|~6h zaG;88Gxh6OgCw_{iSJTV%RKd+Ry4{kp38)uwP*mvrM2eKjHJo5kg5ynRk$;1{|C5ZJ8jf%B(6}BB6!Fo_} zkq(JFseYu$fnL{U;eub|2^EojvD)xodklo;NNv(Zr;D(dU3$&}G9 zLggY;o(!l`=9_%r>cHB{2?d(BpcKICVjs zH}8+lDwlNaeATJ?A3ovDtZszOGvA{Vc=kYcb^7 z%8U;yy8<&}GAngR2%-aB6Hq9m(&5|4F0MRseOZBD_Ydx0n^1aw_p`WNfipr@{DfJr z*O|2jrN#&aB1*e*L&<7;mlX(%Fs#bcH2P{v+=T@tN&*2N=Ptf{*rN;kHnQ8T z1K(c-xt$-+Im03R?H@4z{}~Vgen5CRls#G(Xg7LVXv4`@i&psK0l}Dm&K4GeMI*$e zk=jNC6@~@ZJ#aO6yGPeX%W@Z4!a3)}M(DEte;O1_m0Vue=AJiN=GnS;`+@v1=D|Vjp?cTlii_guTk-X``J5ZAQ8;qGO(K^9vA4XD- zgFOGpUsDG6*tE&tzfj_#*-b%-_Al_g#FppKfbJ!w9yFerEDc&({O-2f)b@{av@Ko_ zT9GnvckrhJoOJ|2DJhwhMF)ig@SY(;X?hA-ZA1`DjHuUvLJ7|4Z@k|1OvR+F3llnw z3GCRcaX-#F*C?4h9h8A66awenfJA(&M34?Knw78?(&_z_s$jDj?076SAd;lg4zFE4 zGnUW3K6?0v`^g`5TRDgRj3bk$y)#E@)|z#oLCZ1qSvhiWU3m7+mkF?1cya2&F`W1; zGh?!kJRM}Zj@8zN5Nm1ADy0^*w&096ha!|nr zrRDrGqzyvw6Vmw$Gtqh=1lW#|9R3`|0tq;IwfYZHc2(&l<`z# z?)?q-om<}Lj=PXEtkL9CoGmn2FxmTsgQkW|Y6u1md+CRT$QS6j1snv7yz=W1*cbU5i`KZhs!(c2Bi7F0J2; z=(KY=KxG^!QfA~#o|B}8r3H~ZPNK3G$8;DHo9F4?xO=fR@@<4U>s=&eX%^WHaynR? zJWtDMw`GHBu)SPSk)${cIaD_07 zoYFFRst#u~>8}u2r;$Gbf$KriBVPwi#Xl`{d2WMUhxrFvELim*I)t;0HWMa$p2)$G zuTX;r`Q5vC=wd#_`e*q|hPQjo+2}eoOEQ6r$}Cwo%QhbgGJ_R~q`n(Yt{&uwIYLURV=dWyP6^ z%Fm@$QxZ5!aN4l{a~9(5^n;bQq6k%P%)gFrwTp^lttS4O`F3u@b0^Vw+ZA#q&zxlp zE)iB>FlfX9nK8>TXA(Q}`1tteH07PT{a1WWX%u=$!P!oq3kz8?qKqc6SqJlpQpgR% zDjgU)w&u?puOF0Iz2;FtG)qQ@4GaF<6l^f)LDeojcu?Ao$q;-yZn_z_O#N`MkmrHM z#l-Eq4Unuu{W&c@bWU$c5k#$$!zwYX5K4s#u|Ncg`Fy@iB7)UYu}bc3J*KSD8v_y8 z8*I~!dMzC01)9SAKxl3Tzi0zNfl^>;6SMxJL~Fs|3P&SEQcEuUs!WBusftr;ANxkV zzu9dAXB%xMbPiwq1p#RYC(fO7{@J2|6PCSp>wUzqtO;k6ML3rk(CLu-3xZi&%23Uv z*B5|R3DvpzO^fJO_46JRa<*lI8_hd)<*c(vlsP4xrp13HN|@G+n_P|87D>&&@p$W+ z(VQvpvd1SlYbhnc6S69Z2JC#5_9~g~dzN3t!+YoFKC`Pnc=mJ-nII&DbP92QT_fpu z@Z$>ZFfF;{;M*!wH!RY-txVc5u_|Ycqe2|%Sk;H#0Cu0x3Zs7S4Z_u06KIxK_WeA?+W!_joaGAa+uWS||bw zI?Lw26)Z#xBYK=@W81Yqmt)kq2KQ^E)o4252_n>V-oZ-1ZPp9(q@3fOX$-OY4lyfHSsh;=L^!D)hKKB-WS{+);eY+R^G2~uB zg(jHO6}#HkK`MJO<}XwmZ(uW(QGI+N3p6_RGWCJZ0aD5v~&p~ID+y$PHLCRn1Q$jIL3zjOKK6Rh+8+4^SpMX#_Mkx;K|<=_%K zrXx>XW|8OgF9!-%2%Z=Bp~mUmOE-NA#YLW(&@vr)lEWdaa9rML82VPG?Am6pyN>@k zV^O6?xX9B5dZr^!3P|buXKd1yF8IE!*8q6gt23#!wnQV1agnD>9GG4xoPn~_*Of)N z%jW&Q?EUnlnJu~(do&8SP`J#6>B!R_n0@fb^|6T!UwywkR1h-yjy&=ZF7kAR0n=VDFf*@L=F9S~WiI8v)iEM1aO|5! zDxBBLgqCTqM-InMJ*`4Fj45;`b^g$9d29F=U%n3K^<1E5+Urq3viEuilg4pd&V5sI zW{DBo{B=(|mGZqjh%e*8qVuwM$EL=qrhXQrlH~o`aY*~mfRS*Gwuu&dY8O$ZHg8 zcFwIBV8HFS>9JzVq1fw_WWW7H)9*m_qRHQ;pScy6cVxSnBn~B0E==#YsRo~Nhs@>W zD-ziD{Zwww)BAtkcMtD91-IX(&5h};Cjp>KdqpnqUFzmp$y3+K^1MtQcHWI2h1+`4 zXGiBi+uzu0TbhpuMwijnjNLzst20L5xm@{2`MNdz7dLtLP90YYyIIUyPj-~6;(g%wsHB+gd)tw@mQ2|&9g0y}nv>Ae709FCVDPl(AWll;8dZAKe_~ zZIJl|1a(fsFCUpvGroLK0J2*?J_O~QcIQI;vYi7`2P~cS>oR`%aD@ZYJzrr|pzPzb zmXWEgTYJnM!8h0aTq`VKHm>K(MIKCVf1Jaz)7$OkJuWS)$MrBQuAj0p;CFT0_J;-^ zrW<}8q1i`ST;9HogS*TxKIvY=?wdM7@e4=c8h$e;XMDHdV2&9A*{Q4Rqiw6D;YlY$ z4z?-PkrNq;-z~Vrf_Y6jz{+UN#;S~qKbE<&uQ~suIrEyLKxC(> z5$m3$41{;A+GV_OGp^RIDFjWq!h-46>@de!k*+DbZbB}Pd(hC)P%NeGsB5e4J^GYn z#`ZXk>8`tM34 zTAi?`ZMn~ctM*^|KIFm!Zk5$;r=vJ4ZSgN9(K&X(TjviZKv&iDJU=^)SXcAPmr6co zBu#Nw=-Y3}@aI_=4sD5pncjW{sRR6s`rsfKr;al>*5~LIaiehBf-YBQZE;V;LR;53 z(7B`JFC+|zpv+ouFD}8l?oLt}Mf!um9d`Roi054!##u*hUG|i8uJ8B*G15<}Q{~=q zYRUgWw`xS4dacjZ2tRVQ_OKnc`=v4^WoTh_E(o}VI#6W-_ci11?)bG}4L9QEoLk?N zm-_@19@xZoaS@eBBup6EY)}aY?!7gDXDJY+Iv5BC-YD1N9ovB6`FtY=EdEkF_WrfH zx5S9;EW4w8&iG^(5v?A>;w=m~t86v4Uh#R0cI5uNJa$CiLMyp0h)BZc7&GoX<5q|a zU8Uayh?C{c)5vKn;$lwt8k0lEZQ0s}v(za8L*Y&a1}%7kMg@V}Z%qcB)~vKXmSd^& zS?)%~$#9@lkB;gMv-_5hoff#p{aHm$936T_U4_yjk_iEw&){jD@J!^|er;~-tn#rB zZfhbh+$w%oVsjNVn4DqM$OsF6dO;SarZ>0N<%&uAzMxL0%M*J{2@FIpV0K2vP@OWv zU`UXV_+KtBqM7^50S!|#IL zmf+$;&Q`iSvV&+O&X&ttdHZ9Ho}U83lZON1A>L{TT-IvBE+H^^ioHdM zOd%17U`V8q$>n@0q7sWGkQz~_`3j**CBXg~T#%#I2YUJG_24QauZ+8Lylgi%@n)9K z?KQ8%jG#w3p2%v;9tl6u03p^0L>jqJ$`^=a8bpkUMG~P<1qmRDLMRrgGz1XnEj^II z000>vvlloYrVlo%5fg8F%MX_uoQ9@NeAHk&)IgE?jRp#}P$d&fR3dO=gG3I&axtO; z*Y;}EVyS|!7KthD3bI^W2W|oa55}Zx+ACBG`ypmt=WBhfSa-=Q8sCOQ zDg>4)5S4&0l}P0>l}suJ1EWyO)!fBcUKU|Na4(l!r6!je3DghP3cW1$1};@IBfzy;PQ*GOc}~OX5V=4om8oTX7#4{Y zFsu>+Z-gKMFc=U(B6Ehs;lpoed{`wD${<7y34{t2@O}zNER+i%NG1?VWeS;0O#Wd@ zio<%vDR>Xc;qxD9d|r$Qg+h@^qJY8Y5a8xS5`+(nz}0ASL?BaB*qvIhH-gLOEmvfv zdprjWbli;u62c+`R*5uXg#b~@fro>D1&H_vq>+K&$%nvtYnzr-@gHamfLwwA>jO>= z;wz*;1qzK&AQvcLuoQxoQza$;I2;}X1%i{lR@sN_Nsur{$= zE{4<+L?Z$Vk3dKcAq3pb3AA8)f;Alq0y`jiM`JLg0B@HMp=)DwS$Pj;Gk znOd$Aip44r0>ZFV0?AY$%mH(skAUe(E-@N!I0#M0|4PMDjZ`fKI+no_NGevy#E=X) zVhxN)6fy}h_(kJRBccvhgI7;17_!^v>9}6G8id(mg&O7y<-pKn5{aBIQGv)?3~R({ z8HKH-C)h}3|L^0j?705=us@~Y}~zLjJ*B%UW`mp$~~XQ}qo{|&Nh zmmdCSQZA=y{xhj8niQQ}m_{rX%ET}T|6xRdXh2XP0}G@Ekx5{_3@n!9p@>eaNe>9T zblMOEhRl#dP(UXaCewf*T&2;-z>Wwc1P~b?Y>uT6A8ZT+8ki4d2Ewv3Ti(3TWm6P% zHmD#Z6T&iZW4C}W0NX*S2wdQ;mVu3$5Ef`82t`H?Q;5N+2T4K4h@8#_4UvIuvRtEp zg&MhBfyjV9L=d>#l@CkQ0+oUyIe=lX8HII&;Gh#aqag?Ta=8i-3qX_%ax@}HBvpuo z8Z{phAQ~Y=v0KHE7=wc>d140)ziGq|A~gi=wS`n5WujI?kXQw2KzdNE5I`!48YHV+ zwoWe-1SX5g4C?C+fM~^$AX%xlPFj$t6i9)J_;M8=R;kq@fdJ%=$pJa}I33#n={c1O zq-zukkir3}G`>OuOXV6NqC$jV14%I&P!P!ETeDVP;B7d>2y_Bo4R)NbZ)xZSk!Zvq ze~*A|6b#abU^gQXf^@%3B37%wfKbNrMw1@Y1|S0{u{fxK&ej>E3P4;72`x!9iApL{ zi9{j|$RG>Uuv#J#QzY}i{M3M+9xceAgL{riAkazR0&9c>u$Zq_$OK@T@L`ZlmTP1( zu)WiO>^%hpHDrWIH#2nhkwT#q%u2abCg!X7DhXIM6u?zUqymu`p>L^bD|ajTj`!L260_NmL404zk%o;DEv9=M?EeSg#JYxI4?VcM$yx z4RvcEA;JeqYeb+?Xh7vc0y6d*A(-ZB4Jc{KC?4v zG;j!jw?Tw3h}R%F$Q=Rumr21>BMPuMDkO3lh4CAVVDdYBm)GxtsmG!!7ktazFXlJ= z`IGyLVFX;r4HnPB#}UnNGRZg=TAU^5tQ^m z)(eJ-F{P6tucy(=9A@V7qB}3kA(xC3bZM(NDwu!nz590>U{o+DFM$XSWW7PYPXUP# z5iEs83XL2VszJt&e7cYndu?dmzrHuIYrnS5-O7D<_NGl>MfWrsXr#byz!ITRD1?wg zhNuN#_A11X3Jj810$d0=8j7N?4N>r@RNbOY@1}%Sb*HnOgQ7Qxr9jjT z)-nZ{*fJFe`e5*Nu$qB5gJMCmtfT2gU>k_NUtTS3_rt$awO^-<5wW+t-02h~Kp{>8 zi7Y`ja3><62o{6HxJU-8KxrJb2T+7|w)b9a5CRiIJ=T=FbFAOMBNg;B{vOL8omY*@F^A*TV>V;A#bVky-F|W9>a~SHF(vbrcG%N*ejRcYlq@X^ANI)4us8S0B5Lo)j0pKgQHW>MWJ?6QOpZU6upW?}} z$pwbG)7gM%RC2HZ5y?QC1|-vfOab^e4DrD#DCeuxRI86e1=ohj;&C2o^6$0B3 z?dhbANS(p0sJ&frR@}f*ZQMW87#u{ZQp4ceDvesDlBq$@mjE<8fZhWTy^De2kQ*%# zkqt=Hj>Aj1+<+w!ietSm`dp2sr6sixk$}*V4?3(s?}L8qD%~OYjTMIcw3c3qY%PUjR34MVhSy# z7hG)s1~rLq=flwn_sg%WEbFUZMQgcN%Yku7)G`EgzwzY)u^Rke2!zt$u{yb2V%LC& z)*#WP)`nrlmlwLaJ!3Cm6R$^|ywdY_-qz*`u}7XiRnzhyV3idKbBh&tpkGTe{H(=J@yA`MKMJl}|NG9&U}RH=9>x-0Q8DMpihPm`WHZl zq#SGlL5NB*W3Z92smZzzw;}r8HrMi?4)O)&lFw_V%F7<3H98s)qJgeCkPU{!YDmf# z3PC5dhEb}))|G<;Us1|#z2=>>BW#dZ7iKfC;7 zt1}3#ML+{Op+HbA2gz*U>44{#LZIjaN(%}QTuU{SQ6qQ)gP7j6p?NrN_SB$j*FQ}Z zH7OoZSlrE>PN7310qHid41sk?A`+LFGjNj8+0NlH{fe>I;@MuMNS?B27>E zzTZ^5#=GIc%L4LF!cs~cgJ~J3Oej!*;)WPBOoHZFwWVsU0ee3osDgkHPD8Z;#-)F4Fvb?Y ze0y!brLhHK7QeW>H}tjpPa0bqp-RdJUq(Ps0*OEpK#Bkdq6W>}e4#`NQa0quAWZ|? z@WgL!Gh;<-vHPkqd-gnVPYZT`O#_d>(nSkGBq``42J0>u4S_(Qma0JR225M3#Dp~+ zZ2NvfKaWo{H9M~^P3qgN@5{tA_l9)h$G@BEb;$IxnCRu%=XqI9^YZMoyo@J#dGF?)_8DzD4(!hp+C2MwHp`!<6IcC}Y&y?AnNG)p|E*j)&pwr&EkMw5-hU^Z&$G|w z{|CWR)5r#+z+_d0XJ1tL@8hnVHT%~!*+n{keX7yP`u*LiG0(ne zOegF2mutp6`;u{X!a`?L{a35kJp1A`osHx_s9p2yOV@Np=C4++dG>|t>`}Mo*_W;9 z#BYD6YR$7RTGO$ae^9gL*_W(YsaW&u3)XZt{eQDw&9g68(@Eq0jcPT|zF19b!}*tL z)ja!Bb+!OOXU+M`<#L{VwVdH%InTaUPUri7p;XSZuawit2K|*nInTaMPRAtwR+*e< zUnOU?NY1mbkuzE%=h;`tc?s`5Ws%Vralg6NhI8n!M_1h{-Xcf!~^Ax#PAbzNZj_ zgx3Br`ajS{#*M7DQ##5(aCs;0{?%>2mzSO_SU8N&55KzRv!*V3Q#d)n>3?rNfm%Z# zWblN7!eN6J+%GT1+Yt_V%c{zg1B$xG-0bwFg7HYbK+ZbXC@-)qg3|t#3aO?Pr|E~( zV`C04c=@hC{YsoTr-Ing+g~{U4@@Wnjz7=`K^LKj%HX8|j|OmgyJtitY#fy<;T*Kc z?LcJzB+klAiR>>iXAXGA2;$)1Ua{P?cu{Prj^&>Z%D;GcGtPPn`1YjCjlSjaZmQ7_ zP7!&u@oXPhsf9>iAWr)d9ervd=0@KhgZ&V4d99J5`m*Ogje?q`-5t;Aa2_4~%t((j zHkGaK5K#^P%8xhGmOnREY=4Wl<%)1o`97m3{b#l6F(CFQqV>gNmIc%>G?o|=JxE(FpABPLHsqeTD9 z3o@G287pyUr`@u>NmGS4r^?R?7jM46S&IG{83BWU1JUmX;sF=CT&juqPQEc$r*+aK z*JwH!158T5AYda3*oX&QWvTnFs}&;`Z7uw2z*7CBxfozl0tNw_P{1ZU;Aw-xgUZ)j znG*GL+Qg+P#~xvTNeLJPJQM{y6c0F}hxF=g_}=}|(_j8rl`>)g2AGt90Y9EGhg5YD zQ(dt@VS{b^Hy(V)BimklIw|!`K3}DN%h$Jeb2hk4Z2wT(KX8O77L&1V2gn?RNs{pc zUX=HRPxk&DlU%lyZxMOJM+a_kVrh^wXGSUnl>$7~fw{su@cD{$iVvOLXiwm$M?Z#6fijfgMiTiQxis5t|EW5j5EC!gAfH}Z0 zI>InvgnJa8-=tCpU-N|{g^~|`8XSQFCMRGJFzVJ|f?KQGS5z@i(KBhatCVkg>%#S3 z7+_KY<^Ur)n++p6ybXJ{@m^EACx3eHSylF)|M_DM3YeV0{yE=&w+bRbp2lW9QP9?Z z;enqYnY;FrQ%M?yK=6Cpfws>$YctkA=Y-4((4rY$fELa00$hB2p#1!*of3;|8e3&( z?1ngk0Mvxc3edVaUVzrk@dBK9(YIU7$2~iBtBQ6%t(W(DwVffvBH1zv#q+Dg9VFX!=A4xe`TMrFYhf&kQn z3<_ZKH1_O{3Sj*gUVz6lU+fT-zy57e%wW^1dtcsR0yrgP&~2g%BSKh7$MT0=DdPEi z-7D`NX-kR>Z-}`~QUV46o6*rW<3~DbK4)W}PMha7OAg<=6b}510VXA25O6RGI2aH3 zRh|387LSOVcC&A+=l#WZUt@qt377+{L1PsSAy(;hX4dY5H9qWvkNXC9PMW_T1x!xB zAYiR+gf&|H2uC+>61?~B&$U$tse)%tX@dn<8d3u0yoSc;X~Y)5^nc-j@2lB)OsRww z748l_@on$Qp2bnG;hd1c5l53v8bWqz`J1Hmo*pCKxObEfxKemE4>J)`0_Fhwq0ylq zAvzRaGB=7EUt?zF@q*#)yH#t70wyP55HRWl{0Ls7Pw1%{jnW$I_v3jqc$2GmZVWIf z!L5IvoX?0#{YBtj4uhvbZ!~*`2t>9SY4O4%+9+G@5QQ<32NCFKuUWA`9RtyR$1~)m92ub`I zL&oLx402nv_|daD^+y%pDaKz&!h|H!ph6OV##k{Zq(nk$uEd`)WL(}$UfUI~Z*1}F zcy{W$%_)0EVnPyWP$7vwW2`PRHz#G*If2$Z_N|mcR#je z{ME<)wR`WEjJ=o#158T59AGV)Vh0U6N=(bf$*yld)`nKMK%^ljTJh?l;xFo*> z8(~rc1_6iKY*-tLH;K2sDy}Nn0d8L`?rW3exTJ{~U{V6+01rm@xq}J&+~wz6v`NUB zG_XSV&&AfYS?_}aCMRGHZ~zK8fB^W}>lbfYwvKyqz3G^@1PlU3yFLO4Z6a4MO^m*Ib4lvn6}e(%`@aNW zfJq4$1dRIO0D>Pr3O`t{-f>{=+oGT(cA$8E3@|AHgMjs@N$Bw=v4sDtW8Be!PYX#? zW1H%_3oyW>1PlU3SK0u=(p>O_p#Yp~{=?d@da5qPjK|q9DFFk$x*374Wpip9W6OWz zN4fgL0_9}9)u&?{#Xms2=7)1uW=h0de~S(R=Q}(@(CFUwZ@d66#`kNSR=ku)%)XOt zRz`I_h4#1D{uq-yof$^VTz`uW)|rjq@PGgXWBUO^!{zzhn!xRsuU_z?mAQ_LsnID9 z+TY>|Ig`Q|%{q|mkYU1P{D2pxm{*e{{*pPoMt$}s{L-E7hZ81qa^@zp4s|9vg7@jM zVp+Ry!J$u~soqHafnC<3-iMrkLBMEGrz1px{eN=({Kt9M$X9)d`$GOuGX|KHfI+|^ zsGWom45VAsXl&^!zk>DN29gpm z2RKM&b8A5=yjy#rIyv^~GqZQUdapdZ_MXQ&oeScNW#lz_SDFG%a>4=P7;beuE(jUVkBW#-L(UbaM9!wqXk41IIUghqdv6EisS zsJjg!_~(FmS31kPuhV?kd;jP6!@A+ zoA7nM`_YNUR(&zRqy)_EAuUy0+eEbdH+~Y9{S46tu&W06> zTIM^^YRl!FI~yj}d_xd`nvg+T#|(#HHaonLjq%mGZtU6hw6W8Q#|F&SNeP$(Y()2j zM#7#j?X6V$rl?*JKVo`#yR{b)6fijfgMiUum61^061J8cGwMg2fI1I;DLg#jDh8O8 zfH}Y>wBTtX6g)3I{djL@qp8QbnF_uvCb-`j1x!xBAYgP)Xd>(hi+sHH_S`{jsa6er zdwDE-T^|EXO28msbiFVU7MK>E+gE=ayMI{jSA_*jVh<)_fJq6Mi}p-`kPc*(#5PA~ z`#0XzjrY=2Bm%;3lmK~W6BgCBeOV!p)YKdSy*nd7F+ zSB@3)O{4@20!E`f6Cv7LFz4;=LfaS2N|`>kj`B^n>6odI5-c`0=`F&w-Qa%08_D-YiOTibEv*I{@27V8HoZG% zOGYS#`+L;9Fs>L22DN||YfXgeZq$*2wN~`cnRF|0dpFIzF1;}=kP(A5yFa=88#|9oPQV~wbOUZC?AXWe7_HgjVeIYOe*5CExW>295jK+& zFbLS+W}9Yz%p|$Is;PN2SGu--SYUEu_57`m9K!&U5-0Fx3h2pDy}W`eIS>v^iC=t{41+VQb_wj}N^iUB4iU=DCF8V3av0;f+q ziYapD{JCOphdstc&#Qbw0h1Fj2pAo(V8RH?;k*8QYYy8Nvv|sl7Nrk2!~l~LFbEjE zgdmu3YeA16Wda|}&A;pCfm={;k%+?>U{Zo3jID+t0;$bSfd9n%iA8eJxi<3^KW`i_ zod$nbKudYH(|;PcY~vOlt9I1_qjf zgh|js)TV_(Jm^mzn}v7B=JTx^F-%`7Z@IcS(Bvdcf)-(*MR?G0`@Qe_#ZSvSaOByC z4~370;6Rg;FbNvnB8CXXc+kye-qQ35|Nc3qPjvf$8kG`ppvg&?1TDcvT7m~XwO!XU z(t$lo|IoHR^Xc;{BMvk<36r2PKP@EqY4?LQd!Gt@f9d%7RX-a~>(>+qnw*45(3t-c z5?tP>A=-D*e!WFU#3O$6T%x*)15HlCAZQWV7!)ERxV&nWw#Qr)6zbTk{rG^`6#+Ou zO+msWXlz!A2orH&=Xbfb&nenupnGFQ`+AqlVk0dgCt)sF3PBT(A%w)^8ePZM-OjaZ zy*9ja#rE?x%h6zooPfDgNulY7=nJL|Xugcvd|PdvB(cPMi8MZcbVpA?+JuZt6sK!XWM_!(ox zppar~4#+`B;?Ec|F0Wfo<N-W zAOJNXvjX(!jTfLtZ@d7dr+(&%IzO%c8Qy^7?iw`QAt$hZ4eg&@ft4}T_%W7@8(O-^k^%EgCsNkK()ZIi3)6E# z4uATC_K z7JACJGF0k=bm2-j_XduRnj95+ z`C#30E61g+ef7@d&MqJaJPwbvOb>*Dv>L=@wv3+1{mfm0)xjq(wW+xV=)-@ zYQ$u+4qivw2ld8`7h$}c1;IwW7PkF=EVGHr>(Tj$@ZFpRrnO%~D;()-D#@8k@@Ic` zzd%;;>VwVT0UOUi#0*&`m)BsEK8VYEwC99RzjG-`gFH9%@6f1G1?<909<)G>)lRsoc;0{`q5i*9iL<~p}j0CB*;Ay6uGrP6WK_*jYtA)3NjGRA< z+12_$18^)#%fUlqaFAIWh$w^fW@Qi*h?syaTOMsvsx4ns4u*_2M~m|osCW17<^}%3 zjdwSu?-f(y*(ZMPtz-NxSaxjj{_$Tn3U4Iwb1VSQKV^87bof4c9gG;=lK*JrGh7$p zbt$|%!vF&FAlJPc?;7uAk%0yG1~#nuG^EkKyY9=apntk^<^s(6U?XsjU=0DURe3=M zr5o?-y%SA3O!`nR0V%%gN8sHmU*jz@zCPKX>&81#T`@c_ROxr0iUo`Ixg$NDV~NRZ zdDW^doS`(!%-8xW&8obzW9W;$ofvszY+N-b#d0 z^1sE}Fc=Qd1!xh8zn@VTZt_ihzP9 znYJ^tf(V2ly?4Pd6#{8yHxxyB@4YtxQK~fQy-V*ML_nH!1f>7p+1(^No6YKcEJ$eXo$-g))N!OSbJ{EzW?!MN;Y)bRM&0%yxDlq z$Avl9d>eiF26_LXldh%C32K(vX|$^*;zIrJx1#R`yB8tE1x@D(#!7iFTZ5^l>bhwLdNam7tyTKL7dS3#VAkYE>kSkr>HpBL#}% zWvfUEHXAD_te}PC)D&merBapfSj^SLXfY;~3Zv*SGSs~`!=3vV4uKFLgy_^({puil z?~h(@fBnlYszlzP!5)A1rX}(xnpKrFNwBF_j-muvq-0KJXigA#MdMgTh`qzDcYeKA_Q`WrsF0$d(4@e~q`+Gl8%r4^OjV;F<+WOVegA_Q)w1UAIGFW?6mE#nWCMnHkQzffaV>Hz``8q_a9TPyGnMh;$k?9R=P21#>S6hs| zclygojv8pjGRS6zKv&^3Qj%y=VklZvI9?SP8>!j!iO4ZFt7uT0mMFG~RpT6x%o@h} z9?-RUYsKbnf1vg}M;*tI-@caqXUVLJK-p{{iXka0Mpcs~#Y$TRN%LA42zhjf zc65ehLV7xDb+O5sbCo`mzqrzAY3X*G9R|tFOf{MXuAeTLB$G1DX`-qyvOr4;t6HrR zNg8y9txpYY@93l(6DGY?FsMV=ski!G-P$X@Ql6%3V?zw0nK34$%xNl28b|YrXeCua zV|a=qHIAcgGQ%3zsTv#KE}9P2XPiB>tr`PY5>hhh>2Gts+O@=mix;)XKkt0=_YRgb z2x*3bo>f_iA~}iV1uIQ!l+2J=4ZN&Lsz}m;Y|x)uNI!C2`)$aU@z08%+Sub_(AV(| zjqB75?YhL!tg0$J#N!03Y7;O8d6~3YMMx)zM&;>Dv1+2*z+r6D8`=-n<_oK?jGgzj zR$%zK+^so-*1X&K{8$Hyls(Q%?9-c!VM zwz81Is|MRobSqbcyYN%R1$7DZy5dlmq^hD@ne^80=jZdZSUsR(_Ayz5gFbB; zxz!-(Mib5eEwU2pv??SlAWN(GKoAsB)%RKa>`zcX@+~?dv}qD`5e(SaoM8y{Yy`;&y)9?wv)dhldE;f{`vC{skb@H{_l2G?N{}QK`t{}oGjDuLaiDpi&mQ;Nh~b0Mq+?f5*`+9 z+tjAU>eLKH)>e1Ah85U9b45FE_(mW~Bs>CP)TqzQ^hO)}6RlzJ2d5+<% zR)fkCRk^bqqbBMi`db@hj8>!e^tQtXj~%mdZ_W${4APk~fg*1sd2DBjCXq5r!b_$^ zTBca|^)jz8M(N}vyCXjK&t%)!INl$NQTs{5Uu1p=-JfS0cb~LVUGsj@~g_?p* zg~gc(15YWMP2okAr>wA!lw>^8rOr#lVq)RHIwzztJT&FSvJp?3_So+@J@3wrD?_sw zM%j$zp(uu7D1~Dvl~Yx~@*{YF-9!*298W~qILhtg9Wl{yokFopkfn%@L%PAaV%l|x z#qP(2u|^@=zn9_KocP@vf1JNgf< zC}9|DGY2V(MC1=UHP0i?z$5;riZ+_UoMbpfO<)WXCdW}B zVgk-o`eDyw@bxnQWn47JTWcq$w7s#deca$nEwzO$3}TwGISd?F1SxU;w8GvfR)tg) zMpIOd<`B8`j;SI*?sgQ@J(Zjs(y>b6YH>d;`EcGZE#xWJ43e2~u~}6^c)@Cwv6FBR zNnr$@6%k$KRQxU(73j?UB*Y`AAMbYp(o_5W)U$umotZsHXFqLJq6=D2c$Cx&mPFNvQnceUmPk` zDe3r++1DC`^seaeHwQTuCpwd{^;$&rL*;?x^ylg|6&UfR9c{9ism)h z#`6-X%81z@SVI~eY#5V7M^Zwv&+l(Qtua7?b_6WQ zt>JUptZEkZw8YY!2IxoCn_6=|!DqY&Z{Y*vI=&e5W4aj%;xPU46nAPe5vPW z%WleBbjvM+OlBq-_D~z*EWULSe)db0gElSW6%nEFVAS0zK8_zgt()9ND z7`RIq%``sm{-=*Fze}7_+E#+r)klh(Zja%c>ym+9z)o-Sft{cJ*Q> z4>q%p2e#aTSk)jp_x__R_zi12j?C2NbnS;GbYTr#Q3W9!N-EK1c!3umWh zAO;r98uPr>@;MXR1>Nj5tY;PP(o}!voB$O;5FgF1{l(m%o9}U}+x0k|t9ni|zEU7d z9f+T6WtD#|dw0@?opW>TytQt;DZ>-?M*hc!MGv$hWhrBx~{7s9%7bg&p`canItMbmj*^cY|BI400GfrW^N)U(< zZ%qAV`?L;+4{V4&c=}4$e6NQTrsBn~pxlAzbUdQQnp@vqiT&zfr6#owbu?wb{%%nN zF>%S4vqlv9R#`CqT|!E%%m1@aH?xriqHuzko3(3?ruT;LSlqj7n@zvI(aDVc4p4an zaqqi3jmdE(d&N=5YFubG_ubb)1~aBRAcYu2n{nq3@4H<6^Bo7CwrpMh?aKd2@H*(= zHxu5}-z|C}=H#5*ul|FGzEj%Iqs74&qW^n%a>Knpf8js1|F2b6|4q36mfAmSWXwcD z16sUClqt5i^&ng9ldOX-Rg9fkzMq*Bd|*rTh@w@NzVrL~kIFUquAsfenY*97MxvNG zN(ZtgkeHRBaK(kfr5Q8Mt~^q=Mb{3AZzIjGaUsf`|&JyiPZU6;aMn9)lh z>-&i8EkEsB;BwSMaeTQ|5kKU-Wu|oMl~wT(v$Tp8yOb-ErQAYwe}k6CyO{A^15&F; z>?f-I65ftI^=MZ2(>*o~U0^068i0yCVtJ=!cNbP!QCoXA!~NN7Ki*|#4F|UFj`(`# z4o>aRHdpB!+w+wCwn=|eHa3veb;P}jl|CG0zw-Ub3z>6oiA<0Z8V@E}HuwDe zzKQcqpsEFlZygWji-M(nFaFk`UxMcTXeLS-z?wiJ$FRv`+6@?3EZ^?L_M02UKQPm_ z66nf5VoHY{-wo%XL=h}L>Fd(q4$5$O6lV%o1G>vyS2>)Ic9Wn0q=Y{#Y z>x-W~HFzxX_{*_oQYC-8R*slZ`i&lPt=aE1e>X$d<#k7|H1q0zw<3#Pn;<5Qd3mHtkJ9TAG9NJdbZ8^Xh&D0tk{HvlbDX2C>WG%@mf6v9K%%VY z>ZYk0pNKCubQQtZO#s+l^q0y3T4-P5jl0JCPPEdypv8Hj&9^?&|g*5(y&S|EJIl>KF{72H|%aQ?EriWA-+ zSysmPGK@{RZ3v_w@+7Nb&P8+-O? z-rr~^b`YI#b}Bju?ZFe%{JleLBQdd!>c}$J-yrEPj#qYlwSSE!wWFvgVY>Itz!QPh z-9}B8H_f}CTOKfQIzD8`K%jI*IhX8M@7u)1*HGFArTI8M!BIUfdzy!$V7(3cm+Y9Y zwb6_poaQ==d`&udj1q0vtF)cw3txmB)gyw3qyH0zJK9kxAzHuMvN}3WPE=j}pb^fA z@3g&<&I)g(q-(uKwLwoN@K6(Ck^qAk1^Lk@95m9UYq>o%P%lx{qB~i}qwm0_vnFCp zH1G^C$@Ir$S^H9e$^A zGLEBj!n)_P=Y9Ol;qU!C7SOI8MEBTdnWVp=OHcX~4$}p7|7}o{$Oa9o*R2yp@q=Ph zW`t!-tPUAi&y64G)_CwZ=cmc2f(;#sNwVIrmfN!JFT7$++Bw{5uJ-eSL*qN@LzH%! zF0jjq(FqQ0Eoz*OS7`S)8FE<0=+n+=$t$HA*5Fb2)OGhNSdh-9z@TyX4D&^fwyVz3 zM0Z(xn1rCLOWlprwZzWYCmSR~0{VNdWwt*XnDRHv!jvD=8tkw%e`CDCcl|~|tUS<{ z1Pxt7dcTCiPzxqx2QdH}8DR)gp&+9uI*JU%JoO<@ma5AS>@CjpuK0eF z=^Oj}@E~}*2^a@a2iy~Qnk997B3We62r1wvw77DB-!aD2Q-KSU`kkJ1VCEMTu5*L?s)VmVqW`IGd#DCV{%5 zsB{#zvvPq6t={Zdv+H|HiVqB{_^zn|WEGy{M6{TZ5JN-*D-b#WkA;*KsVUyAqNxh= zr>09CCliB5mY#O2`mRmCm!IJXHj@z0G3;=3(_~~Lc$vWrmIPS>!~h3q9mQ&#P zZ|uxV#dM6aMzQIPSKQ$6?Y%<>Y^%2X&a}H*J8d^54he7)ATI!%iAF;{PzePUxH)KW z$7<)SUY&0`cZCbcF-k~RJ5q!EIUhV5nfGv&J!I!{%b2%u6) zrBoXIS}Y5h01#@EfWT!OEhFk6T&(m~nDyBrN13i$C)D0m=+UC@*5nU1lanSTJr-dD z5CN0~bHt-*QGm@v53~kZjWgN@)F9+aZ(?8B`n2<}eEl+2k91xz_~P|ZrVNsVUP+o} z1;C&Hjz{KLk|hBn#E}$FOX%Y@7^Jiqety>5A^O*!8-=gF6)+t8Q}JUIc##z1&d6}sE81B-^YUApby=CTDF z#O4k*lX#?UyoTuw*ee0`5j+X7U`hlc2wVezf@sEW++=V^Kf)Ah*Y@Gk7s2gvDMe}) zux2?BY^I0=fMB9Piz1_gj01-n8;**B6tO7-i%anuJsq?d6FdDaFN1V}eq(H&K0h5S zcQ3eM-I!oA2riTjE1%UNlPM7{5@5D?V6D*rh@dGea4QUUJQZy#1qF_d;-ctuT$NtL zH@~mm(zwEh9r6iFn-n)^$pI7qObW>cA5I3et_G-BhNXcM0mq!>NaF^RDwykdALl$nlhY#ZH8Y$>rSQ3$|*4F@SI2>#xs%v=r`kDoGMa^ zuACl>KZRv@XTjukOt%B$pMEueYpaT4d9nnU?{7q z7m7v-s$>c_ik~SquJy3JD+)?I7nZx`=(S*aso;YqjFxHzgsKRPO9{|-IDJxpZJ{(L zDkq>(C@;j<6uDA0=7EgoPkH%ooSiW8-kbeKgx;@~x9Df(O-(vd))c^&!ea-JE)cUA zwEuB31)wy*9B8Z&-@p~`Ne6TeYGi#ZiP$DzZhrWpe#h^oo|@48=B+EirjXnO6$tPE zE~QmcXLF!%z7${PWRZes8Yt+e+>Mg+|y}=4)2=&d2>^<-byn%Bsi?U z1f)0}2~s~e3y=*ZhJt1^wW&xWp+=$VZtHR@@3n)S|CwaDS;B6@^*XsAz+WL1JQ2Iwvk9<)(oatef=K^@eln>?fClTrXKz<`+H9^ z{uKK2+yh(8i9|CzqE(bC$O11=6ip$x07Pn=1`7_C)iAYE%F}h+po@7c2lZ?G z``w8n;x47(1@#xk7kMiJ)WA68bS4S~t_;Q6C=yUxRCNDf1)Snd3KYH8u`D zJM7cKHLdYWubVpUSZN!}0637LaMZy(XBF%yfXIWf#1xl}-k%$s%#SR$)-<4Y?{6PH zrNZQlHIL_}O`V%r9JFK-+%-E#+(jb3xa0G=6H2f-K|GI|5)IRYzd z?|huC{EV-=JlZs{+wFdHO@;N4Pmlp_s{ydwCU88=fTjR|j8iEfrUA3wpdh0>ZYz+U zSZSOlGskyTMNa_>14+>^Og!pWWgUhOp$?oY;IkOSN*y;OWEh`gmaltc8=}b4hD-Zc zc0U)7l`<9UPjjXqjglcDMPrkraL@vEnFcI!0H%Xs%DDBW$rU9dkEJ8o)uG>C zt2wE`n4(8>b$jFNH&cVnR6eT|93~lbU@}VT6vSp>$N^c16$xj7^};K59}RqHr_9j< z^Sgbx@bcBl;@zq>8(cQEy#eJ<$5{oi9$Yv9$30#LW)r}gLeoGeHkwN3jvFJ!N{R?4 zJV|m=rg~*S7w63!Em1;=T*oRL*d^b78T@~lfK8Ks{YTTUgm?D!HA%h_-nrM;A@xdl zXI{+=UBDBsgm>Q6%<(bsX;;EK>-tY7T?y};s~KSeopL3-Gp=T)O~4bbgm=F6pH84OX2$MSBw7jYJgXTS6!ODw3*%cTUxenS8}5Rl+-?YUV)l3KOb?cRtmOm-5Qesf2en_4P}p65hE~Gn4HV zr&0;;OzP{CNF}`UsAk-SSCd91yaR$}M0zzz)HEWQ@fiZ2LM6O2sAlH+D^8#i-ucsi zJbg-dXHU%>(gU45CA@Q|X7-&|m^vlAGpA-8y}%|;3GckA89(M#q)iF$tm!|PG$p)q zre>7$DpIC|cgEC|K(8QSN_gi>cbX{tdZp=7!aG}P<^&VaWGUgDD>bv91wK_ucxOt@ z1PB72C?&k}q-H{LuPRNN#se{9p97mDCA@Q_W+E1^JVi=)XGqO#u&*#dN_gi-|IgE- zgm-q-%r+L_^6y~Ewr4iH!eSV#<2V?k4> z=w0gJE><|yse>pGwIt{wLzRMnT4K;=GB(r)>P7YnYReP}RMvj(oK(0A+AnEK1RgMv>7_C;Kbc5c}PRi#kJ0O}nc<(~|o9Z@Gs(FzD6Q5TA08C9~9 zAe>E>-IET_CGPd0JWGb2+n#gM++_)~s@hux{}y0zoekZ|Jfm*0QG-d5=&M8t4~S~4 z0y-E_u&U|h`6zWj^ALJ3MIQC5$)zfWn|Nyb-ig_#W@l)hY3{dWw?B>_l{5I~z={uu z0i9PCa&uu68IIlt6-Bn_xkAG%ixv=?1f4jVu_Q@U6%j4iBC6gPI$3b{<&apv+@ zAAB~d?SwV0j}GhpO~(rpE>z_a*cqz?himc43N| zU`Jt4doJ+$})NvpZH7)F3@V>t(e7Hx= zRk)Mv5nUA;iK-}+AZp-ShFB_(YCphfsbB<^B%4U1%TKgz^VDk1n^YQ~8|xukvK);x^bdhr1H>Blc$XCqFmSs0b{^TLt^)bqn;RIk2z z=fBB>69p=s>%QVly#j|X=II)q^RvdUy8$PbY|i?V{U~+$?#D@)b|@9f{`<@~aeC0X z_ruo{XAk8f?>3%3wZ^}~coRRgD%JK#(fdWP_$ABMF1wl!Vlon1jco_G;TG-`3TM!VD5S8o6CYJ9nx8!0SQ5)k_$qjH4*4`09>`U7H?&B*NetdcFWn4`8 zPs#;N^MA$vIxX(}cz1zq&cs=@I<+1*C|8|f|KqfHMYnkc)53clq?r~WexU%<;9KeV zlc)dkByd^?w?iE6KD&E@Bc|LwG#Mf>XsW#}T94a@ru~zSo@gP)d{wVhpY@-1F46eJ zm&Z#rU%&6Hj!Jp43NR_HUFz-o>R`vjZp-QmOG@{6kztIY+8xnxPAoYHjuT*fVrKxp z{Z*6V65kPN5WK!lduQqEGQi0bjyI+k&P;aRkU>M#qWLNd}=}5uF>il^Lp*wU9tVnXk|jpJ(2im@#vFz>%}hrabuP$<1e-Ab|Axg z9rw;A zx-L8s6g1A)!=j=s#I8MsBF`2+J@*s!@RL2Qhn94|Tle6gNxm;}y;O(%5kGXBVLAR? z*$4CZzP)RmcPcXrW=*}`S3doI(3vJZAGOTgd0Vrxmfp^>aSdkB80Yj46&;SmXer47 zv3-usft0cF^?lE=$bYn?YTh3@v*hLx!ieFOHVnP^#p9=Y?$0IA0g) zL-TgNmfcTBj2)GOY7;x>-9>ZVuci-;?@N3SO|pP4jM-4_i_kdWhw7`tHNd_{;85}i zxBwA-U*>NhQf@HUC9KcqrryB!c${)8ce=lO_#BqxEB%V^F*+4nH_OBlNiEyP9PF@o zwWEMb{KTNCexB@Wkle40L7L(BO5bCZEcIk(+iaW|^OwfzNXl6Gxhz%H7NW-cCvV>< zbLV3CkE1@^=rPW0ia*V7vjc>-(+4{EU@Le2kT!>-DiJ z`{K*I6`$Js&Y!;b%>@CC&I@ zVGTA}cSBRJaO$||{#)!fEUeE6*%1Ed%o3`EWp^*ZN<4j(%S-D zB4B%-?(+gqHG1#QDVNUrlS^HadT-Fli*TavtNl*lbcFR#b>8PwFTItcNQ>~v8_G?5 zIPQ0su%8Ew_xUtk>)u~Go>k_lOA>DH@+WHd)&Nd zF*rNGztNO5e-me+nZL!NaXXWU0sn`Y@B6Cd9`DZw5zM2=6=_X@ZBSft-) z#~PI#^$Xjn1D|cmD9L4-LxP6s`D5MFiB^1jIcJmS`UK-QJ%`ELx};n)CB180uj*}9 z&bjxCQC^q%obkzD_Lj?InC3AL@>QPDA>ymYm--Cd^l*#orTL%{#{2uSAnsSdtambO zq-rQC+V?Oei!&@*(Z8%e!KKhlRm*(-&NZ1VGjLwDtUVIvxP*Y!o?!f@r$Q(0U%{WV zfAU@JZyk*M{KesvYo?@kjZ3H|y+aFceCOr&7w@dtdZ*&)_++6*d0pmTpG$X2KSFTdu#m^AR(=lAIT z^zoG0GuGp4p4#cTquA*D?eeHU9$z$UTv+EXQZAV2^8%M@R&8F{v+kim5jW0=O0cER z@MKwrdtT$z%h>Y!+vJX2GOf?^>}A*=cNIwfra>GJr3@`O=;9A&=JtqM*1XZ_Wb|ZOpO0ZZgxxeu(m_Ea*>l{j8aQX4iA8mMf=XGgb zWYM2JC@eZQA;v`%qEDlc;T_aCB_3P`31D*2qUFVZdV_yno8SMbjINgo=`F@}cBa|f z3?8P~J;cOlN9Wv@l^)}gGTrr6;GPIhS`6oR8$yL1wkG;`p_xzn7ah`RYWxrDs$W<# z$r%lHeiQ3P10$7_u0tm)3hED%7@eCVw`IA<<8=NJqg8XSNjL3}$HTmr*ckT>!(iQ< zMS4z}oo{`7nxvD)z>GN=SnOdX$=sIBe`dBIMl4Kbt>`!v_ch$1k^(j_H8G7X{Nb-W zIt-LP&b!%j!Wg(z;`s)KC+V`fI6rh^9((q`@^Vye%PMH(FWURME(ySF)*wDUHq9%o z`3n+K7(kt-NME{wK6=90xSYSbpPSp_t+881Cx5Jo(J^)7 zoUBhlLsCABPi!BY`W5_EH+e$)-;ki&f8$TY=~vDufJoBIwyUK zCOjyTDruObRq-aEv;E}KMiz7y!7&DdaqY`pE zN{{TL{2EM|QHfE`hv`^dZe6fpmsc*jV+ukPc$9$DwpwXYWKl{A`XmtmVpawCZ#Gi4szx}vgaloKq9ZgJ3l6Y! zVZ5g>8JC~eDsO($wBqDp)9OqYdj^}KPgMmFN~@@4l>myzqoh~{vM{A^3Tp+@wv99h zlLqb$N(pnqth&@P{XvT=r?1r5vHXXFY{U0IIBIHSL?F8gz%>>@z90`eLSD@0miFbK-W>s?I$C79d4K9X{A)KvDA$cOUa0JlG7`yryA_iZTl#8J0!UBrk{> zCr|`=-vb08nE{3K^ zNu*G}&(J`b22ljY!DeJTNTvA+6Fev7x=s(;U0(O@=z8P!44U*w*P^DTf+lbb2t4#@ z305eLwxSXrv>rf~C22ri8&`-EWzWg%6NU<4kJRJQ^;k~b0v7|DFXC{HO~jF=eKsmZ_*a-Pu2j~;z7 zC-{*GYem9J03=ehsw`?4AdiHqXj+sM!0JjU==NHjIA-hBBJqhaP8vDPOO&4L^a`$7 zacfhC)5lM)AJTS8^`&{nb{uZXP%wZ(2jH;=FnKHnFc$z)TeRx+c=tG7N{->mlDM-#8U5nBFyrW~`{{A9{jfYr$c?hT+Wb2ik?Lm4XLM2g1-Bg1kU zhQ^ba2P@S>6K`iKRj$<3;kn~?-&|KNdSqi$fV3dq0K78Vh=8N7S`|{2VKjk>DS=yw zk~ky%h8Nq77>5c+giE}YvUp0?52em02Tu})y?^L-=!@XrP0UwWXWS4#0z%TDzS0{F zbZlA-6sMuL#tUiHOCYbw+U4R`b)SSbsQmf52OnIfkLNXIKtLy@;{$U%MS~2Gl0kuh z-VIuXia;mh#V?g&$i3}&v(Vo!EQrclbi&yyS$htu6J~0D=-AHSN`p&*rXuuP=yVY@ z%n5*~L3AS+w=++Y9pjqqHLY=%yARH07_aplob7UWQ&U*e00ZY$32X`=){__!&ISAq z8%>kgVl^9WoTGktb&QMm)}=-CTm8Qre)0SMW1kGpUo_YZQMh1b6qqp<%8@ykQn0nD z=$iqqJ2)gUG=^o9Or>Ld{^_LO?+vEM--!tOu-V3LBcBAD;;IL251L(M!AgQ4Mgdox zjESMa;gKm;QjJT-xwT+k8n%^Rd){tdug2tk`|CYid%o|y7pCB>!5_rJa?7xzAThC0 zEQk^)5)TGwvkgsu#@A0F4M`z^q0zzRB+PMH^xiw!d@EX?OE`I*$zEm4g*E?6-|HnDYg4{F4K__l0vQ{plU`UsM6a+S1J@C}05o_B z(;3fH5*ROG)KaH2)hzMRj)G5iWqP^0ZBy*NI1`H#i2;3J(6BRKd4?ePhh!T}9t2 zQR9ycbjgYtOnE0X`fRO?-d|2@GADwtn1>;i(ATPJlGTeu&SNc7VYKJrM)|13z145t zPGs0&pWbNsysIf=uBi-8nleknUlqal3j#aLL<$|BB%?EH8Eiyq%+HIZ2TRGrogUhH zV?^`QPutYa`S8)45oh}c-#6jCs#dGWfXYb2EaG@Zu`(hC$4c@xs{l4oFX;QEM5Hj0 zh0{a#7#G9&rb-*FXr)Obn%(Z)=HgH5r(ZF3{$?;J`t)TL0K*HQYGp8|ZD{Vs^oEmS z)JrNCk5Ph_zmD%hj(p?Zq$|^i1SxWpsa*|xDIlk#DF9pXltR)9xC+3f1UH)0G#mmA zBjZlmsY-$f6owc*xD0jRf2jx0k9V)#*W~7sVH3A?tN*rEX=Csa^Tr{?O-UuyK}SZ6 z-WHE65SA8(Ae_=@9N0;n=!F9Z722_(J~$?bqadJS#m|U$f#lBPN~f%DTTqT$5wz^s zFG)SyH0b!U!`R2Bj-}vE0{j8CUkOK3TH%3l%+dn51|?aN;kX!-=5$0-H(o<<@w27% z`_{OZFs<3wTcd~eV7~}H`Zu(NF=>l*P@;-g1{GwAKZhrVgI8J-Bv93XF9==WvXuk5 z0yukgVo4sn>J)-LBp4t(FNG_o2mPF;v;V=MkDni0w)f7g5~G)WbabmJb%F9mlr)f6 zYBYQ%8%}BnF2M?tV3ieQ43YE9ti>lHKp*am)F;Hp=&=p&wbtVLTKUG{r7JeP*N5*j zHbXX3Qh<_?0^S1;J`P0ubdM6#Mj*j4qkzQOW;_lU*?5fWt<&_nZ>qx{5qCeocOvi2 zNy|*JZ{ZLCE^UBi=rrFrCfYz$hJ}Yynxr2fjZ&mTz+)6=MLY~Xflb93(l9h`&K=|9C(PK^@Y`w^h~JXlF0rV6 zOxfTwe`gA(RE~J$Tl6*>rzb;(1GfP5iwuw?tTbrjH5(X}7>p&zalrTq9fDsT_#?E} z)tE_i4JI{mD&Yd4Iy69uz!&3SjbNSO%ECuO5S~>y8Cwm{fYnU%e>118q+Hf| zcO>`)R!0baUQ6G4WpN7~c74R#&e#`PZG=MP<0m+kpL`ts0#6X79^gRgnH zcz>3kOs^jjxySUIe4QD}5Q3fj zMs9nys%+v*YTB0n>+C5p^T%m5Z>)&?sNan8&#LtqRmBWSU0`#k#O1k1zPn$b$hhkj zS{2?_VCL`tQ09~fpV?+2L9Fga{?<0v*!3Guni-QoLjv#-J8AsP0tTN z#+E3OVMy*erI(MX^d(pJiyV%8W~N{u^0h>+U;A9jd0@retR0GMEnGNvmwzBzODrkV z{NDaf1HU*OH2Q#2{fAHgsa!1)RjN_>;JeLFkn0}pi2L$fLo0+XjDW|r^3Bgnl!)M-^AifSVn6Zxm$rKY~N!z_@za4$? z=>n?eg%|uxGibbl&l3~7uhnak?M}PlpN?KVW)MnYc z?i`Zq^^n4h=?p}sn)qSL9>6DP4J(Laq+m!;u zy)`F~M<1)YZ}gRr3yM5-=0E%N|H~=`BDQgf!%cU5)T>hBb0cLI-5C41ik``$bNPFqp2r~W`BHa_&2#Wep=2< zJTS2JSH%4fd#rBtO~*BpGOn!KIroAOUn5b>gdzf22u6_hP8o_>_7o^gRDbi^)jLj@ zAsc*UWnjei)h#04pb9tdG;!3R^~YCU{MQzN5rZ1H$+d)EvZ87W^353aD)BEZ0V5_Y zAKR_Rl+Y zcUcfQ>Csd1dSx>Q?tm135shaS+V}D_`~Amj?lxSq;ldd+yGY z161%uWS-Zn(Stjmz1=xv=}!KO!~?Hqxfju~!o$1IKOeBIR+}aFYm2?Fno(7NioJ;3 zhj%12I?|@rp60EKFOpYXHX}oTO1+4&>(1w`kY#<7m}k{L=_y|S(F{{)pbNc-nKRjs zDylPzdyFAmUa;> zYgKL4woSXMSL(e#^09b=3>46P8hCi3>4k!c8T!2c+m#aay1iey!J!nqlhiuA6hIFh zY{)Vx8Mj1=k9X*WZV67P6CEETc#W|*uu`0o7$2>KH&oh(C!k_kFJacvMVz08GHmjX zu4=XgxsDwBbwK3tW_hcg{D@Bf7u{)h-mg>rK*&hU zE`P6G)r$kWELkz`T+er!+S3fmrl4e{yD>x(y@8VeXG8&)C=IZjjs{Z|AT6&G$dY6m8MjOv2i`|D`7S7hEa;y9M@zKB)EgE0Ed%@Ch?7nSv%XF`l;k)D+nZoSknuuOZ zAC}`L)su3&a4{h&<(DYeymynQgoCdGGSxl0;aD?fRPH`mn8nt}5koQn4qfdK9iL>6 zaN-`hs9S*47-V*g^eW}_M$rp1J7hqRHB{s5(T?a2 zYS3tpzv#?6`pzHHW1{D$(TVlc#Mo%NT}K|YO!fRzQbJ6$4nS&e2=~CDw&|SZJ1<;9 zCl+y)G~erAy-q}}##JIGdE8C^s^^m?8~=uuL!i$^v=tNWs>2OJ=lK=Dw#6hVYGiDJ zqq7c07Zfxo^#&PtnOqNk3g&}?dMWCGz}?SPfFBezAi1pmSfKCiqIL@k8kYP7*9QT6 zhZJg~pcIy)tATol!Qi=O1qs#K}9~G?A)eL-#gOoqds;Md{p3GwO-lo z4{O0ZEWS8H)#z>bsBx$13(MyaOAI=6{;kj{_8R{aoz@2Dj*t$Wmbb$6T_Y2XT|<3@ zf4B92{&tO1{W7+Gd3x4et>&-_H3!dZIWvUt{>ZZPFK-*QRe*uIHRptO{?nb~)!jSe z0JW3Tvf6VL3mF-nvbJhfkBF?(FfwFpnvcR9ogAJY*RE8jdez8=jlybI4H=R8?K*WE z;T9odygzYXK0Ni)vSC#kRtg#B`9Wla@%M&RLkt%*zy+gHFNhTZ^c!Bbtmm@;x7a30 zOjN?lhD=NSCR~dY&{x-)6Ib;QcZ)jM{ex4&A>nQfIDZ?E{9DMNvSq`=>>ZrX8;GAH znl#iOt$*AwBEtFe0R1av^-udce{%k(Y}b$>_|4HaDHbPMMG6^;-x9FB+C|_1M>~HN zB`l+`wvO1Ckm34YMY+A$Ms`Uzgs5iccaPWWu+bE3+I=+BRGK7R~; zDw|?Z-3Z$u6H^tE`bQ@U@!(i}W;T@L!B3JSIEyb-bRBw4Omsw}&)MNbkq)cw<_&UQ zrc`qO&0f;*`OwH_jUpS=sZ=YfR`tpa19|5m4I5XEs@I@yjmU^b4f{D?0J3{dP`j=* zpr7g^GQOQC$IJ1d&}*C{4C>QKHKJAfptyM5y@ippXCH)NX-k2eG))p-2=>KNTaU~Z%*W2sQ2Zt}@`|cl|Wn}&GzkXo~)C#~IjFr?`+7*@p zL?t$Mfl)+>24tjF(v1D$sftQZJ)bTsSDPPa>o>7Sx9=A|%4{_ST|vq!&tQOP9YICr zI3O_r##1E)jbu?4V}un*L4I>Xc={Nt4Ro={%Ac(Lqv635c~0j@oNNk^iBW+M!T`>I z)f;#j%pa@FP=Lh)mif~Ys{EMfda}OW~lBTN^i+xp+|4#%sD(%h=D<8W(iCA^`1x z!eSQ`8E|62DU@gyfOL#P8_`zP*!XtQbf`XS?4fPd7+6EBamMEwC(AlkEpJmTkJ7Qk z@aNl~Z3%wh%d7<5IuiWkeF!64hP@8H7hQg{9^N@qce}qT>RUpTz9WzS|^!8%CK1_ zj)RE-5Czbw6jHIl3^G8jLiGgxZ?t}CVOf1lpM#G+dw6|L*JJai?+ZR?sn9ieqlqm- z17O~Y;KmY*ogf{NyzENX+h;)5J1vy{zw>h%5 zpC?uBSvWd)yNNLa$QkAhkd>^8jIpACKyIZqQJ^>*Y=G5>lIMj{Y6MO7A=&;hm+zI@ zfA#oJYeMcnTiNn$Q>zV_rLfYPq61JdkW17AR<%uq< zhg7=~y8eTDvDJfjnoyO(kU9*s?rZ=72B76EuvCCKO9Q(cAh$;A_$TxE^&v=Y>Ou9c z1xM9+xU7UAF=b|%+Rm)3C<3dC!4A*b1dRcX8gP@a?aKgxgggd^EXCt+B6Ij!ZsDg} zUb)jQW<|wL(<*0oyfhm|IxCDjYz%^L&PhcJ#xOEdRc z*09r;i(l-xA5>+lDQsd1s~kf`^DL=DhmwFKwuv??J^-e+BpAWnoo)x#6p&wi$Wc0e ze4}p)e}1IGvUeZNWUS+ZH)FE{TCzc!^}-dp#CmL&$7@`C_GD+8yK!RZT#d@ReuSr&lqDo~J$9X+Vib6}nJ^zU^|e(hyVID~>a&tj}pywE-oO2aub<0znrCL>lO(>A}6? zpsLe%xKL+($n-elx>C}LCZCkpTr{*xg=|etZ6B;4vI@=V7-c}B=Yi6XGY*go8BrsF zl$V}NDZ}TSS?P`8`!l{7y!^*?1xCMEGoC(0mNTU-kq7uTg(HT+D4LDM zP6m1joPux|Vys$v+De^Q9@vxVDJ@&{f#EAF>`HnpWV}&!Y=LE_OcX*3K*tqzQcUJy41L~g4+{Cfd)KW(#l!~F2>yKdaG&gk^A z$Hy>X9 z)Y73(@G}#^1TgAovdXX;_6E^L;%ET`ZaAh2#j9{qja$2%7S+~=Jh$%6t$%;s`!~1F zTu`LOkWQma9SN-}HYc6}oe56NyvC{mf-i_*S{a<_aa=X{%h<~GR5-x%93rq@UGWxQ zF4>pcOGUk1UwqVhkUFUcKsv0W|<24VSoWZD?_~k zCE|QS0-Bs9IgVr*Qd9)v+1rRC>|@L)gcZ#`T#B7Jxkk~?PW{$oim7u6DT@p^NkCa+ z6=cjnK}ANy2IzDikis^}7?pLVQw?CRKExS2=18-S%hsG4+xGqAi%)!>-ITWrIu0Aq z=xr(}LMY%oBNhu_cTgHoSgtf{42GtQZ|p-VZS|H+>fL2q`aJBhukh&tF|RAo@%%>_ zejk=t=aRi@+cCvvw(Agl$^QYy7lwXH&oYt>FdK-(mT zT=Y}$3loMAF*!kGR89m8v`o_=wgLeN$Vc!C0L*O0Xgusqq9Z9GG}$}Wh45u}3S6e| zUaR}C;E(I_Tw~6^+1V7QlEi?}33Cy!wQ$x&jYhLk`?2` zgZ8l$o(J2OXS-H&#_2QD`|pitvh=k@vEFkt>Ep{0&wlK3bd2MLW9%oU^u_`*9`PQQ zLokuYaTR)`5RgK25wUx#<`s{Qmz`{^`i_?FFpBvf_FA=i%eU(KJ^2Q|zu+@-v>Pz5 zqM*Y!YX~R60YN+y#7Bya#F0x8jC-peAZZ`t`SsWNN9V0rRJP^CJHBZy_9F9$ z`Z63TQ3yxrSlgT+gPKG}!cZY4qg)<{(mv#F%d>(;Z#Fu4JNprQ+zB+w|Cg+d5Y`1rBw>`z5+z7u>C)2+b z_xg`wWg?0K{vYUHbjt`UZ!~*jHaX@*0%Y5DU*A zT>f*JmP!2wzOQ`qxIhat;CHX0sD{|N>CJ0fM=XtGE|kw1)4b?5Gs6|ok{TlFkH%L! zj=d1ybNUC1noqObF#`(_*n%2DdAWFRJK^^3-?gv!_JWD0 z{_#p4Lda90v0P(8p)na^-`T@2{KJgl4Qw3`5lIn0RH_v);`1_$sP+ zh+5|t|M5}bLKBl>BVu}dlymWGQo}=>x-jS0$2Z1qzsCtv7xs(y@z~Eh5nMOvI4-Mel!Y zUHZwIY(ZfU`|hjpS_xxjcL;206(J}kZiH2C_@qo|+t1W))g%5B1+jzISu19k4gyyB zM)b|xSIJ4;sWO-g?1Xt%3Q?4AE~5%Zree58ug%!_}%W|*MP z_MU!nZmt6@hAui9vEtp`X5uWbsA8Ci&-C8U^VK7pH-5S#!AgFg|8gB=<^dO=+{H|JjGie@zRO6r%136Wji z-q2|G&Rhd$Qzwf`RbQ{_Wuo%6XH6R~nD}1e+HBe4vY-FijN={H+GQeJw#K>U?Y&iF z*X~8TTJKyF`>*3M_zweKbx1k~uicGe&?&rqydx$$t`lIQ5`mTw9jDqsHSEGC)akF; za1^>*H5uKdqC(j?6)iGornI7!ktJ2is)6#GMx!My`MDEPt+fOr-k^TB&Vb9P zpc6K2fe(cK!_pGo~WB9H`tTJcn*r%qBy86+ko@aDF|K0YTx_`$6wAFZ1hcix@ zv+UccC*API9hbc_jebX*!+_LV9wR5&l8dVLX@h}ETb0XJ1dvEm9{g-Sx@1+d;`8&2&vnYo4_>>i?Z(`1Zje`H8XvCkXbwJ$9sX#-f)z{8-m!Us=%&g4fn@MN9H|T< zNu>nbXW;3X7ar(A9xtC%BJ>O4iLX>BfS2wPKbP>pBNefLacHNAsk_b754tn&J=idw zcz^aiTJ2MRI{^cuIlpvIG^ZNKo$DRW2Nb`5Rrw!SiJHMm{B%R2Io`K>yL{`$uU^@c zes$!GJ7WJHXc3$%H<{y&g6_UVGDUx>`A6XUYlbHZXHEJU*_b{oIk4xLjsaPR(bormmb3sko zUKTc-DVee3k${-PO!8Zi6?q<+@t6lJ8CKmiFYXNzkSdw=@sMUTBq&c2F?ceHN9jDt z6RBLJrKQFrO$YrdY4S@a*M<1#*U(1sBno$pkqSdzE9C@UBt$E`B8U!W2@Zi;F*Q-a8YT< zWke|jmk1X-fspyiU@JxV*Ln3=uTY|I*UGc{SRs(i2#g7nF(wQ|B_W+B0fbC=%a}cPPR|tLm^`vE8gK1{6`ZLTR>1 zJH+;6yj7y+r=(FNkr|0b_swVX5Mj2{9m?6a4H{B0I6Wxuyz*eCQx)Ty44rzPx}%_LPpQzvVcriuq&jt* z2uS^}b%h3#H`a@}f+h2gLktcO>WkBg|w704)DpAhO zBRgecxi3J?)aTFD-MqhRx9?WXdZP84e>py;1pf2gF<39|)OiFpXUZE@kdchkE>H)% z$i@(t>_C0P^a|4wUz`n1l)EDQ_I8`u=6CRQI;%6BZNW*E)Me12sxnW=w8R}tgIKR8 zXjV%2g`z0oDynRnLO9iy%O=}!l^0EMW)wL+{4*B7qVk5iG!eW#C)InjdQD16iW)UK zNlsdDqfTWy_vos=au-z9Yi;w9!A>zhX40o35|!2NbEd<2k6xk$LMC7qJ#X$h9qUzz z%}%pl9?iEZI`u79vB4+jsz?Km%S8g251;7ezx&=4*6X*VaegH1^=Oh}kD*Z1hZ7nR zH`(qAAwuSJ6M9YEy>1-Vt5LS7?4(fDr4md0F0w7GPCy2cf;SOCgiJFIJ#TJ&5t^t; zCAs#3R_SoGs0(I`f#-=?{iZgfTB8C&ri+;Fo9m&bZBnsV0G>8^PmmQ+|})B9ACVpk%Y$eP7=AKs>yOI%j97*&+{$cS#?!Bt!k7!`mu*8M!*=wq`q{jzYxJ;Ym8U zaa2=gNIN}kUfnqw>(z(q&qp)Ht>WEELOK4n9ik@+x%ZsV@CATi>z7uAF)-^Ocm3JP&vqn2BgW@37o z8LcTM$TQuk56p1^p(-eDNe2r=(QJzWCQ2mgG&r-of(1uyWJXrKN3G%&-|2xc9gwuP zv{?KaHP;mu#wCpwt)esM$cvC>WP0N1;h(9)dgF~;Wkw-Xd5O3^X>jSK&RAOED0)m* zG>lC17(L(ioP+fm6*gx(*CUm7S!3#;f!`iegcT-}tJR368`I4~w{TA<&?)^k5s{17 z9jVTcs9k4r^Yr$PkgG$D);`l4Leur`gRzKPr5cB$)yS7?lR>pyD3Y1m?L@}ZmPXo! zY3iUW`c)q2(rS~;8g;8Qa$UM0b?`GLeM>r7=;}fZOx^#hcX!P2{_l9sSGTv^{IgNC zmb!i#EU37{#>BgQd~n(4kqw1VE()PP-E8O{j}40aq|9up9Fh zYeymG%iBp3*DJiJqD;dlO*aKJe$op_7mko=i%mEhKY#PbA|+@|ebPx@Yb= z02NL8I=D8KpxCKVbU2(rr`sJ!ndJ#dhKCju(+5Hm_N+vNDw$K)Rv?@rA)yKSd=_&i zn;_F#Lji5WOvfEfcoz@o!Xa<2F~&2wP2xz0vdf)J_+y=2ov{o$O))Q&beFz70qbo~ zh}E_(M@p@2wfG{gq$f-^MjW_4uSS!b8T>%c(Z`;Ku}{feHg~JZAWCORpWMmi8Do-8 zmqG1OpvlI3TDgr{6(2l09tbQm0kq|`uTGFG6YxGLF*lKi9ead{?L9hHZTna{uImA~;Z=u>N`%joIygq&oY+n#hL+O3AX zOBdCKLa1+;54LED%U6y7LXtE%JpsQ%nk_hO9U+T24w-vJeo~AGnP`YRs5VZ0=v1sX z9SIt_S&v8K_DJ=zV3d$2@O)AmF{IHEh53$;uIkqtPr-U^SxMN@#cxfkjGd8SzO^eW z)SCFDNA5;#WV);9;s5+HtT(4IhI1}~S!6aRWkIj39q*EoxTs+9pwVE0DAN;s<15gq zxlWBUN3=&QxYoigv}t^H+$Hh`lDUEb2$|+6dfxP03v@-CNO{w8o73Hxk*X90Z_3|c zQx;p>QAL>+U|QfTC)Vo}ngqeFw83rj1>MDnLn+IrwD|}(>_YRK8U0W1G+Vzv3+v6> z4K_iMG-xwz0Ulw91QYyrg*Pnm+K|p*n(1kQ-@(>a%qLSkdDs$4xf8lbTUR!aka|ou zOIU%%kcl}<(>?kS8(>^M@ygyq7Hw!`InKgR=0}B~A0bs3Fw`l((fr}38G!q|Mu9~`unsHArqfo<$gMj}s z_IvmN44AQB9|`~E{OOmk`4a0{iMzVCd&8ILHrI2QpQ^xrQ4)E1${PfLE(&K3PAo@5 z4m)=Imuh*BneHRU?NG*Jji0hAH}yR+{r zog_h?3>gwW0-}2Yb$2uWsEH;#c+^^mr-MW~ETs*qfz)#iaz(4wsB)X-fHTvgS1sxj6br=x1JzEX5LjA0i^ZC- zxbKfS02WjdWF~+kBr|MPKim*fol3;Y$SAf{31fpaQL6*`{f%RW4pI&_bsFF+h%B)? z!a&^CzfQ+p`n*^uPxvU9nBy+HY$^TG1lwU&;PEtjI-rI8hFS&vj8VtER-=~o&0D|) zM02(UFa#;6O9}?{j*7n@LI-BuRq;1~#!)2V{!l;-d7wyEf5;q)48HZBdN5t-g8gPh zxm7|$LB7k_i_Wat~-v$2ogXX2>9&wqVRs$T2i##4s5#+YTyIvsY;K*+yAh{K_n=rC~1D6cTK1G={Y z;gwy1@QT4EbQGGO*6ifGz0&m$^745v9DMTEsqcA9pC2~7!AEX;>kM=3@zu|cQZD)^ z{D;3+3;kN@XgcPBs{qNZ@QU?Qq-8BK;=%qq-4StvlA0w0zegWSr!UZCTREI2rGQQAFWq)IFSPK2UA1Bju zO~3eR&V*uQ|AW*$<_+F(h~UvzrOh2cC~XcCE|}44u=RnE#hu` zoZ{S7C*AnyDQ~XO-@o*XC6tK!8iqrJfEF?9$V?0L!sZS*RZwOB zxTOAySzY9~nP(QqjL*CG-b9t1G8*pl&m7RDUN)~EQU3&ye=Of}GJH~NdcK{1>%aCc zTky9%TkFp%!lx+T{`{#=xHib%y13(|-H$GSPw!m!)LZAge8uakPHfeNt*`XfFYI%? z_Fs%c(-FWEC0|4V5XZJ4p=K56=70mssRug%XFmMQKtD&a1I*oZTKiR_q*wgxj!P%} z`f2eLFNgVswYHkOoB{AQ;pTSK`+p6Xj+_$*C{iM2^0#EX5h6{Z`z+^H5)ilvU)dnA z`3E+p!P<|_5iX>Q`ileo?8yXZ;{fvy=zeP}B#BYWEAIA03MqE@dy|s-A1XG-D7R_t zDz~9SZ__GO&ZPt7#NcQRW%ZDrk-oN!W4%8d4Q)WHYXIXTH2p6}u2NGnil-40ry&zf zhoFJx5~8go16QokcMPPiuuGgg6-W?H`slqwI@(mVzM6+;yJJ^ucf+Arsh#wM>I`aQ zW^l3OosKXAM!#wN^M`uv1PpHnIPG#(hQ`vBI z2F3b>>I~}m$mTGQkHgU!6zk82bgQdwHz@_0?mMm`X@d{MT$XJ=%;)RX*{G^*aesRg zhRrTlf{sHSnw4TGRcU5iG1wJX3~cGZx-uy?9mit`qbAHd51Yfh^I%}o?%(qR?Wk~) zsymKmgNobJ&~8apTT&|SNEKnU3w@bnG~~t8M9JQ!2ol~1YXL%mP!dTZ?jz#f0vv=< zRPEdV!*j=49zqU7GmV1;ZaXMwrLjqnOD+~F;>a<_dUW6smwB{q!trEUL&S*`)Wb)e zidhdHg#_$#DLhpuTL~XKO7RRyq{_!{9YG|K(}MM66-3ZR$ONA%)ef7Upd5avSGEmF zslkkFrY=j(lm{Hdpi407aCC!Wb#t+ql*a(_H$hQ|ySYEFICXmQ&RsGO~x-;K@e>zYfhADq=S%Seo3kUx!8tilTpsc$G z<=j0e8yEdIki3nFJkPap03MLn`jECSm^Llk~| z=;uhbiT^v;DAT_-@l8i`{8=;h&t1B)j>G)KdZyy`T=tBoAq0VJGUMI|9w6jNdVRw( zJi-mOZg|9h8LUd&ai2Q<5 z4GM7l0km}@-Vlld7&smc6$vU%p@G-HSi129a4 zysCH_8kh1Bsk()*iaSU`PXuspfgU5UcVM%^@esA*De}78;aB7#s4Q7GHwK;Iht5I9 z5hFN1+4IeEg-)(fDcuISQL9#2ZPrwT`{G!>BMB%odf^3IgRu_|a=MMwOC1qwo7{T04@h;H(8)ym5nC($IX! z(ynxRI`o^Wl&Yr9izOZv1AX^E8D&;95!uwh9miT-xkM_2mYn%C8Jceuf>s?(P!kGL zqDJCoY6h%4DghlN}rbsI2J%XnUi`&_in?l5b( zJZ1xWjyAq!=+)a`qBcjwte_l5 z06qM71#3>}oD9zZ=-!wDy|IK01>!LA=^88XG~N)P7O@*4hmB(m)@-^!6XkP@Q&Gu<)fSCeg!3lv-xkSEq4DP{>EGMuqq%s}$c9Aqw(n2q)QdN}7&RPVh|T zS?mX}GDB2GE|K!J;$)D$7LySYk$~@)c>p_!=l2VJLXXIU<6NH<7YlfPE_l&oJiy!( zf_IHC06<6pujh&Y4$tcc;5i9*b+uK9BQ;4c&gZJGKM6Y%G0ZJ^s@fJ%l|T!MeM>Up zC3*buJpegMoqkb}549hnMNhI;!uP&k9pJS_E5sC!!fuleT8TIbn<$Dz8Kk6z082G& z1k92%Vci&rH131df-!TvS9gmBPVQKVRq5cHONG*K*?{A&yiW{zvIx)aXqm7dgZCJG z?*z%_EL(iu!SCN`nY4P>jt!?gd~gD`=rBcpsFe-IEb?Z>&58XJL z``tF!oH5JSZg}d$_wO6w|Hich+xO{!%g8%5y!bS8F|3fYXe{sDT6QN~`7pTm4bAp(ln&($=rA^id8@=`4=hpJ21B31 zRkgM<_(%r7wlV}rhM=}Ggh+<4wlYLWhNz~?2!^AZUsDM%7~O)JN`Rs07S>b(3`BQr z$3YAd#5HY$1SCjmDnSYoq&1Zw0|~OXhEwUo{asly9Mbz|&A3w=*4A3py|h`?jz7IO z)Q&&BFVv1dy(iR;KfNE+jz7H@)NFQA`#{aOQ+q(oxKsMSX51;=Uo-BM-me*VO6S*% zJEiYy#+}mj>@CBoF#FxvIQO4Ea%HdStSO(G7hV+p=DO2s>5{7OZ47Ix`fXvHxhIpG zuKK57%@drp8>XK;VtR%15_>Rq%I4hnRZp_#OgY=Rd9LmmjP*#}k5P?^C$<&OGiHEWqGW(zO)vW)$T}v> zUUe2Bc)NuhRX+D2h9%Pk7=66px}hvXhLY0*{1zq0R&&WPS^i5?J{DzjY^JsRFXs1< z%fHT@yVgaXh21ttu^|Ru{J{FsCh$I+R+vo0*_`cbUQl28;=XsTp1A7w`bm?{#TE=! z4r3VPcw2m%3vgV$Vr#@G)0_RfZBOknn1?!3*`P3IPzmyj!>yO}6 zgI8V!D>#KbiM%BfhX?^eMS-gO;4Q8VJtbz%0&iX40+o|_Hs7Ie9>S0V@!8nvGk^ERy7#DgzRF+ zMp;3~d3nzTbGEO0pmTGRVfU8nXKk#e@~Fy+L^KLcZWImkKUEn2?cnYPt2>avT!rv) z6mYU|0Db8RJBe)>Qdm}rCpf{-<6n2l9amm7eI|Nqf0tKTc5{gukUS9e#4>dgt>awY z=Px^D*1kE5r(b`;r8B1Qs{6^-mBXxR#klvB+6Jz=bSeR!7JmW_FN-}N{C-r<0~4i2 zsA)R1a~L>mOFC;X&BWq7d(CM*myWr4ovg?p+gh=nQx6-?wki1mgwr-|wUv_xI21vDy94Y$O*F z`~7Ow&8Ize`jxNBSA6&Lw=Y;j7yaO3h{I7&dA32SG0%Vez2}zgzvU_v@56g~)$130 zv*eUB=U#8!*krgFKHc@&E7%ineR<9!qj$e_)8*qnub)GAc;A_F{gBlAp@GB(y5m_K za@@Tha^$x83;$qRA~7r5KcRpMrXI2B(u4H6Q-^o`TeN9aKgIN8xE zun;~fzUQbfqiV^Wh0ToiRSB!*!em!0%$ka;Df5b^aAc3qyYSDAA547Kw{FY6>&H&U zZiP2y)c8^wZ^Mu_Ay_DGP@`~KqglHBFn>xqkPf~oxrrl#%&+D$6|HynuDI4RRkA~| VPN-#>&Y5=20cvTf(V}3F`+sJHlUe`( literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/executionHistory/executionHistory.lock b/driver-app/.gradle/8.7/executionHistory/executionHistory.lock new file mode 100644 index 0000000000000000000000000000000000000000..a45935c5b0525307356bfa86bec6accf5a307b8f GIT binary patch literal 17 UcmZQ>?vYyl=!a7v0|aOS05xRy_{pWN2uJ2`CSFe4}v-`2`weEGVd#%^*=%^D2D>?t7 zM)*%#{-1wb_@{*kEJR=-0t*pXh`>Sw79y|^frSVxL|`ET3lUg|z(NETBCrsFg$OJ} zU?Bnv5m<=8LInO_iGVSf2n(D{p&K3PA2`ks2nwtO0#VaX&{E({?w=9(+rIa)KR@tu zrPo_$-QxxItBIKIFSPtaY4UtF)MGqx-BF5vubN&iStp99;d+*5ne-_Q3uqsF1k(dw zx-1?{zq1(XsWX@!MAv4k!*ccm>}TzN^muos89u=psITV2?QcJ|a<%cOg8iIckLec< zb1O{BKlFpT@ffZ*J|(nl78Zv6u*+h4u-;X(Ewlcf&^~-KreAz?`e09O-WI4w*5Udm z!S4q-^rWGFbO)w~gddwc-sHIo>Id^MJv1_crJa8M7+EK-wZimEO;*Gml9>_E-ccFT z!{mhTcBLO4gSvY(riY8%=m}*!5ejwhc1(}p?rbQO2~30i^H1S=bdL6&w;JZq-nbIi zZ!yKNIV`G%x_$Iu|OzQOD-`w%s2`ZXM(9ukP_ z5qlljxg>O2vyb*ZuN`*$)kUbMDq?z!KiiJUpY&*7WV7LV%#L8E;ZJbm*X4?NgA3G3$o&(!({TMvT(_i^|4!(4-(p-(5@Y2qb~1&!CqAz$ z`IfKWN51|9^|LydeJl&Rt=6Xta9xN3_2%_JA ze6QZWR!0;|;D`2S3^Dt-Bf=R&E11#xniS*u?BaTxBqNwVL|$)9k6+KSYPs<4K-kZb zDqPq4%QtZ;DG2H=_`1g*4=)+oBrykd=gYYLuitAPcGX;ky5=)XPgs5OymL(QHmIM< z!u2iZtuJv0oP@f65w6>{XSptMs)TyjD_oBn^py3}G1MN?k;Ckib zN5a*SEOh)k)UR}6da`+? zi0+^W+7|~t;`-?!qCVX>8))yj9M?|dzsbz^!8%eW=a z{+@cMA9cfZ=}MMsyDdbZe#{xuQyGgTT=K|rJ60YCA;nyE74(*A&_WJB=ZQEYduF-|g9k&!*k6t6JUpFHQ{p#ZTF|D}AXQp#oEY!2k;P!t{gPz}$VO??k_*Fj9bZt(nbarJ9>E)dy>xL)vfqhn905wtJR!1NnN51$1=PJZT?CGKXSzlcLr0R8T{v_Iu0lP3gZ^+_9Y^&NMvOSS+38v?>GP60* zrNVQZ$c~?b`76HZ@7?@J2imX3`^gVfB3wy}Re^p@wD5jjOjx+=RPlnk?Fg>V?Y7jh zK9BBE0-=~*pnu}r-qlv-GH#kl=gK*zU;AynUj@bxV;zxxhW%W`>tSJL&i3-+X(^~%;&CoYx#V~;FrEYIn)o^v6$NA* zKU~@Zb*pDs|2OwrTRi#h5C?S&UtDi3QZ@*F1@AuuJ$GDxIpfrN;L$y@J#jUz7fYT_ zF<-BY&T%LFTq~B{%lRN&8Tus(-o^SU-fpYx(%_HIDQ9V1Kay18UM&FgnaE~?>%nj9 zQ;&N=d*X6@zZZWK=rtBvb{dY~sS&fk#pH4&nKg|I>gUaHy=_|7XX0EL)MNT^y(7y} zPO}k>-x!Z`3H`&d9fMDQLVG{_94YZ$RcjMmD-Lz7pIAR7A*#ZiZ?l-8ezpYHFK28J zZwW!;JarP&Z!a1eQaLlF0qytm;Ch!5FCo?$o!8b!F}-vNUDb*;CxfB=kwdsHs3dwj zK>sGx!`N{BNOjcGgb=ikZ16agp1p77CA(~4WRWpj>qR->%j6Ag~zR6KYQ_dUgo`bQRC}psZdXRkM&=6K_&8U zhUO4iC$7cwq@2UgDqhGH)&Hzzn0@)aH76Kip1}JR!37`x{XBc+&DLedVgI>!e%}B3 zis)d`isE+F4(q3azSOk8E+ZD&dxYWo;jyqYOqQtL9tgzrN@;0_IGG4rI8Js8T+cCf z)DK^b?iB&&o_mFjhWdW}L z=+02mN`~hGVc%9vuR67XYoBLdF6>8W5Z8Se2F>!{(!qYxMR7fAlJPoO z-7=(8@mh}w+Q+uz_TP`jnZ3ON&kMpnTz^>55zfZ!c^lg2#$)ymfAqRu3H~fc)``oX z;rh&)fDcX0&d}b(2h(eqNBD1-UPgYSeQ{lCg^xho@=R!-fbW-@4FaAiai*xQW_-l$ zlb0S&-EW%?{qj7-_0n?;gE|7;u%B!Fm|ol6epK4dpabe@M=m`K~P+##F z>*q0B&90*Bl1WfsX^iPjJg4$JLwwMCgu5)RuVPmGd9mRF*`5%B$Dzsktm28?X)w=; z!n<+%CvTG~C!_eGy(tr}&o3Um`mTE?^vhm{=}%RS#)_D2vY>s;a$MJKRndE#*97fX zT*39EJr2#eCs3U+!tY~GpJ%PnZLDvD{aoR|?4N1&-|06`v4;IDbHnvRbsrsC2y#I;v({rVIAvM;A}VE?CyxZWJa$l^6&40XL-nBL6awQA8PjxSL6 z^T&0KSOv*1&1>LzR$s^Up+plQ=5t!mJ`uNXc@mke%y4=h>KF0-+tOKXH}>I)B-HcD zuzsHJEGi_%AAtQ6k~1*9RqoBiiAKgMXn#N-*NcCgW(oR*>VRh-rnfspuPG8s@rU+q zt+<|)BVnVQ&q>yat4cBbg@K#FzSXM&puJZot{VlW=A2(X1od1zZZ9sZx3YF3j=+BS zUgGw*{pO-S$fEjr+#Au%GN#xL$G7;lrB~*`Bx* zUzgXJKEZqRo?nCgXvyRKlomgHRndUf>kxjg=rojF{{7Rh7tlUN1GDcUI`ZkL-HL+x zv8}kyq3dq@OhO3yUB-dyAFS_h+31AUF*^&>yOYYc53ybpfc6}CJbUbO`@R$9KEVDD z;cPg+W-jG@Fqy7)-fA0=VAL4kd$S_yG1=<@Z$q(HO#H&QW+1_ zkK%d$vD%}TQ|;t$s5@Q7?ME`dJW4wJgRB!d4Ke+bOn=?6ZUZ=e;u=i;`{~N0#O>^m zN!ZU3aqKrf4~U*B@vJ!o^{h9TKH|PkNo|?fL#U_Y`8E=<*x`711zMN93z+>Vhwht> z{B&DrACIs5sLo#bQ(yYNLEYaQw~rFDWO4L??-#^1_PCz>CDxwn7TnjwmH7QE`+7>0)zmGhwA6=sQu7?|q->($Y$2r}Pq};NF`9@sz9@pEG z7-nQwqJ5o;$NB5F`BQ2?mmh-t2QIKr8jsLtEt`{*rh3phC`FZFmk6xfkR5GpXu`{auYP4xFDc zeWK6!*+H=s_`MCm`Z1rMK?Z>2v&bK+`zUef}@*B!&=?ci?&U&idGFCBH8G2D#qz1Q)5FrY}nR)>h8^D$5r*I(F4(dq7sfcEDlG5y!BDV>Qo z6DZF4t8qQ_qzmDt^fpz9R|-;(Exy@Pwqc zAMA&-4A*B&mAvxbet`X$reONtMdo8;48wg;&n(9E&sPkki-42o)F(Y;UCUb zMDJfG@i-7a20!XuJNpazO*g^&`Po>mokHgW^+*d$r)yS}=a4yu=9?ah>GUU-7v(i{ zqk6&?kL#Jdn$Nz<9z}6jh3l{N(7w2ir_iZk6f_kzGuKTnALp`bt(`7l^;_leoK=UynR0o~``$3hD_Lar-Ad%}f_EK0@6AujlLI1O-Io!r=E6 z1QUE6*FV*n-n-<)S7?8{2zh)${Wh^Wws@!?{*K$vpXCU> zwpteI4ofh7qb2>U{MJQKCM5qy_gm8NNcTxU{EY+rxc!XNnZg-EbEsR(WBR6*<^q!i zHms=s3{2m=tfp-A%N`4;N8{(h=8ZcVl`l)9{TL~W+nawVl@t1b)+@CU*F%@Szp(e? zPS{UQE2eJ|j=QAT#N!P0OS^IXl=uOzXzLYFH^%dDOMC#+1D-Z1sGnlP>{U*Oc664t zAA`E49j2=$=rpZcw4NF2T1Rocv4xX;f7b1 zs${4KzQpxjMS?||cm>o$@jA2p$zS{P_2Vf}Pf^C~x6fJk4R8IT4Rs4Vo;%!FdnN9r zpmWMaAG6;PE?I3efPJ5HBMjH?4L%7Yh7Q7hqCVq#Lr=qJ89y(m@5l3bXJEQpjgTSQ zUv~KYVP~Vm&3CtW(K&c259?>=Q=^7%u`R-|pG$8reV2k%&Hd-;P$t+4SXS~MMwDKK1*9eX+xV}kdNG{{UYuHgT9#3^m_Cw<`I_TbV0PAO!y`81OV{8P~jT|OS*Ip+w{fuYZVrUOu<<)eC z$E&qak64fOqazf&Q;V7REY!nsdmY7PE52E5L+jUe9`#Rrf~g&;?9uS zZ|<;v-;0=TD4Kupw!20-)U_vYJ@mJ*wW+Nf)RXXhFgn2gvOF*h`8CAvZ$?Q=5=*A5 z(D~>zgY{!nalk)bdpD|M=kWD1nz;P+OWFjwzn#bZ8cTSL&1dkRfqt(lVf`3y{S|xn zx=0|@GqrHt>hH#fT|?;J=!UPa@p<;i8TG%%q5b}T+`jsX@Z&$Z=zKB5?|}!B!>>%G zXIVmf-Tj!oi5UGx^@4DepZ+|!K6pPjV)2GFXn%G7Kl;3oh|-$VP|rSz>4%PaN`@Ta zx(W4AeEg<7LmDjBx6%FK8h-AZW}5FhW??!7?cFV~e#`=uo(61odLkDM{B9qu03 z0sA+q#q~>qyK*jaq52=&Z{g`CTIq z^@8P?y+!Gbx0BXP2cT|+=Yz%k(SV)-;wGqH|Bl&PGOTs2&A*7g9}aZEbteAuUEx{- z(B38j*SFQaX_yN}_kq1Rxc+uTJA04CFKDkbg6T&U&5y=}R@OuPOc}0U?YvV~cBl&K z#}?yyJv&p#VsMC&+c`T-Kem45?PpboN1>jN?_VoUk-BN&Hguo4jGsqVJJhT%2Yf4n z_CEMJ+U)G??~G|h^)`Zt^>4ePb+ySZ<}qk*E{N-$#sSA>9sQu5l7#7YzQmCqRq5!x zDGgs=yNrbFe#3Q^&|VAoYtI%^T=#$(<+CfE&-VLQ#k{`w6V=sNXRLqwTd8F$c|*{? z)5hcPaCB$x*nbY5w+>!nAC9N8{)W2Wd#oRaGRK!JG8Pd~_r=dghp+bH<5&B3 zLA}5evv>S7Q@rWT7nCPDc-?cH&q{wNd}c4SH*Cc0os?dmde*ol1M2o%xE>kaM}Ofe z+Sd;FdFs@&VK&S4xhS;Pmc;CxEpq14qZH7+MIX0!c99)9wDdlTn^_ZXe=_5Tb<_<% z*pL1aT+eYDZjpCGby(XB(_Iw!qxq7m!=U}aWw^dyqGR6%?7zQ_!0Ve!MSbwaPrR3* zeZ(wg@4DJ^-qqwLy6+vr>y@iCD|2`+a~HJt!uN%1!rrL#Ma$@+elZm9=Nk)KsQpK@ z-%q{5_4&B2cia5X_h9jOd`?z-Zp;q0=Z5`Ux4`UA>A3Uld|;2}d!q{1tLVi$9=833 z_D4H0-L3RU&eW~P==+3g`!M~qlBCFG_H0&Y?}*8N-NiT24KwQ|LOmQmFWe6ttGDUHKu@_u={Mk$=mo!B%cR)HU&Q?TlS{0DZFn>c`g@>*vf={?Ml& zvE$I*WDwKOs&qOlUavsw=y3?sJ>FO@BsPb8;D(+EMbDW#cIs{{OhAO z%baeZ^V$wSAAMO0yrQP(>Y)8eJP&=<1*SQs+Y_Mf@fGXG*GfR9@Ul`L)Xng5`o6rs zJ@(H)8`N|0{KPo$^8j4y!EZ`}UxK7xoSAh)nF1fbf7zlOt~0?m15RjSOm$5Kdb8N6 z3XJ6bNm$J+-J!5+>6BD?+~*qac#y+n0{xkf0%;FZ5XYWA=wGyEj4h18oayjqCoV`l zkO!8aaioI>1yOw~n8k0z^GWT>T`xbZodrWB`FMct&y42O#G5yhmE{+l_P_JJ%fmaz z2r40&Ks$gwkD7R}PO#pnykY68&Bf2sJulBA0^NNXNblejqq?E;HI-g9=wOdYQ-;UQ z1~Wux0ZY*6N#8zF5SwCm7rsfZnB}?2Q@>@^A!bBqlK}$#OKKwKrpXtnuiQ1C{%+X6 z$;>$)5va1z$59j7LgV?x9p^smX4sl^(1g(P&rvNJp(Z#Z_bc->q>jk!N?+l(&JE0z z94ietDz>xKM56A~`4wv}w11D{=KFO*9{l%TWMVHQn9He&-YUC1N88M=;e1tccLa^W ziAW~)L4x5iHIX+lN|#kI_;+C0j~}0MuYp?eUsrGu>25(0-HfjRZ$7-|4mjwM#BaCH z{5Hj?KTrp3Cd;#%S0d?Ncm=jn1%U8L}#z^}>sZY@iPg`ad^4oB5b zM36QRXiTIVHU$x%q0Ya=)UL?dW980u?RMZ@f$T$;3=kLwsEKFavQ{~iWVbx3{<$kB zCl~ZdCa^WnrY4rFZt8s{+34Tz{xn3iKXUk=KIlpHf?`zMZyve-6!3BX%iQuSd{rKJ z^CSDv1eT!DdxHlBu~}xQGUr13SV>8cN{LM-SUEBwLk0+RV82ijJ_epeJi-sxx+eX; z-*}f^7!ekbAXrfo!Rs>4@I_h#=S;X8@Jt7Q^NkoSBzg(#EOJ{xO+39Qd+BxyYuhoC zs_68KXZ6X1$kk0Gdt!_lsq#_GVnoth}j4D0^$W`tqtQIh&)h6i9@kclQp@bFR-7x=ct7RJ^vZqVS<|Ec#3 zi&Y*Z7;~u!*{@M12eo|iY<;KeRAqUM-00P=wcx!W-Pga!-4Wb`$n&U#K9(3z6CGXoOEMFj(xvB;jQ3j5 zy+%Y8B#jUvZgD=jXOTE_ohv;jJ2y`oA9Hl1sdfvG1_K8i=4lVjUO-umi z9(m@a&(v*!G>{Y^aS+oBm2q{cJRsK7ZwY8;EegCe@$hQHj?Pw$TN zFs+FM6{9t!dkGRltiTcPF8;9y@yz<@}6zdaY#YLBS0cr`T5Tv#Y>`6)=+pRp>Qc_k6 z#y|4$nZFPufCy5~k{Sp2MKLORQ`>t_|2Y1MoH1XaxK(!zBoe^xCAC%T;6Xu5&anN; zEUqn;ujkIuVV4GX9@3~1mXQGh{Wvu-rnEb;JM>l7a?4S}?Z2DIwFD5$Awd^JO{70e z35{M_;r^+?DkV;zPE(_8()brRzN1VXkjLJ_oC14u?X5{L{4*74DJWrE6ziR7k%%fB`TJ1{BGJ4kK=CTONi>mXwC24QMjV1ZWJupYQ4mJ^YuA0f67QD#^URuB zQ#Ww;B+Vlc5lcwtAq8=#@rSc}bV}{LR`%oft~8SGKK~&yRH%tz2?se#=c7jTaj;M)wS{4A+ef~n&=VT z{8jJi*>m&vru^?T?*q3aQgq{wLShLxvnXe7&2uHlxl@(fJ0&zT_f>8fB8(ux+eu9j z4FsC?%#&Q=&53$Jr+vX&9odHsBv#Y7$$U)y{8F^C=9{YmA(oT>g%~2Nk&iBF9}ZK$ zODskDA3sU8;nFu=24+h3VTlMDS>jPWbh=to&f?;xO8sa4R^Z)+Ol(60>8*ld&4tRf zDp;xxJx*wN`8h}R>qSIZAYzc3Ff?OZu~>w$jwy3cu*f6}jDqZAJ0gBj6Gdf>{g=Ml z7xyfR=?l5GUH}nC5b=(hn0K<(n(<|Pb1(2u(1>;-xO>WdC(26*idQT=m7OO$2CJ> zUyw&-3Hk<&_X~JXjB3`a@iLb zzd!`G9yH!kO&{FJiRISl2(&t*7s6RRgotCLF%bw$NN;%*qxzDrKkodxJ8dnSkjR(R z<`P60k^$BbQr1%tuZb76oGkg%Iajyag-coXA;OkS5NPee(N}v;rZSJ+pns~l`4DG< z9wM+c@22)~=eTU-iL0tAo)xjvQ{yK7h}e#N(8$EQT(+UP>e>Y?%G{xf+ANWXK)aUi zF13$8^BWuvPmQ+RdocG~*-DBP5#X#MHQs*kpqTl<{(UnX@%vIYJq)RM@zAjy5$0ro zzzZTlN&KE#c5l#U;P$1;-dg9oUFaN)$1?E)HBsohNyPI_iPSSajpZj_l#L-D=$i@N z0ct{h2e*ZIXBOA^o+uC5-BQ@hQ5EH-Q5nvvuBqNmND?~eZLyersYe3xfmKl&d+>$u z=FVulv;@Hu{))C+OSU5dt3EU;+@yFpVR9?C?TF&sbYtf&aPE=!2bLu?-aq0tCi#ig z2yWx;-qGh-zrh_5YGB5o@zQt`&XTiG9xT~ANdKlHZX!$*B>XM(yo)8P`!RCP~950Q^u>L8BqS;y1JBH^o zjh>!AfW-=(&b-sqJ{kyt9dgx+nw4hFe$xlGfpL>ZwF6j!#tZU{a#Xsh(x$h}zHq)U znBinCVB|%FCCMHTH1aAlaW$jeGYbO(@oC+s!m2HZ!19VlbZ0L+JZ!wTzxI8v?x&f| zbKHp7PIf_9Ee1X*R`4+E$eGGDS=j~`*P4&4mI4;!c^rlWtt=@Inrr*(uj#VJ>`JJZ z{0Wd1WWpX1AE|v*ZT3GEZ0-AXtFpgzL{1f;lTE*x} z;~fga7#B0SRZhzMMFdtE27n`qETJ1Nxc*#?`%C=Uu|K`R64L)9=#{96F<)ynohd)} z;;&nibc959{*$1UyHTMEmER0XwcL)J-{>p)IuQ{luV|gl(pr*j&W(l4_T!h&gSV^mGYqL|&C8|7B{k4oC?JdKEhz!EgNui!y3bG?U~=*}5lzqca%NE7R( zvrdTEMg|CsKGekHTv2ZYnf7IW{!R@R2?`b=0$Xz$S<;YZ5m;a5%J6N*cSr4II*_a6 zd7wSWOXI9vyf%jUHoa@~RDj~Hx{b5T5rMLujz;yl>UX;N?Q$zeX@!bLZYJJ%M4)p} z(tvs%pGDd(1;*Jfc3rO(tiW+{2ob1?(nV1dFML064P4;Ax%c*-(@(GeO+y5hSC!Pn z$qU~+4zIYf!7nIzpj`7qAR^R&C1|`q!GmHw1Qgo1n8nYxrS5z6Na3KnG9s{j-bzg{ z?Hkm4&@ff*;(uZENU2W)BH-#%d@_SK(SiAgnCqtgJ;%sg+5O{!XLPyZl)G}YY>mEIgMT0FtNABB;tI+ zyB@EVzkff&ZW$;O7lZSiGFGxdJkNSkn3*Q;Txoy!`XGo6Ij>N*)6Y;7S`#}O*JfyK zt>d1~uQggT@XvYBs#isOO!=$@89uT!J$<7*_-zp)j)J~Hqq_kf6f4*?d?tbYuS55& z%wo;PRog%fB##PJI1XcKBKUo8I{To_DYm+6&&|0m*8I~4t(qv|vwp^~CTrdO@-oE< zAq`$cSc1MmTfG=OC`KjJQfWBl7Q&)4DI8JocCG^v*m?e&nrMEwX7>#zt)y308p_{? zEx-+iJP(v5j9|Y|`WT*J6fzG#^jpS##F0jYZIrHVydr~J`^})T6JSuG0KA`py`Tf9g*;)O1i!BopDO()= zA_9BI>7*voxPJ)0IDRwi+ldp`dkT($wI=&O`<#x34`=P6pw@T$ubwiFV(mUekHtzA z^bH!Vo8@rGp0TsK(d{q!yhe2VjWduBlvlLgy!<}eiPxK@Z|J_i@BDHpTkK7E2lDX> zd{V4A!!o;%f4%tl8y}f#=%`DDA|KcdfJWUlw_aLdKmMp}d#sRL_vlzNMXZLYeO$YC z&MAF;EN^w+Yt88vXEj7%GpBJQv(dPr*l0S`_wLnb#))L73Phm1qV?`9U)J2K|Ji;o z>sdp!!l*9;hycDwjn-YX`He>Rf!grH3})&>kLq88YC~Q@TS(A@I|OB{^mRF18TZT8 zYPcH;)~+5Vs!UiIdpT0xC5xO zWWo}R1~j@H@Sqq~*7(u+n>9q0{x@s7(iDwAu968@sp;2#rzUo8$+mmLqyIyoPEc8( z@0SiDu(NiIn)u^HFdL8h@@=ie#F&|=!d*n5Y-jGFCRTawT=Q-~VlsA?t&%L+Io<}}N*#R1F zH+WEt>KcRaJC8X2jej!JFI_0<1LG!-3RNGv$J7LC>mC`o?Y~({a)#V6NK;Em~Ji9fBz;c&Hz2Z#d zM1&F~h@=ygVpMuna*umba$Pb<8C=3Yd@Mr*10=+0%%lHP z?d#rG(e-uL2kv(s-~Ja8aep8oB~I;Qt$CMveKX<9x=8QB1($lY;E%^wjYOVA|vz=MML zbHPzbV`Qp4zBfm`k9!lS<)r9h^N?|+CM*LIAE^KGjAiFtcE+Gobr>DO z;UmHA0`vZ2gN#UG65~@YwOT}Mf`lB6Ti?%2Vdp1;>qpPzd|?yNdkxNS@~8wMK?FA& zN*`%+0Syj63dV&t8D(7`YHwaAl)uNV{ZfxikT;g|JqQ}eKqrv`C#P5$H(cA4+Szn5Z^#e zbieUi^+Ngi=kMKD!koApG7!N830XgC!YGxI@v28uX!{qZ0E+%A3}HXq{E#!ei5=tF_DdnsoAJanV= z^@EHzHecAvX4Vn;3;7U+gfxu`cRxFR!^*eizJi?+F=_KLix5GI5olsd!GpqwxX;ni zPUX)^JwM7y3_TPn>v#I`XlYWKST--T)5@LX~JLxj}Zt$m*zH8%;bN!HSXhAPX5FD1z^3C<%|r zEnLU?3J2$J9E+ZKQY(T8RH^Cxsfo-Z6ZhyI?A}#X)DYsbR28f>*@qbPp``=WObc2R^gUGVjVX%VRwzC$n0`r z6Kh;G{ibDktB?;cI#Q$cXLqiP(x#Ql%p&~CW42TXl?fn%bkcw(VFVr&(Tyw=)4Jon z_3UNtkgb1~vN$sEH+2hC6Puif>O-=d9hLtb7s?q?H40GpI(Cqx!&S zsM+?(NFqf`Md6-v-4;ZE{311_P2fQhtF1!A!ZPc88s46nkt~*rC_)4;832Ff1U12Q zI_w(Hkrk0uEg>}m(+$`j1eK1|#Mr=t!bd{tIls}_q@Zn0)}L52RWSt15TNl8>6 zPS@y&4f1?K_uWEq^{3xBN&c>im@~%buoL1d^`{@!3YpHij@HB!MN#Sex`%4;~~zko1dlznXWp`SM>o3Nq)89t*d5fadWX z{3d7;;5?xuZts7=_4(YoS84H!HdfXyO+Y?G$pAro8#VELUG7KWEBv?m_gu|+ADl9Y z2yj0kH6o}jls+aF@f8<{nx3=^Bhq=@FAYJ&3NkVU^HN_p^K@r`);+-mY%Ehu87_yizWL@G!qY@z5gH<5aMhYVMy0YQH#Y4v)c#8?R z2HHMF1gRo`rbx;!3Zf$Vn8kGHA9myRO#umlrEQ2nwS?e7O>E@jQR~$I_E5}LF04!B z2D*{O{Umt+?H2e&;iJv%bJwD$8cw4_Dz>^ilfl~qIlAEcYEmmK0}l$q(1_UdxpbHI zdM2*=7l%6DKq8J*5kM1<1`i6NUNBL)r&r?Cl_7=TuKXP+y76e{Vx+XCAfn7iR0EQZ z=*l>Sf7)`%`z;#PB9aH%Z;*29_*po;3M|4$T|<@VHZDQLYDmcYf=>z`u1ew_%HnS| zmNjmF#S`=A1DeNgNQgb5Cb)f0@xDnl`ox^-Vs?JTa}a-Wtk7Ll2COKhkCKSsQRBZI z_t?x&^zc6z-iHVU=tF9Rn(#UL%~0TtN#3)Ak-3Mr^kX|p0uo{%5|ln}I}Nc6eh_^c zJ^IrwSkyxc`4EDHEXYhs!gsfA;}tP!jtBD=7V_tGt{`G5B&2Da&c7a(SE$SvoD!^j zR=xJsvoJ)+KtkM)+DA*vJC$K;rf-|;b3co=)#M=ptP81$*MJAbdi=|-B^5K!XzkjM zSO0pyG@PEOOVxeAE>ZFj`iPr`gm?q^r0`LEBX6eR##F#YbEh8h`>rK@baFD? zrY0V$9Oqs1w(`z(!?#hATeMOTL8@$^iGzQq^s!Zi{g8*_N7K|#zIrK^%aRd+t%n#j z;n5Q0Wg{M;|Bvvp8TkJmhWk|;sxMAF^^w7qTt*7&udqQ4Gdj=V*d+`igb>HCi@LMC0(UTYP>gEZ%QD5PGosAq?bSBl^jmLNfisCbsx^=hC+&9%Vtpb{%HQE3En>%ki5th_z`iCE*y((R zny{1x-4#Hil~=2eNK7UY202D zcNMPdT>A5cmf+1c{~;Eza^z8MfC#N`yvB_;8Qyg`_s+q4r^`7P`({XBcLp{ZHF3IS zV^Ll$V_WIt{Z(zZcukQHUg%>zxNlL$D%5R}?Du6h%O+j)&M>PU1}7zXROmEd2R%>{ zKgx-6?jfgqBZzSwNq3j5Km-r;A@h@(IKH@Zf;IWxCUMm}nuRm@DBJP)WiGcSQcN0!p% zb?N?CbE;Ox8Tv?gMY0Eff~5i;6h!=$@iO+(_~@y~ASsJ6gGfY_kpY4@4Pr#9-#h7i zQAC$%p=^IrFNh{-1rr${Aw+tIrtq;$PObL1(iKkCL-$+eot~H>AEA&Sg6yXx92mCl zewNbuY(pqZT&=|wbmAoVKthm4Es-`|zm|Dv(;rD8zU|%5Umrj|UO+-fo!ZCp93j`i z50y`K)nr^c8Pu~8@evY)aB5;t_eFX$78&=%Ovc(kF*I&q9)#5VqR@z_w`Pb zx4!J>_U&`X2bd4336VZ2*25?xP4k!gnfFJ-5x5KIa8NFYTXh$V@kO2bY4QfKIIrqgz{QNH{W8(wP z@i)pf4<(JI#D4{~kUXjyNJ!G~A-h*TN77g!(j;2we)HVy6+|>6ViC2E^yXcATNwJx z*BE|Zc75-SJ%~ViP>6<)Wd_%t9JKY^)8@JDN3N4*7$Qob4`CXF5l5UFzxKh?&uiJg zR8KpcL&P6Q2+B~8>hUL2gS^S|yG~h44Q&E~P-RFU-S9yZ0_1H96Hk|rut{=13ON^tz(Sb;7>}((R~ShNWG)>(UXzxmXuh? zqr>;na!Ha8x{D@GKw=3g>nY};+Z0_^EjCeUU4PJhe_z~#fBFyw6_1j*R?8-lahRd6 zyRFo~_NtxI3MY$ncHfE zh)c*vIyF&t`C3bXA7jh2qltv7fWufOc0+=J#tOd<%b6>`2=Pf&(r{Q0Vr^>GLc_+(g|~Uy@8}NjA4e0lL3Wb~6kVp%)P$XO@LZsbGu|H<^7RDx=mTFw;=s@r;{0V9Y*~ei> z$k3>8K`&Za+IG$g&t)#^Qa-o|BOV|hD%3t!M(~Kft>~Iu5!;*D7V83{O7;QnC!{8H z4m>DEwPXMJp93p0IXbE$eF6&9=@C&y1_(qjFG}K18hdiZoA>jR_5)vcemMau0@=qY zNXW=g6K8bGl<)V2uj>lm^mJWP@pD9wG7vPuMc_d(D$Aq~KDsk)CGYdLcV4$4{eAyr zA01?XAT2^o6g`mdwX29&Z0`GXaB$twNkoul4B84y@SyOabir#SSMrfKx5raAtT%oG zIZN`9*haD^uvu@QCM>RdwTz2A>#I(`JY^l7i^ZyfOb`TVWa8mDdb{HnbyO*d?m{n9M7MSZjf z-0;ahNErwkFO5C8A@=a^qXF5icEXX(-j5aykF_=zfRK>uQdGKFOmBgam1uQxfNlHg@z_zwP&r{5+dA zb^Ztekg7-@<*}vCEEY!T6qe9*{twGm_2yhZ1?+U3+S6_vDoLqr!O zSVE|Mq*@Nfn_bM`@XhD#(J0#i@K#426*@VW)Ke3W-@J}Io))8X!TwX@LD5YLh-igA z*sZAv-3x(5i48dhyUu-%EZ*Dbi3pTeVy@JL(d;Vcf!HPY=Bm1nx^tbYK|~+)A^47( zaFgT;DE>jGeKVQwR=e3ja5Mg|^H>WaLAmC+(plA9Synf;_twPL_VE)JVHiZ1I0 zYQky^e7NKM&!sRn0+hzSz?VqFKA?*_iB6G6qPx{AGYqh#LZ@paS6#xnBEtTmL zHIb|^uT%8M{5|`|nZoT(hKh(lGZ$>5Ce)HApI-5;w`?wvc73_?CAQDAfhEb9#;7`1 zU5)w3yZnzze(rg%v2Hgsk4KQ;p|J-)jD8wZ*C-l$ZJMjzuvFs#8Wm~fK$8LgPC4_x zPS0C4ZMX(kh`tiZDZsu}OE^dd2tuS!idcnf>NjmPH(ohwuhBI9Jqw(F|1}e7eJ2z0 z&9LrPaL4d*Ns|XkL9HMw$OMQ0sfqJ}2Zay+OOm4^4hJ~z?@=}V*tZ3|caRBiCnYr@ z8kM2_{p8!bs^N78Zfu{IDfaJ2#9c^8bAwL`A19Y2D)B|DAIjVDj4-4u1pYjY>;v8U zSc0et-??j1dzfBzaQUxm$Zz*dL%?zUPFIH6qZ=X?;_avQy3de(zkau;nrLsIa}~5P`n&5~NYv_gQc_ z?xCYkuKx2?W^PkDcIz{Mv7&oIJt~jFj`1HvSE+WxV&TUwTG);Pw+&JgItv~Y(G{Ly zwtcCuG01wUO>~JyZ5ou+_e7L-nh+ko%JjKSpWLC5)ml6#3*WlO;zAa^#N_> z)V?eM`>)dv!aF4`>T z%kO*`g<_RR2MKYI{gm_Iopx-xY3;GL?zrKQj9eZ%aS}QpK>+ijBpMk%`ji-k>)O3ZU`%X<6c zD8D6)YxZgkbyT-`}5k-&??4l+fSr6Q>x>FT9z7*U_tGJgS zg0v1K^4`k^zDUjl2rC6}0&iAgk+kOHluKr-(Zuj37bljsEuE^p%$s6TB4^ zJUeo}+hVokBO++*+B@<#1r;Lt1;+YMPU&V0yZ+M$3yn-vIJ>0x!bnn@q1tilD z@dC|*Mszo{pH{sVEEXjYtmvaJ?}Z%%KSDHPf6IOD5;2=px{T^luVBrOMZe9VV6L)A?=T(2t-&?6TNw+FWt7qJf6ERb?UET z8aka*;eS)aDo3g*6f5|O^D~z@+kIyh@%J98mA#Tz{XD?SHaBF26vKNfPdZw9uz)uRVE$w3|~5TyDa`~z*^G()rR!90;kfG z0m4>UYJx4dwy|P(pn$=4)-;tk^$CtDXP!*Nd<8i`>Eo)mp6G>Y4NoECF0W3}L)DPD z3BF?@H6d_jQ4)6smf8`0>>2ibX>vATtJgvV9~mGl>Z2wui&Z6`+Y$3f&QLGh`n2FA zB1mPN)M$*VxjONF?gN`myJO;gtCgja5YZ0-PSOWOtg7~2eX85bj31s{K?9R#;; zQeNFe1c8~F@K~{{*f*2Vd0pyzfpTz=HX;T{or6Y$c=;pyR{JDdcH;W>H^CQ0j{eU+ z+x2qnGA5OF?u2KNRz5WQum05fO-p2-@ltI;d6kPlDFWpEj@B-M9Kp zzM9R;-_4ehBL5`(NOPg^@h|h}A(?_kW9I)7-T#L8mlbS>E@;hz!%n?4KhVJ}CDq9N z(x5m4ng^-gf<}w@7atw}PW;Q7gHwUrXv{q9{DDZRp+$>kH=leZ@=z3uF8Zd3umNxs z(Y<(+qh{_$o_gH1dtJYz--4SMITQbzSpCbIqZ5bL%>QN05#dLg48^GaW#(^4rl8T7 z`M<0Ox&hD{)wZjN?OlJ2?MsfiXBOYo1hFB{{J-(>!qk@GzF1C2l=OHqPh%^3+s6KX zxqhUPQOrYAqWkNpR`6eZpjgrJA@#?Ld;6?gaAA5&_w`*fAe`h_p?T1n`M->+mlPz>XsqDB5dY0Q z4v8QA-s`jG(`E_h)74d{&@CKW55i&Khhja(%N<|#Yn$m?aUXT$^H^tr=JDU`bN<$G zVdb^Hr{#wQ+AhuB1ljRFWr>k+UERQp@nyD%54R44{yFqN$0|Y3{jc+8@6BEUWT2rNWkAp#2#Sct$v1QsH&5P^jVEJR=-0t*pXh`>Sw79y|^frSVxL|`ET z3lUg|z(NETBCrsFg$OJ}U?Bnv5m<=8LIf5fun>WT2rNWkAp#2#Sct$v1QsH&5P^jV zEJWb{ClNqD6hKsDI`HD{Q$M;fI4%Q*zo;=C9=R~Leu)m$3;J+9I_S1voya<Su z8Si4APQShb^(#4;&b-37{#+0j_!${eJ9q}y&Ap`6V`LUX-E0=q7t_C)vVBVcKM6-_ z#-g~+#3Xf?P_!HBhtzQ0?ADVSzm4f+ow#&4rn4yJ2Hwi~PWrh%&@SPAS!&v=d6qpV z{rn7Qn)8_bl0box@aQ*Rpzdgo>jS~(x;j>*L*0cR(^+2+beax@UxWJfI$ZCx^b-r2 z06%jL8d3NSt`DZfq^@rUKR-!oE+27y>Z9-C66I{DhdW|A+pmr1U-P^GKWR#8Dfqgu zpV0f5ReBf2|8O*B&vE?O%-P~PeQ1B z;he*b(BouyUX09%OIPEZGosS&x;V=sV1K*{=Sy}yFDwmelHOhsd1B zCW82Q{jhjr_cXA#Z^!vknM~ocnw}GY`=dHp8g%IA#KcZ`S8VzTWd9{2=d$cz5wJh= z2Jvqt?T&in-^s!Lbm%C~xyL`QS9!Az+_*y&I)-zet~ zfTyE*v>ZtQ?~MW5M8$?oH1PF&)NbAIU`!`0`C_W^su z2*j;!$J)uNj{&aJiFgX5>38!^cz2pD+JE>f>nCjeS-^THvZFfZZ<2BCimmekaoPKE zKLV8@X$na-_|-a_wdqT8oBKVxaDoc zBM9;C#EbU;&p~+*jI!*e36#tLJi!OqH*XfaJftuMxE{*C5R3bCh<7^J-w4)GxV_M7 zG10mlUhIBkQnN}xd_%~wPcDyE0=`EJ@y)T4+VQPTfES?kC8R69^1f!8D&S5H$iB7G zI;RER6HZ8Fz`5{_GaFKiRbhU%7vo%H&yYS_mk9hdoV}M3kGEsfPWCqe{!r5d@9Pl)Bz7v_`*~_D`AyEB^9&V(ZSgm-6KTzsnlKPHKDvHY_JdoFNx0PcY1T`d1TZ^4VNrvT4gh3udA z>8$qunE-g?3!IDR?>TKPDm+f+MB&{ymsnWS`01QQIIs`WMx1qIg*>|;sDC0WT3-@! zYwezJaNPxdgiyULe|&)JxQ92ahYSnck0f_b(^c!%YYY{b1j20yjZ zPJ{Mn9#{FSP|q89(gyg+kI3Fnp1+cQJ-p%4@hi@yiyL~r-HIy)_Q_};lWvfX?+AXI zNan;Ps<^!j+oSZ0P9-o8#_~9qO_p2~9Y8+_{G7(|Z`qWU!M#mCS^>{y$N#W;cmFO) zu?|JR_r)O|z5KD4wKu$T+$aR`m|wfIry2`@{aFRX&mZSEC}73zk0mv0W1P!vXAD1J z;SSG(c14Jr4?oM$>op~t69w9EE^pGzY1tCgPv(SVw2sy!L7~-P zLWgPJ2;eT~k^SJxgJ<6z9{@ZK*{{{2iFGcLg4fTwxw!q>;=4>7g&V_w{RuzBTaVQ4 zZV_Y!JQ}TQMa3+Kl{}%pp#KWoUa{R(ZTW3xxNlp2L45iEYg`te46t`&!udK|+8?V` z7XVB+^lmQ96HX06#?!5g)mlYTa?)lgx>n zsD4y9u1)n9mmCFLj1#w45lfGkzsn8m3GrHp`%3O&Kkm2`_%}s$u96W+caPKq`}=a3lvEAuVYQm4)NwTHWnUb0l*{C`cjKMB-vt-+5>n< zE^e<@?mK$y^EJ4iAMQZBTb^K(D_IZhOH6j>`M|5|LaXl0x|9l;K_rCH@$2clnxID z+z8db#^F4_8=}T=ojSk6?KPU+F1)Seh1dD35Apye z>=i@2?Ve?-jAlCd4@6Nt#K(RmK4tEM*JEY{IN!1;i~TOoTNU8Qy$x|?=|0)~_s;-7 zh4Q>*8;jYnw1F<*`>r7S@TwiFUM0(exGZRWX>B_zx=4i+UQb3Ay%8=ul10c z;|ZK^3qCZ$F7Yx7@L*QN!=+aVdGvAs?vRQ2d7-l|>$C&NoXBo~b3GaNvcx#C;H7BR+ADTa5wuIgIuneRBi$HzNMrfSaRz zL%;3mM1H_i_&VsQ0`A8^G+INCp7#K-Pek?x@|;UYZPZ|0Md%{?x;4J)83cHKbVhkL z=y0^%Te_0;;|bX7N?}w#hAy5%`qxA~$eeJ}6!&A8q`mnezmhVU6S-&+?`hh@PvbKR z?9ZV*Z?|FGpuD=a1aO-w+ zi@~|EMA@Edf9*QJ^~Vs8`!42azE>9TY*gpQSI%71y090{FB>{9o9trgs5_hh`)Qnp z`!UI8%B-5W2Cq*%z9C+}DK&KC*d!u;&WbsE#QVmIN!aTcHNfpM7UlexDkJI`Rq}KwYk7PZTi1_T2x$7U_ao6sGiO2 zgQQ}u*x~DrIMjc$u$-&58K1%Y5_vx2e#~x!Hl;n=8c+5^T!#8%&fTZY=vWP}_p(B8 zd-F5an)Wv4pFv!I8=PAlR&0%2?|u*PBd$2N)c^FL>7&zLz!Og+UKTnLb1(qbN%|ec z-{dYF&c8YV>{D|QpRUnJd9n?@U*}zcbE`n}oBc0(;g64)+(bNHM6)P{ogVl(>V$aF zbrbnDL?6HlH{sm+_eC176fIDP1Y=ZJHU?`7KYqWl8rYX};r2E)B|YPgbh`j|K=orY zZ5R2nmk8D)q4*1KZ@W;?`({~;C9ps2g*cs1oo1q5FW^o`5m&p})$}tu18|)p#IMkO zY1*%)M&`t25s3GE)Gyp>GX?Ao(EQrTTid0?U1r~2MC%TIupq5Z^xP5kzR*duuTc`O09cTnHt zcr0@CJg^T%^X{b4`MNXZAv}K_CF1sbmpMhPcEt-=lqj}uZ`E(0B<~i zar-JgTwmU3eYqMfOL-Ra6`n^@J#qi8l{vLMys>Z}&`0y@W~Y%cW~c<;*D6Bm!Yz3D zdzYNWp#OyMceo$7)57ex1JmF-75N+SJl=A-P4%G8i5%sK*SdEwO4}R-{SQOeKW-zg zlEZ1QGyyLU!tLD$zEvo9eSmdq5QF%1L0*GcpboG%ZpOKX;xpfS%_{kTyRsvml=zA^ zDh=*SZXJlfT>GQI`+)?o*O$V%r%ln%ykxn0z;_^fPcNB|W*nDco-OVod!PJC$K;Z5 zXwQUrkw<^qYCm{>(YL_)z7M%>ada{;Z$fB(z2t%QMC?j*6>)&u6^L>i=bo%qRYT?enJ_F_1 z$F**OFs+LTnG+YIdh@v+w5~APbqTO9w!!`Q8u;^TTy=%{EV+jGHCo9h4Uc{Ud%I4= zTltJqZdrlzAdwl(m+w1{TvlNz77&*k)xTejRnh0lJMjIwEM45senlzqV=RS>fq!=# z|Mr(urs=0QgztkT(&2yb-(}xuGZi-g>@#Z+f4Jn{Lw}_Pz;)4j4A?rz{BEz5JLnJB zG;SZTlW^XJ)&{&UM-*6ycv+=G(_UF4;Ab1Ut_YOP{mQ?+61)#U6lccm1D)$4Y3~ce z{)Cw#{<*Ag;K*{2AHwc8I6ttV(^I~<9@b$1s;eMt35N!$c=$d;lml)bR3g;v@dtt~*6|y20N?L~^I(T7-5qZhJ_bB+5b@$61?gcAu>TNw(Ebo2_qe`x*zh*l zp2#YR+lTIZq1MnXv>EvELlYBPwsU#>coiMsHhj4Kp=WkZoF0|%y2}||SA;Q^2PaSb z1pWy=Xx)WLhMKqL>VWrKh+HVoVOxYJSSQ*~0{;Ocxc@K*Vd-ufyNuwad~s< zuii(1pGE5t*AWQ(rQmP#$N3D*XJ9@9^BI`Wz49sWX|C0d)Oe}@{6CwR$TUn}}pm%O0@>OA}a?8<;N!Z8Rq-WE>cj^eFcUUQ& zsxZfs8{l{4W_#Ad9M3|5?|!mjAt+WB(|6HOG@p;5XD}Q!xDEq;szL zuGwPAd82V80{hMmdE|c>hX9vlc$a4S31)d`&r-3VsaJq|L z7xoH%8bJ7pjfY|ecO8-8yCL|yq<^%waddN+7gS(tk=$lk=W{$=2*wB}$tYs*$5=cw zS$X2k+5-VfjHgdv-|-`_LGaxu>^JV>CdmC|DN5*X5rMOZX8aRIxCN5$Od7bW0J@5hml{tRTpXWI6?DMx1A#mAu9Rb zW6be9B78o4v9VB$e7#}pn|JK}{_%s><7;BqVC&-FdNoJw{-Lh29@Z-L_-!gSDB7>! zF#QYL3;#KTv(5P&^YMomb3EJZ4~p~+51rXPt8=5KnWWZUYUTd-?Edc~pJRvn!<;YL zDrGG==pZK*U#`Ot;fsB8_iwqf`fay9*~7z_USs8*ti!85K!pRjatQNywXdB*o- zF-eaReV53fMy;?*qIG-AlU9<;_x?eeVpIrJ^n+e)*iWtKS>iRKm8oJ7-ughKiN_c7 z{m)(<8mCt5R*0z2RT2>q(5VY67gpziiarp77TdolvzuV*%v!BfUAxs>j?=?w09z2` z7(lT!R)$&;E3?Uk&7fX%!}Evt3%KfbLItdLy6@DAq^qm<``mmH`tFc zq&l_YWnbyLZ=ceeM%D?c`uVWxLj|1kXwqlw6fv~q*(%hx?h_dhIP1T&$ME_L1ryM^UmeMNQO5enJgM@jW~~_Z4L|aH^kSA+ z)5iXvGKPETjRKE>DalTu`~I}Iv+*i{*=6yjR!G>$Z1)xS`_Qy|&v{MD$9S*aks=TX zY8lvpV&u_u(T*(gqgxW?CFI&1zLmpXfpZk+rWMqRSl0SjdfRH*jH`OfHuZhbg9=!Q zmrqkGPPS&)W%~)#$ow>=u`;TIdt!AjW{I`+qyt5-meQ!%(sbo5GBh3Zyw@dzQhcSC6HV@<&P$5nF{trd2TzQNH%H$dugvX?RKaCu~dj%?Sfj#L( zBZWd^@aJyR^I4Lx~gtwuJkuk zD=uE~e} zkqpR8Z&!Ei>+cxg+upgAIC=SOQjk6AJZjdW4k{&yKsFhHlS9t zYKbitSgT1>6LN9X=TW5}Z`z){Mv!W;b>*!7#^zzJA=WA>pfeKh9PKT*u_{tsdvO3b$ z`a?CIeJS6A?N9;NhsjxLg{A&hD;H>Tn;M0H#}*%W2qI4jHayRZNuAI z?^U+iwp_up+lyIZP2T}KP|VmNlUa7^^{JY75(*~o*A^~LuShp+p3y6s-cQsqeq0?akM8Jp8M7Q1 zvg+%>&M@Q{J)}Mn2yw31fudKp1@xk)e1;v5YBxFQ{P?~bD!_cudXer@pime+($8!^ zUt*Nzxn;odqS2X|<6sb`Rw$&IwY6vp?Z3IM@lyqVAePO4_Ubtewc^c>oVU6CHE*7z zZaW;P5`pImRy!~0^({rOe9uYsyiagw=VqJ8(un57=Nzu{E#cIPqdSB?hbq==y2415 zos534ZAPyaHjwssiWmQcavW@`G3=C>1R?IR_h$*Jvs9ZD8>* z6S@Nx;Pv^!7k1PN{obl66~1Lz{+^m15h^TIPytpgAq~3SPCyQdOAzJ1v4)W6d@ z7Amk}3cyk!he~!=*h?kx3R1*d?eH1Wo;dci#Jt8}Uvg^8~w3 zLB$22;CV)^c)Gt!Uu>o=*cYGi>T9lI8y?3KmCMJe~ALUt`_?FnLY zRlu)gB7kB6wntJbigFfgPV(_%Pvi<_=00FE2746+6bonBOM=IQWDm=1y^|hLJU;z= zxd-gkC9;BOjjb@s7)h6z?mVHoQ3X3tC~h2N z$ymW0O~<0x>B)1*8XGBT1}|YbBQ@eIyXfoP!5MBPt!tQ>PH{VBZN>6WQe1@VgE-5c z82O3ky`I6Tsn4HBc??C=Eny5d5MtdU?7tMf>X9moW~t|}c&uLXYgxAlHd1o0fP%m| z%c}KbFR=Hc>pGDhW|X6}eajB0a3;qv9a~HtW2_`}XROkD&BnF51S9@9xF=r1u7Svn HyaxXR(E-x& literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/fileHashes/fileHashes.lock b/driver-app/.gradle/8.7/fileHashes/fileHashes.lock new file mode 100644 index 0000000000000000000000000000000000000000..ef6bd68b439df512c80eda6c88a478a57106b8af GIT binary patch literal 17 UcmZR+&{bKdYi-QK00vA80V)y$p8x;= literal 0 HcmV?d00001 diff --git a/driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin b/driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin new file mode 100644 index 0000000000000000000000000000000000000000..7af4d07b3b9a8d9b79b6a34cd8a511e7e89462a7 GIT binary patch literal 19483 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 + + + + + + + + + + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt b/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt new file mode 100644 index 00000000..82713e7b --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt @@ -0,0 +1,13 @@ +package de.motis.prima + +import android.os.Bundle +import androidx.activity.enableEdgeToEdge +import androidx.appcompat.app.AppCompatActivity + +class MainActivity : AppCompatActivity() { + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + enableEdgeToEdge() + } +} \ No newline at end of file diff --git a/driver-app/app/src/main/res/drawable/ic_launcher_background.xml b/driver-app/app/src/main/res/drawable/ic_launcher_background.xml new file mode 100644 index 00000000..07d5da9c --- /dev/null +++ b/driver-app/app/src/main/res/drawable/ic_launcher_background.xml @@ -0,0 +1,170 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/driver-app/app/src/main/res/drawable/ic_launcher_foreground.xml b/driver-app/app/src/main/res/drawable/ic_launcher_foreground.xml new file mode 100644 index 00000000..2b068d11 --- /dev/null +++ b/driver-app/app/src/main/res/drawable/ic_launcher_foreground.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/layout/activity_main.xml b/driver-app/app/src/main/res/layout/activity_main.xml new file mode 100644 index 00000000..77d9ef65 --- /dev/null +++ b/driver-app/app/src/main/res/layout/activity_main.xml @@ -0,0 +1,6 @@ + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml b/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml new file mode 100644 index 00000000..6f3b755b --- /dev/null +++ b/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml b/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml new file mode 100644 index 00000000..6f3b755b --- /dev/null +++ b/driver-app/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/mipmap-hdpi/ic_launcher.webp b/driver-app/app/src/main/res/mipmap-hdpi/ic_launcher.webp new file mode 100644 index 0000000000000000000000000000000000000000..c209e78ecd372343283f4157dcfd918ec5165bb3 GIT binary patch literal 1404 zcmV-?1%vuhNk&F=1pok7MM6+kP&il$0000G0000-002h-06|PpNX!5L00Dqw+t%{r zzW2vH!KF=w&cMnnN@{whkTw+#mAh0SV?YL=)3MimFYCWp#fpdtz~8$hD5VPuQgtcN zXl<@<#Cme5f5yr2h%@8TWh?)bSK`O z^Z@d={gn7J{iyxL_y_%J|L>ep{dUxUP8a{byupH&!UNR*OutO~0{*T4q5R6@ApLF! z5{w?Z150gC7#>(VHFJZ-^6O@PYp{t!jH(_Z*nzTK4 zkc{fLE4Q3|mA2`CWQ3{8;gxGizgM!zccbdQoOLZc8hThi-IhN90RFT|zlxh3Ty&VG z?Fe{#9RrRnxzsu|Lg2ddugg7k%>0JeD+{XZ7>Z~{=|M+sh1MF7~ zz>To~`~LVQe1nNoR-gEzkpe{Ak^7{{ZBk2i_<+`Bq<^GB!RYG+z)h;Y3+<{zlMUYd zrd*W4w&jZ0%kBuDZ1EW&KLpyR7r2=}fF2%0VwHM4pUs}ZI2egi#DRMYZPek*^H9YK zay4Iy3WXFG(F14xYsoDA|KXgGc5%2DhmQ1gFCkrgHBm!lXG8I5h*uf{rn48Z!_@ z4Bk6TJAB2CKYqPjiX&mWoW>OPFGd$wqroa($ne7EUK;#3VYkXaew%Kh^3OrMhtjYN?XEoY`tRPQsAkH-DSL^QqyN0>^ zmC>{#F14jz4GeW{pJoRpLFa_*GI{?T93^rX7SPQgT@LbLqpNA}<@2wH;q493)G=1Y z#-sCiRNX~qf3KgiFzB3I>4Z%AfS(3$`-aMIBU+6?gbgDb!)L~A)je+;fR0jWLL-Fu z4)P{c7{B4Hp91&%??2$v9iRSFnuckHUm}or9seH6 z>%NbT+5*@L5(I9j@06@(!{ZI?U0=pKn8uwIg&L{JV14+8s2hnvbRrU|hZCd}IJu7*;;ECgO%8_*W Kmw_-CKmY()leWbG literal 0 HcmV?d00001 diff --git a/driver-app/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp b/driver-app/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp new file mode 100644 index 0000000000000000000000000000000000000000..b2dfe3d1ba5cf3ee31b3ecc1ced89044a1f3b7a9 GIT binary patch literal 2898 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 literal 0 HcmV?d00001 diff --git a/driver-app/app/src/main/res/mipmap-mdpi/ic_launcher.webp b/driver-app/app/src/main/res/mipmap-mdpi/ic_launcher.webp new file mode 100644 index 0000000000000000000000000000000000000000..4f0f1d64e58ba64d180ce43ee13bf9a17835fbca GIT binary patch literal 982 zcmV;{11bDcNk&G_0{{S5MM6+kP&il$0000G0000l001ul06|PpNU8t;00Dqo+t#w^ z^1csucXz7-Qrhzl9HuHB%l>&>1tG2^vb*E&k^T3$FG1eQZ51g$uv4V+kI`0<^1Z@N zk?Jjh$olyC%l>)Xq;7!>{iBj&BjJ`P&$fsCfpve_epJOBkTF?nu-B7D!hO=2ZR}

C%4 zc_9eOXvPbC4kzU8YowIA8cW~Uv|eB&yYwAObSwL2vY~UYI7NXPvf3b+c^?wcs~_t{ ze_m66-0)^{JdOMKPwjpQ@Sna!*?$wTZ~su*tNv7o!gXT!GRgivP}ec?5>l1!7<(rT zds|8x(qGc673zrvYIz;J23FG{9nHMnAuP}NpAED^laz3mAN1sy+NXK)!6v1FxQ;lh zOBLA>$~P3r4b*NcqR;y6pwyhZ3_PiDb|%n1gGjl3ZU}ujInlP{eks-#oA6>rh&g+!f`hv#_%JrgYPu z(U^&XLW^QX7F9Z*SRPpQl{B%x)_AMp^}_v~?j7 zapvHMKxSf*Mtyx8I}-<*UGn3)oHd(nn=)BZ`d$lDBwq_GL($_TPaS{UeevT(AJ`p0 z9%+hQb6z)U9qjbuXjg|dExCLjpS8$VKQ55VsIC%@{N5t{NsW)=hNGI`J=x97_kbz@ E0Of=7!TQj4N+cqN`nQhxvX7dAV-`K|Ub$-q+H-5I?Tx0g9jWxd@A|?POE8`3b8fO$T))xP* z(X?&brZw({`)WU&rdAs1iTa0x6F@PIxJ&&L|dpySV!ID|iUhjCcKz(@mE z!x@~W#3H<)4Ae(4eQJRk`Iz3<1)6^m)0b_4_TRZ+cz#eD3f8V;2r-1fE!F}W zEi0MEkTTx}8i1{`l_6vo0(Vuh0HD$I4SjZ=?^?k82R51bC)2D_{y8mi_?X^=U?2|F{Vr7s!k(AZC$O#ZMyavHhlQ7 zUR~QXuH~#o#>(b$u4?s~HLF*3IcF7023AlwAYudn0FV~|odGH^05AYPEfR)8p`i{n zwg3zPVp{+wOsxKc>)(pMupKF!Y2HoUqQ3|Yu|8lwR=?5zZuhG6J?H`bSNk_wPoM{u zSL{c@pY7+c2kck>`^q1^^gR0QB7Y?KUD{vz-uVX~;V-rW)PDcI)$_UjgVV?S?=oLR zf4}zz{#*R_{LkiJ#0RdQLNC^2Vp%JPEUvG9ra2BVZ92(p9h7Ka@!yf9(lj#}>+|u* z;^_?KWdzkM`6gqPo9;;r6&JEa)}R3X{(CWv?NvgLeOTq$cZXqf7|sPImi-7cS8DCN zGf;DVt3Am`>hH3{4-WzH43Ftx)SofNe^-#|0HdCo<+8Qs!}TZP{HH8~z5n`ExcHuT zDL1m&|DVpIy=xsLO>8k92HcmfSKhflQ0H~9=^-{#!I1g(;+44xw~=* zxvNz35vfsQE)@)Zsp*6_GjYD};Squ83<_?^SbALb{a`j<0Gn%6JY!zhp=Fg}Ga2|8 z52e1WU%^L1}15Ex0fF$e@eCT(()_P zvV?CA%#Sy08_U6VPt4EtmVQraWJX` zh=N|WQ>LgrvF~R&qOfB$!%D3cGv?;Xh_z$z7k&s4N)$WYf*k=|*jCEkO19{h_(%W4 zPuOqbCw`SeAX*R}UUsbVsgtuG?xs(#Ikx9`JZoQFz0n*7ZG@Fv@kZk`gzO$HoA9kN z8U5{-yY zvV{`&WKU2$mZeoBmiJrEdzUZAv1sRxpePdg1)F*X^Y)zp^Y*R;;z~vOv-z&)&G)JQ{m!C9cmziu1^nHA z`#`0c>@PnQ9CJKgC5NjJD8HM3|KC(g5nnCq$n0Gsu_DXk36@ql%npEye|?%RmG)

FJ$wK}0tWNB{uH;AM~i literal 0 HcmV?d00001 diff --git a/driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher.webp b/driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher.webp new file mode 100644 index 0000000000000000000000000000000000000000..948a3070fe34c611c42c0d3ad3013a0dce358be0 GIT binary patch literal 1900 zcmV-y2b1_xNk&Fw2LJ$9MM6+kP&il$0000G0001A003VA06|PpNH75a00DqwTbm-~ zullQTcXxO9ki!OCRx^i?oR|n!<8G0=kI^!JSjFi-LL*`V;ET0H2IXfU0*i>o6o6Gy zRq6Ap5(_{XLdXcL-MzlN`ugSdZY_`jXhcENAu)N_0?GhF))9R;E`!bo9p?g?SRgw_ zEXHhFG$0{qYOqhdX<(wE4N@es3VIo$%il%6xP9gjiBri+2pI6aY4 zJbgh-Ud|V%3O!IcHKQx1FQH(_*TK;1>FQWbt^$K1zNn^cczkBs=QHCYZ8b&l!UV{K z{L0$KCf_&KR^}&2Fe|L&?1I7~pBENnCtCuH3sjcx6$c zwqkNkru);ie``q+_QI;IYLD9OV0ZxkuyBz|5<$1BH|vtey$> z5oto4=l-R-Aaq`Dk0}o9N0VrkqW_#;!u{!bJLDq%0092{Ghe=F;(kn} z+sQ@1=UlX30+2nWjkL$B^b!H2^QYO@iFc0{(-~yXj2TWz?VG{v`Jg zg}WyYnwGgn>{HFaG7E~pt=)sOO}*yd(UU-D(E&x{xKEl6OcU?pl)K%#U$dn1mDF19 zSw@l8G!GNFB3c3VVK0?uyqN&utT-D5%NM4g-3@Sii9tSXKtwce~uF zS&Jn746EW^wV~8zdQ1XC28~kXu8+Yo9p!<8h&(Q({J*4DBglPdpe4M_mD8AguZFn~ ztiuO~{6Bx?SfO~_ZV(GIboeR9~hAym{{fV|VM=77MxDrbW6`ujX z<3HF(>Zr;#*uCvC*bpoSr~C$h?_%nXps@A)=l_;({Fo#6Y1+Zv`!T5HB+)#^-Ud_; zBwftPN=d8Vx)*O1Mj+0oO=mZ+NVH*ptNDC-&zZ7Hwho6UQ#l-yNvc0Cm+2$$6YUk2D2t#vdZX-u3>-Be1u9gtTBiMB^xwWQ_rgvGpZ6(C@e23c!^K=>ai-Rqu zhqT`ZQof;9Bu!AD(i^PCbYV%yha9zuoKMp`U^z;3!+&d@Hud&_iy!O-$b9ZLcSRh? z)R|826w}TU!J#X6P%@Zh=La$I6zXa#h!B;{qfug}O%z@K{EZECu6zl)7CiNi%xti0 zB{OKfAj83~iJvmpTU|&q1^?^cIMn2RQ?jeSB95l}{DrEPTW{_gmU_pqTc)h@4T>~& zluq3)GM=xa(#^VU5}@FNqpc$?#SbVsX!~RH*5p0p@w z;~v{QMX0^bFT1!cXGM8K9FP+=9~-d~#TK#ZE{4umGT=;dfvWi?rYj;^l_Zxywze`W z^Cr{55U@*BalS}K%Czii_80e0#0#Zkhlij4-~I@}`-JFJ7$5{>LnoJSs??J8kWVl6|8A}RCGAu9^rAsfCE=2}tHwl93t0C?#+jMpvr7O3`2=tr{Hg$=HlnjVG^ewm|Js0J*kfPa6*GhtB>`fN!m#9J(sU!?(OSfzY*zS(FJ<-Vb zfAIg+`U)YaXv#sY(c--|X zEB+TVyZ%Ie4L$gi#Fc++`h6%vzsS$pjz9aLt+ZL(g;n$Dzy5=m=_TV(3H8^C{r0xd zp#a%}ht55dOq?yhwYPrtp-m1xXp;4X;)NhxxUpgP%XTLmO zcjaFva^}dP3$&sfFTIR_jC=2pHh9kpI@2(6V*GQo7Ws)`j)hd+tr@P~gR*2gO@+1? zG<`_tB+LJuF|SZ9tIec;h%}}6WClT`L>HSW?E{Hp1h^+mlbf_$9zA>!ug>NALJsO{ mU%z=YwVD?}XMya)Bp;vlyE5&E_6!fzx9pwrdz474!~g(M6R?N? literal 0 HcmV?d00001 diff --git a/driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp b/driver-app/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp new file mode 100644 index 0000000000000000000000000000000000000000..1b9a6956b3acdc11f40ce2bb3f6efbd845cc243f GIT binary patch literal 3918 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�(p-{x$&=IACIfoAR!za)F-^da-t3#0Dycnp zwO~NVXwXCl;jE<}>%@xz|=8fIJAB?>+E{7)|4l${4ngA3G|=r z2Dyv;VVWSgZx9Wj>qUjleGl3Ei9K4>h!(lPS%8VOG>Xu0%6VDz^O=bjJmuP7>DeUv zrbI}MlHB^^d?{zv6d=@_ZD2lg1&G7UjnVN{1}9WkaM3H~btX0GtSzB+tZ^qRgWo4m z!GmimlG$=wgXCnr6j@m<1gAL46#T~5Bnm=2{^@>|t&`9mkEPddj zAvG~@Tv~TAm2i%VW}R-g(Z0)z-Y|szHr@rk>4MAyG*Ma*7Yh#H7(!-5>DZ@8r;_dx z{prSe<>~099F8vsYd2xff7uAS%7{S)f(|@me3t2$iy&NEc7OUEchp@9A|X;;IA>8!oX+y(BKJ$EzV* znR$z;!L$s7uy@{OT~nG#B!NRraT8(X##Ho!0r_o@gg0CA-9H^;-uE&?$2$nHv_00o z%cbuUc-tCx$Uh&EZ4Nf4Zgqv)Y6>usG3>GeQnxx_Z6+PcbX-+ysbt1hQ`K1LDpOE? zrAhIZhSN9yVIAOa22gn577tbc&i3|3V8NWy&!tw##`}9*x}gtI^h1DzZRA>UuaJG) zaZ7j)dq!O}{?#8Y7~7i6fHh4{`pL?>-18|p!S75Y#^DM>-S3)vuZG+Q7l@ek zQP~#cBpWgg#mApc_sPYjpw8odQuRokmTkzcNl`^CcKB7e&;zViV;{Y{o^Y$%7i0m# z62%#1Lq!RC?}lK>%mp}T!3Xv;L*0v*>USLm``N%>w>@fwC+#T&Tx2bN4w(20JB}oU zuSa6v^kXi0xPs?pbaOHnyiqq6By1EZY9OZ^^QA>{q-Hsd&m`pbQ%8121aWG-F5xf zlZ%;B{;C>X19|`^_?dVyCq>n+41w7|!tUS!{9rHlbhX=SZO5CQ^;!Du_E7*`GiR^Q w)2!4MKjfSAeNo!9>IaV6aUZ*?W>} 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

UmY2RIYtNPVDpE$%vda+HD#3m z&VuXJ{BK&Qe+rBa7eq}Q(bq|tn(RrJAk|ztj2(i{d>nmQnM?;HF2k&9sA6up5tmjl z7lySlzMbifH17-m-Lwa_F&e7nOH?ESi3#ckR3tsM+jsck3`oG!uMS}|eAwVXv>}qxwq?QY%QJ0}r@^;fhuUA9W z*BVl>TGo&N004@xSiwDUXUvp51sVmqO3m)=B55aPwf@0=e}cN+$-BdKxY`YrT_4)0 z_d10#i44Q*rFr8MC>*)v$EJvz``(pb{e&*6k+b zsMz%($|1+8hn8c2?P(l@;Rb&CsZeYoCI3?2!LqjbwPXW3z4G$Qfj=cT5Yb%vY0(AX oeb?AaKtwrnc|$|zzw9vfvn^aJJ!zd)XFXqqy0000001=f@-~a#s literal 0 HcmV?d00001 diff --git a/driver-app/app/src/main/res/values-night/themes.xml b/driver-app/app/src/main/res/values-night/themes.xml new file mode 100644 index 00000000..90a777e6 --- /dev/null +++ b/driver-app/app/src/main/res/values-night/themes.xml @@ -0,0 +1,16 @@ + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/values/colors.xml b/driver-app/app/src/main/res/values/colors.xml new file mode 100644 index 00000000..f8c6127d --- /dev/null +++ b/driver-app/app/src/main/res/values/colors.xml @@ -0,0 +1,10 @@ + + + #FFBB86FC + #FF6200EE + #FF3700B3 + #FF03DAC5 + #FF018786 + #FF000000 + #FFFFFFFF + \ No newline at end of file diff --git a/driver-app/app/src/main/res/values/strings.xml b/driver-app/app/src/main/res/values/strings.xml new file mode 100644 index 00000000..1139b02b --- /dev/null +++ b/driver-app/app/src/main/res/values/strings.xml @@ -0,0 +1,3 @@ + + Prima+ÖV + \ No newline at end of file diff --git a/driver-app/app/src/main/res/values/themes.xml b/driver-app/app/src/main/res/values/themes.xml new file mode 100644 index 00000000..40ff8db6 --- /dev/null +++ b/driver-app/app/src/main/res/values/themes.xml @@ -0,0 +1,16 @@ + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/xml/backup_rules.xml b/driver-app/app/src/main/res/xml/backup_rules.xml new file mode 100644 index 00000000..fa0f996d --- /dev/null +++ b/driver-app/app/src/main/res/xml/backup_rules.xml @@ -0,0 +1,13 @@ + + + + \ No newline at end of file diff --git a/driver-app/app/src/main/res/xml/data_extraction_rules.xml b/driver-app/app/src/main/res/xml/data_extraction_rules.xml new file mode 100644 index 00000000..9ee9997b --- /dev/null +++ b/driver-app/app/src/main/res/xml/data_extraction_rules.xml @@ -0,0 +1,19 @@ + + + + + + + \ No newline at end of file diff --git a/driver-app/app/src/test/java/de/motis/prima/ExampleUnitTest.kt b/driver-app/app/src/test/java/de/motis/prima/ExampleUnitTest.kt new file mode 100644 index 00000000..e45b587b --- /dev/null +++ b/driver-app/app/src/test/java/de/motis/prima/ExampleUnitTest.kt @@ -0,0 +1,17 @@ +package de.motis.prima + +import org.junit.Test + +import org.junit.Assert.* + +/** + * Example local unit test, which will execute on the development machine (host). + * + * See [testing documentation](http://d.android.com/tools/testing). + */ +class ExampleUnitTest { + @Test + fun addition_isCorrect() { + assertEquals(4, 2 + 2) + } +} \ No newline at end of file diff --git a/driver-app/build.gradle.kts b/driver-app/build.gradle.kts new file mode 100644 index 00000000..f74b04bf --- /dev/null +++ b/driver-app/build.gradle.kts @@ -0,0 +1,5 @@ +// Top-level build file where you can add configuration options common to all sub-projects/modules. +plugins { + alias(libs.plugins.android.application) apply false + alias(libs.plugins.jetbrains.kotlin.android) apply false +} \ No newline at end of file diff --git a/driver-app/gradle.properties b/driver-app/gradle.properties new file mode 100644 index 00000000..20e2a015 --- /dev/null +++ b/driver-app/gradle.properties @@ -0,0 +1,23 @@ +# Project-wide Gradle settings. +# IDE (e.g. Android Studio) users: +# Gradle settings configured through the IDE *will override* +# any settings specified in this file. +# For more details on how to configure your build environment visit +# http://www.gradle.org/docs/current/userguide/build_environment.html +# Specifies the JVM arguments used for the daemon process. +# The setting is particularly useful for tweaking memory settings. +org.gradle.jvmargs=-Xmx2048m -Dfile.encoding=UTF-8 +# When configured, Gradle will run in incubating parallel mode. +# This option should only be used with decoupled projects. For more details, visit +# https://developer.android.com/r/tools/gradle-multi-project-decoupled-projects +# org.gradle.parallel=true +# AndroidX package structure to make it clearer which packages are bundled with the +# Android operating system, and which are packaged with your app's APK +# https://developer.android.com/topic/libraries/support-library/androidx-rn +android.useAndroidX=true +# Kotlin code style for this project: "official" or "obsolete": +kotlin.code.style=official +# Enables namespacing of each library's R class so that its R class includes only the +# resources declared in the library itself and none from the library's dependencies, +# thereby reducing the size of the R class for that library +android.nonTransitiveRClass=true \ No newline at end of file diff --git a/driver-app/gradle/libs.versions.toml b/driver-app/gradle/libs.versions.toml new file mode 100644 index 00000000..ec9c4678 --- /dev/null +++ b/driver-app/gradle/libs.versions.toml @@ -0,0 +1,24 @@ +[versions] +agp = "8.5.2" +kotlin = "1.9.0" +coreKtx = "1.13.1" +junit = "4.13.2" +junitVersion = "1.2.1" +espressoCore = "3.6.1" +appcompat = "1.7.0" +material = "1.12.0" + + +[libraries] +androidx-core-ktx = { group = "androidx.core", name = "core-ktx", version.ref = "coreKtx" } +junit = { group = "junit", name = "junit", version.ref = "junit" } +androidx-junit = { group = "androidx.test.ext", name = "junit", version.ref = "junitVersion" } +androidx-espresso-core = { group = "androidx.test.espresso", name = "espresso-core", version.ref = "espressoCore" } +androidx-appcompat = { group = "androidx.appcompat", name = "appcompat", version.ref = "appcompat" } +material = { group = "com.google.android.material", name = "material", version.ref = "material" } + + +[plugins] +android-application = { id = "com.android.application", version.ref = "agp" } +jetbrains-kotlin-android = { id = "org.jetbrains.kotlin.android", version.ref = "kotlin" } + diff --git a/driver-app/gradle/wrapper/gradle-wrapper.jar b/driver-app/gradle/wrapper/gradle-wrapper.jar new file mode 100644 index 0000000000000000000000000000000000000000..e708b1c023ec8b20f512888fe07c5bd3ff77bb8f GIT binary patch literal 59203 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

K7UpUK$>l@ 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 E2O(~oYXATM literal 0 HcmV?d00001 diff --git a/driver-app/gradle/wrapper/gradle-wrapper.properties b/driver-app/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 00000000..d648311a --- /dev/null +++ b/driver-app/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,6 @@ +#Thu Oct 24 11:58:59 CEST 2024 +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-8.7-bin.zip +zipStoreBase=GRADLE_USER_HOME + diff --git a/driver-app/gradlew b/driver-app/gradlew new file mode 100755 index 00000000..4f906e0c --- /dev/null +++ b/driver-app/gradlew @@ -0,0 +1,185 @@ +#!/usr/bin/env sh + +# +# Copyright 2015 the original author or authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# https://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +############################################################################## +## +## Gradle start up script for UN*X +## +############################################################################## + +# Attempt to set APP_HOME +# Resolve links: $0 may be a link +PRG="$0" +# Need this for relative symlinks. +while [ -h "$PRG" ] ; do + ls=`ls -ld "$PRG"` + link=`expr "$ls" : '.*-> \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG=`dirname "$PRG"`"/$link" + fi +done +SAVED="`pwd`" +cd "`dirname \"$PRG\"`/" >/dev/null +APP_HOME="`pwd -P`" +cd "$SAVED" >/dev/null + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn () { + echo "$*" +} + +die () { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +nonstop=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; + NONSTOP* ) + nonstop=true + ;; +esac + +CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar + + +# Determine the Java command to use to start the JVM. +if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + if [ ! -x "$JAVACMD" ] ; then + die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." + fi +else + JAVACMD="java" + which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." +fi + +# Increase the maximum file descriptors if we can. +if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then + MAX_FD_LIMIT=`ulimit -H -n` + if [ $? -eq 0 ] ; then + if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then + MAX_FD="$MAX_FD_LIMIT" + fi + ulimit -n $MAX_FD + if [ $? -ne 0 ] ; then + warn "Could not set maximum file descriptor limit: $MAX_FD" + fi + else + warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" + fi +fi + +# For Darwin, add options to specify how the application appears in the dock +if $darwin; then + GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" +fi + +# For Cygwin or MSYS, switch paths to Windows format before running java +if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then + APP_HOME=`cygpath --path --mixed "$APP_HOME"` + CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` + + JAVACMD=`cygpath --unix "$JAVACMD"` + + # We build the pattern for arguments to be converted via cygpath + ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` + SEP="" + for dir in $ROOTDIRSRAW ; do + ROOTDIRS="$ROOTDIRS$SEP$dir" + SEP="|" + done + OURCYGPATTERN="(^($ROOTDIRS))" + # Add a user-defined pattern to the cygpath arguments + if [ "$GRADLE_CYGPATTERN" != "" ] ; then + OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" + fi + # Now convert the arguments - kludge to limit ourselves to /bin/sh + i=0 + for arg in "$@" ; do + CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` + CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option + + if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition + eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` + else + eval `echo args$i`="\"$arg\"" + fi + i=`expr $i + 1` + done + case $i in + 0) set -- ;; + 1) set -- "$args0" ;; + 2) set -- "$args0" "$args1" ;; + 3) set -- "$args0" "$args1" "$args2" ;; + 4) set -- "$args0" "$args1" "$args2" "$args3" ;; + 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; + 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; + 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; + 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; + 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; + esac +fi + +# Escape application args +save () { + for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done + echo " " +} +APP_ARGS=`save "$@"` + +# Collect all arguments for the java command, following the shell quoting and substitution rules +eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" + +exec "$JAVACMD" "$@" diff --git a/driver-app/gradlew.bat b/driver-app/gradlew.bat new file mode 100644 index 00000000..ac1b06f9 --- /dev/null +++ b/driver-app/gradlew.bat @@ -0,0 +1,89 @@ +@rem +@rem Copyright 2015 the original author or authors. +@rem +@rem Licensed under the Apache License, Version 2.0 (the "License"); +@rem you may not use this file except in compliance with the License. +@rem You may obtain a copy of the License at +@rem +@rem https://www.apache.org/licenses/LICENSE-2.0 +@rem +@rem Unless required by applicable law or agreed to in writing, software +@rem distributed under the License is distributed on an "AS IS" BASIS, +@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +@rem See the License for the specific language governing permissions and +@rem limitations under the License. +@rem + +@if "%DEBUG%" == "" @echo off +@rem ########################################################################## +@rem +@rem Gradle startup script for Windows +@rem +@rem ########################################################################## + +@rem Set local scope for the variables with windows NT shell +if "%OS%"=="Windows_NT" setlocal + +set DIRNAME=%~dp0 +if "%DIRNAME%" == "" set DIRNAME=. +set APP_BASE_NAME=%~n0 +set APP_HOME=%DIRNAME% + +@rem Resolve any "." and ".." in APP_HOME to make it shorter. +for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi + +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" + +@rem Find java.exe +if defined JAVA_HOME goto findJavaFromJavaHome + +set JAVA_EXE=java.exe +%JAVA_EXE% -version >NUL 2>&1 +if "%ERRORLEVEL%" == "0" goto execute + +echo. +echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:findJavaFromJavaHome +set JAVA_HOME=%JAVA_HOME:"=% +set JAVA_EXE=%JAVA_HOME%/bin/java.exe + +if exist "%JAVA_EXE%" goto execute + +echo. +echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:execute +@rem Setup the command line + +set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar + + +@rem Execute Gradle +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* + +:end +@rem End local scope for the variables with windows NT shell +if "%ERRORLEVEL%"=="0" goto mainEnd + +:fail +rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of +rem the _cmd.exe /c_ return code! +if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 +exit /b 1 + +:mainEnd +if "%OS%"=="Windows_NT" endlocal + +:omega diff --git a/driver-app/local.properties b/driver-app/local.properties new file mode 100644 index 00000000..52087993 --- /dev/null +++ b/driver-app/local.properties @@ -0,0 +1,10 @@ +## This file is automatically generated by Android Studio. +# Do not modify this file -- YOUR CHANGES WILL BE ERASED! +# +# This file should *NOT* be checked into Version Control Systems, +# as it contains information specific to your local configuration. +# +# Location of the SDK. This is only used by Gradle. +# For customization when using a Version Control System, please read the +# header note. +sdk.dir=/home/steffen/Android/Sdk \ No newline at end of file diff --git a/driver-app/settings.gradle.kts b/driver-app/settings.gradle.kts new file mode 100644 index 00000000..cdb3f0b8 --- /dev/null +++ b/driver-app/settings.gradle.kts @@ -0,0 +1,24 @@ +pluginManagement { + repositories { + google { + content { + includeGroupByRegex("com\\.android.*") + includeGroupByRegex("com\\.google.*") + includeGroupByRegex("androidx.*") + } + } + mavenCentral() + gradlePluginPortal() + } +} +dependencyResolutionManagement { + repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS) + repositories { + google() + mavenCentral() + } +} + +rootProject.name = "Prima+ÖV" +include(":app") + \ No newline at end of file From c8afb8cda7d50478575a447e82a633657a95aae2 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 24 Oct 2024 15:58:38 +0200 Subject: [PATCH 03/28] remove .gradle from VC --- .gitignore | 1 + .../.gradle/8.7/checksums/checksums.lock | Bin 17 -> 0 bytes ...rariesForLibs$AndroidPluginAccessors.class | Bin 920 -> 0 bytes ...ForLibs$AndroidxCoreLibraryAccessors.class | Bin 918 -> 0 bytes ...ibs$AndroidxEspressoLibraryAccessors.class | Bin 932 -> 0 bytes ...riesForLibs$AndroidxLibraryAccessors.class | Bin 1911 -> 0 bytes .../dm/LibrariesForLibs$BundleAccessors.class | Bin 765 -> 0 bytes ...rLibs$JetbrainsKotlinPluginAccessors.class | Bin 937 -> 0 bytes ...riesForLibs$JetbrainsPluginAccessors.class | Bin 1175 -> 0 bytes .../dm/LibrariesForLibs$PluginAccessors.class | Bin 1504 -> 0 bytes .../LibrariesForLibs$VersionAccessors.class | Bin 1435 -> 0 bytes .../accessors/dm/LibrariesForLibs.class | Bin 4000 -> 0 bytes ...nPluginsBlock$AndroidPluginAccessors.class | Bin 962 -> 0 bytes ...nsBlock$AndroidxCoreLibraryAccessors.class | Bin 2218 -> 0 bytes ...ock$AndroidxEspressoLibraryAccessors.class | Bin 2232 -> 0 bytes ...luginsBlock$AndroidxLibraryAccessors.class | Bin 3448 -> 0 bytes ...orLibsInPluginsBlock$BundleAccessors.class | Bin 891 -> 0 bytes ...Block$JetbrainsKotlinPluginAccessors.class | Bin 979 -> 0 bytes ...luginsBlock$JetbrainsPluginAccessors.class | Bin 1259 -> 0 bytes ...orLibsInPluginsBlock$PluginAccessors.class | Bin 1630 -> 0 bytes ...rLibsInPluginsBlock$VersionAccessors.class | Bin 1477 -> 0 bytes .../dm/LibrariesForLibsInPluginsBlock.class | Bin 5631 -> 0 bytes .../metadata.bin | Bin 99 -> 0 bytes .../gradle/accessors/dm/LibrariesForLibs.java | 313 --------------- .../dm/LibrariesForLibsInPluginsBlock.java | 369 ------------------ .../8.7/dependencies-accessors/gc.properties | 0 .../8.7/executionHistory/executionHistory.bin | Bin 1062082 -> 0 bytes .../executionHistory/executionHistory.lock | Bin 17 -> 0 bytes .../.gradle/8.7/fileChanges/last-build.bin | Bin 1 -> 0 bytes .../.gradle/8.7/fileHashes/fileHashes.bin | Bin 74915 -> 0 bytes .../.gradle/8.7/fileHashes/fileHashes.lock | Bin 17 -> 0 bytes .../8.7/fileHashes/resourceHashesCache.bin | Bin 19483 -> 0 bytes driver-app/.gradle/8.7/gc.properties | 0 .../buildOutputCleanup.lock | Bin 17 -> 0 bytes .../buildOutputCleanup/cache.properties | 2 - .../buildOutputCleanup/outputFiles.bin | Bin 22007 -> 0 bytes driver-app/.gradle/config.properties | 2 - driver-app/.gradle/file-system.probe | Bin 8 -> 0 bytes driver-app/.gradle/vcs-1/gc.properties | 0 39 files changed, 1 insertion(+), 686 deletions(-) delete mode 100644 driver-app/.gradle/8.7/checksums/checksums.lock delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$BundleAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$JetbrainsKotlinPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$JetbrainsPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$PluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxEspressoLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$BundleAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsKotlinPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.class delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java delete mode 100644 driver-app/.gradle/8.7/dependencies-accessors/gc.properties delete mode 100644 driver-app/.gradle/8.7/executionHistory/executionHistory.bin delete mode 100644 driver-app/.gradle/8.7/executionHistory/executionHistory.lock delete mode 100644 driver-app/.gradle/8.7/fileChanges/last-build.bin delete mode 100644 driver-app/.gradle/8.7/fileHashes/fileHashes.bin delete mode 100644 driver-app/.gradle/8.7/fileHashes/fileHashes.lock delete mode 100644 driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin delete mode 100644 driver-app/.gradle/8.7/gc.properties delete mode 100644 driver-app/.gradle/buildOutputCleanup/buildOutputCleanup.lock delete mode 100644 driver-app/.gradle/buildOutputCleanup/cache.properties delete mode 100644 driver-app/.gradle/buildOutputCleanup/outputFiles.bin delete mode 100644 driver-app/.gradle/config.properties delete mode 100644 driver-app/.gradle/file-system.probe delete mode 100644 driver-app/.gradle/vcs-1/gc.properties diff --git a/.gitignore b/.gitignore index 8b34bc53..2a8f5aea 100644 --- a/.gitignore +++ b/.gitignore @@ -12,3 +12,4 @@ vite.config.ts.timestamp-* booking-generator/data/stops.txt booking-generator/test .vscode +/driver-app/.gradle/ diff --git a/driver-app/.gradle/8.7/checksums/checksums.lock b/driver-app/.gradle/8.7/checksums/checksums.lock deleted file mode 100644 index 3d91ceb22ee1f2f86f01854347be44b4af3eced1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 17 ScmZP$+sGNIyh~ey0SW*iz5<;9 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidPluginAccessors.class deleted file mode 100644 index 0e55e2b9966b9fa80c88d12163743a88c5b25fa3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 920 zcmbVLO-~d-5PiKM!>$Vm2#TLE*~6lSz8EhO2(85B5#V+n(N#LV(narF@bCRmi zQky`|s9Yv0sN809F!jNyB)tDx|2U+AOiCs>A92*W^WJe@X4=e70!#ba=x`vA^v8|j zg|lZmB`1$(&MYZz0)7|bL0zkEYH$e^=q8R-pgJz_wm<%&&XmlR z$>bzBZL)Z`*~YbgV}Zq?O-W#FtPLHNr&DsD)HLVFYDQsj)qp^+f2)G+iO!4)rQ;e$ zw@BHaXIWfmCreMV?(9n5_<-4VCbo15jdaCut2wN_Y6Lu*55|xi=E{5W5q1Oy^W*-n ztrA$N3C&g{!V`i1eA!EBZcSg7>1uHvw!#bp_b2@##4h_yMAquU`Lz_|C4t zJ+>79Vx8?eHaMvUSIHH4Bl>~%w+46zn;dE3KEGQR-Zmcaw@Po}As(U4EFR-2+W!Eo CG!DQ3 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxCoreLibraryAccessors.class deleted file mode 100644 index 8756f5836d35130fb019844c0478ba2a5fbadfb8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 918 zcmbtTO>Yx15Pc3I+k`-AY56Rzka9?i6kiaRRF$I8NQe|61@(+~*Q^X1I~sed^wrJv(@&C)%dkCbI#19nD&!BL2fEP}?`wgad&=d-&gX zba#(eup+RgY)a0g(@x?@cix9-0}Wh@&}`y5ZU`JMUX>);dq-ZTV>vW2DKgp*9I@_O zz4J_cPIPuS>&*dNeL`9VE%3BGe5X#7%$3dLD3GyPcX#Mb3S#V=OF;IQt5X!rTjt8kBc^1m@;Q}9 zE-iBXo4f7-*WDPof)YJ2Wv!dbZR?cH5NJNPR#QJ$-fJJ>oRX@Jk@UF4(}zrg1fk1t#c6%@DTN1)8`Ld diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$AndroidxEspressoLibraryAccessors.class deleted file mode 100644 index bc2da5db48b709b721964615505c3f2aa9eda632..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 932 zcmbtT&2AGh5dIuOwh4jK(w6@MQVwY=#TUdSRi!92Ql%6j1@(+~*Q|^-b~N@@%~NpY zG2j9c2OfZjLd>>_h(aYQICwlWo^L#!Z~Wuux9&n^yL>WQ|gw#jtBUPsf`sEGe?3e@(EHQ_*D&>sHx z9o?Oi6|4wsDVvfr=~+kn32EgLD_7Uz2^cK7SPZK4uaoJ2o zcqGtX%s!{-GHwN){*7Hc*dJxuI^nC{*@*o zi6;I4f0S{qyV*$*|be>g`u3S z{Iiez+=hZahSG5)O%tx`NLSVCYQ?NcE=}Q<9Z739Q?PaEnEGzfk)o~KD+C5{B+#!Q znZzXwFci854FfX7oR7AU48{MDYXS;-{1`7Mk-`;*8H;NgC3aR$49`!v4sz|fIC%xb z469w&q~tcF{~qDmB#>@rGn<TxXaKWpkP#!>jHyIt?t}hcSi}KkSMH-e_n}y}`W% z)%j);6PToy)uiB_U|7mlw)qZMEp8iX)sv=eB3AxT|7M&yw;T3{77&6&&xL}A^O~dA1Qxd|~IZT$radYXJ z?}@sux<(AGb1Pu>nxi)@aYW_(N}i#Qf_&LdM4_cmC+d!n--|aJLqDMgug0);5#+!; z+Yx15Pc45mWGruge`ey?Dw8$#{Tx>%U1v|@vw^)Ze?iquz`-jX^^oU3zZdHnmFrx zV)0bjf)Z6>Z2NgkLPdJ_aei>b6ZR$hVmj2_Ak)3KjaT*}GU&W^-laFjboNJU;&mvw zvZwha7iob%T*pi#T)C3Po-Lfe0dHh_#23_5>6|6H;0N>kZ|E;+l#;l-NgVBQT{nsH ziu=pGf8I)x+=X@^+A>ylKoiPc<l7(|)19l2ac z9LHf0_2Z(O{cDUtd!Su2*d960CrzERe3+$b(0v~oDR}5+!J~DdgG;(1gWj?CEQ5+- zfgc5Ph4Lx(O+TLZN&WA?1+rk-Y#HSCyiaARsE0f_mTBgSExojds@+{a0`S zi32}?AB7mliHK5!Dr9*)JDxXsZ)W!AukSwqJi~SaH7rF~ZsHPF1m0Pf$;_!VC#l9- zY7@vAmCHm0mD@~qM?N@}gqNSHANw>Wlafi!`W&_HtaX?dnKsjtz{;*RI_wD~?ZHCv zv9qT-B_|K3&J+|cCZ1!lPajl~ha+-cThpt!#XCodfwhXzbXOwW6KKzuosH#hlN8wg_bl;{ccjKw18hZkC)lp@=>eAb0is8b zpL~P(!mhwowq*juQ?}Qz!JsO+1eeJh(O1+zFC;(5b&k|440*W4{0!(9u@Y2{gjIHP;G8BCk zDxFHJMG{6L6^V(%X4j=wMCsFa!;2l+m%1l)bkb(6u_x92WDqMok_a=8l~(B!LR9PI zg7>XCRy}FM{Sh;AYUB;iRIwuu#UM!!q;<;Z*08q5_JM~>glE5}i6ZHou`cW#g&ozk z!Yb+7#xn1!&t=LQrQM!M6QzfhH^(kMO1SJH2r!E|Li69l<^mG@@sk~4JO9e@-5EHt zLKXsC!6L&M8GWc?!o$4#IYBDHLotiE9N-$R6E^!IiWreUgF)DxNH_-R0=PB^Q!Uez zg!zur^2Ok&EA4C1O<3c{G95O9uveRe=>JldUYUW7WLsrvmh+=<|E)L{gkV=|Xv0AI9>C5>+P>3iYZ9xfIQ3`(C+-<|kbua8)iv3p# zmV$ymz@MZj&XG%LuLjb7xShGZnP;APcJ_Y${q_UEV?45vL*7Ec!2~7=Z$i^`yGHnd zbVX0OO2^V@5xAa+MG$t~W+#e`@Z!x+gAW_BC$%rNcd*5~p*dLE4*FfC(>KE8Go@Ah zoZ!{k8StJ7_mwY=yPY~|QX?C9hQ)^575yOIktR~1ZVk9KmUk>%BD^?R#`9zpg(h8awKhJipzOs4*s(**|q5c&`eo9BUeu!z_s+`!md5HNhoItq4YZ(Pz|1jJy z%;7gy*(WZ(n8H`t5=Trh-t=d725CukP{QOMmUvB=oD7}Mh9=G2=b#)O;33;ZuA4&* Ubrkt>uV9U>&32t_g{_O?KT58^+5i9m diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs$VersionAccessors.class deleted file mode 100644 index 903d941f68f3cdadca775ec6ff6e5c4d596acd4a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1435 zcmbW0OK;Oa6ot>EZS16>Ers%i@(7SVsCfy2QdNr5MuG-ZDX9C2Ggwocu{Cz8_Sdjx z2SNe~3ARY=ShHr$KR{e3PGyo=R4CHq`p*44=ghtS{^#>o01xq?h#V#?OqMW(Ji|_) zJ;&3$;|qs}(vd0_T5;cTdCdL5b877<*4&M^4h9>WA{444lzZ5qY@iRzyFy1YQ0XH> zeqAaVZ!ox(=E&Pa9qh}F(9TX8q)>IVa7@Ogc*T2uoSs!5h^sE`+OQcWxEB^t#I%J{ z2`4ba@FaV(>xw7}bmVlpPE)ou*HT1{KvNtI<=2Kq3`I{24`O&!Y3}iT?)Y4JPAk?@ zdDW#+xnsVnHs%-#JPh5S8}iu3JcH#1T5QJ$Hcm5?L=@^oR-KYI&M-{v_2}MgoTJTt zn3}b5fiCrR5c^WuxWr(0IrTzvpJB2dbOgg}Q!4SI*KG^^lDB=z=y1ZRI=|K zPLXNU80J#^XxMO##x_S^CQty40P?h6rl&2@P^h!TqSf+ zoa<+;<$3EP3hzdW-_j|d((6=o!vxJ5pbr_SY=TZ2pf4HdrU^P_fWBp*TPA410R6~7 zw@uJl1N1WkRZP%%1N18cEt#N;2I%(@l*4lW@>j4*|MS#_9PYrOb{BCM_fhx@xEf8Z diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibs.class deleted file mode 100644 index 34a5842efa753171490776dca19bb18610d73fa3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4000 zcmb_fdsiDp6#q>NETmi8qNQLT6pNOokJXBOg+9^%6$%tfMeDPh%@7ASyK#0?;e+@+ z^c*SY=sA7>Ka|Jc=G8JuAo2Le=I+ki_x;VCo4^10<1YZyh*CI&!xs8%^kYCE8|tD{ z)Na9-j$2la3Sy}P*LOTOcKxvEWb;w1T`!*7s%^~5vJ46`@V4i<8tQF{yN6M zT$~cP-EAEv>*#FeASvjWjdyWcV5osjmg|yPrp8_iZW9e>ZJfh6kBb)u8>%R9(-d#1 za{JSg!U!gklDsG2wUnfz5C73x4bPJ{-p2<5r(V|TWu{1A@7dh9PNp#HGbM1V>-s#b z1ngIP%9FNn8CL|Xu-Xe)oJlj@cD*90%QYJgJ`_0dx+0 zKE|}bsMn!o2t4R)rn{z-!bRLjAaS!@7j751Y4QJtjj6xK#B~<$E+IA4-nMZE8G(^} z4YdYv1n%syvoB~3Sz`8XFPL5RD@7GFF`L2+CK7Z!u#v?>x>&BcXz=yqq9L0Z#4PWW z%?fYl6ivT&)6QPb)#JN^)IAD!FTepng^Ic%H19-r~TK+}+MXm9SKUMHw$9 z9`giGb>R#<@|r3JZd}o{_@WDunLRb<%;Pp8wah`Lk zGxp@Gad!#K8Rqu|R71?XaqBkfO_Hg)+l$tg-YSryk2UmC*-S6WOw8AG)nL}EE)$&8 zwH8*iC+Agym6PT)bS;6Vz-hBuD`Buw@%?OBF;VtHz=0{}yHOR#MV^SVrR6|mW3aAr*$1qJ)151 zN7`>#2m}^-)xI?sm31-{o995_e50J5SS{OBa)+OO0jHt9(A%#V0$s#qF6lB<}6t{%-!G?FY&mA2IeBnw{Z;%4DYPVdG17}B^QO_ z$^_|*&^#4EXq)q7?1K|&c=M_Lu`3H{GHKG&K1HoN?dG=M{nIy%tz)LK4&W*5Q@7(^YnvW*lDcvoOU@G++NqNw$U4sO zsyjRsCxUBXay|-9nLOT{ZR%3@F~fY%W|CoLsEphzkH^w|5Mxb|9PiSUplm@a!R)V~#GSpT!ectRW0pgRMythy{@SLn2XIeLKT z+4C3Qz`l^naD!|G02`3KiB(Ff!BuhvUX8w@`FRHX9%~e7;1<2N&%AZqp>LJmz+K!& LlUO{!BQ$>l>)9XX diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxCoreLibraryAccessors.class deleted file mode 100644 index 230a2e82e7bf8c871486d4fe456c88a7c8f328d6..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2218 zcmb_e-&Y$&6#fPxOJcMoR{LT+@?X&9xMP>1(qaDM}zPA8Nm64ulS*ugq}< zfhm<4?h3Q-MXpqV+4X#TuUbF>FB>Qp@d{pLxRHtR5Ccc_wIDa-&7u_3e#>`Vp&3f) zyl9ABK9GJy#%`tch!42saphX=P*be6g)9OmdEcZ2xhoox^cA6Q|)TVKsVRcJ+ z2WAwAG~Wb>G{*#plK?2;H3JulcpbA0FEm7k!ebfk)}4X01;f^h#iUk132zi}5pOcg zK9-)>5cfsT9|&hdttVVwX4tNr1@`YK{1ke+{s*!rJgEd>e~Dpf&kt$TaRRS%$N{I5 z;@uhFLMLHb0ax(00kepAaFyZPQxNT6R5&IkhPfE*?S5RwVm*?MXbU?gEyK0S#?$C{ z#L%toBU)QCP-eJ$#?X8_>IoGl^-{n*-Yeo7Dh!6=?sgDY%w#1l%Qr0>IWO@-l(n{aaot^W4~+UcC_?h zq#3lGM9J2Ihs4O6CowYC!oKzg1g5s`jXO1l+?wyu{&OuN!#7c{EA#{2^~f^iitui@ z&rtp+?~Zd+NZBPEhJ0JPiieRVN8dlk{*`RC#wTzc%7>)Kfwf7p+v8p;*PFf*d4kRw zi+1f6C2{e7q(Wl!jtnFPUsuW>-5NnOo8ik*h_tEDCVjI-Q^wiOKl>W0F~Jy$8%hbi z=J6m9fdP69>e*}kU(XH0g{M6@2I>sU8Skf)SrYTZWHVwucWlYcBr{pY8)y=*G7+4D zwhWh^MO;#jC3?2w&jeWfaMSM%8eO4rY@b@Z{wvr|)MNNC9#aeaK))Z+o1aV8u3|E= zmP^KO$d}FyG4lkaA?D6cm);uU@)OJt@$O=2VTkKL9(s!ZE&xB{GJe4))B|qPcLJZ{ zGiu{=mZ{C*^Tb*kugT7>(99ymJb^FpWiC(By^03%6#FXHsGX z_$EWM);jYZ_1T>XOfY=e@O@#eRG}NmuHi-s>uTe66GaJF_rB3RcOZ5+_g8^J*Of??~~Vp1=mf>+A8gjX4+9?2+L z5qCsS4@9t`)-x_IGHln*0{cA*KZl-<|E}zbNGd_tzs@lKP{;Jv32f9kd9A$oo7zy{Zm8P_#l4c&cC|5dzBcrIFn#Yp zJjey9lWzo%iJCV~qGl?JeWM42s_||QJ9UP!RUOd!b1h=U*GaD{%w67%$l`<|UZq?Z zs()qRah^&!&qTm5*_NT=agwh8_CKs&D%Nef12?g}Ps(h)O%mW9k8_W#IxK)Q;iP%vvALDUL1C$Q;Eyg3s{z*dz)0GFC82u`gql+8JtZQ9F+{tYh*|N3F)0 diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$AndroidxLibraryAccessors.class deleted file mode 100644 index 484959aa81aa850b65a8df51948053fd4b27b263..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3448 zcmb_eTUQ%Z6#fnb2GX&m5lgGBjwRASD`RUd(jXEjAT$(8xQJEL$;@duFqz4kOMoAs z&-$!CqOR3am#*dNvp>q^o+JYyCQu9y$v(H)m+yT0?EUvYfBXgDF7znc&@Le&qXV4` zYqpbD^NwbiT-Ay~6_&>xOEXnn^EA`WtErspIhyWG?^ZS*@FKSiZs~h7v}!wh@rnbv zQAP}JGxVF9u2ay*MaZyv#B>;Wi@+r%yu+~GB3{#O(FyLc9=9lZE0JE7aRu)(+^CDR z*@p}ptw!5Sb+QXr8Rje05msI?L)s~}qvU*xvdC4QId(xQamN+5rBu_%RfMH@n_MYY zXsP4^UJgg`K0c73$oLS~8E)5Ld60+(CxA!|X;UfB!g1Qp=L1&7!hJr;H?@+meOk;V z(py?dQ%%jvs~OKBUz3BisGOvIfv!Z$^GRQr26y72-9sA$MVw(`(K7cG-{oPvZU96W zV;P8(02sgx2?-g47-Be67a5{E!rM$4C82Xl?6bur8N~o@$@mz<43~Cw)GqgmE)&FldOjBJQ^wt5TMGSi~C zgHI*gmGK$wF+4s6(dwws#3zQn0PNLbP)qo%FASdHdO%vr+{9cXIvz4~F}Fo$={@I6>nlAE@U&wK1 zMa!AABImi63jJV+A7xHs6GZWlAKYN*&WOCFdA>vHp1#5NW3~AfSkN3#JfpJistZ)T z3z`{L{RP|bO-{C|wLdwYWVo{ITOM(8O}K(WNLiL$!QG{dsJZb&7wMxe3Uj^!g+#-k zB2y8mbM~w%6vH{P5kBV(Pg=JVDyy$o6k0SxkFU;WL~xz`l>^OMlHq{;bm?;z^#)U> z=DOUKu+EUG;s5_@$QXJXwPX^$Au88ue{+->t{&fDTn@MEVPR0ht!Btc$TE!9ICi?? zM0tEbu$mIs*Yu&fSl+39C#d=cZ87K<3)(6g#e$}TWCy5$Lnr-D)9fom%ID%kH(!Ab z{RwGf=mol8;lfMw(6qNYz4Q`&ztMT>e#^Qd^uJAdHmRu*=%+EmY*|~Nbpq`)2ja2! ze#f;~|2{r?je&jK?CFZB`?&oYBl{Q~ihZ$G?5)zyeQLVfu!gTA-89<369gUj2EHZPOY%FC1Na_KN!}r;ksKkJ GL-)V&T_^Iv?+gp*(;)KM3 z58$H^vm_0n6;xtZ_RM(ZJ=@Rr_a9%s0eFdrZ8UHrL9>Gmv;UQ((BRM3zwq&NH%6#|6>I|BXn zjsDkt64?6VMkRP4@M@j*LXGS7W1$vYD+Tcg3BQ2)6a4cV;C_>%J@#5`JJ0r?A9S1D vjV}Yx15PeQdw+ShQ@>RZy5ILlP;tS%Es!~XaRESEYK=01(uyVVxBimcie+3ti zIPe4bQHa@WBBE3(6$rjyf%n#>GIc7+NUE`x z+5~b&WinPlWj2+ap$|^Q;mzmrV2{RR5;E~wkE7O|H4d{p)n>XASlQ7=hh2fV*!;fS2q)^tm5?d_vgtO{%%Qy4m>jc=XUkZIFWCUI6L zHPmo5LcNYPTod>>PbZGad+WSRMzXIN?lk$Hb?p0nQ}*OvXEr`*yq%SQH>qBpb!G(w z>aimgsEiA|YW9!Ssgjv8sT>5SP1@dG?C{(u+5*d6n~=bIUmH5eM?-QS)G*^nEv3*Y zTM}qAFIB8M(5X=&cZ@%{1Y~EP;dmmc%st7ntG}wZcbREzU~?B!PZ#W-UOc{5F$^Bk zzA@ywnev`|gnI&=c{%>;>Itls^rrVH!b2YaeA$^u|5jOG>tdbpgl|)Y9}(D!;`Ojy z=iOs0@drfDp1=4G@s(YH>uiez2x5B!8w@Iw3viLV5q(4T%R=%9H#t(lE&gv$ygRtd RYXPrd6ZcVN77y?U)j#?HCk+4q diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$JetbrainsPluginAccessors.class deleted file mode 100644 index a4118f6539525518602efac84b9a52c83b1fb207..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1259 zcmb_cZBG+H5Pr4=&Z`F~qCypXp%|#f`(iY)#-tXTppBBKRlb;Px65Vq*ll*NME;c~ z8WK(X0sbiCoP9}q7)0WSyP4gYd7ioFX7|U>uipXO!HoiP$a|OwFo`LK=f*~1WO+N5 zA@8VA=|o!1<52K~$0iD^Etgm>lE)uy**8UT>B4riW7uuSRKvkj@$F!uD?1 zP%X=?lCEwn`EFD9dUcOtBi@&u$b{lbyQe0JRX$U;oF%f1awe&8{^PJDr2%_Oq?c(ghb1hNEfP=;SExCkM)*2PWD8_h G;r{}3&V;uB diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$PluginAccessors.class deleted file mode 100644 index 6f1f3eeaf1196e10266cfbb3fbad07908cc58516..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1630 zcmbVMT~8B16g|@dYu81zB32QR4;9MC8Wnx0F)76+kg5<2iI3CWp&4Cfo0%<{CzB+oly*E<#fI4DtsvSH+Q?8<+O?Gy_bgmtc-x)E^Mo;>Hm-l* z)?{6CErqFun&xIxwQDu&LFj#+FDqY%(r>SoJApaaxN5<1Fp6so6#7q~j?X2)Q>YBN z4tv9}m?qrWJEu%s&2bG!^?E|CH1mlAsZv!axj703{y?+dBpHyCFpjX zNz@1Xivdd(?xe0L-54sjf|>gsueK7-1|dGL*X?(?H#ZVYFRa(mE_GGrZ`Ay}Y6f6Blbrr7AHOP^<>PxuHVYPaSsJJ5Z-?etvMa@<tPgoy|-;twl>;yND zF-}W`uBE%jnEXZo3=e3`V~D0})U=<{D|$w}*Jx)3vkCkZSw?=tgg5^6G%U^zR-$nZ t^EAelbh}QbUDt`oLvqUC5gwDBrMwv|poko`k0q>-waKoMEs%AQ`wQ17@K68% diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/classes/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock$VersionAccessors.class deleted file mode 100644 index b4504975e5c69d72f167ec21228539ac65c84075..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1477 zcmbW0T~8B16o%g^(A|~_h@bd{3Tj)B^()4tgrpWQNHruF?x)*vGq9c6%x($%E4|Ug z3x9yOUVH7e*CxiZ?Ut_$c^uT~i@ene%>#tcJ&2Z5_Q0gr6VGFYxQVmmsrah{TJXnuL(&Wh}bC*)tQ- zR1s}%_e3*HlKtvLba7XAjVm@~EOg=T*Siv59@Vv_lrRmShoJ~9tT5EmjvU!%hYfw`jm~^oD@~XgrXo^*VjcV~l=)Rb5*C2=<;#h8wiT z0l-&U=W&zJesHemwW_n$2Nd271%IO~pwQbCw2%c&XF%Um&|(&JHUs*Rg6?EN=Q5z5 zDd=t%bYT=?6DjCk7IY~CnodFGENCtRnoB{IEa++mv~U9DQ0+B;3Cr|9OV^OYeK>U8 KMLfVG6n+Ba;?Z+F{_G#+@q3v}nobhhrv8xJnR)Z>^4;&fd*A%??;n2wcm%)1u@38F*r1^W ztpa_vlTYOxJ!i_4UNlmMH+RrQ;g5H4qp{N2e7Xd&bB~Cv~QLQMOg{V!_TyGj%$1 zMP|K5?^Ht4J6q4 zXLQGvPI~`jJKE45LtMjc&;$-wW0K8E*R>t$D5OS>jH5e-bO&vR*Y2=&#`N=s<@TF) z_NqXOea(`Nz(5q9N<=G8QaXm)1x`2TNmrkhb8I6w8#p}I7X}f>Mr>9@+9EKxeD0T} zQW?8DG~9{11a_NxHcM<8nHP9^2{NHu%VXOxBI2}7V5mu)%B-&7qlnO{;cjdfXb(B< z3hZCvHdkFZR>OCtVW);&*v(~@wXJC*FYs7&dJP}yud+C{VvkDKJp$R9bT#y$No&D6 z=+ba6?i1KH6XY@qk-+d0{j11fR26gAO&&IxyMEu|9=IfRJsR%E0fCrZ+FzKst|h)Q zarO2em9s+{Qg}dM%i^9>-d_ZcMU_<2xA^j{HYlb4Aq@}X5rK|ugKbFQcw;jw+sNYB zhr^04kJa1R>qQ>5_s(+QhHJ-jQKmtY|(eMP)0$Vcyqa(x-cxs8ARS-I&iF|&t zc|HfFq{8Poda*|_=eUMG^wa%f;C|%2HMk$qly1Wbfsw!i!^$Vku-qkWCz&ZNH#a%$ z*oEXw&oZ4io4F38iCIhXWZ8OG}>Ai@|+Kr9EqI8MiKM#IxMD^N|dHM=Mfzh-!s`*Jfz zRi|1l^Uc(D`kxj-bh!&wj1D{w971-yC zs_~XXK3m-hHn8+sU|;ueJvuHjG-!6YIb0GrwMN(MtY45;(7whog^Y$Qa;$ikoe5>vl+eOv&oNh2f3`lz!lYxI8ygWmcz@DMI9_^Y5@~t3bYld!ZCDSZWv%Q zFR*EpSsV8Y8R?u;9lAj0S>N)Q&Pl^HRLgEz<&K*b`K}UJvplz`BS31nB)B`b<)t^G zJZ8~eN~`+LkpCfhBmrojF!Gk}`3}urTEYC@>cyxm=#`Q(#=}uTH^cMOn4R-YNn7Pp zRQjl@B~>Y3bb|x8F^sVaLh3GTh6N@feyyU?gi4|fec58Uvm(5wnzvEYo)KdD9~3#N z9%){6v`_|`gZi^J&4G?e)g&JA2^NX095fUY_XdD9IWw6Z z&$*XZdB8?vrH9_G5$W+z%ro$*(uN%gPGHxqUx?wW=8w4*)iqW-8V$wpt-x55v6eGm zV{L2wff&9QxUe=`vnO3PMf?I0UHJmZkcf?5iQy-1I%~8)U^}wb_KwhYy6u5Y z=TB_B*mDE1o7gmu1aG&h+YbJA+(dF7d--UedbB@$OnH#M2XErhc|6YH-l`c#=W*;e z8WOPhzl&}FNxIyD&FI8#eh7F7+u6MBK#oD#9Bt*h#nOzI;9x_^-Q!r#r$AR?;CGx% zoLa!x-xy!O#OAidg#}#v8&eC=dlGU1`Cm(Ol{NKU4>*XOI0TnhfXClD_!T=dycf8( zYCBi!*h$k)?=9`jVvcbr_>Y$3x#!mL+(054%^YV zmm#G$lA`aTogZl0@E+wp%J(UIDL$AHD5oetrTmQJUr>HY`8DM?l-DW0 Nqx^yLN6Mek{vRR52owMS diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/metadata.bin deleted file mode 100644 index 0b6bada853bcb777c24bfd1907b45a75177e7fc7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 99 zcmbPTS(RK^l4z7sT$Yw*o>^v+l#*YNXku2Lk}A;0&Cv1a#^k@+_y7Ibx%bZHjm%6P z$vKI|#i_-N0uMe)gq}}1@sLmb#SG0GDHA%1^Gl18K{7cFsTT3s-(G diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java deleted file mode 100644 index 726833de..00000000 --- a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibs.java +++ /dev/null @@ -1,313 +0,0 @@ -package org.gradle.accessors.dm; - -import org.gradle.api.NonNullApi; -import org.gradle.api.artifacts.MinimalExternalModuleDependency; -import org.gradle.plugin.use.PluginDependency; -import org.gradle.api.artifacts.ExternalModuleDependencyBundle; -import org.gradle.api.artifacts.MutableVersionConstraint; -import org.gradle.api.provider.Provider; -import org.gradle.api.model.ObjectFactory; -import org.gradle.api.provider.ProviderFactory; -import org.gradle.api.internal.catalog.AbstractExternalDependencyFactory; -import org.gradle.api.internal.catalog.DefaultVersionCatalog; -import java.util.Map; -import org.gradle.api.internal.attributes.ImmutableAttributesFactory; -import org.gradle.api.internal.artifacts.dsl.CapabilityNotationParser; -import javax.inject.Inject; - -/** - * A catalog of dependencies accessible via the {@code libs} extension. - */ -@NonNullApi -public class LibrariesForLibs extends AbstractExternalDependencyFactory { - - private final AbstractExternalDependencyFactory owner = this; - private final AndroidxLibraryAccessors laccForAndroidxLibraryAccessors = new AndroidxLibraryAccessors(owner); - private final VersionAccessors vaccForVersionAccessors = new VersionAccessors(providers, config); - private final BundleAccessors baccForBundleAccessors = new BundleAccessors(objects, providers, config, attributesFactory, capabilityNotationParser); - private final PluginAccessors paccForPluginAccessors = new PluginAccessors(providers, config); - - @Inject - public LibrariesForLibs(DefaultVersionCatalog config, ProviderFactory providers, ObjectFactory objects, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { - super(config, providers, objects, attributesFactory, capabilityNotationParser); - } - - /** - * Dependency provider for junit with junit:junit coordinates and - * with version reference junit - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getJunit() { - return create("junit"); - } - - /** - * Dependency provider for material with com.google.android.material:material coordinates and - * with version reference material - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getMaterial() { - return create("material"); - } - - /** - * Group of libraries at androidx - */ - public AndroidxLibraryAccessors getAndroidx() { - return laccForAndroidxLibraryAccessors; - } - - /** - * Group of versions at versions - */ - public VersionAccessors getVersions() { - return vaccForVersionAccessors; - } - - /** - * Group of bundles at bundles - */ - public BundleAccessors getBundles() { - return baccForBundleAccessors; - } - - /** - * Group of plugins at plugins - */ - public PluginAccessors getPlugins() { - return paccForPluginAccessors; - } - - public static class AndroidxLibraryAccessors extends SubDependencyFactory { - private final AndroidxCoreLibraryAccessors laccForAndroidxCoreLibraryAccessors = new AndroidxCoreLibraryAccessors(owner); - private final AndroidxEspressoLibraryAccessors laccForAndroidxEspressoLibraryAccessors = new AndroidxEspressoLibraryAccessors(owner); - - public AndroidxLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for appcompat with androidx.appcompat:appcompat coordinates and - * with version reference appcompat - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getAppcompat() { - return create("androidx.appcompat"); - } - - /** - * Dependency provider for junit with androidx.test.ext:junit coordinates and - * with version reference junitVersion - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getJunit() { - return create("androidx.junit"); - } - - /** - * Group of libraries at androidx.core - */ - public AndroidxCoreLibraryAccessors getCore() { - return laccForAndroidxCoreLibraryAccessors; - } - - /** - * Group of libraries at androidx.espresso - */ - public AndroidxEspressoLibraryAccessors getEspresso() { - return laccForAndroidxEspressoLibraryAccessors; - } - - } - - public static class AndroidxCoreLibraryAccessors extends SubDependencyFactory { - - public AndroidxCoreLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for ktx with androidx.core:core-ktx coordinates and - * with version reference coreKtx - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getKtx() { - return create("androidx.core.ktx"); - } - - } - - public static class AndroidxEspressoLibraryAccessors extends SubDependencyFactory { - - public AndroidxEspressoLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for core with androidx.test.espresso:espresso-core coordinates and - * with version reference espressoCore - *

- * This dependency was declared in catalog libs.versions.toml - */ - public Provider getCore() { - return create("androidx.espresso.core"); - } - - } - - public static class VersionAccessors extends VersionFactory { - - public VersionAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Version alias agp with value 8.5.2 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getAgp() { return getVersion("agp"); } - - /** - * Version alias appcompat with value 1.7.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getAppcompat() { return getVersion("appcompat"); } - - /** - * Version alias coreKtx with value 1.13.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getCoreKtx() { return getVersion("coreKtx"); } - - /** - * Version alias espressoCore with value 3.6.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getEspressoCore() { return getVersion("espressoCore"); } - - /** - * Version alias junit with value 4.13.2 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getJunit() { return getVersion("junit"); } - - /** - * Version alias junitVersion with value 1.2.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getJunitVersion() { return getVersion("junitVersion"); } - - /** - * Version alias kotlin with value 1.9.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getKotlin() { return getVersion("kotlin"); } - - /** - * Version alias material with value 1.12.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getMaterial() { return getVersion("material"); } - - } - - public static class BundleAccessors extends BundleFactory { - - public BundleAccessors(ObjectFactory objects, ProviderFactory providers, DefaultVersionCatalog config, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { super(objects, providers, config, attributesFactory, capabilityNotationParser); } - - } - - public static class PluginAccessors extends PluginFactory { - private final AndroidPluginAccessors paccForAndroidPluginAccessors = new AndroidPluginAccessors(providers, config); - private final JetbrainsPluginAccessors paccForJetbrainsPluginAccessors = new JetbrainsPluginAccessors(providers, config); - - public PluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Group of plugins at plugins.android - */ - public AndroidPluginAccessors getAndroid() { - return paccForAndroidPluginAccessors; - } - - /** - * Group of plugins at plugins.jetbrains - */ - public JetbrainsPluginAccessors getJetbrains() { - return paccForJetbrainsPluginAccessors; - } - - } - - public static class AndroidPluginAccessors extends PluginFactory { - - public AndroidPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Plugin provider for android.application with plugin id com.android.application and - * with version reference agp - *

- * This plugin was declared in catalog libs.versions.toml - */ - public Provider getApplication() { return createPlugin("android.application"); } - - } - - public static class JetbrainsPluginAccessors extends PluginFactory { - private final JetbrainsKotlinPluginAccessors paccForJetbrainsKotlinPluginAccessors = new JetbrainsKotlinPluginAccessors(providers, config); - - public JetbrainsPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Group of plugins at plugins.jetbrains.kotlin - */ - public JetbrainsKotlinPluginAccessors getKotlin() { - return paccForJetbrainsKotlinPluginAccessors; - } - - } - - public static class JetbrainsKotlinPluginAccessors extends PluginFactory { - - public JetbrainsKotlinPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Plugin provider for jetbrains.kotlin.android with plugin id org.jetbrains.kotlin.android and - * with version reference kotlin - *

- * This plugin was declared in catalog libs.versions.toml - */ - public Provider getAndroid() { return createPlugin("jetbrains.kotlin.android"); } - - } - -} diff --git a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java b/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java deleted file mode 100644 index 19c6b8a0..00000000 --- a/driver-app/.gradle/8.7/dependencies-accessors/e5d0c485ed9081f602aa0c935b664eb63f940590/sources/org/gradle/accessors/dm/LibrariesForLibsInPluginsBlock.java +++ /dev/null @@ -1,369 +0,0 @@ -package org.gradle.accessors.dm; - -import org.gradle.api.NonNullApi; -import org.gradle.api.artifacts.MinimalExternalModuleDependency; -import org.gradle.plugin.use.PluginDependency; -import org.gradle.api.artifacts.ExternalModuleDependencyBundle; -import org.gradle.api.artifacts.MutableVersionConstraint; -import org.gradle.api.provider.Provider; -import org.gradle.api.model.ObjectFactory; -import org.gradle.api.provider.ProviderFactory; -import org.gradle.api.internal.catalog.AbstractExternalDependencyFactory; -import org.gradle.api.internal.catalog.DefaultVersionCatalog; -import java.util.Map; -import org.gradle.api.internal.attributes.ImmutableAttributesFactory; -import org.gradle.api.internal.artifacts.dsl.CapabilityNotationParser; -import javax.inject.Inject; - -/** - * A catalog of dependencies accessible via the {@code libs} extension. - */ -@NonNullApi -public class LibrariesForLibsInPluginsBlock extends AbstractExternalDependencyFactory { - - private final AbstractExternalDependencyFactory owner = this; - private final AndroidxLibraryAccessors laccForAndroidxLibraryAccessors = new AndroidxLibraryAccessors(owner); - private final VersionAccessors vaccForVersionAccessors = new VersionAccessors(providers, config); - private final BundleAccessors baccForBundleAccessors = new BundleAccessors(objects, providers, config, attributesFactory, capabilityNotationParser); - private final PluginAccessors paccForPluginAccessors = new PluginAccessors(providers, config); - - @Inject - public LibrariesForLibsInPluginsBlock(DefaultVersionCatalog config, ProviderFactory providers, ObjectFactory objects, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { - super(config, providers, objects, attributesFactory, capabilityNotationParser); - } - - /** - * Dependency provider for junit with junit:junit coordinates and - * with version reference junit - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getJunit() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("junit"); - } - - /** - * Dependency provider for material with com.google.android.material:material coordinates and - * with version reference material - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getMaterial() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("material"); - } - - /** - * Group of libraries at androidx - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public AndroidxLibraryAccessors getAndroidx() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return laccForAndroidxLibraryAccessors; - } - - /** - * Group of versions at versions - */ - public VersionAccessors getVersions() { - return vaccForVersionAccessors; - } - - /** - * Group of bundles at bundles - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public BundleAccessors getBundles() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return baccForBundleAccessors; - } - - /** - * Group of plugins at plugins - */ - public PluginAccessors getPlugins() { - return paccForPluginAccessors; - } - - /** - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public static class AndroidxLibraryAccessors extends SubDependencyFactory { - private final AndroidxCoreLibraryAccessors laccForAndroidxCoreLibraryAccessors = new AndroidxCoreLibraryAccessors(owner); - private final AndroidxEspressoLibraryAccessors laccForAndroidxEspressoLibraryAccessors = new AndroidxEspressoLibraryAccessors(owner); - - public AndroidxLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for appcompat with androidx.appcompat:appcompat coordinates and - * with version reference appcompat - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getAppcompat() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("androidx.appcompat"); - } - - /** - * Dependency provider for junit with androidx.test.ext:junit coordinates and - * with version reference junitVersion - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getJunit() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("androidx.junit"); - } - - /** - * Group of libraries at androidx.core - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public AndroidxCoreLibraryAccessors getCore() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return laccForAndroidxCoreLibraryAccessors; - } - - /** - * Group of libraries at androidx.espresso - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public AndroidxEspressoLibraryAccessors getEspresso() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return laccForAndroidxEspressoLibraryAccessors; - } - - } - - /** - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public static class AndroidxCoreLibraryAccessors extends SubDependencyFactory { - - public AndroidxCoreLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for ktx with androidx.core:core-ktx coordinates and - * with version reference coreKtx - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getKtx() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("androidx.core.ktx"); - } - - } - - /** - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public static class AndroidxEspressoLibraryAccessors extends SubDependencyFactory { - - public AndroidxEspressoLibraryAccessors(AbstractExternalDependencyFactory owner) { super(owner); } - - /** - * Dependency provider for core with androidx.test.espresso:espresso-core coordinates and - * with version reference espressoCore - *

- * This dependency was declared in catalog libs.versions.toml - * - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public Provider getCore() { - org.gradle.internal.deprecation.DeprecationLogger.deprecateBehaviour("Accessing libraries or bundles from version catalogs in the plugins block.").withAdvice("Only use versions or plugins from catalogs in the plugins block.").willBeRemovedInGradle9().withUpgradeGuideSection(8, "kotlin_dsl_deprecated_catalogs_plugins_block").nagUser(); - return create("androidx.espresso.core"); - } - - } - - public static class VersionAccessors extends VersionFactory { - - public VersionAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Version alias agp with value 8.5.2 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getAgp() { return getVersion("agp"); } - - /** - * Version alias appcompat with value 1.7.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getAppcompat() { return getVersion("appcompat"); } - - /** - * Version alias coreKtx with value 1.13.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getCoreKtx() { return getVersion("coreKtx"); } - - /** - * Version alias espressoCore with value 3.6.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getEspressoCore() { return getVersion("espressoCore"); } - - /** - * Version alias junit with value 4.13.2 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getJunit() { return getVersion("junit"); } - - /** - * Version alias junitVersion with value 1.2.1 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getJunitVersion() { return getVersion("junitVersion"); } - - /** - * Version alias kotlin with value 1.9.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getKotlin() { return getVersion("kotlin"); } - - /** - * Version alias material with value 1.12.0 - *

- * If the version is a rich version and cannot be represented as a - * single version string, an empty string is returned. - *

- * This version was declared in catalog libs.versions.toml - */ - public Provider getMaterial() { return getVersion("material"); } - - } - - /** - * @deprecated Will be removed in Gradle 9.0. - */ - @Deprecated - public static class BundleAccessors extends BundleFactory { - - public BundleAccessors(ObjectFactory objects, ProviderFactory providers, DefaultVersionCatalog config, ImmutableAttributesFactory attributesFactory, CapabilityNotationParser capabilityNotationParser) { super(objects, providers, config, attributesFactory, capabilityNotationParser); } - - } - - public static class PluginAccessors extends PluginFactory { - private final AndroidPluginAccessors paccForAndroidPluginAccessors = new AndroidPluginAccessors(providers, config); - private final JetbrainsPluginAccessors paccForJetbrainsPluginAccessors = new JetbrainsPluginAccessors(providers, config); - - public PluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Group of plugins at plugins.android - */ - public AndroidPluginAccessors getAndroid() { - return paccForAndroidPluginAccessors; - } - - /** - * Group of plugins at plugins.jetbrains - */ - public JetbrainsPluginAccessors getJetbrains() { - return paccForJetbrainsPluginAccessors; - } - - } - - public static class AndroidPluginAccessors extends PluginFactory { - - public AndroidPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Plugin provider for android.application with plugin id com.android.application and - * with version reference agp - *

- * This plugin was declared in catalog libs.versions.toml - */ - public Provider getApplication() { return createPlugin("android.application"); } - - } - - public static class JetbrainsPluginAccessors extends PluginFactory { - private final JetbrainsKotlinPluginAccessors paccForJetbrainsKotlinPluginAccessors = new JetbrainsKotlinPluginAccessors(providers, config); - - public JetbrainsPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Group of plugins at plugins.jetbrains.kotlin - */ - public JetbrainsKotlinPluginAccessors getKotlin() { - return paccForJetbrainsKotlinPluginAccessors; - } - - } - - public static class JetbrainsKotlinPluginAccessors extends PluginFactory { - - public JetbrainsKotlinPluginAccessors(ProviderFactory providers, DefaultVersionCatalog config) { super(providers, config); } - - /** - * Plugin provider for jetbrains.kotlin.android with plugin id org.jetbrains.kotlin.android and - * with version reference kotlin - *

- * This plugin was declared in catalog libs.versions.toml - */ - public Provider getAndroid() { return createPlugin("jetbrains.kotlin.android"); } - - } - -} diff --git a/driver-app/.gradle/8.7/dependencies-accessors/gc.properties b/driver-app/.gradle/8.7/dependencies-accessors/gc.properties deleted file mode 100644 index e69de29b..00000000 diff --git a/driver-app/.gradle/8.7/executionHistory/executionHistory.bin b/driver-app/.gradle/8.7/executionHistory/executionHistory.bin deleted file mode 100644 index 3bffa4c5330c15c7b6fffc55131d2062698daef7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1062082 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 VPN-#>&Y5=20cvTf(V}3F`+sJHlUe`( diff --git a/driver-app/.gradle/8.7/executionHistory/executionHistory.lock b/driver-app/.gradle/8.7/executionHistory/executionHistory.lock deleted file mode 100644 index a45935c5b0525307356bfa86bec6accf5a307b8f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 17 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 HyaxXR(E-x& diff --git a/driver-app/.gradle/8.7/fileHashes/fileHashes.lock b/driver-app/.gradle/8.7/fileHashes/fileHashes.lock deleted file mode 100644 index ef6bd68b439df512c80eda6c88a478a57106b8af..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 17 UcmZR+&{bKdYi-QK00vA80V)y$p8x;= diff --git a/driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin b/driver-app/.gradle/8.7/fileHashes/resourceHashesCache.bin deleted file mode 100644 index 7af4d07b3b9a8d9b79b6a34cd8a511e7e89462a7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 19483 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 Date: Fri, 25 Oct 2024 15:52:03 +0200 Subject: [PATCH 04/28] wip --- .eslintignore | 2 ++ .prettierignore | 2 +- package.json | 2 +- src/lib/api.ts | 21 ---------------- src/lib/motis/index.ts | 2 +- src/routes/+page.server.ts | 6 ++--- src/routes/api/booking/+server.ts | 41 ++++++++++++++++--------------- 7 files changed, 29 insertions(+), 47 deletions(-) diff --git a/.eslintignore b/.eslintignore index 2daeae55..e8971afa 100644 --- a/.eslintignore +++ b/.eslintignore @@ -13,3 +13,5 @@ package-lock.json yarn.lock taxidriver-android-app + +/src/lib/motis diff --git a/.prettierignore b/.prettierignore index d291286a..afc65a11 100644 --- a/.prettierignore +++ b/.prettierignore @@ -5,5 +5,5 @@ yarn.lock src/lib/components/* .github/* migrations/* - +src/lib/motis taxidriver-android-app diff --git a/package.json b/package.json index 3f4647d2..a432a5cb 100644 --- a/package.json +++ b/package.json @@ -68,4 +68,4 @@ "tailwind-variants": "^0.2.1", "zod": "^3.23.8" } -} \ No newline at end of file +} diff --git a/src/lib/api.ts b/src/lib/api.ts index 16fed9c4..a488424b 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -120,24 +120,3 @@ export async function geoCode(address: string): Promise { } return guesses[0]; } - -export class RoutingQuery { - start!: Coordinates; - destination!: Coordinates; - profile!: string; - direction!: string; -} - -export const getRoute = async (query: RoutingQuery) => { - const response = await fetch(`https://osr.motis-project.de/api/route`, { - method: 'POST', - mode: 'cors', - headers: { - 'Access-Control-Allow-Origin': '*', - 'Content-Type': 'application/json' - }, - body: JSON.stringify(query) - }); - return await response.json(); -}; - diff --git a/src/lib/motis/index.ts b/src/lib/motis/index.ts index 0a2b84ba..002afc33 100644 --- a/src/lib/motis/index.ts +++ b/src/lib/motis/index.ts @@ -1,4 +1,4 @@ // This file is auto-generated by @hey-api/openapi-ts export * from './schemas.gen'; export * from './services.gen'; -export * from './types.gen'; \ No newline at end of file +export * from './types.gen'; diff --git a/src/routes/+page.server.ts b/src/routes/+page.server.ts index 0e04b6f2..a860ea64 100644 --- a/src/routes/+page.server.ts +++ b/src/routes/+page.server.ts @@ -3,15 +3,15 @@ import type { PageServerLoad } from './$types'; export const load: PageServerLoad = async (event) => { if (!event.locals.user) { - console.log("redirect guest to login"); + console.log('redirect guest to login'); return redirect(302, '/login'); } if (event.locals.user.is_maintainer) { - console.log("redirect maintainer to /activation"); + console.log('redirect maintainer to /activation'); return redirect(302, '/maintainer/activation'); } if (event.locals.user.is_entrepreneur) { - console.log("redirect entrepreneur to /company"); + console.log('redirect entrepreneur to /company'); return redirect(302, '/user/company'); } return { diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index bcf01033..73ade9f7 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -1,4 +1,3 @@ -import { getRoute } from '$lib/api.js'; import { Coordinates } from '$lib/location.js'; import { db } from '$lib/database'; import { Interval } from '$lib/interval.js'; @@ -11,7 +10,7 @@ import { getFareEstimation } from './fare-estimation/fare_estimation.js'; import { covers } from '$lib/sqlHelpers.js'; import { oneToMany, type Duration } from '$lib/motis'; -const MOTIS_BASE_URL = 'https://europe.motis-project.de' +const MOTIS_BASE_URL = 'https://europe.motis-project.de'; const startAndTargetShareZone = async (from: Coordinates, to: Coordinates) => { const zoneContainingStartAndDestination = await db @@ -36,11 +35,11 @@ export const POST = async (event) => { const coordinatesToStr = (c: Coordinates) => { return `${c.lat};${c.lng}`; - } + }; let travelDuration = 0; try { - travelDuration = ( + const duration = ( await oneToMany({ baseUrl: MOTIS_BASE_URL, query: { @@ -53,6 +52,10 @@ export const POST = async (event) => { } }).then((d) => d.data!) )[0].duration; + if (!duration) { + throw 'keine Route gefunden'; + } + travelDuration = duration; } catch (e) { return json( { @@ -238,26 +241,24 @@ export const POST = async (event) => { return new Coordinates(vehicles![0].latitude!, vehicles![0].longitude!); }); - let durationToStart: Array = []; let durationFromTarget: Array = []; try { - durationToStart = - await oneToMany({ - baseUrl: MOTIS_BASE_URL, - query: { - one: coordinatesToStr(fromCoordinates), - many: centralCoordinates.map(coordinatesToStr), - max: 3600, - maxMatchingDistance: 100, - mode: 'CAR', - arriveBy: false - } - }).then((res) => { - return res.data!.map((d: Duration) => { - return d.duration ?? Number.MAX_VALUE; - }); + durationToStart = await oneToMany({ + baseUrl: MOTIS_BASE_URL, + query: { + one: coordinatesToStr(fromCoordinates), + many: centralCoordinates.map(coordinatesToStr), + max: 3600, + maxMatchingDistance: 100, + mode: 'CAR', + arriveBy: false + } + }).then((res) => { + return res.data!.map((d: Duration) => { + return d.duration ?? Number.MAX_VALUE; }); + }); durationFromTarget = await oneToMany({ baseUrl: MOTIS_BASE_URL, From fc4b7e55098109caf1688385bb2565c0fee38354 Mon Sep 17 00:00:00 2001 From: nils Date: Sat, 26 Oct 2024 17:28:07 +0200 Subject: [PATCH 05/28] Move MOTIS_BASE_URL to constants --- src/lib/constants.ts | 1 + src/lib/motisUtils.ts | 5 +++++ src/routes/api/booking/+server.ts | 9 ++------- 3 files changed, 8 insertions(+), 7 deletions(-) create mode 100644 src/lib/motisUtils.ts diff --git a/src/lib/constants.ts b/src/lib/constants.ts index 56c2190c..7a511341 100644 --- a/src/lib/constants.ts +++ b/src/lib/constants.ts @@ -6,3 +6,4 @@ export const MAX_TRAVEL_DURATION = hoursToMs(1); export const MAX_PASSENGER_WAITING_TIME_PICKUP = minutesToMs(10); export const MAX_PASSENGER_WAITING_TIME_DROPOFF = minutesToMs(10); export const SRID = 4326; +export const MOTIS_BASE_URL = 'https://europe.motis-project.de'; diff --git a/src/lib/motisUtils.ts b/src/lib/motisUtils.ts new file mode 100644 index 00000000..fa4fb563 --- /dev/null +++ b/src/lib/motisUtils.ts @@ -0,0 +1,5 @@ +import type { Coordinates } from "./location"; + +export const coordinatesToStr = (c: Coordinates) => { + return `${c.lat};${c.lng}`; +}; \ No newline at end of file diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index 73ade9f7..bcfefb7b 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -4,13 +4,12 @@ import { Interval } from '$lib/interval.js'; import { groupBy, updateValues } from '$lib/collection_utils.js'; import { error, json } from '@sveltejs/kit'; import { hoursToMs, minutesToMs, secondsToMs } from '$lib/time_utils.js'; -import { MAX_TRAVEL_DURATION, MIN_PREP_MINUTES } from '$lib/constants.js'; +import { MAX_TRAVEL_DURATION, MIN_PREP_MINUTES, MOTIS_BASE_URL } from '$lib/constants.js'; import { sql } from 'kysely'; import { getFareEstimation } from './fare-estimation/fare_estimation.js'; import { covers } from '$lib/sqlHelpers.js'; import { oneToMany, type Duration } from '$lib/motis'; - -const MOTIS_BASE_URL = 'https://europe.motis-project.de'; +import { coordinatesToStr } from '$lib/motisUtils.js'; const startAndTargetShareZone = async (from: Coordinates, to: Coordinates) => { const zoneContainingStartAndDestination = await db @@ -33,10 +32,6 @@ export const POST = async (event) => { const toCoordinates: Coordinates = to.coordinates; const time = new Date(timeStamp); - const coordinatesToStr = (c: Coordinates) => { - return `${c.lat};${c.lng}`; - }; - let travelDuration = 0; try { const duration = ( From 2def2bb99b97c072e294a680da8acb7f05884c10 Mon Sep 17 00:00:00 2001 From: nils Date: Sat, 26 Oct 2024 17:28:43 +0200 Subject: [PATCH 06/28] Change API for geocoding according to new Motis version --- src/routes/user/company/+page.server.ts | 25 +++++++++++++++++-------- 1 file changed, 17 insertions(+), 8 deletions(-) diff --git a/src/routes/user/company/+page.server.ts b/src/routes/user/company/+page.server.ts index ba1ea063..846f5c58 100644 --- a/src/routes/user/company/+page.server.ts +++ b/src/routes/user/company/+page.server.ts @@ -2,8 +2,11 @@ import type { PageServerLoad, Actions } from './$types.js'; import { fail } from '@sveltejs/kit'; import { db } from '$lib/database'; import { AddressGuess, geoCode } from '$lib/api.js'; -import type { Coordinates } from '$lib/location.js'; +import { Coordinates } from '$lib/location.js'; import { covers, intersects } from '$lib/sqlHelpers.js'; +import { geocode } from '$lib/motis/services.gen.js'; +import { MOTIS_BASE_URL } from '$lib/constants.js'; +import type { GeocodeResponse } from '$lib/motis/types.gen.js'; export const load: PageServerLoad = async (event) => { const companyId = event.locals.user?.company; @@ -65,14 +68,20 @@ export const actions = { return fail(400, { error: 'Pflichtfahrgebiet nicht gesetzt.' }); } - let bestAddressGuess: AddressGuess | undefined = undefined; - try { - bestAddressGuess = await geoCode(address); - } catch { + const response: GeocodeResponse = await geocode({ + baseUrl: MOTIS_BASE_URL, + query: { + text: address + } + }).then((res) => { + return res.data! + }); + if(response.length==0){ return fail(400, { error: 'Die Addresse konnte nicht gefunden werden.' }); } + const bestAddressGuess = new Coordinates(response[0].lat, response[0].lon); - if (!(await contains(community_area, bestAddressGuess.pos))) { + if (!(await contains(community_area, bestAddressGuess))) { return fail(400, { error: 'Die Addresse liegt nicht in der ausgewählten Gemeinde.' }); @@ -91,8 +100,8 @@ export const actions = { zone, community_area, address, - latitude: bestAddressGuess!.pos.lat, - longitude: bestAddressGuess!.pos.lng + latitude: bestAddressGuess!.lat, + longitude: bestAddressGuess!.lng }) .where('id', '=', companyId) .execute(); From 79271c03a4897dd242661e91541fd872b6cb3f76 Mon Sep 17 00:00:00 2001 From: nils Date: Sat, 26 Oct 2024 17:29:05 +0200 Subject: [PATCH 07/28] Remove unused imports --- src/lib/TourDialog.svelte | 2 -- src/lib/api.ts | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/lib/TourDialog.svelte b/src/lib/TourDialog.svelte index 6632e859..4d2ebe21 100644 --- a/src/lib/TourDialog.svelte +++ b/src/lib/TourDialog.svelte @@ -3,7 +3,6 @@ import * as Table from '$lib/components/ui/table/index.js'; import * as Card from '$lib/components/ui/card'; import { getStyle } from '$lib/style'; - import { getRoute } from '$lib/api'; import Map from '$lib/Map.svelte'; import GeoJSON from '$lib/GeoJSON.svelte'; import Layer from '$lib/Layer.svelte'; @@ -39,7 +38,6 @@ if (tourEvents == null || tourEvents!.length == 0) { return routes; } - for (let e = 0; e < tourEvents!.length - 1; e++) { let e1 = tourEvents![e]; let e2 = tourEvents![e + 1]; diff --git a/src/lib/api.ts b/src/lib/api.ts index a488424b..17d488d1 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -1,5 +1,5 @@ import type { Company, Vehicle } from './types'; -import { Coordinates, Location } from './location'; +import { Location } from './location'; export const getCompany = async (id: number): Promise => { const response = await fetch(`/api/company?id=${id}`); From 64681d540bc500a61015cb0294877530061df396 Mon Sep 17 00:00:00 2001 From: nils Date: Sat, 26 Oct 2024 17:30:10 +0200 Subject: [PATCH 08/28] Remove old geocoding API --- src/lib/api.ts | 24 ------------------------ src/routes/user/company/+page.server.ts | 1 - 2 files changed, 25 deletions(-) diff --git a/src/lib/api.ts b/src/lib/api.ts index 17d488d1..d77936c4 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -96,27 +96,3 @@ export const reassignTour = async (tourId: number) => { console.log('TODO: reassign tour:', tourId); return false; }; - -export class AddressGuess { - pos!: { lat: number; lng: number }; -} - -export async function geoCode(address: string): Promise { - const response = await fetch('https://europe.motis-project.de/?elm=AddressSuggestions', { - headers: { - 'Content-Type': 'application/json' - }, - body: JSON.stringify({ - destination: { type: 'Module', target: '/address' }, - content_type: 'AddressRequest', - content: { input: address } - }), - method: 'POST', - mode: 'cors' - }).then((res) => res.json()); - const guesses = response.content.guesses; - if (guesses.length == 0) { - throw new Error('geoCode did not return any address guesses.'); - } - return guesses[0]; -} diff --git a/src/routes/user/company/+page.server.ts b/src/routes/user/company/+page.server.ts index 846f5c58..fbdaa2c9 100644 --- a/src/routes/user/company/+page.server.ts +++ b/src/routes/user/company/+page.server.ts @@ -1,7 +1,6 @@ import type { PageServerLoad, Actions } from './$types.js'; import { fail } from '@sveltejs/kit'; import { db } from '$lib/database'; -import { AddressGuess, geoCode } from '$lib/api.js'; import { Coordinates } from '$lib/location.js'; import { covers, intersects } from '$lib/sqlHelpers.js'; import { geocode } from '$lib/motis/services.gen.js'; From c471980e8cba390b1d0287842954907e3a3feb3d Mon Sep 17 00:00:00 2001 From: nils Date: Sat, 26 Oct 2024 17:30:35 +0200 Subject: [PATCH 09/28] Format --- src/lib/motisUtils.ts | 6 +++--- src/routes/api/booking/+server.ts | 2 +- src/routes/user/company/+page.server.ts | 6 +++--- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/lib/motisUtils.ts b/src/lib/motisUtils.ts index fa4fb563..cd80e56d 100644 --- a/src/lib/motisUtils.ts +++ b/src/lib/motisUtils.ts @@ -1,5 +1,5 @@ -import type { Coordinates } from "./location"; +import type { Coordinates } from './location'; export const coordinatesToStr = (c: Coordinates) => { - return `${c.lat};${c.lng}`; -}; \ No newline at end of file + return `${c.lat};${c.lng}`; +}; diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index bcfefb7b..a32a4dd1 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -184,7 +184,7 @@ export const POST = async (event) => { console.assert( Math.max(...[...mergedAvailabilites.values()].map((availabilities) => availabilities.length)) <= - 1 + 1 ); const availableVehicles = [...mergedAvailabilites.entries()] diff --git a/src/routes/user/company/+page.server.ts b/src/routes/user/company/+page.server.ts index fbdaa2c9..45f81489 100644 --- a/src/routes/user/company/+page.server.ts +++ b/src/routes/user/company/+page.server.ts @@ -67,15 +67,15 @@ export const actions = { return fail(400, { error: 'Pflichtfahrgebiet nicht gesetzt.' }); } - const response: GeocodeResponse = await geocode({ + const response: GeocodeResponse = await geocode({ baseUrl: MOTIS_BASE_URL, query: { text: address } }).then((res) => { - return res.data! + return res.data!; }); - if(response.length==0){ + if (response.length == 0) { return fail(400, { error: 'Die Addresse konnte nicht gefunden werden.' }); } const bestAddressGuess = new Coordinates(response[0].lat, response[0].lon); From 9638476b3f8decb19274848a5e2606111d9145d3 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Tue, 29 Oct 2024 11:52:25 +0100 Subject: [PATCH 10/28] update .gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index 2a8f5aea..db3896b6 100644 --- a/.gitignore +++ b/.gitignore @@ -13,3 +13,4 @@ booking-generator/data/stops.txt booking-generator/test .vscode /driver-app/.gradle/ +/driver-app/.idea From 8e7bc4379f65929085a9c736bb46e31bad1acd8d Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 31 Oct 2024 15:27:30 +0100 Subject: [PATCH 11/28] login and basic navigation --- driver-app/app/build.gradle.kts | 13 +- driver-app/app/src/main/AndroidManifest.xml | 6 +- .../app/src/main/java/de/motis/prima/Home.kt | 129 ++++++++++++ .../app/src/main/java/de/motis/prima/Login.kt | 195 ++++++++++++++++++ .../main/java/de/motis/prima/MainActivity.kt | 6 +- .../app/src/main/java/de/motis/prima/Nav.kt | 51 +++++ .../app/src/main/java/de/motis/prima/Tours.kt | 103 +++++++++ .../src/main/java/de/motis/prima/Vehicles.kt | 103 +++++++++ .../java/de/motis/prima/app/DriversApp.kt | 16 ++ .../main/java/de/motis/prima/services/Api.kt | 33 +++ .../de/motis/prima/services/CookieStore.kt | 49 +++++ .../de/motis/prima/services/OkHttpClient.kt | 27 +++ .../app/src/main/res/layout/activity_main.xml | 6 - .../app/src/main/res/values/strings.xml | 7 +- driver-app/gradle/libs.versions.toml | 9 +- 15 files changed, 739 insertions(+), 14 deletions(-) create mode 100644 driver-app/app/src/main/java/de/motis/prima/Home.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/Login.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/Nav.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/Tours.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/Vehicles.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/app/DriversApp.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/services/Api.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/services/CookieStore.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/services/OkHttpClient.kt delete mode 100644 driver-app/app/src/main/res/layout/activity_main.xml diff --git a/driver-app/app/build.gradle.kts b/driver-app/app/build.gradle.kts index e79df9d5..6371c51e 100644 --- a/driver-app/app/build.gradle.kts +++ b/driver-app/app/build.gradle.kts @@ -20,7 +20,7 @@ android { buildTypes { debug { - buildConfigField("String", "BASE_URL", "\"http://130.83.165.211:8080\"") + buildConfigField("String", "BASE_URL", "\"http://130.83.165.211:7777\"") } release { isMinifyEnabled = false @@ -28,10 +28,12 @@ android { getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro" ) + buildConfigField("String", "BASE_URL", "\"https://prima.motis-project.de\"") } } buildFeatures { buildConfig = true + compose = true } composeOptions { kotlinCompilerExtensionVersion = "1.5.0" @@ -49,7 +51,14 @@ dependencies { implementation(libs.androidx.core.ktx) implementation(libs.androidx.appcompat) implementation(libs.material) + implementation(libs.androidx.runtime.android) + implementation(libs.androidx.navigation.compose) + implementation("com.squareup.okhttp3:okhttp:4.12.0") + implementation("com.squareup.retrofit2:retrofit:2.11.0") + implementation("com.squareup.retrofit2:converter-gson:2.9.0") + implementation("androidx.constraintlayout:constraintlayout-compose:1.0.1") + implementation(libs.androidx.material3.android) testImplementation(libs.junit) androidTestImplementation(libs.androidx.junit) androidTestImplementation(libs.androidx.espresso.core) -} \ No newline at end of file +} diff --git a/driver-app/app/src/main/AndroidManifest.xml b/driver-app/app/src/main/AndroidManifest.xml index 64217890..f5cd14cf 100644 --- a/driver-app/app/src/main/AndroidManifest.xml +++ b/driver-app/app/src/main/AndroidManifest.xml @@ -2,7 +2,11 @@ + + - \ No newline at end of file + diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt new file mode 100644 index 00000000..adb79b4b --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -0,0 +1,129 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.width +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material3.Button +import androidx.compose.material3.Icon +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TextButton +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +class HomeViewModel : ViewModel() { + private val cookieStore: CookieStore = CookieStore(DriversApp.instance) + + private val _logoutEvent = MutableSharedFlow() + val logoutEvent = _logoutEvent.asSharedFlow() + + fun logout() { + viewModelScope.launch { + try { + cookieStore.clearCookies() + _logoutEvent.emit(Unit) + } catch (e: Exception) { + Log.d("Logout", "Error while logout.") + } + } + } +} + +@Composable +fun Home( + navController: NavController, + viewModel: HomeViewModel = androidx.lifecycle.viewmodel.compose.viewModel() +) { + LaunchedEffect(key1 = viewModel) { + launch { + viewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + popUpTo(navController.graph.startDestinationId) { + inclusive = true + } + launchSingleTop = true + } + } + } + } + + Scaffold( + modifier = Modifier + .fillMaxSize() + ) { contentPadding -> + Column( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) + ) { + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.End + ) { + TextButton(onClick = { viewModel.logout() }) { + Icon( + Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null + ) + } + } + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("vehicles") {} + } + ) { + Text( + text = "Fahrzeug auswählen", fontSize = 24.sp + ) + } + } + + Spacer(modifier = Modifier.height(20.dp)) + + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("tours") {} + } + ) { + Text( + text = "Aufträge", fontSize = 24.sp + ) + } + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/Login.kt b/driver-app/app/src/main/java/de/motis/prima/Login.kt new file mode 100644 index 00000000..c58ecd63 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Login.kt @@ -0,0 +1,195 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.BoxWithConstraints +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.wrapContentHeight +import androidx.compose.foundation.text.KeyboardOptions +import androidx.compose.material3.Text +import androidx.compose.material3.Button +import androidx.compose.material3.OutlinedTextField +import androidx.compose.material3.Scaffold +import androidx.compose.material3.SnackbarHost +import androidx.compose.material3.SnackbarHostState +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.input.KeyboardType +import androidx.compose.ui.text.input.PasswordVisualTransformation +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.constraintlayout.compose.ConstraintLayout +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.services.Api +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +class LoginViewModel : ViewModel() { + // Event which will be omitted to the Login component, indicating success of the login operation + private val _navigationEvent = MutableSharedFlow() + val navigationEvent = _navigationEvent.asSharedFlow() + + private val _loginErrorEvent = MutableSharedFlow() + val loginErrorEvent = _loginErrorEvent.asSharedFlow() + + private val _networkErrorEvent = MutableSharedFlow() + val networkErrorEvent = _networkErrorEvent.asSharedFlow() + + fun login(email: String, password: String) { + viewModelScope.launch { + try { + val response = Api.apiService.login(email, password) + Log.d("Login Response", response.toString()) + if (response.status == 302) { + // successful login + _navigationEvent.emit(true) + } else { + _loginErrorEvent.emit(true) + } + } catch (e: Exception) { + Log.d("Login Response Network Error", e.message!!) + _networkErrorEvent.emit(Unit) + } + } + } +} + +@Composable +fun Login( + navController: NavController, + viewModel: LoginViewModel = androidx.lifecycle.viewmodel.compose.viewModel() +) { + val snackbarHostState = remember { SnackbarHostState() } + + var isLoginFailed by remember { mutableStateOf(false) } + + val networkErrorMessage = stringResource(id = R.string.network_error_message) + + LaunchedEffect(key1 = viewModel) { + // Catching successful login event and navigation to the next screen + launch { + viewModel.navigationEvent.collect { shouldNavigate -> + Log.d("Navigation event", "Navigation triggered.") + if (shouldNavigate) { + Log.d("Navigation event", "Navigating to vehicle selection.") + navController.navigate("home") { + popUpTo("login") { + inclusive = true + } + } + } + } + } + + // Catching event when login failed due to incorrect login data + launch { + viewModel.loginErrorEvent.collect { error -> + isLoginFailed = error + } + } + + // Catching event when a network error occurs and displaying of error message + launch { + viewModel.networkErrorEvent.collect { + snackbarHostState.showSnackbar(message = networkErrorMessage) + } + } + } + + Scaffold( + modifier = Modifier.fillMaxSize(), + snackbarHost = { + BoxWithConstraints(modifier = Modifier.fillMaxSize()) { + SnackbarHost( + hostState = snackbarHostState, + modifier = Modifier + .fillMaxSize() + .wrapContentHeight(Alignment.Top) + .padding(top = maxHeight * 0.25f) + ) + } + } + ) { contentPadding -> + ConstraintLayout( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) + ) { + var email by remember { + mutableStateOf("") + } + + var password by remember { + mutableStateOf("") + } + + Column( + modifier = Modifier.fillMaxSize(), + verticalArrangement = Arrangement.Center, + horizontalAlignment = Alignment.CenterHorizontally + ) { + when { + isLoginFailed -> + Text( + text = stringResource(id = R.string.wrong_login_data), + color = Color.Red, + fontWeight = FontWeight.Bold, + modifier = Modifier.padding(bottom = 8.dp) + ) + } + OutlinedTextField( + value = email, + onValueChange = { + email = it + isLoginFailed = false + }, + label = { Text(stringResource(id = R.string.email_label)) }, + maxLines = 1, + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Email), + isError = isLoginFailed + ) + Spacer(modifier = Modifier.height(12.dp)) + OutlinedTextField( + value = password, + onValueChange = { + password = it + isLoginFailed = false + }, + label = { Text(stringResource(id = R.string.password_label)) }, + maxLines = 1, + visualTransformation = PasswordVisualTransformation(), + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Password), + isError = isLoginFailed + ) + Spacer(modifier = Modifier.height(20.dp)) + Button( + onClick = { + isLoginFailed = false + Log.d("Login", "E-Mail: ${email}, Password: $password") + viewModel.login(email, password) + } + ) { + Text( + text = stringResource(id = R.string.login_button_text), fontSize = 18.sp + ) + } + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt b/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt index 82713e7b..eed0be81 100644 --- a/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt +++ b/driver-app/app/src/main/java/de/motis/prima/MainActivity.kt @@ -1,6 +1,7 @@ package de.motis.prima import android.os.Bundle +import androidx.activity.compose.setContent import androidx.activity.enableEdgeToEdge import androidx.appcompat.app.AppCompatActivity @@ -9,5 +10,8 @@ class MainActivity : AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) enableEdgeToEdge() + setContent { + Nav() + } } -} \ No newline at end of file +} diff --git a/driver-app/app/src/main/java/de/motis/prima/Nav.kt b/driver-app/app/src/main/java/de/motis/prima/Nav.kt new file mode 100644 index 00000000..814dabe3 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Nav.kt @@ -0,0 +1,51 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.runtime.Composable +import androidx.compose.runtime.derivedStateOf +import androidx.compose.runtime.getValue +import androidx.compose.runtime.remember +import androidx.navigation.compose.NavHost +import androidx.navigation.compose.composable +import androidx.navigation.compose.rememberNavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore + +@Composable +fun Nav() { + + val navController = rememberNavController() + + // Check before render of any component whether user is authenticated. + val startDestination by remember { + derivedStateOf { + val cookieStore = CookieStore(DriversApp.instance) + if (cookieStore.isEmpty()) { + Log.d("Cookie", "No Cookie found. Navigating to Login.") + "login" + } else { + Log.d("Cookie", "Cookie found. Navigating to Journeys.") + "home" + } + } + } + + NavHost(navController = navController, startDestination = startDestination) { + + composable(route = "login") { + Login(navController) + } + + composable(route = "home") { + Home(navController) + } + + composable(route = "vehicles") { + Vehicles(navController) + } + + composable(route = "tours") { + Tours(navController) + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt new file mode 100644 index 00000000..120eb002 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -0,0 +1,103 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.width +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material3.Button +import androidx.compose.material3.Icon +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TextButton +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +class ToursViewModel : ViewModel() { + private val cookieStore: CookieStore = CookieStore(DriversApp.instance) + + private val _logoutEvent = MutableSharedFlow() + val logoutEvent = _logoutEvent.asSharedFlow() + + fun logout() { + viewModelScope.launch { + try { + cookieStore.clearCookies() + _logoutEvent.emit(Unit) + } catch (e: Exception) { + Log.d("Logout", "Error while logout.") + } + } + } +} + +@Composable +fun Tours( + navController: NavController, + viewModel: VehiclesViewModel = androidx.lifecycle.viewmodel.compose.viewModel() +) { + LaunchedEffect(key1 = viewModel) { + launch { + viewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + popUpTo(navController.graph.startDestinationId) { + inclusive = true + } + launchSingleTop = true + } + } + } + } + + Scaffold( + modifier = Modifier + .fillMaxSize() + ) { contentPadding -> + Column( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) + ) { + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.End + ) { + TextButton(onClick = { viewModel.logout() }) { + Icon( + Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null + ) + } + } + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Text( + text = "Liste der Aufträge", fontSize = 24.sp + ) + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt new file mode 100644 index 00000000..90d6ee68 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -0,0 +1,103 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.width +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material3.Button +import androidx.compose.material3.Icon +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TextButton +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +class VehiclesViewModel : ViewModel() { + private val cookieStore: CookieStore = CookieStore(DriversApp.instance) + + private val _logoutEvent = MutableSharedFlow() + val logoutEvent = _logoutEvent.asSharedFlow() + + fun logout() { + viewModelScope.launch { + try { + cookieStore.clearCookies() + _logoutEvent.emit(Unit) + } catch (e: Exception) { + Log.d("Logout", "Error while logout.") + } + } + } +} + +@Composable +fun Vehicles( + navController: NavController, + viewModel: VehiclesViewModel = androidx.lifecycle.viewmodel.compose.viewModel() +) { + LaunchedEffect(key1 = viewModel) { + launch { + viewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + popUpTo(navController.graph.startDestinationId) { + inclusive = true + } + launchSingleTop = true + } + } + } + } + + Scaffold( + modifier = Modifier + .fillMaxSize() + ) { contentPadding -> + Column( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) + ) { + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.End + ) { + TextButton(onClick = { viewModel.logout() }) { + Icon( + Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null + ) + } + } + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Text( + text = "Liste der Fahrzeuge", fontSize = 24.sp + ) + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/app/DriversApp.kt b/driver-app/app/src/main/java/de/motis/prima/app/DriversApp.kt new file mode 100644 index 00000000..af82d604 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/app/DriversApp.kt @@ -0,0 +1,16 @@ +package de.motis.prima.app + +import android.app.Application + +class DriversApp: Application() { + + companion object { + lateinit var instance: DriversApp + private set + } + + override fun onCreate() { + super.onCreate() + instance = this + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/services/Api.kt b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt new file mode 100644 index 00000000..c688533b --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt @@ -0,0 +1,33 @@ +package de.motis.prima.services + +import de.motis.prima.BuildConfig.BASE_URL +import retrofit2.Retrofit +import retrofit2.converter.gson.GsonConverterFactory +import retrofit2.http.Field +import retrofit2.http.FormUrlEncoded +import retrofit2.http.POST + +interface ApiService { + @POST("login") + @FormUrlEncoded + suspend fun login( + @Field("email") email: String, + @Field("password") password: String + ): LoginResponse +} + +object Api { + private val retrofit: Retrofit = Retrofit.Builder() + .baseUrl(BASE_URL) + .client(okHttpClient().build()) + .addConverterFactory(GsonConverterFactory.create()) + .build() + + val apiService: ApiService = retrofit.create(ApiService::class.java) +} + +data class LoginResponse( + val type: String, + val status: Int, + val data: String +) diff --git a/driver-app/app/src/main/java/de/motis/prima/services/CookieStore.kt b/driver-app/app/src/main/java/de/motis/prima/services/CookieStore.kt new file mode 100644 index 00000000..217bebfe --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/services/CookieStore.kt @@ -0,0 +1,49 @@ +package de.motis.prima.services + +import android.content.Context +import android.content.SharedPreferences +import android.util.Log +import okhttp3.Cookie +import okhttp3.CookieJar +import okhttp3.HttpUrl + +class CookieStore(context: Context) : CookieJar { + private val preferences: SharedPreferences = context.getSharedPreferences("cookies", Context.MODE_PRIVATE) + + override fun saveFromResponse(url: HttpUrl, cookies: List) { + val editor = preferences.edit() + val serializedCookie = cookies.joinToString(";") { cookie -> cookie.toString() } + editor.putString(url.host, serializedCookie) + editor.apply() + } + + override fun loadForRequest(url: HttpUrl): List { + val cookiesString = preferences.getString(url.host, null) + if (cookiesString.isNullOrEmpty()) { + Log.d("Cookie", "No stored cookie found.") + return listOf() + } + Log.d("cookie", "Cookie is $cookiesString") + + val cookie = Cookie.parse(url, cookiesString) + if (cookie == null) { + Log.d("Cookie", "No cookie for host found.") + return listOf() + } + return listOf(cookie) + } + + fun clearCookies(host: String? = null) { + val editor = preferences.edit() + if (host != null) { + editor.remove(host) + } else { + editor.clear() + } + editor.apply() + } + + fun isEmpty(): Boolean { + return preferences.all.isEmpty() + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/services/OkHttpClient.kt b/driver-app/app/src/main/java/de/motis/prima/services/OkHttpClient.kt new file mode 100644 index 00000000..32120f80 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/services/OkHttpClient.kt @@ -0,0 +1,27 @@ +package de.motis.prima.services + +import de.motis.prima.BuildConfig +import de.motis.prima.app.DriversApp +import okhttp3.Interceptor +import okhttp3.OkHttpClient +import okhttp3.Request +import okhttp3.Response + +/** + * The login api accepts only requests with the following headers set explicitly + * This must be changed when CORS settings will be changed. + */ +fun okHttpClient() = OkHttpClient().newBuilder() + .cookieJar(CookieStore(DriversApp.instance)) + .addInterceptor( + object : Interceptor { + override fun intercept(chain: Interceptor.Chain): Response { + val request: Request = chain.request() + .newBuilder() + .header("x-sveltekit-action", "true") + .header("Origin", BuildConfig.BASE_URL) + .build() + return chain.proceed(request) + } + } + ) diff --git a/driver-app/app/src/main/res/layout/activity_main.xml b/driver-app/app/src/main/res/layout/activity_main.xml deleted file mode 100644 index 77d9ef65..00000000 --- a/driver-app/app/src/main/res/layout/activity_main.xml +++ /dev/null @@ -1,6 +0,0 @@ - - - - \ No newline at end of file diff --git a/driver-app/app/src/main/res/values/strings.xml b/driver-app/app/src/main/res/values/strings.xml index 1139b02b..49c49cc1 100644 --- a/driver-app/app/src/main/res/values/strings.xml +++ b/driver-app/app/src/main/res/values/strings.xml @@ -1,3 +1,8 @@ Prima+ÖV - \ No newline at end of file + Anmelden + Passwort oder E-Mail sind inkorrekt. + E-Mail + Passwort + Etwas ist schiefgelaufen. Bitte versuchen Sie es später erneut. + diff --git a/driver-app/gradle/libs.versions.toml b/driver-app/gradle/libs.versions.toml index ec9c4678..3669c45d 100644 --- a/driver-app/gradle/libs.versions.toml +++ b/driver-app/gradle/libs.versions.toml @@ -7,7 +7,9 @@ junitVersion = "1.2.1" espressoCore = "3.6.1" appcompat = "1.7.0" material = "1.12.0" - +runtimeAndroid = "1.7.4" +navigationCompose = "2.8.3" +material3Android = "1.3.0" [libraries] androidx-core-ktx = { group = "androidx.core", name = "core-ktx", version.ref = "coreKtx" } @@ -16,9 +18,10 @@ androidx-junit = { group = "androidx.test.ext", name = "junit", version.ref = "j androidx-espresso-core = { group = "androidx.test.espresso", name = "espresso-core", version.ref = "espressoCore" } androidx-appcompat = { group = "androidx.appcompat", name = "appcompat", version.ref = "appcompat" } material = { group = "com.google.android.material", name = "material", version.ref = "material" } - +androidx-runtime-android = { group = "androidx.compose.runtime", name = "runtime-android", version.ref = "runtimeAndroid" } +androidx-navigation-compose = { group = "androidx.navigation", name = "navigation-compose", version.ref = "navigationCompose" } +androidx-material3-android = { group = "androidx.compose.material3", name = "material3-android", version.ref = "material3Android" } [plugins] android-application = { id = "com.android.application", version.ref = "agp" } jetbrains-kotlin-android = { id = "org.jetbrains.kotlin.android", version.ref = "kotlin" } - From 32fe6c1e279de8ef980beb7a20c1e4170530c73f Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Fri, 1 Nov 2024 12:43:16 +0100 Subject: [PATCH 12/28] prevent back navigation from login screen --- driver-app/app/src/main/java/de/motis/prima/Home.kt | 3 --- driver-app/app/src/main/java/de/motis/prima/Login.kt | 8 ++++++++ driver-app/app/src/main/java/de/motis/prima/Tours.kt | 3 --- driver-app/app/src/main/java/de/motis/prima/Vehicles.kt | 3 --- 4 files changed, 8 insertions(+), 9 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index adb79b4b..bed66d28 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -60,9 +60,6 @@ fun Home( viewModel.logoutEvent.collect { Log.d("Logout", "Logout event triggered.") navController.navigate("login") { - popUpTo(navController.graph.startDestinationId) { - inclusive = true - } launchSingleTop = true } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Login.kt b/driver-app/app/src/main/java/de/motis/prima/Login.kt index c58ecd63..315ca3d2 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Login.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Login.kt @@ -1,6 +1,8 @@ package de.motis.prima +import android.app.Activity import android.util.Log +import androidx.activity.compose.BackHandler import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.BoxWithConstraints import androidx.compose.foundation.layout.Column @@ -25,6 +27,7 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.input.KeyboardType @@ -81,6 +84,11 @@ fun Login( val networkErrorMessage = stringResource(id = R.string.network_error_message) + val activity = (LocalContext.current as? Activity) + BackHandler { + activity?.finish() + } + LaunchedEffect(key1 = viewModel) { // Catching successful login event and navigation to the next screen launch { diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index 120eb002..dfc9353f 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -60,9 +60,6 @@ fun Tours( viewModel.logoutEvent.collect { Log.d("Logout", "Logout event triggered.") navController.navigate("login") { - popUpTo(navController.graph.startDestinationId) { - inclusive = true - } launchSingleTop = true } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index 90d6ee68..67b939bf 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -60,9 +60,6 @@ fun Vehicles( viewModel.logoutEvent.collect { Log.d("Logout", "Logout event triggered.") navController.navigate("login") { - popUpTo(navController.graph.startDestinationId) { - inclusive = true - } launchSingleTop = true } } From 6a48b42a2ed8a812ad96ad01e8b895d08be31e06 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Fri, 1 Nov 2024 17:08:13 +0100 Subject: [PATCH 13/28] update .gitignore, test readme --- .gitignore | 1 + driver-app/test-setup.md | 44 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 45 insertions(+) create mode 100644 driver-app/test-setup.md diff --git a/.gitignore b/.gitignore index db3896b6..02febdb2 100644 --- a/.gitignore +++ b/.gitignore @@ -14,3 +14,4 @@ booking-generator/test .vscode /driver-app/.gradle/ /driver-app/.idea +/driver-app/local.properties diff --git a/driver-app/test-setup.md b/driver-app/test-setup.md new file mode 100644 index 00000000..8ecf433a --- /dev/null +++ b/driver-app/test-setup.md @@ -0,0 +1,44 @@ +# Testing the mobile app + +Spin up a docker container with the test version of backend server, setup app config and use an emulator to test. + +## 1 Modify src/lib/auth.ts + +Change line 28: + +``` +secure: !dev +``` +to +``` +secure: false +``` + +in order to allow the backend API to accept plaintext https requests + +## 2 Modify docker-compose.yml + +Set env-variable +``` +ORIGIN=http://your-public-ip:7777 +``` + +## 3 Build backend server and run the docker container + +Run +``` +npm build +docker compose build +docker compose up +``` + +## 4 Modify driver-app/build.gradle.kts (Module :app) + +``` +buildTypes { + debug { + buildConfigField("String", "BASE_URL", "\"http://your-public-ip:7777\"") + } + ... +} +``` From e7d885f3a90756280752f5d671a23d9842e7d097 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Sat, 2 Nov 2024 13:36:05 +0100 Subject: [PATCH 14/28] navigation --- .../app/src/main/java/de/motis/prima/Home.kt | 167 +++++++++++++----- .../app/src/main/java/de/motis/prima/Tours.kt | 115 +++++++++--- .../src/main/java/de/motis/prima/Vehicles.kt | 116 ++++++++++-- 3 files changed, 321 insertions(+), 77 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index bed66d28..8be8cf90 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -2,6 +2,7 @@ package de.motis.prima import android.util.Log import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer @@ -11,16 +12,38 @@ import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack +import androidx.compose.material.icons.automirrored.outlined.ArrowBack import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material.icons.filled.Menu +import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.Button +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DrawerValue +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.ModalNavigationDrawer import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.material3.TextButton +import androidx.compose.material3.TopAppBar +import androidx.compose.material3.TopAppBarDefaults +import androidx.compose.material3.rememberDrawerState import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.rememberCoroutineScope +import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.text.style.TextAlign +import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp import androidx.lifecycle.ViewModel @@ -50,6 +73,7 @@ class HomeViewModel : ViewModel() { } } +@OptIn(ExperimentalMaterial3Api::class) @Composable fun Home( navController: NavController, @@ -66,59 +90,110 @@ fun Home( } } + var dropdownExpanded by remember { + mutableStateOf(false) + } + Scaffold( - modifier = Modifier - .fillMaxSize() - ) { contentPadding -> - Column( - modifier = Modifier - .fillMaxSize() - .padding(contentPadding) - ) { - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.End - ) { - TextButton(onClick = { viewModel.logout() }) { - Icon( - Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null - ) - } - } - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Button( - modifier = Modifier.width(300.dp), - onClick = { - navController.navigate("vehicles") {} - } - ) { + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { Text( - text = "Fahrzeug auswählen", fontSize = 24.sp + "Home", + maxLines = 1, + overflow = TextOverflow.Ellipsis ) - } - } + }, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + // Handle menu item click + dropdownExpanded = false - Spacer(modifier = Modifier.height(20.dp)) + }, + text = {Text("Option 1")} + ) + DropdownMenuItem( + onClick = { + viewModel.logout() + dropdownExpanded = false - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Button( - modifier = Modifier.width(300.dp), - onClick = { - navController.navigate("tours") {} + }, + text = {Text("Logout")} + ) } + }, + // scrollBehavior = scrollBehavior, + ) + + } + ) { innerPadding -> + // Main Content + Box( + modifier = Modifier + .padding(innerPadding) + .fillMaxSize(), + contentAlignment = Alignment.Center + ) { + Scaffold( + modifier = Modifier + .fillMaxSize() + ) { contentPadding -> + Column( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) ) { - Text( - text = "Aufträge", fontSize = 24.sp - ) + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("vehicles") {} + } + ) { + Text( + text = "Fahrzeug auswählen", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + + Spacer(modifier = Modifier.height(20.dp)) + + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("tours") {} + } + ) { + Text( + text = "Aufträge", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index dfc9353f..ad024460 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -2,6 +2,7 @@ package de.motis.prima import android.util.Log import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer @@ -10,17 +11,37 @@ import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.rememberScrollState +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.foundation.verticalScroll import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.Button +import androidx.compose.material3.Card +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.material3.TextButton +import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp import androidx.lifecycle.ViewModel @@ -50,6 +71,7 @@ class ToursViewModel : ViewModel() { } } +@OptIn(ExperimentalMaterial3Api::class) @Composable fun Tours( navController: NavController, @@ -66,35 +88,86 @@ fun Tours( } } + var dropdownExpanded by remember { + mutableStateOf(false) + } + Scaffold( - modifier = Modifier - .fillMaxSize() + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { + Text( + "Aufträge", + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + }, + navigationIcon = { + IconButton(onClick = { navController.navigate("home") }) { + Icon( + imageVector = Icons.AutoMirrored.Filled.ArrowBack, + contentDescription = "Localized description" + ) + } + }, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + dropdownExpanded = false + + }, + text = { Text("Option 1") } + ) + DropdownMenuItem( + onClick = { + viewModel.logout() + dropdownExpanded = false + + }, + text = { Text("Logout") } + ) + } + } + ) + + } ) { contentPadding -> - Column( + LazyColumn( modifier = Modifier .fillMaxSize() .padding(contentPadding) ) { - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.End - ) { - TextButton(onClick = { viewModel.logout() }) { - Icon( - Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null - ) + items(8) { index -> + Card( + shape = RoundedCornerShape(12.dp), + modifier = Modifier + .fillMaxWidth() + .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) + .height(100.dp) + ) { + Box( + modifier = Modifier.fillMaxSize().padding(16.dp), + contentAlignment = Alignment.TopStart + ) { + Column { + Text("08:30", fontSize = 24.sp, fontWeight = FontWeight.Bold) + Spacer(modifier = Modifier.height(12.dp)) + Text("Görlitz, Beispielplatz ${index + 1}", fontSize = 24.sp) + } + } } } - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Text( - text = "Liste der Aufträge", fontSize = 24.sp - ) - } } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index 67b939bf..e178b342 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -2,6 +2,7 @@ package de.motis.prima import android.util.Log import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer @@ -10,17 +11,36 @@ import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width +import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack import androidx.compose.material.icons.automirrored.outlined.ExitToApp +import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.Button +import androidx.compose.material3.Card +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.material3.TextButton +import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextAlign +import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp import androidx.lifecycle.ViewModel @@ -50,6 +70,7 @@ class VehiclesViewModel : ViewModel() { } } +@OptIn(ExperimentalMaterial3Api::class) @Composable fun Vehicles( navController: NavController, @@ -66,9 +87,61 @@ fun Vehicles( } } + var dropdownExpanded by remember { + mutableStateOf(false) + } + Scaffold( - modifier = Modifier - .fillMaxSize() + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { + Text( + "Fahrzeuge", + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + }, + navigationIcon = { + IconButton(onClick = { navController.navigate("home") }) { + Icon( + imageVector = Icons.AutoMirrored.Filled.ArrowBack, + contentDescription = "Localized description" + ) + } + }, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + dropdownExpanded = false + + }, + text = { Text("Option 1") } + ) + DropdownMenuItem( + onClick = { + viewModel.logout() + dropdownExpanded = false + + }, + text = { Text("Logout") } + ) + } + }, + // scrollBehavior = scrollBehavior, + ) + + } ) { contentPadding -> Column( modifier = Modifier @@ -78,22 +151,45 @@ fun Vehicles( Row( modifier = Modifier.fillMaxWidth(), verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.End + horizontalArrangement = Arrangement.Center ) { - TextButton(onClick = { viewModel.logout() }) { - Icon( - Icons.AutoMirrored.Outlined.ExitToApp, contentDescription = null - ) + Card( + shape = RoundedCornerShape(12.dp), + modifier = Modifier + .fillMaxWidth() + .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) + .height(80.dp) + .align(alignment = Alignment.CenterVertically) + ) { + Box( + modifier = Modifier.fillMaxSize(), + contentAlignment = Alignment.Center // Center content within the Box + ) { + Text("GR-TU-11", fontSize = 24.sp, fontWeight = FontWeight.Bold) + } } } + Row( modifier = Modifier.fillMaxWidth(), verticalAlignment = Alignment.CenterVertically, horizontalArrangement = Arrangement.Center ) { - Text( - text = "Liste der Fahrzeuge", fontSize = 24.sp - ) + Card( + shape = RoundedCornerShape(12.dp), + modifier = Modifier + .fillMaxWidth() + .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) + .height(80.dp) + .align(alignment = Alignment.CenterVertically) + ) { + Box( + modifier = Modifier.fillMaxSize(), + contentAlignment = Alignment.Center // Center content within the Box + ) { + Text("GR-TU-12", fontSize = 24.sp, fontWeight = FontWeight.Bold) + } + } } } } From 822de402a1ef1e89d7363ff6bc2826f56177e181 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Sat, 2 Nov 2024 13:43:32 +0100 Subject: [PATCH 15/28] wip --- driver-app/app/src/main/java/de/motis/prima/Home.kt | 10 ---------- driver-app/app/src/main/java/de/motis/prima/Tours.kt | 10 +--------- .../app/src/main/java/de/motis/prima/Vehicles.kt | 7 ------- 3 files changed, 1 insertion(+), 26 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index 8be8cf90..701fc64d 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -12,33 +12,23 @@ import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width import androidx.compose.material.icons.Icons -import androidx.compose.material.icons.automirrored.filled.ArrowBack -import androidx.compose.material.icons.automirrored.outlined.ArrowBack -import androidx.compose.material.icons.automirrored.outlined.ExitToApp -import androidx.compose.material.icons.filled.Menu import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.Button import androidx.compose.material3.CenterAlignedTopAppBar -import androidx.compose.material3.DrawerValue import androidx.compose.material3.DropdownMenu import androidx.compose.material3.DropdownMenuItem import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Icon import androidx.compose.material3.IconButton import androidx.compose.material3.MaterialTheme -import androidx.compose.material3.ModalNavigationDrawer import androidx.compose.material3.Scaffold import androidx.compose.material3.Text -import androidx.compose.material3.TextButton -import androidx.compose.material3.TopAppBar import androidx.compose.material3.TopAppBarDefaults -import androidx.compose.material3.rememberDrawerState import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect import androidx.compose.runtime.getValue import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember -import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index ad024460..65595b3f 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -1,25 +1,18 @@ package de.motis.prima import android.util.Log -import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.width import androidx.compose.foundation.lazy.LazyColumn -import androidx.compose.foundation.rememberScrollState import androidx.compose.foundation.shape.RoundedCornerShape -import androidx.compose.foundation.verticalScroll import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack -import androidx.compose.material.icons.automirrored.outlined.ExitToApp import androidx.compose.material.icons.filled.MoreVert -import androidx.compose.material3.Button import androidx.compose.material3.Card import androidx.compose.material3.CenterAlignedTopAppBar import androidx.compose.material3.DropdownMenu @@ -30,7 +23,6 @@ import androidx.compose.material3.IconButton import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold import androidx.compose.material3.Text -import androidx.compose.material3.TextButton import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect @@ -75,7 +67,7 @@ class ToursViewModel : ViewModel() { @Composable fun Tours( navController: NavController, - viewModel: VehiclesViewModel = androidx.lifecycle.viewmodel.compose.viewModel() + viewModel: ToursViewModel = androidx.lifecycle.viewmodel.compose.viewModel() ) { LaunchedEffect(key1 = viewModel) { launch { diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index e178b342..4cd1b94b 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -5,18 +5,14 @@ import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row -import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.width import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack -import androidx.compose.material.icons.automirrored.outlined.ExitToApp import androidx.compose.material.icons.filled.MoreVert -import androidx.compose.material3.Button import androidx.compose.material3.Card import androidx.compose.material3.CenterAlignedTopAppBar import androidx.compose.material3.DropdownMenu @@ -27,7 +23,6 @@ import androidx.compose.material3.IconButton import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold import androidx.compose.material3.Text -import androidx.compose.material3.TextButton import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect @@ -37,9 +32,7 @@ import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.graphics.Color import androidx.compose.ui.text.font.FontWeight -import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp From c360a40dffd3ad39282678a38a5abccc07f3dd47 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Sat, 2 Nov 2024 14:05:01 +0100 Subject: [PATCH 16/28] wip --- driver-app/app/src/main/java/de/motis/prima/Home.kt | 5 ++--- driver-app/app/src/main/java/de/motis/prima/Vehicles.kt | 3 +-- 2 files changed, 3 insertions(+), 5 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index 701fc64d..10ae0b10 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -123,8 +123,7 @@ fun Home( text = {Text("Logout")} ) } - }, - // scrollBehavior = scrollBehavior, + } ) } @@ -164,7 +163,7 @@ fun Home( } } - Spacer(modifier = Modifier.height(20.dp)) + Spacer(modifier = Modifier.height(36.dp)) Row( modifier = Modifier.fillMaxWidth(), diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index 4cd1b94b..321e47af 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -130,8 +130,7 @@ fun Vehicles( text = { Text("Logout") } ) } - }, - // scrollBehavior = scrollBehavior, + } ) } From 9fa26766b6b8a5179968fb511f5c9a0448d1400d Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 05:06:02 +0100 Subject: [PATCH 17/28] Update Motis api files --- src/lib/motis/index.ts | 2 +- src/lib/motis/schemas.gen.ts | 351 +++++++++++++++----------------- src/lib/motis/services.gen.ts | 14 +- src/lib/motis/types.gen.ts | 366 +++++++++++++++++----------------- 4 files changed, 360 insertions(+), 373 deletions(-) diff --git a/src/lib/motis/index.ts b/src/lib/motis/index.ts index 002afc33..0a2b84ba 100644 --- a/src/lib/motis/index.ts +++ b/src/lib/motis/index.ts @@ -1,4 +1,4 @@ // This file is auto-generated by @hey-api/openapi-ts export * from './schemas.gen'; export * from './services.gen'; -export * from './types.gen'; +export * from './types.gen'; \ No newline at end of file diff --git a/src/lib/motis/schemas.gen.ts b/src/lib/motis/schemas.gen.ts index 8d744eed..396ec2d8 100644 --- a/src/lib/motis/schemas.gen.ts +++ b/src/lib/motis/schemas.gen.ts @@ -15,13 +15,13 @@ export const DurationSchema = { export const AreaSchema = { description: 'Administrative area', type: 'object', - required: ['name', 'admin_level', 'matched'], + required: ['name', 'adminLevel', 'matched'], properties: { name: { type: 'string', description: 'Name of the area' }, - admin_level: { + adminLevel: { type: 'number', description: `[OpenStreetMap \`admin_level\`](https://wiki.openstreetmap.org/wiki/Key:admin_level) of the area @@ -51,7 +51,7 @@ export const TokenSchema = { export const MatchSchema = { description: 'GeoCoding match', type: 'object', - required: ['type', 'name', 'id', 'lat', 'lon', 'level', 'tokens', 'areas', 'score'], + required: ['type', 'name', 'id', 'lat', 'lon', 'tokens', 'areas', 'score'], properties: { type: { description: 'location type', @@ -91,7 +91,7 @@ export const MatchSchema = { description: 'street name', type: 'string' }, - house_number: { + houseNumber: { description: 'house number', type: 'string' }, @@ -142,7 +142,6 @@ export const ModeSchema = { - \`HIGHSPEED_RAIL\`: long distance high speed trains (e.g. TGV) - \`LONG_DISTANCE\`: long distance inter city trains - \`NIGHT_RAIL\`: long distance night trains - - \`COACH\`: long distance buses - \`REGIONAL_FAST_RAIL\`: regional express routes that skip low traffic stops to be faster - \`REGIONAL_RAIL\`: regional train `, @@ -150,88 +149,13 @@ export const ModeSchema = { enum: ['WALK', 'BIKE', 'CAR', 'BIKE_RENTAL', 'BIKE_TO_PARK', 'CAR_TO_PARK', 'CAR_HAILING', 'CAR_SHARING', 'CAR_PICKUP', 'CAR_RENTAL', 'FLEXIBLE', 'SCOOTER_RENTAL', 'TRANSIT', 'TRAM', 'SUBWAY', 'FERRY', 'AIRPLANE', 'METRO', 'BUS', 'COACH', 'RAIL', 'HIGHSPEED_RAIL', 'LONG_DISTANCE', 'NIGHT_RAIL', 'REGIONAL_FAST_RAIL', 'REGIONAL_RAIL', 'OTHER'] } as const; -export const StopTimeSchema = { - description: 'departure or arrival event at a stop', - type: 'object', - required: ['mode', 'time', 'delay', 'realTime', 'route', 'headsign', 'agencyId', 'agencyName', 'agencyUrl', 'routeColor', 'routeTextColor', 'routeType', 'routeId', 'tripId', 'serviceDate', 'routeShortName', 'source'], - properties: { - mode: { - '$ref': '#/components/schemas/Mode', - description: 'Transport mode for this leg' - }, - time: { - type: 'integer', - description: `The offset from the scheduled arrival time of the boarding stop in this leg. -Scheduled time of arrival at boarding stop = endTime - arrivalDelay -` - }, - delay: { - type: 'integer', - description: `The offset from the scheduled departure time of the boarding stop in this leg. -Scheduled time of departure at boarding stop = startTime - departureDelay -` - }, - realTime: { - description: 'Whether there is real-time data about this leg', - type: 'boolean' - }, - route: { - description: `For transit legs, the route of the bus or train being used. -For non-transit legs, the name of the street being traversed. -`, - type: 'string' - }, - headsign: { - description: `For transit legs, the headsign of the bus or train being used. -For non-transit legs, null -`, - type: 'string' - }, - agencyId: { - type: 'string' - }, - agencyName: { - type: 'string' - }, - agencyUrl: { - type: 'string' - }, - routeColor: { - type: 'string' - }, - routeTextColor: { - type: 'string' - }, - routeType: { - type: 'string' - }, - routeId: { - type: 'string' - }, - tripId: { - type: 'string' - }, - serviceDate: { - type: 'string' - }, - routeShortName: { - type: 'string' - }, - source: { - description: 'Filename and line number where this trip is from', - type: 'string' - } - } -} as const; - export const VertexTypeSchema = { type: 'string', description: `- \`NORMAL\` - latitude / longitude coordinate or address - \`BIKESHARE\` - bike sharing station -- \`BIKEPARK\` - bike parking - \`TRANSIT\` - transit stop `, - enum: ['NORMAL', 'BIKESHARE', 'BIKEPARK', 'TRANSIT'] + enum: ['NORMAL', 'BIKESHARE', 'TRANSIT'] } as const; export const PlaceSchema = { @@ -260,26 +184,34 @@ export const PlaceSchema = { }, arrivalDelay: { type: 'integer', - description: `The offset from the scheduled arrival time of the boarding stop in this leg. + description: `The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). Scheduled time of arrival at boarding stop = endTime - arrivalDelay ` }, departureDelay: { type: 'integer', - description: `The offset from the scheduled departure time of the boarding stop in this leg. + description: `The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). Scheduled time of departure at boarding stop = startTime - departureDelay ` }, arrival: { - description: 'arrival time, format = unixtime in milliseconds', - type: 'integer' + description: 'arrival time', + type: 'string', + format: 'date-time' }, departure: { - description: 'departure time, format = unixtime in milliseconds', - type: 'integer' + description: 'departure time', + type: 'string', + format: 'date-time' + }, + scheduledTrack: { + description: 'scheduled track from the static schedule timetable dataset', + type: 'string' }, track: { - description: 'track/platform information, if available', + description: `The current track/platform information, updated with real-time updates if available. +Can be missing if neither real-time updates nor the schedule timetable contains track information. +`, type: 'string' }, vertexType: { @@ -288,19 +220,66 @@ Scheduled time of departure at boarding stop = startTime - departureDelay } } as const; +export const StopTimeSchema = { + description: 'departure or arrival event at a stop', + type: 'object', + required: ['place', 'mode', 'realTime', 'headsign', 'agencyId', 'agencyName', 'agencyUrl', 'tripId', 'routeShortName', 'source'], + properties: { + place: { + '$ref': '#/components/schemas/Place', + description: 'information about the stop place and time' + }, + mode: { + '$ref': '#/components/schemas/Mode', + description: 'Transport mode for this leg' + }, + realTime: { + description: 'Whether there is real-time data about this leg', + type: 'boolean' + }, + headsign: { + description: `For transit legs, the headsign of the bus or train being used. +For non-transit legs, null +`, + type: 'string' + }, + agencyId: { + type: 'string' + }, + agencyName: { + type: 'string' + }, + agencyUrl: { + type: 'string' + }, + routeColor: { + type: 'string' + }, + routeTextColor: { + type: 'string' + }, + tripId: { + type: 'string' + }, + routeShortName: { + type: 'string' + }, + source: { + description: 'Filename and line number where this trip is from', + type: 'string' + } + } +} as const; + export const TripInfoSchema = { description: 'trip id and name', type: 'object', - required: ['tripId', 'serviceDate', 'routeShortName'], + required: ['tripId', 'routeShortName'], properties: { tripId: { description: 'trip ID (dataset trip id prefixed with the dataset tag)', type: 'string' }, - serviceDate: { - description: 'service date', - type: 'string' - }, routeShortName: { description: 'trip display name', type: 'string' @@ -311,7 +290,7 @@ export const TripInfoSchema = { export const TripSegmentSchema = { description: 'trip segment between two stops to show a trip on a map', type: 'object', - required: ['trips', 'routeColor', 'mode', 'distance', 'from', 'to', 'departure', 'arrival', 'departureDelay', 'arrivalDelay', 'realTime', 'polyline'], + required: ['trips', 'mode', 'distance', 'from', 'to', 'departure', 'arrival', 'departureDelay', 'arrivalDelay', 'realTime', 'polyline'], properties: { trips: { type: 'array', @@ -337,22 +316,24 @@ export const TripSegmentSchema = { '$ref': '#/components/schemas/Place' }, departure: { - description: 'departure time, format = unixtime in milliseconds', - type: 'integer' + description: 'departure time', + type: 'string', + format: 'date-time' }, arrival: { - description: 'arrival time, format = unixtime in milliseconds', - type: 'integer' + description: 'arrival time', + type: 'string', + format: 'date-time' }, departureDelay: { type: 'integer', - description: `The offset from the scheduled departure time of the boarding stop in this leg. + description: `The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). Scheduled time of departure at boarding stop = startTime - departureDelay ` }, arrivalDelay: { type: 'integer', - description: `The offset from the scheduled arrival time of the boarding stop in this leg. + description: `The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). Scheduled time of arrival at boarding stop = endTime - arrivalDelay ` }, @@ -361,99 +342,116 @@ Scheduled time of arrival at boarding stop = endTime - arrivalDelay type: 'boolean' }, polyline: { - description: 'Google polyline encoded coordinate sequence where the trip travels on this segment', + description: 'Google polyline encoded coordinate sequence (with precision 7) where the trip travels on this segment.', type: 'string' } } } as const; -export const RelativeDirectionSchema = { +export const DirectionSchema = { type: 'string', - enum: ['DEPART', 'HARD_LEFT', 'LEFT', 'SLIGHTLY_LEFT', 'CONTINUE', 'SLIGHTLY_RIGHT', 'RIGHT', 'HARD_RIGHT', 'CIRCLE_CLOCKWISE', 'CIRCLE_COUNTERCLOCKWISE', 'ELEVATOR', 'UTURN_LEFT', 'UTURN_RIGHT'] + enum: ['DEPART', 'HARD_LEFT', 'LEFT', 'SLIGHTLY_LEFT', 'CONTINUE', 'SLIGHTLY_RIGHT', 'RIGHT', 'HARD_RIGHT', 'CIRCLE_CLOCKWISE', 'CIRCLE_COUNTERCLOCKWISE', 'STAIRS', 'ELEVATOR', 'UTURN_LEFT', 'UTURN_RIGHT'] } as const; -export const AbsoluteDirectionSchema = { - type: 'string', - enum: ['NORTH', 'NORTHEAST', 'EAST', 'SOUTHEAST', 'SOUTH', 'SOUTHWEST', 'WEST', 'NORTHWEST'] +export const EncodedPolylineSchema = { + type: 'object', + required: ['points', 'length'], + properties: { + points: { + description: 'The encoded points of the polyline using the Google polyline encoding with precision 7.', + type: 'string' + }, + length: { + description: 'The number of points in the string', + type: 'integer' + } + } } as const; export const StepInstructionSchema = { type: 'object', - required: ['relativeDirection', 'absoluteDirection', 'distance', 'streetName', 'exit', 'stayOn', 'area', 'lon', 'lat'], + required: ['fromLevel', 'toLevel', 'polyline', 'relativeDirection', 'distance', 'streetName', 'exit', 'stayOn', 'area', 'lon', 'lat'], properties: { relativeDirection: { - '$ref': '#/components/schemas/RelativeDirection' - }, - absoluteDirection: { - '$ref': '#/components/schemas/AbsoluteDirection' + '$ref': '#/components/schemas/Direction' }, distance: { description: 'The distance in meters that this step takes.', type: 'number' }, + fromLevel: { + description: 'level where this segment starts, based on OpenStreetMap data', + type: 'number' + }, + toLevel: { + description: 'level where this segment starts, based on OpenStreetMap data', + type: 'number' + }, + osmWay: { + description: 'OpenStreetMap way index', + type: 'integer' + }, + polyline: { + '$ref': '#/components/schemas/EncodedPolyline' + }, streetName: { description: 'The name of the street.', type: 'string' }, exit: { - description: 'When exiting a highway or traffic circle, the exit name/number.', + description: `Not implemented! +When exiting a highway or traffic circle, the exit name/number. +`, type: 'string' }, stayOn: { - description: `Indicates whether or not a street changes direction at an intersection. + description: `Not implemented! +Indicates whether or not a street changes direction at an intersection. `, type: 'boolean' }, area: { - description: `This step is on an open area, such as a plaza or train platform, + description: `Not implemented! +This step is on an open area, such as a plaza or train platform, and thus the directions should say something like "cross" `, type: 'boolean' - }, - lon: { - description: 'The longitude of start of the step', - type: 'number' - }, - lat: { - description: 'The latitude of start of the step', - type: 'number' } } } as const; -export const EncodedPolylineSchema = { +export const RentalSchema = { + description: 'Vehicle rental', type: 'object', - required: ['points', 'length'], + required: ['systemId'], properties: { - points: { - description: 'The encoded points of the polyline.', - type: 'string' + systemId: { + type: 'string', + description: 'Vehicle share system ID' }, - length: { - description: 'The number of points in the string', - type: 'integer' - } - } -} as const; - -export const LevelEncodedPolylineSchema = { - type: 'object', - required: ['from_level', 'to_level', 'polyline'], - properties: { - from_level: { - description: 'level where this segment starts, based on OpenStreetMap data', - type: 'number' + systemName: { + type: 'string', + description: 'Vehicle share system name' }, - to_level: { - description: 'level where this segment starts, based on OpenStreetMap data', - type: 'number' + url: { + type: 'string', + description: 'URL of the vehicle share system' }, - osm_way: { - description: 'OpenStreetMap way index', - type: 'integer' + stationName: { + type: 'string', + description: 'Name of the station' }, - polyline: { - '$ref': '#/components/schemas/EncodedPolyline' + rentalUriAndroid: { + type: 'string', + description: 'Rental URI for Android (deep link to the specific station or vehicle)' + }, + rentalUriIOS: { + type: 'string', + description: 'Rental URI for iOS (deep link to the specific station or vehicle)' + }, + rentalUriWeb: { + type: 'string', + description: 'Rental URI for web (deep link to the specific station or vehicle)' } } } as const; @@ -477,22 +475,24 @@ export const LegSchema = { type: 'integer' }, startTime: { - type: 'integer', - description: 'leg departure time, format = unixtime in milliseconds' + type: 'string', + format: 'date-time', + description: 'leg departure time' }, endTime: { - type: 'integer', - description: 'leg arrival time, format = unixtime in milliseconds' + type: 'string', + format: 'date-time', + description: 'leg arrival time' }, departureDelay: { type: 'integer', - description: `The offset from the scheduled departure time of the boarding stop in this leg. + description: `The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). Scheduled time of departure at boarding stop = startTime - departureDelay ` }, arrivalDelay: { type: 'integer', - description: `The offset from the scheduled arrival time of the boarding stop in this leg. + description: `The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). Scheduled time of arrival at boarding stop = endTime - arrivalDelay ` }, @@ -544,9 +544,6 @@ For non-transit legs, null tripId: { type: 'string' }, - serviceDate: { - type: 'string' - }, routeShortName: { type: 'string' }, @@ -566,13 +563,6 @@ and the Place where the leg ends. For non-transit legs, null. legGeometry: { '$ref': '#/components/schemas/EncodedPolyline' }, - legGeometryWithLevels: { - description: 'Like `legGeometry`, but split at level changes', - type: 'array', - items: { - '$ref': '#/components/schemas/LevelEncodedPolyline' - } - }, steps: { description: `A series of turn by turn instructions used for walking, biking and driving. @@ -581,41 +571,30 @@ used for walking, biking and driving. items: { '$ref': '#/components/schemas/StepInstruction' } + }, + rental: { + '$ref': '#/components/schemas/Rental' } } } as const; export const ItinerarySchema = { type: 'object', - required: ['duration', 'startTime', 'endTime', 'walkTime', 'transitTime', 'waitingTime', 'walkDistance', 'transfers', 'legs'], + required: ['duration', 'startTime', 'endTime', 'transfers', 'legs'], properties: { duration: { description: 'journey duration in seconds', type: 'integer' }, startTime: { - type: 'integer', - description: 'journey departure time, format = unixtime in milliseconds' + type: 'string', + format: 'date-time', + description: 'journey departure time' }, endTime: { - type: 'integer', - description: 'journey arrival time, format = unixtime in milliseconds' - }, - walkTime: { - type: 'integer', - description: 'How much time is spent walking, in seconds.' - }, - transitTime: { - type: 'integer', - description: 'How much time is spent on transit, in seconds.' - }, - waitingTime: { - type: 'integer', - description: 'How much time is spent waiting for transit to arrive, in seconds.' - }, - walkDistance: { - type: 'integer', - description: 'How far the user has to walk, in meters.' + type: 'string', + format: 'date-time', + description: 'journey arrival time' }, transfers: { type: 'integer', diff --git a/src/lib/motis/services.gen.ts b/src/lib/motis/services.gen.ts index 8de6f499..51b2011a 100644 --- a/src/lib/motis/services.gen.ts +++ b/src/lib/motis/services.gen.ts @@ -1,7 +1,7 @@ // This file is auto-generated by @hey-api/openapi-ts import { createClient, createConfig, type Options } from '@hey-api/client-fetch'; -import type { OneToManyData, OneToManyError, OneToManyResponse, ReverseGeocodeData, ReverseGeocodeError, ReverseGeocodeResponse, GeocodeData, GeocodeError, GeocodeResponse, TripData, TripError, TripResponse, StoptimesData, StoptimesError, StoptimesResponse, PlanData, PlanError, PlanResponse, RailvizData, RailvizError, RailvizResponse, InitialError, InitialResponse, LevelsData, LevelsError, LevelsResponse, FootpathsData, FootpathsError, FootpathsResponse } from './types.gen'; +import type { OneToManyData, OneToManyError, OneToManyResponse, ReverseGeocodeData, ReverseGeocodeError, ReverseGeocodeResponse, GeocodeData, GeocodeError, GeocodeResponse, TripData, TripError, TripResponse, StoptimesData, StoptimesError, StoptimesResponse, PlanData, PlanError, PlanResponse, TripsData, TripsError, TripsResponse, InitialError, InitialResponse, StopsData, StopsError, StopsResponse, LevelsData, LevelsError, LevelsResponse, FootpathsData, FootpathsError, FootpathsResponse } from './types.gen'; export const client = createClient(createConfig()); @@ -62,9 +62,9 @@ export const plan = (options: Options(options: Options) => { return (options?.client ?? client).get({ +export const trips = (options: Options) => { return (options?.client ?? client).get({ ...options, - url: '/api/v1/railviz' + url: '/api/v1/map/trips' }); }; /** @@ -75,6 +75,14 @@ export const initial = (options?: Options< url: '/api/v1/map/initial' }); }; +/** + * Get all stops for a map section + */ +export const stops = (options: Options) => { return (options?.client ?? client).get({ + ...options, + url: '/api/v1/map/stops' +}); }; + /** * Get all available levels for a map section */ diff --git a/src/lib/motis/types.gen.ts b/src/lib/motis/types.gen.ts index 2ecf658e..21f73ec7 100644 --- a/src/lib/motis/types.gen.ts +++ b/src/lib/motis/types.gen.ts @@ -23,7 +23,7 @@ export type Area = { * of the area * */ - admin_level: number; + adminLevel: number; /** * Whether this area was matched by the input text */ @@ -75,7 +75,7 @@ export type Match = { * (at the moment only for public transport) * */ - level: number; + level?: number; /** * street name */ @@ -83,7 +83,7 @@ export type Match = { /** * house number */ - house_number?: string; + houseNumber?: string; /** * zip code */ @@ -132,73 +132,19 @@ export type type = 'ADDRESS' | 'PLACE' | 'STOP'; * - `HIGHSPEED_RAIL`: long distance high speed trains (e.g. TGV) * - `LONG_DISTANCE`: long distance inter city trains * - `NIGHT_RAIL`: long distance night trains - * - `COACH`: long distance buses * - `REGIONAL_FAST_RAIL`: regional express routes that skip low traffic stops to be faster * - `REGIONAL_RAIL`: regional train * */ export type Mode = 'WALK' | 'BIKE' | 'CAR' | 'BIKE_RENTAL' | 'BIKE_TO_PARK' | 'CAR_TO_PARK' | 'CAR_HAILING' | 'CAR_SHARING' | 'CAR_PICKUP' | 'CAR_RENTAL' | 'FLEXIBLE' | 'SCOOTER_RENTAL' | 'TRANSIT' | 'TRAM' | 'SUBWAY' | 'FERRY' | 'AIRPLANE' | 'METRO' | 'BUS' | 'COACH' | 'RAIL' | 'HIGHSPEED_RAIL' | 'LONG_DISTANCE' | 'NIGHT_RAIL' | 'REGIONAL_FAST_RAIL' | 'REGIONAL_RAIL' | 'OTHER'; -/** - * departure or arrival event at a stop - */ -export type StopTime = { - /** - * Transport mode for this leg - */ - mode: Mode; - /** - * The offset from the scheduled arrival time of the boarding stop in this leg. - * Scheduled time of arrival at boarding stop = endTime - arrivalDelay - * - */ - time: number; - /** - * The offset from the scheduled departure time of the boarding stop in this leg. - * Scheduled time of departure at boarding stop = startTime - departureDelay - * - */ - delay: number; - /** - * Whether there is real-time data about this leg - */ - realTime: boolean; - /** - * For transit legs, the route of the bus or train being used. - * For non-transit legs, the name of the street being traversed. - * - */ - route: string; - /** - * For transit legs, the headsign of the bus or train being used. - * For non-transit legs, null - * - */ - headsign: string; - agencyId: string; - agencyName: string; - agencyUrl: string; - routeColor: string; - routeTextColor: string; - routeType: string; - routeId: string; - tripId: string; - serviceDate: string; - routeShortName: string; - /** - * Filename and line number where this trip is from - */ - source: string; -}; - /** * - `NORMAL` - latitude / longitude coordinate or address * - `BIKESHARE` - bike sharing station - * - `BIKEPARK` - bike parking * - `TRANSIT` - transit stop * */ -export type VertexType = 'NORMAL' | 'BIKESHARE' | 'BIKEPARK' | 'TRANSIT'; +export type VertexType = 'NORMAL' | 'BIKESHARE' | 'TRANSIT'; export type Place = { /** @@ -222,32 +168,73 @@ export type Place = { */ level: number; /** - * The offset from the scheduled arrival time of the boarding stop in this leg. + * The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). * Scheduled time of arrival at boarding stop = endTime - arrivalDelay * */ arrivalDelay?: number; /** - * The offset from the scheduled departure time of the boarding stop in this leg. + * The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). * Scheduled time of departure at boarding stop = startTime - departureDelay * */ departureDelay?: number; /** - * arrival time, format = unixtime in milliseconds + * arrival time */ - arrival?: number; + arrival?: string; /** - * departure time, format = unixtime in milliseconds + * departure time */ - departure?: number; + departure?: string; /** - * track/platform information, if available + * scheduled track from the static schedule timetable dataset + */ + scheduledTrack?: string; + /** + * The current track/platform information, updated with real-time updates if available. + * Can be missing if neither real-time updates nor the schedule timetable contains track information. + * */ track?: string; vertexType?: VertexType; }; +/** + * departure or arrival event at a stop + */ +export type StopTime = { + /** + * information about the stop place and time + */ + place: Place; + /** + * Transport mode for this leg + */ + mode: Mode; + /** + * Whether there is real-time data about this leg + */ + realTime: boolean; + /** + * For transit legs, the headsign of the bus or train being used. + * For non-transit legs, null + * + */ + headsign: string; + agencyId: string; + agencyName: string; + agencyUrl: string; + routeColor?: string; + routeTextColor?: string; + tripId: string; + routeShortName: string; + /** + * Filename and line number where this trip is from + */ + source: string; +}; + /** * trip id and name */ @@ -256,10 +243,6 @@ export type TripInfo = { * trip ID (dataset trip id prefixed with the dataset tag) */ tripId: string; - /** - * service date - */ - serviceDate: string; /** * trip display name */ @@ -271,7 +254,7 @@ export type TripInfo = { */ export type TripSegment = { trips: Array; - routeColor: string; + routeColor?: string; /** * Transport mode for this leg */ @@ -283,21 +266,21 @@ export type TripSegment = { from: Place; to: Place; /** - * departure time, format = unixtime in milliseconds + * departure time */ - departure: number; + departure: string; /** - * arrival time, format = unixtime in milliseconds + * arrival time */ - arrival: number; + arrival: string; /** - * The offset from the scheduled departure time of the boarding stop in this leg. + * The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). * Scheduled time of departure at boarding stop = startTime - departureDelay * */ departureDelay: number; /** - * The offset from the scheduled arrival time of the boarding stop in this leg. + * The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). * Scheduled time of arrival at boarding stop = endTime - arrivalDelay * */ @@ -307,76 +290,100 @@ export type TripSegment = { */ realTime: boolean; /** - * Google polyline encoded coordinate sequence where the trip travels on this segment + * Google polyline encoded coordinate sequence (with precision 7) where the trip travels on this segment. */ polyline: string; }; -export type RelativeDirection = 'DEPART' | 'HARD_LEFT' | 'LEFT' | 'SLIGHTLY_LEFT' | 'CONTINUE' | 'SLIGHTLY_RIGHT' | 'RIGHT' | 'HARD_RIGHT' | 'CIRCLE_CLOCKWISE' | 'CIRCLE_COUNTERCLOCKWISE' | 'ELEVATOR' | 'UTURN_LEFT' | 'UTURN_RIGHT'; +export type Direction = 'DEPART' | 'HARD_LEFT' | 'LEFT' | 'SLIGHTLY_LEFT' | 'CONTINUE' | 'SLIGHTLY_RIGHT' | 'RIGHT' | 'HARD_RIGHT' | 'CIRCLE_CLOCKWISE' | 'CIRCLE_COUNTERCLOCKWISE' | 'STAIRS' | 'ELEVATOR' | 'UTURN_LEFT' | 'UTURN_RIGHT'; -export type AbsoluteDirection = 'NORTH' | 'NORTHEAST' | 'EAST' | 'SOUTHEAST' | 'SOUTH' | 'SOUTHWEST' | 'WEST' | 'NORTHWEST'; +export type EncodedPolyline = { + /** + * The encoded points of the polyline using the Google polyline encoding with precision 7. + */ + points: string; + /** + * The number of points in the string + */ + length: number; +}; export type StepInstruction = { - relativeDirection: RelativeDirection; - absoluteDirection: AbsoluteDirection; + relativeDirection: Direction; /** * The distance in meters that this step takes. */ distance: number; + /** + * level where this segment starts, based on OpenStreetMap data + */ + fromLevel: number; + /** + * level where this segment starts, based on OpenStreetMap data + */ + toLevel: number; + /** + * OpenStreetMap way index + */ + osmWay?: number; + polyline: EncodedPolyline; /** * The name of the street. */ streetName: string; /** + * Not implemented! * When exiting a highway or traffic circle, the exit name/number. + * */ exit: string; /** + * Not implemented! * Indicates whether or not a street changes direction at an intersection. * */ stayOn: boolean; /** + * Not implemented! * This step is on an open area, such as a plaza or train platform, * and thus the directions should say something like "cross" * */ area: boolean; +}; + +/** + * Vehicle rental + */ +export type Rental = { /** - * The longitude of start of the step + * Vehicle share system ID */ - lon: number; + systemId: string; /** - * The latitude of start of the step + * Vehicle share system name */ - lat: number; -}; - -export type EncodedPolyline = { + systemName?: string; /** - * The encoded points of the polyline. + * URL of the vehicle share system */ - points: string; + url?: string; /** - * The number of points in the string + * Name of the station */ - length: number; -}; - -export type LevelEncodedPolyline = { + stationName?: string; /** - * level where this segment starts, based on OpenStreetMap data + * Rental URI for Android (deep link to the specific station or vehicle) */ - from_level: number; + rentalUriAndroid?: string; /** - * level where this segment starts, based on OpenStreetMap data + * Rental URI for iOS (deep link to the specific station or vehicle) */ - to_level: number; + rentalUriIOS?: string; /** - * OpenStreetMap way index + * Rental URI for web (deep link to the specific station or vehicle) */ - osm_way?: number; - polyline: EncodedPolyline; + rentalUriWeb?: string; }; export type Leg = { @@ -391,21 +398,21 @@ export type Leg = { */ duration: number; /** - * leg departure time, format = unixtime in milliseconds + * leg departure time */ - startTime: number; + startTime: string; /** - * leg arrival time, format = unixtime in milliseconds + * leg arrival time */ - endTime: number; + endTime: string; /** - * The offset from the scheduled departure time of the boarding stop in this leg. + * The offset from the scheduled departure time of the boarding stop in this leg (in milliseconds). * Scheduled time of departure at boarding stop = startTime - departureDelay * */ departureDelay: number; /** - * The offset from the scheduled arrival time of the boarding stop in this leg. + * The offset from the scheduled arrival time of the boarding stop in this leg (in milliseconds). * Scheduled time of arrival at boarding stop = endTime - arrivalDelay * */ @@ -442,7 +449,6 @@ export type Leg = { routeId?: string; agencyId?: string; tripId?: string; - serviceDate?: string; routeShortName?: string; /** * Filename and line number where this trip is from @@ -455,16 +461,13 @@ export type Leg = { */ intermediateStops?: Array; legGeometry: EncodedPolyline; - /** - * Like `legGeometry`, but split at level changes - */ - legGeometryWithLevels?: Array; /** * A series of turn by turn instructions * used for walking, biking and driving. * */ steps?: Array; + rental?: Rental; }; export type Itinerary = { @@ -473,29 +476,13 @@ export type Itinerary = { */ duration: number; /** - * journey departure time, format = unixtime in milliseconds + * journey departure time */ - startTime: number; + startTime: string; /** - * journey arrival time, format = unixtime in milliseconds + * journey arrival time */ - endTime: number; - /** - * How much time is spent walking, in seconds. - */ - walkTime: number; - /** - * How much time is spent on transit, in seconds. - */ - transitTime: number; - /** - * How much time is spent waiting for transit to arrive, in seconds. - */ - waitingTime: number; - /** - * How far the user has to walk, in meters. - */ - walkDistance: number; + endTime: string; /** * The number of transfers this trip has. */ @@ -607,19 +594,6 @@ export type GeocodeError = unknown; export type TripData = { query: { - /** - * Service date as specified in the source dataset. - * Can be taken from an itinerary leg or stop event. - * - * Not that for GTFS the first departure time can be greater than 24:00:00 - * which means that the service date is shifted by the offset (first departure / 24h). - * A valid use case for this are stay seated transfers expressed by `block_id`. - * - * Example: a train with first departure at 25:00:00 on 9th of Oct 2024 - * has the 8th of Oct 2024 as service date. - * - */ - date: string; /** * trip identifier (e.g. from an itinerary leg or stop event) */ @@ -641,13 +615,6 @@ export type StoptimesData = { * */ arriveBy?: boolean; - /** - * Optional. Defaults to the current date. - * - * Departure date ($arriveBy=false) / arrival date ($arriveBy=true), format: 06-28-2024 - * - */ - date?: string; /** * the number of events */ @@ -659,6 +626,17 @@ export type StoptimesData = { * */ pageCursor?: string; + /** + * Optional. Radius in meters. + * + * Default is that only stop times of the parent of the stop itself + * and all stops with the same name (+ their child stops) are returned. + * + * If set, all stops at parent stations and their child stops in the specified radius + * are returned. + * + */ + radius?: number; /** * stop id of the stop to retrieve departures/arrivals for */ @@ -666,10 +644,6 @@ export type StoptimesData = { /** * Optional. Defaults to the current time. * - * Format: - * - 12h format: 7:06pm - * - 24h format: 19:06 - * */ time?: string; }; @@ -706,17 +680,16 @@ export type PlanData = { * */ arriveBy?: boolean; - /** - * Optional. Defaults to the current date. - * - * Departure date ($arriveBy=false) / arrival date ($arriveBy=true), format: 06-28-2024 - * - */ - date?: string; /** * \`latitude,longitude,level\` tuple in degrees OR stop id */ fromPlace: string; + /** + * Optional. Default is 30min which is `1800`. + * Maximum time in seconds for direct connections. + * + */ + maxDirectTime?: number; /** * The maximum travel time in hours. * If not provided, the routing to uses the value @@ -727,6 +700,8 @@ export type PlanData = { * If this value is too low to reach the destination at all, * it can lead to slow routing performance. * + * TODO: pass parameter to nigiri + * */ maxHours?: number; /** @@ -755,6 +730,8 @@ export type PlanData = { maxTransfers?: number; /** * Minimum transfer time for each transfer. + * TODO: pass parameter to nigiri + * */ minTransferTime?: number; /** @@ -778,6 +755,13 @@ export type PlanData = { * */ pageCursor?: string; + /** + * Optional. Default is `false`. + * + * If set to `true`, all used transit trips are required to allow bike carriage. + * + */ + requireBikeTransport?: boolean; /** * Optional. Default is 2 hours which is `7200`. * @@ -791,13 +775,7 @@ export type PlanData = { /** * Optional. Defaults to the current time. * - * Meaning depending on `arriveBy` - * - Departure time for `arriveBy=false` - * - Arrival time for `arriveBy=true` - * - * Format: - * - 12h format: 7:06pm - * - 24h format: 19:06 + * Departure time ($arriveBy=false) / arrival date ($arriveBy=true), * */ time?: string; @@ -828,6 +806,8 @@ export type PlanData = { toPlace: string; /** * Factor to multiply transfer times with. + * TODO: pass parameter to nigiri + * */ transferTimeFactor?: number; /** @@ -848,14 +828,17 @@ export type PlanResponse = ({ * debug statistics */ debugOutput: { - [key: string]: (string); + [key: string]: (number); }; - /** - * The time and date of travel - */ - date: number; from: Place; to: Place; + /** + * Direct trips by `WALK`, `BIKE`, `CAR`, etc. without time-dependency. + * The starting time (`arriveBy=false`) / arrival time (`arriveBy=true`) is always the queried `time` parameter (set to \"now\" if not set). + * But all `direct` connections are meant to be independent of absolute times. + * + */ + direct: Array; /** * list of itineraries */ @@ -876,12 +859,12 @@ export type PlanResponse = ({ export type PlanError = unknown; -export type RailvizData = { +export type TripsData = { query: { /** - * end if the time window (unix timestamp in milliseconds) + * end if the time window */ - endTime: number; + endTime: string; /** * latitude,longitude pair of the upper left coordinate */ @@ -891,9 +874,9 @@ export type RailvizData = { */ min: string; /** - * start of the time window (unix timestamp in milliseconds) + * start of the time window */ - startTime: number; + startTime: string; /** * current zoom level */ @@ -901,9 +884,9 @@ export type RailvizData = { }; }; -export type RailvizResponse = (Array); +export type TripsResponse = (Array); -export type RailvizError = unknown; +export type TripsError = unknown; export type InitialResponse = ({ /** @@ -922,6 +905,23 @@ export type InitialResponse = ({ export type InitialError = unknown; +export type StopsData = { + query: { + /** + * latitude,longitude pair of the upper left coordinate + */ + max: string; + /** + * latitude,longitude pair of the lower right coordinate + */ + min: string; + }; +}; + +export type StopsResponse = (Array); + +export type StopsError = unknown; + export type LevelsData = { query: { /** From 1952445ef8896c5d5df43458ad06a0db57898585 Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 05:06:48 +0100 Subject: [PATCH 18/28] Remove fare computation --- src/routes/api/booking/+server.ts | 19 -- .../api/booking/fare-estimation/bautzen.json | 24 -- .../fare-estimation/fare_estimation.ts | 229 ------------------ .../api/booking/fare-estimation/goerlitz.json | 35 --- .../api/booking/fare-estimation/rates.ts | 83 ------- 5 files changed, 390 deletions(-) delete mode 100644 src/routes/api/booking/fare-estimation/bautzen.json delete mode 100644 src/routes/api/booking/fare-estimation/fare_estimation.ts delete mode 100644 src/routes/api/booking/fare-estimation/goerlitz.json delete mode 100644 src/routes/api/booking/fare-estimation/rates.ts diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index a32a4dd1..3a68a9c7 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -6,7 +6,6 @@ import { error, json } from '@sveltejs/kit'; import { hoursToMs, minutesToMs, secondsToMs } from '$lib/time_utils.js'; import { MAX_TRAVEL_DURATION, MIN_PREP_MINUTES, MOTIS_BASE_URL } from '$lib/constants.js'; import { sql } from 'kysely'; -import { getFareEstimation } from './fare-estimation/fare_estimation.js'; import { covers } from '$lib/sqlHelpers.js'; import { oneToMany, type Duration } from '$lib/motis'; import { coordinatesToStr } from '$lib/motisUtils.js'; @@ -478,24 +477,6 @@ export const POST = async (event) => { .execute(); }); if (tourId) { - try { - const fare_route = await getFareEstimation( - { - longitude: fromCoordinates.lng, - latitude: fromCoordinates.lat, - scheduled_time: startTime - }, - { - longitude: toCoordinates.lng, - latitude: toCoordinates.lat, - scheduled_time: null - }, - bestVehicle!.vehicleId - ); - await db.updateTable('tour').set({ fare_route }).where('id', '=', tourId).executeTakeFirst(); - } catch (e) { - console.log(e); - } return json({ status: 0, companyId: bestVehicle!.companyId!, diff --git a/src/routes/api/booking/fare-estimation/bautzen.json b/src/routes/api/booking/fare-estimation/bautzen.json deleted file mode 100644 index 22174601..00000000 --- a/src/routes/api/booking/fare-estimation/bautzen.json +++ /dev/null @@ -1,24 +0,0 @@ -{ - "anfahrt": { - "grundpreis": 450, - "pkm": [[0, 130]], - "pauschal": [], - "returnFree": true - }, - "tag": { - "grundpreis": 450, - "pkm": [[0, 250]], - "pauschal": [] - }, - "nacht": { - "grundpreis": 450, - "pkm": [[0, 270]], - "pauschal": [] - }, - "zuschlag": { - "grossraum": 700 - }, - "wartezeitPh": 4500, - "beginnNacht": 22, - "endeNacht": 6 -} diff --git a/src/routes/api/booking/fare-estimation/fare_estimation.ts b/src/routes/api/booking/fare-estimation/fare_estimation.ts deleted file mode 100644 index dbd50955..00000000 --- a/src/routes/api/booking/fare-estimation/fare_estimation.ts +++ /dev/null @@ -1,229 +0,0 @@ -import { getRoute } from '$lib/api'; -import { TZ } from '$lib/constants'; -import { db } from '$lib/database'; -import { sql } from 'kysely'; -import type { Rate, RateInfo } from './rates'; -import { rateInfo } from './rates'; - -type SimpleEvent = { - latitude: number; - longitude: number; - scheduled_time: Date | null; -}; - -type Leg = { - start: SimpleEvent; - destination: SimpleEvent; -}; - -type Segment = { - dist: number; - rate: number; - flat: boolean; -}; - -type Rates = { - base: number; - steps: number[][]; -}; - -const getRouteSegment = async (leg: Leg) => { - return await getRoute({ - start: { - lat: leg.start.latitude, - lng: leg.start.longitude - }, - destination: { - lat: leg.destination.latitude, - lng: leg.destination.longitude - }, - profile: 'car', - direction: 'forward' - }); -}; - -const isWithinNightTime = (isoTimestampUTC: string, startHour: number, endHour: number) => { - const timestamp = new Date(isoTimestampUTC); // GMT + 0 on server - const localDateTime = new Date(timestamp.toLocaleString('en', { timeZone: TZ })); - return localDateTime.getHours() >= startHour || localDateTime.getHours() < endHour; -}; - -/* eslint-disable-next-line */ -const getRates = (rate: Rate): Rates => { - let steps = [[0, 0]]; - let base = 0; - if (rate.pKm.length > 0) { - // rate per km - base = rate.grundpreis; - steps = rate.pKm; - } else if (rate.pauschal.length > 0) { - // pauschale - steps = rate.pauschal; - } - return { base: base, steps: steps }; -}; - -const getSegments = async (rates: Rates, leg: Leg): Promise => { - const segments: Array = []; - const route_leg = await getRouteSegment(leg); - let dist = Math.floor(route_leg.metadata.distance); - if (rates.base === 0) { - // pauschal - let rate = rates.steps[0][1]; - for (let i = 1; i <= rates.steps.length - 1; ++i) { - if (rates.steps[i][0] < dist) { - rate = rates.steps[i][1]; - } - } - segments.push({ dist: dist, rate: rate, flat: true }); - } else { - // segmenting leg - if (rates.steps.length === 1) { - // constant rate - segments.push({ dist: dist, rate: rates.steps[0][1], flat: false }); - } else { - for (let i = 0; i < rates.steps.length - 1; ++i) { - const rate = rates.steps[i][1]; - let diff = rates.steps[i + 1][0] - rates.steps[i][0]; - if (dist - diff < 0) { - diff = dist; - } - dist -= diff; - segments.push({ dist: diff, rate: rate, flat: false }); - if (dist === 0) { - break; - } - } - if (dist != 0) { - segments.push({ dist: dist, rate: rates.steps[rates.steps.length - 1][1], flat: false }); - } - } - } - return segments; -}; - -export const getFareEstimation = async ( - start: SimpleEvent, - destination: SimpleEvent, - vehicleId: number -): Promise => { - const vehicle = await db - .selectFrom('vehicle') - .where('vehicle.id', '=', vehicleId) - .innerJoin('company', 'company.id', 'vehicle.company') - .select(['community_area', 'zone', 'latitude', 'longitude']) - .executeTakeFirst(); - - if (vehicle == null) { - throw new Error('Invalid vehicle ID'); - } - if (vehicle.latitude == null || vehicle.longitude == null) { - throw new Error('Cannot get company coordinates for vehicle'); - } - if (vehicle.community_area == null) { - throw new Error('Cannot get community ID for vehicle'); - } - if (vehicle.zone == null) { - throw new Error('Cannot get zone ID for vehicle'); - } - if (start.scheduled_time == null) { - throw new Error('No start time was defned'); - } - - const companyLatitude = vehicle.latitude; - const companyLongitude = vehicle.longitude; - const communityId = vehicle.community_area; - const zoneId = vehicle.zone; - let totalFare = 0; - - console.log('Betriebssitzgemeinde =', communityId); - console.log('Pflichtfahrgebiet =', zoneId); - - const zoneRates = await db - .selectFrom('zone') - .where('zone.id', '=', zoneId) - .select('rates') - .executeTakeFirst(); - if (!zoneRates) { - throw new Error('Cannot get taxi rates for vehicle'); - } - - const startIsInCommunity = - (await db - .selectFrom('zone') - .where('id', '=', communityId) - .where( - sql`ST_Covers(zone.area, ST_SetSRID(ST_MakePoint(${start.longitude}, ${start.latitude}),4326))` - ) - .selectAll() - .executeTakeFirst()) !== undefined; - - const dstCommunity = await db - .selectFrom('zone') - .where('id', '=', communityId) - .where( - sql`ST_Covers(zone.area, ST_SetSRID(ST_MakePoint(${destination.longitude}, ${destination.latitude}),4326))` - ) - .selectAll() - .executeTakeFirst(); - - let segments: Array = []; - const rates: RateInfo = rateInfo[zoneRates.rates]; - const returnFree = dstCommunity != null && rates.returnFree; - - if (!startIsInCommunity && !returnFree) { - const leg = { - start: { - latitude: companyLatitude, - longitude: companyLongitude, - scheduled_time: null - }, - destination: { - latitude: start.latitude, - longitude: start.longitude, - scheduled_time: null - } - }; - const segments_ = await getSegments(getRates(rates.anfahrt), leg); - segments = segments.concat(segments_); - console.log('Anfahrt:', segments_); - } - - if (isWithinNightTime(start.scheduled_time.toISOString(), rates.beginnNacht, rates.endeNacht)) { - // nighttime rate - totalFare += rates.nacht.grundpreis; - const leg = { - start: start, - destination: destination - }; - const segments_ = await getSegments(getRates(rates.nacht), leg); - segments = segments.concat(segments_); - console.log('Nacht-Tarif:', segments_); - } else { - // daytime rate - totalFare += rates.tag.grundpreis; - const leg = { - start: start, - destination: destination - }; - const segments_ = await getSegments(getRates(rates.tag), leg); - segments = segments.concat(segments_); - console.log('Tag-Tarif:', segments_); - } - - let totalDist = 0; - segments.forEach((e) => { - totalDist += e.dist; - if (e.flat) { - totalFare += e.rate; - } else { - totalFare += e.dist * e.rate; - } - }); - console.log('Distanz =', totalDist); - - totalFare = Math.round(totalFare / 1000); - console.log('Fahrpreis =', totalFare); - - return totalFare; -}; diff --git a/src/routes/api/booking/fare-estimation/goerlitz.json b/src/routes/api/booking/fare-estimation/goerlitz.json deleted file mode 100644 index 65736dc7..00000000 --- a/src/routes/api/booking/fare-estimation/goerlitz.json +++ /dev/null @@ -1,35 +0,0 @@ -{ - "anfahrt": { - "grundpreis": 0, - "pkm": [], - "pauschal": [ - [0, 1000], - [10000, 2000] - ], - "returnFree": true - }, - "tag": { - "grundpreis": 450, - "pkm": [ - [0, 350], - [3000, 210], - [11000, 210] - ], - "pauschal": [] - }, - "nacht": { - "grundpreis": 550, - "pkm": [ - [0, 360], - [3000, 220], - [11000, 220] - ], - "pauschal": [] - }, - "zuschlag": { - "grossraum": 900 - }, - "wartezeitPh": 3500, - "beginnNacht": 21, - "endeNacht": 5 -} diff --git a/src/routes/api/booking/fare-estimation/rates.ts b/src/routes/api/booking/fare-estimation/rates.ts deleted file mode 100644 index db9ad774..00000000 --- a/src/routes/api/booking/fare-estimation/rates.ts +++ /dev/null @@ -1,83 +0,0 @@ -export type RateInfo = { - anfahrt: Rate; - tag: Rate; - nacht: Rate; - returnFree: boolean; - zuschlag: Zuschlag; - wartzeitPStd: number; - beginnNacht: number; - endeNacht: number; -}; - -export type Rate = { - grundpreis: number; - pKm: Array<[number, number]>; - pauschal: Array<[number, number]>; -}; - -export type Zuschlag = { - grossraum: number; -}; - -const ratesGoerlitz: RateInfo = { - anfahrt: { - grundpreis: 0, - pKm: [], - pauschal: [ - [0, 1000], - [10000, 2000] - ] - }, - tag: { - grundpreis: 450, - pKm: [ - [0, 350], - [3000, 210], - [11000, 210] - ], - pauschal: [] - }, - nacht: { - grundpreis: 550, - pKm: [ - [0, 360], - [3000, 220], - [11000, 220] - ], - pauschal: [] - }, - returnFree: true, - zuschlag: { - grossraum: 900 - }, - wartzeitPStd: 3500, - beginnNacht: 21, - endeNacht: 5 -}; - -const ratesBautzen: RateInfo = { - anfahrt: { - grundpreis: 450, - pKm: [[0, 130]], - pauschal: [] - }, - tag: { - grundpreis: 450, - pKm: [[0, 250]], - pauschal: [] - }, - nacht: { - grundpreis: 450, - pKm: [[0, 270]], - pauschal: [] - }, - returnFree: true, - zuschlag: { - grossraum: 700 - }, - wartzeitPStd: 4500, - beginnNacht: 22, - endeNacht: 6 -}; - -export const rateInfo = [ratesGoerlitz, ratesBautzen]; From 0214dcb2d1cc7e4c26f18f662ed7b6f9843e5e1d Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 05:07:45 +0100 Subject: [PATCH 19/28] Use plan Endpoint of Motis instead if route --- package-lock.json | 529 +++++++++++++++++++++++++++++++- package.json | 2 + src/lib/TourDialog.svelte | 105 ++++--- src/lib/motisUtils.ts | 4 + src/routes/request/+page.svelte | 59 ++-- 5 files changed, 611 insertions(+), 88 deletions(-) diff --git a/package-lock.json b/package-lock.json index 1fcd655c..915b943d 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,6 +10,7 @@ "dependencies": { "@hey-api/client-fetch": "^0.4.2", "@lucia-auth/adapter-postgresql": "^3.1.2", + "@mapbox/polyline": "^1.2.1", "@node-rs/argon2": "^1.8.3", "@playwright/test": "^1.45.2", "bits-ui": "^0.21.13", @@ -38,6 +39,7 @@ "@sveltejs/vite-plugin-svelte": "^3.1.1", "@types/eslint": "^8.56.10", "@types/jsonschema": "^1.1.1", + "@types/mapbox__polyline": "^1.0.5", "@types/pg": "^8.11.6", "@typescript-eslint/eslint-plugin": "^7.16.1", "@typescript-eslint/parser": "^7.16.1", @@ -115,6 +117,35 @@ "integrity": "sha512-qCLYICQoCy3kEKDVwirQp8qvxhY7NJd8BhhoHaj1l3wCFAk9NUbcDsxAkPStZEMdPI/d7NcbGJe8SWZuRG2twQ==", "optional": true }, + "node_modules/@babel/code-frame": { + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.26.2.tgz", + "integrity": "sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-validator-identifier": "^7.25.9", + "js-tokens": "^4.0.0", + "picocolors": "^1.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/code-frame/node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "license": "MIT" + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.25.9.tgz", + "integrity": "sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, "node_modules/@babel/runtime": { "version": "7.25.6", "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.25.6.tgz", @@ -1021,6 +1052,17 @@ "resolved": "https://registry.npmjs.org/@mapbox/point-geometry/-/point-geometry-0.1.0.tgz", "integrity": "sha512-6j56HdLTwWGO0fJPlrZtdU/B13q8Uwmo18Ck2GnGgN9PCFyKTZ3UbXeEdRFh18i9XQ92eH2VdtpJHpBD3aripQ==" }, + "node_modules/@mapbox/polyline": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@mapbox/polyline/-/polyline-1.2.1.tgz", + "integrity": "sha512-sn0V18O3OzW4RCcPoUIVDWvEGQaBNH9a0y5lgqrf5hUycyw1CzrhEoxV5irzrMNXKCkw1xRsZXcaVbsVZggHXA==", + "dependencies": { + "meow": "^9.0.0" + }, + "bin": { + "polyline": "bin/polyline.bin.js" + } + }, "node_modules/@mapbox/tiny-sdf": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/@mapbox/tiny-sdf/-/tiny-sdf-2.0.6.tgz", @@ -2148,6 +2190,16 @@ "resolved": "https://registry.npmjs.org/@types/mapbox__point-geometry/-/mapbox__point-geometry-0.1.4.tgz", "integrity": "sha512-mUWlSxAmYLfwnRBmgYV86tgYmMIICX4kza8YnE/eIlywGe2XoOxlpVnXWwir92xRLjwyarqwpu2EJKD2pk0IUA==" }, + "node_modules/@types/mapbox__polyline": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/@types/mapbox__polyline/-/mapbox__polyline-1.0.5.tgz", + "integrity": "sha512-KNkXjtDPu3AgNbtikPyVqZEB5sF+Ls7sFtaZEgGEdU9YZUO5kF9nfDsJAWQqkBW8UVQNbq7Ob3Kube8l/b+3tQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/geojson": "*" + } + }, "node_modules/@types/mapbox__vector-tile": { "version": "1.3.4", "resolved": "https://registry.npmjs.org/@types/mapbox__vector-tile/-/mapbox__vector-tile-1.3.4.tgz", @@ -2158,6 +2210,12 @@ "@types/pbf": "*" } }, + "node_modules/@types/minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-hov8bUuiLiyFPGyFPE1lwWhmzYbirOXQNNo40+y3zow8aFVTeyn3VWL0VFFfdNddA8S4Vf0Tc062rzyNr7Paag==", + "license": "MIT" + }, "node_modules/@types/node": { "version": "22.5.4", "resolved": "https://registry.npmjs.org/@types/node/-/node-22.5.4.tgz", @@ -2167,6 +2225,12 @@ "undici-types": "~6.19.2" } }, + "node_modules/@types/normalize-package-data": { + "version": "2.4.4", + "resolved": "https://registry.npmjs.org/@types/normalize-package-data/-/normalize-package-data-2.4.4.tgz", + "integrity": "sha512-37i+OaWTh9qeK4LSHPsyRC7NahnGotNuZvjLSgcPzblpHB3rrCJxAOgI5gCdKm7coonsaX1Of0ILiTcnZjbfxA==", + "license": "MIT" + }, "node_modules/@types/pbf": { "version": "3.0.5", "resolved": "https://registry.npmjs.org/@types/pbf/-/pbf-3.0.5.tgz", @@ -2674,6 +2738,15 @@ "node": ">=8" } }, + "node_modules/arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha512-3CYzex9M9FGQjCGMGyi6/31c8GJbgb0qGyrx5HWxPd0aCwh4cB2YjMb2Xf9UuoogrMrlO9cTqnB5rI5GHZTcUA==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/assertion-error": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", @@ -2945,6 +3018,32 @@ "node": ">= 6" } }, + "node_modules/camelcase-keys": { + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/camelcase-keys/-/camelcase-keys-6.2.2.tgz", + "integrity": "sha512-YrwaA0vEKazPBkn0ipTiMpSajYDSe+KjQfrjhcBMxJt/znbvlHd8Pw/Vamaz5EB4Wfhs3SUR3Z9mwRu/P3s3Yg==", + "license": "MIT", + "dependencies": { + "camelcase": "^5.3.1", + "map-obj": "^4.0.0", + "quick-lru": "^4.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/camelcase-keys/node_modules/camelcase": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", + "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/caniuse-lite": { "version": "1.0.30001657", "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001657.tgz", @@ -3176,6 +3275,40 @@ } } }, + "node_modules/decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/decamelize-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.1.tgz", + "integrity": "sha512-WiPxgEirIV0/eIOMcnFBA3/IJZAZqKnwAwWyvvdi4lsr1WCN22nhdf/3db3DoZcUjTV2SqfzIwNyp6y2xs3nmg==", + "license": "MIT", + "dependencies": { + "decamelize": "^1.1.0", + "map-obj": "^1.0.0" + }, + "engines": { + "node": ">=0.10.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/decamelize-keys/node_modules/map-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz", + "integrity": "sha512-7N/q3lyZ+LVCp7PzuxrJr4KMbBE2hW7BT7YNia330OFxIf4d3r5zVpicP2650l7CPN6RM9zOJRl3NGpqSiw3Eg==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/deep-eql": { "version": "4.1.4", "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-4.1.4.tgz", @@ -3312,6 +3445,15 @@ "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==" }, + "node_modules/error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "license": "MIT", + "dependencies": { + "is-arrayish": "^0.2.1" + } + }, "node_modules/es6-promise": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-3.3.1.tgz", @@ -4142,6 +4284,15 @@ "uglify-js": "^3.1.4" } }, + "node_modules/hard-rejection": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/hard-rejection/-/hard-rejection-2.1.0.tgz", + "integrity": "sha512-VIZB+ibDhx7ObhAe7OVtoEbuP4h/MuOTHJ+J8h/eBXotJYl0fBgR72xDFCKgIh22OJZIOVNxBMWuhAr10r8HdA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -4162,6 +4313,30 @@ "node": ">= 0.4" } }, + "node_modules/hosted-git-info": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.1.0.tgz", + "integrity": "sha512-kyCuEOWjJqZuDbRHzL8V93NzQhwIB71oFWSyzVo+KPZI+pnQPPxucdkrOZvkLRnrf5URsQM+IJ09Dw29cRALIA==", + "license": "ISC", + "dependencies": { + "lru-cache": "^6.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/hosted-git-info/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "license": "ISC", + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, "node_modules/human-signals": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-5.0.0.tgz", @@ -4233,6 +4408,15 @@ "node": ">=0.8.19" } }, + "node_modules/indent-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-4.0.0.tgz", + "integrity": "sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==", + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", @@ -4258,6 +4442,12 @@ "node": "^14.17.0 || ^16.13.0 || >=18.0.0" } }, + "node_modules/is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", + "license": "MIT" + }, "node_modules/is-binary-path": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", @@ -4356,6 +4546,15 @@ "node": ">=8" } }, + "node_modules/is-plain-obj": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", + "integrity": "sha512-yvkRyxmFKEOQ4pNXCmJG5AEQNlXJS5LaONXo5/cLdTZdWvsZ1ioJEonLGAosKlMWE8lwUy/bJzMjcw8az73+Fg==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/is-plain-object": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", @@ -4460,6 +4659,12 @@ "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", "dev": true }, + "node_modules/json-parse-even-better-errors": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", + "license": "MIT" + }, "node_modules/json-schema-to-ts": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/json-schema-to-ts/-/json-schema-to-ts-3.1.1.tgz", @@ -4697,6 +4902,18 @@ "@jridgewell/sourcemap-codec": "^1.5.0" } }, + "node_modules/map-obj": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-4.3.0.tgz", + "integrity": "sha512-hdN1wVrZbb29eBGiGjJbeP8JbKjq1urkHJ/LIP/NY48MZ1QVXUsQBV1G1zvYFHn1XE06cwjBsOI2K3Ulnj1YXQ==", + "license": "MIT", + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/maplibre-gl": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/maplibre-gl/-/maplibre-gl-4.6.0.tgz", @@ -4763,6 +4980,44 @@ "resolved": "https://registry.npmjs.org/memoize-weak/-/memoize-weak-1.0.2.tgz", "integrity": "sha512-gj39xkrjEw7nCn4nJ1M5ms6+MyMlyiGmttzsqAUsAKn6bYKwuTHh/AO3cKPF8IBrTIYTxb0wWXFs3E//Y8VoWQ==" }, + "node_modules/meow": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/meow/-/meow-9.0.0.tgz", + "integrity": "sha512-+obSblOQmRhcyBt62furQqRAQpNyWXo8BuQ5bN7dG8wmwQ+vwHKp/rCFD4CrTP8CsDQD1sjoZ94K417XEUk8IQ==", + "license": "MIT", + "dependencies": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "decamelize": "^1.2.0", + "decamelize-keys": "^1.1.0", + "hard-rejection": "^2.1.0", + "minimist-options": "4.1.0", + "normalize-package-data": "^3.0.0", + "read-pkg-up": "^7.0.1", + "redent": "^3.0.0", + "trim-newlines": "^3.0.0", + "type-fest": "^0.18.0", + "yargs-parser": "^20.2.3" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/meow/node_modules/type-fest": { + "version": "0.18.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.18.1.tgz", + "integrity": "sha512-OIAYXk8+ISY+qTOwkHtKqzAuxchoMiD9Udx+FSGQDuiRR+PJKJHc2NJAXlbhkGwTt/4/nKZxELY1w3ReWOL8mw==", + "license": "(MIT OR CC0-1.0)", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/merge-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", @@ -4805,7 +5060,6 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/min-indent/-/min-indent-1.0.1.tgz", "integrity": "sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==", - "dev": true, "engines": { "node": ">=4" } @@ -4832,6 +5086,20 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/minimist-options": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/minimist-options/-/minimist-options-4.1.0.tgz", + "integrity": "sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==", + "license": "MIT", + "dependencies": { + "arrify": "^1.0.1", + "is-plain-obj": "^1.1.0", + "kind-of": "^6.0.3" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/minipass": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.2.tgz", @@ -4975,6 +5243,21 @@ "integrity": "sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==", "dev": true }, + "node_modules/normalize-package-data": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-3.0.3.tgz", + "integrity": "sha512-p2W1sgqij3zMMyRC067Dg16bfzVH+w7hyegmpIvZ4JNjqtGOVAIvLmjBx3yP7YTe9vKJgkoNOPjwQGogDoMXFA==", + "license": "BSD-2-Clause", + "dependencies": { + "hosted-git-info": "^4.0.1", + "is-core-module": "^2.5.0", + "semver": "^7.3.4", + "validate-npm-package-license": "^3.0.1" + }, + "engines": { + "node": ">=10" + } + }, "node_modules/normalize-path": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", @@ -5435,6 +5718,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/p-try": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", + "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/package-json-from-dist": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/package-json-from-dist/-/package-json-from-dist-1.0.0.tgz", @@ -5452,11 +5744,28 @@ "node": ">=6" } }, + "node_modules/parse-json": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", + "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", + "license": "MIT", + "dependencies": { + "@babel/code-frame": "^7.0.0", + "error-ex": "^1.3.1", + "json-parse-even-better-errors": "^2.3.0", + "lines-and-columns": "^1.1.6" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", - "dev": true, "engines": { "node": ">=8" } @@ -6118,6 +6427,15 @@ } ] }, + "node_modules/quick-lru": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-4.0.1.tgz", + "integrity": "sha512-ARhCpm70fzdcvNQfPoy49IaanKkTlRWF2JMzqhcJbhSFRZv7nPTvZJdcY7301IPmvW+/p0RgIWnQDLJxifsQ7g==", + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/quickselect": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/quickselect/-/quickselect-3.0.0.tgz", @@ -6147,6 +6465,135 @@ "pify": "^2.3.0" } }, + "node_modules/read-pkg": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-5.2.0.tgz", + "integrity": "sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==", + "license": "MIT", + "dependencies": { + "@types/normalize-package-data": "^2.4.0", + "normalize-package-data": "^2.5.0", + "parse-json": "^5.0.0", + "type-fest": "^0.6.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg-up": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-7.0.1.tgz", + "integrity": "sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==", + "license": "MIT", + "dependencies": { + "find-up": "^4.1.0", + "read-pkg": "^5.2.0", + "type-fest": "^0.8.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/read-pkg-up/node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "license": "MIT", + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg-up/node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "license": "MIT", + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg-up/node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "license": "MIT", + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/read-pkg-up/node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "license": "MIT", + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg-up/node_modules/type-fest": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz", + "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==", + "license": "(MIT OR CC0-1.0)", + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg/node_modules/hosted-git-info": { + "version": "2.8.9", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.9.tgz", + "integrity": "sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==", + "license": "ISC" + }, + "node_modules/read-pkg/node_modules/normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", + "license": "BSD-2-Clause", + "dependencies": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + } + }, + "node_modules/read-pkg/node_modules/semver": { + "version": "5.7.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.2.tgz", + "integrity": "sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g==", + "license": "ISC", + "bin": { + "semver": "bin/semver" + } + }, + "node_modules/read-pkg/node_modules/type-fest": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.6.0.tgz", + "integrity": "sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==", + "license": "(MIT OR CC0-1.0)", + "engines": { + "node": ">=8" + } + }, "node_modules/readdirp": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", @@ -6158,6 +6605,19 @@ "node": ">=8.10.0" } }, + "node_modules/redent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", + "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==", + "license": "MIT", + "dependencies": { + "indent-string": "^4.0.0", + "strip-indent": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/regenerator-runtime": { "version": "0.14.1", "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz", @@ -6418,7 +6878,6 @@ "version": "7.6.3", "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", - "dev": true, "bin": { "semver": "bin/semver.js" }, @@ -6577,6 +7036,38 @@ "source-map": "^0.6.0" } }, + "node_modules/spdx-correct": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.2.0.tgz", + "integrity": "sha512-kN9dJbvnySHULIluDHy32WHRUu3Og7B9sbY7tsFLctQkIqnMh3hErYgdMjTYuqmcXX+lK5T1lnUt3G7zNswmZA==", + "license": "Apache-2.0", + "dependencies": { + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" + } + }, + "node_modules/spdx-exceptions": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.5.0.tgz", + "integrity": "sha512-PiU42r+xO4UbUS1buo3LPJkjlO7430Xn5SVAhdpzzsPHsjbYVflnnFdATgabnLude+Cqu25p6N+g2lw/PFsa4w==", + "license": "CC-BY-3.0" + }, + "node_modules/spdx-expression-parse": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.1.tgz", + "integrity": "sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==", + "license": "MIT", + "dependencies": { + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" + } + }, + "node_modules/spdx-license-ids": { + "version": "3.0.20", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.20.tgz", + "integrity": "sha512-jg25NiDV/1fLtSgEgyvVyDunvaNHbuwF9lfNV17gSmPFAlYzdfNBlLtLzXTevwkPj7DhGbmN9VnmJIgLnhvaBw==", + "license": "CC0-1.0" + }, "node_modules/split-string": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", @@ -6730,7 +7221,6 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/strip-indent/-/strip-indent-3.0.0.tgz", "integrity": "sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ==", - "dev": true, "dependencies": { "min-indent": "^1.0.0" }, @@ -7314,6 +7804,15 @@ "node": ">=6" } }, + "node_modules/trim-newlines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-newlines/-/trim-newlines-3.0.1.tgz", + "integrity": "sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==", + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/ts-algebra": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ts-algebra/-/ts-algebra-2.0.0.tgz", @@ -7527,6 +8026,16 @@ "integrity": "sha512-+i2aCRkReTrd5KBN/dW2BrPOvFnU5LXTV2xjZnjnqUIO8YUx6P2+MgRrkwF2FhkexgyKq/NIZdPdknhHf5A/Ww==", "optional": true }, + "node_modules/validate-npm-package-license": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "license": "Apache-2.0", + "dependencies": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, "node_modules/validator": { "version": "13.12.0", "resolved": "https://registry.npmjs.org/validator/-/validator-13.12.0.tgz", @@ -8254,8 +8763,7 @@ "node_modules/yallist": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" }, "node_modules/yaml": { "version": "1.10.2", @@ -8266,6 +8774,15 @@ "node": ">= 6" } }, + "node_modules/yargs-parser": { + "version": "20.2.9", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.9.tgz", + "integrity": "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==", + "license": "ISC", + "engines": { + "node": ">=10" + } + }, "node_modules/yocto-queue": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", diff --git a/package.json b/package.json index a432a5cb..4f3e4821 100644 --- a/package.json +++ b/package.json @@ -24,6 +24,7 @@ "@sveltejs/vite-plugin-svelte": "^3.1.1", "@types/eslint": "^8.56.10", "@types/jsonschema": "^1.1.1", + "@types/mapbox__polyline": "^1.0.5", "@types/pg": "^8.11.6", "@typescript-eslint/eslint-plugin": "^7.16.1", "@typescript-eslint/parser": "^7.16.1", @@ -48,6 +49,7 @@ "dependencies": { "@hey-api/client-fetch": "^0.4.2", "@lucia-auth/adapter-postgresql": "^3.1.2", + "@mapbox/polyline": "^1.2.1", "@node-rs/argon2": "^1.8.3", "@playwright/test": "^1.45.2", "bits-ui": "^0.21.13", diff --git a/src/lib/TourDialog.svelte b/src/lib/TourDialog.svelte index 4d2ebe21..fb665dd7 100644 --- a/src/lib/TourDialog.svelte +++ b/src/lib/TourDialog.svelte @@ -12,7 +12,19 @@ import ConfirmationDialog from '$lib/ConfirmationDialog.svelte'; import maplibregl from 'maplibre-gl'; import { Button } from '$lib/components/ui/button'; - import { MIN_PREP_MINUTES } from './constants'; + import { MIN_PREP_MINUTES, MOTIS_BASE_URL } from './constants'; + import { plan, type PlanResponse } from './motis'; + import { coordinatesToPlace } from './motisUtils'; + import { Coordinates } from './location'; + import polyline from '@mapbox/polyline'; + + export function polylineToGeoJSON(encodedPolyline: string): GeoJSON.LineString { + const coordinates = polyline.decode(encodedPolyline, 7).map(([lng, lat]) => [lat, lng]); + return { + type: 'LineString', + coordinates + }; + } class Props { open!: { @@ -32,9 +44,8 @@ let tourIndex = $state(0); let tour = $derived(open.tours && open.tours[tourIndex]); - const getRoutes = (tourEvents: Array | null) => { - // eslint-disable-next-line - let routes: Array> = []; + const getRoutes = (tourEvents: Array | null): Promise[] => { + let routes: Array> = []; if (tourEvents == null || tourEvents!.length == 0) { return routes; } @@ -42,21 +53,17 @@ let e1 = tourEvents![e]; let e2 = tourEvents![e + 1]; routes.push( - getRoute({ - start: { - lat: e1.latitude, - lng: e1.longitude - }, - destination: { - lat: e2.latitude, - lng: e2.longitude - }, - profile: 'car', - direction: 'forward' - }) + plan({ + baseUrl: MOTIS_BASE_URL, + query: { + fromPlace: coordinatesToPlace(new Coordinates(e1.latitude, e1.longitude)), + toPlace: coordinatesToPlace(new Coordinates(e2.latitude, e2.longitude)), + maxDirectTime: 3600, + mode: ['CAR'] + } + }).then((d) => d.data!) ); } - return routes; }; @@ -190,37 +197,39 @@ > {#each routes as segment, i} {#await segment then r} - {#if r.type == 'FeatureCollection'} - - - - + {#if r.direct.length != 0 && r.direct[0] != undefined} + {#each r.direct[0].legs as leg} + + + + + {/each} {/if} {/await} {/each} diff --git a/src/lib/motisUtils.ts b/src/lib/motisUtils.ts index cd80e56d..b4c1f3c7 100644 --- a/src/lib/motisUtils.ts +++ b/src/lib/motisUtils.ts @@ -3,3 +3,7 @@ import type { Coordinates } from './location'; export const coordinatesToStr = (c: Coordinates) => { return `${c.lat};${c.lng}`; }; + +export const coordinatesToPlace = (c: Coordinates) => { + return `${c.lat},${c.lng},0`; +}; diff --git a/src/routes/request/+page.svelte b/src/routes/request/+page.svelte index 8d040856..b80576c8 100644 --- a/src/routes/request/+page.svelte +++ b/src/routes/request/+page.svelte @@ -9,13 +9,16 @@ import { Card } from '$lib/components/ui/card'; import * as RadioGroup from '$lib/components/ui/radio-group/index.js'; import { Coordinates } from '$lib/location'; - import { booking, getRoute } from '$lib/api'; + import { booking } from '$lib/api'; import { toTable } from '$lib/toTable'; import * as Alert from '$lib/components/ui/alert/index.js'; import { CircleAlert, CircleCheckBig } from 'lucide-svelte/icons'; import Button from '$lib/components/ui/button/button.svelte'; import GeoJSON from '$lib/GeoJSON.svelte'; import Layer from '$lib/Layer.svelte'; + import { plan } from '$lib/motis/services.gen.js'; + import { coordinatesToPlace } from '$lib/motisUtils.js'; + import { MOTIS_BASE_URL } from '$lib/constants.js'; const { data } = $props(); let zoom = $state(10); @@ -186,47 +189,35 @@ const getRoutes = (companyLat: number, companyLng: number) => { routes = []; routes.push({ - route: getRoute({ - start: { - lat: companyLat, - lng: companyLng - }, - destination: { - lat: start.lat, - lng: start.lng - }, - profile: 'car', - direction: 'forward' + route: plan({ + baseUrl: MOTIS_BASE_URL, + query: { + fromPlace: coordinatesToPlace(new Coordinates(companyLat, companyLng)), + toPlace: coordinatesToPlace(new Coordinates(start.lat, start.lng)), + mode: ['CAR'] + } }), color: 'red' }); routes.push({ - route: getRoute({ - start: { - lat: start.lat, - lng: start.lng - }, - destination: { - lat: destination.lat, - lng: destination.lng - }, - profile: 'car', - direction: 'forward' + route: plan({ + baseUrl: MOTIS_BASE_URL, + query: { + fromPlace: coordinatesToPlace(new Coordinates(start.lat, start.lng)), + toPlace: coordinatesToPlace(new Coordinates(destination.lat, destination.lng)), + mode: ['CAR'] + } }), color: '#42a5f5' }); routes.push({ - route: getRoute({ - start: { - lat: destination.lat, - lng: destination.lng - }, - destination: { - lat: companyLat, - lng: companyLng - }, - profile: 'car', - direction: 'forward' + route: plan({ + baseUrl: MOTIS_BASE_URL, + query: { + fromPlace: coordinatesToPlace(new Coordinates(destination.lat, destination.lng)), + toPlace: coordinatesToPlace(new Coordinates(companyLat, companyLng)), + mode: ['CAR'] + } }), color: 'yellow' }); From 2ac6a00cd260de76a270625350270baad51c5939 Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 07:17:35 +0100 Subject: [PATCH 20/28] Convert time units in booking api --- src/routes/api/booking/+server.ts | 19 +++++++++---------- 1 file changed, 9 insertions(+), 10 deletions(-) diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index 3a68a9c7..e44b7598 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -33,23 +33,22 @@ export const POST = async (event) => { let travelDuration = 0; try { - const duration = ( + const travelDuration = ( await oneToMany({ baseUrl: MOTIS_BASE_URL, query: { one: coordinatesToStr(fromCoordinates), many: [coordinatesToStr(toCoordinates)], max: 3600, - maxMatchingDistance: 100, + maxMatchingDistance: 200, mode: 'CAR', arriveBy: false } }).then((d) => d.data!) )[0].duration; - if (!duration) { + if (!travelDuration) { throw 'keine Route gefunden'; } - travelDuration = duration; } catch (e) { return json( { @@ -244,13 +243,13 @@ export const POST = async (event) => { one: coordinatesToStr(fromCoordinates), many: centralCoordinates.map(coordinatesToStr), max: 3600, - maxMatchingDistance: 100, + maxMatchingDistance: 200, mode: 'CAR', - arriveBy: false + arriveBy: true } }).then((res) => { return res.data!.map((d: Duration) => { - return d.duration ?? Number.MAX_VALUE; + return secondsToMs(d.duration ?? Number.MAX_VALUE); }); }); @@ -260,13 +259,13 @@ export const POST = async (event) => { one: coordinatesToStr(toCoordinates), many: centralCoordinates.map(coordinatesToStr), max: 3600, - maxMatchingDistance: 100, + maxMatchingDistance: 200, mode: 'CAR', - arriveBy: true + arriveBy: false } }).then((res) => { return res.data!.map((d: Duration) => { - return d.duration ?? Number.MAX_VALUE; + return secondsToMs(d.duration ?? Number.MAX_VALUE); }); }); } catch (e) { From 619368bbb89a12ff6d9818a7b9c224bb60674fa6 Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 07:18:11 +0100 Subject: [PATCH 21/28] Use /user routes in test files --- tests/availability.ts | 4 ++-- tests/utils.ts | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/availability.ts b/tests/availability.ts index f61b6119..da747b62 100644 --- a/tests/availability.ts +++ b/tests/availability.ts @@ -3,7 +3,7 @@ import { login, setCompanyData, addVehicle, ENTREPENEUR, COMPANY1 } from './util export async function setAvailability(page: Page) { await login(page, ENTREPENEUR); - await page.goto('/taxi?offset=-120&date=2026-09-30'); + await page.goto('/user/taxi?offset=-120&date=2026-09-30'); await page.waitForTimeout(500); await page.mouse.move(425, 465); @@ -73,7 +73,7 @@ test('Set availability', async ({ page }) => { test('Request ride', async ({ page }) => { await requestRide(page); - await page.goto('/taxi?offset=-120&date=2026-09-30'); + await page.goto('/user/taxi?offset=-120&date=2026-09-30'); await page.waitForTimeout(500); await expect( page.locator( diff --git a/tests/utils.ts b/tests/utils.ts index 5d528043..6c15997b 100644 --- a/tests/utils.ts +++ b/tests/utils.ts @@ -78,7 +78,7 @@ export async function setCompanyData(page: Page, user: UserCredentials, company: export async function addVehicle(page: Page, licensePlate: string) { await login(page, ENTREPENEUR); - await page.goto('/company'); + await page.goto('/user/company'); await page.waitForTimeout(500); await page.getByRole('link', { name: 'Taxi' }).click(); await expect(page.getByRole('heading', { name: 'Fahrzeuge und Touren' })).toBeVisible(); From 14c931fbe052c3bc66b48782f3161d7192c5337f Mon Sep 17 00:00:00 2001 From: nils Date: Tue, 5 Nov 2024 07:21:42 +0100 Subject: [PATCH 22/28] Format --- src/routes/api/booking/+server.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/routes/api/booking/+server.ts b/src/routes/api/booking/+server.ts index e44b7598..02c35a11 100644 --- a/src/routes/api/booking/+server.ts +++ b/src/routes/api/booking/+server.ts @@ -31,9 +31,9 @@ export const POST = async (event) => { const toCoordinates: Coordinates = to.coordinates; const time = new Date(timeStamp); - let travelDuration = 0; + let travelDuration: number | undefined = 0; try { - const travelDuration = ( + travelDuration = ( await oneToMany({ baseUrl: MOTIS_BASE_URL, query: { From 3232339d8bd3d4153ea516095c49a78351084d59 Mon Sep 17 00:00:00 2001 From: nils Date: Wed, 6 Nov 2024 02:26:42 +0100 Subject: [PATCH 23/28] Use /user route in moveTour test --- tests/moveTour.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/moveTour.ts b/tests/moveTour.ts index 66f5d4f3..b4e8d671 100644 --- a/tests/moveTour.ts +++ b/tests/moveTour.ts @@ -4,7 +4,7 @@ import { addVehicle } from './utils'; test('Move tour to other vehicle', async ({ page }) => { await addVehicle(page, 'GR-TU-12'); - await page.goto('/taxi?offset=-120&date=2026-09-30'); + await page.goto('/user/taxi?offset=-120&date=2026-09-30'); await page.waitForTimeout(500); await expect( From d7b98a51cd1ebf5c2eeb12dfbfc6036c85dd2c0a Mon Sep 17 00:00:00 2001 From: nils Date: Wed, 6 Nov 2024 16:34:00 +0100 Subject: [PATCH 24/28] Fix postgis version to 3.4.3 --- docker-compose.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docker-compose.yml b/docker-compose.yml index 449c5ce3..c5b2e95f 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,7 +1,7 @@ version: '3' services: pg: - image: postgis/postgis + image: postgis/postgis:3.4.3 restart: always container_name: pg ports: From 88177c22fcc23476e036e5adfc1166f57d407efc Mon Sep 17 00:00:00 2001 From: nils Date: Wed, 6 Nov 2024 16:39:36 +0100 Subject: [PATCH 25/28] wip --- docker-compose.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docker-compose.yml b/docker-compose.yml index c5b2e95f..7af8d9db 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,7 +1,7 @@ version: '3' services: pg: - image: postgis/postgis:3.4.3 + image: postgis/postgis:16-3.4 restart: always container_name: pg ports: From 269548485b2ac144017655b52e9ea6f362867f37 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 7 Nov 2024 09:44:12 +0100 Subject: [PATCH 26/28] wip --- .../app/src/main/java/de/motis/prima/Home.kt | 119 +++--- .../app/src/main/java/de/motis/prima/Login.kt | 10 +- .../app/src/main/java/de/motis/prima/Nav.kt | 34 +- .../src/main/java/de/motis/prima/Taxameter.kt | 159 +++++++ .../main/java/de/motis/prima/TourDetail.kt | 387 ++++++++++++++++++ .../main/java/de/motis/prima/TourOverview.kt | 163 ++++++++ .../app/src/main/java/de/motis/prima/Tours.kt | 111 ++++- .../src/main/java/de/motis/prima/Vehicles.kt | 113 ++--- .../main/java/de/motis/prima/services/Api.kt | 43 ++ .../app/src/main/res/values/strings.xml | 2 + src/routes/api/tour/+server.ts | 46 +++ src/routes/api/vehicle/+server.ts | 13 + 12 files changed, 1069 insertions(+), 131 deletions(-) create mode 100644 driver-app/app/src/main/java/de/motis/prima/Taxameter.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/TourDetail.kt create mode 100644 driver-app/app/src/main/java/de/motis/prima/TourOverview.kt diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index 10ae0b10..559f5477 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -12,6 +12,7 @@ import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.Button import androidx.compose.material3.CenterAlignedTopAppBar @@ -30,8 +31,8 @@ import androidx.compose.runtime.getValue import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember import androidx.compose.runtime.setValue -import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp @@ -67,6 +68,7 @@ class HomeViewModel : ViewModel() { @Composable fun Home( navController: NavController, + vehiclesViewModel: VehiclesViewModel, viewModel: HomeViewModel = androidx.lifecycle.viewmodel.compose.viewModel() ) { LaunchedEffect(key1 = viewModel) { @@ -98,6 +100,14 @@ fun Home( overflow = TextOverflow.Ellipsis ) }, + navigationIcon = { + IconButton(onClick = { navController.navigate("home") }) { + Icon( + imageVector = Icons.AutoMirrored.Filled.ArrowBack, + contentDescription = "Localized description" + ) + } + }, actions = { IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { Icon(Icons.Filled.MoreVert, contentDescription = "More Options") @@ -108,11 +118,11 @@ fun Home( ) { DropdownMenuItem( onClick = { - // Handle menu item click dropdownExpanded = false + navController.navigate("vehicles") }, - text = {Text("Option 1")} + text = {Text("Fahrzeug wechseln")} ) DropdownMenuItem( onClick = { @@ -120,7 +130,7 @@ fun Home( dropdownExpanded = false }, - text = {Text("Logout")} + text = { Text("Logout") } ) } } @@ -128,61 +138,68 @@ fun Home( } ) { innerPadding -> - // Main Content - Box( + Column( modifier = Modifier + .fillMaxSize() .padding(innerPadding) - .fillMaxSize(), - contentAlignment = Alignment.Center ) { - Scaffold( - modifier = Modifier - .fillMaxSize() - ) { contentPadding -> - Column( - modifier = Modifier - .fillMaxSize() - .padding(contentPadding) - ) { - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Button( - modifier = Modifier.width(300.dp), - onClick = { - navController.navigate("vehicles") {} - } - ) { - Text( - text = "Fahrzeug auswählen", - fontSize = 24.sp, - textAlign = TextAlign.Center - ) + Spacer(modifier = Modifier.height(42.dp)) + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + if (vehiclesViewModel.selectedVehicleId == 0) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("vehicles") {} } + ) { + Text( + text = "Fahrzeug auswählen", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } else { + var licensePlate = "" + try { + val vehicle = vehiclesViewModel.vehicles.value.filter { + v -> v.id == vehiclesViewModel.selectedVehicleId + }[0] + licensePlate = vehicle.plate + } catch (e: Exception) { + licensePlate = "Kein Fahrzeug ausgewählt" + } + + Box() { + Text( + text = licensePlate, + fontWeight = FontWeight.Bold, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) } + } + } - Spacer(modifier = Modifier.height(36.dp)) + Spacer(modifier = Modifier.height(36.dp)) - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Button( - modifier = Modifier.width(300.dp), - onClick = { - navController.navigate("tours") {} - } - ) { - Text( - text = "Aufträge", - fontSize = 24.sp, - textAlign = TextAlign.Center - ) - } + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("tours") {} } + ) { + Text( + text = "Aufträge", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Login.kt b/driver-app/app/src/main/java/de/motis/prima/Login.kt index 315ca3d2..62bdde9e 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Login.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Login.kt @@ -76,6 +76,7 @@ class LoginViewModel : ViewModel() { @Composable fun Login( navController: NavController, + vehiclesViewModel: VehiclesViewModel, viewModel: LoginViewModel = androidx.lifecycle.viewmodel.compose.viewModel() ) { val snackbarHostState = remember { SnackbarHostState() } @@ -92,14 +93,15 @@ fun Login( LaunchedEffect(key1 = viewModel) { // Catching successful login event and navigation to the next screen launch { + // vehiclesViewModel.selectedVehicleId = 0 viewModel.navigationEvent.collect { shouldNavigate -> Log.d("Navigation event", "Navigation triggered.") if (shouldNavigate) { Log.d("Navigation event", "Navigating to vehicle selection.") - navController.navigate("home") { - popUpTo("login") { - inclusive = true - } + if (vehiclesViewModel.selectedVehicleId == 0) { + navController.navigate("vehicles") {} + } else { + navController.navigate("tours") {} } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Nav.kt b/driver-app/app/src/main/java/de/motis/prima/Nav.kt index 814dabe3..0da05f6d 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Nav.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Nav.kt @@ -5,6 +5,7 @@ import androidx.compose.runtime.Composable import androidx.compose.runtime.derivedStateOf import androidx.compose.runtime.getValue import androidx.compose.runtime.remember +import androidx.lifecycle.viewmodel.compose.viewModel import androidx.navigation.compose.NavHost import androidx.navigation.compose.composable import androidx.navigation.compose.rememberNavController @@ -15,8 +16,10 @@ import de.motis.prima.services.CookieStore fun Nav() { val navController = rememberNavController() + val vehiclesViewModel: VehiclesViewModel = viewModel() + val toursViewModel: ToursViewModel = viewModel() - // Check before render of any component whether user is authenticated. + // Before rendering any component, check whether user is authenticated. val startDestination by remember { derivedStateOf { val cookieStore = CookieStore(DriversApp.instance) @@ -25,7 +28,11 @@ fun Nav() { "login" } else { Log.d("Cookie", "Cookie found. Navigating to Journeys.") - "home" + if (vehiclesViewModel.selectedVehicleId == 0) { + "vehicles" + } else { + "tours" + } } } } @@ -33,19 +40,34 @@ fun Nav() { NavHost(navController = navController, startDestination = startDestination) { composable(route = "login") { - Login(navController) + Login(navController, vehiclesViewModel) } composable(route = "home") { - Home(navController) + Home(navController, vehiclesViewModel) } composable(route = "vehicles") { - Vehicles(navController) + Vehicles(navController, vehiclesViewModel) } composable(route = "tours") { - Tours(navController) + Tours(navController, vehiclesViewModel, toursViewModel) + } + + composable(route = "taxameter") { + Taxameter(navController, toursViewModel) + } + + composable(route = "overview") { + TourOverview(navController) + } + + + composable(route = "legs/{tourId}/{eventIndex}") { + val tourId = it.arguments?.getString("tourId")?.toInt() + val eventIndex = it.arguments?.getString("eventIndex")?.toInt() + TourDetail(navController, tourId!!, eventIndex!!, toursViewModel) } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt b/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt new file mode 100644 index 00000000..310f0618 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt @@ -0,0 +1,159 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.text.KeyboardOptions +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack +import androidx.compose.material.icons.filled.MoreVert +import androidx.compose.material3.Button +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.OutlinedTextField +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TopAppBarDefaults +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.input.KeyboardType +import androidx.compose.ui.text.input.PasswordVisualTransformation +import androidx.compose.ui.text.style.TextOverflow +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.constraintlayout.compose.ConstraintLayout +import androidx.navigation.NavController +import kotlinx.coroutines.launch + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun Taxameter( + navController: NavController, + toursViewModel: ToursViewModel +) { + var entryCorrect by remember { mutableStateOf(false) } + var fare by remember { mutableStateOf("") } + + LaunchedEffect(key1 = toursViewModel) { + launch { + toursViewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + launchSingleTop = true + } + } + } + } + + var dropdownExpanded by remember { + mutableStateOf(false) + } + + Scaffold( + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { + Text( + "Taxameter", + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + }, + navigationIcon = { + /*IconButton(onClick = { navController.navigate("home") }) { + Icon( + imageVector = Icons.AutoMirrored.Filled.ArrowBack, + contentDescription = "Localized description" + ) + }*/ + }, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + navController.navigate("home") + dropdownExpanded = false + + }, + text = { Text("Fahrt abbrechen") } + ) + DropdownMenuItem( + onClick = { + toursViewModel.logout() + dropdownExpanded = false + + }, + text = { Text("Logout") } + ) + } + } + ) + + } + ) { contentPadding -> + ConstraintLayout( + modifier = Modifier + .fillMaxSize() + .padding(contentPadding) + ) { + Column( + modifier = Modifier.fillMaxSize(), + horizontalAlignment = Alignment.CenterHorizontally + ) { + Spacer(modifier = Modifier.height(20.dp)) + OutlinedTextField( + value = fare, + onValueChange = { + fare = it + entryCorrect = false + }, + label = { Text(stringResource(id = R.string.fare_label)) }, + maxLines = 1, + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Decimal), + isError = entryCorrect + ) + Spacer(modifier = Modifier.height(20.dp)) + Button( + onClick = { + entryCorrect = false + Log.d("Taxameter", "Fare: ${fare}") + // send fare to API + navController.navigate("tours") + } + ) { + Text( + text = stringResource(id = R.string.send_fare_button_text), fontSize = 18.sp + ) + } + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt b/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt new file mode 100644 index 00000000..c7f7848e --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt @@ -0,0 +1,387 @@ +package de.motis.prima + +import android.content.res.Configuration +import android.util.Log +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxHeight +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.width +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack +import androidx.compose.material.icons.filled.MoreVert +import androidx.compose.material3.Button +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TopAppBarDefaults +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalConfiguration +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextAlign +import androidx.compose.ui.text.style.TextOverflow +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore +import de.motis.prima.services.Event +import de.motis.prima.services.Tour +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +class TourDetailViewModel : ViewModel() { + private val cookieStore: CookieStore = CookieStore(DriversApp.instance) + + private val _logoutEvent = MutableSharedFlow() + val logoutEvent = _logoutEvent.asSharedFlow() + + fun logout() { + viewModelScope.launch { + try { + cookieStore.clearCookies() + _logoutEvent.emit(Unit) + } catch (e: Exception) { + Log.d("Logout", "Error while logout.") + } + } + } +} + +@Composable +fun PortraitLayout( + navController: NavController, + tourId: Int, + eventIndex: Int, + toursViewModel: ToursViewModel, + contentPadding: PaddingValues +) { + Log.d("rotation", "portrait") + + var isLastLeg = false + val tour = toursViewModel.tours.value.filter { t -> t.tour_id == tourId }[0] + val fromEvent = tour.events[eventIndex] + val toEvent = tour.events[eventIndex + 1] + + if (eventIndex + 2 >= tour.events.size) { + isLastLeg = true + } + + Column( + modifier = Modifier + ) { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Box( + modifier = Modifier + .padding(contentPadding) + ) { + Text( + text = "${eventIndex + 1} / ${tour.events.size - 1}", + fontSize = 24.sp, + fontWeight = FontWeight.Bold, + textAlign = TextAlign.Center + ) + } + } + /*Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Box( + modifier = Modifier + .padding(contentPadding) + ) { + EventDetail(event = fromEvent) + } + }*/ + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Box( + modifier = Modifier + .padding(contentPadding) + ) { + EventDetail(event = toEvent) + } + } + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + if (!isLastLeg) { + Box( + modifier = Modifier + .padding(contentPadding) + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("legs/${tour.tour_id}/${eventIndex + 1}") {} + } + ) { + Text( + text = "Weiter", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + } else { + Box( + modifier = Modifier + .padding(contentPadding) + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("taxameter") {} + } + ) { + Text( + text = "Fahrt abgeschlossen", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + } + } + } +} + +@Composable +fun LandscapeLayout( + navController: NavController, + tourId: Int, + eventIndex: Int, + toursViewModel: ToursViewModel +) { + // Define UI elements for landscape layout + Log.d("rotation", "landscape") + + Row( + modifier = Modifier + .fillMaxSize() + .padding(16.dp) + ) { + Column( + modifier = Modifier + .weight(1f) + .fillMaxHeight() + .background(Color.LightGray), + verticalArrangement = Arrangement.Center, + horizontalAlignment = Alignment.CenterHorizontally + ) { + Text("Row 1", fontSize = 20.sp, modifier = Modifier.padding(16.dp)) + } + + Column( + modifier = Modifier + .weight(1f) + .fillMaxHeight() + .background(Color.Gray), + verticalArrangement = Arrangement.Center, + horizontalAlignment = Alignment.CenterHorizontally + ) { + Text("Row 2", fontSize = 20.sp, modifier = Modifier.padding(16.dp)) + } + + Column( + modifier = Modifier + .weight(1f) + .fillMaxHeight() + .background(Color.DarkGray), + verticalArrangement = Arrangement.Center, + horizontalAlignment = Alignment.CenterHorizontally + ) { + Text("Row 3", fontSize = 20.sp, modifier = Modifier.padding(16.dp)) + } + } +} + +@Composable +fun HandleOrientationChanges( + navController: NavController, + tourId: Int, + eventIndex: Int, + toursViewModel: ToursViewModel, + contentPadding: PaddingValues +) { + val configuration = LocalConfiguration.current + val isLandscape = configuration.orientation == Configuration.ORIENTATION_LANDSCAPE + if (isLandscape) { + LandscapeLayout( + navController, + tourId, + eventIndex, + toursViewModel + ) + } else { + PortraitLayout( + navController, + tourId, + eventIndex, + toursViewModel, + contentPadding + ) + } +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun TourDetail( + navController: NavController, + tourId: Int, + eventIndex: Int, + toursViewModel: ToursViewModel +) { + LaunchedEffect(key1 = toursViewModel) { + launch { + toursViewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + launchSingleTop = true + } + } + } + } + + var dropdownExpanded by remember { + mutableStateOf(false) + } + + Scaffold( + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { + Text( + "Fahrt", + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + }, + navigationIcon = {}, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + navController.navigate("home") + dropdownExpanded = false + + }, + text = { Text("Fahrt abbrechen") } + ) + DropdownMenuItem( + onClick = { + toursViewModel.logout() + dropdownExpanded = false + + }, + text = { Text("Logout") } + ) + } + } + ) + + } + ) { contentPadding -> + HandleOrientationChanges( + navController, + tourId, + eventIndex, + toursViewModel, + contentPadding + ) + Box( + modifier = Modifier + .padding(contentPadding) + ) + } +} + +@Composable +fun EventDetail(event: Event) { + Column { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = event.scheduled_time.split("T")[1].substring(0, 5), + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = event.city, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = event.street + " " + event.house_number, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + if (event.is_pickup) { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = event.last_name + ", " + event.first_name, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt b/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt new file mode 100644 index 00000000..1073f749 --- /dev/null +++ b/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt @@ -0,0 +1,163 @@ +package de.motis.prima + +import android.util.Log +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.width +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.automirrored.filled.ArrowBack +import androidx.compose.material.icons.filled.MoreVert +import androidx.compose.material3.Button +import androidx.compose.material3.CenterAlignedTopAppBar +import androidx.compose.material3.DropdownMenu +import androidx.compose.material3.DropdownMenuItem +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.material3.TopAppBarDefaults +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Modifier +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextAlign +import androidx.compose.ui.text.style.TextOverflow +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import androidx.navigation.NavController +import de.motis.prima.app.DriversApp +import de.motis.prima.services.CookieStore +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow +import kotlinx.coroutines.launch + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun TourOverview( + navController: NavController, + viewModel: HomeViewModel = androidx.lifecycle.viewmodel.compose.viewModel() +) { + LaunchedEffect(key1 = viewModel) { + launch { + viewModel.logoutEvent.collect { + Log.d("Logout", "Logout event triggered.") + navController.navigate("login") { + launchSingleTop = true + } + } + } + } + + var dropdownExpanded by remember { + mutableStateOf(false) + } + + Scaffold( + topBar = { + CenterAlignedTopAppBar( + colors = TopAppBarDefaults.centerAlignedTopAppBarColors( + containerColor = MaterialTheme.colorScheme.primaryContainer, + titleContentColor = MaterialTheme.colorScheme.primary, + ), + title = { + Text( + "Fahrt Übersicht", + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + }, + navigationIcon = { + IconButton(onClick = { navController.navigate("home") }) { + Icon( + imageVector = Icons.AutoMirrored.Filled.ArrowBack, + contentDescription = "Localized description" + ) + } + }, + actions = { + IconButton(onClick = { dropdownExpanded = !dropdownExpanded }) { + Icon(Icons.Filled.MoreVert, contentDescription = "More Options") + } + DropdownMenu( + expanded = dropdownExpanded, + onDismissRequest = { dropdownExpanded = false } + ) { + DropdownMenuItem( + onClick = { + dropdownExpanded = false + navController.navigate("vehicles") + + }, + text = {Text("Fahrzeug wechseln")} + ) + DropdownMenuItem( + onClick = { + viewModel.logout() + dropdownExpanded = false + + }, + text = { Text("Logout") } + ) + } + } + ) + + } + ) { innerPadding -> + Column( + modifier = Modifier + .fillMaxSize() + .padding(innerPadding) + ) { + Spacer(modifier = Modifier.height(42.dp)) + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Box() { + Text( + text = "Details zur gesamten Tour", + fontWeight = FontWeight.Bold, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + + Spacer(modifier = Modifier.height(36.dp)) + + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Button( + modifier = Modifier.width(300.dp), + onClick = { + navController.navigate("tours") {} + } + ) { + Text( + text = "Aufträge", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + } + } +} diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index 65595b3f..fd87ffe6 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -1,6 +1,7 @@ package de.motis.prima import android.util.Log +import androidx.compose.foundation.clickable import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Spacer @@ -9,6 +10,7 @@ import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack @@ -33,17 +35,25 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp +import androidx.constraintlayout.compose.ConstraintLayout import androidx.lifecycle.ViewModel import androidx.lifecycle.viewModelScope import androidx.navigation.NavController import de.motis.prima.app.DriversApp +import de.motis.prima.services.Api import de.motis.prima.services.CookieStore +import de.motis.prima.services.Tour +import de.motis.prima.services.Vehicle import kotlinx.coroutines.flow.MutableSharedFlow import kotlinx.coroutines.flow.asSharedFlow import kotlinx.coroutines.launch +import retrofit2.Call +import retrofit2.Callback +import retrofit2.Response class ToursViewModel : ViewModel() { private val cookieStore: CookieStore = CookieStore(DriversApp.instance) @@ -51,6 +61,35 @@ class ToursViewModel : ViewModel() { private val _logoutEvent = MutableSharedFlow() val logoutEvent = _logoutEvent.asSharedFlow() + var tours = mutableStateOf>(emptyList()) + private set + + var isLoading = mutableStateOf(true) + private set + + init { + fetchTours() + } + + private fun fetchTours() { + viewModelScope.launch { + Api.apiService.getTours().enqueue(object : Callback> { + override fun onResponse(call: Call>, response: Response>) { + if (response.isSuccessful) { + tours.value = response.body() ?: emptyList() + isLoading.value = false + } else { + isLoading.value = false + } + } + + override fun onFailure(call: Call>, t: Throwable) { + isLoading.value = false + } + }) + } + } + fun logout() { viewModelScope.launch { try { @@ -67,7 +106,8 @@ class ToursViewModel : ViewModel() { @Composable fun Tours( navController: NavController, - viewModel: ToursViewModel = androidx.lifecycle.viewmodel.compose.viewModel() + vehiclesViewModel: VehiclesViewModel, + viewModel: ToursViewModel //= androidx.lifecycle.viewmodel.compose.viewModel() ) { LaunchedEffect(key1 = viewModel) { launch { @@ -117,9 +157,10 @@ fun Tours( DropdownMenuItem( onClick = { dropdownExpanded = false + navController.navigate("vehicles") }, - text = { Text("Option 1") } + text = {Text("Fahrzeug wechseln")} ) DropdownMenuItem( onClick = { @@ -135,31 +176,65 @@ fun Tours( } ) { contentPadding -> + if (vehiclesViewModel.selectedVehicleId == 0) { + Box( + modifier = Modifier.fillMaxSize().padding(16.dp), + contentAlignment = Alignment.Center + ) { + Text( + text = "Kein Fahrzeug ausgewählt", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } + LazyColumn( modifier = Modifier .fillMaxSize() .padding(contentPadding) ) { - items(8) { index -> - Card( - shape = RoundedCornerShape(12.dp), - modifier = Modifier - .fillMaxWidth() - .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) - .height(100.dp) - ) { - Box( - modifier = Modifier.fillMaxSize().padding(16.dp), - contentAlignment = Alignment.TopStart + val toursForVehicle = viewModel.tours.value.filter { t -> + t.vehicle_id == vehiclesViewModel.selectedVehicleId + } + items(items = toursForVehicle, itemContent = { tour -> + ConstraintLayout(modifier = Modifier.clickable { + navController.navigate("legs/${tour.tour_id}/0") + }) { + var startAddress = "" + var displayTime = "" + try { + val startEvent = tour.events[0] + startAddress = startEvent.city + ", " + startEvent.street + " " + startEvent.house_number + } catch (e: Exception) { + Log.d("error", "Error: Tour has no events") + } + try { + displayTime = tour.from.split("T")[1].substring(0, 5) + } catch (e: Exception) { + Log.d("error", "Error: No display time") + } + + Card( + shape = RoundedCornerShape(12.dp), + modifier = Modifier + .fillMaxWidth() + .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) + .height(100.dp) ) { - Column { - Text("08:30", fontSize = 24.sp, fontWeight = FontWeight.Bold) - Spacer(modifier = Modifier.height(12.dp)) - Text("Görlitz, Beispielplatz ${index + 1}", fontSize = 24.sp) + Box( + modifier = Modifier.fillMaxSize().padding(16.dp), + contentAlignment = Alignment.TopStart + ) { + Column { + Text(displayTime, fontSize = 24.sp, fontWeight = FontWeight.Bold) + Spacer(modifier = Modifier.height(12.dp)) + Text(startAddress, fontSize = 24.sp) + } } } } - } + }) } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index 321e47af..01b50229 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -1,14 +1,14 @@ package de.motis.prima import android.util.Log -import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.clickable import androidx.compose.foundation.layout.Box -import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack @@ -36,14 +36,20 @@ import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp +import androidx.constraintlayout.compose.ConstraintLayout import androidx.lifecycle.ViewModel import androidx.lifecycle.viewModelScope import androidx.navigation.NavController import de.motis.prima.app.DriversApp +import de.motis.prima.services.Api import de.motis.prima.services.CookieStore +import de.motis.prima.services.Vehicle import kotlinx.coroutines.flow.MutableSharedFlow import kotlinx.coroutines.flow.asSharedFlow import kotlinx.coroutines.launch +import retrofit2.Call +import retrofit2.Callback +import retrofit2.Response class VehiclesViewModel : ViewModel() { private val cookieStore: CookieStore = CookieStore(DriversApp.instance) @@ -51,6 +57,38 @@ class VehiclesViewModel : ViewModel() { private val _logoutEvent = MutableSharedFlow() val logoutEvent = _logoutEvent.asSharedFlow() + var vehicles = mutableStateOf>(emptyList()) + private set + + var isLoading = mutableStateOf(true) + private set + + var selectedVehicleId = 0 + + init { + fetchVehicles() + } + + private fun fetchVehicles() { + viewModelScope.launch { + Api.apiService.getVehicles().enqueue(object : Callback> { + override fun onResponse(call: Call>, response: Response>) { + if (response.isSuccessful) { + vehicles.value = response.body() ?: emptyList() + isLoading.value = false + } else { + isLoading.value = false + } + } + + override fun onFailure(call: Call>, t: Throwable) { + isLoading.value = false + } + }) + } + } + + fun logout() { viewModelScope.launch { try { @@ -67,7 +105,7 @@ class VehiclesViewModel : ViewModel() { @Composable fun Vehicles( navController: NavController, - viewModel: VehiclesViewModel = androidx.lifecycle.viewmodel.compose.viewModel() + viewModel: VehiclesViewModel //= androidx.lifecycle.viewmodel.compose.viewModel() ) { LaunchedEffect(key1 = viewModel) { launch { @@ -114,13 +152,6 @@ fun Vehicles( expanded = dropdownExpanded, onDismissRequest = { dropdownExpanded = false } ) { - DropdownMenuItem( - onClick = { - dropdownExpanded = false - - }, - text = { Text("Option 1") } - ) DropdownMenuItem( onClick = { viewModel.logout() @@ -135,54 +166,32 @@ fun Vehicles( } ) { contentPadding -> - Column( + LazyColumn( modifier = Modifier - .fillMaxSize() .padding(contentPadding) ) { - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Card( - shape = RoundedCornerShape(12.dp), - modifier = Modifier - .fillMaxWidth() - .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) - .height(80.dp) - .align(alignment = Alignment.CenterVertically) - ) { - Box( - modifier = Modifier.fillMaxSize(), - contentAlignment = Alignment.Center // Center content within the Box + items(items = viewModel.vehicles.value, itemContent = { vehicle -> + ConstraintLayout(modifier = Modifier.clickable { + viewModel.selectedVehicleId = vehicle.id + navController.navigate("tours") + }) { + Card( + shape = RoundedCornerShape(12.dp), + modifier = Modifier + .fillMaxWidth() + .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) + .height(80.dp) ) { - Text("GR-TU-11", fontSize = 24.sp, fontWeight = FontWeight.Bold) + Box( + modifier = Modifier.fillMaxSize(), + contentAlignment = Alignment.Center // Center content within the Box + ) { + Text(vehicle.plate, fontSize = 24.sp, fontWeight = FontWeight.Bold) + } } } - } - Row( - modifier = Modifier.fillMaxWidth(), - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.Center - ) { - Card( - shape = RoundedCornerShape(12.dp), - modifier = Modifier - .fillMaxWidth() - .padding(start = 24.dp, end = 24.dp, top = 24.dp, bottom = 0.dp) - .height(80.dp) - .align(alignment = Alignment.CenterVertically) - ) { - Box( - modifier = Modifier.fillMaxSize(), - contentAlignment = Alignment.Center // Center content within the Box - ) { - Text("GR-TU-12", fontSize = 24.sp, fontWeight = FontWeight.Bold) - } - } - } + }) } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/services/Api.kt b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt index c688533b..0a5543d3 100644 --- a/driver-app/app/src/main/java/de/motis/prima/services/Api.kt +++ b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt @@ -1,11 +1,14 @@ package de.motis.prima.services import de.motis.prima.BuildConfig.BASE_URL +import retrofit2.Call import retrofit2.Retrofit import retrofit2.converter.gson.GsonConverterFactory import retrofit2.http.Field import retrofit2.http.FormUrlEncoded +import retrofit2.http.GET import retrofit2.http.POST +import java.util.Date interface ApiService { @POST("login") @@ -14,6 +17,12 @@ interface ApiService { @Field("email") email: String, @Field("password") password: String ): LoginResponse + + @GET("api/vehicle") + fun getVehicles() : Call> + + @GET("api/tour") + fun getTours() : Call> } object Api { @@ -31,3 +40,37 @@ data class LoginResponse( val status: Int, val data: String ) + +data class Vehicle( + val id: Int, + val plate: String +) + +data class Event( + val address: Int, + val latitude: Double, + val longitude: Double, + val street: String, + val postal_code: String, + val city: String, + val scheduled_time: String, + val house_number: String, + val first_name: String, + val last_name: String, + val phone: String, + val is_pickup: Boolean, + val customer_id: String +) + +data class Tour( + val tour_id: Int, + val from: String, + val to: String, + val vehicle_id: Int, + val license_plate: String, + val company_id: Int, + val fare: Int, + val fare_route: Int, + val company_name: String, + val events: List +) diff --git a/driver-app/app/src/main/res/values/strings.xml b/driver-app/app/src/main/res/values/strings.xml index 49c49cc1..0fea8b75 100644 --- a/driver-app/app/src/main/res/values/strings.xml +++ b/driver-app/app/src/main/res/values/strings.xml @@ -5,4 +5,6 @@ E-Mail Passwort Etwas ist schiefgelaufen. Bitte versuchen Sie es später erneut. + Fahrpreis + Speichern diff --git a/src/routes/api/tour/+server.ts b/src/routes/api/tour/+server.ts index 33d0bf75..541e5288 100644 --- a/src/routes/api/tour/+server.ts +++ b/src/routes/api/tour/+server.ts @@ -1,6 +1,8 @@ import { error, json } from '@sveltejs/kit'; import { db } from '$lib/database'; import { sql } from 'kysely'; +import { Vehicle } from '../../(user)/taxi/types.js'; +import { mapTourEvents } from '$lib/TourDetails.js'; export const POST = async (event) => { const companyId = event.locals.user?.company; @@ -57,3 +59,47 @@ export const POST = async (event) => { }); return json({}); }; + +export const GET = async (event) => { + const company = event.locals.user?.company; + if (!company) { + error(400, { + message: 'not allowed without write access to company' + }); + } + const url = event.url; + // const localDateParam = url.searchParams.get('id'); + + const earliest_displayed_time = new Date('2024-06-09 08:10:00'); + const latest_displayed_time = new Date('2024-06-09 10:10:00'); + const tours = mapTourEvents( + await db + .selectFrom('event') + .innerJoin('address', 'address.id', 'event.address') + .innerJoin('auth_user', 'auth_user.id', 'event.customer') + .innerJoin('tour', 'tour.id', 'event.tour') + .where((eb) => + eb.and([ + eb('tour.departure', '<', latest_displayed_time), + eb('tour.arrival', '>', earliest_displayed_time) + ]) + ) + .innerJoin('vehicle', 'vehicle.id', 'tour.vehicle') + .innerJoin('company', 'company.id', 'vehicle.company') + .where('company', '=', company) + .orderBy('event.scheduled_time') + .selectAll(['event', 'address', 'tour', 'vehicle']) + .select([ + 'company.name as company_name', + 'company.address as company_address', + 'auth_user.first_name as customer_first_name', + 'auth_user.last_name as customer_last_ame', + 'auth_user.phone as customer_phone' + ]) + .execute() + ); + + console.log(tours[0].events); + + return json(tours); +} diff --git a/src/routes/api/vehicle/+server.ts b/src/routes/api/vehicle/+server.ts index 50333e0b..cfee79ce 100644 --- a/src/routes/api/vehicle/+server.ts +++ b/src/routes/api/vehicle/+server.ts @@ -37,3 +37,16 @@ export const POST = async (event) => { } return json({}); }; + +export const GET = async (event) => { + const company = event.locals.user?.company; + if (!company) { + error(400, { + message: 'not allowed without write access to company' + }); + } + const url = event.url; + // const localDateParam = url.searchParams.get('id'); + + return json([{ id: 1, plate: 'GR-TU-41' }, { id: 2, plate: 'GR-TU-42' }]); +} From 8d2aae918ff09f5ad0b114d207df5c1da9651e49 Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 7 Nov 2024 10:10:10 +0100 Subject: [PATCH 27/28] wip --- driver-app/app/src/main/java/de/motis/prima/Nav.kt | 5 +++-- .../app/src/main/java/de/motis/prima/TourOverview.kt | 8 +++++--- driver-app/app/src/main/java/de/motis/prima/Tours.kt | 3 ++- 3 files changed, 10 insertions(+), 6 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Nav.kt b/driver-app/app/src/main/java/de/motis/prima/Nav.kt index 0da05f6d..6a010718 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Nav.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Nav.kt @@ -59,8 +59,9 @@ fun Nav() { Taxameter(navController, toursViewModel) } - composable(route = "overview") { - TourOverview(navController) + composable(route = "overview/{tourId}") { + val tourId = it.arguments?.getString("tourId")?.toInt() + TourOverview(navController, tourId!!) } diff --git a/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt b/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt index 1073f749..48a829dc 100644 --- a/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt +++ b/driver-app/app/src/main/java/de/motis/prima/TourOverview.kt @@ -50,6 +50,7 @@ import kotlinx.coroutines.launch @Composable fun TourOverview( navController: NavController, + tourId: Int, viewModel: HomeViewModel = androidx.lifecycle.viewmodel.compose.viewModel() ) { LaunchedEffect(key1 = viewModel) { @@ -132,12 +133,12 @@ fun TourOverview( Box() { Text( text = "Details zur gesamten Tour", - fontWeight = FontWeight.Bold, fontSize = 24.sp, textAlign = TextAlign.Center ) } } + // TODO Spacer(modifier = Modifier.height(36.dp)) @@ -148,11 +149,12 @@ fun TourOverview( Button( modifier = Modifier.width(300.dp), onClick = { - navController.navigate("tours") {} + // navController.navigate("tours") {} + navController.navigate("legs/${tourId}/0") } ) { Text( - text = "Aufträge", + text = "Fahrt starten", fontSize = 24.sp, textAlign = TextAlign.Center ) diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index fd87ffe6..97030cd7 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -199,7 +199,8 @@ fun Tours( } items(items = toursForVehicle, itemContent = { tour -> ConstraintLayout(modifier = Modifier.clickable { - navController.navigate("legs/${tour.tour_id}/0") + //navController.navigate("legs/${tour.tour_id}/0") + navController.navigate("overview/${tour.tour_id}") }) { var startAddress = "" var displayTime = "" From 0e074b161484469fffba2472a30f59907f4728cb Mon Sep 17 00:00:00 2001 From: Steffen Heger Date: Thu, 7 Nov 2024 17:21:20 +0100 Subject: [PATCH 28/28] wip --- .../app/src/main/java/de/motis/prima/Home.kt | 2 +- .../src/main/java/de/motis/prima/Taxameter.kt | 39 +++++- .../main/java/de/motis/prima/TourDetail.kt | 120 ++++++++++++------ .../app/src/main/java/de/motis/prima/Tours.kt | 14 +- .../src/main/java/de/motis/prima/Vehicles.kt | 8 +- .../main/java/de/motis/prima/services/Api.kt | 10 +- .../app/src/main/res/values-night/themes.xml | 2 +- driver-app/app/src/main/res/values/themes.xml | 2 +- src/routes/api/tour/+server.ts | 9 +- src/routes/api/vehicle/+server.ts | 6 +- 10 files changed, 147 insertions(+), 65 deletions(-) diff --git a/driver-app/app/src/main/java/de/motis/prima/Home.kt b/driver-app/app/src/main/java/de/motis/prima/Home.kt index 559f5477..28efd2db 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Home.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Home.kt @@ -167,7 +167,7 @@ fun Home( val vehicle = vehiclesViewModel.vehicles.value.filter { v -> v.id == vehiclesViewModel.selectedVehicleId }[0] - licensePlate = vehicle.plate + licensePlate = vehicle.license_plate } catch (e: Exception) { licensePlate = "Kein Fahrzeug ausgewählt" } diff --git a/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt b/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt index 310f0618..89ef72e4 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Taxameter.kt @@ -2,6 +2,7 @@ package de.motis.prima import android.util.Log import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.BoxWithConstraints import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer @@ -9,6 +10,7 @@ import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.wrapContentHeight import androidx.compose.foundation.text.KeyboardOptions import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack @@ -23,6 +25,8 @@ import androidx.compose.material3.IconButton import androidx.compose.material3.MaterialTheme import androidx.compose.material3.OutlinedTextField import androidx.compose.material3.Scaffold +import androidx.compose.material3.SnackbarHost +import androidx.compose.material3.SnackbarHostState import androidx.compose.material3.Text import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable @@ -40,17 +44,30 @@ import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp import androidx.constraintlayout.compose.ConstraintLayout +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope import androidx.navigation.NavController +import de.motis.prima.services.Api +import kotlinx.coroutines.flow.MutableSharedFlow +import kotlinx.coroutines.flow.asSharedFlow import kotlinx.coroutines.launch +class TaxameterViewModel : ViewModel() { + private val _networkErrorEvent = MutableSharedFlow() + val networkErrorEvent = _networkErrorEvent.asSharedFlow() +} + @OptIn(ExperimentalMaterial3Api::class) @Composable fun Taxameter( navController: NavController, - toursViewModel: ToursViewModel + toursViewModel: ToursViewModel, + viewModel: TaxameterViewModel = androidx.lifecycle.viewmodel.compose.viewModel() ) { var entryCorrect by remember { mutableStateOf(false) } var fare by remember { mutableStateOf("") } + val snackbarHostState = remember { SnackbarHostState() } + val networkErrorMessage = stringResource(id = R.string.network_error_message) LaunchedEffect(key1 = toursViewModel) { launch { @@ -61,6 +78,13 @@ fun Taxameter( } } } + + // Catching event when a network error occurs and displaying of error message + launch { + viewModel.networkErrorEvent.collect { + snackbarHostState.showSnackbar(message = networkErrorMessage) + } + } } var dropdownExpanded by remember { @@ -117,6 +141,17 @@ fun Taxameter( } ) + }, + snackbarHost = { + BoxWithConstraints(modifier = Modifier.fillMaxSize()) { + SnackbarHost( + hostState = snackbarHostState, + modifier = Modifier + .fillMaxSize() + .wrapContentHeight(Alignment.Top) + .padding(top = maxHeight * 0.25f) + ) + } } ) { contentPadding -> ConstraintLayout( @@ -145,7 +180,7 @@ fun Taxameter( onClick = { entryCorrect = false Log.d("Taxameter", "Fare: ${fare}") - // send fare to API + // TODO: send fare to API navController.navigate("tours") } ) { diff --git a/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt b/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt index c7f7848e..fb92e406 100644 --- a/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt +++ b/driver-app/app/src/main/java/de/motis/prima/TourDetail.kt @@ -83,13 +83,13 @@ fun PortraitLayout( ) { Log.d("rotation", "portrait") - var isLastLeg = false + var isLastEvent = false val tour = toursViewModel.tours.value.filter { t -> t.tour_id == tourId }[0] - val fromEvent = tour.events[eventIndex] - val toEvent = tour.events[eventIndex + 1] + val event = tour.events[eventIndex] + //val toEvent = tour.events[eventIndex + 1] - if (eventIndex + 2 >= tour.events.size) { - isLastLeg = true + if (eventIndex + 1 == tour.events.size) { + isLastEvent = true } Column( @@ -104,24 +104,12 @@ fun PortraitLayout( .padding(contentPadding) ) { Text( - text = "${eventIndex + 1} / ${tour.events.size - 1}", + text = "${eventIndex + 1} / ${tour.events.size}", fontSize = 24.sp, - fontWeight = FontWeight.Bold, textAlign = TextAlign.Center ) } } - /*Row( - modifier = Modifier.fillMaxWidth(), - horizontalArrangement = Arrangement.Center - ) { - Box( - modifier = Modifier - .padding(contentPadding) - ) { - EventDetail(event = fromEvent) - } - }*/ Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.Center @@ -130,14 +118,14 @@ fun PortraitLayout( modifier = Modifier .padding(contentPadding) ) { - EventDetail(event = toEvent) + EventDetail(event) } } Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.Center ) { - if (!isLastLeg) { + if (!isLastEvent) { Box( modifier = Modifier .padding(contentPadding) @@ -340,44 +328,92 @@ fun TourDetail( @Composable fun EventDetail(event: Event) { + var scheduledTime = "" + var city = "" + var street = "" + var houseNumber = "" + var isPickup = false + var firstName = "" + var lastName = "" + var phone = "" + + try { + scheduledTime = event.scheduled_time.split("T")[1].substring(0, 5) + city = event.city + street = event.street + houseNumber = event.house_number + isPickup = event.is_pickup + firstName = event.first_name + lastName = event.last_name + phone = event.phone + } catch (e: Exception) { + Log.d("Exception", "Failed to read event details") + return + } + Column { Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.Center ) { Text( - text = event.scheduled_time.split("T")[1].substring(0, 5), + text = scheduledTime, fontSize = 24.sp, textAlign = TextAlign.Center ) } - Row( - modifier = Modifier.fillMaxWidth(), - horizontalArrangement = Arrangement.Center - ) { - Text( - text = event.city, - fontSize = 24.sp, - textAlign = TextAlign.Center - ) - } - Row( - modifier = Modifier.fillMaxWidth(), - horizontalArrangement = Arrangement.Center - ) { - Text( - text = event.street + " " + event.house_number, - fontSize = 24.sp, - textAlign = TextAlign.Center - ) + + if (city == "" || street == "") { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = "Fehler: Keine Addresse", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + } else { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = city, + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = "$street $houseNumber", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } } - if (event.is_pickup) { + + if (isPickup) { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center + ) { + Text( + text = "$lastName, $firstName", + fontSize = 24.sp, + textAlign = TextAlign.Center + ) + } Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.Center ) { Text( - text = event.last_name + ", " + event.first_name, + text = phone, fontSize = 24.sp, textAlign = TextAlign.Center ) diff --git a/driver-app/app/src/main/java/de/motis/prima/Tours.kt b/driver-app/app/src/main/java/de/motis/prima/Tours.kt index 97030cd7..50c142bf 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Tours.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Tours.kt @@ -47,13 +47,14 @@ import de.motis.prima.app.DriversApp import de.motis.prima.services.Api import de.motis.prima.services.CookieStore import de.motis.prima.services.Tour -import de.motis.prima.services.Vehicle import kotlinx.coroutines.flow.MutableSharedFlow import kotlinx.coroutines.flow.asSharedFlow import kotlinx.coroutines.launch import retrofit2.Call import retrofit2.Callback import retrofit2.Response +import java.text.SimpleDateFormat +import java.util.Date class ToursViewModel : ViewModel() { private val cookieStore: CookieStore = CookieStore(DriversApp.instance) @@ -71,9 +72,11 @@ class ToursViewModel : ViewModel() { fetchTours() } - private fun fetchTours() { + fun fetchTours() { + val currentDate = SimpleDateFormat("yyyy-MM-dd").format(Date()) + Log.d("date", currentDate) viewModelScope.launch { - Api.apiService.getTours().enqueue(object : Callback> { + Api.apiService.getTours(currentDate).enqueue(object : Callback> { override fun onResponse(call: Call>, response: Response>) { if (response.isSuccessful) { tours.value = response.body() ?: emptyList() @@ -107,9 +110,11 @@ class ToursViewModel : ViewModel() { fun Tours( navController: NavController, vehiclesViewModel: VehiclesViewModel, - viewModel: ToursViewModel //= androidx.lifecycle.viewmodel.compose.viewModel() + viewModel: ToursViewModel ) { LaunchedEffect(key1 = viewModel) { + viewModel.fetchTours() + Log.d("fetch", "tours") launch { viewModel.logoutEvent.collect { Log.d("Logout", "Logout event triggered.") @@ -197,6 +202,7 @@ fun Tours( val toursForVehicle = viewModel.tours.value.filter { t -> t.vehicle_id == vehiclesViewModel.selectedVehicleId } + Log.d("test", viewModel.tours.value.toString()) items(items = toursForVehicle, itemContent = { tour -> ConstraintLayout(modifier = Modifier.clickable { //navController.navigate("legs/${tour.tour_id}/0") diff --git a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt index 01b50229..8279ea50 100644 --- a/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt +++ b/driver-app/app/src/main/java/de/motis/prima/Vehicles.kt @@ -69,7 +69,8 @@ class VehiclesViewModel : ViewModel() { fetchVehicles() } - private fun fetchVehicles() { + fun fetchVehicles() { + Log.d("test", "fetch vehicles") viewModelScope.launch { Api.apiService.getVehicles().enqueue(object : Callback> { override fun onResponse(call: Call>, response: Response>) { @@ -105,9 +106,10 @@ class VehiclesViewModel : ViewModel() { @Composable fun Vehicles( navController: NavController, - viewModel: VehiclesViewModel //= androidx.lifecycle.viewmodel.compose.viewModel() + viewModel: VehiclesViewModel ) { LaunchedEffect(key1 = viewModel) { + viewModel.fetchVehicles() launch { viewModel.logoutEvent.collect { Log.d("Logout", "Logout event triggered.") @@ -186,7 +188,7 @@ fun Vehicles( modifier = Modifier.fillMaxSize(), contentAlignment = Alignment.Center // Center content within the Box ) { - Text(vehicle.plate, fontSize = 24.sp, fontWeight = FontWeight.Bold) + Text(vehicle.license_plate, fontSize = 24.sp, fontWeight = FontWeight.Bold) } } } diff --git a/driver-app/app/src/main/java/de/motis/prima/services/Api.kt b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt index 0a5543d3..cb894cd4 100644 --- a/driver-app/app/src/main/java/de/motis/prima/services/Api.kt +++ b/driver-app/app/src/main/java/de/motis/prima/services/Api.kt @@ -8,6 +8,7 @@ import retrofit2.http.Field import retrofit2.http.FormUrlEncoded import retrofit2.http.GET import retrofit2.http.POST +import retrofit2.http.Query import java.util.Date interface ApiService { @@ -22,7 +23,7 @@ interface ApiService { fun getVehicles() : Call> @GET("api/tour") - fun getTours() : Call> + fun getTours(@Query("date") currentDate: String) : Call> } object Api { @@ -43,7 +44,12 @@ data class LoginResponse( data class Vehicle( val id: Int, - val plate: String + val license_plate: String, + val company: Int, + val seats: Int, + val wheelchair_capacity: Int, + val bike_capacity: Int, + val storage_space: Int ) data class Event( diff --git a/driver-app/app/src/main/res/values-night/themes.xml b/driver-app/app/src/main/res/values-night/themes.xml index 90a777e6..c8d2d108 100644 --- a/driver-app/app/src/main/res/values-night/themes.xml +++ b/driver-app/app/src/main/res/values-night/themes.xml @@ -1,6 +1,6 @@ -