diff --git a/.gitignore b/.gitignore index d3bc52cfb8..89c07647f5 100644 --- a/.gitignore +++ b/.gitignore @@ -270,6 +270,7 @@ modules/blogging/app/Volo.BloggingTestApp/Logs/*.* modules/blogging/app/Volo.BloggingTestApp/wwwroot/files/*.* modules/docs/app/VoloDocs.Web/Logs/*.* modules/setting-management/app/Volo.Abp.SettingManagement.DemoApp/Logs/*.* +modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/** templates/module/app/MyCompanyName.MyProjectName.DemoApp/Logs/*.* templates/module/aspnet-core/host/MyCompanyName.MyProjectName.Blazor.Server.Host/Logs/logs.txt templates/mvc/src/MyCompanyName.MyProjectName.Web/Logs/*.* diff --git a/Directory.Packages.props b/Directory.Packages.props index 7034c62588..1114d54cb3 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -117,12 +117,12 @@ - - - - + + + + - + @@ -183,10 +183,10 @@ - - - - + + + + diff --git a/docs/en/Community-Articles/2026-03-10-Operation-Rate-Limiting-in-ABP-Framework/POST.md b/docs/en/Community-Articles/2026-03-10-Operation-Rate-Limiting-in-ABP-Framework/POST.md index 91a9e26aff..d3a851247f 100644 --- a/docs/en/Community-Articles/2026-03-10-Operation-Rate-Limiting-in-ABP-Framework/POST.md +++ b/docs/en/Community-Articles/2026-03-10-Operation-Rate-Limiting-in-ABP-Framework/POST.md @@ -1,4 +1,4 @@ -# Operation Rate Limiting in ABP Framework +# Operation Rate Limiting in ABP Almost every user-facing system eventually runs into the same problem: **some operations cannot be allowed to run without limits**. @@ -24,15 +24,9 @@ Real-world requirements tend to look like this: The pattern is clear: the identity being throttled is a **business identity** — a user, a phone number, a resource ID — not an IP address. And the action being throttled is a **business operation**, not an HTTP request. -ABP Framework's **Operation Rate Limiting** module is built for exactly this. It lets you enforce limits directly in your application or domain layer, with full awareness of who is doing what. +ABP's **Operation Rate Limiting** module is built for exactly this. It lets you enforce limits directly in your application or domain layer, with full awareness of who is doing what. -Add the package to your project: - -```bash -abp add-package Volo.Abp.OperationRateLimiting -``` - -> Operation Rate Limiting is available starting from **ABP Framework 10.3**. See the [pull request](https://github.com/abpframework/abp/pull/25024) for details. +This module is used by the Account (Pro) modules internally and comes pre-installed in the latest startup templates. You must have an [ABP Team or a higher license](https://abp.io/pricing) to use this module. ## Defining a Policy @@ -66,7 +60,7 @@ public class SmsAppService : ApplicationService _rateLimitChecker = rateLimitChecker; } - public async Task SendCodeAsync(string phoneNumber) + public virtual async Task SendCodeAsync(string phoneNumber) { await _rateLimitChecker.CheckAsync("SendSmsCode", phoneNumber); @@ -77,6 +71,74 @@ public class SmsAppService : ApplicationService `CheckAsync` checks the current usage against the limit and throws `AbpOperationRateLimitingException` (HTTP 429) if the limit is already exceeded. If the check passes, it then increments the counter and proceeds. ABP's exception pipeline catches this automatically and returns a standard error response. Put `CheckAsync` first — the rate limit check is the gate, and everything else only runs if it passes. +## Declarative Usage with `[OperationRateLimiting]` + +The explicit `CheckAsync` approach is useful when you need fine-grained control — for example, when you want to check the limit conditionally, or when the parameter value comes from somewhere other than a method argument. But for the common case where you simply want to enforce a policy on every invocation of a specific method, there's a cleaner way: the `[OperationRateLimiting]` attribute. + +```csharp +public class SmsAppService : ApplicationService +{ + [OperationRateLimiting("SendSmsCode")] + public virtual async Task SendCodeAsync([RateLimitingParameter] string phoneNumber) + { + // Rate limit is enforced automatically — no manual CheckAsync needed. + await _smsSender.SendAsync(phoneNumber, GenerateCode()); + } +} +``` + +The attribute works on both **Application Service methods** (via ABP's interceptor) and **MVC Controller actions** (via an action filter). No manual injection of `IOperationRateLimitingChecker` required. + +### Providing the Partition Key + +When using the attribute, the partition key is resolved from the method's parameters automatically: + +- Mark a parameter with `[RateLimitingParameter]` to use its `ToString()` value as the key — this is the most common case when the key is a single primitive like a phone number or email. +- Have your input DTO implement `IHasOperationRateLimitingParameter` and provide a `GetPartitionParameter()` method — useful when the key is a property buried inside a complex input object. + +```csharp +public class SendSmsCodeInput : IHasOperationRateLimitingParameter +{ + public string PhoneNumber { get; set; } + public string Language { get; set; } + + public string? GetPartitionParameter() => PhoneNumber; +} + +[OperationRateLimiting("SendSmsCode")] +public virtual async Task SendCodeAsync(SendSmsCodeInput input) +{ + // input.GetPartitionParameter() = input.PhoneNumber is used as the partition key. +} +``` + +If neither is provided, `Parameter` is `null` — which is perfectly valid for policies that use `PartitionByCurrentUser`, `PartitionByClientIp`, or similar partition types that don't rely on an explicit value. + +```csharp +// Policy uses PartitionByCurrentUser — no partition key needed. +[OperationRateLimiting("GenerateReport")] +public virtual async Task GenerateMonthlyReportAsync() +{ + // Rate limit is checked per current user, automatically. +} +``` + +> The resolution order is: `[RateLimitingParameter]` first, then `IHasOperationRateLimitingParameter`, then `null`. If the method has parameters but none is resolved, a warning is logged to help you catch the misconfiguration early. + +You can also place `[OperationRateLimiting]` on the class itself to apply the policy to all public methods: + +```csharp +[OperationRateLimiting("MyServiceLimit")] +public class MyAppService : ApplicationService +{ + public virtual async Task MethodAAsync([RateLimitingParameter] string key) { ... } + + public virtual async Task MethodBAsync([RateLimitingParameter] string key) { ... } +} +``` + +A method-level attribute always takes precedence over the class-level one. + ## Choosing a Partition Type The partition type controls **how counters are isolated from each other** — it's the most important decision when setting up a policy, because it determines *what dimension you're counting across*. @@ -87,7 +149,7 @@ Getting this wrong can make your rate limiting completely ineffective. Using `Pa - **`PartitionByCurrentUser`** — uses the authenticated user's ID, with no value to pass. Perfect for "each user gets N per day" scenarios where user identity is all you need. - **`PartitionByClientIp`** — uses the client's IP address. Don't rely on this alone — it's too easy to rotate. Use it as a secondary layer alongside another partition type, as in the login example below. - **`PartitionByEmail`** and **`PartitionByPhoneNumber`** — designed for pre-authentication flows where the user isn't logged in yet. They prefer the `Parameter` value you explicitly pass, and fall back to the current user's email or phone number if none is provided. -- **`PartitionBy`** — a custom async delegate that can produce any partition key you need. When the built-in options don't fit, you're free to implement whatever logic makes sense: look up a resource's owner in the database, derive a key from the user's subscription tier, partition by tenant — anything that returns a string. +- **`PartitionBy`** — a named custom resolver that can produce any partition key you need. Register a resolver function under a unique name via `options.AddPartitionKeyResolver("MyResolver", ctx => ...)`, then reference it by name: `.PartitionBy("MyResolver")`. You can also register and reference in one step: `.PartitionBy("MyResolver", ctx => ...)`. When the built-in options don't fit, you're free to implement whatever logic makes sense: look up a resource's owner in the database, derive a key from the user's subscription tier, partition by tenant — anything that returns a string. Because the resolver is stored by name (not as an anonymous delegate), it can be serialized and managed from a UI or database. > The rule of thumb: partition by the identity of whoever's behavior you're trying to limit. @@ -114,6 +176,70 @@ The two counters are completely independent. If `alice` fails 5 times, her accou When multiple rules are present, the module uses a two-phase approach: it checks all rules first, and only increments counters if every rule passes. This prevents a rule from consuming quota on a request that would have been rejected by another rule anyway. +## Customizing Policies from Reusable Modules + +ABP modules (including your own) can ship with built-in rate limiting policies. For example, an Account module might define a `"Account.SendPasswordResetCode"` policy with conservative defaults that make sense for most applications. When you need different rules in your specific application, you have two options. + +**Complete replacement with `AddPolicy`:** call `AddPolicy` with the same name and the second registration wins, replacing all rules from the module: + +```csharp +Configure(options => +{ + options.AddPolicy("Account.SendPasswordResetCode", policy => + { + policy.AddRule(rule => rule + .WithFixedWindow(TimeSpan.FromMinutes(5), maxCount: 3) + .PartitionByEmail()); + }); +}); +``` + +**Partial modification with `ConfigurePolicy`:** when you only want to tweak part of a policy — change the error code, add a secondary rule, or tighten the window — use `ConfigurePolicy`. The builder starts pre-populated with the module's existing rules, so you only express what changes. + +For example, keep the module's default rules but assign your own localized error code: + +```csharp +Configure(options => +{ + options.ConfigurePolicy("Account.SendPasswordResetCode", policy => + { + policy.WithErrorCode("MyApp:PasswordResetLimit"); + }); +}); +``` + +Or add a secondary IP-based rule on top of what the module already defined, without touching it: + +```csharp +Configure(options => +{ + options.ConfigurePolicy("Account.SendPasswordResetCode", policy => + { + policy.AddRule(rule => rule + .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 20) + .PartitionByClientIp()); + }); +}); +``` + +If you want a clean slate, call `ClearRules()` first and then define entirely new rules — this gives you the same result as `AddPolicy` but makes the intent explicit: + +```csharp +Configure(options => +{ + options.ConfigurePolicy("Account.SendPasswordResetCode", policy => + { + policy.ClearRules() + .WithFixedWindow(TimeSpan.FromMinutes(10), maxCount: 5) + .PartitionByEmail(); + }); +}); +``` + +`ConfigurePolicy` throws if the policy name doesn't exist — which catches typos at startup rather than silently doing nothing. + +The general rule: use `AddPolicy` for full replacements, `ConfigurePolicy` for surgical modifications. + ## Beyond Just Checking Not every scenario calls for throwing an exception. `IOperationRateLimitingChecker` provides three additional methods for more nuanced control. @@ -179,10 +305,10 @@ public override void ConfigureServices(ServiceConfigurationContext context) ## Summary -ABP's Operation Rate Limiting fills the gap that ASP.NET Core's HTTP middleware can't: rate limiting with real awareness of *who* is doing *what*. Define a named policy, pick a time window, a max count, and a partition type. Call `CheckAsync` wherever you need it. Counter storage, distributed locking, and exception handling are all taken care of. +ABP's Operation Rate Limiting fills the gap that ASP.NET Core's HTTP middleware can't: rate limiting with real awareness of *who* is doing *what*. Define a named policy, pick a time window, a max count, and a partition type. Then either call `CheckAsync` explicitly, or just add `[OperationRateLimiting]` to your method and let the framework handle the rest. Counter storage, distributed locking, and exception handling are all taken care of. ## References -- [Operation Rate Limiting](https://abp.io/docs/latest/framework/infrastructure/operation-rate-limiting) +- [Operation Rate Limiting (Pro)](https://abp.io/docs/latest/modules/operation-rate-limiting) - [ASP.NET Core Rate Limiting Middleware](https://learn.microsoft.com/en-us/aspnet/core/performance/rate-limit) - [Exception Handling](https://abp.io/docs/latest/framework/fundamentals/exception-handling) diff --git a/docs/en/Community-Articles/2026-03-10-Tutorial-Validator/article.md b/docs/en/Community-Articles/2026-03-10-Tutorial-Validator/article.md index 2d1b60ebd2..43dee7c712 100644 --- a/docs/en/Community-Articles/2026-03-10-Tutorial-Validator/article.md +++ b/docs/en/Community-Articles/2026-03-10-Tutorial-Validator/article.md @@ -1,49 +1,56 @@ -# How We Built TutorialValidator to Automatically Validate Documentation Tutorials +# Automatically Validate Your Documentation: How We Built a Tutorial Validator -Writing a tutorial is hard. Keeping it correct over time is even harder. +Writing a tutorial is difficult. Keeping technical documentation accurate over time is even harder. +If you maintain developer documentation, you probably know the problem: a tutorial that worked a few months ago can silently break after a framework update, dependency change, or a small missing line in a code snippet. +New developers follow the guide, encounter an error, and quickly lose trust in the documentation. +To solve this problem, we built the tutorial validator — an open-source AI-powered tutorial validator that automatically verifies whether a software tutorial actually works from start to finish. +Instead of manually reviewing documentation, the tutorial validator behaves like a real developer following your guide step by step. +It reads instructions, runs commands, writes files, executes the application, and verifies expected results. +We initially created it to automatically validate ABP Framework tutorials, then released it as an open-source tool so anyone can use it to test their own documentation. -If you maintain technical documentation, you probably know this pain: a tutorial that worked three months ago can quietly break after a framework update, a package change, or a small missing line in a code snippet. New developers follow the steps, hit an error, and lose trust in the docs. -That exact problem is why we built **TutorialValidator**. +![the tutorial validator Orchestrator](docs/images/image.png) -TutorialValidator is an open-source, AI-powered tool that checks whether a software tutorial actually works from start to finish. You give it a tutorial URL, and it behaves like a real developer following the guide: it reads each step, executes commands, writes files, runs the app, and verifies expected results. -We first created it to validate ABP Framework tutorials internally, then shared it publicly so anyone can use it with their own tutorials. +## The Problem: Broken Tutorials in Technical Documentation -![TutorialValidator Orchestrator](docs/images/image.png) +Many documentation issues are difficult to catch during normal reviews. +Common problems include: -## What Problem Does It Solve? +- A command assumes a file already exists -Most documentation issues are not obvious during review: +- A code snippet misses a namespace or import -- A command assumes a file that has not been created yet -- A code sample misses a namespace or import -- A step relies on hidden context that is never explained -- An endpoint is expected to respond, but does not +- A tutorial step relies on hidden context -Traditional proofreading catches wording problems. TutorialValidator targets **execution problems**. +- An endpoint is expected to respond but fails -It turns tutorials into something testable. +- A dependency version changed and breaks the project -## How It Works (Simple View) -TutorialValidator runs in three phases: +Traditional proofreading tools only check grammar or wording. +**The tutorial validator focuses on execution correctness.** +It treats tutorials like testable workflows, ensuring that every step works exactly as written. + +## How the Tutorial Validator Works? + +the tutorial validator validates tutorials using a three-stage pipeline: 1. **Analyst**: Scrapes tutorial pages and converts instructions into a structured test plan 2. **Executor**: Follows the plan step by step in a clean environment 3. **Reporter**: Produces a clear result summary and optional notifications -![TutorialValidator Analyst](docs/images/image-1.png) +![the tutorial validator Analyst](docs/images/image-1.png) +It identifies commands, code edits, HTTP requests, and expected outcomes. The key idea is simple: if a developer would need to do it, the validator does it too. - That includes running terminal commands, editing files, checking HTTP responses, and validating build outcomes. -![TutorialValidator Executor](docs/images/image-2.png) +![the tutorial validator Executor](docs/images/image-2.png) -## Why This Approach Is Useful +## Why Automated Tutorial Validation Matters? -TutorialValidator is designed for practical documentation quality, not just technical experimentation. +The tutorial validator is designed for practical documentation quality, not just technical experimentation. - **Catches real-world breakages early** before readers report them - **Creates repeatable validation** instead of one-off manual checks @@ -54,7 +61,7 @@ For example, `junior` and `mid` personas are great for spotting unclear document ## Built for ABP, Open for Everyone -Even though TutorialValidator was born from ABP documentation needs, it is not limited to ABP content. +Although TutorialValidator was originally built to validate **ABP Framework tutorials**, it works with **any publicly accessible software tutorial**. It supports validating any publicly accessible software tutorial and can run in: @@ -63,28 +70,44 @@ It supports validating any publicly accessible software tutorial and can run in: It also supports multiple AI providers, including OpenAI, Azure OpenAI, and OpenAI-compatible endpoints. -## Open Source and Extensible +## Open Source and Easily Extensible + +The tutorial validator is designed with a modular architecture. +The project consists of multiple focused components: + +- **Core** – shared models and contracts +- **Analyst** – tutorial scraping and step extraction +- **Executor** – step-by-step execution engine +- **Orchestrator** – workflow coordination +- **Reporter** – notifications and result summaries -TutorialValidator is structured as multiple focused projects: +This architecture makes it easy to extend the validator with: -- Core models and shared contracts -- Analyst for scraping and plan extraction -- Executor for step-by-step validation -- Orchestrator for end-to-end workflow -- Reporter for Email/Discord notifications +- new step types +- additional AI providers +- custom reporting integrations This architecture keeps the project easy to understand and extend. Teams can add new step types, plugins, or reporting channels based on their own workflow. ## Final Thoughts -Documentation is part of the product experience. When tutorials fail, trust fails. +Documentation is a critical part of the product experience. +When tutorials break, developer trust breaks too. +TutorialValidator helps teams move from: + +> We believe this tutorial works 🙄 + +to -TutorialValidator helps teams move from “we think this tutorial works” to “we verified it works.” +> We verified this tutorial works ✅ +If your team maintains **technical tutorials, developer guides, or framework documentation**, automated tutorial validation can provide a powerful safety net. + +Documentation is part of the product experience. When tutorials fail, trust fails. If your team maintains technical tutorials, this project can give you a practical safety net and a repeatable quality process. --- -Repository: https://github.com/AbpFramework/TutorialValidator +You can find the source-code of the tutorial validator at this repo 👉 https://github.com/abpframework/tutorial-validator -If you try it in your own docs pipeline, we would love to hear your feedback and ideas. +We would love to hear your feedback, ideas and waiting PRs to improve this application. diff --git a/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/POST.md b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/POST.md new file mode 100644 index 0000000000..a12779289c --- /dev/null +++ b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/POST.md @@ -0,0 +1,185 @@ +# Secure Client Authentication with private_key_jwt in ABP 10.3 + +If you've built a confidential client with ABP's OpenIddict module, you know the drill: create an application in the management UI, set a `client_id`, generate a `client_secret`, and paste that secret into your client's `appsettings.json` or environment variables. It works. It's familiar. And for a lot of projects, it's perfectly fine. + +But `client_secret` is a **shared secret** — and shared secrets carry an uncomfortable truth: the same value exists in two places at once. The authorization server stores a hash of it in the database, and your client stores the raw value in configuration. That means two potential leak points. Worse, the secret has no inherent identity. Anyone who obtains the string can impersonate your client and the server has no way to tell the difference. + +For many teams, this tradeoff is acceptable. But certain scenarios make it hard to ignore: + +- **Microservice-to-microservice calls**: A backend mesh of a dozen services, each with its own `client_secret` scattered across deployment configs and CI/CD pipelines. Rotating them across environments without missing one becomes a coordination problem. +- **Multi-tenant SaaS platforms**: Every tenant's client application deserves truly isolated credentials. With shared secrets, the database holds hashed copies for all tenants — a breach of that table is a breach of everyone's credentials. +- **Financial-grade API (FAPI) compliance**: Standards like [FAPI 2.0](https://openid.net/specs/fapi-2_0-security-profile.html) explicitly require asymmetric client authentication. `client_secret` doesn't make the cut. +- **Zero-trust architectures**: In a zero-trust model, identity must be cryptographically provable, not based on a string that can be copied and pasted. + +The underlying problem is that a shared secret is just a password. It can be stolen, replicated, and used without leaving a trace. The fix has existed in cryptography for decades: **asymmetric keys**. + +With asymmetric key authentication, the client generates a key pair. The public key is registered with the authorization server. The private key never leaves the client. Each time the client needs a token, it signs a short-lived JWT — called a _client assertion_ — with the private key. The server verifies the signature using the registered public key. There is no secret on the server side that could be used to forge a request, because the private key is never transmitted or stored remotely. + +This is exactly what the **`private_key_jwt`** client authentication method, defined in [OpenID Connect Core](https://openid.net/specs/openid-connect-core-1_0.html#ClientAuthentication), provides. ABP's OpenIddict module now supports it end-to-end: you register a **JSON Web Key Set (JWKS)** containing your public key through the application management UI (ABP Commercial), and your client authenticates using the corresponding private key. The key generation tooling (`abp generate-jwks`) ships as part of the open-source ABP CLI. + +> This feature is available starting from **ABP Framework 10.3**. + +## How It Works + +The flow is straightforward: + +1. The client holds an RSA key pair — **private key** (kept locally) and **public key** (registered on the authorization server as a JWKS). +2. On each token request, the client uses the private key to sign a JWT with a short expiry and a unique `jti` claim. +3. The authorization server verifies the signature against the registered public key and issues a token if it checks out. + +The private key never leaves the client. Even if someone obtains the authorization server's database, there's nothing there that can be used to generate a valid client assertion. + +## Generating a Key Pair + +ABP CLI includes a `generate-jwks` command that creates an RSA key pair in the right formats: + +```bash +abp generate-jwks +``` + +This produces two files in the current directory: + +- `jwks.json` — the public key in JWKS format, to be uploaded to the server +- `jwks-private.pem` — the private key in PKCS#8 PEM format, to be kept on the client + +You can customize the output directory, key size, and signing algorithm: + +```bash +abp generate-jwks --alg RS512 --key-size 4096 -o ./keys -f myapp +``` + +> Supported algorithms: `RS256`, `RS384`, `RS512`, `PS256`, `PS384`, `PS512`. The default is `RS256` with a 2048-bit key. + +The command also prints the contents of `jwks.json` to the console so you can copy it directly. + +## Registering the JWKS in the Management UI + +Open **OpenIddict → Applications** in the ABP admin panel and create or edit a confidential application (Client Type: `Confidential`). + +In the **Client authentication method** section, you'll find the new **JSON Web Key Set** field. + +![](./create-edit-ui.png) + +Paste the contents of `jwks.json` into the **JSON Web Key Set** field: + +```json +{ + "keys": [ + { + "kty": "RSA", + "use": "sig", + "kid": "6444...", + "alg": "RS256", + "n": "tx...", + "e": "AQAB" + } + ] +} +``` + +Save the application. It's now configured for `private_key_jwt` authentication. You can set either `client_secret` or a JWKS, or both — ABP enforces that a confidential application always has at least one credential. + +## Requesting a Token with the Private Key + +On the client side, each token request requires building a _client assertion_ JWT signed with the private key. Here's a complete `client_credentials` example: + +```csharp +// Discover the authorization server endpoints (including the issuer URI). +var client = new HttpClient(); +var configuration = await client.GetDiscoveryDocumentAsync("https://your-auth-server/"); + +// Load the private key generated by `abp generate-jwks`. +using var rsaKey = RSA.Create(); +rsaKey.ImportFromPem(await File.ReadAllTextAsync("jwks-private.pem")); + +// Read the kid from jwks.json so it stays in sync with the server-registered public key. +string? signingKid = null; +if (File.Exists("jwks.json")) +{ + using var jwksDoc = JsonDocument.Parse(await File.ReadAllTextAsync("jwks.json")); + if (jwksDoc.RootElement.TryGetProperty("keys", out var keysElem) && + keysElem.GetArrayLength() > 0 && + keysElem[0].TryGetProperty("kid", out var kidElem)) + { + signingKid = kidElem.GetString(); + } +} + +var signingKey = new RsaSecurityKey(rsaKey) { KeyId = signingKid }; +var signingCredentials = new SigningCredentials(signingKey, SecurityAlgorithms.RsaSha256); + +// Build the client assertion JWT. +var now = DateTime.UtcNow; +var jwtHandler = new JsonWebTokenHandler(); +var clientAssertionToken = jwtHandler.CreateToken(new SecurityTokenDescriptor +{ + // OpenIddict requires typ = "client-authentication+jwt" for client assertion JWTs. + TokenType = "client-authentication+jwt", + Issuer = "MyClientId", + // aud must equal the authorization server's issuer URI from the discovery document, + // not the token endpoint URL. + Audience = configuration.Issuer, + Subject = new ClaimsIdentity(new[] + { + new Claim(JwtRegisteredClaimNames.Sub, "MyClientId"), + new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()), + }), + IssuedAt = now, + NotBefore = now, + Expires = now.AddMinutes(5), + SigningCredentials = signingCredentials, +}); + +// Request a token using the client_credentials flow. +var tokenResponse = await client.RequestClientCredentialsTokenAsync( + new ClientCredentialsTokenRequest + { + Address = configuration.TokenEndpoint, + ClientId = "MyClientId", + ClientCredentialStyle = ClientCredentialStyle.PostBody, + ClientAssertion = new ClientAssertion + { + Type = OidcConstants.ClientAssertionTypes.JwtBearer, + Value = clientAssertionToken, + }, + Scope = "MyAPI", + }); +``` + +A few things worth paying attention to: + +- **`TokenType`** must be `"client-authentication+jwt"`. OpenIddict rejects client assertion JWTs that don't carry this header. +- **`Audience`** must match the authorization server's issuer URI exactly — use `configuration.Issuer` from the discovery document, not the token endpoint URL. +- **`Jti`** must be unique per request to prevent replay attacks. +- Keep **`Expires`** short (five minutes or less). A client assertion is a one-time proof of identity, not a long-lived credential. + +This example uses [IdentityModel](https://github.com/IdentityModel/IdentityModel) for the token request helpers and [Microsoft.IdentityModel.JsonWebTokens](https://www.nuget.org/packages/Microsoft.IdentityModel.JsonWebTokens) for JWT creation. + +## Key Rotation Without Downtime + +One of the practical advantages of JWKS is that it can hold multiple public keys simultaneously. This makes **zero-downtime key rotation** straightforward: + +1. Run `abp generate-jwks` to produce a new key pair. +2. Append the new public key to the `keys` array in your existing `jwks.json` and update the JWKS in the management UI. +3. Switch the client to sign assertions with the new private key. +4. Once the transition is complete, remove the old public key from the JWKS. + +During the transition window, both the old and new public keys are registered on the server, so any in-flight requests signed with either key will still validate correctly. + +## Summary + +To use `private_key_jwt` authentication in an ABP Pro application: + +1. Run `abp generate-jwks` to generate an RSA key pair. +2. Paste the `jwks.json` contents into the **JSON Web Key Set** field in the OpenIddict application management UI. +3. On the client side, sign a short-lived _client assertion_ JWT with the private key — making sure to set the correct `typ`, `aud` (from the discovery document), and a unique `jti` — then use it to request a token. + +ABP handles public key storage and validation automatically. OpenIddict handles the signature verification on the token endpoint. As a developer, you only need to keep the private key file secure — there's no shared secret to synchronize between client and server. + +## References + +- [OpenID Connect Core — Client Authentication](https://openid.net/specs/openid-connect-core-1_0.html#ClientAuthentication) +- [RFC 7523 — JWT Profile for Client Authentication](https://datatracker.ietf.org/doc/html/rfc7523) +- [ABP OpenIddict Module Documentation](https://abp.io/docs/latest/modules/openiddict) +- [ABP CLI Documentation](https://abp.io/docs/latest/cli) +- [OpenIddict Documentation](https://documentation.openiddict.com/) diff --git a/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/cover.png b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/cover.png new file mode 100644 index 0000000000..e268703fb6 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/cover.png differ diff --git a/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/create-edit-ui.png b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/create-edit-ui.png new file mode 100644 index 0000000000..1ca04b12bd Binary files /dev/null and b/docs/en/Community-Articles/2026-03-12-OpenIddict-private-key-jwt/create-edit-ui.png differ diff --git a/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/POST.md b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/POST.md new file mode 100644 index 0000000000..6bf5ed5774 --- /dev/null +++ b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/POST.md @@ -0,0 +1,151 @@ +# One Endpoint, Many AI Clients: Turning ABP Workspaces into OpenAI-Compatible Models + +ABP's AI Management module already makes it easy to define and manage AI workspaces (provider, model, API key/base URL, system prompt, permissions, MCP tools, RAG settings, and more). With **ABP v10.2**, there is a major addition: you can now expose those workspaces through **OpenAI-compatible endpoints** under `/v1`. + +That changes the integration story in a practical way. Instead of wiring every external tool directly to a provider, you can point those tools to ABP and keep runtime decisions centralized in one place. + +In this post, we will walk through a practical setup with **AnythingLLM** and show why this pattern is useful in real projects. + +Before we get into the details, here's a quick look at the full flow in action: + +## See It in Action: AnythingLLM + ABP + +The demo below shows the full flow: connecting an OpenAI-compatible client to ABP, selecting a workspace-backed model, and sending a successful chat request through `/v1`. + +![ABP AI Management OpenAI-compatible endpoints demo](./openai-compatible-endpoints-demo.gif) + +## Why This Is a Big Deal + +Many teams end up with AI configuration spread across multiple clients and services. Updating providers, rotating keys, or changing model behavior can become operationally messy. + +With ABP in front of your AI traffic: + +- Clients keep speaking the familiar OpenAI contract. +- ABP resolves the requested `model` to a workspace. +- The workspace decides which provider/model settings are actually used. + +This gives you a clean split: standardized client integration outside, governed AI configuration inside. + +## Key Concept: Workspace = Model + +OpenAI-compatible clients send a `model` value. +In ABP AI Management, that `model` maps to a **workspace name**. + +**For example:** + +- Workspace name: `SupportAgent` +- Client request model: `SupportAgent` + +When the client calls `/v1/chat/completions` with `"model": "SupportAgent"`, ABP routes the request to that workspace and applies that workspace's provider (OpenAI, Ollama etc.) and model configuration. + +This is the main mental model to keep in mind while integrating any OpenAI-compatible tool with ABP. + +## Endpoints Exposed by ABP v10.2 + +The AI Management module exposes OpenAI-compatible REST endpoints at `/v1`. + +| Endpoint | Method | Description | +| ---------------------------- | ------ | ---------------------------------------------- | +| `/v1/chat/completions` | POST | Chat completions (streaming and non-streaming) | +| `/v1/completions` | POST | Legacy text completions | +| `/v1/models` | GET | List available models (workspaces) | +| `/v1/models/{modelId}` | GET | Get a single model (workspace) | +| `/v1/embeddings` | POST | Generate embeddings | +| `/v1/files` | GET | List files | +| `/v1/files` | POST | Upload a file | +| `/v1/files/{fileId}` | GET | Get file metadata | +| `/v1/files/{fileId}` | DELETE | Delete a file | +| `/v1/files/{fileId}/content` | GET | Download file content | + +All endpoints require `Authorization: Bearer `. + +## Quick Setup with AnythingLLM + +Before configuration, ensure: + +1. AI Management is installed and running in your ABP app. +2. At least one workspace is created and **active**. +3. You have a valid Bearer token for your ABP application. + +### 1) Get an access token + +Use any valid token accepted by your app. In a demo-style setup, token retrieval can look like this: + +```bash +curl -X POST http://localhost:44337/connect/token \ + -d "grant_type=password&username=admin&password=1q2w3E*&client_id=DemoApp_API&client_secret=1q2w3e*&scope=DemoApp" +``` + +Use the returned `access_token` as the API key value in your OpenAI-compatible client. + +### 2) Configure AnythingLLM as Generic OpenAI + +In **AnythingLLM -> Settings -> LLM Preference**, select **Generic OpenAI** and set: + +| Setting | Value | +| -------------------- | --------------------------- | +| Base URL | `http://localhost:44337/v1` | +| API Key | `` | +| Chat Model Selection | Select an active workspace | + +In most OpenAI-compatible UIs, the app adds `Bearer` automatically, so the API key field should contain only the raw token string. + +### 3) Optional: configure embeddings + +If you want RAG flows through ABP, go to **Settings -> Embedding Preference** and use the same Base URL/API key values. +Then select a workspace that has embedder settings configured. + +## Validate the Flow + +### List models (workspaces) + +```bash +curl http://localhost:44337/v1/models \ + -H "Authorization: Bearer " +``` + +### Chat completion + +```bash +curl -X POST http://localhost:44337/v1/chat/completions \ + -H "Authorization: Bearer " \ + -H "Content-Type: application/json" \ + -d '{ + "model": "MyWorkspace", + "messages": [ + { "role": "user", "content": "Hello from ABP OpenAI-compatible endpoint!" } + ] + }' +``` + +### Optional SDK check (Python) + +```python +from openai import OpenAI + +client = OpenAI( + base_url="http://localhost:44337/v1", + api_key="" +) + +response = client.chat.completions.create( + model="MyWorkspace", + messages=[{"role": "user", "content": "Hello!"}] +) + +print(response.choices[0].message.content) +``` + +## Where This Fits in Real Projects + +This approach is a strong fit when you want to: + +- Keep ABP as the central control plane for AI workspaces. +- Let client tools integrate through a standard OpenAI contract. +- Switch providers or model settings without rewriting client-side integration. + +If your team uses multiple AI clients, this pattern keeps integration simple while preserving control where it matters. + +## Learn More + +- [ABP AI Management Documentation](https://abp.io/docs/10.2/modules/ai-management) diff --git a/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/cover-image.png b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/cover-image.png new file mode 100644 index 0000000000..3024f341b4 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/cover-image.png differ diff --git a/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/openai-compatible-endpoints-demo.gif b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/openai-compatible-endpoints-demo.gif new file mode 100644 index 0000000000..e1c830087b Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-OpenAI-Compatible-Endpoints/openai-compatible-endpoints-demo.gif differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/POST.md b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/POST.md new file mode 100644 index 0000000000..dcb69c289d --- /dev/null +++ b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/POST.md @@ -0,0 +1,167 @@ +# Shared User Accounts in ABP Multi-Tenancy + +Multi-tenancy is built on **isolation** — isolated data, isolated permissions, isolated users. ABP's default behavior has always followed this assumption: one user belongs to exactly one tenant. Clean, simple, no ambiguity. For most SaaS applications, that's exactly what you want. (The new `TenantUserSharingStrategy` enum formally names this default behavior `Isolated`.) + +But isolation is **the system's** concern, not **the user's**. In practice, people's work doesn't always line up neatly with tenant boundaries. + +Think about a financial consultant who works with three different companies — each one a tenant in your system. Under the Isolated model, she needs three separate accounts, three passwords. Forgot which password goes with which company? Good luck. Worse, the system sees three unrelated people — there's nothing linking those accounts to the same human being. + +This comes up more often than you'd think: + +- In a **corporate group**, an IT admin manages multiple subsidiaries, each running as its own tenant. Every day means logging out, logging back in with different credentials, over and over +- A **SaaS platform's ops team** needs to hop into different customer tenants to debug issues. Each time they create a throwaway account, then delete it — or just share one account and lose all audit trail +- Some users resort to email aliases (`alice+company1@example.com`) to work around uniqueness constraints — that's not a solution, that's a hack + +The common thread here: the user's **identity** is global, but their **working context** is per-tenant. The problem isn't a technical limitation — it's that the Isolated assumption ("one user, one tenant") simply doesn't hold in these scenarios. + +What's needed is not "one account per tenant" but "one account, multiple tenants." + +ABP's **Shared User Accounts** (`TenantUserSharingStrategy.Shared`) does exactly this. It makes user identity global and turns tenants into workspaces that a user can join and switch between — similar to how one person can belong to multiple workspaces in Slack. + +> This is a **commercial** feature, available starting from **ABP 10.2**, provided by the Account.Pro and Identity.Pro modules. + +## Enabling the Shared Strategy + +A single configuration is all it takes: + +```csharp +Configure(options => +{ + options.IsEnabled = true; + options.UserSharingStrategy = TenantUserSharingStrategy.Shared; +}); +``` + +The most important behavior change after switching to Shared: **username and email uniqueness become global** instead of per-tenant. This follows naturally — if the same account needs to be recognized across tenants, its identifiers must be unique across the entire system. + +Security-related settings (2FA, account lockout, password policies, captcha, etc.) are also managed at the **Host** level. This makes sense too: if user identity is global, the security rules around it should be global as well. + +## One Account, Multiple Tenants + +With the Shared strategy enabled, the day-to-day user experience changes fundamentally. + +When a user is associated with only one tenant, the system recognizes it automatically and signs them in directly — the user doesn't even notice that tenants exist. When the user belongs to multiple tenants, the login flow presents a tenant selection screen after credentials are verified: + +![tenant-selection](./tenant-selection.png) + +After signing into a tenant, a tenant switcher appears in the user menu — click it anytime to jump to another tenant without signing out. ABP re-issues the authentication ticket (with the new `TenantId` in the claims) on each switch, so the permission system is fully independent per tenant. + +![switch-tenant](./switch-tenant.png) + +Users can also leave a tenant. Leaving doesn't delete the association record — it marks it as inactive. This preserves foreign key relationships with other entities. If the user is invited back later, the association is simply reactivated instead of recreated. + +Back to our earlier scenario: the financial consultant now has one account, one password. She picks which company to work in at login, switches between them during the day. The system knows it's the same person, and the audit log can trace her actions across every tenant. + +## Invitations + +Users don't just appear in a tenant — someone has to invite them. This is the core operation from the administrator's perspective. + +A tenant admin opens the invitation dialog, enters one or more email addresses (batch invitations are supported), and can pre-assign roles — so the user gets the right permissions the moment they join, no extra setup needed: + +![invite-user](./invite-user.png) + +The invited person receives an email with a link. What happens next depends on whether they already have an account. + +If they **already have an account**, they see a confirmation page and can join the tenant with a single click: + +![exist-user-accept](./exist-user-accept.png) + +If they **don't have an account yet**, the link takes them to a registration form. Once they register, they're automatically added to the tenant: + +![new-user-accept](./new-user-accept.png) + +Admins can also manage pending invitations at any time — resend emails or revoke invitations. + +> The invitation feature is also available under the Isolated strategy, but invited users can only join a single tenant. + +## Setting Up a New Tenant + +There's a notable shift in how new tenants are bootstrapped. + +Under the Isolated model, creating a tenant typically seeds an `admin` user automatically. With Shared, this no longer happens — because users are global, and it doesn't make sense to create one out of thin air for a specific tenant. + +Instead, you create the tenant first, then invite someone in and grant them the admin role. + +![invite-admin-user-to-join-tenant](./invite-admin-user-to-join-tenant.png) + +![invite-admin-user-to-join-tenant-modal](./invite-admin-user-to-join-tenant-modal.png) + +This is a natural fit — the admin is just a global user who happens to hold the admin role in this particular tenant. + +## Where Do Newly Registered Users Go? + +Under the Shared strategy, self-registration runs into an interesting problem: the system doesn't know which tenant the user wants to join. Without being signed in, tenant context is usually determined by subdomain or a tenant switcher on the login page — but for a brand-new user, those signals might not exist at all. + +So ABP's approach is: **don't establish any tenant association at registration time**. A newly registered user doesn't belong to any tenant, and doesn't belong to the Host either — this is an entirely new state. ABP still lets these users sign in, change their password, and manage their account, but they can't access any permission-protected features within a tenant. + +`AbpIdentityPendingTenantUserOptions.Strategy` controls what happens in this "pending" state. + +**CreateTenant** — automatically creates a tenant for the new user. This fits the "sign up and get your own workspace" pattern, like how Slack or Notion handles registration: you register, the system spins up a workspace for you. + +```csharp +Configure(options => +{ + options.Strategy = AbpIdentityPendingTenantUserStrategy.CreateTenant; +}); +``` + +![new-user-join-strategy-create-tenant](./new-user-join-strategy-create-tenant.png) + +**Inform** (the default) — shows a message telling the user to contact an administrator to join a tenant. This is the right choice for invite-only platforms where users must be brought in by an existing tenant admin. + +```csharp +Configure(options => +{ + options.Strategy = AbpIdentityPendingTenantUserStrategy.Inform; +}); +``` + +![new-user-join-strategy-inform](./new-user-join-strategy-inform.png) + +There's also a **Redirect** strategy that sends the user to a custom URL for more complex flows. + +> See the [official documentation](https://abp.io/docs/latest/modules/account/shared-user-accounts) for full configuration details. + +## Database Considerations + +The Shared strategy introduces some mechanisms and constraints at the database level that are worth understanding. + +### Global Uniqueness: Enforced in Code, Not by Database Indexes + +Username and email uniqueness checks must span all tenants. ABP disables the tenant filter (`TenantFilter.Disable()`) during validation and searches globally for conflicts. + +A notable design choice here: **global uniqueness is enforced at the application level, not through database unique indexes**. The reason is practical — in a database-per-tenant setup, users live in separate physical databases, so a cross-database unique index simply isn't possible. Even in a shared database, soft-delete complicates unique indexes (you'd need a composite index on "username + deletion time"). So ABP handles this in application code instead. + +To keep things safe under concurrency — say two tenant admins invite the same email address at the same time — ABP uses a **distributed lock** to serialize uniqueness validation. This means your production environment needs a distributed lock provider configured (such as Redis). + +The uniqueness check goes beyond just "no duplicate usernames." ABP also checks for **cross-field conflicts**: a user's username can't match another user's email, and vice versa. This prevents identity confusion in edge cases. + +### Tenants with Separate Databases + +If some of your tenants use their own database (database-per-tenant), the Shared strategy requires extra attention. + +The login flow and tenant selection happen on the **Host side**. This means the Host database's `AbpUsers` table must contain records for all users — even those originally created in a tenant's separate database. ABP's approach is replication: it saves the primary user record in the Host context and creates a copy in the tenant context. In a shared-database setup, both records live in the same table; in a database-per-tenant setup, they live in different physical databases. Updates and deletes are kept in sync automatically. + +If your application uses social login or passkeys, the `AbpUserLogins` and `AbpUserPasskeys` tables also need to be synced in the Host database. + +### Migrating from the Isolated Strategy + +If you're moving an existing multi-tenant application from Isolated to Shared, ABP automatically runs a global uniqueness check when you switch the strategy and reports any conflicts. + +The most common conflict: the same email address registered as separate users in different tenants. You'll need to resolve these first — merge the accounts or change one side's email — before the Shared strategy can be enabled. + +## Summary + +ABP's Shared User Accounts addresses a real-world need in multi-tenant systems: one person working across multiple tenants. + +- One configuration switch to `TenantUserSharingStrategy.Shared` +- User experience: pick a tenant at login, switch between tenants anytime, one password for everything +- Admin experience: invite users by email, pre-assign roles on invitation +- Database notes: configure a distributed lock provider for production; tenants with separate databases need user records replicated in the Host database + +ABP takes care of global uniqueness validation, tenant association management, and login flow adaptation under the hood. + +## References + +- [Shared User Accounts](https://abp.io/docs/latest/modules/account/shared-user-accounts) +- [ABP Multi-Tenancy](https://abp.io/docs/latest/framework/architecture/multi-tenancy) diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/cover.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/cover.png new file mode 100644 index 0000000000..33cbea2f52 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/cover.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/exist-user-accept.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/exist-user-accept.png new file mode 100644 index 0000000000..23f35c0904 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/exist-user-accept.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant-modal.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant-modal.png new file mode 100644 index 0000000000..8fa9d2fee9 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant-modal.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant.png new file mode 100644 index 0000000000..edfb5bedb0 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-admin-user-to-join-tenant.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-user.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-user.png new file mode 100644 index 0000000000..67a3f04073 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/invite-user.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-accept.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-accept.png new file mode 100644 index 0000000000..ffc887f1ed Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-accept.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-create-tenant.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-create-tenant.png new file mode 100644 index 0000000000..7d4a64c7c0 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-create-tenant.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-inform.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-inform.png new file mode 100644 index 0000000000..a6a62e1c96 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/new-user-join-strategy-inform.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/switch-tenant.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/switch-tenant.png new file mode 100644 index 0000000000..6f19de1da7 Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/switch-tenant.png differ diff --git a/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/tenant-selection.png b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/tenant-selection.png new file mode 100644 index 0000000000..e40bf6aaeb Binary files /dev/null and b/docs/en/Community-Articles/2026-03-17-Shared-User-Accounts-in-ABP/tenant-selection.png differ diff --git a/docs/en/cli/index.md b/docs/en/cli/index.md index e376887baf..bdbe9493b9 100644 --- a/docs/en/cli/index.md +++ b/docs/en/cli/index.md @@ -75,6 +75,7 @@ Here is the list of all available commands before explaining their details: * **[`install-old-cli`](../cli#install-old-cli)**: Installs old ABP CLI. * **[`mcp-studio`](../cli#mcp-studio)**: Starts ABP Studio MCP bridge for AI tools (requires ABP Studio running). * **[`generate-razor-page`](../cli#generate-razor-page)**: Generates a page class that you can use it in the ASP NET Core pipeline to return an HTML page. +* **[`generate-jwks`](../cli#generate-jwks)**: Generates an RSA key pair (JWKS public key + PEM private key) for OpenIddict `private_key_jwt` client authentication. ### help @@ -1127,6 +1128,99 @@ app.Use(async (httpContext, next) => * ```--version``` or ```-v```: Specifies the version for ABP CLI to be installed. +### generate-jwks + +Generates an RSA key pair for use with OpenIddict `private_key_jwt` client authentication. + +The command produces two files: + +| File | Description | +|---|---| +| `.json` | JWKS (JSON Web Key Set) containing the **public key**. Paste this into the **JSON Web Key Set** field of your OpenIddict application in the ABP management UI. | +| `-private.pem` | PKCS#8 PEM **private key**. Store this securely in your client application and use it to sign JWT client assertions. | + +> **Security notice:** Never commit the private key file to source control. Add it to `.gitignore`. Only the JWKS (public key) needs to be shared with the authorization server. + +Usage: + +```bash +abp generate-jwks [options] +``` + +#### Options + +* `--output` or `-o`: Output directory. Defaults to the current directory. +* `--key-size` or `-s`: RSA key size in bits. Supported values: `2048` (default), `4096`. +* `--alg`: Signing algorithm. Supported values: `RS256` (default), `RS384`, `RS512`, `PS256`, `PS384`, `PS512`. +* `--kid`: Custom Key ID. Auto-generated if not specified. +* `--file` or `-f`: Output file name prefix. Defaults to `jwks`. Generates `.json` and `-private.pem`. + +#### Examples + +```bash +# Generate with defaults (2048-bit RS256, current directory) +abp generate-jwks + +# Generate with RS512 and 4096-bit key +abp generate-jwks --alg RS512 --key-size 4096 + +# Output to a specific directory with a custom file prefix +abp generate-jwks -o ./keys -f myapp +``` + +#### Workflow + +1. Run `abp generate-jwks` to generate the key pair. + +2. Open the ABP OpenIddict application management UI, select your **Confidential** application, choose **JWKS (private_key_jwt)** as the authentication method, and paste the contents of `jwks.json` into the **JSON Web Key Set** field. + +3. In your client application, load the private key from the PEM file and sign JWT client assertions: + +```csharp +// Load private key from PEM file +using var rsa = RSA.Create(); +rsa.ImportFromPem(await File.ReadAllTextAsync("jwks-private.pem")); + +// The kid must match the "kid" field in the JWKS registered on the server +var signingKey = new RsaSecurityKey(rsa) { KeyId = "" }; +var signingCredentials = new SigningCredentials(signingKey, SecurityAlgorithms.RsaSha256); + +var now = DateTime.UtcNow; +var jwtHandler = new JsonWebTokenHandler(); +var clientAssertion = jwtHandler.CreateToken(new SecurityTokenDescriptor +{ + // OpenIddict requires typ = "client-authentication+jwt" + TokenType = "client-authentication+jwt", + // iss and sub must both equal the client_id + Issuer = "", + Audience = "", + Subject = new ClaimsIdentity(new[] + { + new Claim(JwtRegisteredClaimNames.Sub, ""), + new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()), + }), + IssuedAt = now, + NotBefore = now, + Expires = now.AddMinutes(5), + SigningCredentials = signingCredentials, +}); + +// Use the assertion in the token request +var tokenResponse = await httpClient.RequestClientCredentialsTokenAsync( + new ClientCredentialsTokenRequest + { + Address = "", + ClientId = "", + ClientCredentialStyle = ClientCredentialStyle.PostBody, + ClientAssertion = new ClientAssertion + { + Type = OidcConstants.ClientAssertionTypes.JwtBearer, + Value = clientAssertion, + }, + Scope = "", + }); +``` + ## See Also * [Examples for the new command](./new-command-samples.md) diff --git a/docs/en/docs-nav.json b/docs/en/docs-nav.json index 0cbdb312ac..b0a76124b4 100644 --- a/docs/en/docs-nav.json +++ b/docs/en/docs-nav.json @@ -807,10 +807,6 @@ "text": "Object to Object Mapping", "path": "framework/infrastructure/object-to-object-mapping.md" }, - { - "text": "Operation Rate Limiting", - "path": "framework/infrastructure/operation-rate-limiting.md" - }, { "text": "Settings", "path": "framework/infrastructure/settings.md" @@ -2577,6 +2573,10 @@ "text": "Language Management (Pro)", "path": "modules/language-management.md" }, + { + "text": "Operation Rate Limiting (Pro)", + "path": "modules/operation-rate-limiting.md" + }, { "text": "OpenIddict", "isLazyExpandable": true, diff --git a/docs/en/framework/api-development/auto-controllers.md b/docs/en/framework/api-development/auto-controllers.md index b40718b079..2c6f0ee39a 100644 --- a/docs/en/framework/api-development/auto-controllers.md +++ b/docs/en/framework/api-development/auto-controllers.md @@ -70,7 +70,7 @@ Route is calculated based on some conventions: * Continues with a **route path**. Default value is '**/app**' and can be configured as like below: ````csharp -Configure(options => +PreConfigure(options => { options.ConventionalControllers .Create(typeof(BookStoreApplicationModule).Assembly, opts => @@ -149,7 +149,7 @@ public class PersonAppService : ApplicationService You can further filter classes to become an API controller by providing the `TypePredicate` option: ````csharp -services.Configure(options => +PreConfigure(options => { options.ConventionalControllers .Create(typeof(BookStoreApplicationModule).Assembly, opts => diff --git a/docs/en/framework/infrastructure/background-jobs/tickerq.md b/docs/en/framework/infrastructure/background-jobs/tickerq.md index de7b3631f2..81dd021607 100644 --- a/docs/en/framework/infrastructure/background-jobs/tickerq.md +++ b/docs/en/framework/infrastructure/background-jobs/tickerq.md @@ -95,13 +95,13 @@ public class CleanupJobs public override Task OnPreApplicationInitializationAsync(ApplicationInitializationContext context) { var abpTickerQFunctionProvider = context.ServiceProvider.GetRequiredService(); - abpTickerQFunctionProvider.Functions.TryAdd(nameof(CleanupJobs), (string.Empty, TickerTaskPriority.Normal, new TickerFunctionDelegate(async (cancellationToken, serviceProvider, tickerFunctionContext) => + abpTickerQFunctionProvider.AddFunction(nameof(CleanupJobs), async (cancellationToken, serviceProvider, tickerFunctionContext) => { var service = new CleanupJobs(); // Or get it from the serviceProvider var request = await TickerRequestProvider.GetRequestAsync(tickerFunctionContext, cancellationToken); var genericContext = new TickerFunctionContext(tickerFunctionContext, request); await service.CleanupLogsAsync(genericContext, cancellationToken); - }))); + }, TickerTaskPriority.Normal); abpTickerQFunctionProvider.RequestTypes.TryAdd(nameof(CleanupJobs), (typeof(string).FullName, typeof(string))); return Task.CompletedTask; } diff --git a/docs/en/framework/infrastructure/background-workers/tickerq.md b/docs/en/framework/infrastructure/background-workers/tickerq.md index d4ddde3cd9..4547b85b85 100644 --- a/docs/en/framework/infrastructure/background-workers/tickerq.md +++ b/docs/en/framework/infrastructure/background-workers/tickerq.md @@ -83,13 +83,13 @@ public class CleanupJobs public override Task OnPreApplicationInitializationAsync(ApplicationInitializationContext context) { var abpTickerQFunctionProvider = context.ServiceProvider.GetRequiredService(); - abpTickerQFunctionProvider.Functions.TryAdd(nameof(CleanupJobs), (string.Empty, TickerTaskPriority.Normal, new TickerFunctionDelegate(async (cancellationToken, serviceProvider, tickerFunctionContext) => + abpTickerQFunctionProvider.AddFunction(nameof(CleanupJobs), async (cancellationToken, serviceProvider, tickerFunctionContext) => { var service = new CleanupJobs(); // Or get it from the serviceProvider var request = await TickerRequestProvider.GetRequestAsync(tickerFunctionContext, cancellationToken); var genericContext = new TickerFunctionContext(tickerFunctionContext, request); await service.CleanupLogsAsync(genericContext, cancellationToken); - }))); + }, TickerTaskPriority.Normal); abpTickerQFunctionProvider.RequestTypes.TryAdd(nameof(CleanupJobs), (typeof(string).FullName, typeof(string))); return Task.CompletedTask; } @@ -112,11 +112,11 @@ await cronTickerManager.AddAsync(new CronTickerEntity You can specify a cron expression instead of using `ICronTickerManager` to add a worker: ```csharp -abpTickerQFunctionProvider.Functions.TryAdd(nameof(CleanupJobs), (string.Empty, TickerTaskPriority.Normal, new TickerFunctionDelegate(async (cancellationToken, serviceProvider, tickerFunctionContext) => +abpTickerQFunctionProvider.AddFunction(nameof(CleanupJobs), async (cancellationToken, serviceProvider, tickerFunctionContext) => { var service = new CleanupJobs(); var request = await TickerRequestProvider.GetRequestAsync(tickerFunctionContext, cancellationToken); var genericContext = new TickerFunctionContext(tickerFunctionContext, request); await service.CleanupLogsAsync(genericContext, cancellationToken); -}))); +}, TickerTaskPriority.Normal); ``` diff --git a/docs/en/framework/infrastructure/entity-cache.md b/docs/en/framework/infrastructure/entity-cache.md index 50f1bc1b3c..aed1f33c6e 100644 --- a/docs/en/framework/infrastructure/entity-cache.md +++ b/docs/en/framework/infrastructure/entity-cache.md @@ -26,7 +26,7 @@ public class Product : AggregateRoot public string Name { get; set; } public string Description { get; set; } - public float Price { get; set; } + public decimal Price { get; set; } public int StockCount { get; set; } } ``` @@ -72,7 +72,7 @@ public class ProductDto : EntityDto { public string Name { get; set; } public string Description { get; set; } - public float Price { get; set; } + public decimal Price { get; set; } public int StockCount { get; set; } } ``` @@ -147,6 +147,115 @@ context.Services.AddEntityCache( * Entity classes should be serializable/deserializable to/from JSON to be cached (because it's serialized to JSON when saving in the [Distributed Cache](../fundamentals/caching.md)). If your entity class is not serializable, you can consider using a cache-item/DTO class instead, as explained before. * Entity Caching System is designed as **read-only**. You should use the standard [repository](../architecture/domain-driven-design/repositories.md) methods to manipulate the entity if you need to. If you need to manipulate (update) the entity, do not get it from the entity cache. Instead, read it from the repository, change it and update using the repository. +## Getting Multiple Entities + +In addition to the single-entity methods `FindAsync` and `GetAsync`, the `IEntityCache` service provides batch retrieval methods for retrieving multiple entities at once. + +### List-Based Batch Retrieval + +`FindManyAsync` and `GetManyAsync` return results as a list, preserving the order of the given IDs (including duplicates): + +```csharp +public class ProductAppService : ApplicationService, IProductAppService +{ + private readonly IEntityCache _productCache; + + public ProductAppService(IEntityCache productCache) + { + _productCache = productCache; + } + + public async Task> GetManyAsync(List ids) + { + return await _productCache.GetManyAsync(ids); + } + + public async Task> FindManyAsync(List ids) + { + return await _productCache.FindManyAsync(ids); + } +} +``` + +* `GetManyAsync` throws `EntityNotFoundException` if any entity is not found for the given IDs. +* `FindManyAsync` returns a list where each entry corresponds to the given ID in the same order; an entry will be `null` if the entity was not found. + +### Dictionary-Based Batch Retrieval + +`FindManyAsDictionaryAsync` and `GetManyAsDictionaryAsync` return results as a dictionary keyed by entity ID, which is convenient when you need fast lookup by ID: + +```csharp +public async Task> FindManyAsDictionaryAsync(List ids) +{ + return await _productCache.FindManyAsDictionaryAsync(ids); +} + +public async Task> GetManyAsDictionaryAsync(List ids) +{ + return await _productCache.GetManyAsDictionaryAsync(ids); +} +``` + +* `GetManyAsDictionaryAsync` throws `EntityNotFoundException` if any entity is not found for the given IDs. +* `FindManyAsDictionaryAsync` returns a dictionary where the value is `null` if the entity was not found for the corresponding key. + +All batch methods internally use `IDistributedCache.GetOrAddManyAsync` to batch-fetch only the cache-missed entities from the database, making them more efficient than calling `FindAsync` or `GetAsync` in a loop. + +## Custom Object Mapping + +When you need full control over how an entity is mapped to a cache item, you can derive from `EntityCacheWithObjectMapper` and override the `MapToValue` method: + +First, define the cache item class: + +```csharp +public class ProductCacheDto +{ + public Guid Id { get; set; } + public string Name { get; set; } + public decimal Price { get; set; } +} +``` + +Then, derive from `EntityCacheWithObjectMapper` and override `MapToValue`: + +```csharp +public class ProductEntityCache : + EntityCacheWithObjectMapper +{ + public ProductEntityCache( + IReadOnlyRepository repository, + IDistributedCache, Guid> cache, + IUnitOfWorkManager unitOfWorkManager, + IObjectMapper objectMapper) + : base(repository, cache, unitOfWorkManager, objectMapper) + { + } + + protected override ProductCacheDto MapToValue(Product entity) + { + // Custom mapping logic here + return new ProductCacheDto + { + Id = entity.Id, + Name = entity.Name.ToUpperInvariant(), + Price = entity.Price + }; + } +} +``` + +Register your custom cache class in the `ConfigureServices` method of your [module class](../architecture/modularity/basics.md): + +```csharp +context.Services.ReplaceEntityCache( + new DistributedCacheEntryOptions + { + AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(10) + }); +``` + +> If no prior `AddEntityCache` registration exists for the same cache item type, `ReplaceEntityCache` will simply add the service instead of throwing an error. + ## See Also * [Distributed caching](../fundamentals/caching.md) diff --git a/docs/en/framework/ui/maui/index.md b/docs/en/framework/ui/maui/index.md index 547617bcae..2622bdc7e0 100644 --- a/docs/en/framework/ui/maui/index.md +++ b/docs/en/framework/ui/maui/index.md @@ -42,15 +42,29 @@ You can examine the [Users Page](#users-page) or any other pre-defined page to s ### Android -If you get the following error when connecting to the emulator or a physical phone, you need to set up port mapping. +If you get the following error when connecting to the emulator or a physical phone, you need to set up port mapping using the `adb` tool: ``` Cannot connect to the backend on localhost. ``` -Open a command line terminal and run the `adb reverse` command to expose a port on your Android device to a port on your computer. For example: +**How to get and use `adb` tool:** -`adb reverse tcp:44305 tcp:44305` +- **Option 1: Install `adb` globally** + Download and install the [Android SDK Platform-Tools](https://developer.android.com/tools/releases/platform-tools) to get the [`adb`](https://developer.android.com/tools/adb) command-line tool. +- **Option 2: Use Visual Studio’s built-in `adb` command prompt** + If you are using Visual Studio, you can access the `adb` command prompt directly from the IDE: + ![Android Adb Command Prompt](../../../images/adb-command-prompt.png) + +> For more information on setting up your environment for Android development and debugging, refer to the [Microsoft MAUI Android device setup guide](https://learn.microsoft.com/en-us/dotnet/maui/android/device/setup). + +**Port mapping command:** + +Once `adb` is available, run the following command in your terminal (or Visual Studio's `adb` command prompt) to map the backend port to your Android device: + +```bash +adb reverse tcp:44305 tcp:44305 +``` > Replace `44305` with the port number your backend application is running on. > diff --git a/docs/en/images/adb-command-prompt.png b/docs/en/images/adb-command-prompt.png new file mode 100644 index 0000000000..19eb84b90f Binary files /dev/null and b/docs/en/images/adb-command-prompt.png differ diff --git a/docs/en/modules/ai-management/index.md b/docs/en/modules/ai-management/index.md index 38693fc366..a551d5beef 100644 --- a/docs/en/modules/ai-management/index.md +++ b/docs/en/modules/ai-management/index.md @@ -44,6 +44,16 @@ abp add-package Volo.AIManagement.OpenAI abp add-package Volo.AIManagement.Ollama ``` +> [!IMPORTANT] +> If you use Ollama, make sure the Ollama server is installed and running, and that the models referenced by your workspace are already available locally. Before configuring an Ollama workspace, pull the chat model and any embedding model you plan to use. For example: +> +> ```bash +> ollama pull llama3.2 +> ollama pull nomic-embed-text +> ``` +> +> Replace the model names with the exact models you configure in the workspace. `nomic-embed-text` is an embedding-only model and can't be used as a chat model. + > [!TIP] > You can install multiple provider packages to support different AI providers simultaneously in your workspaces. @@ -308,6 +318,14 @@ RAG requires an **embedder** and a **vector store** to be configured on the work * **Embedder**: Converts documents and queries into vector embeddings. You can use any provider that supports embedding generation (e.g., OpenAI `text-embedding-3-small`, Ollama `nomic-embed-text`). * **Vector Store**: Stores and retrieves vector embeddings. Supported providers: **MongoDb**, **Pgvector**, and **Qdrant**. +> [!IMPORTANT] +> If the workspace uses Ollama for chat or embeddings, the configured model names must exist in the local Ollama instance first. For example, if you configure `ModelName = "llama3.2"` and `EmbedderModelName = "nomic-embed-text"`, pull both models before using the workspace: +> +> ```bash +> ollama pull llama3.2 +> ollama pull nomic-embed-text +> ``` + ### Configuring RAG on a Workspace To enable RAG for a workspace, configure the embedder and vector store settings in the workspace edit page. @@ -432,6 +450,67 @@ The options class also provides helper methods: > [!NOTE] > Adding new file extensions also requires a matching content extractor to be registered for document processing. The built-in extractors support `.txt`, `.md`, and `.pdf` files. +#### Hosting-Level Upload Limits + +`WorkspaceDataSourceOptions.MaxFileSize` controls the module-level validation, but your hosting stack may reject large uploads before the request reaches AI Management. If you increase `MaxFileSize`, make sure the underlying server and proxy limits are also updated. + +Typical limits to review: + +* **ASP.NET Core form/multipart limit** (`FormOptions.MultipartBodyLengthLimit`) +* **Kestrel request body limit** (`KestrelServerLimits.MaxRequestBodySize`) +* **IIS request filtering limit** (`maxAllowedContentLength`) +* **Reverse proxy limits** such as **Nginx** (`client_max_body_size`) + +Example ASP.NET Core configuration: + +```csharp +using Microsoft.AspNetCore.Http.Features; + +public override void ConfigureServices(ServiceConfigurationContext context) +{ + Configure(options => + { + options.MaxFileSize = 50 * 1024 * 1024; + }); + + Configure(options => + { + options.MultipartBodyLengthLimit = 50 * 1024 * 1024; + }); +} +``` + +```csharp +builder.WebHost.ConfigureKestrel(options => +{ + options.Limits.MaxRequestBodySize = 50 * 1024 * 1024; +}); +``` + +Example IIS configuration in `web.config`: + +```xml + + + + + + + + + +``` + +Example Nginx configuration: + +```nginx +server { + client_max_body_size 50M; +} +``` + +If you are hosting behind another proxy or gateway (for example Apache, YARP, Azure App Gateway, Cloudflare, or Kubernetes ingress), ensure its request-body limit is also greater than or equal to the configured `MaxFileSize`. + ## Permissions The AI Management module defines the following permissions: diff --git a/docs/en/framework/infrastructure/operation-rate-limiting.md b/docs/en/modules/operation-rate-limiting.md similarity index 62% rename from docs/en/framework/infrastructure/operation-rate-limiting.md rename to docs/en/modules/operation-rate-limiting.md index 5208c2c959..f285793695 100644 --- a/docs/en/framework/infrastructure/operation-rate-limiting.md +++ b/docs/en/modules/operation-rate-limiting.md @@ -1,11 +1,13 @@ ````json //[doc-seo] { - "Description": "Learn how to use the Operation Rate Limiting module in ABP Framework to control the frequency of specific operations like SMS sending, login attempts, and resource-intensive tasks." + "Description": "Learn how to use the Operation Rate Limiting module (Pro) in ABP to control the frequency of specific operations like SMS sending, login attempts, and resource-intensive tasks." } ```` -# Operation Rate Limiting +# Operation Rate Limiting Module (Pro) + +> You must have an [ABP Team or a higher license](https://abp.io/pricing) to use this module. ABP provides an operation rate limiting system that allows you to control the frequency of specific operations in your application. You may need operation rate limiting for several reasons: @@ -15,15 +17,9 @@ ABP provides an operation rate limiting system that allows you to control the fr > This is not for [ASP.NET Core's built-in rate limiting middleware](https://learn.microsoft.com/en-us/aspnet/core/performance/rate-limit) which works at the HTTP request pipeline level. This module works at the **application/domain code level** and is called explicitly from your services. See the [Combining with ASP.NET Core Rate Limiting](#combining-with-aspnet-core-rate-limiting) section for a comparison. -## Installation - -You can open a command-line terminal and type the following command to install the [Volo.Abp.OperationRateLimiting](https://www.nuget.org/packages/Volo.Abp.OperationRateLimiting) package into your project: +## How to Install -````bash -abp add-package Volo.Abp.OperationRateLimiting -```` - -> If you haven't done it yet, you first need to install the [ABP CLI](../../../cli). +This module is used by the [Account (Pro)](account-pro.md) module internally and comes pre-installed in the latest [startup templates](../solution-templates). So, no need to manually install it. ## Quick Start @@ -31,7 +27,7 @@ This section shows the basic usage of the operation rate limiting system with a ### Defining a Policy -First, define a rate limiting policy in the `ConfigureServices` method of your [module class](../../architecture/modularity/basics.md): +First, define a rate limiting policy in the `ConfigureServices` method of your [module class](../framework/architecture/modularity/basics.md): ````csharp Configure(options => @@ -62,7 +58,7 @@ public class SmsAppService : ApplicationService _rateLimitChecker = rateLimitChecker; } - public async Task SendCodeAsync(string phoneNumber) + public virtual async Task SendCodeAsync(string phoneNumber) { await _rateLimitChecker.CheckAsync("SendSmsCode", phoneNumber); @@ -78,9 +74,120 @@ public class SmsAppService : ApplicationService That's the basic usage. The following sections explain each concept in detail. +## Declarative Usage (Attribute) + +Instead of injecting `IOperationRateLimitingChecker` manually, you can use the `[OperationRateLimiting]` attribute to enforce a policy declaratively on Application Service methods or MVC Controller actions. + +> **Application Services** are handled by the ABP interceptor (built into the Domain layer). +> **MVC Controllers** are handled by `AbpOperationRateLimitingActionFilter`, which is automatically registered when you reference the `Volo.Abp.OperationRateLimiting.AspNetCore` package. + +### Applying to an Application Service + +````csharp +public class SmsAppService : ApplicationService +{ + [OperationRateLimiting("SendSmsCode")] + public virtual async Task SendCodeAsync([RateLimitingParameter] string phoneNumber) + { + // Rate limit is checked automatically before this line executes. + await _smsSender.SendAsync(phoneNumber, GenerateCode()); + } +} +```` + +### Applying to an MVC Controller + +````csharp +[Route("api/account")] +public class AccountController : AbpController +{ + [HttpPost("send-sms-code")] + [OperationRateLimiting("SendSmsCode")] + public async Task SendSmsCodeAsync([RateLimitingParameter] string phoneNumber) + { + // Rate limit is checked automatically before this line executes. + await _smsSender.SendAsync(phoneNumber, GenerateCode()); + return Ok(); + } +} +```` + +### Resolving the Parameter Value + +The `[OperationRateLimiting]` attribute resolves `OperationRateLimitingContext.Parameter` automatically using the following priority order: + +1. **`[RateLimitingParameter]`** — a method parameter marked with this attribute. Its `ToString()` value is used as the partition key. +2. **`IHasOperationRateLimitingParameter`** — a method parameter whose type implements this interface. The value returned by `GetPartitionParameter()` is used as the partition key. +3. **`null`** — no parameter is resolved; suitable for policies that use `PartitionByCurrentUser`, `PartitionByClientIp`, etc. + +#### Using `[RateLimitingParameter]` + +Mark a single parameter to use its value as the partition key: + +````csharp +[OperationRateLimiting("SendSmsCode")] +public virtual async Task SendCodeAsync([RateLimitingParameter] string phoneNumber) +{ + // partition key = phoneNumber +} +```` + +#### Using `IHasOperationRateLimitingParameter` + +Implement the interface on an input DTO when the partition key is a property of the DTO: + +````csharp +public class SendSmsCodeInput : IHasOperationRateLimitingParameter +{ + public string PhoneNumber { get; set; } + public string Language { get; set; } + + public string? GetPartitionParameter() => PhoneNumber; +} +```` + +````csharp +[OperationRateLimiting("SendSmsCode")] +public virtual async Task SendCodeAsync(SendSmsCodeInput input) +{ + // partition key = input.GetPartitionParameter() = input.PhoneNumber +} +```` + +#### No Partition Parameter + +If no parameter is marked and no DTO implements the interface, the policy is checked without a `Parameter` value. This is appropriate for policies that use `PartitionByCurrentUser`, `PartitionByClientIp`, or `PartitionByCurrentTenant`: + +````csharp +// Policy uses PartitionByCurrentUser — no explicit parameter needed. +[OperationRateLimiting("GenerateReport")] +public virtual async Task GenerateMonthlyReportAsync() +{ + // Rate limit is checked per current user automatically. +} +```` + +> If the method has parameters but none is resolved, a **warning log** is emitted to help you catch misconfigured usages early. + +### Applying to a Class + +You can also place `[OperationRateLimiting]` on the class to apply it to **all public methods** of that class: + +````csharp +[OperationRateLimiting("MyServiceLimit")] +public class MyAppService : ApplicationService +{ + public virtual async Task MethodAAsync([RateLimitingParameter] string key) { ... } + + public virtual async Task MethodBAsync([RateLimitingParameter] string key) { ... } +} +```` + +> A method-level attribute takes precedence over the class-level attribute. + ## Defining Policies -Policies are defined using `AbpOperationRateLimitingOptions` in the `ConfigureServices` method of your [module class](../../architecture/modularity/basics.md). Each policy has a unique name, one or more rules, and a partition strategy. +Policies are defined using `AbpOperationRateLimitingOptions` in the `ConfigureServices` method of your [module class](../framework/architecture/modularity/basics.md). Each policy has a unique name, one or more rules, and a partition strategy. ### Single-Rule Policies @@ -115,6 +222,78 @@ options.AddPolicy("Login", policy => > When multiple rules are present, the module uses a **two-phase check**: it first verifies all rules without incrementing counters, then increments only if all rules pass. This prevents wasted quota when one rule would block the request. +### Overriding an Existing Policy + +If a reusable module (e.g., ABP's Account module) defines a policy with default rules, you have two ways to customize it in your own module's `ConfigureServices`. + +**Option 1 — Full replacement with `AddPolicy`:** + +Call `AddPolicy` with the same name. The last registration wins and completely replaces all rules: + +````csharp +// In your application module — runs after the Account module +Configure(options => +{ + options.AddPolicy("Account.SendPasswordResetCode", policy => + { + // Replaces all rules defined by the Account module for this policy + policy.AddRule(rule => rule + .WithFixedWindow(TimeSpan.FromMinutes(5), maxCount: 3) + .PartitionByEmail()); + }); +}); +```` + +> `AddPolicy` stores policies in a dictionary keyed by name, so calling it again with the same name fully replaces the previous policy and all its rules. + +**Option 2 — Partial modification with `ConfigurePolicy`:** + +Use `ConfigurePolicy` to modify an existing policy without replacing it entirely. The builder is pre-populated with the existing rules, so you only need to express what changes: + +````csharp +Configure(options => +{ + // Only override the error code, keeping the module's original rules + options.ConfigurePolicy("Account.SendPasswordResetCode", policy => + { + policy.WithErrorCode("MyApp:SmsCodeLimit"); + }); +}); +```` + +You can also add a rule on top of the existing ones: + +````csharp +options.ConfigurePolicy("Account.SendPasswordResetCode", policy => +{ + // Keep the module's per-email rule and add a per-IP rule on top + policy.AddRule(rule => rule + .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 20) + .PartitionByClientIp()); +}); +```` + +Or clear all inherited rules first and define entirely new ones using `ClearRules()`: + +````csharp +options.ConfigurePolicy("Account.SendPasswordResetCode", policy => +{ + policy.ClearRules() + .WithFixedWindow(TimeSpan.FromMinutes(5), maxCount: 3) + .PartitionByEmail(); +}); +```` + +`ConfigurePolicy` returns `AbpOperationRateLimitingOptions`, so you can chain multiple calls: + +````csharp +options + .ConfigurePolicy("Account.SendPasswordResetCode", p => p.WithErrorCode("MyApp:SmsLimit")) + .ConfigurePolicy("Account.Login", p => p.WithErrorCode("MyApp:LoginLimit")); +```` + +> `ConfigurePolicy` throws `AbpException` if the policy name is not found. Use `AddPolicy` first (in the module that owns the policy), then `ConfigurePolicy` in downstream modules to customize it. + ### Custom Error Code By default, the exception uses the error code `Volo.Abp.OperationRateLimiting:010001`. You can override it per policy: @@ -195,14 +374,59 @@ Works the same way as `PartitionByEmail`: resolves from `context.Parameter` firs ### Custom Partition (PartitionBy) -You can provide a custom async function to generate the partition key. The async signature allows you to perform database queries or other I/O operations: +You can register a named custom resolver to generate the partition key. The resolver is an async function, so you can perform database queries or other I/O operations. Because the resolver is stored by name (not as an anonymous delegate), it can be serialized and managed from a UI or database. + +**Step 1 — Register the resolver by name:** + +````csharp +Configure(options => +{ + options.AddPartitionKeyResolver("ByDevice", ctx => + Task.FromResult($"{ctx.Parameter}:{ctx.ExtraProperties["DeviceId"]}")); +}); +```` + +**Step 2 — Reference it in a policy:** + +````csharp +policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 100) + .PartitionBy("ByDevice"); +```` + +You can also register and reference in one step (inline): ````csharp policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 100) - .PartitionBy(ctx => Task.FromResult( - $"{ctx.Parameter}:{ctx.ExtraProperties["DeviceId"]}")); + .PartitionBy("ByDevice", ctx => + Task.FromResult($"{ctx.Parameter}:{ctx.ExtraProperties["DeviceId"]}")); +```` + +> If you call `PartitionBy("name")` with a resolver name that hasn't been registered, an exception is thrown at configuration time (not at runtime), so typos are caught early. + +To replace an existing resolver (e.g., in a downstream module), use `ReplacePartitionKeyResolver`: + +````csharp +options.ReplacePartitionKeyResolver("ByDevice", ctx => + Task.FromResult($"v2:{ctx.Parameter}:{ctx.ExtraProperties["DeviceId"]}")); +```` + +### Named Rules (WithName) + +By default, a rule's store key is derived from its `Duration`, `MaxCount`, and `PartitionType`. This means that if you change a rule's parameters (e.g., increase `maxCount` from 5 to 10), the counter resets because the key changes. + +To keep a stable key across parameter changes, give the rule a name: + +````csharp +policy.AddRule(rule => rule + .WithName("HourlyLimit") + .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 100) + .PartitionByCurrentUser()); ```` +When a name is set, it is used as the store key instead of the content-based descriptor. This is particularly useful when rules are managed from a database or UI — changing the `maxCount` or `duration` will not reset existing counters. + +> Rule names must be unique within a policy. Duplicate names cause an exception at build time. + ## Multi-Tenancy By default, partition keys do not include tenant information — for partition types like `PartitionByParameter`, `PartitionByCurrentUser`, `PartitionByClientIp`, etc., counters are shared across tenants unless you call `WithMultiTenancy()`. Note that `PartitionByCurrentTenant()` is inherently per-tenant since the partition key is the tenant ID itself, and `PartitionByClientIp()` is typically kept global since the same IP should share a counter regardless of tenant. @@ -434,7 +658,7 @@ This module and ASP.NET Core's built-in [rate limiting middleware](https://learn |---|---|---| | **Level** | HTTP request pipeline | Application/domain code | | **Scope** | All incoming requests | Specific business operations | -| **Usage** | Middleware (automatic) | Explicit `CheckAsync` calls | +| **Usage** | Middleware (automatic) | `[OperationRateLimiting]` attribute or explicit `CheckAsync` calls | | **Typical use** | API throttling, DDoS protection | Business logic limits (SMS, reports) | A common pattern is to use ASP.NET Core middleware for broad API protection and this module for fine-grained business operation limits. @@ -467,7 +691,7 @@ public class MyCustomStore : IOperationRateLimitingStore, ITransientDependency } ```` -ABP's [dependency injection](../../fundamentals/dependency-injection.md) system will automatically use your implementation since it replaces the default one. +ABP's [dependency injection](../framework/fundamentals/dependency-injection.md) system will automatically use your implementation since it replaces the default one. ### Custom Rule @@ -485,8 +709,33 @@ Replace `IOperationRateLimitingFormatter` to customize how time durations are di Replace `IOperationRateLimitingPolicyProvider` to load policies from a database or external configuration source instead of the in-memory options. +When loading pre-built policies from an external source, use the `AddPolicy` overload that accepts an `OperationRateLimitingPolicy` object directly (bypassing the builder): + +````csharp +options.AddPolicy(new OperationRateLimitingPolicy +{ + Name = "DynamicPolicy", + Rules = + [ + new OperationRateLimitingRuleDefinition + { + Name = "HourlyLimit", + Duration = TimeSpan.FromHours(1), + MaxCount = 100, + PartitionType = OperationRateLimitingPartitionType.CurrentUser + } + ] +}); +```` + +To remove a policy (e.g., when it is deleted from the database), use `RemovePolicy`: + +````csharp +options.RemovePolicy("DynamicPolicy"); +```` + ## See Also * [ASP.NET Core Rate Limiting Middleware](https://learn.microsoft.com/en-us/aspnet/core/performance/rate-limit) -* [Distributed Caching](../fundamentals/caching.md) -* [Exception Handling](../fundamentals/exception-handling.md) +* [Distributed Caching](../framework/fundamentals/caching.md) +* [Exception Handling](../framework/fundamentals/exception-handling.md) diff --git a/docs/en/package-version-changes.md b/docs/en/package-version-changes.md index 3dad0d2f7b..02b76c3be3 100644 --- a/docs/en/package-version-changes.md +++ b/docs/en/package-version-changes.md @@ -1,5 +1,19 @@ # Package Version Changes +## 10.3.0-rc.1 + +| Package | Old Version | New Version | PR | +|---------|-------------|-------------|-----| +| Microsoft.IdentityModel.JsonWebTokens | 8.14.0 | 8.16.0 | #25068 | +| Microsoft.IdentityModel.Protocols.OpenIdConnect | 8.14.0 | 8.16.0 | #25068 | +| Microsoft.IdentityModel.Tokens | 8.14.0 | 8.16.0 | #25068 | +| MongoDB.Driver | 3.7.0 | 3.7.1 | #25114 | +| System.IdentityModel.Tokens.Jwt | 8.14.0 | 8.16.0 | #25068 | +| TickerQ | 10.1.1 | 10.2.0 | #25091 | +| TickerQ.Dashboard | 10.1.1 | 10.2.0 | #25091 | +| TickerQ.EntityFrameworkCore | 10.1.1 | 10.2.0 | #25091 | +| TickerQ.Utilities | 10.1.1 | 10.2.0 | #25091 | + ## 10.3.0-preview | Package | Old Version | New Version | PR | diff --git a/framework/Volo.Abp.slnx b/framework/Volo.Abp.slnx index 1e36f1d212..1302600c09 100644 --- a/framework/Volo.Abp.slnx +++ b/framework/Volo.Abp.slnx @@ -169,7 +169,6 @@ - @@ -257,6 +256,5 @@ - diff --git a/framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/AbpBlazorClientHttpMessageHandler.cs b/framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/AbpBlazorClientHttpMessageHandler.cs index 88855e3fc5..5e1ce7545c 100644 --- a/framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/AbpBlazorClientHttpMessageHandler.cs +++ b/framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/AbpBlazorClientHttpMessageHandler.cs @@ -53,7 +53,10 @@ public class AbpBlazorClientHttpMessageHandler : DelegatingHandler, ITransientDe options.Type = UiPageProgressType.Info; }); - request.SetBrowserRequestStreamingEnabled(true); + if (request.RequestUri?.Scheme == Uri.UriSchemeHttps) + { + request.SetBrowserRequestStreamingEnabled(true); + } await SetLanguageAsync(request, cancellationToken); await SetAntiForgeryTokenAsync(request); await SetTimeZoneAsync(request); diff --git a/framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs b/framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs index 1fb6f806e1..f40ff1030b 100644 --- a/framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs +++ b/framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs @@ -54,7 +54,7 @@ public class AbpInputTagHelperService : AbpTagHelperService output.TagMode = TagMode.StartTagAndEndTag; output.TagName = "div"; LeaveOnlyGroupAttributes(context, output); - if (!IsOutputHidden(output)) + if (!IsInputHidden(context)) { if (TagHelper.FloatingLabel && !isCheckBox) { @@ -86,6 +86,7 @@ public class AbpInputTagHelperService : AbpTagHelperService protected virtual async Task<(string, bool)> GetFormInputGroupAsHtmlAsync(TagHelperContext context, TagHelperOutput output) { var (inputTag, isCheckBox) = await GetInputTagHelperOutputAsync(context, output); + context.Items[nameof(IsOutputHidden)] = IsOutputHidden(inputTag); var inputHtml = inputTag.Render(_encoder); var label = await GetLabelAsHtmlAsync(context, output, inputTag, isCheckBox); @@ -124,7 +125,8 @@ public class AbpInputTagHelperService : AbpTagHelperService protected virtual string SurroundInnerHtmlAndGet(TagHelperContext context, TagHelperOutput output, string innerHtml, bool isCheckbox) { - var mb = TagHelper.AddMarginBottomClass ? (isCheckbox ? "mb-2" : "mb-3") : string.Empty; + var isHidden = IsInputHidden(context); + var mb = !isHidden && TagHelper.AddMarginBottomClass ? (isCheckbox ? "mb-2" : "mb-3") : string.Empty; return "
" + Environment.NewLine + innerHtml + Environment.NewLine + "
"; @@ -516,6 +518,11 @@ public class AbpInputTagHelperService : AbpTagHelperService return inputTag.Attributes.Any(a => a.Name.ToLowerInvariant() == "type" && a.Value.ToString()!.ToLowerInvariant() == "hidden"); } + protected virtual bool IsInputHidden(TagHelperContext context) + { + return context.Items.TryGetValue(nameof(IsOutputHidden), out var val) && val is true; + } + protected virtual string GetIdAttributeValue(TagHelperOutput inputTag) { var idAttr = inputTag.Attributes.FirstOrDefault(a => a.Name == "id"); diff --git a/framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/Validation/AbpValidationActionFilter.cs b/framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/Validation/AbpValidationActionFilter.cs index f866c85585..ad1f7dc1f7 100644 --- a/framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/Validation/AbpValidationActionFilter.cs +++ b/framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/Validation/AbpValidationActionFilter.cs @@ -1,4 +1,5 @@ using System.Linq; +using System.Reflection; using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc.Abstractions; using Microsoft.AspNetCore.Mvc.Filters; @@ -39,27 +40,55 @@ public class AbpValidationActionFilter : IAsyncActionFilter, IAbpFilter, ITransi return; } - if (context.ActionDescriptor.GetMethodInfo().DeclaringType != context.Controller.GetType()) + var effectiveMethod = GetEffectiveMethodInfo(context); + if (effectiveMethod != null) { - var baseMethod = context.ActionDescriptor.GetMethodInfo(); - - var overrideMethod = context.Controller.GetType().GetMethods().FirstOrDefault(x => - x.DeclaringType == context.Controller.GetType() && - x.Name == baseMethod.Name && - x.ReturnType == baseMethod.ReturnType && - x.GetParameters().Select(p => p.ToString()).SequenceEqual(baseMethod.GetParameters().Select(p => p.ToString()))); - - if (overrideMethod != null) + if (ReflectionHelper.GetSingleAttributeOfMemberOrDeclaringTypeOrDefault(effectiveMethod) != null) { - if (ReflectionHelper.GetSingleAttributeOfMemberOrDeclaringTypeOrDefault(overrideMethod) != null) - { - await next(); - return; - } + await next(); + return; } } context.GetRequiredService().Validate(context.ModelState); + + if (context.Controller is IValidationEnabled) + { + await ValidateActionArgumentsAsync(context, effectiveMethod); + } + await next(); } + + protected virtual MethodInfo? GetEffectiveMethodInfo(ActionExecutingContext context) + { + var baseMethod = context.ActionDescriptor.GetMethodInfo(); + if (baseMethod.DeclaringType == context.Controller.GetType()) + { + return null; + } + + return context.Controller.GetType().GetMethods().FirstOrDefault(x => + x.DeclaringType == context.Controller.GetType() && + x.Name == baseMethod.Name && + x.ReturnType == baseMethod.ReturnType && + x.GetParameters().Select(p => p.ToString()).SequenceEqual(baseMethod.GetParameters().Select(p => p.ToString()))); + } + + protected virtual async Task ValidateActionArgumentsAsync(ActionExecutingContext context, MethodInfo? effectiveMethod = null) + { + var methodInfo = effectiveMethod ?? context.ActionDescriptor.GetMethodInfo(); + + var parameterValues = methodInfo.GetParameters() + .Select(p => context.ActionArguments.TryGetValue(p.Name!, out var value) ? value : null) + .ToArray(); + + await context.GetRequiredService().ValidateAsync( + new MethodInvocationValidationContext( + context.Controller, + methodInfo, + parameterValues + ) + ); + } } diff --git a/framework/src/Volo.Abp.BackgroundJobs.RabbitMQ/Volo/Abp/BackgroundJobs/RabbitMQ/JobQueue.cs b/framework/src/Volo.Abp.BackgroundJobs.RabbitMQ/Volo/Abp/BackgroundJobs/RabbitMQ/JobQueue.cs index e3435efc16..dff2a4e33a 100644 --- a/framework/src/Volo.Abp.BackgroundJobs.RabbitMQ/Volo/Abp/BackgroundJobs/RabbitMQ/JobQueue.cs +++ b/framework/src/Volo.Abp.BackgroundJobs.RabbitMQ/Volo/Abp/BackgroundJobs/RabbitMQ/JobQueue.cs @@ -176,10 +176,10 @@ public class JobQueue : IJobQueue CorrelationId = CorrelationIdProvider.Get() }; - if (delay.HasValue) + if (delay.HasValue && delay.Value > TimeSpan.Zero) { routingKey = QueueConfiguration.DelayedQueueName; - basicProperties.Expiration = delay.Value.TotalMilliseconds.ToString(CultureInfo.InvariantCulture); + basicProperties.Expiration = ((long)Math.Ceiling(delay.Value.TotalMilliseconds)).ToString(CultureInfo.InvariantCulture); } if (ChannelAccessor != null) diff --git a/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTickerQModule.cs b/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTickerQModule.cs index 76e3aee2d5..4ff3adbfe4 100644 --- a/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTickerQModule.cs +++ b/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTickerQModule.cs @@ -23,26 +23,14 @@ public class AbpBackgroundJobsTickerQModule : AbpModule { var abpBackgroundJobOptions = context.ServiceProvider.GetRequiredService>(); var abpBackgroundJobsTickerQOptions = context.ServiceProvider.GetRequiredService>(); - var tickerFunctionDelegates = new Dictionary(); - var requestTypes = new Dictionary(); + var abpTickerQFunctionProvider = context.ServiceProvider.GetRequiredService(); foreach (var jobConfiguration in abpBackgroundJobOptions.Value.GetJobs()) { var genericMethod = GetTickerFunctionDelegateMethod.MakeGenericMethod(jobConfiguration.ArgsType); var tickerFunctionDelegate = (TickerFunctionDelegate)genericMethod.Invoke(null, [jobConfiguration.ArgsType])!; var config = abpBackgroundJobsTickerQOptions.Value.GetConfigurationOrNull(jobConfiguration.JobType); - tickerFunctionDelegates.TryAdd(jobConfiguration.JobName, (string.Empty, config?.Priority ?? TickerTaskPriority.Normal, tickerFunctionDelegate)); - requestTypes.TryAdd(jobConfiguration.JobName, (jobConfiguration.ArgsType.FullName, jobConfiguration.ArgsType)!); - } - - var abpTickerQFunctionProvider = context.ServiceProvider.GetRequiredService(); - foreach (var functionDelegate in tickerFunctionDelegates) - { - abpTickerQFunctionProvider.Functions.TryAdd(functionDelegate.Key, functionDelegate.Value); - } - - foreach (var requestType in requestTypes) - { - abpTickerQFunctionProvider.RequestTypes.TryAdd(requestType.Key, requestType.Value); + abpTickerQFunctionProvider.AddFunction(jobConfiguration.JobName, tickerFunctionDelegate, config?.Priority ?? TickerTaskPriority.Normal, config?.MaxConcurrency ?? 0); + abpTickerQFunctionProvider.RequestTypes.TryAdd(jobConfiguration.JobName, (jobConfiguration.ArgsType.FullName, jobConfiguration.ArgsType)!); } } diff --git a/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTimeTickerConfiguration.cs b/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTimeTickerConfiguration.cs index ecceaeb28a..1f2c6d32ac 100644 --- a/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTimeTickerConfiguration.cs +++ b/framework/src/Volo.Abp.BackgroundJobs.TickerQ/Volo/Abp/BackgroundJobs/TickerQ/AbpBackgroundJobsTimeTickerConfiguration.cs @@ -10,5 +10,7 @@ public class AbpBackgroundJobsTimeTickerConfiguration public TickerTaskPriority? Priority { get; set; } + public int? MaxConcurrency { get; set; } + public RunCondition? RunCondition { get; set; } } diff --git a/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpBackgroundWorkersCronTickerConfiguration.cs b/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpBackgroundWorkersCronTickerConfiguration.cs index 0e8ed89a14..662c05a58a 100644 --- a/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpBackgroundWorkersCronTickerConfiguration.cs +++ b/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpBackgroundWorkersCronTickerConfiguration.cs @@ -9,4 +9,6 @@ public class AbpBackgroundWorkersCronTickerConfiguration public int[]? RetryIntervals { get; set; } public TickerTaskPriority? Priority { get; set; } + + public int? MaxConcurrency { get; set; } } diff --git a/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpTickerQBackgroundWorkerManager.cs b/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpTickerQBackgroundWorkerManager.cs index b2f0de80cf..1fbe1c8ad0 100644 --- a/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpTickerQBackgroundWorkerManager.cs +++ b/framework/src/Volo.Abp.BackgroundWorkers.TickerQ/Volo/Abp/BackgroundWorkers/TickerQ/AbpTickerQBackgroundWorkerManager.cs @@ -62,11 +62,11 @@ public class AbpTickerQBackgroundWorkerManager : BackgroundWorkerManager, ISingl var name = BackgroundWorkerNameAttribute.GetNameOrNull(worker.GetType()) ?? worker.GetType().FullName; var config = Options.GetConfigurationOrNull(ProxyHelper.GetUnProxiedType(worker)); - AbpTickerQFunctionProvider.Functions.TryAdd(name!, (string.Empty, config?.Priority ?? TickerTaskPriority.LongRunning, async (tickerQCancellationToken, serviceProvider, tickerFunctionContext) => + AbpTickerQFunctionProvider.AddFunction(name!, async (tickerQCancellationToken, serviceProvider, tickerFunctionContext) => { var workerInvoker = new AbpTickerQPeriodicBackgroundWorkerInvoker(worker, serviceProvider); await workerInvoker.DoWorkAsync(tickerFunctionContext, tickerQCancellationToken); - })); + }, config?.Priority ?? TickerTaskPriority.LongRunning, config?.MaxConcurrency ?? 0); AbpTickerQBackgroundWorkersProvider.BackgroundWorkers.Add(name!, new AbpTickerQCronBackgroundWorker { diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs index a188137ea2..b8af22ff19 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs @@ -80,6 +80,7 @@ public class AbpCliCoreModule : AbpModule options.Commands[RecreateInitialMigrationCommand.Name] = typeof(RecreateInitialMigrationCommand); options.Commands[GenerateRazorPage.Name] = typeof(GenerateRazorPage); options.Commands[McpCommand.Name] = typeof(McpCommand); + options.Commands[GenerateJwksCommand.Name] = typeof(GenerateJwksCommand); options.DisabledModulesToAddToSolution.Add("Volo.Abp.LeptonXTheme.Pro"); options.DisabledModulesToAddToSolution.Add("Volo.Abp.LeptonXTheme.Lite"); diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/GenerateJwksCommand.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/GenerateJwksCommand.cs new file mode 100644 index 0000000000..f8474fea46 --- /dev/null +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/GenerateJwksCommand.cs @@ -0,0 +1,173 @@ +using System; +using System.IO; +using System.Security.Cryptography; +using System.Text; +using System.Text.Json; +using System.Threading.Tasks; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Volo.Abp.Cli.Args; +using Volo.Abp.DependencyInjection; + +namespace Volo.Abp.Cli.Commands; + +public class GenerateJwksCommand : IConsoleCommand, ITransientDependency +{ + public const string Name = "generate-jwks"; + + public ILogger Logger { get; set; } + + public GenerateJwksCommand() + { + Logger = NullLogger.Instance; + } + + public Task ExecuteAsync(CommandLineArgs commandLineArgs) + { + var outputDir = commandLineArgs.Options.GetOrNull("output", "o") + ?? Directory.GetCurrentDirectory(); + var keySizeStr = commandLineArgs.Options.GetOrNull("key-size", "s") ?? "2048"; + var alg = commandLineArgs.Options.GetOrNull("alg") ?? "RS256"; + var kid = commandLineArgs.Options.GetOrNull("kid") ?? Guid.NewGuid().ToString("N"); + var filePrefix = commandLineArgs.Options.GetOrNull("file", "f") ?? "jwks"; + + if (!int.TryParse(keySizeStr, out var keySize) || (keySize != 2048 && keySize != 4096)) + { + Logger.LogError("Invalid key size '{0}'. Supported values: 2048, 4096.", keySizeStr); + return Task.CompletedTask; + } + + if (!IsValidAlgorithm(alg)) + { + Logger.LogError("Invalid algorithm '{0}'. Supported values: RS256, RS384, RS512, PS256, PS384, PS512.", alg); + return Task.CompletedTask; + } + + if (!Directory.Exists(outputDir)) + { + Directory.CreateDirectory(outputDir); + } + + Logger.LogInformation("Generating RSA {0}-bit key pair (algorithm: {1})...", keySize, alg); + + using var rsa = RSA.Create(); + rsa.KeySize = keySize; + + var jwksJson = BuildJwksJson(rsa, alg, kid); + var privateKeyPem = ExportPrivateKeyPem(rsa); + + var jwksFilePath = Path.Combine(outputDir, $"{filePrefix}.json"); + var privateKeyFilePath = Path.Combine(outputDir, $"{filePrefix}-private.pem"); + + File.WriteAllText(jwksFilePath, jwksJson, Encoding.UTF8); + File.WriteAllText(privateKeyFilePath, privateKeyPem, Encoding.UTF8); + + Logger.LogInformation(""); + Logger.LogInformation("Generated files:"); + Logger.LogInformation(" JWKS (public key) : {0}", jwksFilePath); + Logger.LogInformation(" Private key (PEM) : {0}", privateKeyFilePath); + Logger.LogInformation(""); + Logger.LogInformation("JWKS content (paste this into the ABP OpenIddict application's 'JSON Web Key Set' field):"); + Logger.LogInformation(""); + Logger.LogInformation("{0}", jwksJson); + Logger.LogInformation(""); + Logger.LogInformation("IMPORTANT: Keep the private key file safe. Never share it or commit it to source control."); + Logger.LogInformation(" The JWKS file contains only the public key and is safe to share."); + + return Task.CompletedTask; + } + + private static string BuildJwksJson(RSA rsa, string alg, string kid) + { + var parameters = rsa.ExportParameters(false); + + var n = Base64UrlEncode(parameters.Modulus); + var e = Base64UrlEncode(parameters.Exponent); + + using var stream = new System.IO.MemoryStream(); + using var writer = new Utf8JsonWriter(stream, new JsonWriterOptions { Indented = true }); + + writer.WriteStartObject(); + writer.WriteStartArray("keys"); + writer.WriteStartObject(); + writer.WriteString("kty", "RSA"); + writer.WriteString("use", "sig"); + writer.WriteString("kid", kid); + writer.WriteString("alg", alg); + writer.WriteString("n", n); + writer.WriteString("e", e); + writer.WriteEndObject(); + writer.WriteEndArray(); + writer.WriteEndObject(); + writer.Flush(); + + return Encoding.UTF8.GetString(stream.ToArray()); + } + + private static string ExportPrivateKeyPem(RSA rsa) + { +#if NET5_0_OR_GREATER + return rsa.ExportPkcs8PrivateKeyPem(); +#elif NETSTANDARD2_0 + // RSA.ExportPkcs8PrivateKey() was introduced in .NET Standard 2.1. + // The ABP CLI always runs on .NET 5+, so this path is never reached at runtime. + throw new PlatformNotSupportedException("Private key export requires .NET Standard 2.1 or later."); +#else + var privateKeyBytes = rsa.ExportPkcs8PrivateKey(); + var base64 = Convert.ToBase64String(privateKeyBytes, Base64FormattingOptions.InsertLineBreaks); + return $"-----BEGIN PRIVATE KEY-----\n{base64}\n-----END PRIVATE KEY-----"; +#endif + } + + private static string Base64UrlEncode(byte[] input) + { + return Convert.ToBase64String(input) + .TrimEnd('=') + .Replace('+', '-') + .Replace('/', '_'); + } + + private static bool IsValidAlgorithm(string alg) + { + return alg == "RS256" || alg == "RS384" || alg == "RS512" || + alg == "PS256" || alg == "PS384" || alg == "PS512"; + } + + public string GetUsageInfo() + { + var sb = new StringBuilder(); + + sb.AppendLine(""); + sb.AppendLine("Usage:"); + sb.AppendLine(" abp generate-jwks [options]"); + sb.AppendLine(""); + sb.AppendLine("Options:"); + sb.AppendLine(" -o|--output Output directory (default: current directory)"); + sb.AppendLine(" -s|--key-size RSA key size: 2048 or 4096 (default: 2048)"); + sb.AppendLine(" --alg Algorithm: RS256, RS384, RS512, PS256, PS384, PS512 (default: RS256)"); + sb.AppendLine(" --kid Key ID (kid) - auto-generated if not specified"); + sb.AppendLine(" -f|--file Output file name prefix (default: jwks)"); + sb.AppendLine(" Generates: .json (JWKS) and -private.pem (private key)"); + sb.AppendLine(""); + sb.AppendLine("Examples:"); + sb.AppendLine(" abp generate-jwks"); + sb.AppendLine(" abp generate-jwks --alg RS512 --key-size 4096"); + sb.AppendLine(" abp generate-jwks -o ./keys -f myapp"); + sb.AppendLine(""); + sb.AppendLine("Description:"); + sb.AppendLine(" Generates an RSA key pair for use with OpenIddict private_key_jwt client authentication."); + sb.AppendLine(" The JWKS file (public key) should be pasted into the ABP OpenIddict application's"); + sb.AppendLine(" 'JSON Web Key Set' field in the management UI."); + sb.AppendLine(" The private key PEM file should be kept secure and used by the client application"); + sb.AppendLine(" to sign JWT assertions when authenticating to the token endpoint."); + sb.AppendLine(""); + sb.AppendLine("See the documentation for more info: https://abp.io/docs/latest/cli"); + + return sb.ToString(); + } + + public static string GetShortDescription() + { + return "Generates an RSA key pair (JWKS + private key) for OpenIddict private_key_jwt authentication."; + } +} diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheBase.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheBase.cs index 7cea931c12..826984a965 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheBase.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheBase.cs @@ -1,4 +1,6 @@ -using System.Threading.Tasks; +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; using Volo.Abp.Caching; using Volo.Abp.Data; using Volo.Abp.Domain.Entities.Events; @@ -14,6 +16,7 @@ public abstract class EntityCacheBase : ILocalEventHandler> where TEntity : Entity where TEntityCacheItem : class + where TKey : notnull { protected IReadOnlyRepository Repository { get; } protected IDistributedCache, TKey> Cache { get; } @@ -44,6 +47,20 @@ public abstract class EntityCacheBase : }))?.Value; } + public virtual async Task> FindManyAsync(IEnumerable ids) + { + var idArray = ids.ToArray(); + var cacheItemDict = await GetCacheItemDictionaryAsync(idArray.Distinct().ToArray()); + return idArray + .Select(id => cacheItemDict.TryGetValue(id, out var item) ? item : null) + .ToList(); + } + + public virtual async Task> FindManyAsDictionaryAsync(IEnumerable ids) + { + return await GetCacheItemDictionaryAsync(ids.Distinct().ToArray()); + } + public virtual async Task GetAsync(TKey id) { return (await Cache.GetOrAddAsync( @@ -59,6 +76,75 @@ public abstract class EntityCacheBase : }))!.Value!; } + public virtual async Task> GetManyAsync(IEnumerable ids) + { + var idArray = ids.ToArray(); + var cacheItemDict = await GetCacheItemDictionaryAsync(idArray.Distinct().ToArray()); + return idArray + .Select(id => + { + if (!cacheItemDict.TryGetValue(id, out var item) || item == null) + { + throw new EntityNotFoundException(id); + } + return item; + }) + .ToList(); + } + + public virtual async Task> GetManyAsDictionaryAsync(IEnumerable ids) + { + var distinctIds = ids.Distinct().ToArray(); + var cacheItemDict = await GetCacheItemDictionaryAsync(distinctIds); + var result = new Dictionary(); + foreach (var id in distinctIds) + { + if (!cacheItemDict.TryGetValue(id, out var item) || item == null) + { + throw new EntityNotFoundException(id); + } + result[id] = item; + } + return result; + } + + protected virtual async Task> GetCacheItemDictionaryAsync(TKey[] distinctIds) + { + var cacheItems = await GetOrAddManyCacheItemsAsync(distinctIds); + return cacheItems.ToDictionary(x => x.Key, x => x.Value?.Value); + } + + protected virtual async Task?>[]> GetOrAddManyCacheItemsAsync(TKey[] ids) + { + return await Cache.GetOrAddManyAsync( + ids, + async missingKeys => + { + if (HasObjectExtensionInfo()) + { + Repository.EnableTracking(); + } + + var missingKeyArray = missingKeys.ToArray(); + var entities = await Repository.GetListAsync( + x => missingKeyArray.Contains(x.Id), + includeDetails: true + ); + var entityDict = entities.ToDictionary(e => e.Id); + + return missingKeyArray + .Select(key => + { + entityDict.TryGetValue(key, out var entity); + return new KeyValuePair>( + key, + MapToCacheItem(entity)! + ); + }) + .ToList(); + }); + } + protected virtual bool HasObjectExtensionInfo() { return typeof(IHasExtraProperties).IsAssignableFrom(typeof(TEntity)) && diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheServiceCollectionExtensions.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheServiceCollectionExtensions.cs index c35406b45b..febdbd07f9 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheServiceCollectionExtensions.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheServiceCollectionExtensions.cs @@ -14,6 +14,7 @@ public static class EntityCacheServiceCollectionExtensions this IServiceCollection services, DistributedCacheEntryOptions? cacheOptions = null) where TEntity : Entity + where TKey : notnull { services.TryAddTransient, EntityCacheWithoutCacheItem>(); services.TryAddTransient>(); @@ -36,6 +37,7 @@ public static class EntityCacheServiceCollectionExtensions DistributedCacheEntryOptions? cacheOptions = null) where TEntity : Entity where TEntityCacheItem : class + where TKey : notnull { services.TryAddTransient, EntityCacheWithObjectMapper>(); services.TryAddTransient>(); @@ -53,6 +55,7 @@ public static class EntityCacheServiceCollectionExtensions DistributedCacheEntryOptions? cacheOptions = null) where TEntity : Entity where TEntityCacheItem : class + where TKey : notnull { services.TryAddTransient, EntityCacheWithObjectMapperContext>(); services.TryAddTransient>(); @@ -65,6 +68,33 @@ public static class EntityCacheServiceCollectionExtensions return services; } + public static IServiceCollection ReplaceEntityCache( + this IServiceCollection services, + DistributedCacheEntryOptions? cacheOptions = null) + where TEntityCache : EntityCacheBase + where TEntity : Entity + where TEntityCacheItem : class + where TKey : notnull + { + services.Replace(ServiceDescriptor.Transient, TEntityCache>()); + services.TryAddTransient(); + + services.Configure(options => + { + options.ConfigureCache>(cacheOptions ?? GetDefaultCacheOptions()); + }); + + if (typeof(TEntity) == typeof(TEntityCacheItem)) + { + services.Configure(options => + { + options.Modifiers.Add(new AbpIncludeNonPublicPropertiesModifiers().CreateModifyAction(x => x.Id)); + }); + } + + return services; + } + private static DistributedCacheEntryOptions GetDefaultCacheOptions() { return new DistributedCacheEntryOptions { diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapper.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapper.cs index 62b3162cdd..359b9ad716 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapper.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapper.cs @@ -10,6 +10,7 @@ public class EntityCacheWithObjectMapper : EntityCacheBase where TEntity : Entity where TEntityCacheItem : class + where TKey : notnull { protected IObjectMapper ObjectMapper { get; } @@ -30,11 +31,16 @@ public class EntityCacheWithObjectMapper : return null; } + return new EntityCacheItemWrapper(MapToValue(entity)); + } + + protected virtual TEntityCacheItem MapToValue(TEntity entity) + { if (typeof(TEntity) == typeof(TEntityCacheItem)) { - return new EntityCacheItemWrapper(entity.As()); + return entity.As(); } - return new EntityCacheItemWrapper(ObjectMapper.Map(entity)); + return ObjectMapper.Map(entity); } } diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapperContext.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapperContext.cs index 2471e1057c..4121c2aeae 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapperContext.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithObjectMapperContext.cs @@ -9,6 +9,7 @@ public class EntityCacheWithObjectMapperContext where TEntity : Entity where TEntityCacheItem : class + where TKey : notnull { public EntityCacheWithObjectMapperContext( IReadOnlyRepository repository, diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithoutCacheItem.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithoutCacheItem.cs index 4738534831..ecd3973685 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithoutCacheItem.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/EntityCacheWithoutCacheItem.cs @@ -7,6 +7,7 @@ namespace Volo.Abp.Domain.Entities.Caching; public class EntityCacheWithoutCacheItem : EntityCacheBase where TEntity : Entity + where TKey : notnull { public EntityCacheWithoutCacheItem( IReadOnlyRepository repository, diff --git a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/IEntityCache.cs b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/IEntityCache.cs index bd8ba80a63..202d7ca51b 100644 --- a/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/IEntityCache.cs +++ b/framework/src/Volo.Abp.Ddd.Domain/Volo/Abp/Domain/Entities/Caching/IEntityCache.cs @@ -1,21 +1,49 @@ -using System.Threading.Tasks; +using System.Collections.Generic; +using System.Threading.Tasks; using JetBrains.Annotations; namespace Volo.Abp.Domain.Entities.Caching; -public interface IEntityCache +public interface IEntityCache where TEntityCacheItem : class + where TKey : notnull { /// /// Gets the entity with given , /// or returns null if the entity was not found. /// Task FindAsync(TKey id); - + + /// + /// Gets multiple entities with the given . + /// Returns a list where each entry corresponds to the given id in the same order. + /// An entry will be null if the entity was not found for the corresponding id. + /// + Task> FindManyAsync(IEnumerable ids); + + /// + /// Gets multiple entities with the given as a dictionary keyed by id. + /// An entry will be null if the entity was not found for the corresponding id. + /// + Task> FindManyAsDictionaryAsync(IEnumerable ids); + /// /// Gets the entity with given , /// or throws if the entity was not found. /// - [ItemNotNull] + [ItemNotNull] Task GetAsync(TKey id); -} \ No newline at end of file + + /// + /// Gets multiple entities with the given . + /// Returns a list where each entry corresponds to the given id in the same order. + /// Throws if any entity was not found. + /// + Task> GetManyAsync(IEnumerable ids); + + /// + /// Gets multiple entities with the given as a dictionary keyed by id. + /// Throws if any entity was not found. + /// + Task> GetManyAsDictionaryAsync(IEnumerable ids); +} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/FodyWeavers.xml b/framework/src/Volo.Abp.OperationRateLimiting/FodyWeavers.xml deleted file mode 100644 index 7e9f94ead6..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/FodyWeavers.xml +++ /dev/null @@ -1,3 +0,0 @@ - - - diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo.Abp.OperationRateLimiting.csproj b/framework/src/Volo.Abp.OperationRateLimiting/Volo.Abp.OperationRateLimiting.csproj deleted file mode 100644 index ffac7ef34e..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo.Abp.OperationRateLimiting.csproj +++ /dev/null @@ -1,32 +0,0 @@ - - - - - - - netstandard2.0;netstandard2.1;net8.0;net9.0;net10.0 - enable - Nullable - Volo.Abp.OperationRateLimiting - Volo.Abp.OperationRateLimiting - $(AssetTargetFallback);portable-net45+win8+wp8+wpa81; - false - false - false - - - - - - - - - - - - - - - - - diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingErrorCodes.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingErrorCodes.cs deleted file mode 100644 index ba2bb5c189..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingErrorCodes.cs +++ /dev/null @@ -1,14 +0,0 @@ -namespace Volo.Abp.OperationRateLimiting; - -public static class AbpOperationRateLimitingErrorCodes -{ - /// - /// Default error code for rate limit exceeded (with a retry-after window). - /// - public const string ExceedLimit = "Volo.Abp.OperationRateLimiting:010001"; - - /// - /// Error code for ban policy (maxCount: 0) where requests are permanently denied. - /// - public const string ExceedLimitPermanently = "Volo.Abp.OperationRateLimiting:010002"; -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingModule.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingModule.cs deleted file mode 100644 index 0462a285a5..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingModule.cs +++ /dev/null @@ -1,42 +0,0 @@ -using Volo.Abp.AspNetCore; -using Volo.Abp.Caching; -using Volo.Abp.DistributedLocking; -using Volo.Abp.Localization; -using Volo.Abp.Localization.ExceptionHandling; -using Volo.Abp.Modularity; -using Volo.Abp.Security; -using Volo.Abp.VirtualFileSystem; - -namespace Volo.Abp.OperationRateLimiting; - -[DependsOn( - typeof(AbpCachingModule), - typeof(AbpLocalizationModule), - typeof(AbpSecurityModule), - typeof(AbpAspNetCoreAbstractionsModule), - typeof(AbpDistributedLockingAbstractionsModule) -)] -public class AbpOperationRateLimitingModule : AbpModule -{ - public override void ConfigureServices(ServiceConfigurationContext context) - { - Configure(options => - { - options.FileSets.AddEmbedded(); - }); - - Configure(options => - { - options.Resources - .Add("en") - .AddVirtualJson("/Volo/Abp/OperationRateLimiting/Localization"); - }); - - Configure(options => - { - options.MapCodeNamespace( - "Volo.Abp.OperationRateLimiting", - typeof(AbpOperationRateLimitingResource)); - }); - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingOptions.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingOptions.cs deleted file mode 100644 index 711f2b17d0..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingOptions.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace Volo.Abp.OperationRateLimiting; - -public class AbpOperationRateLimitingOptions -{ - public bool IsEnabled { get; set; } = true; - - public TimeSpan LockTimeout { get; set; } = TimeSpan.FromSeconds(5); - - public Dictionary Policies { get; } = new(); - - public void AddPolicy(string name, Action configure) - { - var builder = new OperationRateLimitingPolicyBuilder(name); - configure(builder); - Policies[name] = builder.Build(); - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingResource.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingResource.cs deleted file mode 100644 index e4f93d97d0..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingResource.cs +++ /dev/null @@ -1,8 +0,0 @@ -using Volo.Abp.Localization; - -namespace Volo.Abp.OperationRateLimiting; - -[LocalizationResourceName("AbpOperationRateLimiting")] -public class AbpOperationRateLimitingResource -{ -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/IOperationRateLimitingChecker.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/IOperationRateLimitingChecker.cs deleted file mode 100644 index 2220c241e8..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/IOperationRateLimitingChecker.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public interface IOperationRateLimitingChecker -{ - Task CheckAsync(string policyName, OperationRateLimitingContext? context = null); - - Task IsAllowedAsync(string policyName, OperationRateLimitingContext? context = null); - - Task GetStatusAsync(string policyName, OperationRateLimitingContext? context = null); - - Task ResetAsync(string policyName, OperationRateLimitingContext? context = null); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingChecker.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingChecker.cs deleted file mode 100644 index 095fa6cbf6..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingChecker.cs +++ /dev/null @@ -1,277 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Options; -using Volo.Abp.AspNetCore.WebClientInfo; -using Volo.Abp.DependencyInjection; -using Volo.Abp.MultiTenancy; -using Volo.Abp.Users; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingChecker : IOperationRateLimitingChecker, ITransientDependency -{ - protected AbpOperationRateLimitingOptions Options { get; } - protected IOperationRateLimitingPolicyProvider PolicyProvider { get; } - protected IServiceProvider ServiceProvider { get; } - protected IOperationRateLimitingStore Store { get; } - protected ICurrentUser CurrentUser { get; } - protected ICurrentTenant CurrentTenant { get; } - protected IWebClientInfoProvider WebClientInfoProvider { get; } - - public OperationRateLimitingChecker( - IOptions options, - IOperationRateLimitingPolicyProvider policyProvider, - IServiceProvider serviceProvider, - IOperationRateLimitingStore store, - ICurrentUser currentUser, - ICurrentTenant currentTenant, - IWebClientInfoProvider webClientInfoProvider) - { - Options = options.Value; - PolicyProvider = policyProvider; - ServiceProvider = serviceProvider; - Store = store; - CurrentUser = currentUser; - CurrentTenant = currentTenant; - WebClientInfoProvider = webClientInfoProvider; - } - - public virtual async Task CheckAsync(string policyName, OperationRateLimitingContext? context = null) - { - if (!Options.IsEnabled) - { - return; - } - - context = EnsureContext(context); - var policy = await PolicyProvider.GetAsync(policyName); - var rules = CreateRules(policy); - - // Phase 1: Check ALL rules without incrementing to get complete status. - // Do not exit early: a later rule may have a larger RetryAfter that the caller needs to know about. - var checkResults = new List(); - foreach (var rule in rules) - { - checkResults.Add(await rule.CheckAsync(context)); - } - - if (checkResults.Any(r => !r.IsAllowed)) - { - // Throw without incrementing any counter; RetryAfter is the max across all blocking rules. - var aggregatedResult = AggregateResults(checkResults, policy); - ThrowRateLimitException(policy, aggregatedResult, context); - } - - // Phase 2: All rules passed in Phase 1 - now increment counters. - // Guard against concurrent races where another request consumed the last quota - // between Phase 1 and Phase 2. - // Once any rule fails during increment, stop incrementing subsequent rules - // to minimize wasted quota. Remaining rules use read-only check instead. - var incrementResults = new List(); - var phase2Failed = false; - foreach (var rule in rules) - { - if (phase2Failed) - { - incrementResults.Add(await rule.CheckAsync(context)); - } - else - { - var result = await rule.AcquireAsync(context); - incrementResults.Add(result); - if (!result.IsAllowed) - { - phase2Failed = true; - } - } - } - - if (phase2Failed) - { - var aggregatedResult = AggregateResults(incrementResults, policy); - ThrowRateLimitException(policy, aggregatedResult, context); - } - } - - public virtual async Task IsAllowedAsync(string policyName, OperationRateLimitingContext? context = null) - { - if (!Options.IsEnabled) - { - return true; - } - - context = EnsureContext(context); - var policy = await PolicyProvider.GetAsync(policyName); - var rules = CreateRules(policy); - - foreach (var rule in rules) - { - var result = await rule.CheckAsync(context); - if (!result.IsAllowed) - { - return false; - } - } - - return true; - } - - public virtual async Task GetStatusAsync(string policyName, OperationRateLimitingContext? context = null) - { - if (!Options.IsEnabled) - { - return new OperationRateLimitingResult - { - IsAllowed = true, - RemainingCount = int.MaxValue, - MaxCount = int.MaxValue, - CurrentCount = 0 - }; - } - - context = EnsureContext(context); - var policy = await PolicyProvider.GetAsync(policyName); - var rules = CreateRules(policy); - var ruleResults = new List(); - - foreach (var rule in rules) - { - ruleResults.Add(await rule.CheckAsync(context)); - } - - return AggregateResults(ruleResults, policy); - } - - public virtual async Task ResetAsync(string policyName, OperationRateLimitingContext? context = null) - { - if (!Options.IsEnabled) - { - return; - } - - context = EnsureContext(context); - var policy = await PolicyProvider.GetAsync(policyName); - var rules = CreateRules(policy); - - foreach (var rule in rules) - { - await rule.ResetAsync(context); - } - } - - protected virtual OperationRateLimitingContext EnsureContext(OperationRateLimitingContext? context) - { - context ??= new OperationRateLimitingContext(); - context.ServiceProvider = ServiceProvider; - return context; - } - - protected virtual List CreateRules(OperationRateLimitingPolicy policy) - { - var rules = new List(); - - foreach (var ruleDefinition in policy.Rules) - { - rules.Add(new FixedWindowOperationRateLimitingRule( - policy.Name, - ruleDefinition, - Store, - CurrentUser, - CurrentTenant, - WebClientInfoProvider)); - } - - foreach (var customRuleType in policy.CustomRuleTypes) - { - rules.Add((IOperationRateLimitingRule)ServiceProvider.GetRequiredService(customRuleType)); - } - - return rules; - } - - protected virtual OperationRateLimitingResult AggregateResults( - List ruleResults, - OperationRateLimitingPolicy policy) - { - var isAllowed = ruleResults.All(r => r.IsAllowed); - var mostRestrictive = ruleResults - .OrderBy(r => r.RemainingCount) - .ThenByDescending(r => r.RetryAfter ?? TimeSpan.Zero) - .First(); - - return new OperationRateLimitingResult - { - IsAllowed = isAllowed, - RemainingCount = mostRestrictive.RemainingCount, - MaxCount = mostRestrictive.MaxCount, - CurrentCount = mostRestrictive.CurrentCount, - RetryAfter = ruleResults.Any(r => !r.IsAllowed && r.RetryAfter.HasValue) - ? ruleResults - .Where(r => !r.IsAllowed && r.RetryAfter.HasValue) - .Select(r => r.RetryAfter!.Value) - .Max() - : null, - WindowDuration = mostRestrictive.WindowDuration, - RuleResults = ruleResults - }; - } - - protected virtual void ThrowRateLimitException( - OperationRateLimitingPolicy policy, - OperationRateLimitingResult result, - OperationRateLimitingContext context) - { - var formatter = context.ServiceProvider.GetRequiredService(); - - var exception = new AbpOperationRateLimitingException( - policy.Name, - result, - policy.ErrorCode); - - if (result.RetryAfter.HasValue) - { - exception.SetRetryAfterFormatted(formatter.Format(result.RetryAfter.Value)); - } - - if (result.WindowDuration > TimeSpan.Zero) - { - exception.SetWindowDescriptionFormatted(formatter.Format(result.WindowDuration)); - } - - if (result.RuleResults != null) - { - var ruleDetails = new List>(); - foreach (var ruleResult in result.RuleResults) - { - ruleDetails.Add(new Dictionary - { - ["RuleName"] = ruleResult.RuleName, - ["IsAllowed"] = ruleResult.IsAllowed, - ["MaxCount"] = ruleResult.MaxCount, - ["RemainingCount"] = ruleResult.RemainingCount, - ["CurrentCount"] = ruleResult.CurrentCount, - ["WindowDurationSeconds"] = (int)ruleResult.WindowDuration.TotalSeconds, - ["WindowDescription"] = ruleResult.WindowDuration > TimeSpan.Zero - ? formatter.Format(ruleResult.WindowDuration) - : string.Empty, - ["RetryAfterSeconds"] = (int)(ruleResult.RetryAfter?.TotalSeconds ?? 0), - ["RetryAfter"] = ruleResult.RetryAfter.HasValue - ? formatter.Format(ruleResult.RetryAfter.Value) - : string.Empty - }); - } - - exception.WithData("RuleDetails", ruleDetails); - } - - foreach (var kvp in context.ExtraProperties) - { - exception.WithData(kvp.Key, kvp.Value!); - } - - throw exception; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingCheckerExtensions.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingCheckerExtensions.cs deleted file mode 100644 index df8d195aab..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingCheckerExtensions.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public static class OperationRateLimitingCheckerExtensions -{ - public static Task CheckAsync( - this IOperationRateLimitingChecker checker, - string policyName, - string parameter) - { - return checker.CheckAsync(policyName, new OperationRateLimitingContext { Parameter = parameter }); - } - - public static Task IsAllowedAsync( - this IOperationRateLimitingChecker checker, - string policyName, - string parameter) - { - return checker.IsAllowedAsync(policyName, new OperationRateLimitingContext { Parameter = parameter }); - } - - public static Task GetStatusAsync( - this IOperationRateLimitingChecker checker, - string policyName, - string parameter) - { - return checker.GetStatusAsync(policyName, new OperationRateLimitingContext { Parameter = parameter }); - } - - public static Task ResetAsync( - this IOperationRateLimitingChecker checker, - string policyName, - string parameter) - { - return checker.ResetAsync(policyName, new OperationRateLimitingContext { Parameter = parameter }); - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingContext.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingContext.cs deleted file mode 100644 index f75c06b05b..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingContext.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System; -using System.Collections.Generic; -using Microsoft.Extensions.DependencyInjection; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingContext -{ - /// - /// Optional parameter passed by the caller. - /// Used as the partition key by PartitionByParameter() (required), - /// and as a fallback by PartitionByEmail() and PartitionByPhoneNumber(). - /// Can be email, phone number, user id, resource id, or any string. - /// - public string? Parameter { get; set; } - - /// - /// Additional properties that can be read by custom implementations - /// and are forwarded to the exception's Data dictionary when the rate limit is exceeded. - /// - public Dictionary ExtraProperties { get; set; } = new(); - - /// - /// The service provider for resolving services. - /// Set automatically by the checker. - /// - public IServiceProvider ServiceProvider { get; set; } = default!; - - public T GetRequiredService() where T : notnull - => ServiceProvider.GetRequiredService(); - - public T? GetService() => ServiceProvider.GetService(); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingResult.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingResult.cs deleted file mode 100644 index 6659947099..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingResult.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingResult -{ - public bool IsAllowed { get; set; } - - public int RemainingCount { get; set; } - - public int MaxCount { get; set; } - - public int CurrentCount { get; set; } - - public TimeSpan? RetryAfter { get; set; } - - public TimeSpan WindowDuration { get; set; } - - /// - /// Detailed results per rule (for composite policies). - /// - public List? RuleResults { get; set; } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingRuleResult.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingRuleResult.cs deleted file mode 100644 index d725b8f7f2..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Checker/OperationRateLimitingRuleResult.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingRuleResult -{ - public string RuleName { get; set; } = default!; - - public bool IsAllowed { get; set; } - - public int CurrentCount { get; set; } - - public int RemainingCount { get; set; } - - public int MaxCount { get; set; } - - public TimeSpan? RetryAfter { get; set; } - - public TimeSpan WindowDuration { get; set; } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Exceptions/AbpOperationRateLimitingException.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Exceptions/AbpOperationRateLimitingException.cs deleted file mode 100644 index 88cfb2c6ff..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Exceptions/AbpOperationRateLimitingException.cs +++ /dev/null @@ -1,48 +0,0 @@ -using System; -using Volo.Abp.ExceptionHandling; - -namespace Volo.Abp.OperationRateLimiting; - -public class AbpOperationRateLimitingException : BusinessException, IHasHttpStatusCode -{ - public string PolicyName { get; } - - public OperationRateLimitingResult Result { get; } - - public int HttpStatusCode => 429; - - public AbpOperationRateLimitingException( - string policyName, - OperationRateLimitingResult result, - string? errorCode = null) - : base(code: errorCode ?? ResolveDefaultErrorCode(result)) - { - PolicyName = policyName; - Result = result; - - WithData("PolicyName", policyName); - WithData("MaxCount", result.MaxCount); - WithData("CurrentCount", result.CurrentCount); - WithData("RemainingCount", result.RemainingCount); - WithData("RetryAfterSeconds", (int)(result.RetryAfter?.TotalSeconds ?? 0)); - WithData("RetryAfterMinutes", (int)(result.RetryAfter?.TotalMinutes ?? 0)); - WithData("WindowDurationSeconds", (int)result.WindowDuration.TotalSeconds); - } - - internal void SetRetryAfterFormatted(string formattedRetryAfter) - { - WithData("RetryAfter", formattedRetryAfter); - } - - internal void SetWindowDescriptionFormatted(string formattedWindowDescription) - { - WithData("WindowDescription", formattedWindowDescription); - } - - private static string ResolveDefaultErrorCode(OperationRateLimitingResult result) - { - return result.RetryAfter.HasValue - ? AbpOperationRateLimitingErrorCodes.ExceedLimit - : AbpOperationRateLimitingErrorCodes.ExceedLimitPermanently; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/DefaultOperationRateLimitingFormatter.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/DefaultOperationRateLimitingFormatter.cs deleted file mode 100644 index e69dd7082b..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/DefaultOperationRateLimitingFormatter.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using Microsoft.Extensions.Localization; -using Volo.Abp.DependencyInjection; - -namespace Volo.Abp.OperationRateLimiting; - -public class DefaultOperationRateLimitingFormatter - : IOperationRateLimitingFormatter, ITransientDependency -{ - protected IStringLocalizer Localizer { get; } - - public DefaultOperationRateLimitingFormatter( - IStringLocalizer localizer) - { - Localizer = localizer; - } - - public virtual string Format(TimeSpan duration) - { - if (duration.TotalDays >= 365) - { - var years = (int)(duration.TotalDays / 365); - var remainingDays = (int)(duration.TotalDays % 365); - var months = remainingDays / 30; - return months > 0 - ? Localizer["RetryAfter:YearsAndMonths", years, months] - : Localizer["RetryAfter:Years", years]; - } - - if (duration.TotalDays >= 30) - { - var months = (int)(duration.TotalDays / 30); - var remainingDays = (int)(duration.TotalDays % 30); - return remainingDays > 0 - ? Localizer["RetryAfter:MonthsAndDays", months, remainingDays] - : Localizer["RetryAfter:Months", months]; - } - - if (duration.TotalDays >= 1) - { - var days = (int)duration.TotalDays; - var hours = duration.Hours; - return hours > 0 - ? Localizer["RetryAfter:DaysAndHours", days, hours] - : Localizer["RetryAfter:Days", days]; - } - - if (duration.TotalHours >= 1) - { - var hours = (int)duration.TotalHours; - var minutes = duration.Minutes; - return minutes > 0 - ? Localizer["RetryAfter:HoursAndMinutes", hours, minutes] - : Localizer["RetryAfter:Hours", hours]; - } - - if (duration.TotalMinutes >= 1) - { - var minutes = (int)duration.TotalMinutes; - var seconds = duration.Seconds; - return seconds > 0 - ? Localizer["RetryAfter:MinutesAndSeconds", minutes, seconds] - : Localizer["RetryAfter:Minutes", minutes]; - } - - return Localizer["RetryAfter:Seconds", (int)duration.TotalSeconds]; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/IOperationRateLimitingFormatter.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/IOperationRateLimitingFormatter.cs deleted file mode 100644 index 7e6370e215..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Formatting/IOperationRateLimitingFormatter.cs +++ /dev/null @@ -1,8 +0,0 @@ -using System; - -namespace Volo.Abp.OperationRateLimiting; - -public interface IOperationRateLimitingFormatter -{ - string Format(TimeSpan duration); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ar.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ar.json deleted file mode 100644 index 3ca1c8f042..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ar.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "ar", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "تم تجاوز حد معدل العملية. يمكنك المحاولة مرة أخرى بعد {RetryAfter}.", - "RetryAfter:Years": "{0} سنة/سنوات", - "RetryAfter:YearsAndMonths": "{0} سنة/سنوات و {1} شهر/أشهر", - "RetryAfter:Months": "{0} شهر/أشهر", - "RetryAfter:MonthsAndDays": "{0} شهر/أشهر و {1} يوم/أيام", - "RetryAfter:Days": "{0} يوم/أيام", - "RetryAfter:DaysAndHours": "{0} يوم/أيام و {1} ساعة/ساعات", - "RetryAfter:Hours": "{0} ساعة/ساعات", - "RetryAfter:HoursAndMinutes": "{0} ساعة/ساعات و {1} دقيقة/دقائق", - "RetryAfter:Minutes": "{0} دقيقة/دقائق", - "RetryAfter:MinutesAndSeconds": "{0} دقيقة/دقائق و {1} ثانية/ثوان", - "RetryAfter:Seconds": "{0} ثانية/ثوان", - "Volo.Abp.OperationRateLimiting:010002": "تم تجاوز حد معدل العملية. هذا الطلب مرفوض بشكل دائم." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/cs.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/cs.json deleted file mode 100644 index 44cfb86437..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/cs.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "cs", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Překročen limit rychlosti operace. Můžete to zkusit znovu za {RetryAfter}.", - "RetryAfter:Years": "{0} rok(y/let)", - "RetryAfter:YearsAndMonths": "{0} rok(y/let) a {1} měsíc(e/ů)", - "RetryAfter:Months": "{0} měsíc(e/ů)", - "RetryAfter:MonthsAndDays": "{0} měsíc(e/ů) a {1} den/dny/dní", - "RetryAfter:Days": "{0} den/dny/dní", - "RetryAfter:DaysAndHours": "{0} den/dny/dní a {1} hodina/hodiny/hodin", - "RetryAfter:Hours": "{0} hodina/hodiny/hodin", - "RetryAfter:HoursAndMinutes": "{0} hodina/hodiny/hodin a {1} minuta/minuty/minut", - "RetryAfter:Minutes": "{0} minuta/minuty/minut", - "RetryAfter:MinutesAndSeconds": "{0} minuta/minuty/minut a {1} sekunda/sekundy/sekund", - "RetryAfter:Seconds": "{0} sekunda/sekundy/sekund", - "Volo.Abp.OperationRateLimiting:010002": "Byl překročen limit četnosti operace. Tento požadavek je trvale zamítnut." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/de.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/de.json deleted file mode 100644 index 44286d68a8..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/de.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "de", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Betriebsratenlimit überschritten. Sie können es nach {RetryAfter} erneut versuchen.", - "RetryAfter:Years": "{0} Jahr(e)", - "RetryAfter:YearsAndMonths": "{0} Jahr(e) und {1} Monat(e)", - "RetryAfter:Months": "{0} Monat(e)", - "RetryAfter:MonthsAndDays": "{0} Monat(e) und {1} Tag(e)", - "RetryAfter:Days": "{0} Tag(e)", - "RetryAfter:DaysAndHours": "{0} Tag(e) und {1} Stunde(n)", - "RetryAfter:Hours": "{0} Stunde(n)", - "RetryAfter:HoursAndMinutes": "{0} Stunde(n) und {1} Minute(n)", - "RetryAfter:Minutes": "{0} Minute(n)", - "RetryAfter:MinutesAndSeconds": "{0} Minute(n) und {1} Sekunde(n)", - "RetryAfter:Seconds": "{0} Sekunde(n)", - "Volo.Abp.OperationRateLimiting:010002": "Das Vorgangshäufigkeitslimit wurde überschritten. Diese Anfrage wird dauerhaft abgelehnt." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/el.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/el.json deleted file mode 100644 index a688778eb5..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/el.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "el", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Υπέρβαση ορίου ρυθμού λειτουργίας. Μπορείτε να δοκιμάσετε ξανά μετά από {RetryAfter}.", - "RetryAfter:Years": "{0} έτος/η", - "RetryAfter:YearsAndMonths": "{0} έτος/η και {1} μήνας/ες", - "RetryAfter:Months": "{0} μήνας/ες", - "RetryAfter:MonthsAndDays": "{0} μήνας/ες και {1} ημέρα/ες", - "RetryAfter:Days": "{0} ημέρα/ες", - "RetryAfter:DaysAndHours": "{0} ημέρα/ες και {1} ώρα/ες", - "RetryAfter:Hours": "{0} ώρα/ες", - "RetryAfter:HoursAndMinutes": "{0} ώρα/ες και {1} λεπτό/ά", - "RetryAfter:Minutes": "{0} λεπτό/ά", - "RetryAfter:MinutesAndSeconds": "{0} λεπτό/ά και {1} δευτερόλεπτο/α", - "RetryAfter:Seconds": "{0} δευτερόλεπτο/α", - "Volo.Abp.OperationRateLimiting:010002": "Υπερβλήθηκε το όριο συχνότητας λειτουργίας. Αυτό το αίτημα απορρίπτεται μόνιμα." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en-GB.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en-GB.json deleted file mode 100644 index 4eab97f134..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en-GB.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "en-GB", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Operation rate limit exceeded. You can try again after {RetryAfter}.", - "RetryAfter:Years": "{0} year(s)", - "RetryAfter:YearsAndMonths": "{0} year(s) and {1} month(s)", - "RetryAfter:Months": "{0} month(s)", - "RetryAfter:MonthsAndDays": "{0} month(s) and {1} day(s)", - "RetryAfter:Days": "{0} day(s)", - "RetryAfter:DaysAndHours": "{0} day(s) and {1} hour(s)", - "RetryAfter:Hours": "{0} hour(s)", - "RetryAfter:HoursAndMinutes": "{0} hour(s) and {1} minute(s)", - "RetryAfter:Minutes": "{0} minute(s)", - "RetryAfter:MinutesAndSeconds": "{0} minute(s) and {1} second(s)", - "RetryAfter:Seconds": "{0} second(s)", - "Volo.Abp.OperationRateLimiting:010002": "Operation rate limit exceeded. This request is permanently denied." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en.json deleted file mode 100644 index fc41cabc2f..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/en.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "en", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Operation rate limit exceeded. You can try again after {RetryAfter}.", - "RetryAfter:Years": "{0} year(s)", - "RetryAfter:YearsAndMonths": "{0} year(s) and {1} month(s)", - "RetryAfter:Months": "{0} month(s)", - "RetryAfter:MonthsAndDays": "{0} month(s) and {1} day(s)", - "RetryAfter:Days": "{0} day(s)", - "RetryAfter:DaysAndHours": "{0} day(s) and {1} hour(s)", - "RetryAfter:Hours": "{0} hour(s)", - "RetryAfter:HoursAndMinutes": "{0} hour(s) and {1} minute(s)", - "RetryAfter:Minutes": "{0} minute(s)", - "RetryAfter:MinutesAndSeconds": "{0} minute(s) and {1} second(s)", - "RetryAfter:Seconds": "{0} second(s)", - "Volo.Abp.OperationRateLimiting:010002": "Operation rate limit exceeded. This request is permanently denied." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/es.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/es.json deleted file mode 100644 index ce13a9bceb..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/es.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "es", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Se ha excedido el límite de tasa de operación. Puede intentarlo de nuevo después de {RetryAfter}.", - "RetryAfter:Years": "{0} año(s)", - "RetryAfter:YearsAndMonths": "{0} año(s) y {1} mes(es)", - "RetryAfter:Months": "{0} mes(es)", - "RetryAfter:MonthsAndDays": "{0} mes(es) y {1} día(s)", - "RetryAfter:Days": "{0} día(s)", - "RetryAfter:DaysAndHours": "{0} día(s) y {1} hora(s)", - "RetryAfter:Hours": "{0} hora(s)", - "RetryAfter:HoursAndMinutes": "{0} hora(s) y {1} minuto(s)", - "RetryAfter:Minutes": "{0} minuto(s)", - "RetryAfter:MinutesAndSeconds": "{0} minuto(s) y {1} segundo(s)", - "RetryAfter:Seconds": "{0} segundo(s)", - "Volo.Abp.OperationRateLimiting:010002": "Se superó el límite de frecuencia de operación. Esta solicitud está permanentemente denegada." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fa.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fa.json deleted file mode 100644 index 0f200b5472..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fa.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "fa", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "محدودیت نرخ عملیات فراتر رفته است. می‌توانید بعد از {RetryAfter} دوباره تلاش کنید.", - "RetryAfter:Years": "{0} سال", - "RetryAfter:YearsAndMonths": "{0} سال و {1} ماه", - "RetryAfter:Months": "{0} ماه", - "RetryAfter:MonthsAndDays": "{0} ماه و {1} روز", - "RetryAfter:Days": "{0} روز", - "RetryAfter:DaysAndHours": "{0} روز و {1} ساعت", - "RetryAfter:Hours": "{0} ساعت", - "RetryAfter:HoursAndMinutes": "{0} ساعت و {1} دقیقه", - "RetryAfter:Minutes": "{0} دقیقه", - "RetryAfter:MinutesAndSeconds": "{0} دقیقه و {1} ثانیه", - "RetryAfter:Seconds": "{0} ثانیه", - "Volo.Abp.OperationRateLimiting:010002": "محدودیت نرخ عملیات از حد مجاز فراتر رفت. این درخواست به طور دائمی رد شده است." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fi.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fi.json deleted file mode 100644 index bcb88bf9ed..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fi.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "fi", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Toiminnon nopeusraja ylitetty. Voit yrittää uudelleen {RetryAfter} kuluttua.", - "RetryAfter:Years": "{0} vuosi/vuotta", - "RetryAfter:YearsAndMonths": "{0} vuosi/vuotta ja {1} kuukausi/kuukautta", - "RetryAfter:Months": "{0} kuukausi/kuukautta", - "RetryAfter:MonthsAndDays": "{0} kuukausi/kuukautta ja {1} päivä/päivää", - "RetryAfter:Days": "{0} päivä/päivää", - "RetryAfter:DaysAndHours": "{0} päivä/päivää ja {1} tunti/tuntia", - "RetryAfter:Hours": "{0} tunti/tuntia", - "RetryAfter:HoursAndMinutes": "{0} tunti/tuntia ja {1} minuutti/minuuttia", - "RetryAfter:Minutes": "{0} minuutti/minuuttia", - "RetryAfter:MinutesAndSeconds": "{0} minuutti/minuuttia ja {1} sekunti/sekuntia", - "RetryAfter:Seconds": "{0} sekunti/sekuntia", - "Volo.Abp.OperationRateLimiting:010002": "Toiminnan nopeusraja ylitettiin. Tämä pyyntö on pysyvästi hylätty." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fr.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fr.json deleted file mode 100644 index dca23d7a80..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/fr.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "fr", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Limite de taux d'opération dépassée. Vous pouvez réessayer après {RetryAfter}.", - "RetryAfter:Years": "{0} an(s)", - "RetryAfter:YearsAndMonths": "{0} an(s) et {1} mois", - "RetryAfter:Months": "{0} mois", - "RetryAfter:MonthsAndDays": "{0} mois et {1} jour(s)", - "RetryAfter:Days": "{0} jour(s)", - "RetryAfter:DaysAndHours": "{0} jour(s) et {1} heure(s)", - "RetryAfter:Hours": "{0} heure(s)", - "RetryAfter:HoursAndMinutes": "{0} heure(s) et {1} minute(s)", - "RetryAfter:Minutes": "{0} minute(s)", - "RetryAfter:MinutesAndSeconds": "{0} minute(s) et {1} seconde(s)", - "RetryAfter:Seconds": "{0} seconde(s)", - "Volo.Abp.OperationRateLimiting:010002": "La limite de fréquence d'opération a été dépassée. Cette demande est définitivement refusée." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hi.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hi.json deleted file mode 100644 index a84a1e44a8..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hi.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "hi", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "ऑपरेशन दर सीमा पार हो गई। आप {RetryAfter} के बाद पुनः प्रयास कर सकते हैं।", - "RetryAfter:Years": "{0} वर्ष", - "RetryAfter:YearsAndMonths": "{0} वर्ष और {1} महीना/महीने", - "RetryAfter:Months": "{0} महीना/महीने", - "RetryAfter:MonthsAndDays": "{0} महीना/महीने और {1} दिन", - "RetryAfter:Days": "{0} दिन", - "RetryAfter:DaysAndHours": "{0} दिन और {1} घंटा/घंटे", - "RetryAfter:Hours": "{0} घंटा/घंटे", - "RetryAfter:HoursAndMinutes": "{0} घंटा/घंटे और {1} मिनट", - "RetryAfter:Minutes": "{0} मिनट", - "RetryAfter:MinutesAndSeconds": "{0} मिनट और {1} सेकंड", - "RetryAfter:Seconds": "{0} सेकंड", - "Volo.Abp.OperationRateLimiting:010002": "ऑपरेशन दर सीमा पार हो गई। यह अनुरोध स्थायी रूप से अस्वीकृत है।" - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hr.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hr.json deleted file mode 100644 index c6597be78e..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hr.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "hr", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Prekoračeno ograničenje brzine operacije. Možete pokušati ponovo nakon {RetryAfter}.", - "RetryAfter:Years": "{0} godina/e", - "RetryAfter:YearsAndMonths": "{0} godina/e i {1} mjesec/i", - "RetryAfter:Months": "{0} mjesec/i", - "RetryAfter:MonthsAndDays": "{0} mjesec/i i {1} dan/a", - "RetryAfter:Days": "{0} dan/a", - "RetryAfter:DaysAndHours": "{0} dan/a i {1} sat/i", - "RetryAfter:Hours": "{0} sat/i", - "RetryAfter:HoursAndMinutes": "{0} sat/i i {1} minuta/e", - "RetryAfter:Minutes": "{0} minuta/e", - "RetryAfter:MinutesAndSeconds": "{0} minuta/e i {1} sekunda/e", - "RetryAfter:Seconds": "{0} sekunda/e", - "Volo.Abp.OperationRateLimiting:010002": "Prekoračeno je ograničenje brzine operacije. Ovaj zahtjev je trajno odbijen." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hu.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hu.json deleted file mode 100644 index f72dfea397..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/hu.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "hu", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "A műveleti sebességkorlát túllépve. Újra próbálkozhat {RetryAfter} múlva.", - "RetryAfter:Years": "{0} év", - "RetryAfter:YearsAndMonths": "{0} év és {1} hónap", - "RetryAfter:Months": "{0} hónap", - "RetryAfter:MonthsAndDays": "{0} hónap és {1} nap", - "RetryAfter:Days": "{0} nap", - "RetryAfter:DaysAndHours": "{0} nap és {1} óra", - "RetryAfter:Hours": "{0} óra", - "RetryAfter:HoursAndMinutes": "{0} óra és {1} perc", - "RetryAfter:Minutes": "{0} perc", - "RetryAfter:MinutesAndSeconds": "{0} perc és {1} másodperc", - "RetryAfter:Seconds": "{0} másodperc", - "Volo.Abp.OperationRateLimiting:010002": "A műveleti ráta korlátja túllépve. Ez a kérés véglegesen elutasítva." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/is.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/is.json deleted file mode 100644 index cce36e42cd..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/is.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "is", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Aðgerðarhraðatakmörk náð. Þú getur reynt aftur eftir {RetryAfter}.", - "RetryAfter:Years": "{0} ár", - "RetryAfter:YearsAndMonths": "{0} ár og {1} mánuð(ir)", - "RetryAfter:Months": "{0} mánuð(ur/ir)", - "RetryAfter:MonthsAndDays": "{0} mánuð(ur/ir) og {1} dag(ur/ar)", - "RetryAfter:Days": "{0} dag(ur/ar)", - "RetryAfter:DaysAndHours": "{0} dag(ur/ar) og {1} klukkustund(ir)", - "RetryAfter:Hours": "{0} klukkustund(ir)", - "RetryAfter:HoursAndMinutes": "{0} klukkustund(ir) og {1} mínúta/úr", - "RetryAfter:Minutes": "{0} mínúta/úr", - "RetryAfter:MinutesAndSeconds": "{0} mínúta/úr og {1} sekúnda/úr", - "RetryAfter:Seconds": "{0} sekúnda/úr", - "Volo.Abp.OperationRateLimiting:010002": "Farið var yfir takmörk á rekstrartíðni. Þessari beiðni er varanlega hafnað." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/it.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/it.json deleted file mode 100644 index f602fd1a66..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/it.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "it", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Limite di frequenza operazione superato. Puoi riprovare dopo {RetryAfter}.", - "RetryAfter:Years": "{0} anno/i", - "RetryAfter:YearsAndMonths": "{0} anno/i e {1} mese/i", - "RetryAfter:Months": "{0} mese/i", - "RetryAfter:MonthsAndDays": "{0} mese/i e {1} giorno/i", - "RetryAfter:Days": "{0} giorno/i", - "RetryAfter:DaysAndHours": "{0} giorno/i e {1} ora/e", - "RetryAfter:Hours": "{0} ora/e", - "RetryAfter:HoursAndMinutes": "{0} ora/e e {1} minuto/i", - "RetryAfter:Minutes": "{0} minuto/i", - "RetryAfter:MinutesAndSeconds": "{0} minuto/i e {1} secondo/i", - "RetryAfter:Seconds": "{0} secondo/i", - "Volo.Abp.OperationRateLimiting:010002": "Limite di frequenza operazione superato. Questa richiesta è permanentemente negata." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/nl.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/nl.json deleted file mode 100644 index bb21e7f313..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/nl.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "nl", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Bewerkingssnelheidslimiet overschreden. U kunt het opnieuw proberen na {RetryAfter}.", - "RetryAfter:Years": "{0} jaar", - "RetryAfter:YearsAndMonths": "{0} jaar en {1} maand(en)", - "RetryAfter:Months": "{0} maand(en)", - "RetryAfter:MonthsAndDays": "{0} maand(en) en {1} dag(en)", - "RetryAfter:Days": "{0} dag(en)", - "RetryAfter:DaysAndHours": "{0} dag(en) en {1} uur", - "RetryAfter:Hours": "{0} uur", - "RetryAfter:HoursAndMinutes": "{0} uur en {1} minuut/minuten", - "RetryAfter:Minutes": "{0} minuut/minuten", - "RetryAfter:MinutesAndSeconds": "{0} minuut/minuten en {1} seconde(n)", - "RetryAfter:Seconds": "{0} seconde(n)", - "Volo.Abp.OperationRateLimiting:010002": "Het bewerkingsfrequentielimiet is overschreden. Dit verzoek wordt permanent geweigerd." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pl-PL.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pl-PL.json deleted file mode 100644 index e4503f6aa7..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pl-PL.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "pl-PL", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Przekroczono limit częstotliwości operacji. Możesz spróbować ponownie po {RetryAfter}.", - "RetryAfter:Years": "{0} rok/lat", - "RetryAfter:YearsAndMonths": "{0} rok/lat i {1} miesiąc/miesięcy", - "RetryAfter:Months": "{0} miesiąc/miesięcy", - "RetryAfter:MonthsAndDays": "{0} miesiąc/miesięcy i {1} dzień/dni", - "RetryAfter:Days": "{0} dzień/dni", - "RetryAfter:DaysAndHours": "{0} dzień/dni i {1} godzina/godzin", - "RetryAfter:Hours": "{0} godzina/godzin", - "RetryAfter:HoursAndMinutes": "{0} godzina/godzin i {1} minuta/minut", - "RetryAfter:Minutes": "{0} minuta/minut", - "RetryAfter:MinutesAndSeconds": "{0} minuta/minut i {1} sekunda/sekund", - "RetryAfter:Seconds": "{0} sekunda/sekund", - "Volo.Abp.OperationRateLimiting:010002": "Przekroczono limit częstotliwości operacji. To żądanie jest trwale odrzucone." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pt-BR.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pt-BR.json deleted file mode 100644 index fb6f873805..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/pt-BR.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "pt-BR", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Limite de taxa de operação excedido. Você pode tentar novamente após {RetryAfter}.", - "RetryAfter:Years": "{0} ano(s)", - "RetryAfter:YearsAndMonths": "{0} ano(s) e {1} mês/meses", - "RetryAfter:Months": "{0} mês/meses", - "RetryAfter:MonthsAndDays": "{0} mês/meses e {1} dia(s)", - "RetryAfter:Days": "{0} dia(s)", - "RetryAfter:DaysAndHours": "{0} dia(s) e {1} hora(s)", - "RetryAfter:Hours": "{0} hora(s)", - "RetryAfter:HoursAndMinutes": "{0} hora(s) e {1} minuto(s)", - "RetryAfter:Minutes": "{0} minuto(s)", - "RetryAfter:MinutesAndSeconds": "{0} minuto(s) e {1} segundo(s)", - "RetryAfter:Seconds": "{0} segundo(s)", - "Volo.Abp.OperationRateLimiting:010002": "Limite de taxa de operação excedido. Esta solicitação está permanentemente negada." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ro-RO.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ro-RO.json deleted file mode 100644 index 178042fa85..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ro-RO.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "ro-RO", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Limita ratei de operare a fost depășită. Puteți încerca din nou după {RetryAfter}.", - "RetryAfter:Years": "{0} an/ani", - "RetryAfter:YearsAndMonths": "{0} an/ani și {1} lună/luni", - "RetryAfter:Months": "{0} lună/luni", - "RetryAfter:MonthsAndDays": "{0} lună/luni și {1} zi/zile", - "RetryAfter:Days": "{0} zi/zile", - "RetryAfter:DaysAndHours": "{0} zi/zile și {1} oră/ore", - "RetryAfter:Hours": "{0} oră/ore", - "RetryAfter:HoursAndMinutes": "{0} oră/ore și {1} minut(e)", - "RetryAfter:Minutes": "{0} minut(e)", - "RetryAfter:MinutesAndSeconds": "{0} minut(e) și {1} secundă/secunde", - "RetryAfter:Seconds": "{0} secundă/secunde", - "Volo.Abp.OperationRateLimiting:010002": "Limita de rată a operației a fost depășită. Această solicitare este permanent refuzată." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ru.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ru.json deleted file mode 100644 index 5260a9c90c..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/ru.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "ru", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Превышен лимит частоты операций. Вы можете повторить попытку через {RetryAfter}.", - "RetryAfter:Years": "{0} год/лет", - "RetryAfter:YearsAndMonths": "{0} год/лет и {1} месяц/месяцев", - "RetryAfter:Months": "{0} месяц/месяцев", - "RetryAfter:MonthsAndDays": "{0} месяц/месяцев и {1} день/дней", - "RetryAfter:Days": "{0} день/дней", - "RetryAfter:DaysAndHours": "{0} день/дней и {1} час/часов", - "RetryAfter:Hours": "{0} час/часов", - "RetryAfter:HoursAndMinutes": "{0} час/часов и {1} минута/минут", - "RetryAfter:Minutes": "{0} минута/минут", - "RetryAfter:MinutesAndSeconds": "{0} минута/минут и {1} секунда/секунд", - "RetryAfter:Seconds": "{0} секунда/секунд", - "Volo.Abp.OperationRateLimiting:010002": "Превышен лимит частоты операций. Этот запрос постоянно отклонён." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sk.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sk.json deleted file mode 100644 index 73cdbb2b5d..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sk.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "sk", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Prekročený limit rýchlosti operácie. Môžete to skúsiť znova po {RetryAfter}.", - "RetryAfter:Years": "{0} rok/rokov", - "RetryAfter:YearsAndMonths": "{0} rok/rokov a {1} mesiac/mesiacov", - "RetryAfter:Months": "{0} mesiac/mesiacov", - "RetryAfter:MonthsAndDays": "{0} mesiac/mesiacov a {1} deň/dní", - "RetryAfter:Days": "{0} deň/dní", - "RetryAfter:DaysAndHours": "{0} deň/dní a {1} hodina/hodín", - "RetryAfter:Hours": "{0} hodina/hodín", - "RetryAfter:HoursAndMinutes": "{0} hodina/hodín a {1} minúta/minút", - "RetryAfter:Minutes": "{0} minúta/minút", - "RetryAfter:MinutesAndSeconds": "{0} minúta/minút a {1} sekunda/sekúnd", - "RetryAfter:Seconds": "{0} sekunda/sekúnd", - "Volo.Abp.OperationRateLimiting:010002": "Bol prekročený limit frekvencie operácie. Táto požiadavka je trvalo zamietnutá." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sl.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sl.json deleted file mode 100644 index 333f51efb5..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sl.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "sl", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Presežena omejitev hitrosti operacije. Poskusite lahko znova čez {RetryAfter}.", - "RetryAfter:Years": "{0} leto/let", - "RetryAfter:YearsAndMonths": "{0} leto/let in {1} mesec/mesecev", - "RetryAfter:Months": "{0} mesec/mesecev", - "RetryAfter:MonthsAndDays": "{0} mesec/mesecev in {1} dan/dni", - "RetryAfter:Days": "{0} dan/dni", - "RetryAfter:DaysAndHours": "{0} dan/dni in {1} ura/ur", - "RetryAfter:Hours": "{0} ura/ur", - "RetryAfter:HoursAndMinutes": "{0} ura/ur in {1} minuta/minut", - "RetryAfter:Minutes": "{0} minuta/minut", - "RetryAfter:MinutesAndSeconds": "{0} minuta/minut in {1} sekunda/sekund", - "RetryAfter:Seconds": "{0} sekunda/sekund", - "Volo.Abp.OperationRateLimiting:010002": "Prekoračena je omejitev hitrosti operacije. Ta zahteva je trajno zavrnjena." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sv.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sv.json deleted file mode 100644 index ef5172867c..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/sv.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "sv", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Hastighetsgränsen för operationen har överskridits. Du kan försöka igen efter {RetryAfter}.", - "RetryAfter:Years": "{0} år", - "RetryAfter:YearsAndMonths": "{0} år och {1} månad(er)", - "RetryAfter:Months": "{0} månad(er)", - "RetryAfter:MonthsAndDays": "{0} månad(er) och {1} dag(ar)", - "RetryAfter:Days": "{0} dag(ar)", - "RetryAfter:DaysAndHours": "{0} dag(ar) och {1} timme/timmar", - "RetryAfter:Hours": "{0} timme/timmar", - "RetryAfter:HoursAndMinutes": "{0} timme/timmar och {1} minut(er)", - "RetryAfter:Minutes": "{0} minut(er)", - "RetryAfter:MinutesAndSeconds": "{0} minut(er) och {1} sekund(er)", - "RetryAfter:Seconds": "{0} sekund(er)", - "Volo.Abp.OperationRateLimiting:010002": "Hastighetsgränsen för operationen har överskridits. Denna förfrågan är permanent nekad." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/tr.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/tr.json deleted file mode 100644 index 0480003f9c..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/tr.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "tr", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "İşlem hız sınırı aşıldı. {RetryAfter} sonra tekrar deneyebilirsiniz.", - "RetryAfter:Years": "{0} yıl", - "RetryAfter:YearsAndMonths": "{0} yıl ve {1} ay", - "RetryAfter:Months": "{0} ay", - "RetryAfter:MonthsAndDays": "{0} ay ve {1} gün", - "RetryAfter:Days": "{0} gün", - "RetryAfter:DaysAndHours": "{0} gün ve {1} saat", - "RetryAfter:Hours": "{0} saat", - "RetryAfter:HoursAndMinutes": "{0} saat ve {1} dakika", - "RetryAfter:Minutes": "{0} dakika", - "RetryAfter:MinutesAndSeconds": "{0} dakika ve {1} saniye", - "RetryAfter:Seconds": "{0} saniye", - "Volo.Abp.OperationRateLimiting:010002": "İşlem hızı sınırı aşıldı. Bu istek kalıcı olarak reddedildi." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/vi.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/vi.json deleted file mode 100644 index 53059f819c..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/vi.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "vi", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "Đã vượt quá giới hạn tốc độ thao tác. Bạn có thể thử lại sau {RetryAfter}.", - "RetryAfter:Years": "{0} năm", - "RetryAfter:YearsAndMonths": "{0} năm và {1} tháng", - "RetryAfter:Months": "{0} tháng", - "RetryAfter:MonthsAndDays": "{0} tháng và {1} ngày", - "RetryAfter:Days": "{0} ngày", - "RetryAfter:DaysAndHours": "{0} ngày và {1} giờ", - "RetryAfter:Hours": "{0} giờ", - "RetryAfter:HoursAndMinutes": "{0} giờ và {1} phút", - "RetryAfter:Minutes": "{0} phút", - "RetryAfter:MinutesAndSeconds": "{0} phút và {1} giây", - "RetryAfter:Seconds": "{0} giây", - "Volo.Abp.OperationRateLimiting:010002": "Vượt quá giới hạn tần suất thao tác. Yêu cầu này bị từ chối vĩnh viễn." - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/zh-Hans.json b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/zh-Hans.json deleted file mode 100644 index 632d0e438f..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Localization/zh-Hans.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "culture": "zh-Hans", - "texts": { - "Volo.Abp.OperationRateLimiting:010001": "操作频率超出限制。请在 {RetryAfter} 后重试。", - "RetryAfter:Years": "{0} 年", - "RetryAfter:YearsAndMonths": "{0} 年 {1} 个月", - "RetryAfter:Months": "{0} 个月", - "RetryAfter:MonthsAndDays": "{0} 个月 {1} 天", - "RetryAfter:Days": "{0} 天", - "RetryAfter:DaysAndHours": "{0} 天 {1} 小时", - "RetryAfter:Hours": "{0} 小时", - "RetryAfter:HoursAndMinutes": "{0} 小时 {1} 分钟", - "RetryAfter:Minutes": "{0} 分钟", - "RetryAfter:MinutesAndSeconds": "{0} 分钟 {1} 秒", - "RetryAfter:Seconds": "{0} 秒", - "Volo.Abp.OperationRateLimiting:010002": "操作频率超出限制。此请求已被永久拒绝。" - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/DefaultOperationRateLimitingPolicyProvider.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/DefaultOperationRateLimitingPolicyProvider.cs deleted file mode 100644 index 305863381a..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/DefaultOperationRateLimitingPolicyProvider.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System.Collections.Generic; -using System.Linq; -using System.Threading.Tasks; -using Microsoft.Extensions.Options; -using Volo.Abp.DependencyInjection; - -namespace Volo.Abp.OperationRateLimiting; - -public class DefaultOperationRateLimitingPolicyProvider : IOperationRateLimitingPolicyProvider, ITransientDependency -{ - protected AbpOperationRateLimitingOptions Options { get; } - - public DefaultOperationRateLimitingPolicyProvider(IOptions options) - { - Options = options.Value; - } - - public virtual Task GetAsync(string policyName) - { - if (!Options.Policies.TryGetValue(policyName, out var policy)) - { - throw new AbpException( - $"Operation rate limit policy '{policyName}' was not found. " + - $"Make sure to configure it using AbpOperationRateLimitingOptions.AddPolicy()."); - } - - return Task.FromResult(policy); - } - - public virtual Task> GetListAsync() - { - return Task.FromResult(Options.Policies.Values.ToList()); - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/IOperationRateLimitingPolicyProvider.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/IOperationRateLimitingPolicyProvider.cs deleted file mode 100644 index 1f87137a68..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/IOperationRateLimitingPolicyProvider.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System.Collections.Generic; -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public interface IOperationRateLimitingPolicyProvider -{ - Task GetAsync(string policyName); - - Task> GetListAsync(); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPartitionType.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPartitionType.cs deleted file mode 100644 index e330bd8e46..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPartitionType.cs +++ /dev/null @@ -1,12 +0,0 @@ -namespace Volo.Abp.OperationRateLimiting; - -public enum OperationRateLimitingPartitionType -{ - Parameter, - CurrentUser, - CurrentTenant, - ClientIp, - Email, - PhoneNumber, - Custom -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicy.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicy.cs deleted file mode 100644 index 45634e5de1..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicy.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingPolicy -{ - public string Name { get; set; } = default!; - - public string? ErrorCode { get; set; } - - public List Rules { get; set; } = new(); - - public List CustomRuleTypes { get; set; } = new(); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicyBuilder.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicyBuilder.cs deleted file mode 100644 index 72cb247614..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingPolicyBuilder.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingPolicyBuilder -{ - private readonly string _name; - private string? _errorCode; - private readonly List _rules = new(); - private readonly List _customRuleTypes = new(); - - public OperationRateLimitingPolicyBuilder(string name) - { - _name = Check.NotNullOrWhiteSpace(name, nameof(name)); - } - - /// - /// Add a built-in rule. Multiple rules are AND-combined. - /// - public OperationRateLimitingPolicyBuilder AddRule( - Action configure) - { - var builder = new OperationRateLimitingRuleBuilder(this); - configure(builder); - if (!builder.IsCommitted) - { - _rules.Add(builder.Build()); - } - return this; - } - - /// - /// Add a custom rule type (resolved from DI). - /// - public OperationRateLimitingPolicyBuilder AddRule() - where TRule : class, IOperationRateLimitingRule - { - _customRuleTypes.Add(typeof(TRule)); - return this; - } - - /// - /// Shortcut: single-rule policy with fixed window. - /// Returns the rule builder for partition configuration. - /// - public OperationRateLimitingRuleBuilder WithFixedWindow( - TimeSpan duration, int maxCount) - { - var builder = new OperationRateLimitingRuleBuilder(this); - builder.WithFixedWindow(duration, maxCount); - return builder; - } - - /// - /// Set a custom ErrorCode for this policy's exception. - /// - public OperationRateLimitingPolicyBuilder WithErrorCode(string errorCode) - { - _errorCode = Check.NotNullOrWhiteSpace(errorCode, nameof(errorCode)); - return this; - } - - internal void AddRuleDefinition(OperationRateLimitingRuleDefinition definition) - { - _rules.Add(definition); - } - - internal OperationRateLimitingPolicy Build() - { - if (_rules.Count == 0 && _customRuleTypes.Count == 0) - { - throw new AbpException( - $"Operation rate limit policy '{_name}' has no rules. " + - "Call AddRule() or WithFixedWindow(...).PartitionBy*() to add at least one rule."); - } - - var duplicate = _rules - .Where(r => r.PartitionType != OperationRateLimitingPartitionType.Custom) - .GroupBy(r => (r.Duration, r.MaxCount, r.PartitionType, r.IsMultiTenant)) - .FirstOrDefault(g => g.Count() > 1); - - if (duplicate != null) - { - var (duration, maxCount, partitionType, isMultiTenant) = duplicate.Key; - throw new AbpException( - $"Operation rate limit policy '{_name}' has duplicate rules with the same " + - $"Duration ({duration}), MaxCount ({maxCount}), PartitionType ({partitionType}), " + - $"and IsMultiTenant ({isMultiTenant}). " + - "Each rule in a policy must have a unique combination of these properties."); - } - - return new OperationRateLimitingPolicy - { - Name = _name, - ErrorCode = _errorCode, - Rules = new List(_rules), - CustomRuleTypes = new List(_customRuleTypes) - }; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleBuilder.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleBuilder.cs deleted file mode 100644 index b9f2eacf9a..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleBuilder.cs +++ /dev/null @@ -1,157 +0,0 @@ -using System; -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingRuleBuilder -{ - private readonly OperationRateLimitingPolicyBuilder _policyBuilder; - private TimeSpan _duration; - private int _maxCount; - private OperationRateLimitingPartitionType? _partitionType; - private Func>? _customPartitionKeyResolver; - private bool _isMultiTenant; - - internal bool IsCommitted { get; private set; } - - internal OperationRateLimitingRuleBuilder(OperationRateLimitingPolicyBuilder policyBuilder) - { - _policyBuilder = policyBuilder; - } - - public OperationRateLimitingRuleBuilder WithFixedWindow( - TimeSpan duration, int maxCount) - { - _duration = duration; - _maxCount = maxCount; - return this; - } - - public OperationRateLimitingRuleBuilder WithMultiTenancy() - { - _isMultiTenant = true; - return this; - } - - /// - /// Use context.Parameter as partition key. - /// - public OperationRateLimitingPolicyBuilder PartitionByParameter() - { - _partitionType = OperationRateLimitingPartitionType.Parameter; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Partition by the current authenticated user (ICurrentUser.Id). - /// Use PartitionByParameter() if you need to specify the user ID explicitly. - /// - public OperationRateLimitingPolicyBuilder PartitionByCurrentUser() - { - _partitionType = OperationRateLimitingPartitionType.CurrentUser; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Partition by the current tenant (ICurrentTenant.Id). Uses "host" when no tenant is active. - /// - public OperationRateLimitingPolicyBuilder PartitionByCurrentTenant() - { - _partitionType = OperationRateLimitingPartitionType.CurrentTenant; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Partition by the client IP address (IWebClientInfoProvider.ClientIpAddress). - /// Use PartitionByParameter() if you need to specify the IP explicitly. - /// - public OperationRateLimitingPolicyBuilder PartitionByClientIp() - { - _partitionType = OperationRateLimitingPartitionType.ClientIp; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Partition by email address. - /// Resolves from context.Parameter, falls back to ICurrentUser.Email. - /// - public OperationRateLimitingPolicyBuilder PartitionByEmail() - { - _partitionType = OperationRateLimitingPartitionType.Email; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Partition by phone number. - /// Resolves from context.Parameter, falls back to ICurrentUser.PhoneNumber. - /// - public OperationRateLimitingPolicyBuilder PartitionByPhoneNumber() - { - _partitionType = OperationRateLimitingPartitionType.PhoneNumber; - CommitToPolicyBuilder(); - return _policyBuilder; - } - - /// - /// Custom async partition key resolver from context. - /// - public OperationRateLimitingPolicyBuilder PartitionBy( - Func> keyResolver) - { - _partitionType = OperationRateLimitingPartitionType.Custom; - _customPartitionKeyResolver = Check.NotNull(keyResolver, nameof(keyResolver)); - CommitToPolicyBuilder(); - return _policyBuilder; - } - - protected virtual void CommitToPolicyBuilder() - { - _policyBuilder.AddRuleDefinition(Build()); - IsCommitted = true; - } - - internal OperationRateLimitingRuleDefinition Build() - { - if (_duration <= TimeSpan.Zero) - { - throw new AbpException( - "Operation rate limit rule requires a positive duration. " + - "Call WithFixedWindow(duration, maxCount) before building the rule."); - } - - if (_maxCount < 0) - { - throw new AbpException( - "Operation rate limit rule requires maxCount >= 0. " + - "Use maxCount: 0 to completely deny all requests (ban policy)."); - } - - if (!_partitionType.HasValue) - { - throw new AbpException( - "Operation rate limit rule requires a partition type. " + - "Call PartitionByParameter(), PartitionByCurrentUser(), PartitionByClientIp(), or another PartitionBy*() method."); - } - - if (_partitionType == OperationRateLimitingPartitionType.Custom && _customPartitionKeyResolver == null) - { - throw new AbpException( - "Custom partition type requires a key resolver. " + - "Call PartitionBy(keyResolver) instead of setting partition type directly."); - } - - return new OperationRateLimitingRuleDefinition - { - Duration = _duration, - MaxCount = _maxCount, - PartitionType = _partitionType.Value, - CustomPartitionKeyResolver = _customPartitionKeyResolver, - IsMultiTenant = _isMultiTenant - }; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleDefinition.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleDefinition.cs deleted file mode 100644 index f8d1bcf9e7..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Policies/OperationRateLimitingRuleDefinition.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingRuleDefinition -{ - public TimeSpan Duration { get; set; } - - public int MaxCount { get; set; } - - public OperationRateLimitingPartitionType PartitionType { get; set; } - - public Func>? CustomPartitionKeyResolver { get; set; } - - public bool IsMultiTenant { get; set; } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/FixedWindowOperationRateLimitingRule.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/FixedWindowOperationRateLimitingRule.cs deleted file mode 100644 index bd869e2c5b..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/FixedWindowOperationRateLimitingRule.cs +++ /dev/null @@ -1,147 +0,0 @@ -using System.Threading.Tasks; -using Volo.Abp.AspNetCore.WebClientInfo; -using Volo.Abp.MultiTenancy; -using Volo.Abp.Users; - -namespace Volo.Abp.OperationRateLimiting; - -public class FixedWindowOperationRateLimitingRule : IOperationRateLimitingRule -{ - private const string HostTenantKey = "host"; - - protected string PolicyName { get; } - protected OperationRateLimitingRuleDefinition Definition { get; } - protected IOperationRateLimitingStore Store { get; } - protected ICurrentUser CurrentUser { get; } - protected ICurrentTenant CurrentTenant { get; } - protected IWebClientInfoProvider WebClientInfoProvider { get; } - - public FixedWindowOperationRateLimitingRule( - string policyName, - OperationRateLimitingRuleDefinition definition, - IOperationRateLimitingStore store, - ICurrentUser currentUser, - ICurrentTenant currentTenant, - IWebClientInfoProvider webClientInfoProvider) - { - PolicyName = policyName; - Definition = definition; - Store = store; - CurrentUser = currentUser; - CurrentTenant = currentTenant; - WebClientInfoProvider = webClientInfoProvider; - } - - public virtual async Task AcquireAsync( - OperationRateLimitingContext context) - { - var partitionKey = await ResolvePartitionKeyAsync(context); - var storeKey = BuildStoreKey(partitionKey); - var storeResult = await Store.IncrementAsync(storeKey, Definition.Duration, Definition.MaxCount); - - return ToRuleResult(storeResult); - } - - public virtual async Task CheckAsync( - OperationRateLimitingContext context) - { - var partitionKey = await ResolvePartitionKeyAsync(context); - var storeKey = BuildStoreKey(partitionKey); - var storeResult = await Store.GetAsync(storeKey, Definition.Duration, Definition.MaxCount); - - return ToRuleResult(storeResult); - } - - public virtual async Task ResetAsync(OperationRateLimitingContext context) - { - var partitionKey = await ResolvePartitionKeyAsync(context); - var storeKey = BuildStoreKey(partitionKey); - await Store.ResetAsync(storeKey); - } - - protected virtual async Task ResolvePartitionKeyAsync(OperationRateLimitingContext context) - { - return Definition.PartitionType switch - { - OperationRateLimitingPartitionType.Parameter => - context.Parameter ?? throw new AbpException( - $"OperationRateLimitingContext.Parameter is required for policy '{PolicyName}' (PartitionByParameter)."), - - OperationRateLimitingPartitionType.CurrentUser => - CurrentUser.Id?.ToString() - ?? throw new AbpException( - $"Current user is not authenticated. Policy '{PolicyName}' requires PartitionByCurrentUser. " + - "Use PartitionByParameter() if you need to specify the user ID explicitly."), - - OperationRateLimitingPartitionType.CurrentTenant => - CurrentTenant.Id?.ToString() - ?? HostTenantKey, - - OperationRateLimitingPartitionType.ClientIp => - WebClientInfoProvider.ClientIpAddress - ?? throw new AbpException( - $"Client IP address could not be determined. Policy '{PolicyName}' requires PartitionByClientIp. " + - "Ensure IWebClientInfoProvider is properly configured or use PartitionByParameter() to pass the IP explicitly."), - - OperationRateLimitingPartitionType.Email => - context.Parameter - ?? CurrentUser.Email - ?? throw new AbpException( - $"Email is required for policy '{PolicyName}' (PartitionByEmail). Provide it via context.Parameter or ensure the user has an email."), - - OperationRateLimitingPartitionType.PhoneNumber => - context.Parameter - ?? CurrentUser.PhoneNumber - ?? throw new AbpException( - $"Phone number is required for policy '{PolicyName}' (PartitionByPhoneNumber). Provide it via context.Parameter or ensure the user has a phone number."), - - OperationRateLimitingPartitionType.Custom => - await ResolveCustomPartitionKeyAsync(context), - - _ => throw new AbpException($"Unknown partition type: {Definition.PartitionType}") - }; - } - - protected virtual async Task ResolveCustomPartitionKeyAsync(OperationRateLimitingContext context) - { - var key = await Definition.CustomPartitionKeyResolver!(context); - if (string.IsNullOrEmpty(key)) - { - throw new AbpException( - $"Custom partition key resolver returned null or empty for policy '{PolicyName}'. " + - "The resolver must return a non-empty string."); - } - return key; - } - - protected virtual string BuildStoreKey(string partitionKey) - { - // Stable rule descriptor based on content so reordering rules does not change the key. - // Changing Duration or MaxCount intentionally resets counters for that rule. - var ruleKey = $"{(long)Definition.Duration.TotalSeconds}_{Definition.MaxCount}_{(int)Definition.PartitionType}"; - - // Tenant isolation is opt-in via WithMultiTenancy() on the rule builder. - // When not set, the key is global (shared across all tenants). - if (!Definition.IsMultiTenant) - { - return $"orl:{PolicyName}:{ruleKey}:{partitionKey}"; - } - - var tenantId = CurrentTenant.Id.HasValue ? CurrentTenant.Id.Value.ToString() : HostTenantKey; - return $"orl:t:{tenantId}:{PolicyName}:{ruleKey}:{partitionKey}"; - } - - protected virtual OperationRateLimitingRuleResult ToRuleResult(OperationRateLimitingStoreResult storeResult) - { - return new OperationRateLimitingRuleResult - { - RuleName = $"{PolicyName}:Rule[{(long)Definition.Duration.TotalSeconds}s,{Definition.MaxCount},{Definition.PartitionType}]", - IsAllowed = storeResult.IsAllowed, - CurrentCount = storeResult.CurrentCount, - RemainingCount = storeResult.MaxCount - storeResult.CurrentCount, - MaxCount = storeResult.MaxCount, - RetryAfter = storeResult.RetryAfter, - WindowDuration = Definition.Duration - }; - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/IOperationRateLimitingRule.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/IOperationRateLimitingRule.cs deleted file mode 100644 index 1bb42a1727..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Rules/IOperationRateLimitingRule.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public interface IOperationRateLimitingRule -{ - Task AcquireAsync(OperationRateLimitingContext context); - - Task CheckAsync(OperationRateLimitingContext context); - - Task ResetAsync(OperationRateLimitingContext context); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/DistributedCacheOperationRateLimitingStore.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/DistributedCacheOperationRateLimitingStore.cs deleted file mode 100644 index d9f13b41d1..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/DistributedCacheOperationRateLimitingStore.cs +++ /dev/null @@ -1,155 +0,0 @@ -using System; -using System.Threading.Tasks; -using Microsoft.Extensions.Caching.Distributed; -using Microsoft.Extensions.Options; -using Volo.Abp.Caching; -using Volo.Abp.DependencyInjection; -using Volo.Abp.DistributedLocking; -using Volo.Abp.Timing; - -namespace Volo.Abp.OperationRateLimiting; - -public class DistributedCacheOperationRateLimitingStore : IOperationRateLimitingStore, ITransientDependency -{ - protected IDistributedCache Cache { get; } - protected IClock Clock { get; } - protected IAbpDistributedLock DistributedLock { get; } - protected AbpOperationRateLimitingOptions Options { get; } - - public DistributedCacheOperationRateLimitingStore( - IDistributedCache cache, - IClock clock, - IAbpDistributedLock distributedLock, - IOptions options) - { - Cache = cache; - Clock = clock; - DistributedLock = distributedLock; - Options = options.Value; - } - - public virtual async Task IncrementAsync( - string key, TimeSpan duration, int maxCount) - { - if (maxCount <= 0) - { - return new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = 0, - MaxCount = maxCount, - RetryAfter = null - }; - } - - await using (var handle = await DistributedLock.TryAcquireAsync( - $"OperationRateLimiting:{key}", Options.LockTimeout)) - { - if (handle == null) - { - throw new AbpException( - "Could not acquire distributed lock for operation rate limit. " + - "This is an infrastructure issue, not a rate limit violation."); - } - - var cacheItem = await Cache.GetAsync(key); - var now = new DateTimeOffset(Clock.Now.ToUniversalTime()); - - if (cacheItem == null || now >= cacheItem.WindowStart.Add(duration)) - { - cacheItem = new OperationRateLimitingCacheItem { Count = 1, WindowStart = now }; - await Cache.SetAsync(key, cacheItem, - new DistributedCacheEntryOptions - { - AbsoluteExpirationRelativeToNow = duration - }); - - return new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = 1, - MaxCount = maxCount - }; - } - - if (cacheItem.Count >= maxCount) - { - var retryAfter = cacheItem.WindowStart.Add(duration) - now; - return new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = cacheItem.Count, - MaxCount = maxCount, - RetryAfter = retryAfter - }; - } - - cacheItem.Count++; - var expiration = cacheItem.WindowStart.Add(duration) - now; - await Cache.SetAsync(key, cacheItem, - new DistributedCacheEntryOptions - { - AbsoluteExpirationRelativeToNow = expiration > TimeSpan.Zero ? expiration : duration - }); - - return new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = cacheItem.Count, - MaxCount = maxCount - }; - } - } - - public virtual async Task GetAsync( - string key, TimeSpan duration, int maxCount) - { - if (maxCount <= 0) - { - return new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = 0, - MaxCount = maxCount, - RetryAfter = null - }; - } - - var cacheItem = await Cache.GetAsync(key); - var now = new DateTimeOffset(Clock.Now.ToUniversalTime()); - - if (cacheItem == null || now >= cacheItem.WindowStart.Add(duration)) - { - return new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = 0, - MaxCount = maxCount - }; - } - - if (cacheItem.Count >= maxCount) - { - var retryAfter = cacheItem.WindowStart.Add(duration) - now; - return new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = cacheItem.Count, - MaxCount = maxCount, - RetryAfter = retryAfter - }; - } - - return new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = cacheItem.Count, - MaxCount = maxCount - }; - } - - public virtual async Task ResetAsync(string key) - { - await Cache.RemoveAsync(key); - } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/IOperationRateLimitingStore.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/IOperationRateLimitingStore.cs deleted file mode 100644 index 049fa35b0c..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/IOperationRateLimitingStore.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; -using System.Threading.Tasks; - -namespace Volo.Abp.OperationRateLimiting; - -public interface IOperationRateLimitingStore -{ - Task IncrementAsync(string key, TimeSpan duration, int maxCount); - - Task GetAsync(string key, TimeSpan duration, int maxCount); - - Task ResetAsync(string key); -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingCacheItem.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingCacheItem.cs deleted file mode 100644 index 2d92d8578e..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingCacheItem.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using Volo.Abp.Caching; -using Volo.Abp.MultiTenancy; - -namespace Volo.Abp.OperationRateLimiting; - -[CacheName("OperationRateLimiting")] -[IgnoreMultiTenancy] -public class OperationRateLimitingCacheItem -{ - public int Count { get; set; } - - public DateTimeOffset WindowStart { get; set; } -} diff --git a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingStoreResult.cs b/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingStoreResult.cs deleted file mode 100644 index caa2bd640d..0000000000 --- a/framework/src/Volo.Abp.OperationRateLimiting/Volo/Abp/OperationRateLimiting/Store/OperationRateLimitingStoreResult.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingStoreResult -{ - public bool IsAllowed { get; set; } - - public int CurrentCount { get; set; } - - public int MaxCount { get; set; } - - public TimeSpan? RetryAfter { get; set; } -} diff --git a/framework/src/Volo.Abp.TickerQ/Volo/Abp/TickerQ/AbpTickerQFunctionProvider.cs b/framework/src/Volo.Abp.TickerQ/Volo/Abp/TickerQ/AbpTickerQFunctionProvider.cs index b92888e533..b6b05e7787 100644 --- a/framework/src/Volo.Abp.TickerQ/Volo/Abp/TickerQ/AbpTickerQFunctionProvider.cs +++ b/framework/src/Volo.Abp.TickerQ/Volo/Abp/TickerQ/AbpTickerQFunctionProvider.cs @@ -8,13 +8,33 @@ namespace Volo.Abp.TickerQ; public class AbpTickerQFunctionProvider : ISingletonDependency { - public Dictionary Functions { get;} + public Dictionary Functions { get; } - public Dictionary RequestTypes { get; } + public Dictionary RequestTypes { get; } public AbpTickerQFunctionProvider() { - Functions = new Dictionary(); + Functions = new Dictionary(); RequestTypes = new Dictionary(); } + + public void AddFunction( + string name, + TickerFunctionDelegate function, + TickerTaskPriority priority = TickerTaskPriority.Normal, + int maxConcurrency = 0) + { + Check.NotNullOrWhiteSpace(name, nameof(name)); + Check.NotNull(function, nameof(function)); + + if (maxConcurrency < 0) + { + throw new ArgumentException("maxConcurrency must be greater than or equal to 0.", nameof(maxConcurrency)); + } + + if (!Functions.TryAdd(name, (string.Empty, priority, function, maxConcurrency))) + { + throw new AbpException($"A function with the name '{name}' is already registered."); + } + } } diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo.Abp.AspNetCore.Mvc.Tests.csproj b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo.Abp.AspNetCore.Mvc.Tests.csproj index 347da6f0bd..8a929dd38a 100644 --- a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo.Abp.AspNetCore.Mvc.Tests.csproj +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo.Abp.AspNetCore.Mvc.Tests.csproj @@ -26,6 +26,7 @@ + diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/AbpAspNetCoreMvcTestModule.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/AbpAspNetCoreMvcTestModule.cs index 1c705d8df3..9154608680 100644 --- a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/AbpAspNetCoreMvcTestModule.cs +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/AbpAspNetCoreMvcTestModule.cs @@ -23,6 +23,7 @@ using Volo.Abp.TestApp; using Volo.Abp.TestApp.Application; using Volo.Abp.Threading; using Volo.Abp.Validation.Localization; +using Volo.Abp.FluentValidation; using Volo.Abp.VirtualFileSystem; namespace Volo.Abp.AspNetCore.Mvc; @@ -31,7 +32,8 @@ namespace Volo.Abp.AspNetCore.Mvc; typeof(AbpAspNetCoreTestBaseModule), typeof(AbpMemoryDbTestModule), typeof(AbpAspNetCoreMvcModule), - typeof(AbpAutofacModule) + typeof(AbpAutofacModule), + typeof(AbpFluentValidationModule) )] public class AbpAspNetCoreMvcTestModule : AbpModule { diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestAppService_Tests.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestAppService_Tests.cs new file mode 100644 index 0000000000..24360b1254 --- /dev/null +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestAppService_Tests.cs @@ -0,0 +1,62 @@ +using System.Net; +using System.Net.Http; +using System.Text; +using System.Threading.Tasks; +using Shouldly; +using Xunit; + +namespace Volo.Abp.AspNetCore.Mvc.Validation; + +public class FluentValidationTestAppService_Tests : AspNetCoreMvcTestBase +{ + [Fact] + public async Task Should_Validate_With_FluentValidation_On_ConventionalController() + { + // Name is "A" which is less than 3 characters, should fail FluentValidation + var response = await PostAsync("{\"name\": \"A\"}"); + response.StatusCode.ShouldBe(HttpStatusCode.BadRequest); + } + + [Fact] + public async Task Should_Validate_With_FluentValidation_On_ConventionalController_EmptyName() + { + // Empty name should fail FluentValidation (NotEmpty rule) + var response = await PostAsync("{\"name\": \"\"}"); + response.StatusCode.ShouldBe(HttpStatusCode.BadRequest); + } + + [Fact] + public async Task Should_Validate_With_FluentValidation_On_ConventionalController_MaxLength() + { + // Name exceeds 10 characters, should fail FluentValidation (MaximumLength rule) + var response = await PostAsync("{\"name\": \"12345678901\"}"); + response.StatusCode.ShouldBe(HttpStatusCode.BadRequest); + } + + [Fact] + public async Task Should_Return_Validation_Errors_With_Details() + { + var response = await PostAsync("{\"name\": \"A\"}"); + response.StatusCode.ShouldBe(HttpStatusCode.BadRequest); + + var content = await response.Content.ReadAsStringAsync(); + content.ShouldContain("Name"); + content.ShouldContain("validationErrors"); + } + + [Fact] + public async Task Should_Pass_Validation_With_Valid_Input() + { + var response = await PostAsync("{\"name\": \"Hello\"}"); + response.StatusCode.ShouldBe(HttpStatusCode.OK); + } + + private async Task PostAsync(string jsonContent) + { + using var request = new HttpRequestMessage(HttpMethod.Post, "/api/app/fluent-validation-test") + { + Content = new StringContent(jsonContent, Encoding.UTF8, "application/json") + }; + return await Client.SendAsync(request); + } +} diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestInputValidator.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestInputValidator.cs new file mode 100644 index 0000000000..d99ee32179 --- /dev/null +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/FluentValidationTestInputValidator.cs @@ -0,0 +1,12 @@ +using FluentValidation; +using Volo.Abp.TestApp.Application; + +namespace Volo.Abp.AspNetCore.Mvc.Validation; + +public class FluentValidationTestInputValidator : AbstractValidator +{ + public FluentValidationTestInputValidator() + { + RuleFor(x => x.Name).NotEmpty().MinimumLength(3).MaximumLength(10); + } +} diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController.cs index 3a4fe19fc8..72fb5ccb7d 100644 --- a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController.cs +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController.cs @@ -5,6 +5,7 @@ using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc; using Shouldly; using Volo.Abp.DependencyInjection; +using Volo.Abp.TestApp.Application; using Volo.Abp.Validation; namespace Volo.Abp.AspNetCore.Mvc.Validation; @@ -120,6 +121,16 @@ public class ValidationTestController : AbpController } } + [HttpPost] + [Route("fluent-validation-action")] + public Task FluentValidationAction([FromBody] FluentValidationTestInput input) + { + // This action uses a DTO that has a FluentValidator registered, + // but since this is a regular AbpController (not IValidationEnabled), + // FluentValidation should NOT be triggered by AbpValidationActionFilter. + return Task.FromResult(input.Name); + } + public class CustomValidateModel : IValidatableObject { public string Value1 { get; set; } diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController_Tests.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController_Tests.cs index 409a804fa2..651a2650dc 100644 --- a/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController_Tests.cs +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.Tests/Volo/Abp/AspNetCore/Mvc/Validation/ValidationTestController_Tests.cs @@ -1,4 +1,6 @@ using System.Net; +using System.Net.Http; +using System.Text; using System.Threading.Tasks; using Microsoft.Extensions.DependencyInjection; using Shouldly; @@ -112,6 +114,22 @@ public class ValidationTestController_Tests : AspNetCoreMvcTestBase var result = await GetResponseAsStringAsync("/api/validation-test/object-result-action2"); result.ShouldBe("ModelState.IsValid: false"); } + + [Fact] + public async Task Should_Not_Trigger_FluentValidation_On_Regular_Controller() + { + // FluentValidationTestInput has a FluentValidator with MinimumLength(3) rule, + // but this is a regular AbpController (not IValidationEnabled), + // so FluentValidation should NOT be triggered. + using var request = new HttpRequestMessage(HttpMethod.Post, "/api/validation-test/fluent-validation-action") + { + Content = new StringContent("{\"name\": \"A\"}", Encoding.UTF8, "application/json") + }; + var response = await Client.SendAsync(request); + + // Should return OK because FluentValidation is not triggered for regular controllers + response.StatusCode.ShouldBe(HttpStatusCode.OK); + } } public class DisableAutoModelValidationTestController_Tests : AspNetCoreMvcTestBase diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo.Abp.AspNetCore.Mvc.UI.Tests.csproj b/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo.Abp.AspNetCore.Mvc.UI.Tests.csproj index 19dae03734..654b6b0d0c 100644 --- a/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo.Abp.AspNetCore.Mvc.UI.Tests.csproj +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo.Abp.AspNetCore.Mvc.UI.Tests.csproj @@ -18,6 +18,7 @@ + diff --git a/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo/Abp/AspNetCore/Mvc/UI/Bootstrap/TagHelpers/Form/AbpInputTagHelperService_Tests.cs b/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo/Abp/AspNetCore/Mvc/UI/Bootstrap/TagHelpers/Form/AbpInputTagHelperService_Tests.cs new file mode 100644 index 0000000000..33e2e35bec --- /dev/null +++ b/framework/test/Volo.Abp.AspNetCore.Mvc.UI.Tests/Volo/Abp/AspNetCore/Mvc/UI/Bootstrap/TagHelpers/Form/AbpInputTagHelperService_Tests.cs @@ -0,0 +1,122 @@ +using System.Collections.Generic; +using System.Text.Encodings.Web; +using System.Threading.Tasks; +using Microsoft.AspNetCore.Mvc.ModelBinding; +using Microsoft.AspNetCore.Mvc.ViewFeatures; +using Microsoft.AspNetCore.Razor.TagHelpers; +using Shouldly; +using Xunit; + +namespace Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Form; + +public class AbpInputTagHelperService_Tests +{ + [Fact] + public async Task Hidden_inputs_should_not_add_margin_bottom_classes() + { + var service = new TestAbpInputTagHelperService("hidden"); + var tagHelper = new AbpInputTagHelper(service) + { + AspFor = CreateModelExpression() + }; + + var output = CreateOutput(); + + await tagHelper.ProcessAsync(CreateContext(), output); + + output.Attributes.ContainsName("class").ShouldBeFalse(); + service.LastGroupHtml.ShouldNotContain("mb-3"); + } + + [Fact] + public async Task Visible_inputs_should_keep_margin_bottom_classes() + { + var service = new TestAbpInputTagHelperService("text"); + var tagHelper = new AbpInputTagHelper(service) + { + AspFor = CreateModelExpression() + }; + + var output = CreateOutput(); + + await tagHelper.ProcessAsync(CreateContext(), output); + + output.Attributes["class"].Value.ShouldBe("mb-3"); + service.LastGroupHtml.ShouldContain("mb-3"); + } + + private static TagHelperContext CreateContext() + { + return new TagHelperContext( + new TagHelperAttributeList(), + new Dictionary(), + "test"); + } + + private static TagHelperOutput CreateOutput() + { + return new TagHelperOutput( + "abp-input", + new TagHelperAttributeList(), + (_, _) => Task.FromResult(new DefaultTagHelperContent())); + } + + private static ModelExpression CreateModelExpression() + { + var metadataProvider = new EmptyModelMetadataProvider(); + return new ModelExpression( + "HiddenInput", + metadataProvider.GetModelExplorerForType(typeof(string), null)); + } + + private sealed class TestAbpInputTagHelperService : AbpInputTagHelperService + { + private readonly string _inputTypeName; + + public string LastGroupHtml { get; private set; } = string.Empty; + + public TestAbpInputTagHelperService(string inputTypeName) + : base(null!, HtmlEncoder.Default, null!) + { + _inputTypeName = inputTypeName; + } + + protected override Task<(TagHelperOutput, bool)> GetInputTagHelperOutputAsync(TagHelperContext context, TagHelperOutput output) + { + var inputTagHelperOutput = new TagHelperOutput( + "input", + new TagHelperAttributeList + { + { "type", _inputTypeName }, + { "id", "HiddenInput" }, + { "class", "form-control" } + }, + (_, _) => Task.FromResult(new DefaultTagHelperContent())); + + inputTagHelperOutput.TagMode = TagMode.SelfClosing; + + return Task.FromResult((inputTagHelperOutput, false)); + } + + protected override Task GetLabelAsHtmlAsync(TagHelperContext context, TagHelperOutput output, TagHelperOutput inputTag, bool isCheckbox) + { + return Task.FromResult(string.Empty); + } + + protected override Task GetValidationAsHtmlAsync(TagHelperContext context, TagHelperOutput output, TagHelperOutput inputTag) + { + return Task.FromResult(string.Empty); + } + + protected override string GetInfoAsHtml(TagHelperContext context, TagHelperOutput output, TagHelperOutput inputTag, bool isCheckbox) + { + return string.Empty; + } + + protected override void AddGroupToFormGroupContents(TagHelperContext context, string propertyName, string html, int order, out bool suppress) + { + LastGroupHtml = html; + suppress = false; + } + } +} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo.Abp.OperationRateLimiting.Tests.csproj b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo.Abp.OperationRateLimiting.Tests.csproj deleted file mode 100644 index a9d2d9ee36..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo.Abp.OperationRateLimiting.Tests.csproj +++ /dev/null @@ -1,18 +0,0 @@ - - - - - - net10.0 - - - - - - - - - - - - diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingException_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingException_Tests.cs deleted file mode 100644 index 9d88c5e57d..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingException_Tests.cs +++ /dev/null @@ -1,117 +0,0 @@ -using System; -using Shouldly; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -public class AbpOperationRateLimitingException_Tests -{ - [Fact] - public void Should_Set_HttpStatusCode_To_429() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 3, - CurrentCount = 3, - RemainingCount = 0, - RetryAfter = TimeSpan.FromMinutes(15) - }; - - var exception = new AbpOperationRateLimitingException("TestPolicy", result); - - exception.HttpStatusCode.ShouldBe(429); - } - - [Fact] - public void Should_Use_ExceedLimit_Code_When_RetryAfter_Is_Set() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 3, - CurrentCount = 3, - RemainingCount = 0, - RetryAfter = TimeSpan.FromMinutes(5) - }; - - var exception = new AbpOperationRateLimitingException("TestPolicy", result); - - exception.Code.ShouldBe(AbpOperationRateLimitingErrorCodes.ExceedLimit); - } - - [Fact] - public void Should_Use_ExceedLimitPermanently_Code_When_RetryAfter_Is_Null() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 0, - CurrentCount = 0, - RemainingCount = 0, - RetryAfter = null - }; - - var exception = new AbpOperationRateLimitingException("TestPolicy", result); - - exception.Code.ShouldBe(AbpOperationRateLimitingErrorCodes.ExceedLimitPermanently); - } - - [Fact] - public void Should_Set_Custom_ErrorCode() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 3, - CurrentCount = 3, - RemainingCount = 0 - }; - - var exception = new AbpOperationRateLimitingException("TestPolicy", result, "App:Custom:Error"); - - exception.Code.ShouldBe("App:Custom:Error"); - } - - [Fact] - public void Should_Include_Data_Properties() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 3, - CurrentCount = 3, - RemainingCount = 0, - RetryAfter = TimeSpan.FromMinutes(15), - WindowDuration = TimeSpan.FromHours(1) - }; - - var exception = new AbpOperationRateLimitingException("TestPolicy", result); - - exception.Data["PolicyName"].ShouldBe("TestPolicy"); - exception.Data["MaxCount"].ShouldBe(3); - exception.Data["CurrentCount"].ShouldBe(3); - exception.Data["RemainingCount"].ShouldBe(0); - exception.Data["RetryAfterSeconds"].ShouldBe(900); - exception.Data["RetryAfterMinutes"].ShouldBe(15); - exception.Data["WindowDurationSeconds"].ShouldBe(3600); - } - - [Fact] - public void Should_Store_PolicyName_And_Result() - { - var result = new OperationRateLimitingResult - { - IsAllowed = false, - MaxCount = 5, - CurrentCount = 5, - RemainingCount = 0, - RetryAfter = TimeSpan.FromHours(1) - }; - - var exception = new AbpOperationRateLimitingException("MyPolicy", result); - - exception.PolicyName.ShouldBe("MyPolicy"); - exception.Result.ShouldBeSameAs(result); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2EarlyBreakTestModule.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2EarlyBreakTestModule.cs deleted file mode 100644 index b36b9778cd..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2EarlyBreakTestModule.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; -using System.Threading; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.DependencyInjection.Extensions; -using Volo.Abp.Autofac; -using Volo.Abp.ExceptionHandling; -using Volo.Abp.Modularity; - -namespace Volo.Abp.OperationRateLimiting; - -/// -/// A mock store that simulates a multi-rule Phase 2 race condition: -/// - GetAsync always reports quota available (Phase 1 passes for all rules). -/// - IncrementAsync succeeds for the first call, fails on the second call -/// (simulating a concurrent race on Rule2), and tracks total increment calls -/// so tests can verify that Rule3 was never incremented (early break). -/// -internal class MultiRuleRaceConditionSimulatorStore : IOperationRateLimitingStore -{ - private int _incrementCallCount; - - /// - /// Total number of IncrementAsync calls made. - /// - public int IncrementCallCount => _incrementCallCount; - - public Task GetAsync(string key, TimeSpan duration, int maxCount) - { - return Task.FromResult(new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = 0, - MaxCount = maxCount - }); - } - - public Task IncrementAsync(string key, TimeSpan duration, int maxCount) - { - var callIndex = Interlocked.Increment(ref _incrementCallCount); - - if (callIndex == 2) - { - // Second rule: simulate concurrent race - another request consumed the last slot. - return Task.FromResult(new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = maxCount, - MaxCount = maxCount, - RetryAfter = duration - }); - } - - // First rule (and any others if early break fails): succeed. - return Task.FromResult(new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = 1, - MaxCount = maxCount - }); - } - - public Task ResetAsync(string key) - { - return Task.CompletedTask; - } -} - -[DependsOn( - typeof(AbpOperationRateLimitingModule), - typeof(AbpExceptionHandlingModule), - typeof(AbpTestBaseModule), - typeof(AbpAutofacModule) -)] -public class AbpOperationRateLimitingPhase2EarlyBreakTestModule : AbpModule -{ - public override void ConfigureServices(ServiceConfigurationContext context) - { - context.Services.Replace( - ServiceDescriptor.Singleton()); - - Configure(options => - { - // 3-rule composite policy: all PartitionByParameter with different durations - // so they generate unique cache keys and don't trigger duplicate rule validation. - options.AddPolicy("TestMultiRuleRacePolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(2), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(3), maxCount: 5) - .PartitionByParameter()); - }); - }); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2RaceTestModule.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2RaceTestModule.cs deleted file mode 100644 index c60381c774..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingPhase2RaceTestModule.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.DependencyInjection.Extensions; -using Volo.Abp.Autofac; -using Volo.Abp.ExceptionHandling; -using Volo.Abp.Modularity; - -namespace Volo.Abp.OperationRateLimiting; - -/// -/// A mock store that simulates a concurrent race condition: -/// - GetAsync always says the quota is available (Phase 1 checks pass). -/// - IncrementAsync always says the quota is exhausted (Phase 2 finds another request consumed it). -/// -internal class RaceConditionSimulatorStore : IOperationRateLimitingStore -{ - public Task GetAsync(string key, TimeSpan duration, int maxCount) - { - return Task.FromResult(new OperationRateLimitingStoreResult - { - IsAllowed = true, - CurrentCount = 0, - MaxCount = maxCount - }); - } - - public Task IncrementAsync(string key, TimeSpan duration, int maxCount) - { - // Simulate: between Phase 1 and Phase 2 another concurrent request consumed the last slot. - return Task.FromResult(new OperationRateLimitingStoreResult - { - IsAllowed = false, - CurrentCount = maxCount, - MaxCount = maxCount, - RetryAfter = duration - }); - } - - public Task ResetAsync(string key) - { - return Task.CompletedTask; - } -} - -[DependsOn( - typeof(AbpOperationRateLimitingModule), - typeof(AbpExceptionHandlingModule), - typeof(AbpTestBaseModule), - typeof(AbpAutofacModule) -)] -public class AbpOperationRateLimitingPhase2RaceTestModule : AbpModule -{ - public override void ConfigureServices(ServiceConfigurationContext context) - { - context.Services.Replace( - ServiceDescriptor.Transient()); - - Configure(options => - { - options.AddPolicy("TestRacePolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByParameter(); - }); - }); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingTestModule.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingTestModule.cs deleted file mode 100644 index cd436546f1..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/AbpOperationRateLimitingTestModule.cs +++ /dev/null @@ -1,187 +0,0 @@ -using System; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using NSubstitute; -using Volo.Abp.AspNetCore.WebClientInfo; -using Volo.Abp.Autofac; -using Volo.Abp.ExceptionHandling; -using Volo.Abp.Modularity; - -namespace Volo.Abp.OperationRateLimiting; - -[DependsOn( - typeof(AbpOperationRateLimitingModule), - typeof(AbpExceptionHandlingModule), - typeof(AbpTestBaseModule), - typeof(AbpAutofacModule) -)] -public class AbpOperationRateLimitingTestModule : AbpModule -{ - public override void ConfigureServices(ServiceConfigurationContext context) - { - var mockWebClientInfoProvider = Substitute.For(); - mockWebClientInfoProvider.ClientIpAddress.Returns("127.0.0.1"); - context.Services.AddSingleton(mockWebClientInfoProvider); - - Configure(options => - { - options.AddPolicy("TestSimple", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByParameter(); - }); - - options.AddPolicy("TestUserBased", policy => - { - policy.WithFixedWindow(TimeSpan.FromMinutes(30), maxCount: 5) - .PartitionByCurrentUser(); - }); - - options.AddPolicy("TestComposite", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromDays(1), maxCount: 10) - .PartitionByCurrentUser()); - }); - - options.AddPolicy("TestCustomErrorCode", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionByParameter() - .WithErrorCode("Test:CustomError"); - }); - - options.AddPolicy("TestTenantBased", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByCurrentTenant(); - }); - - options.AddPolicy("TestClientIp", policy => - { - policy.WithFixedWindow(TimeSpan.FromMinutes(15), maxCount: 10) - .PartitionByClientIp(); - }); - - options.AddPolicy("TestEmailBased", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByEmail(); - }); - - options.AddPolicy("TestPhoneNumberBased", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByPhoneNumber(); - }); - - // Composite where Rule2 triggers before Rule1 (to test no-wasted-increment) - options.AddPolicy("TestCompositeRule2First", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionByCurrentUser()); - }); - - // Composite: ByParameter + ByClientIp (different partition types, no auth) - options.AddPolicy("TestCompositeParamIp", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByClientIp()); - }); - - // Composite: Triple - ByParameter + ByCurrentUser + ByClientIp - options.AddPolicy("TestCompositeTriple", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 4) - .PartitionByCurrentUser()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByClientIp()); - }); - - // Fix #6: policy where both rules block simultaneously with different RetryAfter durations. - // Used to verify that Phase 1 checks ALL rules and reports the maximum RetryAfter. - // Rule0: 5-minute window → RetryAfter ~5 min when full - // Rule1: 2-hour window → RetryAfter ~2 hr when full - options.AddPolicy("TestCompositeMaxRetryAfter", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromMinutes(5), maxCount: 1) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(2), maxCount: 1) - .PartitionByParameter()); - }); - - // Fix #6: policy where only Rule0 blocks but Rule1 is still within limit. - // Used to verify that RuleResults contains all rules, not just the blocking one. - options.AddPolicy("TestCompositePartialBlock", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 1) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 100) - .PartitionByParameter()); - }); - - // Ban policy: maxCount=0 should always deny - options.AddPolicy("TestBanPolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 0) - .PartitionByParameter(); - }); - - // Custom resolver: combines Parameter + a static prefix to simulate multi-value key - options.AddPolicy("TestCustomResolver", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionBy(ctx => Task.FromResult($"action:{ctx.Parameter}")); - }); - - // Custom resolver returning null - should throw - options.AddPolicy("TestCustomResolverNull", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionBy(ctx => Task.FromResult(null!)); - }); - - // Multi-tenant: ByParameter with tenant isolation - same param, different tenants = different counters - options.AddPolicy("TestMultiTenantByParameter", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .WithMultiTenancy() - .PartitionByParameter(); - }); - - // Multi-tenant: ByClientIp (global) - same IP, different tenants = same counter - options.AddPolicy("TestMultiTenantByClientIp", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionByClientIp(); - }); - }); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/DistributedCacheOperationRateLimitingStore_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/DistributedCacheOperationRateLimitingStore_Tests.cs deleted file mode 100644 index b612419e48..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/DistributedCacheOperationRateLimitingStore_Tests.cs +++ /dev/null @@ -1,135 +0,0 @@ -using System; -using System.Threading.Tasks; -using Shouldly; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -public class DistributedCacheOperationRateLimitingStore_Tests : OperationRateLimitingTestBase -{ - private readonly IOperationRateLimitingStore _store; - - public DistributedCacheOperationRateLimitingStore_Tests() - { - _store = GetRequiredService(); - } - - [Fact] - public async Task Should_Create_New_Window_On_First_Request() - { - var key = $"store-new-{Guid.NewGuid()}"; - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 5); - - result.IsAllowed.ShouldBeTrue(); - result.CurrentCount.ShouldBe(1); - result.MaxCount.ShouldBe(5); - result.RetryAfter.ShouldBeNull(); - } - - [Fact] - public async Task Should_Increment_Within_Window() - { - var key = $"store-incr-{Guid.NewGuid()}"; - - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 5); - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 5); - - result.IsAllowed.ShouldBeTrue(); - result.CurrentCount.ShouldBe(2); - } - - [Fact] - public async Task Should_Reject_When_MaxCount_Reached() - { - var key = $"store-max-{Guid.NewGuid()}"; - - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - - result.IsAllowed.ShouldBeFalse(); - result.CurrentCount.ShouldBe(2); - result.RetryAfter.ShouldNotBeNull(); - result.RetryAfter!.Value.TotalSeconds.ShouldBeGreaterThan(0); - } - - [Fact] - public async Task Should_Reset_Counter() - { - var key = $"store-reset-{Guid.NewGuid()}"; - - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - - // At max now - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - result.IsAllowed.ShouldBeFalse(); - - // Reset - await _store.ResetAsync(key); - - // Should be allowed again - result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - result.IsAllowed.ShouldBeTrue(); - result.CurrentCount.ShouldBe(1); - } - - [Fact] - public async Task Should_Get_Status_Without_Incrementing() - { - var key = $"store-get-{Guid.NewGuid()}"; - - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 5); - - var result = await _store.GetAsync(key, TimeSpan.FromHours(1), 5); - result.IsAllowed.ShouldBeTrue(); - result.CurrentCount.ShouldBe(1); - - // Get again should still be 1 (no increment) - result = await _store.GetAsync(key, TimeSpan.FromHours(1), 5); - result.CurrentCount.ShouldBe(1); - } - - [Fact] - public async Task Should_Not_Isolate_By_Tenant_At_Store_Level() - { - // Tenant isolation is now handled at the rule level (BuildStoreKey), - // not at the store level. The store treats keys as opaque strings. - var key = $"store-tenant-{Guid.NewGuid()}"; - - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 2); - result.IsAllowed.ShouldBeFalse(); - - // Same key, same counter regardless of tenant context - result = await _store.GetAsync(key, TimeSpan.FromHours(1), 2); - result.IsAllowed.ShouldBeFalse(); - result.CurrentCount.ShouldBe(2); - } - - [Fact] - public async Task Should_Deny_Immediately_When_MaxCount_Is_Zero_Increment() - { - var key = $"store-zero-incr-{Guid.NewGuid()}"; - var result = await _store.IncrementAsync(key, TimeSpan.FromHours(1), 0); - - result.IsAllowed.ShouldBeFalse(); - result.CurrentCount.ShouldBe(0); - result.MaxCount.ShouldBe(0); - result.RetryAfter.ShouldBeNull(); - } - - [Fact] - public async Task Should_Deny_Immediately_When_MaxCount_Is_Zero_Get() - { - var key = $"store-zero-get-{Guid.NewGuid()}"; - var result = await _store.GetAsync(key, TimeSpan.FromHours(1), 0); - - result.IsAllowed.ShouldBeFalse(); - result.CurrentCount.ShouldBe(0); - result.MaxCount.ShouldBe(0); - result.RetryAfter.ShouldBeNull(); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingCheckerFixes_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingCheckerFixes_Tests.cs deleted file mode 100644 index fce15fa466..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingCheckerFixes_Tests.cs +++ /dev/null @@ -1,197 +0,0 @@ -using System; -using System.Threading.Tasks; -using Shouldly; -using Volo.Abp.Testing; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -/// -/// Tests for Fix #6: Phase 1 in CheckAsync now checks ALL rules before throwing, -/// so RetryAfter is the maximum across all blocking rules and RuleResults is complete. -/// -public class OperationRateLimitingCheckerPhase1_Tests : OperationRateLimitingTestBase -{ - private readonly IOperationRateLimitingChecker _checker; - - public OperationRateLimitingCheckerPhase1_Tests() - { - _checker = GetRequiredService(); - } - - [Fact] - public async Task Should_Report_Max_RetryAfter_When_Multiple_Rules_Block() - { - // TestCompositeMaxRetryAfter: Rule0 (5-min window, max=1), Rule1 (2-hr window, max=1) - // Both rules use PartitionByParameter with the same key, so one request exhausts both. - var param = $"max-retry-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // First request: both rules go from 0 to 1 (exhausted, since maxCount=1) - await _checker.CheckAsync("TestCompositeMaxRetryAfter", context); - - // Second request: both Rule0 and Rule1 are blocking. - // Phase 1 checks all rules → RetryAfter must be the larger one (~2 hours). - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCompositeMaxRetryAfter", context); - }); - - // RetryAfter should be at least 1 hour (i.e., from Rule1's 2-hour window, not Rule0's 5-min window) - exception.Result.RetryAfter.ShouldNotBeNull(); - exception.Result.RetryAfter!.Value.ShouldBeGreaterThan(TimeSpan.FromHours(1)); - } - - [Fact] - public async Task Should_Include_All_Rules_In_RuleResults_When_Multiple_Rules_Block() - { - var param = $"all-rules-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Exhaust both rules - await _checker.CheckAsync("TestCompositeMaxRetryAfter", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCompositeMaxRetryAfter", context); - }); - - // Both rules must appear in RuleResults (not just the first blocking one) - exception.Result.RuleResults.ShouldNotBeNull(); - exception.Result.RuleResults!.Count.ShouldBe(2); - exception.Result.RuleResults[0].IsAllowed.ShouldBeFalse(); - exception.Result.RuleResults[1].IsAllowed.ShouldBeFalse(); - } - - [Fact] - public async Task Should_Include_Non_Blocking_Rules_In_RuleResults() - { - // TestCompositePartialBlock: Rule0 (max=1) blocks, Rule1 (max=100) is still within limit. - // RuleResults must contain BOTH rules so callers get the full picture. - var param = $"partial-block-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Exhaust only Rule0 (max=1) - await _checker.CheckAsync("TestCompositePartialBlock", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCompositePartialBlock", context); - }); - - exception.Result.RuleResults.ShouldNotBeNull(); - exception.Result.RuleResults!.Count.ShouldBe(2); - - // Rule0 is blocking - exception.Result.RuleResults[0].IsAllowed.ShouldBeFalse(); - exception.Result.RuleResults[0].MaxCount.ShouldBe(1); - - // Rule1 is still allowed (only 1/100 used), but is still present in results - exception.Result.RuleResults[1].IsAllowed.ShouldBeTrue(); - exception.Result.RuleResults[1].MaxCount.ShouldBe(100); - exception.Result.RuleResults[1].RemainingCount.ShouldBe(99); - - // The overall RetryAfter comes only from the blocking Rule0 - exception.Result.RetryAfter.ShouldNotBeNull(); - exception.Result.RetryAfter!.Value.TotalMinutes.ShouldBeLessThan(61); // ~1 hour from Rule0 - } -} - -/// -/// Tests for Phase 2 early break: when a multi-rule policy encounters a race condition -/// in Phase 2 (Rule2 fails), Rule3 should NOT be incremented. -/// Uses a mock store where IncrementAsync fails on the 2nd call. -/// -public class OperationRateLimitingCheckerPhase2EarlyBreak_Tests - : AbpIntegratedTest -{ - protected override void SetAbpApplicationCreationOptions(AbpApplicationCreationOptions options) - { - options.UseAutofac(); - } - - [Fact] - public async Task Should_Not_Increment_Remaining_Rules_After_Phase2_Failure() - { - // 3-rule policy. Mock store: Rule1 increment succeeds, Rule2 increment fails (race), - // Rule3 should NOT be incremented due to early break. - var checker = GetRequiredService(); - var store = (MultiRuleRaceConditionSimulatorStore)GetRequiredService(); - var context = new OperationRateLimitingContext { Parameter = "early-break-test" }; - - var exception = await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestMultiRuleRacePolicy", context); - }); - - exception.PolicyName.ShouldBe("TestMultiRuleRacePolicy"); - exception.Result.IsAllowed.ShouldBeFalse(); - - // Key assertion: only 2 IncrementAsync calls were made (Rule1 + Rule2). - // Rule3 was skipped (used CheckAsync instead) due to early break. - store.IncrementCallCount.ShouldBe(2); - } - - [Fact] - public async Task Should_Include_All_Rule_Results_Despite_Early_Break() - { - // Even with early break, the aggregated result should contain all 3 rules - // (Rule3 via CheckAsync instead of AcquireAsync). - var checker = GetRequiredService(); - var context = new OperationRateLimitingContext { Parameter = $"all-results-{Guid.NewGuid()}" }; - - var exception = await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestMultiRuleRacePolicy", context); - }); - - exception.Result.RuleResults.ShouldNotBeNull(); - exception.Result.RuleResults!.Count.ShouldBe(3); - } -} - -/// -/// Tests for Fix #1: Phase 2 in CheckAsync now checks the result of AcquireAsync. -/// Uses a mock store that simulates a concurrent race condition: -/// GetAsync (Phase 1) always reports quota available, but IncrementAsync (Phase 2) returns denied. -/// -public class OperationRateLimitingCheckerPhase2Race_Tests - : AbpIntegratedTest -{ - protected override void SetAbpApplicationCreationOptions(AbpApplicationCreationOptions options) - { - options.UseAutofac(); - } - - [Fact] - public async Task Should_Throw_When_Phase2_Increment_Returns_Denied_Due_To_Race() - { - // The mock store always returns IsAllowed=true in GetAsync (Phase 1 passes) - // but always returns IsAllowed=false in IncrementAsync (simulates concurrent exhaustion). - // Before Fix #1, CheckAsync would silently succeed. After the fix it must throw. - var checker = GetRequiredService(); - var context = new OperationRateLimitingContext { Parameter = "race-test" }; - - var exception = await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestRacePolicy", context); - }); - - exception.PolicyName.ShouldBe("TestRacePolicy"); - exception.Result.IsAllowed.ShouldBeFalse(); - exception.HttpStatusCode.ShouldBe(429); - } - - [Fact] - public async Task IsAllowedAsync_Should_Not_Be_Affected_By_Phase2_Fix() - { - // IsAllowedAsync is read-only and does not call IncrementAsync, - // so it should not be affected by the mock store's deny-on-increment behavior. - var checker = GetRequiredService(); - var context = new OperationRateLimitingContext { Parameter = "is-allowed-race" }; - - // Should return true because GetAsync always returns allowed in the mock store - var allowed = await checker.IsAllowedAsync("TestRacePolicy", context); - allowed.ShouldBeTrue(); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingChecker_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingChecker_Tests.cs deleted file mode 100644 index fd3d9f4214..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingChecker_Tests.cs +++ /dev/null @@ -1,798 +0,0 @@ -using System; -using System.Security.Claims; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using Shouldly; -using Volo.Abp.Security.Claims; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingChecker_Tests : OperationRateLimitingTestBase -{ - private readonly IOperationRateLimitingChecker _checker; - - public OperationRateLimitingChecker_Tests() - { - _checker = GetRequiredService(); - } - - [Fact] - public async Task Should_Allow_Within_Limit() - { - var context = new OperationRateLimitingContext { Parameter = "test@example.com" }; - - // Should not throw for 3 requests (max is 3) - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - } - - [Fact] - public async Task Should_Reject_When_Exceeded() - { - var param = $"exceed-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - exception.PolicyName.ShouldBe("TestSimple"); - exception.Result.IsAllowed.ShouldBeFalse(); - exception.HttpStatusCode.ShouldBe(429); - exception.Code.ShouldBe(AbpOperationRateLimitingErrorCodes.ExceedLimit); - } - - [Fact] - public async Task Should_Return_Correct_RemainingCount() - { - var param = $"remaining-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - var status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeTrue(); - status.RemainingCount.ShouldBe(3); - status.CurrentCount.ShouldBe(0); - - // Increment once - await _checker.CheckAsync("TestSimple", context); - - status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeTrue(); - status.RemainingCount.ShouldBe(2); - status.CurrentCount.ShouldBe(1); - } - - [Fact] - public async Task Should_Return_Correct_RetryAfter() - { - var param = $"retry-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - exception.Result.RetryAfter.ShouldNotBeNull(); - exception.Result.RetryAfter!.Value.TotalSeconds.ShouldBeGreaterThan(0); - } - - [Fact] - public async Task Should_Handle_Composite_Policy_All_Pass() - { - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var context = new OperationRateLimitingContext { Parameter = $"composite-{Guid.NewGuid()}" }; - - // Should pass: both rules within limits - await checker.CheckAsync("TestComposite", context); - await checker.CheckAsync("TestComposite", context); - await checker.CheckAsync("TestComposite", context); - } - } - } - - [Fact] - public async Task Should_Reject_Composite_Policy_When_Any_Rule_Exceeds() - { - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var param = $"composite-reject-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await checker.CheckAsync("TestComposite", context); - await checker.CheckAsync("TestComposite", context); - await checker.CheckAsync("TestComposite", context); - - // 4th request: Rule1 (max 3 per hour by parameter) should fail - var exception = await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestComposite", context); - }); - - exception.PolicyName.ShouldBe("TestComposite"); - } - } - } - - [Fact] - public async Task Should_Reset_Counter() - { - var param = $"reset-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - // Should be at limit - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - // Reset - await _checker.ResetAsync("TestSimple", context); - - // Should be allowed again - await _checker.CheckAsync("TestSimple", context); - } - - [Fact] - public async Task Should_Use_Custom_ErrorCode() - { - var param = $"custom-error-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestCustomErrorCode", context); - await _checker.CheckAsync("TestCustomErrorCode", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCustomErrorCode", context); - }); - - exception.Code.ShouldBe("Test:CustomError"); - } - - [Fact] - public async Task Should_Throw_For_Unknown_Policy() - { - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("NonExistentPolicy"); - }); - } - - [Fact] - public async Task Should_Skip_When_Disabled() - { - var options = GetRequiredService>(); - var originalValue = options.Value.IsEnabled; - - try - { - options.Value.IsEnabled = false; - - var param = $"disabled-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Should pass unlimited times - for (var i = 0; i < 100; i++) - { - await _checker.CheckAsync("TestSimple", context); - } - } - finally - { - options.Value.IsEnabled = originalValue; - } - } - - [Fact] - public async Task Should_Work_With_IsAllowedAsync() - { - var param = $"is-allowed-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // IsAllowedAsync does not consume quota - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeTrue(); - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeTrue(); - - // Status should still show 0 consumed - var status = await _checker.GetStatusAsync("TestSimple", context); - status.CurrentCount.ShouldBe(0); - status.RemainingCount.ShouldBe(3); - - // Now consume all - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeFalse(); - } - - [Fact] - public async Task Should_Partition_By_Different_Parameters() - { - var param1 = $"param1-{Guid.NewGuid()}"; - var param2 = $"param2-{Guid.NewGuid()}"; - - var context1 = new OperationRateLimitingContext { Parameter = param1 }; - var context2 = new OperationRateLimitingContext { Parameter = param2 }; - - // Consume all for param1 - await _checker.CheckAsync("TestSimple", context1); - await _checker.CheckAsync("TestSimple", context1); - await _checker.CheckAsync("TestSimple", context1); - - // param2 should still be allowed - await _checker.CheckAsync("TestSimple", context2); - (await _checker.IsAllowedAsync("TestSimple", context2)).ShouldBeTrue(); - } - - [Fact] - public async Task Should_Support_ExtraProperties_In_Exception_Data() - { - var param = $"extra-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext - { - Parameter = param, - ExtraProperties = - { - ["Email"] = "test@example.com", - ["UserId"] = "user-123" - } - }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - exception.Data["Email"].ShouldBe("test@example.com"); - exception.Data["UserId"].ShouldBe("user-123"); - exception.Data["PolicyName"].ShouldBe("TestSimple"); - exception.Data["MaxCount"].ShouldBe(3); - } - - [Fact] - public async Task Should_Partition_By_Email_Via_Parameter() - { - var email = $"email-param-{Guid.NewGuid()}@example.com"; - var context = new OperationRateLimitingContext { Parameter = email }; - - await _checker.CheckAsync("TestEmailBased", context); - await _checker.CheckAsync("TestEmailBased", context); - await _checker.CheckAsync("TestEmailBased", context); - - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestEmailBased", context); - }); - } - - [Fact] - public async Task Should_Partition_By_Email_Via_CurrentUser_Fallback() - { - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - - // No Parameter set, should fall back to ICurrentUser.Email - var context = new OperationRateLimitingContext(); - - await checker.CheckAsync("TestEmailBased", context); - await checker.CheckAsync("TestEmailBased", context); - await checker.CheckAsync("TestEmailBased", context); - - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestEmailBased", context); - }); - } - } - } - - [Fact] - public async Task Should_Partition_By_PhoneNumber_Via_Parameter() - { - var phone = $"phone-param-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = phone }; - - await _checker.CheckAsync("TestPhoneNumberBased", context); - await _checker.CheckAsync("TestPhoneNumberBased", context); - await _checker.CheckAsync("TestPhoneNumberBased", context); - - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestPhoneNumberBased", context); - }); - } - - [Fact] - public async Task Should_Partition_By_PhoneNumber_Via_CurrentUser_Fallback() - { - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - - // No Parameter set, should fall back to ICurrentUser.PhoneNumber - var context = new OperationRateLimitingContext(); - - await checker.CheckAsync("TestPhoneNumberBased", context); - await checker.CheckAsync("TestPhoneNumberBased", context); - await checker.CheckAsync("TestPhoneNumberBased", context); - - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestPhoneNumberBased", context); - }); - } - } - } - - [Fact] - public async Task Should_Throw_When_Email_Not_Available() - { - // No Parameter and no authenticated user - var context = new OperationRateLimitingContext(); - - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestEmailBased", context); - }); - } - - [Fact] - public async Task Should_Not_Waste_Rule1_Count_When_Rule2_Blocks() - { - // TestCompositeRule2First: Rule1 (Parameter, 5/hour), Rule2 (CurrentUser, 2/hour) - // Rule2 triggers at 2. Rule1 should NOT be incremented for blocked requests. - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var param = $"no-waste-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // 2 successful requests (Rule1: 2/5, Rule2: 2/2) - await checker.CheckAsync("TestCompositeRule2First", context); - await checker.CheckAsync("TestCompositeRule2First", context); - - // 3rd request: Rule2 blocks (2/2 at max) - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestCompositeRule2First", context); - }); - - // Verify Rule1 was NOT incremented for the blocked request - // Rule1 should still be at 2/5, not 3/5 - var status = await checker.GetStatusAsync("TestCompositeRule2First", context); - // GetStatusAsync returns the most restrictive rule (Rule2 at 2/2) - // But we can verify Rule1 by checking RuleResults - status.RuleResults.ShouldNotBeNull(); - status.RuleResults!.Count.ShouldBe(2); - - // Rule1 (index 0): should be 2/5, remaining 3 - status.RuleResults[0].RemainingCount.ShouldBe(3); - status.RuleResults[0].MaxCount.ShouldBe(5); - - // Rule2 (index 1): should be 2/2, remaining 0 - status.RuleResults[1].RemainingCount.ShouldBe(0); - status.RuleResults[1].MaxCount.ShouldBe(2); - } - } - } - - [Fact] - public async Task Should_Composite_ParamIp_Ip_Triggers_First() - { - // TestCompositeParamIp: Rule1 (Parameter, 5/hour), Rule2 (ClientIp, 3/hour) - // IP limit (3) is lower, should trigger first - var param = $"param-ip-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // 3 successful requests - await _checker.CheckAsync("TestCompositeParamIp", context); - await _checker.CheckAsync("TestCompositeParamIp", context); - await _checker.CheckAsync("TestCompositeParamIp", context); - - // 4th: IP rule blocks (3/3) - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCompositeParamIp", context); - }); - - exception.PolicyName.ShouldBe("TestCompositeParamIp"); - - // Verify counts: Rule1 should be 3/5, Rule2 should be 3/3 - var status = await _checker.GetStatusAsync("TestCompositeParamIp", context); - status.RuleResults.ShouldNotBeNull(); - status.RuleResults!.Count.ShouldBe(2); - - status.RuleResults[0].RemainingCount.ShouldBe(2); // Parameter: 3/5, remaining 2 - status.RuleResults[0].MaxCount.ShouldBe(5); - status.RuleResults[1].RemainingCount.ShouldBe(0); // IP: 3/3, remaining 0 - status.RuleResults[1].MaxCount.ShouldBe(3); - } - - [Fact] - public async Task Should_Composite_ParamIp_Different_Params_Share_Ip() - { - // Different parameters should have independent Rule1 counters - // but share the same Rule2 (IP) counter - var param1 = $"share-ip-1-{Guid.NewGuid()}"; - var param2 = $"share-ip-2-{Guid.NewGuid()}"; - var context1 = new OperationRateLimitingContext { Parameter = param1 }; - var context2 = new OperationRateLimitingContext { Parameter = param2 }; - - // 2 requests with param1 - await _checker.CheckAsync("TestCompositeParamIp", context1); - await _checker.CheckAsync("TestCompositeParamIp", context1); - - // 1 request with param2 (IP counter is now at 3/3) - await _checker.CheckAsync("TestCompositeParamIp", context2); - - // 4th request with param2: IP rule blocks (3/3 from combined) - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCompositeParamIp", context2); - }); - - // param1 Rule1 should be at 2/5 - var status1 = await _checker.GetStatusAsync("TestCompositeParamIp", context1); - status1.RuleResults![0].RemainingCount.ShouldBe(3); // Parameter: 2/5 - status1.RuleResults[0].MaxCount.ShouldBe(5); - - // param2 Rule1 should be at 1/5 - var status2 = await _checker.GetStatusAsync("TestCompositeParamIp", context2); - status2.RuleResults![0].RemainingCount.ShouldBe(4); // Parameter: 1/5 - status2.RuleResults[0].MaxCount.ShouldBe(5); - } - - [Fact] - public async Task Should_Composite_Triple_Lowest_Limit_Triggers_First() - { - // TestCompositeTriple: Rule1 (Parameter, 5/hour), Rule2 (User, 4/hour), Rule3 (IP, 3/hour) - // IP limit (3) is lowest, should trigger first - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var param = $"triple-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // 3 successful requests - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - - // 4th: IP rule blocks (3/3) - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestCompositeTriple", context); - }); - - // Verify all three rules - var status = await checker.GetStatusAsync("TestCompositeTriple", context); - status.RuleResults.ShouldNotBeNull(); - status.RuleResults!.Count.ShouldBe(3); - - status.RuleResults[0].RemainingCount.ShouldBe(2); // Parameter: 3/5 - status.RuleResults[0].MaxCount.ShouldBe(5); - status.RuleResults[1].RemainingCount.ShouldBe(1); // User: 3/4 - status.RuleResults[1].MaxCount.ShouldBe(4); - status.RuleResults[2].RemainingCount.ShouldBe(0); // IP: 3/3 - status.RuleResults[2].MaxCount.ShouldBe(3); - } - } - } - - [Fact] - public async Task Should_Composite_Triple_No_Wasted_Increment_On_Block() - { - // When IP (Rule3) blocks, Rule1 and Rule2 should NOT be incremented - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var param = $"triple-nowaste-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // 3 successful requests (all rules increment to 3) - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - - // Attempt 3 more blocked requests - for (var i = 0; i < 3; i++) - { - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestCompositeTriple", context); - }); - } - - // Verify Rule1 and Rule2 were NOT incremented beyond 3 - var status = await checker.GetStatusAsync("TestCompositeTriple", context); - status.RuleResults![0].RemainingCount.ShouldBe(2); // Parameter: still 3/5 - status.RuleResults[1].RemainingCount.ShouldBe(1); // User: still 3/4 - status.RuleResults[2].RemainingCount.ShouldBe(0); // IP: still 3/3 - } - } - } - - [Fact] - public async Task Should_Composite_Reset_All_Rules() - { - // Verify reset clears all rules in a composite policy - var userId = Guid.NewGuid(); - - using (var scope = ServiceProvider.CreateScope()) - { - var principalAccessor = scope.ServiceProvider.GetRequiredService(); - var claimsPrincipal = CreateClaimsPrincipal(userId); - - using (principalAccessor.Change(claimsPrincipal)) - { - var checker = scope.ServiceProvider.GetRequiredService(); - var param = $"triple-reset-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Exhaust IP limit - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - await checker.CheckAsync("TestCompositeTriple", context); - - await Assert.ThrowsAsync(async () => - { - await checker.CheckAsync("TestCompositeTriple", context); - }); - - // Reset - await checker.ResetAsync("TestCompositeTriple", context); - - // All rules should be cleared - var status = await checker.GetStatusAsync("TestCompositeTriple", context); - status.IsAllowed.ShouldBeTrue(); - status.RuleResults![0].RemainingCount.ShouldBe(5); // Parameter: 0/5 - status.RuleResults[1].RemainingCount.ShouldBe(4); // User: 0/4 - status.RuleResults[2].RemainingCount.ShouldBe(3); // IP: 0/3 - - // Should be able to use again - await checker.CheckAsync("TestCompositeTriple", context); - } - } - } - - [Fact] - public async Task Should_Throw_When_PhoneNumber_Not_Available() - { - // No Parameter and no authenticated user - var context = new OperationRateLimitingContext(); - - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestPhoneNumberBased", context); - }); - } - - [Fact] - public async Task Should_Deny_First_Request_When_MaxCount_Is_Zero() - { - var context = new OperationRateLimitingContext { Parameter = $"ban-{Guid.NewGuid()}" }; - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestBanPolicy", context); - }); - - exception.Result.IsAllowed.ShouldBeFalse(); - exception.Result.MaxCount.ShouldBe(0); - exception.Result.RetryAfter.ShouldBeNull(); - exception.HttpStatusCode.ShouldBe(429); - exception.Code.ShouldBe(AbpOperationRateLimitingErrorCodes.ExceedLimitPermanently); - } - - [Fact] - public async Task Should_IsAllowed_Return_False_When_MaxCount_Is_Zero() - { - var context = new OperationRateLimitingContext { Parameter = $"ban-allowed-{Guid.NewGuid()}" }; - - var allowed = await _checker.IsAllowedAsync("TestBanPolicy", context); - allowed.ShouldBeFalse(); - } - - [Fact] - public async Task Should_GetStatus_Show_Not_Allowed_When_MaxCount_Is_Zero() - { - var context = new OperationRateLimitingContext { Parameter = $"ban-status-{Guid.NewGuid()}" }; - - var status = await _checker.GetStatusAsync("TestBanPolicy", context); - status.IsAllowed.ShouldBeFalse(); - status.MaxCount.ShouldBe(0); - status.RemainingCount.ShouldBe(0); - status.RetryAfter.ShouldBeNull(); - } - - [Fact] - public async Task Should_Partition_By_Custom_Resolver() - { - // TestCustomResolver uses PartitionBy(ctx => $"action:{ctx.Parameter}") - // Two different parameters => independent counters - var param1 = $"op1-{Guid.NewGuid()}"; - var param2 = $"op2-{Guid.NewGuid()}"; - - var ctx1 = new OperationRateLimitingContext { Parameter = param1 }; - var ctx2 = new OperationRateLimitingContext { Parameter = param2 }; - - // Exhaust param1's quota (max=2) - await _checker.CheckAsync("TestCustomResolver", ctx1); - await _checker.CheckAsync("TestCustomResolver", ctx1); - - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCustomResolver", ctx1); - }); - - // param2 should still be allowed - await _checker.CheckAsync("TestCustomResolver", ctx2); - (await _checker.IsAllowedAsync("TestCustomResolver", ctx2)).ShouldBeTrue(); - } - - [Fact] - public async Task Should_Throw_When_Custom_Resolver_Returns_Null() - { - var context = new OperationRateLimitingContext { Parameter = "test" }; - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCustomResolverNull", context); - }); - - exception.Message.ShouldContain("Custom partition key resolver returned null or empty"); - } - - [Fact] - public void Should_Throw_When_Policy_Has_Duplicate_Rules() - { - var options = new AbpOperationRateLimitingOptions(); - - Assert.Throws(() => - { - options.AddPolicy("DuplicateRulePolicy", policy => - { - policy.AddRule(r => r.WithFixedWindow(TimeSpan.FromHours(1), 5).PartitionByParameter()); - policy.AddRule(r => r.WithFixedWindow(TimeSpan.FromHours(1), 5).PartitionByParameter()); - }); - }); - } - - - [Fact] - public async Task Should_Return_Correct_CurrentCount_In_RuleResults() - { - var param = $"current-count-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var status = await _checker.GetStatusAsync("TestSimple", context); - status.RuleResults.ShouldNotBeNull(); - status.RuleResults!.Count.ShouldBe(1); - status.RuleResults[0].CurrentCount.ShouldBe(2); - status.RuleResults[0].RemainingCount.ShouldBe(1); - status.RuleResults[0].MaxCount.ShouldBe(3); - } - - [Fact] - public async Task ResetAsync_Should_Skip_When_Disabled() - { - var options = GetRequiredService>(); - var originalValue = options.Value.IsEnabled; - - try - { - var param = $"reset-disabled-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Exhaust the quota - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - // Disable and call ResetAsync — should be a no-op (counter not actually reset) - options.Value.IsEnabled = false; - await _checker.ResetAsync("TestSimple", context); - - // Re-enable: quota should still be exhausted because reset was skipped - options.Value.IsEnabled = true; - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - } - finally - { - options.Value.IsEnabled = originalValue; - } - } - - private static ClaimsPrincipal CreateClaimsPrincipal(Guid userId) - { - return new ClaimsPrincipal( - new ClaimsIdentity( - new[] - { - new Claim(AbpClaimTypes.UserId, userId.ToString()), - new Claim(AbpClaimTypes.Email, "test@example.com"), - new Claim(AbpClaimTypes.PhoneNumber, "1234567890") - }, - "TestAuth")); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingFrontendIntegration_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingFrontendIntegration_Tests.cs deleted file mode 100644 index 6566bbccdb..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingFrontendIntegration_Tests.cs +++ /dev/null @@ -1,408 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Threading.Tasks; -using Shouldly; -using Volo.Abp.AspNetCore.ExceptionHandling; -using Volo.Abp.Localization; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingFrontendIntegration_Tests : OperationRateLimitingTestBase -{ - private readonly IOperationRateLimitingChecker _checker; - private readonly IExceptionToErrorInfoConverter _errorInfoConverter; - private readonly IOperationRateLimitingFormatter _formatter; - - public OperationRateLimitingFrontendIntegration_Tests() - { - _checker = GetRequiredService(); - _errorInfoConverter = GetRequiredService(); - _formatter = GetRequiredService(); - } - - [Fact] - public async Task ErrorInfo_Should_Contain_Localized_Message_En() - { - using (CultureHelper.Use("en")) - { - var param = $"frontend-en-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - var errorInfo = _errorInfoConverter.Convert(exception); - - // The localized message should contain "Operation rate limit exceeded" - errorInfo.Message.ShouldContain("Operation rate limit exceeded"); - errorInfo.Message.ShouldContain("minute(s)"); - } - } - - [Fact] - public async Task ErrorInfo_Should_Contain_Localized_Message_ZhHans() - { - using (CultureHelper.Use("zh-Hans")) - { - var param = $"frontend-zh-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - var errorInfo = _errorInfoConverter.Convert(exception); - - // The localized message should be in Chinese - errorInfo.Message.ShouldContain("操作频率超出限制"); - errorInfo.Message.ShouldContain("分钟"); - } - } - - [Fact] - public async Task ErrorInfo_Should_Include_Structured_Data_For_Frontend() - { - var param = $"frontend-data-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext - { - Parameter = param, - ExtraProperties = - { - ["Email"] = "user@example.com" - } - }; - - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestSimple", context); - }); - - var errorInfo = _errorInfoConverter.Convert(exception); - - // Frontend receives error.code - errorInfo.Code.ShouldBe(AbpOperationRateLimitingErrorCodes.ExceedLimit); - - // Frontend receives error.data for countdown timer and UI display - exception.Data["PolicyName"].ShouldBe("TestSimple"); - exception.Data["MaxCount"].ShouldBe(3); - exception.Data["CurrentCount"].ShouldBe(3); - exception.Data["RemainingCount"].ShouldBe(0); - - // RetryAfterSeconds: frontend uses this for countdown - var retryAfterSeconds = (int)exception.Data["RetryAfterSeconds"]!; - retryAfterSeconds.ShouldBeGreaterThan(0); - retryAfterSeconds.ShouldBeLessThanOrEqualTo(3600); // max 1 hour window - - // RetryAfterMinutes: frontend uses this for display - var retryAfterMinutes = (int)exception.Data["RetryAfterMinutes"]!; - retryAfterMinutes.ShouldBeGreaterThan(0); - - // RetryAfter: localized human-readable string - exception.Data["RetryAfter"].ShouldNotBeNull(); - exception.Data["RetryAfter"].ShouldBeOfType(); - - // WindowDurationSeconds: the configured window duration - var windowDurationSeconds = (int)exception.Data["WindowDurationSeconds"]!; - windowDurationSeconds.ShouldBe(3600); // 1 hour window - - // WindowDescription: localized human-readable window description (e.g. "1 hour(s)") - exception.Data["WindowDescription"].ShouldNotBeNull(); - exception.Data["WindowDescription"].ShouldBeOfType(); - - // RuleDetails: complete rule information for frontend - var ruleDetails = exception.Data["RuleDetails"].ShouldBeOfType>>(); - ruleDetails.Count.ShouldBe(1); - ruleDetails[0]["RuleName"].ShouldBe("TestSimple:Rule[3600s,3,Parameter]"); - ruleDetails[0]["MaxCount"].ShouldBe(3); - ruleDetails[0]["IsAllowed"].ShouldBe(false); - ruleDetails[0]["WindowDurationSeconds"].ShouldBe(3600); - ((string)ruleDetails[0]["WindowDescription"]).ShouldNotBeNullOrEmpty(); - ((int)ruleDetails[0]["RetryAfterSeconds"]).ShouldBeGreaterThan(0); - ((string)ruleDetails[0]["RetryAfter"]).ShouldNotBeNullOrEmpty(); - - // ExtraProperties passed through - exception.Data["Email"].ShouldBe("user@example.com"); - } - - [Fact] - public async Task GetStatusAsync_Should_Provide_Countdown_Data_For_Frontend() - { - var param = $"frontend-status-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Before any requests: frontend can show "3 remaining" - var status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeTrue(); - status.RemainingCount.ShouldBe(3); - status.MaxCount.ShouldBe(3); - status.CurrentCount.ShouldBe(0); - status.RetryAfter.ShouldBeNull(); - status.WindowDuration.ShouldBe(TimeSpan.FromHours(1)); - - // After 2 requests: frontend shows "1 remaining" - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeTrue(); - status.RemainingCount.ShouldBe(1); - status.MaxCount.ShouldBe(3); - status.CurrentCount.ShouldBe(2); - - // After exhausting limit: frontend shows countdown - await _checker.CheckAsync("TestSimple", context); - - status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeFalse(); - status.RemainingCount.ShouldBe(0); - status.CurrentCount.ShouldBe(3); - status.RetryAfter.ShouldNotBeNull(); - status.RetryAfter!.Value.TotalSeconds.ShouldBeGreaterThan(0); - } - - [Fact] - public async Task Custom_ErrorCode_Should_Appear_In_ErrorInfo() - { - var param = $"frontend-custom-code-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - await _checker.CheckAsync("TestCustomErrorCode", context); - await _checker.CheckAsync("TestCustomErrorCode", context); - - var exception = await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestCustomErrorCode", context); - }); - - var errorInfo = _errorInfoConverter.Convert(exception); - - // Frontend can use error.code to decide which UI to show - errorInfo.Code.ShouldBe("Test:CustomError"); - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Seconds() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromSeconds(30)).ShouldBe("30 second(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromSeconds(30)).ShouldBe("30 秒"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Minutes() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromMinutes(15)).ShouldBe("15 minute(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromMinutes(15)).ShouldBe("15 分钟"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_MinutesAndSeconds() - { - using (CultureHelper.Use("en")) - { - // 70 seconds = 1 minute and 10 seconds - _formatter.Format(TimeSpan.FromSeconds(70)).ShouldBe("1 minute(s) and 10 second(s)"); - _formatter.Format(TimeSpan.FromSeconds(90)).ShouldBe("1 minute(s) and 30 second(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromSeconds(70)).ShouldBe("1 分钟 10 秒"); - _formatter.Format(TimeSpan.FromSeconds(90)).ShouldBe("1 分钟 30 秒"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Hours() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromHours(2)).ShouldBe("2 hour(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromHours(2)).ShouldBe("2 小时"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_HoursAndMinutes() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromMinutes(90)).ShouldBe("1 hour(s) and 30 minute(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromMinutes(90)).ShouldBe("1 小时 30 分钟"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Days() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromDays(1)).ShouldBe("1 day(s)"); - _formatter.Format(TimeSpan.FromDays(3)).ShouldBe("3 day(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromDays(1)).ShouldBe("1 天"); - _formatter.Format(TimeSpan.FromDays(3)).ShouldBe("3 天"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_DaysAndHours() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromHours(30)).ShouldBe("1 day(s) and 6 hour(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromHours(30)).ShouldBe("1 天 6 小时"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Months() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromDays(30)).ShouldBe("1 month(s)"); - _formatter.Format(TimeSpan.FromDays(90)).ShouldBe("3 month(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromDays(30)).ShouldBe("1 个月"); - _formatter.Format(TimeSpan.FromDays(90)).ShouldBe("3 个月"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_MonthsAndDays() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromDays(45)).ShouldBe("1 month(s) and 15 day(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromDays(45)).ShouldBe("1 个月 15 天"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_Years() - { - using (CultureHelper.Use("en")) - { - _formatter.Format(TimeSpan.FromDays(365)).ShouldBe("1 year(s)"); - _formatter.Format(TimeSpan.FromDays(730)).ShouldBe("2 year(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromDays(365)).ShouldBe("1 年"); - _formatter.Format(TimeSpan.FromDays(730)).ShouldBe("2 年"); - } - } - - [Fact] - public void RetryAfterFormatter_Should_Format_YearsAndMonths() - { - using (CultureHelper.Use("en")) - { - // 1 year + 60 days = 1 year and 2 months - _formatter.Format(TimeSpan.FromDays(425)).ShouldBe("1 year(s) and 2 month(s)"); - } - - using (CultureHelper.Use("zh-Hans")) - { - _formatter.Format(TimeSpan.FromDays(425)).ShouldBe("1 年 2 个月"); - } - } - - [Fact] - public async Task Reset_Should_Allow_Frontend_To_Resume() - { - var param = $"frontend-reset-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Exhaust limit - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - // Frontend shows "limit reached" - var status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeFalse(); - - // After reset (e.g. CAPTCHA verified), frontend can resume - await _checker.ResetAsync("TestSimple", context); - - status = await _checker.GetStatusAsync("TestSimple", context); - status.IsAllowed.ShouldBeTrue(); - status.RemainingCount.ShouldBe(3); - status.CurrentCount.ShouldBe(0); - status.RetryAfter.ShouldBeNull(); - } - - [Fact] - public async Task IsAllowedAsync_Can_Be_Used_For_Frontend_PreCheck() - { - var param = $"frontend-precheck-{Guid.NewGuid()}"; - var context = new OperationRateLimitingContext { Parameter = param }; - - // Frontend precheck: button should be enabled - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeTrue(); - - // Consume all - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - await _checker.CheckAsync("TestSimple", context); - - // Frontend precheck: button should be disabled - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeFalse(); - - // IsAllowedAsync does NOT consume — calling again still returns false, not error - (await _checker.IsAllowedAsync("TestSimple", context)).ShouldBeFalse(); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingMultiTenant_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingMultiTenant_Tests.cs deleted file mode 100644 index b55ffbc966..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingMultiTenant_Tests.cs +++ /dev/null @@ -1,106 +0,0 @@ -using System; -using System.Threading.Tasks; -using Microsoft.Extensions.DependencyInjection; -using Shouldly; -using Volo.Abp.MultiTenancy; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -/// -/// Verifies per-tenant isolation for tenant-scoped partition types and -/// global (cross-tenant) sharing for ClientIp partition type. -/// -public class OperationRateLimitingMultiTenant_Tests : OperationRateLimitingTestBase -{ - private readonly ICurrentTenant _currentTenant; - private readonly IOperationRateLimitingChecker _checker; - - private static readonly Guid TenantA = Guid.NewGuid(); - private static readonly Guid TenantB = Guid.NewGuid(); - - public OperationRateLimitingMultiTenant_Tests() - { - _currentTenant = GetRequiredService(); - _checker = GetRequiredService(); - } - - [Fact] - public async Task Should_Isolate_ByParameter_Between_Tenants() - { - // Same parameter value in different tenants should have independent counters. - var param = $"shared-param-{Guid.NewGuid()}"; - - using (_currentTenant.Change(TenantA)) - { - var ctx = new OperationRateLimitingContext { Parameter = param }; - await _checker.CheckAsync("TestMultiTenantByParameter", ctx); - await _checker.CheckAsync("TestMultiTenantByParameter", ctx); - - // Tenant A exhausted (max=2) - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestMultiTenantByParameter", ctx); - }); - } - - using (_currentTenant.Change(TenantB)) - { - var ctx = new OperationRateLimitingContext { Parameter = param }; - - // Tenant B has its own counter and should still be allowed - await _checker.CheckAsync("TestMultiTenantByParameter", ctx); - (await _checker.IsAllowedAsync("TestMultiTenantByParameter", ctx)).ShouldBeTrue(); - } - } - - [Fact] - public async Task Should_Share_ByClientIp_Across_Tenants() - { - // ClientIp counters are global: requests from the same IP are counted together - // regardless of which tenant context is active. - // The mock IWebClientInfoProvider returns "127.0.0.1" for all requests. - - using (_currentTenant.Change(TenantA)) - { - var ctx = new OperationRateLimitingContext(); - await _checker.CheckAsync("TestMultiTenantByClientIp", ctx); - await _checker.CheckAsync("TestMultiTenantByClientIp", ctx); - } - - using (_currentTenant.Change(TenantB)) - { - var ctx = new OperationRateLimitingContext(); - - // Tenant B shares the same IP counter; should be at limit now - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestMultiTenantByClientIp", ctx); - }); - } - } - - [Fact] - public async Task Should_Isolate_ByParameter_Host_Tenant_From_Named_Tenant() - { - // Host context (no tenant) and a specific tenant should have separate counters. - var param = $"host-vs-tenant-{Guid.NewGuid()}"; - - // Host context: exhaust quota - var hostCtx = new OperationRateLimitingContext { Parameter = param }; - await _checker.CheckAsync("TestMultiTenantByParameter", hostCtx); - await _checker.CheckAsync("TestMultiTenantByParameter", hostCtx); - await Assert.ThrowsAsync(async () => - { - await _checker.CheckAsync("TestMultiTenantByParameter", hostCtx); - }); - - // Tenant A should have its own counter, unaffected by host - using (_currentTenant.Change(TenantA)) - { - var tenantCtx = new OperationRateLimitingContext { Parameter = param }; - await _checker.CheckAsync("TestMultiTenantByParameter", tenantCtx); - (await _checker.IsAllowedAsync("TestMultiTenantByParameter", tenantCtx)).ShouldBeTrue(); - } - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingPolicyBuilder_Tests.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingPolicyBuilder_Tests.cs deleted file mode 100644 index 6a503a6191..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingPolicyBuilder_Tests.cs +++ /dev/null @@ -1,258 +0,0 @@ -using System; -using System.Threading.Tasks; -using Shouldly; -using Xunit; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingPolicyBuilder_Tests -{ - [Fact] - public void Should_Build_Simple_Policy() - { - var options = new AbpOperationRateLimitingOptions(); - options.AddPolicy("TestPolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter(); - }); - - var policy = options.Policies["TestPolicy"]; - - policy.Name.ShouldBe("TestPolicy"); - policy.Rules.Count.ShouldBe(1); - policy.Rules[0].Duration.ShouldBe(TimeSpan.FromHours(1)); - policy.Rules[0].MaxCount.ShouldBe(5); - policy.Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Parameter); - policy.ErrorCode.ShouldBeNull(); - } - - [Fact] - public void Should_Build_Composite_Policy() - { - var options = new AbpOperationRateLimitingOptions(); - options.AddPolicy("CompositePolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 3) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromDays(1), maxCount: 10) - .PartitionByCurrentUser()); - }); - - var policy = options.Policies["CompositePolicy"]; - - policy.Name.ShouldBe("CompositePolicy"); - policy.Rules.Count.ShouldBe(2); - policy.Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Parameter); - policy.Rules[0].MaxCount.ShouldBe(3); - policy.Rules[1].PartitionType.ShouldBe(OperationRateLimitingPartitionType.CurrentUser); - policy.Rules[1].MaxCount.ShouldBe(10); - } - - [Fact] - public void Should_Set_ErrorCode() - { - var options = new AbpOperationRateLimitingOptions(); - options.AddPolicy("ErrorPolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 2) - .PartitionByParameter() - .WithErrorCode("App:Custom:Error"); - }); - - var policy = options.Policies["ErrorPolicy"]; - policy.ErrorCode.ShouldBe("App:Custom:Error"); - } - - [Fact] - public void Should_Build_Custom_Partition() - { - var options = new AbpOperationRateLimitingOptions(); - options.AddPolicy("CustomPolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromMinutes(30), maxCount: 5) - .PartitionBy(ctx => Task.FromResult($"custom:{ctx.Parameter}"))); - }); - - var policy = options.Policies["CustomPolicy"]; - - policy.Rules.Count.ShouldBe(1); - policy.Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Custom); - policy.Rules[0].CustomPartitionKeyResolver.ShouldNotBeNull(); - } - - [Fact] - public void Should_Support_All_Partition_Types() - { - var options = new AbpOperationRateLimitingOptions(); - - options.AddPolicy("P1", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByParameter()); - options.AddPolicy("P2", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByCurrentUser()); - options.AddPolicy("P3", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByCurrentTenant()); - options.AddPolicy("P4", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByClientIp()); - options.AddPolicy("P5", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByEmail()); - options.AddPolicy("P6", p => p.WithFixedWindow(TimeSpan.FromHours(1), 1).PartitionByPhoneNumber()); - - options.Policies["P1"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Parameter); - options.Policies["P2"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.CurrentUser); - options.Policies["P3"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.CurrentTenant); - options.Policies["P4"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.ClientIp); - options.Policies["P5"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Email); - options.Policies["P6"].Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.PhoneNumber); - } - - [Fact] - public void Should_Throw_When_Policy_Has_No_Rules() - { - var options = new AbpOperationRateLimitingOptions(); - - var exception = Assert.Throws(() => - { - options.AddPolicy("EmptyPolicy", policy => - { - // Intentionally not adding any rules - }); - }); - - exception.Message.ShouldContain("no rules"); - } - - [Fact] - public void Should_Throw_When_WithFixedWindow_Without_PartitionBy() - { - var options = new AbpOperationRateLimitingOptions(); - - var exception = Assert.Throws(() => - { - options.AddPolicy("IncompletePolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5); - // Missing PartitionBy*() call - rule never committed - }); - }); - - exception.Message.ShouldContain("no rules"); - } - - [Fact] - public void Should_Throw_When_AddRule_Without_WithFixedWindow() - { - var options = new AbpOperationRateLimitingOptions(); - - var exception = Assert.Throws(() => - { - options.AddPolicy("NoWindowPolicy", policy => - { - policy.AddRule(rule => - { - // Missing WithFixedWindow call - duration is zero - }); - }); - }); - - exception.Message.ShouldContain("positive duration"); - } - - [Fact] - public void Should_Allow_MaxCount_Zero_For_Ban_Policy() - { - var options = new AbpOperationRateLimitingOptions(); - - // maxCount=0 is a valid "ban" policy - always deny - options.AddPolicy("BanPolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: 0) - .PartitionByParameter(); - }); - - var policy = options.Policies["BanPolicy"]; - policy.Rules[0].MaxCount.ShouldBe(0); - } - - [Fact] - public void Should_Throw_When_AddRule_Without_PartitionBy() - { - var options = new AbpOperationRateLimitingOptions(); - - var exception = Assert.Throws(() => - { - options.AddPolicy("NoPartitionPolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5)); - // Missing PartitionBy*() call - }); - }); - - exception.Message.ShouldContain("partition type"); - } - - [Fact] - public void Should_Throw_When_MaxCount_Is_Negative() - { - var options = new AbpOperationRateLimitingOptions(); - - var exception = Assert.Throws(() => - { - options.AddPolicy("NegativePolicy", policy => - { - policy.WithFixedWindow(TimeSpan.FromHours(1), maxCount: -1) - .PartitionByParameter(); - }); - }); - - exception.Message.ShouldContain("maxCount >= 0"); - } - - [Fact] - public void Should_Allow_Same_Rule_With_Different_MultiTenancy() - { - var options = new AbpOperationRateLimitingOptions(); - - // Same Duration/MaxCount/PartitionType but different IsMultiTenant should be allowed - options.AddPolicy("MultiTenancyPolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionByParameter()); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .WithMultiTenancy() - .PartitionByParameter()); - }); - - var policy = options.Policies["MultiTenancyPolicy"]; - policy.Rules.Count.ShouldBe(2); - policy.Rules[0].IsMultiTenant.ShouldBeFalse(); - policy.Rules[1].IsMultiTenant.ShouldBeTrue(); - } - - [Fact] - public void Should_Allow_Multiple_Custom_Partition_Rules() - { - var options = new AbpOperationRateLimitingOptions(); - - // Multiple custom partition rules with same Duration/MaxCount should be allowed - // because they may use different key resolvers - options.AddPolicy("MultiCustomPolicy", policy => - { - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionBy(ctx => Task.FromResult($"by-ip:{ctx.Parameter}"))); - - policy.AddRule(rule => rule - .WithFixedWindow(TimeSpan.FromHours(1), maxCount: 5) - .PartitionBy(ctx => Task.FromResult($"by-device:{ctx.Parameter}"))); - }); - - var policy = options.Policies["MultiCustomPolicy"]; - policy.Rules.Count.ShouldBe(2); - policy.Rules[0].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Custom); - policy.Rules[1].PartitionType.ShouldBe(OperationRateLimitingPartitionType.Custom); - } -} diff --git a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingTestBase.cs b/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingTestBase.cs deleted file mode 100644 index 4316437e57..0000000000 --- a/framework/test/Volo.Abp.OperationRateLimiting.Tests/Volo/Abp/OperationRateLimiting/OperationRateLimitingTestBase.cs +++ /dev/null @@ -1,11 +0,0 @@ -using Volo.Abp.Testing; - -namespace Volo.Abp.OperationRateLimiting; - -public class OperationRateLimitingTestBase : AbpIntegratedTest -{ - protected override void SetAbpApplicationCreationOptions(AbpApplicationCreationOptions options) - { - options.UseAutofac(); - } -} diff --git a/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Application/FluentValidationTestAppService.cs b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Application/FluentValidationTestAppService.cs new file mode 100644 index 0000000000..ea4fcf7480 --- /dev/null +++ b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Application/FluentValidationTestAppService.cs @@ -0,0 +1,17 @@ +using System.Threading.Tasks; +using Volo.Abp.Application.Services; + +namespace Volo.Abp.TestApp.Application; + +public class FluentValidationTestAppService : ApplicationService +{ + public virtual Task CreateAsync(FluentValidationTestInput input) + { + return Task.FromResult(input.Name); + } +} + +public class FluentValidationTestInput +{ + public string Name { get; set; } +} diff --git a/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/TestAppModule.cs b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/TestAppModule.cs index 438bf4b3b9..466d3c9dd7 100644 --- a/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/TestAppModule.cs +++ b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/TestAppModule.cs @@ -39,6 +39,13 @@ public class TestAppModule : AbpModule AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(9) }); context.Services.AddEntityCache(); + + // Test ReplaceEntityCache: first add default, then replace with custom implementation + context.Services.AddEntityCache(); + context.Services.ReplaceEntityCache(); + + // Test ReplaceEntityCache without prior registration + context.Services.ReplaceEntityCache(); } public override void OnApplicationInitialization(ApplicationInitializationContext context) diff --git a/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Testing/EntityCache_Tests.cs b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Testing/EntityCache_Tests.cs index 6ef8da9b7c..de5340b8d8 100644 --- a/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Testing/EntityCache_Tests.cs +++ b/framework/test/Volo.Abp.TestApp/Volo/Abp/TestApp/Testing/EntityCache_Tests.cs @@ -9,6 +9,8 @@ using Volo.Abp.Domain.Entities.Auditing; using Volo.Abp.Domain.Entities.Caching; using Volo.Abp.Domain.Repositories; using Volo.Abp.Modularity; +using Volo.Abp.ObjectMapping; +using Volo.Abp.Uow; using Xunit; namespace Volo.Abp.TestApp.Testing; @@ -19,12 +21,16 @@ public abstract class EntityCache_Tests : TestAppTestBase ProductRepository; protected readonly IEntityCache ProductEntityCache; protected readonly IEntityCache ProductCacheItem; + protected readonly IEntityCache CustomProductCacheItem; + protected readonly IEntityCache CustomProductCacheItemWithoutPriorRegistration; protected EntityCache_Tests() { ProductRepository = GetRequiredService>(); ProductEntityCache = GetRequiredService>(); ProductCacheItem = GetRequiredService>(); + CustomProductCacheItem = GetRequiredService>(); + CustomProductCacheItemWithoutPriorRegistration = GetRequiredService>(); } [Fact] @@ -35,6 +41,19 @@ public abstract class EntityCache_Tests : TestAppTestBase : TestAppTestBase>(() => ProductCacheItem.GetAsync(notExistId)); } + [Fact] + public async Task GetMany_Should_Throw_EntityNotFoundException_For_Not_Existing_Entities() + { + var notExistId = Guid.NewGuid(); + await Assert.ThrowsAsync>(() => ProductEntityCache.GetManyAsync(new[] { notExistId })); + await Assert.ThrowsAsync>(() => ProductCacheItem.GetManyAsync(new[] { notExistId })); + } + [Fact] public async Task Should_Return_EntityCache() { @@ -63,6 +90,56 @@ public abstract class EntityCache_Tests : TestAppTestBase : TestAppTestBase>(() => ProductEntityCache.GetManyAsDictionaryAsync(new[] { notExistId })); + await Assert.ThrowsAsync>(() => ProductCacheItem.GetManyAsDictionaryAsync(new[] { notExistId })); + } + + [Fact] + public async Task FindManyAsDictionary_Should_Return_EntityCache() + { + var notExistId = Guid.NewGuid(); + var ids = new[] { TestDataBuilder.ProductId, notExistId }; + + var products = await ProductEntityCache.FindManyAsDictionaryAsync(ids); + products.Count.ShouldBe(2); + products[TestDataBuilder.ProductId].ShouldNotBeNull(); + products[TestDataBuilder.ProductId]!.Id.ShouldBe(TestDataBuilder.ProductId); + products[TestDataBuilder.ProductId]!.Name.ShouldBe("Product1"); + products[TestDataBuilder.ProductId]!.Price.ShouldBe(decimal.One); + products[notExistId].ShouldBeNull(); + + // Call again to test caching + products = await ProductEntityCache.FindManyAsDictionaryAsync(ids); + products.Count.ShouldBe(2); + products[TestDataBuilder.ProductId].ShouldNotBeNull(); + + var productCacheItems = await ProductCacheItem.FindManyAsDictionaryAsync(ids); + productCacheItems.Count.ShouldBe(2); + productCacheItems[TestDataBuilder.ProductId].ShouldNotBeNull(); + productCacheItems[TestDataBuilder.ProductId]!.Id.ShouldBe(TestDataBuilder.ProductId); + productCacheItems[TestDataBuilder.ProductId]!.Name.ShouldBe("Product1"); + productCacheItems[TestDataBuilder.ProductId]!.Price.ShouldBe(decimal.One); + productCacheItems[notExistId].ShouldBeNull(); + } + + [Fact] + public async Task GetManyAsDictionary_Should_Return_EntityCache() + { + var products = await ProductEntityCache.GetManyAsDictionaryAsync(new[] { TestDataBuilder.ProductId }); + products.Count.ShouldBe(1); + products[TestDataBuilder.ProductId].Id.ShouldBe(TestDataBuilder.ProductId); + products[TestDataBuilder.ProductId].Name.ShouldBe("Product1"); + products[TestDataBuilder.ProductId].Price.ShouldBe(decimal.One); + + // Call again to test caching + products = await ProductEntityCache.GetManyAsDictionaryAsync(new[] { TestDataBuilder.ProductId }); + products.Count.ShouldBe(1); + products[TestDataBuilder.ProductId].Id.ShouldBe(TestDataBuilder.ProductId); + + var productCacheItems = await ProductCacheItem.GetManyAsDictionaryAsync(new[] { TestDataBuilder.ProductId }); + productCacheItems.Count.ShouldBe(1); + productCacheItems[TestDataBuilder.ProductId].Id.ShouldBe(TestDataBuilder.ProductId); + productCacheItems[TestDataBuilder.ProductId].Name.ShouldBe("Product1"); + productCacheItems[TestDataBuilder.ProductId].Price.ShouldBe(decimal.One); + } + + [Fact] + public async Task FindManyAsDictionary_Should_Handle_Duplicate_Ids() + { + var ids = new[] { TestDataBuilder.ProductId, TestDataBuilder.ProductId }; + + var products = await ProductEntityCache.FindManyAsDictionaryAsync(ids); + products.Count.ShouldBe(1); + products[TestDataBuilder.ProductId].ShouldNotBeNull(); + products[TestDataBuilder.ProductId]!.Id.ShouldBe(TestDataBuilder.ProductId); + } + + [Fact] + public async Task GetManyAsDictionary_Should_Handle_Duplicate_Ids() + { + var ids = new[] { TestDataBuilder.ProductId, TestDataBuilder.ProductId }; + + var products = await ProductEntityCache.GetManyAsDictionaryAsync(ids); + products.Count.ShouldBe(1); + products[TestDataBuilder.ProductId].Id.ShouldBe(TestDataBuilder.ProductId); + } + [Fact] public void EntityCache_Default_Options_Should_Be_2_Minutes() { @@ -204,3 +415,69 @@ public class ProductCacheItem2 public decimal Price { get; set; } } + +[Serializable] +[CacheName("CustomProductCacheItem")] +public class CustomProductCacheItem +{ + public Guid Id { get; set; } + + public string Name { get; set; } + + public decimal Price { get; set; } +} + +public class CustomProductEntityCache : EntityCacheWithObjectMapper +{ + public CustomProductEntityCache( + IReadOnlyRepository repository, + IDistributedCache, Guid> cache, + IUnitOfWorkManager unitOfWorkManager, + IObjectMapper objectMapper) + : base(repository, cache, unitOfWorkManager, objectMapper) + { + } + + protected override CustomProductCacheItem MapToValue(Product entity) + { + return new CustomProductCacheItem + { + Id = entity.Id, + Name = entity.Name.ToUpperInvariant(), + Price = entity.Price + }; + } +} + +[Serializable] +[CacheName("CustomProductCacheItemWithoutPriorRegistration")] +public class CustomProductCacheItemWithoutPriorRegistration +{ + public Guid Id { get; set; } + + public string Name { get; set; } + + public decimal Price { get; set; } +} + +public class CustomProductEntityCacheWithoutPriorRegistration : EntityCacheWithObjectMapper +{ + public CustomProductEntityCacheWithoutPriorRegistration( + IReadOnlyRepository repository, + IDistributedCache, Guid> cache, + IUnitOfWorkManager unitOfWorkManager, + IObjectMapper objectMapper) + : base(repository, cache, unitOfWorkManager, objectMapper) + { + } + + protected override CustomProductCacheItemWithoutPriorRegistration MapToValue(Product entity) + { + return new CustomProductCacheItemWithoutPriorRegistration + { + Id = entity.Id, + Name = entity.Name.ToUpperInvariant(), + Price = entity.Price + }; + } +} diff --git a/modules/account/src/Volo.Abp.Account.Web/Pages/Account/Manage.cshtml.cs b/modules/account/src/Volo.Abp.Account.Web/Pages/Account/Manage.cshtml.cs index 415a6851b6..ae615611e0 100644 --- a/modules/account/src/Volo.Abp.Account.Web/Pages/Account/Manage.cshtml.cs +++ b/modules/account/src/Volo.Abp.Account.Web/Pages/Account/Manage.cshtml.cs @@ -47,8 +47,15 @@ public class ManageModel : AccountPageModel return Page(); } - public virtual Task OnPostAsync() + public virtual async Task OnPostAsync() { - return Task.FromResult(Page()); + ProfileManagementPageCreationContext = new ProfileManagementPageCreationContext(ServiceProvider); + + foreach (var contributor in Options.Contributors) + { + await contributor.ConfigureAsync(ProfileManagementPageCreationContext); + } + + return Page(); } } diff --git a/modules/background-jobs/app/Volo.Abp.BackgroundJobs.DemoApp.TickerQ/DemoAppTickerQModule.cs b/modules/background-jobs/app/Volo.Abp.BackgroundJobs.DemoApp.TickerQ/DemoAppTickerQModule.cs index de3ef3c05d..29027a2a75 100644 --- a/modules/background-jobs/app/Volo.Abp.BackgroundJobs.DemoApp.TickerQ/DemoAppTickerQModule.cs +++ b/modules/background-jobs/app/Volo.Abp.BackgroundJobs.DemoApp.TickerQ/DemoAppTickerQModule.cs @@ -77,13 +77,13 @@ public class DemoAppTickerQModule : AbpModule public override Task OnPreApplicationInitializationAsync(ApplicationInitializationContext context) { var abpTickerQFunctionProvider = context.ServiceProvider.GetRequiredService(); - abpTickerQFunctionProvider.Functions.TryAdd(nameof(CleanupJobs), (string.Empty, TickerTaskPriority.Normal, new TickerFunctionDelegate(async (cancellationToken, serviceProvider, tickerFunctionContext) => + abpTickerQFunctionProvider.AddFunction(nameof(CleanupJobs), async (cancellationToken, serviceProvider, tickerFunctionContext) => { var service = new CleanupJobs(); var request = await TickerRequestProvider.GetRequestAsync(tickerFunctionContext, cancellationToken); var genericContext = new TickerFunctionContext(tickerFunctionContext, request); await service.CleanupLogsAsync(genericContext, cancellationToken); - }))); + }, TickerTaskPriority.Normal); abpTickerQFunctionProvider.RequestTypes.TryAdd(nameof(CleanupJobs), (typeof(string).FullName, typeof(string))); return Task.CompletedTask; } diff --git a/modules/basic-theme/test/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.Demo/Pages/Components/DynamicForms.cshtml b/modules/basic-theme/test/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.Demo/Pages/Components/DynamicForms.cshtml index ab44e878c7..544925e53b 100644 --- a/modules/basic-theme/test/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.Demo/Pages/Components/DynamicForms.cshtml +++ b/modules/basic-theme/test/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.Demo/Pages/Components/DynamicForms.cshtml @@ -317,7 +317,7 @@ public class DynamicFormsModel : PageModel

 <form method="post">
-    <div class="mb-3">
+    <div>
         <input type="hidden" id="MyAttributeExamplesModel_HiddenInput" name="MyAttributeExamplesModel.HiddenInput" value="" class="form-control ">
     </div>
     <div class="mb-3">
@@ -433,4 +433,4 @@ public class DynamicFormsModel : PageModel
 
 
-@await Component.InvokeAsync("TagHelperProperties", typeof(AbpDynamicFormTagHelper)) \ No newline at end of file +@await Component.InvokeAsync("TagHelperProperties", typeof(AbpDynamicFormTagHelper)) diff --git a/modules/identity/src/Volo.Abp.Identity.Application/Volo/Abp/Identity/Integration/IdentityUserIntegrationService.cs b/modules/identity/src/Volo.Abp.Identity.Application/Volo/Abp/Identity/Integration/IdentityUserIntegrationService.cs index 4019cd9031..ca8228b9b6 100644 --- a/modules/identity/src/Volo.Abp.Identity.Application/Volo/Abp/Identity/Integration/IdentityUserIntegrationService.cs +++ b/modules/identity/src/Volo.Abp.Identity.Application/Volo/Abp/Identity/Integration/IdentityUserIntegrationService.cs @@ -100,7 +100,7 @@ public class IdentityUserIntegrationService : IdentityAppServiceBase, IIdentityU { using (RoleRepository.DisableTracking()) { - var roles = await RoleRepository.GetListAsync(input.Filter); + var roles = await RoleRepository.GetListAsync(sorting: input.Sorting, maxResultCount: input.MaxResultCount, skipCount: input.SkipCount, filter: input.Filter); return new ListResultDto(roles.Select(r => new RoleData(r.Id, r.Name, r.IsDefault, r.IsStatic, r.IsPublic, r.TenantId, r.ExtraProperties)).ToList()); } } diff --git a/modules/openiddict/app/OpenIddict.Demo.Client.Console/OpenIddict.Demo.Client.Console.csproj b/modules/openiddict/app/OpenIddict.Demo.Client.Console/OpenIddict.Demo.Client.Console.csproj index 67c3354faf..cd8ab94121 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Client.Console/OpenIddict.Demo.Client.Console.csproj +++ b/modules/openiddict/app/OpenIddict.Demo.Client.Console/OpenIddict.Demo.Client.Console.csproj @@ -9,7 +9,20 @@ + + + + + PreserveNewest + + + PreserveNewest + + + diff --git a/modules/openiddict/app/OpenIddict.Demo.Client.Console/Program.cs b/modules/openiddict/app/OpenIddict.Demo.Client.Console/Program.cs index a17e4ce5df..bb1142b76c 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Client.Console/Program.cs +++ b/modules/openiddict/app/OpenIddict.Demo.Client.Console/Program.cs @@ -1,6 +1,11 @@ using System.Net.Http.Headers; +using System.Security.Claims; +using System.Security.Cryptography; using System.Text.Json; +using Duende.IdentityModel; using Duende.IdentityModel.Client; +using Microsoft.IdentityModel.JsonWebTokens; +using Microsoft.IdentityModel.Tokens; using Volo.Abp.AspNetCore.Mvc.ApplicationConfigurations; const string email = "admin@abp.io"; @@ -195,3 +200,89 @@ Console.WriteLine("ClientCredentials API response: {0}", JsonSerializer.Serializ })); Console.WriteLine(); + +// private_key_jwt client credentials flow +// The private key file is generated by `abp generate-jwks` and stored in the parent app/ directory, +// then copied to the output directory during build. +// The corresponding public key (jwks.json) is registered on the authorization server side. +var privateKeyPath = Path.Combine(AppContext.BaseDirectory, "jwks-private.pem"); +if (!File.Exists(privateKeyPath)) +{ + Console.WriteLine("private_key_jwt demo skipped: private key file not found at {0}.", privateKeyPath); + return; +} + +using var rsaKey = RSA.Create(); +rsaKey.ImportFromPem(await File.ReadAllTextAsync(privateKeyPath)); + +// Read the kid dynamically from the JWKS file so it stays in sync with the server-registered JWKS. +string? signingKid = null; +var jwksForKidPath = Path.Combine(AppContext.BaseDirectory, "jwks.json"); +if (File.Exists(jwksForKidPath)) +{ + using var jwksDoc = JsonDocument.Parse(await File.ReadAllTextAsync(jwksForKidPath)); + if (jwksDoc.RootElement.TryGetProperty("keys", out var keysElem) && + keysElem.GetArrayLength() > 0 && + keysElem[0].TryGetProperty("kid", out var kidElem)) + { + signingKid = kidElem.GetString(); + } +} +var signingKey = new RsaSecurityKey(rsaKey) { KeyId = signingKid }; +var signingCredentials = new SigningCredentials(signingKey, SecurityAlgorithms.RsaSha256); + +var now = DateTime.UtcNow; +var jwtHandler = new JsonWebTokenHandler(); +var clientAssertionToken = jwtHandler.CreateToken(new SecurityTokenDescriptor +{ + // OpenIddict requires typ = "client-authentication+jwt" for client assertion JWTs. + // The aud claim must equal the authorization server's issuer URI (Options.Issuer), not the token endpoint. + TokenType = "client-authentication+jwt", + Issuer = "AbpConsoleAppWithJwks", + Audience = configuration.Issuer, + Subject = new ClaimsIdentity(new[] + { + new Claim(JwtRegisteredClaimNames.Sub, "AbpConsoleAppWithJwks"), + new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()), + }), + IssuedAt = now, + NotBefore = now, + Expires = now.AddMinutes(5), + SigningCredentials = signingCredentials, +}); + +client = new HttpClient(); + +var jwksTokenResponse = await client.RequestClientCredentialsTokenAsync(new ClientCredentialsTokenRequest +{ + Address = configuration.TokenEndpoint, + ClientId = "AbpConsoleAppWithJwks", + ClientCredentialStyle = ClientCredentialStyle.PostBody, + ClientAssertion = new ClientAssertion + { + Type = OidcConstants.ClientAssertionTypes.JwtBearer, + Value = clientAssertionToken, + }, + Scope = "AbpAPI", +}); + +if (jwksTokenResponse.IsError) +{ + Console.WriteLine("private_key_jwt error: {0}", jwksTokenResponse.Error); + return; +} + +Console.WriteLine("private_key_jwt Access token: {0}", jwksTokenResponse.AccessToken); +Console.WriteLine(); + +serverRequest = new HttpRequestMessage(HttpMethod.Get, api); +serverRequest.Headers.Authorization = new AuthenticationHeaderValue("Bearer", jwksTokenResponse.AccessToken); +serverResponse = await client.SendAsync(serverRequest); +serverResponse.EnsureSuccessStatusCode(); + +Console.WriteLine("private_key_jwt API response: {0}", JsonSerializer.Serialize(JsonDocument.Parse(await serverResponse.Content.ReadAsStringAsync()), new JsonSerializerOptions +{ + WriteIndented = true +})); + +Console.WriteLine(); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/EntityFrameworkCore/ServerDataSeedContributor.cs b/modules/openiddict/app/OpenIddict.Demo.Server/EntityFrameworkCore/ServerDataSeedContributor.cs index e1fd97136b..71018b7744 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Server/EntityFrameworkCore/ServerDataSeedContributor.cs +++ b/modules/openiddict/app/OpenIddict.Demo.Server/EntityFrameworkCore/ServerDataSeedContributor.cs @@ -1,4 +1,7 @@ using System.Globalization; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Microsoft.IdentityModel.Tokens; using OpenIddict.Abstractions; using OpenIddict.Demo.Server.ExtensionGrants; using Volo.Abp.Data; @@ -13,6 +16,8 @@ public class ServerDataSeedContributor : IDataSeedContributor, ITransientDepende private readonly IOpenIddictApplicationManager _applicationManager; private readonly IOpenIddictScopeManager _scopeManager; + public ILogger Logger { get; set; } + public ServerDataSeedContributor( ICurrentTenant currentTenant, IOpenIddictApplicationManager applicationManager, @@ -21,6 +26,7 @@ public class ServerDataSeedContributor : IDataSeedContributor, ITransientDepende _currentTenant = currentTenant; _applicationManager = applicationManager; _scopeManager = scopeManager; + Logger = NullLogger.Instance; } public async Task SeedAsync(DataSeedContext context) @@ -159,6 +165,43 @@ public class ServerDataSeedContributor : IDataSeedContributor, ITransientDepende }); } + if (await _applicationManager.FindByClientIdAsync("AbpConsoleAppWithJwks") == null) + { + // Load the pre-generated JWKS (public key) from the jwks.json file. + // The corresponding private key (jwks-private.pem) is stored in the parent app/ directory + // and used by OpenIddict.Demo.Client.Console to sign JWT client assertions. + // Both files are generated with: abp generate-jwks + var jwksPath = Path.Combine(AppContext.BaseDirectory, "jwks.json"); + if (!File.Exists(jwksPath)) + { + Logger.LogWarning( + "JWKS file not found at '{JwksPath}'. " + + "Skipping creation of the 'AbpConsoleAppWithJwks' client. " + + "Run 'abp generate-jwks' in the app/ directory to generate the key pair.", + jwksPath); + } + else + { + var jwks = new JsonWebKeySet(await File.ReadAllTextAsync(jwksPath)); + + await _applicationManager.CreateAsync(new OpenIddictApplicationDescriptor + { + ApplicationType = OpenIddictConstants.ApplicationTypes.Web, + ClientId = "AbpConsoleAppWithJwks", + ClientType = OpenIddictConstants.ClientTypes.Confidential, + DisplayName = "Abp Console App (private_key_jwt)", + JsonWebKeySet = jwks, + Permissions = + { + OpenIddictConstants.Permissions.Endpoints.Token, + OpenIddictConstants.Permissions.Endpoints.Introspection, + OpenIddictConstants.Permissions.GrantTypes.ClientCredentials, + OpenIddictConstants.Permissions.Prefixes.Scope + "AbpAPI" + } + }); + } + } + if (await _applicationManager.FindByClientIdAsync("Swagger") == null) { await _applicationManager.CreateAsync(new OpenIddictApplicationDescriptor diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.Designer.cs b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.Designer.cs similarity index 90% rename from modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.Designer.cs rename to modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.Designer.cs index 1ba6189674..a67fcb4cc5 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.Designer.cs +++ b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.Designer.cs @@ -13,7 +13,7 @@ using Volo.Abp.EntityFrameworkCore; namespace OpenIddict.Demo.Server.Migrations { [DbContext(typeof(ServerDbContext))] - [Migration("20250710090114_Initial")] + [Migration("20260311061448_Initial")] partial class Initial { /// @@ -22,7 +22,7 @@ namespace OpenIddict.Demo.Server.Migrations #pragma warning disable 612, 618 modelBuilder .HasAnnotation("_Abp_DatabaseProvider", EfCoreDatabaseProvider.SqlServer) - .HasAnnotation("ProductVersion", "9.0.5") + .HasAnnotation("ProductVersion", "10.0.2") .HasAnnotation("Relational:MaxIdentifierLength", 128); SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder); @@ -408,8 +408,8 @@ namespace OpenIddict.Demo.Server.Migrations .HasColumnType("nvarchar(64)"); b.Property("DeviceInfo") - .HasMaxLength(64) - .HasColumnType("nvarchar(64)"); + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); b.Property("ExtraProperties") .HasColumnType("nvarchar(max)") @@ -530,6 +530,15 @@ namespace OpenIddict.Demo.Server.Migrations b.Property("LastPasswordChangeTime") .HasColumnType("datetimeoffset"); + b.Property("LastSignInTime") + .HasColumnType("datetimeoffset"); + + b.Property("Leaved") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("Leaved"); + b.Property("LockoutEnabled") .ValueGeneratedOnAdd() .HasColumnType("bit") @@ -726,6 +735,47 @@ namespace OpenIddict.Demo.Server.Migrations b.ToTable("AbpUserOrganizationUnits", (string)null); }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasskey", b => + { + b.Property("CredentialId") + .HasMaxLength(1024) + .HasColumnType("varbinary(1024)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.HasKey("CredentialId"); + + b.HasIndex("UserId"); + + b.ToTable("AbpUserPasskeys", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasswordHistory", b => + { + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("Password") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("CreatedAt") + .HasColumnType("datetimeoffset"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("UserId", "Password"); + + b.ToTable("AbpUserPasswordHistories", (string)null); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => { b.Property("UserId") @@ -1194,13 +1244,16 @@ namespace OpenIddict.Demo.Server.Migrations .HasColumnName("ExtraProperties"); b.Property("GroupName") - .IsRequired() .HasMaxLength(128) .HasColumnType("nvarchar(128)"); b.Property("IsEnabled") .HasColumnType("bit"); + b.Property("ManagementPermissionName") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + b.Property("MultiTenancySide") .HasColumnType("tinyint"); @@ -1217,6 +1270,10 @@ namespace OpenIddict.Demo.Server.Migrations .HasMaxLength(128) .HasColumnType("nvarchar(128)"); + b.Property("ResourceName") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + b.Property("StateCheckers") .HasMaxLength(256) .HasColumnType("nvarchar(256)"); @@ -1225,8 +1282,9 @@ namespace OpenIddict.Demo.Server.Migrations b.HasIndex("GroupName"); - b.HasIndex("Name") - .IsUnique(); + b.HasIndex("ResourceName", "Name") + .IsUnique() + .HasFilter("[ResourceName] IS NOT NULL"); b.ToTable("AbpPermissions", (string)null); }); @@ -1293,6 +1351,50 @@ namespace OpenIddict.Demo.Server.Migrations b.ToTable("AbpPermissionGroups", (string)null); }); + modelBuilder.Entity("Volo.Abp.PermissionManagement.ResourcePermissionGrant", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ProviderKey") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ProviderName") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ResourceKey") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ResourceName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name", "ResourceName", "ResourceKey", "ProviderName", "ProviderKey") + .IsUnique() + .HasFilter("[TenantId] IS NOT NULL"); + + b.ToTable("AbpResourcePermissionGrants", (string)null); + }); + modelBuilder.Entity("Volo.Abp.SettingManagement.Setting", b => { b.Property("Id") @@ -1506,6 +1608,62 @@ namespace OpenIddict.Demo.Server.Migrations .IsRequired(); }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasskey", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Passkeys") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + + b.OwnsOne("Volo.Abp.Identity.IdentityPasskeyData", "Data", b1 => + { + b1.Property("IdentityUserPasskeyCredentialId"); + + b1.Property("AttestationObject"); + + b1.Property("ClientDataJson"); + + b1.Property("CreatedAt"); + + b1.Property("IsBackedUp"); + + b1.Property("IsBackupEligible"); + + b1.Property("IsUserVerified"); + + b1.Property("Name"); + + b1.Property("PublicKey"); + + b1.Property("SignCount"); + + b1.PrimitiveCollection("Transports"); + + b1.HasKey("IdentityUserPasskeyCredentialId"); + + b1.ToTable("AbpUserPasskeys"); + + b1 + .ToJson("Data") + .HasColumnType("nvarchar(max)"); + + b1.WithOwner() + .HasForeignKey("IdentityUserPasskeyCredentialId"); + }); + + b.Navigation("Data"); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasswordHistory", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("PasswordHistories") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => { b.HasOne("Volo.Abp.Identity.IdentityRole", null) @@ -1592,6 +1750,10 @@ namespace OpenIddict.Demo.Server.Migrations b.Navigation("OrganizationUnits"); + b.Navigation("Passkeys"); + + b.Navigation("PasswordHistories"); + b.Navigation("Roles"); b.Navigation("Tokens"); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.cs b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.cs similarity index 91% rename from modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.cs rename to modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.cs index a992bf78c2..2524447b0d 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20250710090114_Initial.cs +++ b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/20260311061448_Initial.cs @@ -162,8 +162,10 @@ namespace OpenIddict.Demo.Server.Migrations columns: table => new { Id = table.Column(type: "uniqueidentifier", nullable: false), - GroupName = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: false), + GroupName = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: true), Name = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: false), + ResourceName = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: true), + ManagementPermissionName = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: true), ParentName = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: true), DisplayName = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: false), IsEnabled = table.Column(type: "bit", nullable: false), @@ -177,6 +179,23 @@ namespace OpenIddict.Demo.Server.Migrations table.PrimaryKey("PK_AbpPermissions", x => x.Id); }); + migrationBuilder.CreateTable( + name: "AbpResourcePermissionGrants", + columns: table => new + { + Id = table.Column(type: "uniqueidentifier", nullable: false), + TenantId = table.Column(type: "uniqueidentifier", nullable: true), + Name = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: false), + ProviderName = table.Column(type: "nvarchar(64)", maxLength: 64, nullable: false), + ProviderKey = table.Column(type: "nvarchar(64)", maxLength: 64, nullable: false), + ResourceName = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: false), + ResourceKey = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_AbpResourcePermissionGrants", x => x.Id); + }); + migrationBuilder.CreateTable( name: "AbpRoles", columns: table => new @@ -230,7 +249,7 @@ namespace OpenIddict.Demo.Server.Migrations Id = table.Column(type: "uniqueidentifier", nullable: false), SessionId = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: false), Device = table.Column(type: "nvarchar(64)", maxLength: 64, nullable: false), - DeviceInfo = table.Column(type: "nvarchar(64)", maxLength: 64, nullable: true), + DeviceInfo = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: true), TenantId = table.Column(type: "uniqueidentifier", nullable: true), UserId = table.Column(type: "uniqueidentifier", nullable: false), ClientId = table.Column(type: "nvarchar(64)", maxLength: 64, nullable: true), @@ -344,6 +363,8 @@ namespace OpenIddict.Demo.Server.Migrations ShouldChangePasswordOnNextLogin = table.Column(type: "bit", nullable: false), EntityVersion = table.Column(type: "int", nullable: false), LastPasswordChangeTime = table.Column(type: "datetimeoffset", nullable: true), + LastSignInTime = table.Column(type: "datetimeoffset", nullable: true), + Leaved = table.Column(type: "bit", nullable: false, defaultValue: false), ExtraProperties = table.Column(type: "nvarchar(max)", nullable: false), ConcurrencyStamp = table.Column(type: "nvarchar(40)", maxLength: 40, nullable: false), CreationTime = table.Column(type: "datetime2", nullable: false), @@ -559,6 +580,46 @@ namespace OpenIddict.Demo.Server.Migrations onDelete: ReferentialAction.Cascade); }); + migrationBuilder.CreateTable( + name: "AbpUserPasskeys", + columns: table => new + { + CredentialId = table.Column(type: "varbinary(1024)", maxLength: 1024, nullable: false), + TenantId = table.Column(type: "uniqueidentifier", nullable: true), + UserId = table.Column(type: "uniqueidentifier", nullable: false), + Data = table.Column(type: "nvarchar(max)", nullable: true) + }, + constraints: table => + { + table.PrimaryKey("PK_AbpUserPasskeys", x => x.CredentialId); + table.ForeignKey( + name: "FK_AbpUserPasskeys_AbpUsers_UserId", + column: x => x.UserId, + principalTable: "AbpUsers", + principalColumn: "Id", + onDelete: ReferentialAction.Cascade); + }); + + migrationBuilder.CreateTable( + name: "AbpUserPasswordHistories", + columns: table => new + { + UserId = table.Column(type: "uniqueidentifier", nullable: false), + Password = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: false), + TenantId = table.Column(type: "uniqueidentifier", nullable: true), + CreatedAt = table.Column(type: "datetimeoffset", nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_AbpUserPasswordHistories", x => new { x.UserId, x.Password }); + table.ForeignKey( + name: "FK_AbpUserPasswordHistories_AbpUsers_UserId", + column: x => x.UserId, + principalTable: "AbpUsers", + principalColumn: "Id", + onDelete: ReferentialAction.Cascade); + }); + migrationBuilder.CreateTable( name: "AbpUserRoles", columns: table => new @@ -729,10 +790,18 @@ namespace OpenIddict.Demo.Server.Migrations column: "GroupName"); migrationBuilder.CreateIndex( - name: "IX_AbpPermissions_Name", + name: "IX_AbpPermissions_ResourceName_Name", table: "AbpPermissions", - column: "Name", - unique: true); + columns: new[] { "ResourceName", "Name" }, + unique: true, + filter: "[ResourceName] IS NOT NULL"); + + migrationBuilder.CreateIndex( + name: "IX_AbpResourcePermissionGrants_TenantId_Name_ResourceName_ResourceKey_ProviderName_ProviderKey", + table: "AbpResourcePermissionGrants", + columns: new[] { "TenantId", "Name", "ResourceName", "ResourceKey", "ProviderName", "ProviderKey" }, + unique: true, + filter: "[TenantId] IS NOT NULL"); migrationBuilder.CreateIndex( name: "IX_AbpRoleClaims_RoleId", @@ -817,6 +886,11 @@ namespace OpenIddict.Demo.Server.Migrations table: "AbpUserOrganizationUnits", columns: new[] { "UserId", "OrganizationUnitId" }); + migrationBuilder.CreateIndex( + name: "IX_AbpUserPasskeys_UserId", + table: "AbpUserPasskeys", + column: "UserId"); + migrationBuilder.CreateIndex( name: "IX_AbpUserRoles_RoleId_UserId", table: "AbpUserRoles", @@ -903,6 +977,9 @@ namespace OpenIddict.Demo.Server.Migrations migrationBuilder.DropTable( name: "AbpPermissions"); + migrationBuilder.DropTable( + name: "AbpResourcePermissionGrants"); + migrationBuilder.DropTable( name: "AbpRoleClaims"); @@ -933,6 +1010,12 @@ namespace OpenIddict.Demo.Server.Migrations migrationBuilder.DropTable( name: "AbpUserOrganizationUnits"); + migrationBuilder.DropTable( + name: "AbpUserPasskeys"); + + migrationBuilder.DropTable( + name: "AbpUserPasswordHistories"); + migrationBuilder.DropTable( name: "AbpUserRoles"); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/ServerDbContextModelSnapshot.cs b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/ServerDbContextModelSnapshot.cs index b1caafb242..b746bafee4 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/ServerDbContextModelSnapshot.cs +++ b/modules/openiddict/app/OpenIddict.Demo.Server/Migrations/ServerDbContextModelSnapshot.cs @@ -19,7 +19,7 @@ namespace OpenIddict.Demo.Server.Migrations #pragma warning disable 612, 618 modelBuilder .HasAnnotation("_Abp_DatabaseProvider", EfCoreDatabaseProvider.SqlServer) - .HasAnnotation("ProductVersion", "9.0.5") + .HasAnnotation("ProductVersion", "10.0.2") .HasAnnotation("Relational:MaxIdentifierLength", 128); SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder); @@ -405,8 +405,8 @@ namespace OpenIddict.Demo.Server.Migrations .HasColumnType("nvarchar(64)"); b.Property("DeviceInfo") - .HasMaxLength(64) - .HasColumnType("nvarchar(64)"); + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); b.Property("ExtraProperties") .HasColumnType("nvarchar(max)") @@ -527,6 +527,15 @@ namespace OpenIddict.Demo.Server.Migrations b.Property("LastPasswordChangeTime") .HasColumnType("datetimeoffset"); + b.Property("LastSignInTime") + .HasColumnType("datetimeoffset"); + + b.Property("Leaved") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("Leaved"); + b.Property("LockoutEnabled") .ValueGeneratedOnAdd() .HasColumnType("bit") @@ -723,6 +732,47 @@ namespace OpenIddict.Demo.Server.Migrations b.ToTable("AbpUserOrganizationUnits", (string)null); }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasskey", b => + { + b.Property("CredentialId") + .HasMaxLength(1024) + .HasColumnType("varbinary(1024)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.HasKey("CredentialId"); + + b.HasIndex("UserId"); + + b.ToTable("AbpUserPasskeys", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasswordHistory", b => + { + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("Password") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("CreatedAt") + .HasColumnType("datetimeoffset"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("UserId", "Password"); + + b.ToTable("AbpUserPasswordHistories", (string)null); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => { b.Property("UserId") @@ -1191,13 +1241,16 @@ namespace OpenIddict.Demo.Server.Migrations .HasColumnName("ExtraProperties"); b.Property("GroupName") - .IsRequired() .HasMaxLength(128) .HasColumnType("nvarchar(128)"); b.Property("IsEnabled") .HasColumnType("bit"); + b.Property("ManagementPermissionName") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + b.Property("MultiTenancySide") .HasColumnType("tinyint"); @@ -1214,6 +1267,10 @@ namespace OpenIddict.Demo.Server.Migrations .HasMaxLength(128) .HasColumnType("nvarchar(128)"); + b.Property("ResourceName") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + b.Property("StateCheckers") .HasMaxLength(256) .HasColumnType("nvarchar(256)"); @@ -1222,8 +1279,9 @@ namespace OpenIddict.Demo.Server.Migrations b.HasIndex("GroupName"); - b.HasIndex("Name") - .IsUnique(); + b.HasIndex("ResourceName", "Name") + .IsUnique() + .HasFilter("[ResourceName] IS NOT NULL"); b.ToTable("AbpPermissions", (string)null); }); @@ -1290,6 +1348,50 @@ namespace OpenIddict.Demo.Server.Migrations b.ToTable("AbpPermissionGroups", (string)null); }); + modelBuilder.Entity("Volo.Abp.PermissionManagement.ResourcePermissionGrant", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ProviderKey") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ProviderName") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ResourceKey") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ResourceName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name", "ResourceName", "ResourceKey", "ProviderName", "ProviderKey") + .IsUnique() + .HasFilter("[TenantId] IS NOT NULL"); + + b.ToTable("AbpResourcePermissionGrants", (string)null); + }); + modelBuilder.Entity("Volo.Abp.SettingManagement.Setting", b => { b.Property("Id") @@ -1503,6 +1605,62 @@ namespace OpenIddict.Demo.Server.Migrations .IsRequired(); }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasskey", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Passkeys") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + + b.OwnsOne("Volo.Abp.Identity.IdentityPasskeyData", "Data", b1 => + { + b1.Property("IdentityUserPasskeyCredentialId"); + + b1.Property("AttestationObject"); + + b1.Property("ClientDataJson"); + + b1.Property("CreatedAt"); + + b1.Property("IsBackedUp"); + + b1.Property("IsBackupEligible"); + + b1.Property("IsUserVerified"); + + b1.Property("Name"); + + b1.Property("PublicKey"); + + b1.Property("SignCount"); + + b1.PrimitiveCollection("Transports"); + + b1.HasKey("IdentityUserPasskeyCredentialId"); + + b1.ToTable("AbpUserPasskeys"); + + b1 + .ToJson("Data") + .HasColumnType("nvarchar(max)"); + + b1.WithOwner() + .HasForeignKey("IdentityUserPasskeyCredentialId"); + }); + + b.Navigation("Data"); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserPasswordHistory", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("PasswordHistories") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => { b.HasOne("Volo.Abp.Identity.IdentityRole", null) @@ -1589,6 +1747,10 @@ namespace OpenIddict.Demo.Server.Migrations b.Navigation("OrganizationUnits"); + b.Navigation("Passkeys"); + + b.Navigation("PasswordHistories"); + b.Navigation("Roles"); b.Navigation("Tokens"); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/OpenIddict.Demo.Server.csproj b/modules/openiddict/app/OpenIddict.Demo.Server/OpenIddict.Demo.Server.csproj index c6c8742e4b..09a185919a 100644 --- a/modules/openiddict/app/OpenIddict.Demo.Server/OpenIddict.Demo.Server.csproj +++ b/modules/openiddict/app/OpenIddict.Demo.Server/OpenIddict.Demo.Server.csproj @@ -79,4 +79,13 @@ + + + + PreserveNewest + + + diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/openiddict.pfx b/modules/openiddict/app/OpenIddict.Demo.Server/openiddict.pfx index 8dc3bf1771..586e269982 100644 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/openiddict.pfx and b/modules/openiddict/app/OpenIddict.Demo.Server/openiddict.pfx differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/all.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/all.css deleted file mode 100644 index d9ade752d8..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/all.css +++ /dev/null @@ -1,4616 +0,0 @@ -/*! - * Font Awesome Free 5.15.4 by @fontawesome - https://fontawesome.com - * License - https://fontawesome.com/license/free (Icons: CC BY 4.0, Fonts: SIL OFL 1.1, Code: MIT License) - */ -.fa, -.fas, -.far, -.fal, -.fad, -.fab { - -moz-osx-font-smoothing: grayscale; - -webkit-font-smoothing: antialiased; - display: inline-block; - font-style: normal; - font-variant: normal; - text-rendering: auto; - line-height: 1; } - -.fa-lg { - font-size: 1.33333em; - line-height: 0.75em; - vertical-align: -.0667em; } - -.fa-xs { - font-size: .75em; } - -.fa-sm { - font-size: .875em; } - -.fa-1x { - font-size: 1em; } - -.fa-2x { - font-size: 2em; } - -.fa-3x { - font-size: 3em; } - -.fa-4x { - font-size: 4em; } - -.fa-5x { - font-size: 5em; } - -.fa-6x { - font-size: 6em; } - -.fa-7x { - font-size: 7em; } - -.fa-8x { - font-size: 8em; } - -.fa-9x { - font-size: 9em; } - -.fa-10x { - font-size: 10em; } - -.fa-fw { - text-align: center; - width: 1.25em; } - -.fa-ul { - list-style-type: none; - margin-left: 2.5em; - padding-left: 0; } - .fa-ul > li { - position: relative; } - -.fa-li { - left: -2em; - position: absolute; - text-align: center; - width: 2em; - line-height: inherit; } - -.fa-border { - border: solid 0.08em #eee; - border-radius: .1em; - padding: .2em .25em .15em; } - -.fa-pull-left { - float: left; } - -.fa-pull-right { - float: right; } - -.fa.fa-pull-left, -.fas.fa-pull-left, -.far.fa-pull-left, -.fal.fa-pull-left, -.fab.fa-pull-left { - margin-right: .3em; } - -.fa.fa-pull-right, -.fas.fa-pull-right, -.far.fa-pull-right, -.fal.fa-pull-right, -.fab.fa-pull-right { - margin-left: .3em; } - -.fa-spin { - -webkit-animation: fa-spin 2s infinite linear; - animation: fa-spin 2s infinite linear; } - -.fa-pulse { - -webkit-animation: fa-spin 1s infinite steps(8); - animation: fa-spin 1s infinite steps(8); } - -@-webkit-keyframes fa-spin { - 0% { - -webkit-transform: rotate(0deg); - transform: rotate(0deg); } - 100% { - -webkit-transform: rotate(360deg); - transform: rotate(360deg); } } - -@keyframes fa-spin { - 0% { - -webkit-transform: rotate(0deg); - transform: rotate(0deg); } - 100% { - -webkit-transform: rotate(360deg); - transform: rotate(360deg); } } - -.fa-rotate-90 { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; - -webkit-transform: rotate(90deg); - transform: rotate(90deg); } - -.fa-rotate-180 { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2)"; - -webkit-transform: rotate(180deg); - transform: rotate(180deg); } - -.fa-rotate-270 { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; - -webkit-transform: rotate(270deg); - transform: rotate(270deg); } - -.fa-flip-horizontal { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)"; - -webkit-transform: scale(-1, 1); - transform: scale(-1, 1); } - -.fa-flip-vertical { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)"; - -webkit-transform: scale(1, -1); - transform: scale(1, -1); } - -.fa-flip-both, .fa-flip-horizontal.fa-flip-vertical { - -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)"; - -webkit-transform: scale(-1, -1); - transform: scale(-1, -1); } - -:root .fa-rotate-90, -:root .fa-rotate-180, -:root .fa-rotate-270, -:root .fa-flip-horizontal, -:root .fa-flip-vertical, -:root .fa-flip-both { - -webkit-filter: none; - filter: none; } - -.fa-stack { - display: inline-block; - height: 2em; - line-height: 2em; - position: relative; - vertical-align: middle; - width: 2.5em; } - -.fa-stack-1x, -.fa-stack-2x { - left: 0; - position: absolute; - text-align: center; - width: 100%; } - -.fa-stack-1x { - line-height: inherit; } - -.fa-stack-2x { - font-size: 2em; } - -.fa-inverse { - color: #fff; } - -/* Font Awesome uses the Unicode Private Use Area (PUA) to ensure screen -readers do not read off random characters that represent icons */ -.fa-500px:before { - content: "\f26e"; } - -.fa-accessible-icon:before { - content: "\f368"; } - -.fa-accusoft:before { - content: "\f369"; } - -.fa-acquisitions-incorporated:before { - content: "\f6af"; } - -.fa-ad:before { - content: "\f641"; } - -.fa-address-book:before { - content: "\f2b9"; } - -.fa-address-card:before { - content: "\f2bb"; } - -.fa-adjust:before { - content: "\f042"; } - -.fa-adn:before { - content: "\f170"; } - -.fa-adversal:before { - content: "\f36a"; } - -.fa-affiliatetheme:before { - content: "\f36b"; } - -.fa-air-freshener:before { - content: "\f5d0"; } - -.fa-airbnb:before { - content: "\f834"; } - -.fa-algolia:before { - content: "\f36c"; } - -.fa-align-center:before { - content: "\f037"; } - -.fa-align-justify:before { - content: "\f039"; } - -.fa-align-left:before { - content: "\f036"; } - -.fa-align-right:before { - content: "\f038"; } - -.fa-alipay:before { - content: "\f642"; } - -.fa-allergies:before { - content: "\f461"; } - -.fa-amazon:before { - content: "\f270"; } - -.fa-amazon-pay:before { - content: "\f42c"; } - -.fa-ambulance:before { - content: "\f0f9"; } - -.fa-american-sign-language-interpreting:before { - content: "\f2a3"; } - -.fa-amilia:before { - content: "\f36d"; } - -.fa-anchor:before { - content: "\f13d"; } - -.fa-android:before { - content: "\f17b"; } - -.fa-angellist:before { - content: "\f209"; } - -.fa-angle-double-down:before { - content: "\f103"; } - -.fa-angle-double-left:before { - content: "\f100"; } - -.fa-angle-double-right:before { - content: "\f101"; } - -.fa-angle-double-up:before { - content: "\f102"; } - -.fa-angle-down:before { - content: "\f107"; } - -.fa-angle-left:before { - content: "\f104"; } - -.fa-angle-right:before { - content: "\f105"; } - -.fa-angle-up:before { - content: "\f106"; } - -.fa-angry:before { - content: "\f556"; } - -.fa-angrycreative:before { - content: "\f36e"; } - -.fa-angular:before { - content: "\f420"; } - -.fa-ankh:before { - content: "\f644"; } - -.fa-app-store:before { - content: "\f36f"; } - -.fa-app-store-ios:before { - content: "\f370"; } - -.fa-apper:before { - content: "\f371"; } - -.fa-apple:before { - content: "\f179"; } - -.fa-apple-alt:before { - content: "\f5d1"; } - -.fa-apple-pay:before { - content: "\f415"; } - -.fa-archive:before { - content: "\f187"; } - -.fa-archway:before { - content: "\f557"; } - -.fa-arrow-alt-circle-down:before { - content: "\f358"; } - -.fa-arrow-alt-circle-left:before { - content: "\f359"; } - -.fa-arrow-alt-circle-right:before { - content: "\f35a"; } - -.fa-arrow-alt-circle-up:before { - content: "\f35b"; } - -.fa-arrow-circle-down:before { - content: "\f0ab"; } - -.fa-arrow-circle-left:before { - content: "\f0a8"; } - -.fa-arrow-circle-right:before { - content: "\f0a9"; } - -.fa-arrow-circle-up:before { - content: "\f0aa"; } - -.fa-arrow-down:before { - content: "\f063"; } - -.fa-arrow-left:before { - content: "\f060"; } - -.fa-arrow-right:before { - content: "\f061"; } - -.fa-arrow-up:before { - content: "\f062"; } - -.fa-arrows-alt:before { - content: "\f0b2"; } - -.fa-arrows-alt-h:before { - content: "\f337"; } - -.fa-arrows-alt-v:before { - content: "\f338"; } - -.fa-artstation:before { - content: "\f77a"; } - -.fa-assistive-listening-systems:before { - content: "\f2a2"; } - -.fa-asterisk:before { - content: "\f069"; } - -.fa-asymmetrik:before { - content: "\f372"; } - -.fa-at:before { - content: "\f1fa"; } - -.fa-atlas:before { - content: "\f558"; } - -.fa-atlassian:before { - content: "\f77b"; } - -.fa-atom:before { - content: "\f5d2"; } - -.fa-audible:before { - content: "\f373"; } - -.fa-audio-description:before { - content: "\f29e"; } - -.fa-autoprefixer:before { - content: "\f41c"; } - -.fa-avianex:before { - content: "\f374"; } - -.fa-aviato:before { - content: "\f421"; } - -.fa-award:before { - content: "\f559"; } - -.fa-aws:before { - content: "\f375"; } - -.fa-baby:before { - content: "\f77c"; } - -.fa-baby-carriage:before { - content: "\f77d"; } - -.fa-backspace:before { - content: "\f55a"; } - -.fa-backward:before { - content: "\f04a"; } - -.fa-bacon:before { - content: "\f7e5"; } - -.fa-bacteria:before { - content: "\e059"; } - -.fa-bacterium:before { - content: "\e05a"; } - -.fa-bahai:before { - content: "\f666"; } - -.fa-balance-scale:before { - content: "\f24e"; } - -.fa-balance-scale-left:before { - content: "\f515"; } - -.fa-balance-scale-right:before { - content: "\f516"; } - -.fa-ban:before { - content: "\f05e"; } - -.fa-band-aid:before { - content: "\f462"; } - -.fa-bandcamp:before { - content: "\f2d5"; } - -.fa-barcode:before { - content: "\f02a"; } - -.fa-bars:before { - content: "\f0c9"; } - -.fa-baseball-ball:before { - content: "\f433"; } - -.fa-basketball-ball:before { - content: "\f434"; } - -.fa-bath:before { - content: "\f2cd"; } - -.fa-battery-empty:before { - content: "\f244"; } - -.fa-battery-full:before { - content: "\f240"; } - -.fa-battery-half:before { - content: "\f242"; } - -.fa-battery-quarter:before { - content: "\f243"; } - -.fa-battery-three-quarters:before { - content: "\f241"; } - -.fa-battle-net:before { - content: "\f835"; } - -.fa-bed:before { - content: "\f236"; } - -.fa-beer:before { - content: "\f0fc"; } - -.fa-behance:before { - content: "\f1b4"; } - -.fa-behance-square:before { - content: "\f1b5"; } - -.fa-bell:before { - content: "\f0f3"; } - -.fa-bell-slash:before { - content: "\f1f6"; } - -.fa-bezier-curve:before { - content: "\f55b"; } - -.fa-bible:before { - content: "\f647"; } - -.fa-bicycle:before { - content: "\f206"; } - -.fa-biking:before { - content: "\f84a"; } - -.fa-bimobject:before { - content: "\f378"; } - -.fa-binoculars:before { - content: "\f1e5"; } - -.fa-biohazard:before { - content: "\f780"; } - -.fa-birthday-cake:before { - content: "\f1fd"; } - -.fa-bitbucket:before { - content: "\f171"; } - -.fa-bitcoin:before { - content: "\f379"; } - -.fa-bity:before { - content: "\f37a"; } - -.fa-black-tie:before { - content: "\f27e"; } - -.fa-blackberry:before { - content: "\f37b"; } - -.fa-blender:before { - content: "\f517"; } - -.fa-blender-phone:before { - content: "\f6b6"; } - -.fa-blind:before { - content: "\f29d"; } - -.fa-blog:before { - content: "\f781"; } - -.fa-blogger:before { - content: "\f37c"; } - -.fa-blogger-b:before { - content: "\f37d"; } - -.fa-bluetooth:before { - content: "\f293"; } - -.fa-bluetooth-b:before { - content: "\f294"; } - -.fa-bold:before { - content: "\f032"; } - -.fa-bolt:before { - content: "\f0e7"; } - -.fa-bomb:before { - content: "\f1e2"; } - -.fa-bone:before { - content: "\f5d7"; } - -.fa-bong:before { - content: "\f55c"; } - -.fa-book:before { - content: "\f02d"; } - -.fa-book-dead:before { - content: "\f6b7"; } - -.fa-book-medical:before { - content: "\f7e6"; } - -.fa-book-open:before { - content: "\f518"; } - -.fa-book-reader:before { - content: "\f5da"; } - -.fa-bookmark:before { - content: "\f02e"; } - -.fa-bootstrap:before { - content: "\f836"; } - -.fa-border-all:before { - content: "\f84c"; } - -.fa-border-none:before { - content: "\f850"; } - -.fa-border-style:before { - content: "\f853"; } - -.fa-bowling-ball:before { - content: "\f436"; } - -.fa-box:before { - content: "\f466"; } - -.fa-box-open:before { - content: "\f49e"; } - -.fa-box-tissue:before { - content: "\e05b"; } - -.fa-boxes:before { - content: "\f468"; } - -.fa-braille:before { - content: "\f2a1"; } - -.fa-brain:before { - content: "\f5dc"; } - -.fa-bread-slice:before { - content: "\f7ec"; } - -.fa-briefcase:before { - content: "\f0b1"; } - -.fa-briefcase-medical:before { - content: "\f469"; } - -.fa-broadcast-tower:before { - content: "\f519"; } - -.fa-broom:before { - content: "\f51a"; } - -.fa-brush:before { - content: "\f55d"; } - -.fa-btc:before { - content: "\f15a"; } - -.fa-buffer:before { - content: "\f837"; } - -.fa-bug:before { - content: "\f188"; } - -.fa-building:before { - content: "\f1ad"; } - -.fa-bullhorn:before { - content: "\f0a1"; } - -.fa-bullseye:before { - content: "\f140"; } - -.fa-burn:before { - content: "\f46a"; } - -.fa-buromobelexperte:before { - content: "\f37f"; } - -.fa-bus:before { - content: "\f207"; } - -.fa-bus-alt:before { - content: "\f55e"; } - -.fa-business-time:before { - content: "\f64a"; } - -.fa-buy-n-large:before { - content: "\f8a6"; } - -.fa-buysellads:before { - content: "\f20d"; } - -.fa-calculator:before { - content: "\f1ec"; } - -.fa-calendar:before { - content: "\f133"; } - -.fa-calendar-alt:before { - content: "\f073"; } - -.fa-calendar-check:before { - content: "\f274"; } - -.fa-calendar-day:before { - content: "\f783"; } - -.fa-calendar-minus:before { - content: "\f272"; } - -.fa-calendar-plus:before { - content: "\f271"; } - -.fa-calendar-times:before { - content: "\f273"; } - -.fa-calendar-week:before { - content: "\f784"; } - -.fa-camera:before { - content: "\f030"; } - -.fa-camera-retro:before { - content: "\f083"; } - -.fa-campground:before { - content: "\f6bb"; } - -.fa-canadian-maple-leaf:before { - content: "\f785"; } - -.fa-candy-cane:before { - content: "\f786"; } - -.fa-cannabis:before { - content: "\f55f"; } - -.fa-capsules:before { - content: "\f46b"; } - -.fa-car:before { - content: "\f1b9"; } - -.fa-car-alt:before { - content: "\f5de"; } - -.fa-car-battery:before { - content: "\f5df"; } - -.fa-car-crash:before { - content: "\f5e1"; } - -.fa-car-side:before { - content: "\f5e4"; } - -.fa-caravan:before { - content: "\f8ff"; } - -.fa-caret-down:before { - content: "\f0d7"; } - -.fa-caret-left:before { - content: "\f0d9"; } - -.fa-caret-right:before { - content: "\f0da"; } - -.fa-caret-square-down:before { - content: "\f150"; } - -.fa-caret-square-left:before { - content: "\f191"; } - -.fa-caret-square-right:before { - content: "\f152"; } - -.fa-caret-square-up:before { - content: "\f151"; } - -.fa-caret-up:before { - content: "\f0d8"; } - -.fa-carrot:before { - content: "\f787"; } - -.fa-cart-arrow-down:before { - content: "\f218"; } - -.fa-cart-plus:before { - content: "\f217"; } - -.fa-cash-register:before { - content: "\f788"; } - -.fa-cat:before { - content: "\f6be"; } - -.fa-cc-amazon-pay:before { - content: "\f42d"; } - -.fa-cc-amex:before { - content: "\f1f3"; } - -.fa-cc-apple-pay:before { - content: "\f416"; } - -.fa-cc-diners-club:before { - content: "\f24c"; } - -.fa-cc-discover:before { - content: "\f1f2"; } - -.fa-cc-jcb:before { - content: "\f24b"; } - -.fa-cc-mastercard:before { - content: "\f1f1"; } - -.fa-cc-paypal:before { - content: "\f1f4"; } - -.fa-cc-stripe:before { - content: "\f1f5"; } - -.fa-cc-visa:before { - content: "\f1f0"; } - -.fa-centercode:before { - content: "\f380"; } - -.fa-centos:before { - content: "\f789"; } - -.fa-certificate:before { - content: "\f0a3"; } - -.fa-chair:before { - content: "\f6c0"; } - -.fa-chalkboard:before { - content: "\f51b"; } - -.fa-chalkboard-teacher:before { - content: "\f51c"; } - -.fa-charging-station:before { - content: "\f5e7"; } - -.fa-chart-area:before { - content: "\f1fe"; } - -.fa-chart-bar:before { - content: "\f080"; } - -.fa-chart-line:before { - content: "\f201"; } - -.fa-chart-pie:before { - content: "\f200"; } - -.fa-check:before { - content: "\f00c"; } - -.fa-check-circle:before { - content: "\f058"; } - -.fa-check-double:before { - content: "\f560"; } - -.fa-check-square:before { - content: "\f14a"; } - -.fa-cheese:before { - content: "\f7ef"; } - -.fa-chess:before { - content: "\f439"; } - -.fa-chess-bishop:before { - content: "\f43a"; } - -.fa-chess-board:before { - content: "\f43c"; } - -.fa-chess-king:before { - content: "\f43f"; } - -.fa-chess-knight:before { - content: "\f441"; } - -.fa-chess-pawn:before { - content: "\f443"; } - -.fa-chess-queen:before { - content: "\f445"; } - -.fa-chess-rook:before { - content: "\f447"; } - -.fa-chevron-circle-down:before { - content: "\f13a"; } - -.fa-chevron-circle-left:before { - content: "\f137"; } - -.fa-chevron-circle-right:before { - content: "\f138"; } - -.fa-chevron-circle-up:before { - content: "\f139"; } - -.fa-chevron-down:before { - content: "\f078"; } - -.fa-chevron-left:before { - content: "\f053"; } - -.fa-chevron-right:before { - content: "\f054"; } - -.fa-chevron-up:before { - content: "\f077"; } - -.fa-child:before { - content: "\f1ae"; } - -.fa-chrome:before { - content: "\f268"; } - -.fa-chromecast:before { - content: "\f838"; } - -.fa-church:before { - content: "\f51d"; } - -.fa-circle:before { - content: "\f111"; } - -.fa-circle-notch:before { - content: "\f1ce"; } - -.fa-city:before { - content: "\f64f"; } - -.fa-clinic-medical:before { - content: "\f7f2"; } - -.fa-clipboard:before { - content: "\f328"; } - -.fa-clipboard-check:before { - content: "\f46c"; } - -.fa-clipboard-list:before { - content: "\f46d"; } - -.fa-clock:before { - content: "\f017"; } - -.fa-clone:before { - content: "\f24d"; } - -.fa-closed-captioning:before { - content: "\f20a"; } - -.fa-cloud:before { - content: "\f0c2"; } - -.fa-cloud-download-alt:before { - content: "\f381"; } - -.fa-cloud-meatball:before { - content: "\f73b"; } - -.fa-cloud-moon:before { - content: "\f6c3"; } - -.fa-cloud-moon-rain:before { - content: "\f73c"; } - -.fa-cloud-rain:before { - content: "\f73d"; } - -.fa-cloud-showers-heavy:before { - content: "\f740"; } - -.fa-cloud-sun:before { - content: "\f6c4"; } - -.fa-cloud-sun-rain:before { - content: "\f743"; } - -.fa-cloud-upload-alt:before { - content: "\f382"; } - -.fa-cloudflare:before { - content: "\e07d"; } - -.fa-cloudscale:before { - content: "\f383"; } - -.fa-cloudsmith:before { - content: "\f384"; } - -.fa-cloudversify:before { - content: "\f385"; } - -.fa-cocktail:before { - content: "\f561"; } - -.fa-code:before { - content: "\f121"; } - -.fa-code-branch:before { - content: "\f126"; } - -.fa-codepen:before { - content: "\f1cb"; } - -.fa-codiepie:before { - content: "\f284"; } - -.fa-coffee:before { - content: "\f0f4"; } - -.fa-cog:before { - content: "\f013"; } - -.fa-cogs:before { - content: "\f085"; } - -.fa-coins:before { - content: "\f51e"; } - -.fa-columns:before { - content: "\f0db"; } - -.fa-comment:before { - content: "\f075"; } - -.fa-comment-alt:before { - content: "\f27a"; } - -.fa-comment-dollar:before { - content: "\f651"; } - -.fa-comment-dots:before { - content: "\f4ad"; } - -.fa-comment-medical:before { - content: "\f7f5"; } - -.fa-comment-slash:before { - content: "\f4b3"; } - -.fa-comments:before { - content: "\f086"; } - -.fa-comments-dollar:before { - content: "\f653"; } - -.fa-compact-disc:before { - content: "\f51f"; } - -.fa-compass:before { - content: "\f14e"; } - -.fa-compress:before { - content: "\f066"; } - -.fa-compress-alt:before { - content: "\f422"; } - -.fa-compress-arrows-alt:before { - content: "\f78c"; } - -.fa-concierge-bell:before { - content: "\f562"; } - -.fa-confluence:before { - content: "\f78d"; } - -.fa-connectdevelop:before { - content: "\f20e"; } - -.fa-contao:before { - content: "\f26d"; } - -.fa-cookie:before { - content: "\f563"; } - -.fa-cookie-bite:before { - content: "\f564"; } - -.fa-copy:before { - content: "\f0c5"; } - -.fa-copyright:before { - content: "\f1f9"; } - -.fa-cotton-bureau:before { - content: "\f89e"; } - -.fa-couch:before { - content: "\f4b8"; } - -.fa-cpanel:before { - content: "\f388"; } - -.fa-creative-commons:before { - content: "\f25e"; } - -.fa-creative-commons-by:before { - content: "\f4e7"; } - -.fa-creative-commons-nc:before { - content: "\f4e8"; } - -.fa-creative-commons-nc-eu:before { - content: "\f4e9"; } - -.fa-creative-commons-nc-jp:before { - content: "\f4ea"; } - -.fa-creative-commons-nd:before { - content: "\f4eb"; } - -.fa-creative-commons-pd:before { - content: "\f4ec"; } - -.fa-creative-commons-pd-alt:before { - content: "\f4ed"; } - -.fa-creative-commons-remix:before { - content: "\f4ee"; } - -.fa-creative-commons-sa:before { - content: "\f4ef"; } - -.fa-creative-commons-sampling:before { - content: "\f4f0"; } - -.fa-creative-commons-sampling-plus:before { - content: "\f4f1"; } - -.fa-creative-commons-share:before { - content: "\f4f2"; } - -.fa-creative-commons-zero:before { - content: "\f4f3"; } - -.fa-credit-card:before { - content: "\f09d"; } - -.fa-critical-role:before { - content: "\f6c9"; } - -.fa-crop:before { - content: "\f125"; } - -.fa-crop-alt:before { - content: "\f565"; } - -.fa-cross:before { - content: "\f654"; } - -.fa-crosshairs:before { - content: "\f05b"; } - -.fa-crow:before { - content: "\f520"; } - -.fa-crown:before { - content: "\f521"; } - -.fa-crutch:before { - content: "\f7f7"; } - -.fa-css3:before { - content: "\f13c"; } - -.fa-css3-alt:before { - content: "\f38b"; } - -.fa-cube:before { - content: "\f1b2"; } - -.fa-cubes:before { - content: "\f1b3"; } - -.fa-cut:before { - content: "\f0c4"; } - -.fa-cuttlefish:before { - content: "\f38c"; } - -.fa-d-and-d:before { - content: "\f38d"; } - -.fa-d-and-d-beyond:before { - content: "\f6ca"; } - -.fa-dailymotion:before { - content: "\e052"; } - -.fa-dashcube:before { - content: "\f210"; } - -.fa-database:before { - content: "\f1c0"; } - -.fa-deaf:before { - content: "\f2a4"; } - -.fa-deezer:before { - content: "\e077"; } - -.fa-delicious:before { - content: "\f1a5"; } - -.fa-democrat:before { - content: "\f747"; } - -.fa-deploydog:before { - content: "\f38e"; } - -.fa-deskpro:before { - content: "\f38f"; } - -.fa-desktop:before { - content: "\f108"; } - -.fa-dev:before { - content: "\f6cc"; } - -.fa-deviantart:before { - content: "\f1bd"; } - -.fa-dharmachakra:before { - content: "\f655"; } - -.fa-dhl:before { - content: "\f790"; } - -.fa-diagnoses:before { - content: "\f470"; } - -.fa-diaspora:before { - content: "\f791"; } - -.fa-dice:before { - content: "\f522"; } - -.fa-dice-d20:before { - content: "\f6cf"; } - -.fa-dice-d6:before { - content: "\f6d1"; } - -.fa-dice-five:before { - content: "\f523"; } - -.fa-dice-four:before { - content: "\f524"; } - -.fa-dice-one:before { - content: "\f525"; } - -.fa-dice-six:before { - content: "\f526"; } - -.fa-dice-three:before { - content: "\f527"; } - -.fa-dice-two:before { - content: "\f528"; } - -.fa-digg:before { - content: "\f1a6"; } - -.fa-digital-ocean:before { - content: "\f391"; } - -.fa-digital-tachograph:before { - content: "\f566"; } - -.fa-directions:before { - content: "\f5eb"; } - -.fa-discord:before { - content: "\f392"; } - -.fa-discourse:before { - content: "\f393"; } - -.fa-disease:before { - content: "\f7fa"; } - -.fa-divide:before { - content: "\f529"; } - -.fa-dizzy:before { - content: "\f567"; } - -.fa-dna:before { - content: "\f471"; } - -.fa-dochub:before { - content: "\f394"; } - -.fa-docker:before { - content: "\f395"; } - -.fa-dog:before { - content: "\f6d3"; } - -.fa-dollar-sign:before { - content: "\f155"; } - -.fa-dolly:before { - content: "\f472"; } - -.fa-dolly-flatbed:before { - content: "\f474"; } - -.fa-donate:before { - content: "\f4b9"; } - -.fa-door-closed:before { - content: "\f52a"; } - -.fa-door-open:before { - content: "\f52b"; } - -.fa-dot-circle:before { - content: "\f192"; } - -.fa-dove:before { - content: "\f4ba"; } - -.fa-download:before { - content: "\f019"; } - -.fa-draft2digital:before { - content: "\f396"; } - -.fa-drafting-compass:before { - content: "\f568"; } - -.fa-dragon:before { - content: "\f6d5"; } - -.fa-draw-polygon:before { - content: "\f5ee"; } - -.fa-dribbble:before { - content: "\f17d"; } - -.fa-dribbble-square:before { - content: "\f397"; } - -.fa-dropbox:before { - content: "\f16b"; } - -.fa-drum:before { - content: "\f569"; } - -.fa-drum-steelpan:before { - content: "\f56a"; } - -.fa-drumstick-bite:before { - content: "\f6d7"; } - -.fa-drupal:before { - content: "\f1a9"; } - -.fa-dumbbell:before { - content: "\f44b"; } - -.fa-dumpster:before { - content: "\f793"; } - -.fa-dumpster-fire:before { - content: "\f794"; } - -.fa-dungeon:before { - content: "\f6d9"; } - -.fa-dyalog:before { - content: "\f399"; } - -.fa-earlybirds:before { - content: "\f39a"; } - -.fa-ebay:before { - content: "\f4f4"; } - -.fa-edge:before { - content: "\f282"; } - -.fa-edge-legacy:before { - content: "\e078"; } - -.fa-edit:before { - content: "\f044"; } - -.fa-egg:before { - content: "\f7fb"; } - -.fa-eject:before { - content: "\f052"; } - -.fa-elementor:before { - content: "\f430"; } - -.fa-ellipsis-h:before { - content: "\f141"; } - -.fa-ellipsis-v:before { - content: "\f142"; } - -.fa-ello:before { - content: "\f5f1"; } - -.fa-ember:before { - content: "\f423"; } - -.fa-empire:before { - content: "\f1d1"; } - -.fa-envelope:before { - content: "\f0e0"; } - -.fa-envelope-open:before { - content: "\f2b6"; } - -.fa-envelope-open-text:before { - content: "\f658"; } - -.fa-envelope-square:before { - content: "\f199"; } - -.fa-envira:before { - content: "\f299"; } - -.fa-equals:before { - content: "\f52c"; } - -.fa-eraser:before { - content: "\f12d"; } - -.fa-erlang:before { - content: "\f39d"; } - -.fa-ethereum:before { - content: "\f42e"; } - -.fa-ethernet:before { - content: "\f796"; } - -.fa-etsy:before { - content: "\f2d7"; } - -.fa-euro-sign:before { - content: "\f153"; } - -.fa-evernote:before { - content: "\f839"; } - -.fa-exchange-alt:before { - content: "\f362"; } - -.fa-exclamation:before { - content: "\f12a"; } - -.fa-exclamation-circle:before { - content: "\f06a"; } - -.fa-exclamation-triangle:before { - content: "\f071"; } - -.fa-expand:before { - content: "\f065"; } - -.fa-expand-alt:before { - content: "\f424"; } - -.fa-expand-arrows-alt:before { - content: "\f31e"; } - -.fa-expeditedssl:before { - content: "\f23e"; } - -.fa-external-link-alt:before { - content: "\f35d"; } - -.fa-external-link-square-alt:before { - content: "\f360"; } - -.fa-eye:before { - content: "\f06e"; } - -.fa-eye-dropper:before { - content: "\f1fb"; } - -.fa-eye-slash:before { - content: "\f070"; } - -.fa-facebook:before { - content: "\f09a"; } - -.fa-facebook-f:before { - content: "\f39e"; } - -.fa-facebook-messenger:before { - content: "\f39f"; } - -.fa-facebook-square:before { - content: "\f082"; } - -.fa-fan:before { - content: "\f863"; } - -.fa-fantasy-flight-games:before { - content: "\f6dc"; } - -.fa-fast-backward:before { - content: "\f049"; } - -.fa-fast-forward:before { - content: "\f050"; } - -.fa-faucet:before { - content: "\e005"; } - -.fa-fax:before { - content: "\f1ac"; } - -.fa-feather:before { - content: "\f52d"; } - -.fa-feather-alt:before { - content: "\f56b"; } - -.fa-fedex:before { - content: "\f797"; } - -.fa-fedora:before { - content: "\f798"; } - -.fa-female:before { - content: "\f182"; } - -.fa-fighter-jet:before { - content: "\f0fb"; } - -.fa-figma:before { - content: "\f799"; } - -.fa-file:before { - content: "\f15b"; } - -.fa-file-alt:before { - content: "\f15c"; } - -.fa-file-archive:before { - content: "\f1c6"; } - -.fa-file-audio:before { - content: "\f1c7"; } - -.fa-file-code:before { - content: "\f1c9"; } - -.fa-file-contract:before { - content: "\f56c"; } - -.fa-file-csv:before { - content: "\f6dd"; } - -.fa-file-download:before { - content: "\f56d"; } - -.fa-file-excel:before { - content: "\f1c3"; } - -.fa-file-export:before { - content: "\f56e"; } - -.fa-file-image:before { - content: "\f1c5"; } - -.fa-file-import:before { - content: "\f56f"; } - -.fa-file-invoice:before { - content: "\f570"; } - -.fa-file-invoice-dollar:before { - content: "\f571"; } - -.fa-file-medical:before { - content: "\f477"; } - -.fa-file-medical-alt:before { - content: "\f478"; } - -.fa-file-pdf:before { - content: "\f1c1"; } - -.fa-file-powerpoint:before { - content: "\f1c4"; } - -.fa-file-prescription:before { - content: "\f572"; } - -.fa-file-signature:before { - content: "\f573"; } - -.fa-file-upload:before { - content: "\f574"; } - -.fa-file-video:before { - content: "\f1c8"; } - -.fa-file-word:before { - content: "\f1c2"; } - -.fa-fill:before { - content: "\f575"; } - -.fa-fill-drip:before { - content: "\f576"; } - -.fa-film:before { - content: "\f008"; } - -.fa-filter:before { - content: "\f0b0"; } - -.fa-fingerprint:before { - content: "\f577"; } - -.fa-fire:before { - content: "\f06d"; } - -.fa-fire-alt:before { - content: "\f7e4"; } - -.fa-fire-extinguisher:before { - content: "\f134"; } - -.fa-firefox:before { - content: "\f269"; } - -.fa-firefox-browser:before { - content: "\e007"; } - -.fa-first-aid:before { - content: "\f479"; } - -.fa-first-order:before { - content: "\f2b0"; } - -.fa-first-order-alt:before { - content: "\f50a"; } - -.fa-firstdraft:before { - content: "\f3a1"; } - -.fa-fish:before { - content: "\f578"; } - -.fa-fist-raised:before { - content: "\f6de"; } - -.fa-flag:before { - content: "\f024"; } - -.fa-flag-checkered:before { - content: "\f11e"; } - -.fa-flag-usa:before { - content: "\f74d"; } - -.fa-flask:before { - content: "\f0c3"; } - -.fa-flickr:before { - content: "\f16e"; } - -.fa-flipboard:before { - content: "\f44d"; } - -.fa-flushed:before { - content: "\f579"; } - -.fa-fly:before { - content: "\f417"; } - -.fa-folder:before { - content: "\f07b"; } - -.fa-folder-minus:before { - content: "\f65d"; } - -.fa-folder-open:before { - content: "\f07c"; } - -.fa-folder-plus:before { - content: "\f65e"; } - -.fa-font:before { - content: "\f031"; } - -.fa-font-awesome:before { - content: "\f2b4"; } - -.fa-font-awesome-alt:before { - content: "\f35c"; } - -.fa-font-awesome-flag:before { - content: "\f425"; } - -.fa-font-awesome-logo-full:before { - content: "\f4e6"; } - -.fa-fonticons:before { - content: "\f280"; } - -.fa-fonticons-fi:before { - content: "\f3a2"; } - -.fa-football-ball:before { - content: "\f44e"; } - -.fa-fort-awesome:before { - content: "\f286"; } - -.fa-fort-awesome-alt:before { - content: "\f3a3"; } - -.fa-forumbee:before { - content: "\f211"; } - -.fa-forward:before { - content: "\f04e"; } - -.fa-foursquare:before { - content: "\f180"; } - -.fa-free-code-camp:before { - content: "\f2c5"; } - -.fa-freebsd:before { - content: "\f3a4"; } - -.fa-frog:before { - content: "\f52e"; } - -.fa-frown:before { - content: "\f119"; } - -.fa-frown-open:before { - content: "\f57a"; } - -.fa-fulcrum:before { - content: "\f50b"; } - -.fa-funnel-dollar:before { - content: "\f662"; } - -.fa-futbol:before { - content: "\f1e3"; } - -.fa-galactic-republic:before { - content: "\f50c"; } - -.fa-galactic-senate:before { - content: "\f50d"; } - -.fa-gamepad:before { - content: "\f11b"; } - -.fa-gas-pump:before { - content: "\f52f"; } - -.fa-gavel:before { - content: "\f0e3"; } - -.fa-gem:before { - content: "\f3a5"; } - -.fa-genderless:before { - content: "\f22d"; } - -.fa-get-pocket:before { - content: "\f265"; } - -.fa-gg:before { - content: "\f260"; } - -.fa-gg-circle:before { - content: "\f261"; } - -.fa-ghost:before { - content: "\f6e2"; } - -.fa-gift:before { - content: "\f06b"; } - -.fa-gifts:before { - content: "\f79c"; } - -.fa-git:before { - content: "\f1d3"; } - -.fa-git-alt:before { - content: "\f841"; } - -.fa-git-square:before { - content: "\f1d2"; } - -.fa-github:before { - content: "\f09b"; } - -.fa-github-alt:before { - content: "\f113"; } - -.fa-github-square:before { - content: "\f092"; } - -.fa-gitkraken:before { - content: "\f3a6"; } - -.fa-gitlab:before { - content: "\f296"; } - -.fa-gitter:before { - content: "\f426"; } - -.fa-glass-cheers:before { - content: "\f79f"; } - -.fa-glass-martini:before { - content: "\f000"; } - -.fa-glass-martini-alt:before { - content: "\f57b"; } - -.fa-glass-whiskey:before { - content: "\f7a0"; } - -.fa-glasses:before { - content: "\f530"; } - -.fa-glide:before { - content: "\f2a5"; } - -.fa-glide-g:before { - content: "\f2a6"; } - -.fa-globe:before { - content: "\f0ac"; } - -.fa-globe-africa:before { - content: "\f57c"; } - -.fa-globe-americas:before { - content: "\f57d"; } - -.fa-globe-asia:before { - content: "\f57e"; } - -.fa-globe-europe:before { - content: "\f7a2"; } - -.fa-gofore:before { - content: "\f3a7"; } - -.fa-golf-ball:before { - content: "\f450"; } - -.fa-goodreads:before { - content: "\f3a8"; } - -.fa-goodreads-g:before { - content: "\f3a9"; } - -.fa-google:before { - content: "\f1a0"; } - -.fa-google-drive:before { - content: "\f3aa"; } - -.fa-google-pay:before { - content: "\e079"; } - -.fa-google-play:before { - content: "\f3ab"; } - -.fa-google-plus:before { - content: "\f2b3"; } - -.fa-google-plus-g:before { - content: "\f0d5"; } - -.fa-google-plus-square:before { - content: "\f0d4"; } - -.fa-google-wallet:before { - content: "\f1ee"; } - -.fa-gopuram:before { - content: "\f664"; } - -.fa-graduation-cap:before { - content: "\f19d"; } - -.fa-gratipay:before { - content: "\f184"; } - -.fa-grav:before { - content: "\f2d6"; } - -.fa-greater-than:before { - content: "\f531"; } - -.fa-greater-than-equal:before { - content: "\f532"; } - -.fa-grimace:before { - content: "\f57f"; } - -.fa-grin:before { - content: "\f580"; } - -.fa-grin-alt:before { - content: "\f581"; } - -.fa-grin-beam:before { - content: "\f582"; } - -.fa-grin-beam-sweat:before { - content: "\f583"; } - -.fa-grin-hearts:before { - content: "\f584"; } - -.fa-grin-squint:before { - content: "\f585"; } - -.fa-grin-squint-tears:before { - content: "\f586"; } - -.fa-grin-stars:before { - content: "\f587"; } - -.fa-grin-tears:before { - content: "\f588"; } - -.fa-grin-tongue:before { - content: "\f589"; } - -.fa-grin-tongue-squint:before { - content: "\f58a"; } - -.fa-grin-tongue-wink:before { - content: "\f58b"; } - -.fa-grin-wink:before { - content: "\f58c"; } - -.fa-grip-horizontal:before { - content: "\f58d"; } - -.fa-grip-lines:before { - content: "\f7a4"; } - -.fa-grip-lines-vertical:before { - content: "\f7a5"; } - -.fa-grip-vertical:before { - content: "\f58e"; } - -.fa-gripfire:before { - content: "\f3ac"; } - -.fa-grunt:before { - content: "\f3ad"; } - -.fa-guilded:before { - content: "\e07e"; } - -.fa-guitar:before { - content: "\f7a6"; } - -.fa-gulp:before { - content: "\f3ae"; } - -.fa-h-square:before { - content: "\f0fd"; } - -.fa-hacker-news:before { - content: "\f1d4"; } - -.fa-hacker-news-square:before { - content: "\f3af"; } - -.fa-hackerrank:before { - content: "\f5f7"; } - -.fa-hamburger:before { - content: "\f805"; } - -.fa-hammer:before { - content: "\f6e3"; } - -.fa-hamsa:before { - content: "\f665"; } - -.fa-hand-holding:before { - content: "\f4bd"; } - -.fa-hand-holding-heart:before { - content: "\f4be"; } - -.fa-hand-holding-medical:before { - content: "\e05c"; } - -.fa-hand-holding-usd:before { - content: "\f4c0"; } - -.fa-hand-holding-water:before { - content: "\f4c1"; } - -.fa-hand-lizard:before { - content: "\f258"; } - -.fa-hand-middle-finger:before { - content: "\f806"; } - -.fa-hand-paper:before { - content: "\f256"; } - -.fa-hand-peace:before { - content: "\f25b"; } - -.fa-hand-point-down:before { - content: "\f0a7"; } - -.fa-hand-point-left:before { - content: "\f0a5"; } - -.fa-hand-point-right:before { - content: "\f0a4"; } - -.fa-hand-point-up:before { - content: "\f0a6"; } - -.fa-hand-pointer:before { - content: "\f25a"; } - -.fa-hand-rock:before { - content: "\f255"; } - -.fa-hand-scissors:before { - content: "\f257"; } - -.fa-hand-sparkles:before { - content: "\e05d"; } - -.fa-hand-spock:before { - content: "\f259"; } - -.fa-hands:before { - content: "\f4c2"; } - -.fa-hands-helping:before { - content: "\f4c4"; } - -.fa-hands-wash:before { - content: "\e05e"; } - -.fa-handshake:before { - content: "\f2b5"; } - -.fa-handshake-alt-slash:before { - content: "\e05f"; } - -.fa-handshake-slash:before { - content: "\e060"; } - -.fa-hanukiah:before { - content: "\f6e6"; } - -.fa-hard-hat:before { - content: "\f807"; } - -.fa-hashtag:before { - content: "\f292"; } - -.fa-hat-cowboy:before { - content: "\f8c0"; } - -.fa-hat-cowboy-side:before { - content: "\f8c1"; } - -.fa-hat-wizard:before { - content: "\f6e8"; } - -.fa-hdd:before { - content: "\f0a0"; } - -.fa-head-side-cough:before { - content: "\e061"; } - -.fa-head-side-cough-slash:before { - content: "\e062"; } - -.fa-head-side-mask:before { - content: "\e063"; } - -.fa-head-side-virus:before { - content: "\e064"; } - -.fa-heading:before { - content: "\f1dc"; } - -.fa-headphones:before { - content: "\f025"; } - -.fa-headphones-alt:before { - content: "\f58f"; } - -.fa-headset:before { - content: "\f590"; } - -.fa-heart:before { - content: "\f004"; } - -.fa-heart-broken:before { - content: "\f7a9"; } - -.fa-heartbeat:before { - content: "\f21e"; } - -.fa-helicopter:before { - content: "\f533"; } - -.fa-highlighter:before { - content: "\f591"; } - -.fa-hiking:before { - content: "\f6ec"; } - -.fa-hippo:before { - content: "\f6ed"; } - -.fa-hips:before { - content: "\f452"; } - -.fa-hire-a-helper:before { - content: "\f3b0"; } - -.fa-history:before { - content: "\f1da"; } - -.fa-hive:before { - content: "\e07f"; } - -.fa-hockey-puck:before { - content: "\f453"; } - -.fa-holly-berry:before { - content: "\f7aa"; } - -.fa-home:before { - content: "\f015"; } - -.fa-hooli:before { - content: "\f427"; } - -.fa-hornbill:before { - content: "\f592"; } - -.fa-horse:before { - content: "\f6f0"; } - -.fa-horse-head:before { - content: "\f7ab"; } - -.fa-hospital:before { - content: "\f0f8"; } - -.fa-hospital-alt:before { - content: "\f47d"; } - -.fa-hospital-symbol:before { - content: "\f47e"; } - -.fa-hospital-user:before { - content: "\f80d"; } - -.fa-hot-tub:before { - content: "\f593"; } - -.fa-hotdog:before { - content: "\f80f"; } - -.fa-hotel:before { - content: "\f594"; } - -.fa-hotjar:before { - content: "\f3b1"; } - -.fa-hourglass:before { - content: "\f254"; } - -.fa-hourglass-end:before { - content: "\f253"; } - -.fa-hourglass-half:before { - content: "\f252"; } - -.fa-hourglass-start:before { - content: "\f251"; } - -.fa-house-damage:before { - content: "\f6f1"; } - -.fa-house-user:before { - content: "\e065"; } - -.fa-houzz:before { - content: "\f27c"; } - -.fa-hryvnia:before { - content: "\f6f2"; } - -.fa-html5:before { - content: "\f13b"; } - -.fa-hubspot:before { - content: "\f3b2"; } - -.fa-i-cursor:before { - content: "\f246"; } - -.fa-ice-cream:before { - content: "\f810"; } - -.fa-icicles:before { - content: "\f7ad"; } - -.fa-icons:before { - content: "\f86d"; } - -.fa-id-badge:before { - content: "\f2c1"; } - -.fa-id-card:before { - content: "\f2c2"; } - -.fa-id-card-alt:before { - content: "\f47f"; } - -.fa-ideal:before { - content: "\e013"; } - -.fa-igloo:before { - content: "\f7ae"; } - -.fa-image:before { - content: "\f03e"; } - -.fa-images:before { - content: "\f302"; } - -.fa-imdb:before { - content: "\f2d8"; } - -.fa-inbox:before { - content: "\f01c"; } - -.fa-indent:before { - content: "\f03c"; } - -.fa-industry:before { - content: "\f275"; } - -.fa-infinity:before { - content: "\f534"; } - -.fa-info:before { - content: "\f129"; } - -.fa-info-circle:before { - content: "\f05a"; } - -.fa-innosoft:before { - content: "\e080"; } - -.fa-instagram:before { - content: "\f16d"; } - -.fa-instagram-square:before { - content: "\e055"; } - -.fa-instalod:before { - content: "\e081"; } - -.fa-intercom:before { - content: "\f7af"; } - -.fa-internet-explorer:before { - content: "\f26b"; } - -.fa-invision:before { - content: "\f7b0"; } - -.fa-ioxhost:before { - content: "\f208"; } - -.fa-italic:before { - content: "\f033"; } - -.fa-itch-io:before { - content: "\f83a"; } - -.fa-itunes:before { - content: "\f3b4"; } - -.fa-itunes-note:before { - content: "\f3b5"; } - -.fa-java:before { - content: "\f4e4"; } - -.fa-jedi:before { - content: "\f669"; } - -.fa-jedi-order:before { - content: "\f50e"; } - -.fa-jenkins:before { - content: "\f3b6"; } - -.fa-jira:before { - content: "\f7b1"; } - -.fa-joget:before { - content: "\f3b7"; } - -.fa-joint:before { - content: "\f595"; } - -.fa-joomla:before { - content: "\f1aa"; } - -.fa-journal-whills:before { - content: "\f66a"; } - -.fa-js:before { - content: "\f3b8"; } - -.fa-js-square:before { - content: "\f3b9"; } - -.fa-jsfiddle:before { - content: "\f1cc"; } - -.fa-kaaba:before { - content: "\f66b"; } - -.fa-kaggle:before { - content: "\f5fa"; } - -.fa-key:before { - content: "\f084"; } - -.fa-keybase:before { - content: "\f4f5"; } - -.fa-keyboard:before { - content: "\f11c"; } - -.fa-keycdn:before { - content: "\f3ba"; } - -.fa-khanda:before { - content: "\f66d"; } - -.fa-kickstarter:before { - content: "\f3bb"; } - -.fa-kickstarter-k:before { - content: "\f3bc"; } - -.fa-kiss:before { - content: "\f596"; } - -.fa-kiss-beam:before { - content: "\f597"; } - -.fa-kiss-wink-heart:before { - content: "\f598"; } - -.fa-kiwi-bird:before { - content: "\f535"; } - -.fa-korvue:before { - content: "\f42f"; } - -.fa-landmark:before { - content: "\f66f"; } - -.fa-language:before { - content: "\f1ab"; } - -.fa-laptop:before { - content: "\f109"; } - -.fa-laptop-code:before { - content: "\f5fc"; } - -.fa-laptop-house:before { - content: "\e066"; } - -.fa-laptop-medical:before { - content: "\f812"; } - -.fa-laravel:before { - content: "\f3bd"; } - -.fa-lastfm:before { - content: "\f202"; } - -.fa-lastfm-square:before { - content: "\f203"; } - -.fa-laugh:before { - content: "\f599"; } - -.fa-laugh-beam:before { - content: "\f59a"; } - -.fa-laugh-squint:before { - content: "\f59b"; } - -.fa-laugh-wink:before { - content: "\f59c"; } - -.fa-layer-group:before { - content: "\f5fd"; } - -.fa-leaf:before { - content: "\f06c"; } - -.fa-leanpub:before { - content: "\f212"; } - -.fa-lemon:before { - content: "\f094"; } - -.fa-less:before { - content: "\f41d"; } - -.fa-less-than:before { - content: "\f536"; } - -.fa-less-than-equal:before { - content: "\f537"; } - -.fa-level-down-alt:before { - content: "\f3be"; } - -.fa-level-up-alt:before { - content: "\f3bf"; } - -.fa-life-ring:before { - content: "\f1cd"; } - -.fa-lightbulb:before { - content: "\f0eb"; } - -.fa-line:before { - content: "\f3c0"; } - -.fa-link:before { - content: "\f0c1"; } - -.fa-linkedin:before { - content: "\f08c"; } - -.fa-linkedin-in:before { - content: "\f0e1"; } - -.fa-linode:before { - content: "\f2b8"; } - -.fa-linux:before { - content: "\f17c"; } - -.fa-lira-sign:before { - content: "\f195"; } - -.fa-list:before { - content: "\f03a"; } - -.fa-list-alt:before { - content: "\f022"; } - -.fa-list-ol:before { - content: "\f0cb"; } - -.fa-list-ul:before { - content: "\f0ca"; } - -.fa-location-arrow:before { - content: "\f124"; } - -.fa-lock:before { - content: "\f023"; } - -.fa-lock-open:before { - content: "\f3c1"; } - -.fa-long-arrow-alt-down:before { - content: "\f309"; } - -.fa-long-arrow-alt-left:before { - content: "\f30a"; } - -.fa-long-arrow-alt-right:before { - content: "\f30b"; } - -.fa-long-arrow-alt-up:before { - content: "\f30c"; } - -.fa-low-vision:before { - content: "\f2a8"; } - -.fa-luggage-cart:before { - content: "\f59d"; } - -.fa-lungs:before { - content: "\f604"; } - -.fa-lungs-virus:before { - content: "\e067"; } - -.fa-lyft:before { - content: "\f3c3"; } - -.fa-magento:before { - content: "\f3c4"; } - -.fa-magic:before { - content: "\f0d0"; } - -.fa-magnet:before { - content: "\f076"; } - -.fa-mail-bulk:before { - content: "\f674"; } - -.fa-mailchimp:before { - content: "\f59e"; } - -.fa-male:before { - content: "\f183"; } - -.fa-mandalorian:before { - content: "\f50f"; } - -.fa-map:before { - content: "\f279"; } - -.fa-map-marked:before { - content: "\f59f"; } - -.fa-map-marked-alt:before { - content: "\f5a0"; } - -.fa-map-marker:before { - content: "\f041"; } - -.fa-map-marker-alt:before { - content: "\f3c5"; } - -.fa-map-pin:before { - content: "\f276"; } - -.fa-map-signs:before { - content: "\f277"; } - -.fa-markdown:before { - content: "\f60f"; } - -.fa-marker:before { - content: "\f5a1"; } - -.fa-mars:before { - content: "\f222"; } - -.fa-mars-double:before { - content: "\f227"; } - -.fa-mars-stroke:before { - content: "\f229"; } - -.fa-mars-stroke-h:before { - content: "\f22b"; } - -.fa-mars-stroke-v:before { - content: "\f22a"; } - -.fa-mask:before { - content: "\f6fa"; } - -.fa-mastodon:before { - content: "\f4f6"; } - -.fa-maxcdn:before { - content: "\f136"; } - -.fa-mdb:before { - content: "\f8ca"; } - -.fa-medal:before { - content: "\f5a2"; } - -.fa-medapps:before { - content: "\f3c6"; } - -.fa-medium:before { - content: "\f23a"; } - -.fa-medium-m:before { - content: "\f3c7"; } - -.fa-medkit:before { - content: "\f0fa"; } - -.fa-medrt:before { - content: "\f3c8"; } - -.fa-meetup:before { - content: "\f2e0"; } - -.fa-megaport:before { - content: "\f5a3"; } - -.fa-meh:before { - content: "\f11a"; } - -.fa-meh-blank:before { - content: "\f5a4"; } - -.fa-meh-rolling-eyes:before { - content: "\f5a5"; } - -.fa-memory:before { - content: "\f538"; } - -.fa-mendeley:before { - content: "\f7b3"; } - -.fa-menorah:before { - content: "\f676"; } - -.fa-mercury:before { - content: "\f223"; } - -.fa-meteor:before { - content: "\f753"; } - -.fa-microblog:before { - content: "\e01a"; } - -.fa-microchip:before { - content: "\f2db"; } - -.fa-microphone:before { - content: "\f130"; } - -.fa-microphone-alt:before { - content: "\f3c9"; } - -.fa-microphone-alt-slash:before { - content: "\f539"; } - -.fa-microphone-slash:before { - content: "\f131"; } - -.fa-microscope:before { - content: "\f610"; } - -.fa-microsoft:before { - content: "\f3ca"; } - -.fa-minus:before { - content: "\f068"; } - -.fa-minus-circle:before { - content: "\f056"; } - -.fa-minus-square:before { - content: "\f146"; } - -.fa-mitten:before { - content: "\f7b5"; } - -.fa-mix:before { - content: "\f3cb"; } - -.fa-mixcloud:before { - content: "\f289"; } - -.fa-mixer:before { - content: "\e056"; } - -.fa-mizuni:before { - content: "\f3cc"; } - -.fa-mobile:before { - content: "\f10b"; } - -.fa-mobile-alt:before { - content: "\f3cd"; } - -.fa-modx:before { - content: "\f285"; } - -.fa-monero:before { - content: "\f3d0"; } - -.fa-money-bill:before { - content: "\f0d6"; } - -.fa-money-bill-alt:before { - content: "\f3d1"; } - -.fa-money-bill-wave:before { - content: "\f53a"; } - -.fa-money-bill-wave-alt:before { - content: "\f53b"; } - -.fa-money-check:before { - content: "\f53c"; } - -.fa-money-check-alt:before { - content: "\f53d"; } - -.fa-monument:before { - content: "\f5a6"; } - -.fa-moon:before { - content: "\f186"; } - -.fa-mortar-pestle:before { - content: "\f5a7"; } - -.fa-mosque:before { - content: "\f678"; } - -.fa-motorcycle:before { - content: "\f21c"; } - -.fa-mountain:before { - content: "\f6fc"; } - -.fa-mouse:before { - content: "\f8cc"; } - -.fa-mouse-pointer:before { - content: "\f245"; } - -.fa-mug-hot:before { - content: "\f7b6"; } - -.fa-music:before { - content: "\f001"; } - -.fa-napster:before { - content: "\f3d2"; } - -.fa-neos:before { - content: "\f612"; } - -.fa-network-wired:before { - content: "\f6ff"; } - -.fa-neuter:before { - content: "\f22c"; } - -.fa-newspaper:before { - content: "\f1ea"; } - -.fa-nimblr:before { - content: "\f5a8"; } - -.fa-node:before { - content: "\f419"; } - -.fa-node-js:before { - content: "\f3d3"; } - -.fa-not-equal:before { - content: "\f53e"; } - -.fa-notes-medical:before { - content: "\f481"; } - -.fa-npm:before { - content: "\f3d4"; } - -.fa-ns8:before { - content: "\f3d5"; } - -.fa-nutritionix:before { - content: "\f3d6"; } - -.fa-object-group:before { - content: "\f247"; } - -.fa-object-ungroup:before { - content: "\f248"; } - -.fa-octopus-deploy:before { - content: "\e082"; } - -.fa-odnoklassniki:before { - content: "\f263"; } - -.fa-odnoklassniki-square:before { - content: "\f264"; } - -.fa-oil-can:before { - content: "\f613"; } - -.fa-old-republic:before { - content: "\f510"; } - -.fa-om:before { - content: "\f679"; } - -.fa-opencart:before { - content: "\f23d"; } - -.fa-openid:before { - content: "\f19b"; } - -.fa-opera:before { - content: "\f26a"; } - -.fa-optin-monster:before { - content: "\f23c"; } - -.fa-orcid:before { - content: "\f8d2"; } - -.fa-osi:before { - content: "\f41a"; } - -.fa-otter:before { - content: "\f700"; } - -.fa-outdent:before { - content: "\f03b"; } - -.fa-page4:before { - content: "\f3d7"; } - -.fa-pagelines:before { - content: "\f18c"; } - -.fa-pager:before { - content: "\f815"; } - -.fa-paint-brush:before { - content: "\f1fc"; } - -.fa-paint-roller:before { - content: "\f5aa"; } - -.fa-palette:before { - content: "\f53f"; } - -.fa-palfed:before { - content: "\f3d8"; } - -.fa-pallet:before { - content: "\f482"; } - -.fa-paper-plane:before { - content: "\f1d8"; } - -.fa-paperclip:before { - content: "\f0c6"; } - -.fa-parachute-box:before { - content: "\f4cd"; } - -.fa-paragraph:before { - content: "\f1dd"; } - -.fa-parking:before { - content: "\f540"; } - -.fa-passport:before { - content: "\f5ab"; } - -.fa-pastafarianism:before { - content: "\f67b"; } - -.fa-paste:before { - content: "\f0ea"; } - -.fa-patreon:before { - content: "\f3d9"; } - -.fa-pause:before { - content: "\f04c"; } - -.fa-pause-circle:before { - content: "\f28b"; } - -.fa-paw:before { - content: "\f1b0"; } - -.fa-paypal:before { - content: "\f1ed"; } - -.fa-peace:before { - content: "\f67c"; } - -.fa-pen:before { - content: "\f304"; } - -.fa-pen-alt:before { - content: "\f305"; } - -.fa-pen-fancy:before { - content: "\f5ac"; } - -.fa-pen-nib:before { - content: "\f5ad"; } - -.fa-pen-square:before { - content: "\f14b"; } - -.fa-pencil-alt:before { - content: "\f303"; } - -.fa-pencil-ruler:before { - content: "\f5ae"; } - -.fa-penny-arcade:before { - content: "\f704"; } - -.fa-people-arrows:before { - content: "\e068"; } - -.fa-people-carry:before { - content: "\f4ce"; } - -.fa-pepper-hot:before { - content: "\f816"; } - -.fa-perbyte:before { - content: "\e083"; } - -.fa-percent:before { - content: "\f295"; } - -.fa-percentage:before { - content: "\f541"; } - -.fa-periscope:before { - content: "\f3da"; } - -.fa-person-booth:before { - content: "\f756"; } - -.fa-phabricator:before { - content: "\f3db"; } - -.fa-phoenix-framework:before { - content: "\f3dc"; } - -.fa-phoenix-squadron:before { - content: "\f511"; } - -.fa-phone:before { - content: "\f095"; } - -.fa-phone-alt:before { - content: "\f879"; } - -.fa-phone-slash:before { - content: "\f3dd"; } - -.fa-phone-square:before { - content: "\f098"; } - -.fa-phone-square-alt:before { - content: "\f87b"; } - -.fa-phone-volume:before { - content: "\f2a0"; } - -.fa-photo-video:before { - content: "\f87c"; } - -.fa-php:before { - content: "\f457"; } - -.fa-pied-piper:before { - content: "\f2ae"; } - -.fa-pied-piper-alt:before { - content: "\f1a8"; } - -.fa-pied-piper-hat:before { - content: "\f4e5"; } - -.fa-pied-piper-pp:before { - content: "\f1a7"; } - -.fa-pied-piper-square:before { - content: "\e01e"; } - -.fa-piggy-bank:before { - content: "\f4d3"; } - -.fa-pills:before { - content: "\f484"; } - -.fa-pinterest:before { - content: "\f0d2"; } - -.fa-pinterest-p:before { - content: "\f231"; } - -.fa-pinterest-square:before { - content: "\f0d3"; } - -.fa-pizza-slice:before { - content: "\f818"; } - -.fa-place-of-worship:before { - content: "\f67f"; } - -.fa-plane:before { - content: "\f072"; } - -.fa-plane-arrival:before { - content: "\f5af"; } - -.fa-plane-departure:before { - content: "\f5b0"; } - -.fa-plane-slash:before { - content: "\e069"; } - -.fa-play:before { - content: "\f04b"; } - -.fa-play-circle:before { - content: "\f144"; } - -.fa-playstation:before { - content: "\f3df"; } - -.fa-plug:before { - content: "\f1e6"; } - -.fa-plus:before { - content: "\f067"; } - -.fa-plus-circle:before { - content: "\f055"; } - -.fa-plus-square:before { - content: "\f0fe"; } - -.fa-podcast:before { - content: "\f2ce"; } - -.fa-poll:before { - content: "\f681"; } - -.fa-poll-h:before { - content: "\f682"; } - -.fa-poo:before { - content: "\f2fe"; } - -.fa-poo-storm:before { - content: "\f75a"; } - -.fa-poop:before { - content: "\f619"; } - -.fa-portrait:before { - content: "\f3e0"; } - -.fa-pound-sign:before { - content: "\f154"; } - -.fa-power-off:before { - content: "\f011"; } - -.fa-pray:before { - content: "\f683"; } - -.fa-praying-hands:before { - content: "\f684"; } - -.fa-prescription:before { - content: "\f5b1"; } - -.fa-prescription-bottle:before { - content: "\f485"; } - -.fa-prescription-bottle-alt:before { - content: "\f486"; } - -.fa-print:before { - content: "\f02f"; } - -.fa-procedures:before { - content: "\f487"; } - -.fa-product-hunt:before { - content: "\f288"; } - -.fa-project-diagram:before { - content: "\f542"; } - -.fa-pump-medical:before { - content: "\e06a"; } - -.fa-pump-soap:before { - content: "\e06b"; } - -.fa-pushed:before { - content: "\f3e1"; } - -.fa-puzzle-piece:before { - content: "\f12e"; } - -.fa-python:before { - content: "\f3e2"; } - -.fa-qq:before { - content: "\f1d6"; } - -.fa-qrcode:before { - content: "\f029"; } - -.fa-question:before { - content: "\f128"; } - -.fa-question-circle:before { - content: "\f059"; } - -.fa-quidditch:before { - content: "\f458"; } - -.fa-quinscape:before { - content: "\f459"; } - -.fa-quora:before { - content: "\f2c4"; } - -.fa-quote-left:before { - content: "\f10d"; } - -.fa-quote-right:before { - content: "\f10e"; } - -.fa-quran:before { - content: "\f687"; } - -.fa-r-project:before { - content: "\f4f7"; } - -.fa-radiation:before { - content: "\f7b9"; } - -.fa-radiation-alt:before { - content: "\f7ba"; } - -.fa-rainbow:before { - content: "\f75b"; } - -.fa-random:before { - content: "\f074"; } - -.fa-raspberry-pi:before { - content: "\f7bb"; } - -.fa-ravelry:before { - content: "\f2d9"; } - -.fa-react:before { - content: "\f41b"; } - -.fa-reacteurope:before { - content: "\f75d"; } - -.fa-readme:before { - content: "\f4d5"; } - -.fa-rebel:before { - content: "\f1d0"; } - -.fa-receipt:before { - content: "\f543"; } - -.fa-record-vinyl:before { - content: "\f8d9"; } - -.fa-recycle:before { - content: "\f1b8"; } - -.fa-red-river:before { - content: "\f3e3"; } - -.fa-reddit:before { - content: "\f1a1"; } - -.fa-reddit-alien:before { - content: "\f281"; } - -.fa-reddit-square:before { - content: "\f1a2"; } - -.fa-redhat:before { - content: "\f7bc"; } - -.fa-redo:before { - content: "\f01e"; } - -.fa-redo-alt:before { - content: "\f2f9"; } - -.fa-registered:before { - content: "\f25d"; } - -.fa-remove-format:before { - content: "\f87d"; } - -.fa-renren:before { - content: "\f18b"; } - -.fa-reply:before { - content: "\f3e5"; } - -.fa-reply-all:before { - content: "\f122"; } - -.fa-replyd:before { - content: "\f3e6"; } - -.fa-republican:before { - content: "\f75e"; } - -.fa-researchgate:before { - content: "\f4f8"; } - -.fa-resolving:before { - content: "\f3e7"; } - -.fa-restroom:before { - content: "\f7bd"; } - -.fa-retweet:before { - content: "\f079"; } - -.fa-rev:before { - content: "\f5b2"; } - -.fa-ribbon:before { - content: "\f4d6"; } - -.fa-ring:before { - content: "\f70b"; } - -.fa-road:before { - content: "\f018"; } - -.fa-robot:before { - content: "\f544"; } - -.fa-rocket:before { - content: "\f135"; } - -.fa-rocketchat:before { - content: "\f3e8"; } - -.fa-rockrms:before { - content: "\f3e9"; } - -.fa-route:before { - content: "\f4d7"; } - -.fa-rss:before { - content: "\f09e"; } - -.fa-rss-square:before { - content: "\f143"; } - -.fa-ruble-sign:before { - content: "\f158"; } - -.fa-ruler:before { - content: "\f545"; } - -.fa-ruler-combined:before { - content: "\f546"; } - -.fa-ruler-horizontal:before { - content: "\f547"; } - -.fa-ruler-vertical:before { - content: "\f548"; } - -.fa-running:before { - content: "\f70c"; } - -.fa-rupee-sign:before { - content: "\f156"; } - -.fa-rust:before { - content: "\e07a"; } - -.fa-sad-cry:before { - content: "\f5b3"; } - -.fa-sad-tear:before { - content: "\f5b4"; } - -.fa-safari:before { - content: "\f267"; } - -.fa-salesforce:before { - content: "\f83b"; } - -.fa-sass:before { - content: "\f41e"; } - -.fa-satellite:before { - content: "\f7bf"; } - -.fa-satellite-dish:before { - content: "\f7c0"; } - -.fa-save:before { - content: "\f0c7"; } - -.fa-schlix:before { - content: "\f3ea"; } - -.fa-school:before { - content: "\f549"; } - -.fa-screwdriver:before { - content: "\f54a"; } - -.fa-scribd:before { - content: "\f28a"; } - -.fa-scroll:before { - content: "\f70e"; } - -.fa-sd-card:before { - content: "\f7c2"; } - -.fa-search:before { - content: "\f002"; } - -.fa-search-dollar:before { - content: "\f688"; } - -.fa-search-location:before { - content: "\f689"; } - -.fa-search-minus:before { - content: "\f010"; } - -.fa-search-plus:before { - content: "\f00e"; } - -.fa-searchengin:before { - content: "\f3eb"; } - -.fa-seedling:before { - content: "\f4d8"; } - -.fa-sellcast:before { - content: "\f2da"; } - -.fa-sellsy:before { - content: "\f213"; } - -.fa-server:before { - content: "\f233"; } - -.fa-servicestack:before { - content: "\f3ec"; } - -.fa-shapes:before { - content: "\f61f"; } - -.fa-share:before { - content: "\f064"; } - -.fa-share-alt:before { - content: "\f1e0"; } - -.fa-share-alt-square:before { - content: "\f1e1"; } - -.fa-share-square:before { - content: "\f14d"; } - -.fa-shekel-sign:before { - content: "\f20b"; } - -.fa-shield-alt:before { - content: "\f3ed"; } - -.fa-shield-virus:before { - content: "\e06c"; } - -.fa-ship:before { - content: "\f21a"; } - -.fa-shipping-fast:before { - content: "\f48b"; } - -.fa-shirtsinbulk:before { - content: "\f214"; } - -.fa-shoe-prints:before { - content: "\f54b"; } - -.fa-shopify:before { - content: "\e057"; } - -.fa-shopping-bag:before { - content: "\f290"; } - -.fa-shopping-basket:before { - content: "\f291"; } - -.fa-shopping-cart:before { - content: "\f07a"; } - -.fa-shopware:before { - content: "\f5b5"; } - -.fa-shower:before { - content: "\f2cc"; } - -.fa-shuttle-van:before { - content: "\f5b6"; } - -.fa-sign:before { - content: "\f4d9"; } - -.fa-sign-in-alt:before { - content: "\f2f6"; } - -.fa-sign-language:before { - content: "\f2a7"; } - -.fa-sign-out-alt:before { - content: "\f2f5"; } - -.fa-signal:before { - content: "\f012"; } - -.fa-signature:before { - content: "\f5b7"; } - -.fa-sim-card:before { - content: "\f7c4"; } - -.fa-simplybuilt:before { - content: "\f215"; } - -.fa-sink:before { - content: "\e06d"; } - -.fa-sistrix:before { - content: "\f3ee"; } - -.fa-sitemap:before { - content: "\f0e8"; } - -.fa-sith:before { - content: "\f512"; } - -.fa-skating:before { - content: "\f7c5"; } - -.fa-sketch:before { - content: "\f7c6"; } - -.fa-skiing:before { - content: "\f7c9"; } - -.fa-skiing-nordic:before { - content: "\f7ca"; } - -.fa-skull:before { - content: "\f54c"; } - -.fa-skull-crossbones:before { - content: "\f714"; } - -.fa-skyatlas:before { - content: "\f216"; } - -.fa-skype:before { - content: "\f17e"; } - -.fa-slack:before { - content: "\f198"; } - -.fa-slack-hash:before { - content: "\f3ef"; } - -.fa-slash:before { - content: "\f715"; } - -.fa-sleigh:before { - content: "\f7cc"; } - -.fa-sliders-h:before { - content: "\f1de"; } - -.fa-slideshare:before { - content: "\f1e7"; } - -.fa-smile:before { - content: "\f118"; } - -.fa-smile-beam:before { - content: "\f5b8"; } - -.fa-smile-wink:before { - content: "\f4da"; } - -.fa-smog:before { - content: "\f75f"; } - -.fa-smoking:before { - content: "\f48d"; } - -.fa-smoking-ban:before { - content: "\f54d"; } - -.fa-sms:before { - content: "\f7cd"; } - -.fa-snapchat:before { - content: "\f2ab"; } - -.fa-snapchat-ghost:before { - content: "\f2ac"; } - -.fa-snapchat-square:before { - content: "\f2ad"; } - -.fa-snowboarding:before { - content: "\f7ce"; } - -.fa-snowflake:before { - content: "\f2dc"; } - -.fa-snowman:before { - content: "\f7d0"; } - -.fa-snowplow:before { - content: "\f7d2"; } - -.fa-soap:before { - content: "\e06e"; } - -.fa-socks:before { - content: "\f696"; } - -.fa-solar-panel:before { - content: "\f5ba"; } - -.fa-sort:before { - content: "\f0dc"; } - -.fa-sort-alpha-down:before { - content: "\f15d"; } - -.fa-sort-alpha-down-alt:before { - content: "\f881"; } - -.fa-sort-alpha-up:before { - content: "\f15e"; } - -.fa-sort-alpha-up-alt:before { - content: "\f882"; } - -.fa-sort-amount-down:before { - content: "\f160"; } - -.fa-sort-amount-down-alt:before { - content: "\f884"; } - -.fa-sort-amount-up:before { - content: "\f161"; } - -.fa-sort-amount-up-alt:before { - content: "\f885"; } - -.fa-sort-down:before { - content: "\f0dd"; } - -.fa-sort-numeric-down:before { - content: "\f162"; } - -.fa-sort-numeric-down-alt:before { - content: "\f886"; } - -.fa-sort-numeric-up:before { - content: "\f163"; } - -.fa-sort-numeric-up-alt:before { - content: "\f887"; } - -.fa-sort-up:before { - content: "\f0de"; } - -.fa-soundcloud:before { - content: "\f1be"; } - -.fa-sourcetree:before { - content: "\f7d3"; } - -.fa-spa:before { - content: "\f5bb"; } - -.fa-space-shuttle:before { - content: "\f197"; } - -.fa-speakap:before { - content: "\f3f3"; } - -.fa-speaker-deck:before { - content: "\f83c"; } - -.fa-spell-check:before { - content: "\f891"; } - -.fa-spider:before { - content: "\f717"; } - -.fa-spinner:before { - content: "\f110"; } - -.fa-splotch:before { - content: "\f5bc"; } - -.fa-spotify:before { - content: "\f1bc"; } - -.fa-spray-can:before { - content: "\f5bd"; } - -.fa-square:before { - content: "\f0c8"; } - -.fa-square-full:before { - content: "\f45c"; } - -.fa-square-root-alt:before { - content: "\f698"; } - -.fa-squarespace:before { - content: "\f5be"; } - -.fa-stack-exchange:before { - content: "\f18d"; } - -.fa-stack-overflow:before { - content: "\f16c"; } - -.fa-stackpath:before { - content: "\f842"; } - -.fa-stamp:before { - content: "\f5bf"; } - -.fa-star:before { - content: "\f005"; } - -.fa-star-and-crescent:before { - content: "\f699"; } - -.fa-star-half:before { - content: "\f089"; } - -.fa-star-half-alt:before { - content: "\f5c0"; } - -.fa-star-of-david:before { - content: "\f69a"; } - -.fa-star-of-life:before { - content: "\f621"; } - -.fa-staylinked:before { - content: "\f3f5"; } - -.fa-steam:before { - content: "\f1b6"; } - -.fa-steam-square:before { - content: "\f1b7"; } - -.fa-steam-symbol:before { - content: "\f3f6"; } - -.fa-step-backward:before { - content: "\f048"; } - -.fa-step-forward:before { - content: "\f051"; } - -.fa-stethoscope:before { - content: "\f0f1"; } - -.fa-sticker-mule:before { - content: "\f3f7"; } - -.fa-sticky-note:before { - content: "\f249"; } - -.fa-stop:before { - content: "\f04d"; } - -.fa-stop-circle:before { - content: "\f28d"; } - -.fa-stopwatch:before { - content: "\f2f2"; } - -.fa-stopwatch-20:before { - content: "\e06f"; } - -.fa-store:before { - content: "\f54e"; } - -.fa-store-alt:before { - content: "\f54f"; } - -.fa-store-alt-slash:before { - content: "\e070"; } - -.fa-store-slash:before { - content: "\e071"; } - -.fa-strava:before { - content: "\f428"; } - -.fa-stream:before { - content: "\f550"; } - -.fa-street-view:before { - content: "\f21d"; } - -.fa-strikethrough:before { - content: "\f0cc"; } - -.fa-stripe:before { - content: "\f429"; } - -.fa-stripe-s:before { - content: "\f42a"; } - -.fa-stroopwafel:before { - content: "\f551"; } - -.fa-studiovinari:before { - content: "\f3f8"; } - -.fa-stumbleupon:before { - content: "\f1a4"; } - -.fa-stumbleupon-circle:before { - content: "\f1a3"; } - -.fa-subscript:before { - content: "\f12c"; } - -.fa-subway:before { - content: "\f239"; } - -.fa-suitcase:before { - content: "\f0f2"; } - -.fa-suitcase-rolling:before { - content: "\f5c1"; } - -.fa-sun:before { - content: "\f185"; } - -.fa-superpowers:before { - content: "\f2dd"; } - -.fa-superscript:before { - content: "\f12b"; } - -.fa-supple:before { - content: "\f3f9"; } - -.fa-surprise:before { - content: "\f5c2"; } - -.fa-suse:before { - content: "\f7d6"; } - -.fa-swatchbook:before { - content: "\f5c3"; } - -.fa-swift:before { - content: "\f8e1"; } - -.fa-swimmer:before { - content: "\f5c4"; } - -.fa-swimming-pool:before { - content: "\f5c5"; } - -.fa-symfony:before { - content: "\f83d"; } - -.fa-synagogue:before { - content: "\f69b"; } - -.fa-sync:before { - content: "\f021"; } - -.fa-sync-alt:before { - content: "\f2f1"; } - -.fa-syringe:before { - content: "\f48e"; } - -.fa-table:before { - content: "\f0ce"; } - -.fa-table-tennis:before { - content: "\f45d"; } - -.fa-tablet:before { - content: "\f10a"; } - -.fa-tablet-alt:before { - content: "\f3fa"; } - -.fa-tablets:before { - content: "\f490"; } - -.fa-tachometer-alt:before { - content: "\f3fd"; } - -.fa-tag:before { - content: "\f02b"; } - -.fa-tags:before { - content: "\f02c"; } - -.fa-tape:before { - content: "\f4db"; } - -.fa-tasks:before { - content: "\f0ae"; } - -.fa-taxi:before { - content: "\f1ba"; } - -.fa-teamspeak:before { - content: "\f4f9"; } - -.fa-teeth:before { - content: "\f62e"; } - -.fa-teeth-open:before { - content: "\f62f"; } - -.fa-telegram:before { - content: "\f2c6"; } - -.fa-telegram-plane:before { - content: "\f3fe"; } - -.fa-temperature-high:before { - content: "\f769"; } - -.fa-temperature-low:before { - content: "\f76b"; } - -.fa-tencent-weibo:before { - content: "\f1d5"; } - -.fa-tenge:before { - content: "\f7d7"; } - -.fa-terminal:before { - content: "\f120"; } - -.fa-text-height:before { - content: "\f034"; } - -.fa-text-width:before { - content: "\f035"; } - -.fa-th:before { - content: "\f00a"; } - -.fa-th-large:before { - content: "\f009"; } - -.fa-th-list:before { - content: "\f00b"; } - -.fa-the-red-yeti:before { - content: "\f69d"; } - -.fa-theater-masks:before { - content: "\f630"; } - -.fa-themeco:before { - content: "\f5c6"; } - -.fa-themeisle:before { - content: "\f2b2"; } - -.fa-thermometer:before { - content: "\f491"; } - -.fa-thermometer-empty:before { - content: "\f2cb"; } - -.fa-thermometer-full:before { - content: "\f2c7"; } - -.fa-thermometer-half:before { - content: "\f2c9"; } - -.fa-thermometer-quarter:before { - content: "\f2ca"; } - -.fa-thermometer-three-quarters:before { - content: "\f2c8"; } - -.fa-think-peaks:before { - content: "\f731"; } - -.fa-thumbs-down:before { - content: "\f165"; } - -.fa-thumbs-up:before { - content: "\f164"; } - -.fa-thumbtack:before { - content: "\f08d"; } - -.fa-ticket-alt:before { - content: "\f3ff"; } - -.fa-tiktok:before { - content: "\e07b"; } - -.fa-times:before { - content: "\f00d"; } - -.fa-times-circle:before { - content: "\f057"; } - -.fa-tint:before { - content: "\f043"; } - -.fa-tint-slash:before { - content: "\f5c7"; } - -.fa-tired:before { - content: "\f5c8"; } - -.fa-toggle-off:before { - content: "\f204"; } - -.fa-toggle-on:before { - content: "\f205"; } - -.fa-toilet:before { - content: "\f7d8"; } - -.fa-toilet-paper:before { - content: "\f71e"; } - -.fa-toilet-paper-slash:before { - content: "\e072"; } - -.fa-toolbox:before { - content: "\f552"; } - -.fa-tools:before { - content: "\f7d9"; } - -.fa-tooth:before { - content: "\f5c9"; } - -.fa-torah:before { - content: "\f6a0"; } - -.fa-torii-gate:before { - content: "\f6a1"; } - -.fa-tractor:before { - content: "\f722"; } - -.fa-trade-federation:before { - content: "\f513"; } - -.fa-trademark:before { - content: "\f25c"; } - -.fa-traffic-light:before { - content: "\f637"; } - -.fa-trailer:before { - content: "\e041"; } - -.fa-train:before { - content: "\f238"; } - -.fa-tram:before { - content: "\f7da"; } - -.fa-transgender:before { - content: "\f224"; } - -.fa-transgender-alt:before { - content: "\f225"; } - -.fa-trash:before { - content: "\f1f8"; } - -.fa-trash-alt:before { - content: "\f2ed"; } - -.fa-trash-restore:before { - content: "\f829"; } - -.fa-trash-restore-alt:before { - content: "\f82a"; } - -.fa-tree:before { - content: "\f1bb"; } - -.fa-trello:before { - content: "\f181"; } - -.fa-trophy:before { - content: "\f091"; } - -.fa-truck:before { - content: "\f0d1"; } - -.fa-truck-loading:before { - content: "\f4de"; } - -.fa-truck-monster:before { - content: "\f63b"; } - -.fa-truck-moving:before { - content: "\f4df"; } - -.fa-truck-pickup:before { - content: "\f63c"; } - -.fa-tshirt:before { - content: "\f553"; } - -.fa-tty:before { - content: "\f1e4"; } - -.fa-tumblr:before { - content: "\f173"; } - -.fa-tumblr-square:before { - content: "\f174"; } - -.fa-tv:before { - content: "\f26c"; } - -.fa-twitch:before { - content: "\f1e8"; } - -.fa-twitter:before { - content: "\f099"; } - -.fa-twitter-square:before { - content: "\f081"; } - -.fa-typo3:before { - content: "\f42b"; } - -.fa-uber:before { - content: "\f402"; } - -.fa-ubuntu:before { - content: "\f7df"; } - -.fa-uikit:before { - content: "\f403"; } - -.fa-umbraco:before { - content: "\f8e8"; } - -.fa-umbrella:before { - content: "\f0e9"; } - -.fa-umbrella-beach:before { - content: "\f5ca"; } - -.fa-uncharted:before { - content: "\e084"; } - -.fa-underline:before { - content: "\f0cd"; } - -.fa-undo:before { - content: "\f0e2"; } - -.fa-undo-alt:before { - content: "\f2ea"; } - -.fa-uniregistry:before { - content: "\f404"; } - -.fa-unity:before { - content: "\e049"; } - -.fa-universal-access:before { - content: "\f29a"; } - -.fa-university:before { - content: "\f19c"; } - -.fa-unlink:before { - content: "\f127"; } - -.fa-unlock:before { - content: "\f09c"; } - -.fa-unlock-alt:before { - content: "\f13e"; } - -.fa-unsplash:before { - content: "\e07c"; } - -.fa-untappd:before { - content: "\f405"; } - -.fa-upload:before { - content: "\f093"; } - -.fa-ups:before { - content: "\f7e0"; } - -.fa-usb:before { - content: "\f287"; } - -.fa-user:before { - content: "\f007"; } - -.fa-user-alt:before { - content: "\f406"; } - -.fa-user-alt-slash:before { - content: "\f4fa"; } - -.fa-user-astronaut:before { - content: "\f4fb"; } - -.fa-user-check:before { - content: "\f4fc"; } - -.fa-user-circle:before { - content: "\f2bd"; } - -.fa-user-clock:before { - content: "\f4fd"; } - -.fa-user-cog:before { - content: "\f4fe"; } - -.fa-user-edit:before { - content: "\f4ff"; } - -.fa-user-friends:before { - content: "\f500"; } - -.fa-user-graduate:before { - content: "\f501"; } - -.fa-user-injured:before { - content: "\f728"; } - -.fa-user-lock:before { - content: "\f502"; } - -.fa-user-md:before { - content: "\f0f0"; } - -.fa-user-minus:before { - content: "\f503"; } - -.fa-user-ninja:before { - content: "\f504"; } - -.fa-user-nurse:before { - content: "\f82f"; } - -.fa-user-plus:before { - content: "\f234"; } - -.fa-user-secret:before { - content: "\f21b"; } - -.fa-user-shield:before { - content: "\f505"; } - -.fa-user-slash:before { - content: "\f506"; } - -.fa-user-tag:before { - content: "\f507"; } - -.fa-user-tie:before { - content: "\f508"; } - -.fa-user-times:before { - content: "\f235"; } - -.fa-users:before { - content: "\f0c0"; } - -.fa-users-cog:before { - content: "\f509"; } - -.fa-users-slash:before { - content: "\e073"; } - -.fa-usps:before { - content: "\f7e1"; } - -.fa-ussunnah:before { - content: "\f407"; } - -.fa-utensil-spoon:before { - content: "\f2e5"; } - -.fa-utensils:before { - content: "\f2e7"; } - -.fa-vaadin:before { - content: "\f408"; } - -.fa-vector-square:before { - content: "\f5cb"; } - -.fa-venus:before { - content: "\f221"; } - -.fa-venus-double:before { - content: "\f226"; } - -.fa-venus-mars:before { - content: "\f228"; } - -.fa-vest:before { - content: "\e085"; } - -.fa-vest-patches:before { - content: "\e086"; } - -.fa-viacoin:before { - content: "\f237"; } - -.fa-viadeo:before { - content: "\f2a9"; } - -.fa-viadeo-square:before { - content: "\f2aa"; } - -.fa-vial:before { - content: "\f492"; } - -.fa-vials:before { - content: "\f493"; } - -.fa-viber:before { - content: "\f409"; } - -.fa-video:before { - content: "\f03d"; } - -.fa-video-slash:before { - content: "\f4e2"; } - -.fa-vihara:before { - content: "\f6a7"; } - -.fa-vimeo:before { - content: "\f40a"; } - -.fa-vimeo-square:before { - content: "\f194"; } - -.fa-vimeo-v:before { - content: "\f27d"; } - -.fa-vine:before { - content: "\f1ca"; } - -.fa-virus:before { - content: "\e074"; } - -.fa-virus-slash:before { - content: "\e075"; } - -.fa-viruses:before { - content: "\e076"; } - -.fa-vk:before { - content: "\f189"; } - -.fa-vnv:before { - content: "\f40b"; } - -.fa-voicemail:before { - content: "\f897"; } - -.fa-volleyball-ball:before { - content: "\f45f"; } - -.fa-volume-down:before { - content: "\f027"; } - -.fa-volume-mute:before { - content: "\f6a9"; } - -.fa-volume-off:before { - content: "\f026"; } - -.fa-volume-up:before { - content: "\f028"; } - -.fa-vote-yea:before { - content: "\f772"; } - -.fa-vr-cardboard:before { - content: "\f729"; } - -.fa-vuejs:before { - content: "\f41f"; } - -.fa-walking:before { - content: "\f554"; } - -.fa-wallet:before { - content: "\f555"; } - -.fa-warehouse:before { - content: "\f494"; } - -.fa-watchman-monitoring:before { - content: "\e087"; } - -.fa-water:before { - content: "\f773"; } - -.fa-wave-square:before { - content: "\f83e"; } - -.fa-waze:before { - content: "\f83f"; } - -.fa-weebly:before { - content: "\f5cc"; } - -.fa-weibo:before { - content: "\f18a"; } - -.fa-weight:before { - content: "\f496"; } - -.fa-weight-hanging:before { - content: "\f5cd"; } - -.fa-weixin:before { - content: "\f1d7"; } - -.fa-whatsapp:before { - content: "\f232"; } - -.fa-whatsapp-square:before { - content: "\f40c"; } - -.fa-wheelchair:before { - content: "\f193"; } - -.fa-whmcs:before { - content: "\f40d"; } - -.fa-wifi:before { - content: "\f1eb"; } - -.fa-wikipedia-w:before { - content: "\f266"; } - -.fa-wind:before { - content: "\f72e"; } - -.fa-window-close:before { - content: "\f410"; } - -.fa-window-maximize:before { - content: "\f2d0"; } - -.fa-window-minimize:before { - content: "\f2d1"; } - -.fa-window-restore:before { - content: "\f2d2"; } - -.fa-windows:before { - content: "\f17a"; } - -.fa-wine-bottle:before { - content: "\f72f"; } - -.fa-wine-glass:before { - content: "\f4e3"; } - -.fa-wine-glass-alt:before { - content: "\f5ce"; } - -.fa-wix:before { - content: "\f5cf"; } - -.fa-wizards-of-the-coast:before { - content: "\f730"; } - -.fa-wodu:before { - content: "\e088"; } - -.fa-wolf-pack-battalion:before { - content: "\f514"; } - -.fa-won-sign:before { - content: "\f159"; } - -.fa-wordpress:before { - content: "\f19a"; } - -.fa-wordpress-simple:before { - content: "\f411"; } - -.fa-wpbeginner:before { - content: "\f297"; } - -.fa-wpexplorer:before { - content: "\f2de"; } - -.fa-wpforms:before { - content: "\f298"; } - -.fa-wpressr:before { - content: "\f3e4"; } - -.fa-wrench:before { - content: "\f0ad"; } - -.fa-x-ray:before { - content: "\f497"; } - -.fa-xbox:before { - content: "\f412"; } - -.fa-xing:before { - content: "\f168"; } - -.fa-xing-square:before { - content: "\f169"; } - -.fa-y-combinator:before { - content: "\f23b"; } - -.fa-yahoo:before { - content: "\f19e"; } - -.fa-yammer:before { - content: "\f840"; } - -.fa-yandex:before { - content: "\f413"; } - -.fa-yandex-international:before { - content: "\f414"; } - -.fa-yarn:before { - content: "\f7e3"; } - -.fa-yelp:before { - content: "\f1e9"; } - -.fa-yen-sign:before { - content: "\f157"; } - -.fa-yin-yang:before { - content: "\f6ad"; } - -.fa-yoast:before { - content: "\f2b1"; } - -.fa-youtube:before { - content: "\f167"; } - -.fa-youtube-square:before { - content: "\f431"; } - -.fa-zhihu:before { - content: "\f63f"; } - -.sr-only { - border: 0; - clip: rect(0, 0, 0, 0); - height: 1px; - margin: -1px; - overflow: hidden; - padding: 0; - position: absolute; - width: 1px; } - -.sr-only-focusable:active, .sr-only-focusable:focus { - clip: auto; - height: auto; - margin: 0; - overflow: visible; - position: static; - width: auto; } -@font-face { - font-family: 'Font Awesome 5 Brands'; - font-style: normal; - font-weight: 400; - font-display: block; - src: url("../webfonts/fa-brands-400.eot"); - src: url("../webfonts/fa-brands-400.eot?#iefix") format("embedded-opentype"), url("../webfonts/fa-brands-400.woff2") format("woff2"), url("../webfonts/fa-brands-400.woff") format("woff"), url("../webfonts/fa-brands-400.ttf") format("truetype"), url("../webfonts/fa-brands-400.svg#fontawesome") format("svg"); } - -.fab { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } -@font-face { - font-family: 'Font Awesome 5 Free'; - font-style: normal; - font-weight: 400; - font-display: block; - src: url("../webfonts/fa-regular-400.eot"); - src: url("../webfonts/fa-regular-400.eot?#iefix") format("embedded-opentype"), url("../webfonts/fa-regular-400.woff2") format("woff2"), url("../webfonts/fa-regular-400.woff") format("woff"), url("../webfonts/fa-regular-400.ttf") format("truetype"), url("../webfonts/fa-regular-400.svg#fontawesome") format("svg"); } - -.far { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } -@font-face { - font-family: 'Font Awesome 5 Free'; - font-style: normal; - font-weight: 900; - font-display: block; - src: url("../webfonts/fa-solid-900.eot"); - src: url("../webfonts/fa-solid-900.eot?#iefix") format("embedded-opentype"), url("../webfonts/fa-solid-900.woff2") format("woff2"), url("../webfonts/fa-solid-900.woff") format("woff"), url("../webfonts/fa-solid-900.ttf") format("truetype"), url("../webfonts/fa-solid-900.svg#fontawesome") format("svg"); } - -.fa, -.fas { - font-family: 'Font Awesome 5 Free'; - font-weight: 900; } diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/v4-shims.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/v4-shims.css deleted file mode 100644 index 1ef4893b4a..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/css/v4-shims.css +++ /dev/null @@ -1,2172 +0,0 @@ -/*! - * Font Awesome Free 5.15.4 by @fontawesome - https://fontawesome.com - * License - https://fontawesome.com/license/free (Icons: CC BY 4.0, Fonts: SIL OFL 1.1, Code: MIT License) - */ -.fa.fa-glass:before { - content: "\f000"; } - -.fa.fa-meetup { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-star-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-star-o:before { - content: "\f005"; } - -.fa.fa-remove:before { - content: "\f00d"; } - -.fa.fa-close:before { - content: "\f00d"; } - -.fa.fa-gear:before { - content: "\f013"; } - -.fa.fa-trash-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-trash-o:before { - content: "\f2ed"; } - -.fa.fa-file-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-o:before { - content: "\f15b"; } - -.fa.fa-clock-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-clock-o:before { - content: "\f017"; } - -.fa.fa-arrow-circle-o-down { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-arrow-circle-o-down:before { - content: "\f358"; } - -.fa.fa-arrow-circle-o-up { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-arrow-circle-o-up:before { - content: "\f35b"; } - -.fa.fa-play-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-play-circle-o:before { - content: "\f144"; } - -.fa.fa-repeat:before { - content: "\f01e"; } - -.fa.fa-rotate-right:before { - content: "\f01e"; } - -.fa.fa-refresh:before { - content: "\f021"; } - -.fa.fa-list-alt { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-dedent:before { - content: "\f03b"; } - -.fa.fa-video-camera:before { - content: "\f03d"; } - -.fa.fa-picture-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-picture-o:before { - content: "\f03e"; } - -.fa.fa-photo { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-photo:before { - content: "\f03e"; } - -.fa.fa-image { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-image:before { - content: "\f03e"; } - -.fa.fa-pencil:before { - content: "\f303"; } - -.fa.fa-map-marker:before { - content: "\f3c5"; } - -.fa.fa-pencil-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-pencil-square-o:before { - content: "\f044"; } - -.fa.fa-share-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-share-square-o:before { - content: "\f14d"; } - -.fa.fa-check-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-check-square-o:before { - content: "\f14a"; } - -.fa.fa-arrows:before { - content: "\f0b2"; } - -.fa.fa-times-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-times-circle-o:before { - content: "\f057"; } - -.fa.fa-check-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-check-circle-o:before { - content: "\f058"; } - -.fa.fa-mail-forward:before { - content: "\f064"; } - -.fa.fa-expand:before { - content: "\f424"; } - -.fa.fa-compress:before { - content: "\f422"; } - -.fa.fa-eye { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-eye-slash { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-warning:before { - content: "\f071"; } - -.fa.fa-calendar:before { - content: "\f073"; } - -.fa.fa-arrows-v:before { - content: "\f338"; } - -.fa.fa-arrows-h:before { - content: "\f337"; } - -.fa.fa-bar-chart { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-bar-chart:before { - content: "\f080"; } - -.fa.fa-bar-chart-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-bar-chart-o:before { - content: "\f080"; } - -.fa.fa-twitter-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-facebook-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gears:before { - content: "\f085"; } - -.fa.fa-thumbs-o-up { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-thumbs-o-up:before { - content: "\f164"; } - -.fa.fa-thumbs-o-down { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-thumbs-o-down:before { - content: "\f165"; } - -.fa.fa-heart-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-heart-o:before { - content: "\f004"; } - -.fa.fa-sign-out:before { - content: "\f2f5"; } - -.fa.fa-linkedin-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-linkedin-square:before { - content: "\f08c"; } - -.fa.fa-thumb-tack:before { - content: "\f08d"; } - -.fa.fa-external-link:before { - content: "\f35d"; } - -.fa.fa-sign-in:before { - content: "\f2f6"; } - -.fa.fa-github-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-lemon-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-lemon-o:before { - content: "\f094"; } - -.fa.fa-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-square-o:before { - content: "\f0c8"; } - -.fa.fa-bookmark-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-bookmark-o:before { - content: "\f02e"; } - -.fa.fa-twitter { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-facebook { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-facebook:before { - content: "\f39e"; } - -.fa.fa-facebook-f { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-facebook-f:before { - content: "\f39e"; } - -.fa.fa-github { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-credit-card { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-feed:before { - content: "\f09e"; } - -.fa.fa-hdd-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hdd-o:before { - content: "\f0a0"; } - -.fa.fa-hand-o-right { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-o-right:before { - content: "\f0a4"; } - -.fa.fa-hand-o-left { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-o-left:before { - content: "\f0a5"; } - -.fa.fa-hand-o-up { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-o-up:before { - content: "\f0a6"; } - -.fa.fa-hand-o-down { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-o-down:before { - content: "\f0a7"; } - -.fa.fa-arrows-alt:before { - content: "\f31e"; } - -.fa.fa-group:before { - content: "\f0c0"; } - -.fa.fa-chain:before { - content: "\f0c1"; } - -.fa.fa-scissors:before { - content: "\f0c4"; } - -.fa.fa-files-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-files-o:before { - content: "\f0c5"; } - -.fa.fa-floppy-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-floppy-o:before { - content: "\f0c7"; } - -.fa.fa-navicon:before { - content: "\f0c9"; } - -.fa.fa-reorder:before { - content: "\f0c9"; } - -.fa.fa-pinterest { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pinterest-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus:before { - content: "\f0d5"; } - -.fa.fa-money { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-money:before { - content: "\f3d1"; } - -.fa.fa-unsorted:before { - content: "\f0dc"; } - -.fa.fa-sort-desc:before { - content: "\f0dd"; } - -.fa.fa-sort-asc:before { - content: "\f0de"; } - -.fa.fa-linkedin { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-linkedin:before { - content: "\f0e1"; } - -.fa.fa-rotate-left:before { - content: "\f0e2"; } - -.fa.fa-legal:before { - content: "\f0e3"; } - -.fa.fa-tachometer:before { - content: "\f3fd"; } - -.fa.fa-dashboard:before { - content: "\f3fd"; } - -.fa.fa-comment-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-comment-o:before { - content: "\f075"; } - -.fa.fa-comments-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-comments-o:before { - content: "\f086"; } - -.fa.fa-flash:before { - content: "\f0e7"; } - -.fa.fa-clipboard { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-paste { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-paste:before { - content: "\f328"; } - -.fa.fa-lightbulb-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-lightbulb-o:before { - content: "\f0eb"; } - -.fa.fa-exchange:before { - content: "\f362"; } - -.fa.fa-cloud-download:before { - content: "\f381"; } - -.fa.fa-cloud-upload:before { - content: "\f382"; } - -.fa.fa-bell-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-bell-o:before { - content: "\f0f3"; } - -.fa.fa-cutlery:before { - content: "\f2e7"; } - -.fa.fa-file-text-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-text-o:before { - content: "\f15c"; } - -.fa.fa-building-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-building-o:before { - content: "\f1ad"; } - -.fa.fa-hospital-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hospital-o:before { - content: "\f0f8"; } - -.fa.fa-tablet:before { - content: "\f3fa"; } - -.fa.fa-mobile:before { - content: "\f3cd"; } - -.fa.fa-mobile-phone:before { - content: "\f3cd"; } - -.fa.fa-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-circle-o:before { - content: "\f111"; } - -.fa.fa-mail-reply:before { - content: "\f3e5"; } - -.fa.fa-github-alt { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-folder-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-folder-o:before { - content: "\f07b"; } - -.fa.fa-folder-open-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-folder-open-o:before { - content: "\f07c"; } - -.fa.fa-smile-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-smile-o:before { - content: "\f118"; } - -.fa.fa-frown-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-frown-o:before { - content: "\f119"; } - -.fa.fa-meh-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-meh-o:before { - content: "\f11a"; } - -.fa.fa-keyboard-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-keyboard-o:before { - content: "\f11c"; } - -.fa.fa-flag-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-flag-o:before { - content: "\f024"; } - -.fa.fa-mail-reply-all:before { - content: "\f122"; } - -.fa.fa-star-half-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-star-half-o:before { - content: "\f089"; } - -.fa.fa-star-half-empty { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-star-half-empty:before { - content: "\f089"; } - -.fa.fa-star-half-full { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-star-half-full:before { - content: "\f089"; } - -.fa.fa-code-fork:before { - content: "\f126"; } - -.fa.fa-chain-broken:before { - content: "\f127"; } - -.fa.fa-shield:before { - content: "\f3ed"; } - -.fa.fa-calendar-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-calendar-o:before { - content: "\f133"; } - -.fa.fa-maxcdn { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-html5 { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-css3 { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ticket:before { - content: "\f3ff"; } - -.fa.fa-minus-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-minus-square-o:before { - content: "\f146"; } - -.fa.fa-level-up:before { - content: "\f3bf"; } - -.fa.fa-level-down:before { - content: "\f3be"; } - -.fa.fa-pencil-square:before { - content: "\f14b"; } - -.fa.fa-external-link-square:before { - content: "\f360"; } - -.fa.fa-compass { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-caret-square-o-down { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-caret-square-o-down:before { - content: "\f150"; } - -.fa.fa-toggle-down { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-toggle-down:before { - content: "\f150"; } - -.fa.fa-caret-square-o-up { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-caret-square-o-up:before { - content: "\f151"; } - -.fa.fa-toggle-up { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-toggle-up:before { - content: "\f151"; } - -.fa.fa-caret-square-o-right { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-caret-square-o-right:before { - content: "\f152"; } - -.fa.fa-toggle-right { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-toggle-right:before { - content: "\f152"; } - -.fa.fa-eur:before { - content: "\f153"; } - -.fa.fa-euro:before { - content: "\f153"; } - -.fa.fa-gbp:before { - content: "\f154"; } - -.fa.fa-usd:before { - content: "\f155"; } - -.fa.fa-dollar:before { - content: "\f155"; } - -.fa.fa-inr:before { - content: "\f156"; } - -.fa.fa-rupee:before { - content: "\f156"; } - -.fa.fa-jpy:before { - content: "\f157"; } - -.fa.fa-cny:before { - content: "\f157"; } - -.fa.fa-rmb:before { - content: "\f157"; } - -.fa.fa-yen:before { - content: "\f157"; } - -.fa.fa-rub:before { - content: "\f158"; } - -.fa.fa-ruble:before { - content: "\f158"; } - -.fa.fa-rouble:before { - content: "\f158"; } - -.fa.fa-krw:before { - content: "\f159"; } - -.fa.fa-won:before { - content: "\f159"; } - -.fa.fa-btc { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bitcoin { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bitcoin:before { - content: "\f15a"; } - -.fa.fa-file-text:before { - content: "\f15c"; } - -.fa.fa-sort-alpha-asc:before { - content: "\f15d"; } - -.fa.fa-sort-alpha-desc:before { - content: "\f881"; } - -.fa.fa-sort-amount-asc:before { - content: "\f160"; } - -.fa.fa-sort-amount-desc:before { - content: "\f884"; } - -.fa.fa-sort-numeric-asc:before { - content: "\f162"; } - -.fa.fa-sort-numeric-desc:before { - content: "\f886"; } - -.fa.fa-youtube-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-youtube { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-xing { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-xing-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-youtube-play { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-youtube-play:before { - content: "\f167"; } - -.fa.fa-dropbox { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-stack-overflow { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-instagram { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-flickr { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-adn { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bitbucket { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bitbucket-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bitbucket-square:before { - content: "\f171"; } - -.fa.fa-tumblr { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-tumblr-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-long-arrow-down:before { - content: "\f309"; } - -.fa.fa-long-arrow-up:before { - content: "\f30c"; } - -.fa.fa-long-arrow-left:before { - content: "\f30a"; } - -.fa.fa-long-arrow-right:before { - content: "\f30b"; } - -.fa.fa-apple { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-windows { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-android { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-linux { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-dribbble { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-skype { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-foursquare { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-trello { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gratipay { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gittip { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gittip:before { - content: "\f184"; } - -.fa.fa-sun-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-sun-o:before { - content: "\f185"; } - -.fa.fa-moon-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-moon-o:before { - content: "\f186"; } - -.fa.fa-vk { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-weibo { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-renren { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pagelines { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-stack-exchange { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-arrow-circle-o-right { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-arrow-circle-o-right:before { - content: "\f35a"; } - -.fa.fa-arrow-circle-o-left { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-arrow-circle-o-left:before { - content: "\f359"; } - -.fa.fa-caret-square-o-left { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-caret-square-o-left:before { - content: "\f191"; } - -.fa.fa-toggle-left { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-toggle-left:before { - content: "\f191"; } - -.fa.fa-dot-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-dot-circle-o:before { - content: "\f192"; } - -.fa.fa-vimeo-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-try:before { - content: "\f195"; } - -.fa.fa-turkish-lira:before { - content: "\f195"; } - -.fa.fa-plus-square-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-plus-square-o:before { - content: "\f0fe"; } - -.fa.fa-slack { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wordpress { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-openid { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-institution:before { - content: "\f19c"; } - -.fa.fa-bank:before { - content: "\f19c"; } - -.fa.fa-mortar-board:before { - content: "\f19d"; } - -.fa.fa-yahoo { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-reddit { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-reddit-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-stumbleupon-circle { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-stumbleupon { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-delicious { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-digg { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pied-piper-pp { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pied-piper-alt { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-drupal { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-joomla { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-spoon:before { - content: "\f2e5"; } - -.fa.fa-behance { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-behance-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-steam { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-steam-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-automobile:before { - content: "\f1b9"; } - -.fa.fa-envelope-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-envelope-o:before { - content: "\f0e0"; } - -.fa.fa-spotify { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-deviantart { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-soundcloud { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-file-pdf-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-pdf-o:before { - content: "\f1c1"; } - -.fa.fa-file-word-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-word-o:before { - content: "\f1c2"; } - -.fa.fa-file-excel-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-excel-o:before { - content: "\f1c3"; } - -.fa.fa-file-powerpoint-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-powerpoint-o:before { - content: "\f1c4"; } - -.fa.fa-file-image-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-image-o:before { - content: "\f1c5"; } - -.fa.fa-file-photo-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-photo-o:before { - content: "\f1c5"; } - -.fa.fa-file-picture-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-picture-o:before { - content: "\f1c5"; } - -.fa.fa-file-archive-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-archive-o:before { - content: "\f1c6"; } - -.fa.fa-file-zip-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-zip-o:before { - content: "\f1c6"; } - -.fa.fa-file-audio-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-audio-o:before { - content: "\f1c7"; } - -.fa.fa-file-sound-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-sound-o:before { - content: "\f1c7"; } - -.fa.fa-file-video-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-video-o:before { - content: "\f1c8"; } - -.fa.fa-file-movie-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-movie-o:before { - content: "\f1c8"; } - -.fa.fa-file-code-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-file-code-o:before { - content: "\f1c9"; } - -.fa.fa-vine { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-codepen { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-jsfiddle { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-life-ring { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-life-bouy { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-life-bouy:before { - content: "\f1cd"; } - -.fa.fa-life-buoy { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-life-buoy:before { - content: "\f1cd"; } - -.fa.fa-life-saver { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-life-saver:before { - content: "\f1cd"; } - -.fa.fa-support { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-support:before { - content: "\f1cd"; } - -.fa.fa-circle-o-notch:before { - content: "\f1ce"; } - -.fa.fa-rebel { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ra { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ra:before { - content: "\f1d0"; } - -.fa.fa-resistance { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-resistance:before { - content: "\f1d0"; } - -.fa.fa-empire { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ge { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ge:before { - content: "\f1d1"; } - -.fa.fa-git-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-git { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-hacker-news { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-y-combinator-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-y-combinator-square:before { - content: "\f1d4"; } - -.fa.fa-yc-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-yc-square:before { - content: "\f1d4"; } - -.fa.fa-tencent-weibo { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-qq { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-weixin { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wechat { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wechat:before { - content: "\f1d7"; } - -.fa.fa-send:before { - content: "\f1d8"; } - -.fa.fa-paper-plane-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-paper-plane-o:before { - content: "\f1d8"; } - -.fa.fa-send-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-send-o:before { - content: "\f1d8"; } - -.fa.fa-circle-thin { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-circle-thin:before { - content: "\f111"; } - -.fa.fa-header:before { - content: "\f1dc"; } - -.fa.fa-sliders:before { - content: "\f1de"; } - -.fa.fa-futbol-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-futbol-o:before { - content: "\f1e3"; } - -.fa.fa-soccer-ball-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-soccer-ball-o:before { - content: "\f1e3"; } - -.fa.fa-slideshare { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-twitch { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-yelp { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-newspaper-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-newspaper-o:before { - content: "\f1ea"; } - -.fa.fa-paypal { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-wallet { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-visa { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-mastercard { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-discover { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-amex { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-paypal { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-stripe { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bell-slash-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-bell-slash-o:before { - content: "\f1f6"; } - -.fa.fa-trash:before { - content: "\f2ed"; } - -.fa.fa-copyright { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-eyedropper:before { - content: "\f1fb"; } - -.fa.fa-area-chart:before { - content: "\f1fe"; } - -.fa.fa-pie-chart:before { - content: "\f200"; } - -.fa.fa-line-chart:before { - content: "\f201"; } - -.fa.fa-lastfm { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-lastfm-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ioxhost { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-angellist { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-cc:before { - content: "\f20a"; } - -.fa.fa-ils:before { - content: "\f20b"; } - -.fa.fa-shekel:before { - content: "\f20b"; } - -.fa.fa-sheqel:before { - content: "\f20b"; } - -.fa.fa-meanpath { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-meanpath:before { - content: "\f2b4"; } - -.fa.fa-buysellads { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-connectdevelop { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-dashcube { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-forumbee { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-leanpub { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-sellsy { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-shirtsinbulk { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-simplybuilt { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-skyatlas { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-diamond { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-diamond:before { - content: "\f3a5"; } - -.fa.fa-intersex:before { - content: "\f224"; } - -.fa.fa-facebook-official { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-facebook-official:before { - content: "\f09a"; } - -.fa.fa-pinterest-p { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-whatsapp { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-hotel:before { - content: "\f236"; } - -.fa.fa-viacoin { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-medium { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-y-combinator { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-yc { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-yc:before { - content: "\f23b"; } - -.fa.fa-optin-monster { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-opencart { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-expeditedssl { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-battery-4:before { - content: "\f240"; } - -.fa.fa-battery:before { - content: "\f240"; } - -.fa.fa-battery-3:before { - content: "\f241"; } - -.fa.fa-battery-2:before { - content: "\f242"; } - -.fa.fa-battery-1:before { - content: "\f243"; } - -.fa.fa-battery-0:before { - content: "\f244"; } - -.fa.fa-object-group { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-object-ungroup { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-sticky-note-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-sticky-note-o:before { - content: "\f249"; } - -.fa.fa-cc-jcb { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cc-diners-club { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-clone { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hourglass-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hourglass-o:before { - content: "\f254"; } - -.fa.fa-hourglass-1:before { - content: "\f251"; } - -.fa.fa-hourglass-2:before { - content: "\f252"; } - -.fa.fa-hourglass-3:before { - content: "\f253"; } - -.fa.fa-hand-rock-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-rock-o:before { - content: "\f255"; } - -.fa.fa-hand-grab-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-grab-o:before { - content: "\f255"; } - -.fa.fa-hand-paper-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-paper-o:before { - content: "\f256"; } - -.fa.fa-hand-stop-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-stop-o:before { - content: "\f256"; } - -.fa.fa-hand-scissors-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-scissors-o:before { - content: "\f257"; } - -.fa.fa-hand-lizard-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-lizard-o:before { - content: "\f258"; } - -.fa.fa-hand-spock-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-spock-o:before { - content: "\f259"; } - -.fa.fa-hand-pointer-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-pointer-o:before { - content: "\f25a"; } - -.fa.fa-hand-peace-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-hand-peace-o:before { - content: "\f25b"; } - -.fa.fa-registered { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-creative-commons { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gg { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gg-circle { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-tripadvisor { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-odnoklassniki { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-odnoklassniki-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-get-pocket { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wikipedia-w { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-safari { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-chrome { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-firefox { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-opera { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-internet-explorer { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-television:before { - content: "\f26c"; } - -.fa.fa-contao { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-500px { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-amazon { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-calendar-plus-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-calendar-plus-o:before { - content: "\f271"; } - -.fa.fa-calendar-minus-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-calendar-minus-o:before { - content: "\f272"; } - -.fa.fa-calendar-times-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-calendar-times-o:before { - content: "\f273"; } - -.fa.fa-calendar-check-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-calendar-check-o:before { - content: "\f274"; } - -.fa.fa-map-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-map-o:before { - content: "\f279"; } - -.fa.fa-commenting:before { - content: "\f4ad"; } - -.fa.fa-commenting-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-commenting-o:before { - content: "\f4ad"; } - -.fa.fa-houzz { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-vimeo { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-vimeo:before { - content: "\f27d"; } - -.fa.fa-black-tie { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-fonticons { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-reddit-alien { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-edge { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-credit-card-alt:before { - content: "\f09d"; } - -.fa.fa-codiepie { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-modx { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-fort-awesome { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-usb { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-product-hunt { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-mixcloud { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-scribd { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pause-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-pause-circle-o:before { - content: "\f28b"; } - -.fa.fa-stop-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-stop-circle-o:before { - content: "\f28d"; } - -.fa.fa-bluetooth { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-bluetooth-b { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-gitlab { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wpbeginner { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wpforms { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-envira { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wheelchair-alt { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wheelchair-alt:before { - content: "\f368"; } - -.fa.fa-question-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-question-circle-o:before { - content: "\f059"; } - -.fa.fa-volume-control-phone:before { - content: "\f2a0"; } - -.fa.fa-asl-interpreting:before { - content: "\f2a3"; } - -.fa.fa-deafness:before { - content: "\f2a4"; } - -.fa.fa-hard-of-hearing:before { - content: "\f2a4"; } - -.fa.fa-glide { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-glide-g { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-signing:before { - content: "\f2a7"; } - -.fa.fa-viadeo { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-viadeo-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-snapchat { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-snapchat-ghost { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-snapchat-square { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-pied-piper { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-first-order { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-yoast { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-themeisle { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus-official { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus-official:before { - content: "\f2b3"; } - -.fa.fa-google-plus-circle { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-google-plus-circle:before { - content: "\f2b3"; } - -.fa.fa-font-awesome { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-fa { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-fa:before { - content: "\f2b4"; } - -.fa.fa-handshake-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-handshake-o:before { - content: "\f2b5"; } - -.fa.fa-envelope-open-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-envelope-open-o:before { - content: "\f2b6"; } - -.fa.fa-linode { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-address-book-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-address-book-o:before { - content: "\f2b9"; } - -.fa.fa-vcard:before { - content: "\f2bb"; } - -.fa.fa-address-card-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-address-card-o:before { - content: "\f2bb"; } - -.fa.fa-vcard-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-vcard-o:before { - content: "\f2bb"; } - -.fa.fa-user-circle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-user-circle-o:before { - content: "\f2bd"; } - -.fa.fa-user-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-user-o:before { - content: "\f007"; } - -.fa.fa-id-badge { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-drivers-license:before { - content: "\f2c2"; } - -.fa.fa-id-card-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-id-card-o:before { - content: "\f2c2"; } - -.fa.fa-drivers-license-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-drivers-license-o:before { - content: "\f2c2"; } - -.fa.fa-quora { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-free-code-camp { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-telegram { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-thermometer-4:before { - content: "\f2c7"; } - -.fa.fa-thermometer:before { - content: "\f2c7"; } - -.fa.fa-thermometer-3:before { - content: "\f2c8"; } - -.fa.fa-thermometer-2:before { - content: "\f2c9"; } - -.fa.fa-thermometer-1:before { - content: "\f2ca"; } - -.fa.fa-thermometer-0:before { - content: "\f2cb"; } - -.fa.fa-bathtub:before { - content: "\f2cd"; } - -.fa.fa-s15:before { - content: "\f2cd"; } - -.fa.fa-window-maximize { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-window-restore { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-times-rectangle:before { - content: "\f410"; } - -.fa.fa-window-close-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-window-close-o:before { - content: "\f410"; } - -.fa.fa-times-rectangle-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-times-rectangle-o:before { - content: "\f410"; } - -.fa.fa-bandcamp { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-grav { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-etsy { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-imdb { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-ravelry { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-eercast { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-eercast:before { - content: "\f2da"; } - -.fa.fa-snowflake-o { - font-family: 'Font Awesome 5 Free'; - font-weight: 400; } - -.fa.fa-snowflake-o:before { - content: "\f2dc"; } - -.fa.fa-superpowers { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-wpexplorer { - font-family: 'Font Awesome 5 Brands'; - font-weight: 400; } - -.fa.fa-cab:before { - content: "\f1ba"; } diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.eot b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.eot deleted file mode 100644 index cba6c6cce8..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.eot and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.svg b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.svg deleted file mode 100644 index b9881a43b7..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.svg +++ /dev/null @@ -1,3717 +0,0 @@ - - - - -Created by FontForge 20201107 at Wed Aug 4 12:25:29 2021 - By Robert Madole -Copyright (c) Font Awesome - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.ttf b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.ttf deleted file mode 100644 index 8d75deddae..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.ttf and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff deleted file mode 100644 index 3375bef091..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff2 b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff2 deleted file mode 100644 index 402f81c0bc..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-brands-400.woff2 and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.eot b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.eot deleted file mode 100644 index a4e598936b..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.eot and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.svg b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.svg deleted file mode 100644 index 463af27c02..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.svg +++ /dev/null @@ -1,801 +0,0 @@ - - - - -Created by FontForge 20201107 at Wed Aug 4 12:25:29 2021 - By Robert Madole -Copyright (c) Font Awesome - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.ttf b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.ttf deleted file mode 100644 index 7157aafbac..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.ttf and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff deleted file mode 100644 index ad077c6bec..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff2 b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff2 deleted file mode 100644 index 56328948b3..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-regular-400.woff2 and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.eot b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.eot deleted file mode 100644 index e99417197e..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.eot and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.svg b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.svg deleted file mode 100644 index 00296e9598..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.svg +++ /dev/null @@ -1,5034 +0,0 @@ - - - - -Created by FontForge 20201107 at Wed Aug 4 12:25:29 2021 - By Robert Madole -Copyright (c) Font Awesome - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.ttf b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.ttf deleted file mode 100644 index 25abf389e2..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.ttf and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff deleted file mode 100644 index 23ee663443..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff2 b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff2 deleted file mode 100644 index 2217164f0c..0000000000 Binary files a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/@fortawesome/fontawesome-free/webfonts/fa-solid-900.woff2 and /dev/null differ diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.css deleted file mode 100644 index ee3c5080a5..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.css +++ /dev/null @@ -1,56 +0,0 @@ -@keyframes spin { - 0% { - transform: translateZ(0) rotate(0deg); - } - - 100% { - transform: translateZ(0) rotate(360deg); - } -} - -.abp-block-area { - position: fixed; - top: 0; - left: 0; - width: 100%; - height: 100%; - z-index: 102; - background-color: #fff; - opacity: .8; - transition: opacity .25s; -} - - .abp-block-area.abp-block-area-disappearing { - opacity: 0; - } - - .abp-block-area.abp-block-area-busy:after { - content: attr(data-text); - display: block; - max-width: 125px; - position: absolute; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); - font-size: 20px; - font-family: sans-serif; - color: #343a40; - text-align: center; - text-transform: uppercase; - } - - .abp-block-area.abp-block-area-busy:before { - content: ""; - display: block; - width: 150px; - height: 150px; - border-radius: 50%; - border-width: 2px; - border-style: solid; - border-color: transparent #228ae6 #228ae6 #228ae6; - position: absolute; - top: calc(50% - 75px); - left: calc(50% - 75px); - will-change: transform; - animation: spin .75s infinite ease-in-out; - } diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.js deleted file mode 100644 index ad1d238448..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/core/abp.js +++ /dev/null @@ -1,823 +0,0 @@ -var abp = abp || {}; -(function () { - - /* Application paths *****************************************/ - - //Current application root path (including virtual directory if exists). - abp.appPath = abp.appPath || '/'; - - abp.pageLoadTime = new Date(); - - //Converts given path to absolute path using abp.appPath variable. - abp.toAbsAppPath = function (path) { - if (path.indexOf('/') == 0) { - path = path.substring(1); - } - - return abp.appPath + path; - }; - - /* LOGGING ***************************************************/ - //Implements Logging API that provides secure & controlled usage of console.log - - abp.log = abp.log || {}; - - abp.log.levels = { - DEBUG: 1, - INFO: 2, - WARN: 3, - ERROR: 4, - FATAL: 5 - }; - - abp.log.level = abp.log.levels.DEBUG; - - abp.log.log = function (logObject, logLevel) { - if (!window.console || !window.console.log) { - return; - } - - if (logLevel != undefined && logLevel < abp.log.level) { - return; - } - - console.log(logObject); - }; - - abp.log.debug = function (logObject) { - abp.log.log("DEBUG: ", abp.log.levels.DEBUG); - abp.log.log(logObject, abp.log.levels.DEBUG); - }; - - abp.log.info = function (logObject) { - abp.log.log("INFO: ", abp.log.levels.INFO); - abp.log.log(logObject, abp.log.levels.INFO); - }; - - abp.log.warn = function (logObject) { - abp.log.log("WARN: ", abp.log.levels.WARN); - abp.log.log(logObject, abp.log.levels.WARN); - }; - - abp.log.error = function (logObject) { - abp.log.log("ERROR: ", abp.log.levels.ERROR); - abp.log.log(logObject, abp.log.levels.ERROR); - }; - - abp.log.fatal = function (logObject) { - abp.log.log("FATAL: ", abp.log.levels.FATAL); - abp.log.log(logObject, abp.log.levels.FATAL); - }; - - /* LOCALIZATION ***********************************************/ - - abp.localization = abp.localization || {}; - abp.localization.internal = abp.localization.internal || {}; - abp.localization.values = abp.localization.values || {}; - abp.localization.resources = abp.localization.resources || {}; - - abp.localization.internal.getResource = function (resourceName) { - var resource = abp.localization.resources[resourceName]; - if (resource) { - return resource; - } - - var legacySource = abp.localization.values[resourceName]; - if (legacySource) { - return { - texts: abp.localization.values[resourceName], - baseResources: [] - }; - } - - abp.log.warn('Could not find localization source: ' + resourceName); - return null; - }; - - abp.localization.internal.localize = function (key, sourceName) { - var resource = abp.localization.internal.getResource(sourceName); - if (!resource){ - return { - value: key, - found: false - }; - } - - var value = resource.texts[key]; - if (value === undefined) { - for (var i = 0; i < resource.baseResources.length; i++){ - var basedArguments = Array.prototype.slice.call(arguments, 0); - basedArguments[1] = resource.baseResources[i]; - - var result = abp.localization.internal.localize.apply(this, basedArguments); - if (result.found){ - return result; - } - } - - return { - value: key, - found: false - }; - } - - var copiedArguments = Array.prototype.slice.call(arguments, 0); - copiedArguments.splice(1, 1); - copiedArguments[0] = value; - - return { - value: abp.utils.formatString.apply(this, copiedArguments), - found: true - }; - }; - - abp.localization.localize = function (key, sourceName) { - if (sourceName === '_') { //A convention to suppress the localization - return key; - } - - if (sourceName) { - return abp.localization.internal.localize.apply(this, arguments).value; - } - - if (!abp.localization.defaultResourceName) { - abp.log.warn('Localization source name is not specified and the defaultResourceName was not defined!'); - return key; - } - - var copiedArguments = Array.prototype.slice.call(arguments, 0); - copiedArguments.splice(1, 1, abp.localization.defaultResourceName); - - return abp.localization.internal.localize.apply(this, copiedArguments).value; - }; - - abp.localization.isLocalized = function (key, sourceName) { - if (sourceName === '_') { //A convention to suppress the localization - return true; - } - - sourceName = sourceName || abp.localization.defaultResourceName; - if (!sourceName) { - return false; - } - - return abp.localization.internal.localize(key, sourceName).found; - }; - - abp.localization.getResource = function (name) { - return function () { - var copiedArguments = Array.prototype.slice.call(arguments, 0); - copiedArguments.splice(1, 0, name); - return abp.localization.localize.apply(this, copiedArguments); - }; - }; - - abp.localization.defaultResourceName = undefined; - abp.localization.currentCulture = { - cultureName: undefined - }; - - var getMapValue = function (packageMaps, packageName, language) { - language = language || abp.localization.currentCulture.name; - if (!packageMaps || !packageName || !language) { - return language; - } - - var packageMap = packageMaps[packageName]; - if (!packageMap) { - return language; - } - - for (var i = 0; i < packageMap.length; i++) { - var map = packageMap[i]; - if (map.name === language){ - return map.value; - } - } - - return language; - }; - - abp.localization.getLanguagesMap = function (packageName, language) { - return getMapValue(abp.localization.languagesMap, packageName, language); - }; - - abp.localization.getLanguageFilesMap = function (packageName, language) { - return getMapValue(abp.localization.languageFilesMap, packageName, language); - }; - - /* AUTHORIZATION **********************************************/ - - abp.auth = abp.auth || {}; - - abp.auth.grantedPolicies = abp.auth.grantedPolicies || {}; - - abp.auth.isGranted = function (policyName) { - return abp.auth.grantedPolicies[policyName] != undefined; - }; - - abp.auth.isAnyGranted = function () { - if (!arguments || arguments.length <= 0) { - return true; - } - - for (var i = 0; i < arguments.length; i++) { - if (abp.auth.isGranted(arguments[i])) { - return true; - } - } - - return false; - }; - - abp.auth.areAllGranted = function () { - if (!arguments || arguments.length <= 0) { - return true; - } - - for (var i = 0; i < arguments.length; i++) { - if (!abp.auth.isGranted(arguments[i])) { - return false; - } - } - - return true; - }; - - abp.auth.tokenCookieName = 'Abp.AuthToken'; - - abp.auth.setToken = function (authToken, expireDate) { - abp.utils.setCookieValue(abp.auth.tokenCookieName, authToken, expireDate, abp.appPath, abp.domain); - }; - - abp.auth.getToken = function () { - return abp.utils.getCookieValue(abp.auth.tokenCookieName); - } - - abp.auth.clearToken = function () { - abp.auth.setToken(); - } - - /* SETTINGS *************************************************/ - - abp.setting = abp.setting || {}; - - abp.setting.values = abp.setting.values || {}; - - abp.setting.get = function (name) { - return abp.setting.values[name]; - }; - - abp.setting.getBoolean = function (name) { - var value = abp.setting.get(name); - return value == 'true' || value == 'True'; - }; - - abp.setting.getInt = function (name) { - return parseInt(abp.setting.values[name]); - }; - - /* NOTIFICATION *********************************************/ - //Defines Notification API, not implements it - - abp.notify = abp.notify || {}; - - abp.notify.success = function (message, title, options) { - abp.log.warn('abp.notify.success is not implemented!'); - }; - - abp.notify.info = function (message, title, options) { - abp.log.warn('abp.notify.info is not implemented!'); - }; - - abp.notify.warn = function (message, title, options) { - abp.log.warn('abp.notify.warn is not implemented!'); - }; - - abp.notify.error = function (message, title, options) { - abp.log.warn('abp.notify.error is not implemented!'); - }; - - /* MESSAGE **************************************************/ - //Defines Message API, not implements it - - abp.message = abp.message || {}; - - abp.message._showMessage = function (message, title) { - alert((title || '') + ' ' + message); - }; - - abp.message.info = function (message, title) { - abp.log.warn('abp.message.info is not implemented!'); - return abp.message._showMessage(message, title); - }; - - abp.message.success = function (message, title) { - abp.log.warn('abp.message.success is not implemented!'); - return abp.message._showMessage(message, title); - }; - - abp.message.warn = function (message, title) { - abp.log.warn('abp.message.warn is not implemented!'); - return abp.message._showMessage(message, title); - }; - - abp.message.error = function (message, title) { - abp.log.warn('abp.message.error is not implemented!'); - return abp.message._showMessage(message, title); - }; - - abp.message.confirm = function (message, titleOrCallback, callback) { - abp.log.warn('abp.message.confirm is not properly implemented!'); - - if (titleOrCallback && !(typeof titleOrCallback == 'string')) { - callback = titleOrCallback; - } - - var result = confirm(message); - callback && callback(result); - }; - - /* UI *******************************************************/ - - abp.ui = abp.ui || {}; - - /* UI BLOCK */ - //Defines UI Block API and implements basically - - var $abpBlockArea = document.createElement('div'); - $abpBlockArea.classList.add('abp-block-area'); - - /* opts: { //Can be an object with options or a string for query a selector - * elm: a query selector (optional - default: document.body) - * busy: boolean (optional - default: false) - * promise: A promise with always or finally handler (optional - auto unblocks the ui if provided) - * } - */ - abp.ui.block = function (opts) { - if (!opts) { - opts = {}; - } else if (typeof opts == 'string') { - opts = { - elm: opts - }; - } - - var $elm = document.querySelector(opts.elm) || document.body; - - if (opts.busy) { - $abpBlockArea.classList.add('abp-block-area-busy'); - } else { - $abpBlockArea.classList.remove('abp-block-area-busy'); - } - - if (document.querySelector(opts.elm)) { - $abpBlockArea.style.position = 'absolute'; - } else { - $abpBlockArea.style.position = 'fixed'; - } - - $elm.appendChild($abpBlockArea); - - if (opts.promise) { - if (opts.promise.always) { //jQuery.Deferred style - opts.promise.always(function () { - abp.ui.unblock({ - $elm: opts.elm - }); - }); - } else if (opts.promise['finally']) { //Q style - opts.promise['finally'](function () { - abp.ui.unblock({ - $elm: opts.elm - }); - }); - } - } - }; - - /* opts: { - * - * } - */ - abp.ui.unblock = function (opts) { - var element = document.querySelector('.abp-block-area'); - if (element) { - element.classList.add('abp-block-area-disappearing'); - setTimeout(function () { - if (element) { - element.classList.remove('abp-block-area-disappearing'); - if (element.parentElement) { - element.parentElement.removeChild(element); - } - } - }, 250); - } - }; - - /* UI BUSY */ - //Defines UI Busy API, not implements it - - abp.ui.setBusy = function (opts) { - if (!opts) { - opts = { - busy: true - }; - } else if (typeof opts == 'string') { - opts = { - elm: opts, - busy: true - }; - } - - abp.ui.block(opts); - }; - - abp.ui.clearBusy = function (opts) { - abp.ui.unblock(opts); - }; - - /* SIMPLE EVENT BUS *****************************************/ - - abp.event = (function () { - - var _callbacks = {}; - - var on = function (eventName, callback) { - if (!_callbacks[eventName]) { - _callbacks[eventName] = []; - } - - _callbacks[eventName].push(callback); - }; - - var off = function (eventName, callback) { - var callbacks = _callbacks[eventName]; - if (!callbacks) { - return; - } - - var index = -1; - for (var i = 0; i < callbacks.length; i++) { - if (callbacks[i] === callback) { - index = i; - break; - } - } - - if (index < 0) { - return; - } - - _callbacks[eventName].splice(index, 1); - }; - - var trigger = function (eventName) { - var callbacks = _callbacks[eventName]; - if (!callbacks || !callbacks.length) { - return; - } - - var args = Array.prototype.slice.call(arguments, 1); - for (var i = 0; i < callbacks.length; i++) { - callbacks[i].apply(this, args); - } - }; - - // Public interface /////////////////////////////////////////////////// - - return { - on: on, - off: off, - trigger: trigger - }; - })(); - - - /* UTILS ***************************************************/ - - abp.utils = abp.utils || {}; - - /* Creates a name namespace. - * Example: - * var taskService = abp.utils.createNamespace(abp, 'services.task'); - * taskService will be equal to abp.services.task - * first argument (root) must be defined first - ************************************************************/ - abp.utils.createNamespace = function (root, ns) { - var parts = ns.split('.'); - for (var i = 0; i < parts.length; i++) { - if (typeof root[parts[i]] == 'undefined') { - root[parts[i]] = {}; - } - - root = root[parts[i]]; - } - - return root; - }; - - /* Find and replaces a string (search) to another string (replacement) in - * given string (str). - * Example: - * abp.utils.replaceAll('This is a test string', 'is', 'X') = 'ThX X a test string' - ************************************************************/ - abp.utils.replaceAll = function (str, search, replacement) { - var fix = search.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); - return str.replace(new RegExp(fix, 'g'), replacement); - }; - - /* Formats a string just like string.format in C#. - * Example: - * abp.utils.formatString('Hello {0}','Tuana') = 'Hello Tuana' - ************************************************************/ - abp.utils.formatString = function () { - if (arguments.length < 1) { - return null; - } - - var str = arguments[0]; - - for (var i = 1; i < arguments.length; i++) { - var placeHolder = '{' + (i - 1) + '}'; - str = abp.utils.replaceAll(str, placeHolder, arguments[i]); - } - - return str; - }; - - abp.utils.toPascalCase = function (str) { - if (!str || !str.length) { - return str; - } - - if (str.length === 1) { - return str.charAt(0).toUpperCase(); - } - - return str.charAt(0).toUpperCase() + str.substr(1); - } - - abp.utils.toCamelCase = function (str) { - if (!str || !str.length) { - return str; - } - - if (str.length === 1) { - return str.charAt(0).toLowerCase(); - } - - return str.charAt(0).toLowerCase() + str.substr(1); - } - - abp.utils.truncateString = function (str, maxLength) { - if (!str || !str.length || str.length <= maxLength) { - return str; - } - - return str.substr(0, maxLength); - }; - - abp.utils.truncateStringWithPostfix = function (str, maxLength, postfix) { - postfix = postfix || '...'; - - if (!str || !str.length || str.length <= maxLength) { - return str; - } - - if (maxLength <= postfix.length) { - return postfix.substr(0, maxLength); - } - - return str.substr(0, maxLength - postfix.length) + postfix; - }; - - abp.utils.isFunction = function (obj) { - return !!(obj && obj.constructor && obj.call && obj.apply); - }; - - /** - * parameterInfos should be an array of { name, value } objects - * where name is query string parameter name and value is it's value. - * includeQuestionMark is true by default. - */ - abp.utils.buildQueryString = function (parameterInfos, includeQuestionMark) { - if (includeQuestionMark === undefined) { - includeQuestionMark = true; - } - - var qs = ''; - - function addSeperator() { - if (!qs.length) { - if (includeQuestionMark) { - qs = qs + '?'; - } - } else { - qs = qs + '&'; - } - } - - for (var i = 0; i < parameterInfos.length; ++i) { - var parameterInfo = parameterInfos[i]; - if (parameterInfo.value === undefined) { - continue; - } - - if (parameterInfo.value === null) { - parameterInfo.value = ''; - } - - addSeperator(); - - if (parameterInfo.value.toJSON && typeof parameterInfo.value.toJSON === "function") { - qs = qs + parameterInfo.name + '=' + encodeURIComponent(parameterInfo.value.toJSON()); - } else if (Array.isArray(parameterInfo.value) && parameterInfo.value.length) { - for (var j = 0; j < parameterInfo.value.length; j++) { - if (j > 0) { - addSeperator(); - } - - qs = qs + parameterInfo.name + '[' + j + ']=' + encodeURIComponent(parameterInfo.value[j]); - } - } else { - qs = qs + parameterInfo.name + '=' + encodeURIComponent(parameterInfo.value); - } - } - - return qs; - } - - /** - * Sets a cookie value for given key. - * This is a simple implementation created to be used by ABP. - * Please use a complete cookie library if you need. - * @param {string} key - * @param {string} value - * @param {Date} expireDate (optional). If not specified the cookie will expire at the end of session. - * @param {string} path (optional) - */ - abp.utils.setCookieValue = function (key, value, expireDate, path) { - var cookieValue = encodeURIComponent(key) + '='; - - if (value) { - cookieValue = cookieValue + encodeURIComponent(value); - } - - if (expireDate) { - cookieValue = cookieValue + "; expires=" + expireDate.toUTCString(); - } - - if (path) { - cookieValue = cookieValue + "; path=" + path; - } - - document.cookie = cookieValue; - }; - - /** - * Gets a cookie with given key. - * This is a simple implementation created to be used by ABP. - * Please use a complete cookie library if you need. - * @param {string} key - * @returns {string} Cookie value or null - */ - abp.utils.getCookieValue = function (key) { - var equalities = document.cookie.split('; '); - for (var i = 0; i < equalities.length; i++) { - if (!equalities[i]) { - continue; - } - - var splitted = equalities[i].split('='); - if (splitted.length != 2) { - continue; - } - - if (decodeURIComponent(splitted[0]) === key) { - return decodeURIComponent(splitted[1] || ''); - } - } - - return null; - }; - - /** - * Deletes cookie for given key. - * This is a simple implementation created to be used by ABP. - * Please use a complete cookie library if you need. - * @param {string} key - * @param {string} path (optional) - */ - abp.utils.deleteCookie = function (key, path) { - var cookieValue = encodeURIComponent(key) + '='; - - cookieValue = cookieValue + "; expires=" + (new Date(new Date().getTime() - 86400000)).toUTCString(); - - if (path) { - cookieValue = cookieValue + "; path=" + path; - } - - document.cookie = cookieValue; - } - - /** - * Escape HTML to help prevent XSS attacks. - */ - abp.utils.htmlEscape = function (html) { - return typeof html === 'string' ? html.replace(/&/g, '&').replace(//g, '>').replace(/"/g, '"') : html; - } - - /* SECURITY ***************************************/ - abp.security = abp.security || {}; - abp.security.antiForgery = abp.security.antiForgery || {}; - - abp.security.antiForgery.tokenCookieName = 'XSRF-TOKEN'; - abp.security.antiForgery.tokenHeaderName = 'RequestVerificationToken'; - - abp.security.antiForgery.getToken = function () { - return abp.utils.getCookieValue(abp.security.antiForgery.tokenCookieName); - }; - - /* CLOCK *****************************************/ - abp.clock = abp.clock || {}; - - abp.clock.kind = 'Unspecified'; - - abp.clock.supportsMultipleTimezone = function () { - return abp.clock.kind === 'Utc'; - }; - - var toLocal = function (date) { - return new Date( - date.getFullYear(), - date.getMonth(), - date.getDate(), - date.getHours(), - date.getMinutes(), - date.getSeconds(), - date.getMilliseconds() - ); - }; - - var toUtc = function (date) { - return Date.UTC( - date.getUTCFullYear(), - date.getUTCMonth(), - date.getUTCDate(), - date.getUTCHours(), - date.getUTCMinutes(), - date.getUTCSeconds(), - date.getUTCMilliseconds() - ); - }; - - abp.clock.now = function () { - if (abp.clock.kind === 'Utc') { - return toUtc(new Date()); - } - return new Date(); - }; - - abp.clock.normalize = function (date) { - var kind = abp.clock.kind; - - if (kind === 'Unspecified') { - return date; - } - - if (kind === 'Local') { - return toLocal(date); - } - - if (kind === 'Utc') { - return toUtc(date); - } - }; - - /* FEATURES *************************************************/ - - abp.features = abp.features || {}; - - abp.features.values = abp.features.values || {}; - - abp.features.isEnabled = function(name){ - var value = abp.features.get(name); - return value == 'true' || value == 'True'; - } - - abp.features.get = function (name) { - return abp.features.values[name]; - }; - - /* GLOBAL FEATURES *************************************************/ - - abp.globalFeatures = abp.globalFeatures || {}; - - abp.globalFeatures.enabledFeatures = abp.globalFeatures.enabledFeatures || []; - - abp.globalFeatures.isEnabled = function(name){ - return abp.globalFeatures.enabledFeatures.indexOf(name) != -1; - } - -})(); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/jquery/abp.jquery.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/jquery/abp.jquery.js deleted file mode 100644 index 9137fcc989..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/jquery/abp.jquery.js +++ /dev/null @@ -1,411 +0,0 @@ -var abp = abp || {}; -(function($) { - - if (!$) { - throw "abp/jquery library requires the jquery library included to the page!"; - } - - // ABP CORE OVERRIDES ///////////////////////////////////////////////////// - - abp.message._showMessage = function (message, title) { - alert((title || '') + ' ' + message); - - return $.Deferred(function ($dfd) { - $dfd.resolve(); - }); - }; - - abp.message.confirm = function (message, titleOrCallback, callback) { - if (titleOrCallback && !(typeof titleOrCallback == 'string')) { - callback = titleOrCallback; - } - - var result = confirm(message); - callback && callback(result); - - return $.Deferred(function ($dfd) { - $dfd.resolve(result); - }); - }; - - abp.utils.isFunction = function (obj) { - return $.isFunction(obj); - }; - - // JQUERY EXTENSIONS ////////////////////////////////////////////////////// - - $.fn.findWithSelf = function (selector) { - return this.filter(selector).add(this.find(selector)); - }; - - // DOM //////////////////////////////////////////////////////////////////// - - abp.dom = abp.dom || {}; - - abp.dom.onNodeAdded = function (callback) { - abp.event.on('abp.dom.nodeAdded', callback); - }; - - abp.dom.onNodeRemoved = function (callback) { - abp.event.on('abp.dom.nodeRemoved', callback); - }; - - var mutationObserverCallback = function (mutationsList) { - for (var i = 0; i < mutationsList.length; i++) { - var mutation = mutationsList[i]; - if (mutation.type === 'childList') { - if (mutation.addedNodes && mutation.removedNodes.length) { - for (var k = 0; k < mutation.removedNodes.length; k++) { - abp.event.trigger( - 'abp.dom.nodeRemoved', - { - $el: $(mutation.removedNodes[k]) - } - ); - } - } - - if (mutation.addedNodes && mutation.addedNodes.length) { - for (var j = 0; j < mutation.addedNodes.length; j++) { - abp.event.trigger( - 'abp.dom.nodeAdded', - { - $el: $(mutation.addedNodes[j]) - } - ); - } - } - } - } - }; - - $(function(){ - new MutationObserver(mutationObserverCallback).observe( - $('body')[0], - { - subtree: true, - childList: true - } - ); - }); - - // AJAX /////////////////////////////////////////////////////////////////// - - abp.ajax = function (userOptions) { - userOptions = userOptions || {}; - - var options = $.extend(true, {}, abp.ajax.defaultOpts, userOptions); - - options.success = undefined; - options.error = undefined; - - var xhr = null; - var promise = $.Deferred(function ($dfd) { - xhr = $.ajax(options) - .done(function (data, textStatus, jqXHR) { - $dfd.resolve(data); - userOptions.success && userOptions.success(data); - }).fail(function (jqXHR) { - if(jqXHR.statusText === 'abort') { - //ajax request is abort, ignore error handle. - return; - } - if (jqXHR.getResponseHeader('_AbpErrorFormat') === 'true') { - abp.ajax.handleAbpErrorResponse(jqXHR, userOptions, $dfd); - } else { - abp.ajax.handleNonAbpErrorResponse(jqXHR, userOptions, $dfd); - } - }); - }).promise(); - - promise['jqXHR'] = xhr; - - return promise; - }; - - $.extend(abp.ajax, { - defaultOpts: { - dataType: 'json', - type: 'POST', - contentType: 'application/json', - headers: { - 'X-Requested-With': 'XMLHttpRequest' - } - }, - - defaultError: { - message: 'An error has occurred!', - details: 'Error detail not sent by server.' - }, - - defaultError401: { - message: 'You are not authenticated!', - details: 'You should be authenticated (sign in) in order to perform this operation.' - }, - - defaultError403: { - message: 'You are not authorized!', - details: 'You are not allowed to perform this operation.' - }, - - defaultError404: { - message: 'Resource not found!', - details: 'The resource requested could not found on the server.' - }, - - logError: function (error) { - abp.log.error(error); - }, - - showError: function (error) { - if (error.details) { - return abp.message.error(error.details, error.message); - } else { - return abp.message.error(error.message || abp.ajax.defaultError.message); - } - }, - - handleTargetUrl: function (targetUrl) { - if (!targetUrl) { - location.href = abp.appPath; - } else { - location.href = targetUrl; - } - }, - - handleErrorStatusCode: function (status) { - switch (status) { - case 401: - abp.ajax.handleUnAuthorizedRequest( - abp.ajax.showError(abp.ajax.defaultError401), - abp.appPath - ); - break; - case 403: - abp.ajax.showError(abp.ajax.defaultError403); - break; - case 404: - abp.ajax.showError(abp.ajax.defaultError404); - break; - default: - abp.ajax.showError(abp.ajax.defaultError); - break; - } - }, - - handleNonAbpErrorResponse: function (jqXHR, userOptions, $dfd) { - if (userOptions.abpHandleError !== false) { - abp.ajax.handleErrorStatusCode(jqXHR.status); - } - - $dfd.reject.apply(this, arguments); - userOptions.error && userOptions.error.apply(this, arguments); - }, - - handleAbpErrorResponse: function (jqXHR, userOptions, $dfd) { - var messagePromise = null; - - var responseJSON = jqXHR.responseJSON ? jqXHR.responseJSON : JSON.parse(jqXHR.responseText); - - if (userOptions.abpHandleError !== false) { - messagePromise = abp.ajax.showError(responseJSON.error); - } - - abp.ajax.logError(responseJSON.error); - - $dfd && $dfd.reject(responseJSON.error, jqXHR); - userOptions.error && userOptions.error(responseJSON.error, jqXHR); - - if (jqXHR.status === 401 && userOptions.abpHandleError !== false) { - abp.ajax.handleUnAuthorizedRequest(messagePromise); - } - }, - - handleUnAuthorizedRequest: function (messagePromise, targetUrl) { - if (messagePromise) { - messagePromise.done(function () { - abp.ajax.handleTargetUrl(targetUrl); - }); - } else { - abp.ajax.handleTargetUrl(targetUrl); - } - }, - - blockUI: function (options) { - if (options.blockUI) { - if (options.blockUI === true) { //block whole page - abp.ui.setBusy(); - } else { //block an element - abp.ui.setBusy(options.blockUI); - } - } - }, - - unblockUI: function (options) { - if (options.blockUI) { - if (options.blockUI === true) { //unblock whole page - abp.ui.clearBusy(); - } else { //unblock an element - abp.ui.clearBusy(options.blockUI); - } - } - }, - - ajaxSendHandler: function (event, request, settings) { - var token = abp.security.antiForgery.getToken(); - if (!token) { - return; - } - - if (!settings.headers || settings.headers[abp.security.antiForgery.tokenHeaderName] === undefined) { - request.setRequestHeader(abp.security.antiForgery.tokenHeaderName, token); - } - } - }); - - $(document).ajaxSend(function (event, request, settings) { - return abp.ajax.ajaxSendHandler(event, request, settings); - }); - - abp.event.on('abp.configurationInitialized', function () { - var l = abp.localization.getResource('AbpUi'); - - abp.ajax.defaultError.message = l('DefaultErrorMessage'); - abp.ajax.defaultError.details = l('DefaultErrorMessageDetail'); - abp.ajax.defaultError401.message = l('DefaultErrorMessage401'); - abp.ajax.defaultError401.details = l('DefaultErrorMessage401Detail'); - abp.ajax.defaultError403.message = l('DefaultErrorMessage403'); - abp.ajax.defaultError403.details = l('DefaultErrorMessage403Detail'); - abp.ajax.defaultError404.message = l('DefaultErrorMessage404'); - abp.ajax.defaultError404.details = l('DefaultErrorMessage404Detail'); - }); - - // RESOURCE LOADER //////////////////////////////////////////////////////// - - /* UrlStates enum */ - var UrlStates = { - LOADING: 'LOADING', - LOADED: 'LOADED', - FAILED: 'FAILED' - }; - - /* UrlInfo class */ - function UrlInfo(url) { - this.url = url; - this.state = UrlStates.LOADING; - this.loadCallbacks = []; - this.failCallbacks = []; - } - - UrlInfo.prototype.succeed = function () { - this.state = UrlStates.LOADED; - for (var i = 0; i < this.loadCallbacks.length; i++) { - this.loadCallbacks[i](); - } - }; - - UrlInfo.prototype.failed = function () { - this.state = UrlStates.FAILED; - for (var i = 0; i < this.failCallbacks.length; i++) { - this.failCallbacks[i](); - } - }; - - UrlInfo.prototype.handleCallbacks = function (loadCallback, failCallback) { - switch (this.state) { - case UrlStates.LOADED: - loadCallback && loadCallback(); - break; - case UrlStates.FAILED: - failCallback && failCallback(); - break; - case UrlStates.LOADING: - this.addCallbacks(loadCallback, failCallback); - break; - } - }; - - UrlInfo.prototype.addCallbacks = function (loadCallback, failCallback) { - loadCallback && this.loadCallbacks.push(loadCallback); - failCallback && this.failCallbacks.push(failCallback); - }; - - /* ResourceLoader API */ - - abp.ResourceLoader = (function () { - - var _urlInfos = {}; - - function getCacheKey(url) { - return url; - } - - function appendTimeToUrl(url) { - - if (url.indexOf('?') < 0) { - url += '?'; - } else { - url += '&'; - } - - url += '_=' + new Date().getTime(); - - return url; - } - - var _loadFromUrl = function (url, loadCallback, failCallback, serverLoader) { - - var cacheKey = getCacheKey(url); - - var urlInfo = _urlInfos[cacheKey]; - - if (urlInfo) { - urlInfo.handleCallbacks(loadCallback, failCallback); - return; - } - - _urlInfos[cacheKey] = urlInfo = new UrlInfo(url); - urlInfo.addCallbacks(loadCallback, failCallback); - - serverLoader(urlInfo); - }; - - var _loadScript = function (url, loadCallback, failCallback) { - var nonce = document.body.nonce || document.body.getAttribute('nonce'); - _loadFromUrl(url, loadCallback, failCallback, function (urlInfo) { - $.get({ - url: url, - dataType: 'text' - }) - .done(function (script) { - if(nonce){ - $.globalEval(script, { nonce: nonce}); - }else{ - $.globalEval(script); - } - urlInfo.succeed(); - }) - .fail(function () { - urlInfo.failed(); - }); - }); - }; - - var _loadStyle = function (url) { - _loadFromUrl(url, undefined, undefined, function (urlInfo) { - - $('', { - rel: 'stylesheet', - type: 'text/css', - href: appendTimeToUrl(url) - }).appendTo('head'); - }); - }; - - return { - loadScript: _loadScript, - loadStyle: _loadStyle - } - })(); - -})(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/luxon/abp.luxon.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/luxon/abp.luxon.js deleted file mode 100644 index fcd9b44246..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/luxon/abp.luxon.js +++ /dev/null @@ -1,46 +0,0 @@ -var abp = abp || {}; -(function () { - - if (!luxon) { - throw "abp/luxon library requires the luxon library included to the page!"; - } - - /* TIMING *************************************************/ - - abp.timing = abp.timing || {}; - - var setObjectValue = function (obj, property, value) { - if (typeof property === "string") { - property = property.split('.'); - } - - if (property.length > 1) { - var p = property.shift(); - setObjectValue(obj[p], property, value); - } else { - obj[property[0]] = value; - } - } - - var getObjectValue = function (obj, property) { - return property.split('.').reduce((a, v) => a[v], obj) - } - - abp.timing.convertFieldsToIsoDate = function (form, fields) { - for (var field of fields) { - var dateTime = luxon.DateTime - .fromFormat( - getObjectValue(form, field), - abp.localization.currentCulture.dateTimeFormat.shortDatePattern, - {locale: abp.localization.currentCulture.cultureName} - ); - - if (!dateTime.invalid) { - setObjectValue(form, field, dateTime.toFormat("yyyy-MM-dd HH:mm:ss")) - } - } - - return form; - } - -})(jQuery); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js deleted file mode 100644 index 359d2f7247..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js +++ /dev/null @@ -1,694 +0,0 @@ -(function (global, factory) { - typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('just-compare')) : - typeof define === 'function' && define.amd ? define('@abp/utils', ['exports', 'just-compare'], factory) : - (global = global || self, factory((global.abp = global.abp || {}, global.abp.utils = global.abp.utils || {}, global.abp.utils.common = {}), global.compare)); -}(this, (function (exports, compare) { 'use strict'; - - compare = compare && Object.prototype.hasOwnProperty.call(compare, 'default') ? compare['default'] : compare; - - /*! ***************************************************************************** - Copyright (c) Microsoft Corporation. - - Permission to use, copy, modify, and/or distribute this software for any - purpose with or without fee is hereby granted. - - THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH - REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY - AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM - LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR - OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR - PERFORMANCE OF THIS SOFTWARE. - ***************************************************************************** */ - /* global Reflect, Promise */ - var extendStatics = function (d, b) { - extendStatics = Object.setPrototypeOf || - ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || - function (d, b) { for (var p in b) - if (b.hasOwnProperty(p)) - d[p] = b[p]; }; - return extendStatics(d, b); - }; - function __extends(d, b) { - extendStatics(d, b); - function __() { this.constructor = d; } - d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); - } - var __assign = function () { - __assign = Object.assign || function __assign(t) { - for (var s, i = 1, n = arguments.length; i < n; i++) { - s = arguments[i]; - for (var p in s) - if (Object.prototype.hasOwnProperty.call(s, p)) - t[p] = s[p]; - } - return t; - }; - return __assign.apply(this, arguments); - }; - function __rest(s, e) { - var t = {}; - for (var p in s) - if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) - t[p] = s[p]; - if (s != null && typeof Object.getOwnPropertySymbols === "function") - for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { - if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) - t[p[i]] = s[p[i]]; - } - return t; - } - function __decorate(decorators, target, key, desc) { - var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d; - if (typeof Reflect === "object" && typeof Reflect.decorate === "function") - r = Reflect.decorate(decorators, target, key, desc); - else - for (var i = decorators.length - 1; i >= 0; i--) - if (d = decorators[i]) - r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; - return c > 3 && r && Object.defineProperty(target, key, r), r; - } - function __param(paramIndex, decorator) { - return function (target, key) { decorator(target, key, paramIndex); }; - } - function __metadata(metadataKey, metadataValue) { - if (typeof Reflect === "object" && typeof Reflect.metadata === "function") - return Reflect.metadata(metadataKey, metadataValue); - } - function __awaiter(thisArg, _arguments, P, generator) { - function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } - return new (P || (P = Promise))(function (resolve, reject) { - function fulfilled(value) { try { - step(generator.next(value)); - } - catch (e) { - reject(e); - } } - function rejected(value) { try { - step(generator["throw"](value)); - } - catch (e) { - reject(e); - } } - function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } - step((generator = generator.apply(thisArg, _arguments || [])).next()); - }); - } - function __generator(thisArg, body) { - var _ = { label: 0, sent: function () { if (t[0] & 1) - throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g; - return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function () { return this; }), g; - function verb(n) { return function (v) { return step([n, v]); }; } - function step(op) { - if (f) - throw new TypeError("Generator is already executing."); - while (_) - try { - if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) - return t; - if (y = 0, t) - op = [op[0] & 2, t.value]; - switch (op[0]) { - case 0: - case 1: - t = op; - break; - case 4: - _.label++; - return { value: op[1], done: false }; - case 5: - _.label++; - y = op[1]; - op = [0]; - continue; - case 7: - op = _.ops.pop(); - _.trys.pop(); - continue; - default: - if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { - _ = 0; - continue; - } - if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { - _.label = op[1]; - break; - } - if (op[0] === 6 && _.label < t[1]) { - _.label = t[1]; - t = op; - break; - } - if (t && _.label < t[2]) { - _.label = t[2]; - _.ops.push(op); - break; - } - if (t[2]) - _.ops.pop(); - _.trys.pop(); - continue; - } - op = body.call(thisArg, _); - } - catch (e) { - op = [6, e]; - y = 0; - } - finally { - f = t = 0; - } - if (op[0] & 5) - throw op[1]; - return { value: op[0] ? op[1] : void 0, done: true }; - } - } - var __createBinding = Object.create ? (function (o, m, k, k2) { - if (k2 === undefined) - k2 = k; - Object.defineProperty(o, k2, { enumerable: true, get: function () { return m[k]; } }); - }) : (function (o, m, k, k2) { - if (k2 === undefined) - k2 = k; - o[k2] = m[k]; - }); - function __exportStar(m, exports) { - for (var p in m) - if (p !== "default" && !exports.hasOwnProperty(p)) - __createBinding(exports, m, p); - } - function __values(o) { - var s = typeof Symbol === "function" && Symbol.iterator, m = s && o[s], i = 0; - if (m) - return m.call(o); - if (o && typeof o.length === "number") - return { - next: function () { - if (o && i >= o.length) - o = void 0; - return { value: o && o[i++], done: !o }; - } - }; - throw new TypeError(s ? "Object is not iterable." : "Symbol.iterator is not defined."); - } - function __read(o, n) { - var m = typeof Symbol === "function" && o[Symbol.iterator]; - if (!m) - return o; - var i = m.call(o), r, ar = [], e; - try { - while ((n === void 0 || n-- > 0) && !(r = i.next()).done) - ar.push(r.value); - } - catch (error) { - e = { error: error }; - } - finally { - try { - if (r && !r.done && (m = i["return"])) - m.call(i); - } - finally { - if (e) - throw e.error; - } - } - return ar; - } - function __spread() { - for (var ar = [], i = 0; i < arguments.length; i++) - ar = ar.concat(__read(arguments[i])); - return ar; - } - function __spreadArrays() { - for (var s = 0, i = 0, il = arguments.length; i < il; i++) - s += arguments[i].length; - for (var r = Array(s), k = 0, i = 0; i < il; i++) - for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++) - r[k] = a[j]; - return r; - } - ; - function __await(v) { - return this instanceof __await ? (this.v = v, this) : new __await(v); - } - function __asyncGenerator(thisArg, _arguments, generator) { - if (!Symbol.asyncIterator) - throw new TypeError("Symbol.asyncIterator is not defined."); - var g = generator.apply(thisArg, _arguments || []), i, q = []; - return i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i; - function verb(n) { if (g[n]) - i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; } - function resume(n, v) { try { - step(g[n](v)); - } - catch (e) { - settle(q[0][3], e); - } } - function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); } - function fulfill(value) { resume("next", value); } - function reject(value) { resume("throw", value); } - function settle(f, v) { if (f(v), q.shift(), q.length) - resume(q[0][0], q[0][1]); } - } - function __asyncDelegator(o) { - var i, p; - return i = {}, verb("next"), verb("throw", function (e) { throw e; }), verb("return"), i[Symbol.iterator] = function () { return this; }, i; - function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === "return" } : f ? f(v) : v; } : f; } - } - function __asyncValues(o) { - if (!Symbol.asyncIterator) - throw new TypeError("Symbol.asyncIterator is not defined."); - var m = o[Symbol.asyncIterator], i; - return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i); - function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; } - function settle(resolve, reject, d, v) { Promise.resolve(v).then(function (v) { resolve({ value: v, done: d }); }, reject); } - } - function __makeTemplateObject(cooked, raw) { - if (Object.defineProperty) { - Object.defineProperty(cooked, "raw", { value: raw }); - } - else { - cooked.raw = raw; - } - return cooked; - } - ; - var __setModuleDefault = Object.create ? (function (o, v) { - Object.defineProperty(o, "default", { enumerable: true, value: v }); - }) : function (o, v) { - o["default"] = v; - }; - function __importStar(mod) { - if (mod && mod.__esModule) - return mod; - var result = {}; - if (mod != null) - for (var k in mod) - if (Object.hasOwnProperty.call(mod, k)) - __createBinding(result, mod, k); - __setModuleDefault(result, mod); - return result; - } - function __importDefault(mod) { - return (mod && mod.__esModule) ? mod : { default: mod }; - } - function __classPrivateFieldGet(receiver, privateMap) { - if (!privateMap.has(receiver)) { - throw new TypeError("attempted to get private field on non-instance"); - } - return privateMap.get(receiver); - } - function __classPrivateFieldSet(receiver, privateMap, value) { - if (!privateMap.has(receiver)) { - throw new TypeError("attempted to set private field on non-instance"); - } - privateMap.set(receiver, value); - return value; - } - - var ListNode = /** @class */ (function () { - function ListNode(value) { - this.value = value; - } - return ListNode; - }()); - var LinkedList = /** @class */ (function () { - function LinkedList() { - this.size = 0; - } - Object.defineProperty(LinkedList.prototype, "head", { - get: function () { - return this.first; - }, - enumerable: false, - configurable: true - }); - Object.defineProperty(LinkedList.prototype, "tail", { - get: function () { - return this.last; - }, - enumerable: false, - configurable: true - }); - Object.defineProperty(LinkedList.prototype, "length", { - get: function () { - return this.size; - }, - enumerable: false, - configurable: true - }); - LinkedList.prototype.attach = function (value, previousNode, nextNode) { - if (!previousNode) - return this.addHead(value); - if (!nextNode) - return this.addTail(value); - var node = new ListNode(value); - node.previous = previousNode; - previousNode.next = node; - node.next = nextNode; - nextNode.previous = node; - this.size++; - return node; - }; - LinkedList.prototype.attachMany = function (values, previousNode, nextNode) { - if (!values.length) - return []; - if (!previousNode) - return this.addManyHead(values); - if (!nextNode) - return this.addManyTail(values); - var list = new LinkedList(); - list.addManyTail(values); - list.first.previous = previousNode; - previousNode.next = list.first; - list.last.next = nextNode; - nextNode.previous = list.last; - this.size += values.length; - return list.toNodeArray(); - }; - LinkedList.prototype.detach = function (node) { - if (!node.previous) - return this.dropHead(); - if (!node.next) - return this.dropTail(); - node.previous.next = node.next; - node.next.previous = node.previous; - this.size--; - return node; - }; - LinkedList.prototype.add = function (value) { - var _this = this; - return { - after: function () { - var _a; - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return (_a = _this.addAfter).call.apply(_a, __spread([_this, value], params)); - }, - before: function () { - var _a; - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return (_a = _this.addBefore).call.apply(_a, __spread([_this, value], params)); - }, - byIndex: function (position) { return _this.addByIndex(value, position); }, - head: function () { return _this.addHead(value); }, - tail: function () { return _this.addTail(value); }, - }; - }; - LinkedList.prototype.addMany = function (values) { - var _this = this; - return { - after: function () { - var _a; - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return (_a = _this.addManyAfter).call.apply(_a, __spread([_this, values], params)); - }, - before: function () { - var _a; - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return (_a = _this.addManyBefore).call.apply(_a, __spread([_this, values], params)); - }, - byIndex: function (position) { return _this.addManyByIndex(values, position); }, - head: function () { return _this.addManyHead(values); }, - tail: function () { return _this.addManyTail(values); }, - }; - }; - LinkedList.prototype.addAfter = function (value, previousValue, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var previous = this.find(function (node) { return compareFn(node.value, previousValue); }); - return previous ? this.attach(value, previous, previous.next) : this.addTail(value); - }; - LinkedList.prototype.addBefore = function (value, nextValue, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var next = this.find(function (node) { return compareFn(node.value, nextValue); }); - return next ? this.attach(value, next.previous, next) : this.addHead(value); - }; - LinkedList.prototype.addByIndex = function (value, position) { - if (position < 0) - position += this.size; - else if (position >= this.size) - return this.addTail(value); - if (position <= 0) - return this.addHead(value); - var next = this.get(position); - return this.attach(value, next.previous, next); - }; - LinkedList.prototype.addHead = function (value) { - var node = new ListNode(value); - node.next = this.first; - if (this.first) - this.first.previous = node; - else - this.last = node; - this.first = node; - this.size++; - return node; - }; - LinkedList.prototype.addTail = function (value) { - var node = new ListNode(value); - if (this.first) { - node.previous = this.last; - this.last.next = node; - this.last = node; - } - else { - this.first = node; - this.last = node; - } - this.size++; - return node; - }; - LinkedList.prototype.addManyAfter = function (values, previousValue, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var previous = this.find(function (node) { return compareFn(node.value, previousValue); }); - return previous ? this.attachMany(values, previous, previous.next) : this.addManyTail(values); - }; - LinkedList.prototype.addManyBefore = function (values, nextValue, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var next = this.find(function (node) { return compareFn(node.value, nextValue); }); - return next ? this.attachMany(values, next.previous, next) : this.addManyHead(values); - }; - LinkedList.prototype.addManyByIndex = function (values, position) { - if (position < 0) - position += this.size; - if (position <= 0) - return this.addManyHead(values); - if (position >= this.size) - return this.addManyTail(values); - var next = this.get(position); - return this.attachMany(values, next.previous, next); - }; - LinkedList.prototype.addManyHead = function (values) { - var _this = this; - return values.reduceRight(function (nodes, value) { - nodes.unshift(_this.addHead(value)); - return nodes; - }, []); - }; - LinkedList.prototype.addManyTail = function (values) { - var _this = this; - return values.map(function (value) { return _this.addTail(value); }); - }; - LinkedList.prototype.drop = function () { - var _this = this; - return { - byIndex: function (position) { return _this.dropByIndex(position); }, - byValue: function () { - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return _this.dropByValue.apply(_this, params); - }, - byValueAll: function () { - var params = []; - for (var _i = 0; _i < arguments.length; _i++) { - params[_i] = arguments[_i]; - } - return _this.dropByValueAll.apply(_this, params); - }, - head: function () { return _this.dropHead(); }, - tail: function () { return _this.dropTail(); }, - }; - }; - LinkedList.prototype.dropMany = function (count) { - var _this = this; - return { - byIndex: function (position) { return _this.dropManyByIndex(count, position); }, - head: function () { return _this.dropManyHead(count); }, - tail: function () { return _this.dropManyTail(count); }, - }; - }; - LinkedList.prototype.dropByIndex = function (position) { - if (position < 0) - position += this.size; - var current = this.get(position); - return current ? this.detach(current) : undefined; - }; - LinkedList.prototype.dropByValue = function (value, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var position = this.findIndex(function (node) { return compareFn(node.value, value); }); - return position < 0 ? undefined : this.dropByIndex(position); - }; - LinkedList.prototype.dropByValueAll = function (value, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - var dropped = []; - for (var current = this.first, position = 0; current; position++, current = current.next) { - if (compareFn(current.value, value)) { - dropped.push(this.dropByIndex(position - dropped.length)); - } - } - return dropped; - }; - LinkedList.prototype.dropHead = function () { - var head = this.first; - if (head) { - this.first = head.next; - if (this.first) - this.first.previous = undefined; - else - this.last = undefined; - this.size--; - return head; - } - return undefined; - }; - LinkedList.prototype.dropTail = function () { - var tail = this.last; - if (tail) { - this.last = tail.previous; - if (this.last) - this.last.next = undefined; - else - this.first = undefined; - this.size--; - return tail; - } - return undefined; - }; - LinkedList.prototype.dropManyByIndex = function (count, position) { - if (count <= 0) - return []; - if (position < 0) - position = Math.max(position + this.size, 0); - else if (position >= this.size) - return []; - count = Math.min(count, this.size - position); - var dropped = []; - while (count--) { - var current = this.get(position); - dropped.push(this.detach(current)); - } - return dropped; - }; - LinkedList.prototype.dropManyHead = function (count) { - if (count <= 0) - return []; - count = Math.min(count, this.size); - var dropped = []; - while (count--) - dropped.unshift(this.dropHead()); - return dropped; - }; - LinkedList.prototype.dropManyTail = function (count) { - if (count <= 0) - return []; - count = Math.min(count, this.size); - var dropped = []; - while (count--) - dropped.push(this.dropTail()); - return dropped; - }; - LinkedList.prototype.find = function (predicate) { - for (var current = this.first, position = 0; current; position++, current = current.next) { - if (predicate(current, position, this)) - return current; - } - return undefined; - }; - LinkedList.prototype.findIndex = function (predicate) { - for (var current = this.first, position = 0; current; position++, current = current.next) { - if (predicate(current, position, this)) - return position; - } - return -1; - }; - LinkedList.prototype.forEach = function (iteratorFn) { - for (var node = this.first, position = 0; node; position++, node = node.next) { - iteratorFn(node, position, this); - } - }; - LinkedList.prototype.get = function (position) { - return this.find(function (_, index) { return position === index; }); - }; - LinkedList.prototype.indexOf = function (value, compareFn) { - if (compareFn === void 0) { compareFn = compare; } - return this.findIndex(function (node) { return compareFn(node.value, value); }); - }; - LinkedList.prototype.toArray = function () { - var array = new Array(this.size); - this.forEach(function (node, index) { return (array[index] = node.value); }); - return array; - }; - LinkedList.prototype.toNodeArray = function () { - var array = new Array(this.size); - this.forEach(function (node, index) { return (array[index] = node); }); - return array; - }; - LinkedList.prototype.toString = function (mapperFn) { - if (mapperFn === void 0) { mapperFn = JSON.stringify; } - return this.toArray() - .map(function (value) { return mapperFn(value); }) - .join(' <-> '); - }; - // Cannot use Generator type because of ng-packagr - LinkedList.prototype[Symbol.iterator] = function () { - var node, position; - return __generator(this, function (_a) { - switch (_a.label) { - case 0: - node = this.first, position = 0; - _a.label = 1; - case 1: - if (!node) return [3 /*break*/, 4]; - return [4 /*yield*/, node.value]; - case 2: - _a.sent(); - _a.label = 3; - case 3: - position++, node = node.next; - return [3 /*break*/, 1]; - case 4: return [2 /*return*/]; - } - }); - }; - return LinkedList; - }()); - - /* - * Public API Surface of utils - */ - - /** - * Generated bundle index. Do not edit. - */ - - exports.LinkedList = LinkedList; - exports.ListNode = ListNode; - - Object.defineProperty(exports, '__esModule', { value: true }); - -}))); -//# sourceMappingURL=abp-utils.umd.js.map diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js.map b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js.map deleted file mode 100644 index c8cf999f3b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.js.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"file":"abp-utils.umd.js","sources":["../../node_modules/tslib/tslib.es6.js","../../projects/utils/src/lib/linked-list.ts","../../projects/utils/src/public-api.ts","../../projects/utils/src/abp-utils.ts"],"sourcesContent":["/*! *****************************************************************************\r\nCopyright (c) Microsoft Corporation.\r\n\r\nPermission to use, copy, modify, and/or distribute this software for any\r\npurpose with or without fee is hereby granted.\r\n\r\nTHE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH\r\nREGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY\r\nAND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,\r\nINDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM\r\nLOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR\r\nOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\r\nPERFORMANCE OF THIS SOFTWARE.\r\n***************************************************************************** */\r\n/* global Reflect, Promise */\r\n\r\nvar extendStatics = function(d, b) {\r\n extendStatics = Object.setPrototypeOf ||\r\n ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||\r\n function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };\r\n return extendStatics(d, b);\r\n};\r\n\r\nexport function __extends(d, b) {\r\n extendStatics(d, b);\r\n function __() { this.constructor = d; }\r\n d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());\r\n}\r\n\r\nexport var __assign = function() {\r\n __assign = Object.assign || function __assign(t) {\r\n for (var s, i = 1, n = arguments.length; i < n; i++) {\r\n s = arguments[i];\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];\r\n }\r\n return t;\r\n }\r\n return __assign.apply(this, arguments);\r\n}\r\n\r\nexport function __rest(s, e) {\r\n var t = {};\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)\r\n t[p] = s[p];\r\n if (s != null && typeof Object.getOwnPropertySymbols === \"function\")\r\n for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {\r\n if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))\r\n t[p[i]] = s[p[i]];\r\n }\r\n return t;\r\n}\r\n\r\nexport function __decorate(decorators, target, key, desc) {\r\n var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;\r\n if (typeof Reflect === \"object\" && typeof Reflect.decorate === \"function\") r = Reflect.decorate(decorators, target, key, desc);\r\n else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;\r\n return c > 3 && r && Object.defineProperty(target, key, r), r;\r\n}\r\n\r\nexport function __param(paramIndex, decorator) {\r\n return function (target, key) { decorator(target, key, paramIndex); }\r\n}\r\n\r\nexport function __metadata(metadataKey, metadataValue) {\r\n if (typeof Reflect === \"object\" && typeof Reflect.metadata === \"function\") return Reflect.metadata(metadataKey, metadataValue);\r\n}\r\n\r\nexport function __awaiter(thisArg, _arguments, P, generator) {\r\n function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\r\n return new (P || (P = Promise))(function (resolve, reject) {\r\n function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\r\n function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\r\n function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\r\n step((generator = generator.apply(thisArg, _arguments || [])).next());\r\n });\r\n}\r\n\r\nexport function __generator(thisArg, body) {\r\n var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\r\n return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\r\n function verb(n) { return function (v) { return step([n, v]); }; }\r\n function step(op) {\r\n if (f) throw new TypeError(\"Generator is already executing.\");\r\n while (_) try {\r\n if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\r\n if (y = 0, t) op = [op[0] & 2, t.value];\r\n switch (op[0]) {\r\n case 0: case 1: t = op; break;\r\n case 4: _.label++; return { value: op[1], done: false };\r\n case 5: _.label++; y = op[1]; op = [0]; continue;\r\n case 7: op = _.ops.pop(); _.trys.pop(); continue;\r\n default:\r\n if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\r\n if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\r\n if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\r\n if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\r\n if (t[2]) _.ops.pop();\r\n _.trys.pop(); continue;\r\n }\r\n op = body.call(thisArg, _);\r\n } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\r\n if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\r\n }\r\n}\r\n\r\nexport var __createBinding = Object.create ? (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });\r\n}) : (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n o[k2] = m[k];\r\n});\r\n\r\nexport function __exportStar(m, exports) {\r\n for (var p in m) if (p !== \"default\" && !exports.hasOwnProperty(p)) __createBinding(exports, m, p);\r\n}\r\n\r\nexport function __values(o) {\r\n var s = typeof Symbol === \"function\" && Symbol.iterator, m = s && o[s], i = 0;\r\n if (m) return m.call(o);\r\n if (o && typeof o.length === \"number\") return {\r\n next: function () {\r\n if (o && i >= o.length) o = void 0;\r\n return { value: o && o[i++], done: !o };\r\n }\r\n };\r\n throw new TypeError(s ? \"Object is not iterable.\" : \"Symbol.iterator is not defined.\");\r\n}\r\n\r\nexport function __read(o, n) {\r\n var m = typeof Symbol === \"function\" && o[Symbol.iterator];\r\n if (!m) return o;\r\n var i = m.call(o), r, ar = [], e;\r\n try {\r\n while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);\r\n }\r\n catch (error) { e = { error: error }; }\r\n finally {\r\n try {\r\n if (r && !r.done && (m = i[\"return\"])) m.call(i);\r\n }\r\n finally { if (e) throw e.error; }\r\n }\r\n return ar;\r\n}\r\n\r\nexport function __spread() {\r\n for (var ar = [], i = 0; i < arguments.length; i++)\r\n ar = ar.concat(__read(arguments[i]));\r\n return ar;\r\n}\r\n\r\nexport function __spreadArrays() {\r\n for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length;\r\n for (var r = Array(s), k = 0, i = 0; i < il; i++)\r\n for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++)\r\n r[k] = a[j];\r\n return r;\r\n};\r\n\r\nexport function __await(v) {\r\n return this instanceof __await ? (this.v = v, this) : new __await(v);\r\n}\r\n\r\nexport function __asyncGenerator(thisArg, _arguments, generator) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var g = generator.apply(thisArg, _arguments || []), i, q = [];\r\n return i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i;\r\n function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; }\r\n function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } }\r\n function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); }\r\n function fulfill(value) { resume(\"next\", value); }\r\n function reject(value) { resume(\"throw\", value); }\r\n function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); }\r\n}\r\n\r\nexport function __asyncDelegator(o) {\r\n var i, p;\r\n return i = {}, verb(\"next\"), verb(\"throw\", function (e) { throw e; }), verb(\"return\"), i[Symbol.iterator] = function () { return this; }, i;\r\n function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === \"return\" } : f ? f(v) : v; } : f; }\r\n}\r\n\r\nexport function __asyncValues(o) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var m = o[Symbol.asyncIterator], i;\r\n return m ? m.call(o) : (o = typeof __values === \"function\" ? __values(o) : o[Symbol.iterator](), i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i);\r\n function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }\r\n function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }\r\n}\r\n\r\nexport function __makeTemplateObject(cooked, raw) {\r\n if (Object.defineProperty) { Object.defineProperty(cooked, \"raw\", { value: raw }); } else { cooked.raw = raw; }\r\n return cooked;\r\n};\r\n\r\nvar __setModuleDefault = Object.create ? (function(o, v) {\r\n Object.defineProperty(o, \"default\", { enumerable: true, value: v });\r\n}) : function(o, v) {\r\n o[\"default\"] = v;\r\n};\r\n\r\nexport function __importStar(mod) {\r\n if (mod && mod.__esModule) return mod;\r\n var result = {};\r\n if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);\r\n __setModuleDefault(result, mod);\r\n return result;\r\n}\r\n\r\nexport function __importDefault(mod) {\r\n return (mod && mod.__esModule) ? mod : { default: mod };\r\n}\r\n\r\nexport function __classPrivateFieldGet(receiver, privateMap) {\r\n if (!privateMap.has(receiver)) {\r\n throw new TypeError(\"attempted to get private field on non-instance\");\r\n }\r\n return privateMap.get(receiver);\r\n}\r\n\r\nexport function __classPrivateFieldSet(receiver, privateMap, value) {\r\n if (!privateMap.has(receiver)) {\r\n throw new TypeError(\"attempted to set private field on non-instance\");\r\n }\r\n privateMap.set(receiver, value);\r\n return value;\r\n}\r\n","/* tslint:disable:no-non-null-assertion */\r\n\r\nimport compare from 'just-compare';\r\n\r\nexport class ListNode {\r\n next: ListNode | undefined;\r\n previous: ListNode | undefined;\r\n constructor(public readonly value: T) {}\r\n}\r\n\r\nexport class LinkedList {\r\n private first: ListNode | undefined;\r\n private last: ListNode | undefined;\r\n private size = 0;\r\n\r\n get head(): ListNode | undefined {\r\n return this.first;\r\n }\r\n get tail(): ListNode | undefined {\r\n return this.last;\r\n }\r\n get length(): number {\r\n return this.size;\r\n }\r\n\r\n private attach(\r\n value: T,\r\n previousNode: ListNode | undefined,\r\n nextNode: ListNode | undefined,\r\n ): ListNode {\r\n if (!previousNode) return this.addHead(value);\r\n\r\n if (!nextNode) return this.addTail(value);\r\n\r\n const node = new ListNode(value);\r\n node.previous = previousNode;\r\n previousNode.next = node;\r\n node.next = nextNode;\r\n nextNode.previous = node;\r\n\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n private attachMany(\r\n values: T[],\r\n previousNode: ListNode | undefined,\r\n nextNode: ListNode | undefined,\r\n ): ListNode[] {\r\n if (!values.length) return [];\r\n\r\n if (!previousNode) return this.addManyHead(values);\r\n\r\n if (!nextNode) return this.addManyTail(values);\r\n\r\n const list = new LinkedList();\r\n list.addManyTail(values);\r\n list.first!.previous = previousNode;\r\n previousNode.next = list.first;\r\n list.last!.next = nextNode;\r\n nextNode.previous = list.last;\r\n\r\n this.size += values.length;\r\n\r\n return list.toNodeArray();\r\n }\r\n\r\n private detach(node: ListNode) {\r\n if (!node.previous) return this.dropHead();\r\n\r\n if (!node.next) return this.dropTail();\r\n\r\n node.previous.next = node.next;\r\n node.next.previous = node.previous;\r\n\r\n this.size--;\r\n\r\n return node;\r\n }\r\n\r\n add(value: T) {\r\n return {\r\n after: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addAfter.call(this, value, ...params),\r\n before: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addBefore.call(this, value, ...params),\r\n byIndex: (position: number) => this.addByIndex(value, position),\r\n head: () => this.addHead(value),\r\n tail: () => this.addTail(value),\r\n };\r\n }\r\n\r\n addMany(values: T[]) {\r\n return {\r\n after: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addManyAfter.call(this, values, ...params),\r\n before: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addManyBefore.call(this, values, ...params),\r\n byIndex: (position: number) => this.addManyByIndex(values, position),\r\n head: () => this.addManyHead(values),\r\n tail: () => this.addManyTail(values),\r\n };\r\n }\r\n\r\n addAfter(value: T, previousValue: T): ListNode;\r\n addAfter(value: T, previousValue: any, compareFn: ListComparisonFn): ListNode;\r\n addAfter(value: T, previousValue: any, compareFn: ListComparisonFn = compare): ListNode {\r\n const previous = this.find(node => compareFn(node.value, previousValue));\r\n\r\n return previous ? this.attach(value, previous, previous.next) : this.addTail(value);\r\n }\r\n\r\n addBefore(value: T, nextValue: T): ListNode;\r\n addBefore(value: T, nextValue: any, compareFn: ListComparisonFn): ListNode;\r\n addBefore(value: T, nextValue: any, compareFn: ListComparisonFn = compare): ListNode {\r\n const next = this.find(node => compareFn(node.value, nextValue));\r\n\r\n return next ? this.attach(value, next.previous, next) : this.addHead(value);\r\n }\r\n\r\n addByIndex(value: T, position: number): ListNode {\r\n if (position < 0) position += this.size;\r\n else if (position >= this.size) return this.addTail(value);\r\n\r\n if (position <= 0) return this.addHead(value);\r\n\r\n const next = this.get(position)!;\r\n\r\n return this.attach(value, next.previous, next);\r\n }\r\n\r\n addHead(value: T): ListNode {\r\n const node = new ListNode(value);\r\n\r\n node.next = this.first;\r\n\r\n if (this.first) this.first.previous = node;\r\n else this.last = node;\r\n\r\n this.first = node;\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n addTail(value: T): ListNode {\r\n const node = new ListNode(value);\r\n\r\n if (this.first) {\r\n node.previous = this.last;\r\n this.last!.next = node;\r\n this.last = node;\r\n } else {\r\n this.first = node;\r\n this.last = node;\r\n }\r\n\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n addManyAfter(values: T[], previousValue: T): ListNode[];\r\n addManyAfter(values: T[], previousValue: any, compareFn: ListComparisonFn): ListNode[];\r\n addManyAfter(\r\n values: T[],\r\n previousValue: any,\r\n compareFn: ListComparisonFn = compare,\r\n ): ListNode[] {\r\n const previous = this.find(node => compareFn(node.value, previousValue));\r\n\r\n return previous ? this.attachMany(values, previous, previous.next) : this.addManyTail(values);\r\n }\r\n\r\n addManyBefore(values: T[], nextValue: T): ListNode[];\r\n addManyBefore(values: T[], nextValue: any, compareFn: ListComparisonFn): ListNode[];\r\n addManyBefore(\r\n values: T[],\r\n nextValue: any,\r\n compareFn: ListComparisonFn = compare,\r\n ): ListNode[] {\r\n const next = this.find(node => compareFn(node.value, nextValue));\r\n\r\n return next ? this.attachMany(values, next.previous, next) : this.addManyHead(values);\r\n }\r\n\r\n addManyByIndex(values: T[], position: number): ListNode[] {\r\n if (position < 0) position += this.size;\r\n\r\n if (position <= 0) return this.addManyHead(values);\r\n\r\n if (position >= this.size) return this.addManyTail(values);\r\n\r\n const next = this.get(position)!;\r\n\r\n return this.attachMany(values, next.previous, next);\r\n }\r\n\r\n addManyHead(values: T[]): ListNode[] {\r\n return values.reduceRight[]>((nodes, value) => {\r\n nodes.unshift(this.addHead(value));\r\n return nodes;\r\n }, []);\r\n }\r\n\r\n addManyTail(values: T[]): ListNode[] {\r\n return values.map(value => this.addTail(value));\r\n }\r\n\r\n drop() {\r\n return {\r\n byIndex: (position: number) => this.dropByIndex(position),\r\n byValue: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.dropByValue.apply(this, params),\r\n byValueAll: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.dropByValueAll.apply(this, params),\r\n head: () => this.dropHead(),\r\n tail: () => this.dropTail(),\r\n };\r\n }\r\n\r\n dropMany(count: number) {\r\n return {\r\n byIndex: (position: number) => this.dropManyByIndex(count, position),\r\n head: () => this.dropManyHead(count),\r\n tail: () => this.dropManyTail(count),\r\n };\r\n }\r\n\r\n dropByIndex(position: number): ListNode | undefined {\r\n if (position < 0) position += this.size;\r\n\r\n const current = this.get(position);\r\n\r\n return current ? this.detach(current) : undefined;\r\n }\r\n\r\n dropByValue(value: T): ListNode | undefined;\r\n dropByValue(value: any, compareFn: ListComparisonFn): ListNode | undefined;\r\n dropByValue(value: any, compareFn: ListComparisonFn = compare): ListNode | undefined {\r\n const position = this.findIndex(node => compareFn(node.value, value));\r\n\r\n return position < 0 ? undefined : this.dropByIndex(position);\r\n }\r\n\r\n dropByValueAll(value: T): ListNode[];\r\n dropByValueAll(value: any, compareFn: ListComparisonFn): ListNode[];\r\n dropByValueAll(value: any, compareFn: ListComparisonFn = compare): ListNode[] {\r\n const dropped: ListNode[] = [];\r\n\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (compareFn(current.value, value)) {\r\n dropped.push(this.dropByIndex(position - dropped.length)!);\r\n }\r\n }\r\n\r\n return dropped;\r\n }\r\n\r\n dropHead(): ListNode | undefined {\r\n const head = this.first;\r\n\r\n if (head) {\r\n this.first = head.next;\r\n\r\n if (this.first) this.first.previous = undefined;\r\n else this.last = undefined;\r\n\r\n this.size--;\r\n\r\n return head;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n dropTail(): ListNode | undefined {\r\n const tail = this.last;\r\n\r\n if (tail) {\r\n this.last = tail.previous;\r\n\r\n if (this.last) this.last.next = undefined;\r\n else this.first = undefined;\r\n\r\n this.size--;\r\n\r\n return tail;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n dropManyByIndex(count: number, position: number): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n if (position < 0) position = Math.max(position + this.size, 0);\r\n else if (position >= this.size) return [];\r\n\r\n count = Math.min(count, this.size - position);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) {\r\n const current = this.get(position);\r\n dropped.push(this.detach(current!)!);\r\n }\r\n\r\n return dropped;\r\n }\r\n\r\n dropManyHead(count: Exclude): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n count = Math.min(count, this.size);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) dropped.unshift(this.dropHead()!);\r\n\r\n return dropped;\r\n }\r\n\r\n dropManyTail(count: Exclude): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n count = Math.min(count, this.size);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) dropped.push(this.dropTail()!);\r\n\r\n return dropped;\r\n }\r\n\r\n find(predicate: ListIteratorFn): ListNode | undefined {\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (predicate(current, position, this)) return current;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n findIndex(predicate: ListIteratorFn): number {\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (predicate(current, position, this)) return position;\r\n }\r\n\r\n return -1;\r\n }\r\n\r\n forEach(iteratorFn: ListIteratorFn) {\r\n for (let node = this.first, position = 0; node; position++, node = node.next) {\r\n iteratorFn(node, position, this);\r\n }\r\n }\r\n\r\n get(position: number): ListNode | undefined {\r\n return this.find((_, index) => position === index);\r\n }\r\n\r\n indexOf(value: T): number;\r\n indexOf(value: any, compareFn: ListComparisonFn): number;\r\n indexOf(value: any, compareFn: ListComparisonFn = compare): number {\r\n return this.findIndex(node => compareFn(node.value, value));\r\n }\r\n\r\n toArray(): T[] {\r\n const array = new Array(this.size);\r\n\r\n this.forEach((node, index) => (array[index!] = node.value));\r\n\r\n return array;\r\n }\r\n\r\n toNodeArray(): ListNode[] {\r\n const array = new Array(this.size);\r\n\r\n this.forEach((node, index) => (array[index!] = node));\r\n\r\n return array;\r\n }\r\n\r\n toString(mapperFn: ListMapperFn = JSON.stringify): string {\r\n return this.toArray()\r\n .map(value => mapperFn(value))\r\n .join(' <-> ');\r\n }\r\n\r\n // Cannot use Generator type because of ng-packagr\r\n *[Symbol.iterator](): any {\r\n for (let node = this.first, position = 0; node; position++, node = node.next) {\r\n yield node.value;\r\n }\r\n }\r\n}\r\n\r\nexport type ListMapperFn = (value: T) => any;\r\n\r\nexport type ListComparisonFn = (value1: T, value2: any) => boolean;\r\n\r\nexport type ListIteratorFn = (\r\n node: ListNode,\r\n index?: number,\r\n list?: LinkedList,\r\n) => R;\r\n","/*\r\n * Public API Surface of utils\r\n */\r\n\r\nexport * from './lib/linked-list';\r\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js deleted file mode 100644 index 57b22e5188..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js +++ /dev/null @@ -1,2 +0,0 @@ -!function(t,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports,require("just-compare")):"function"==typeof define&&define.amd?define("@abp/utils",["exports","just-compare"],r):r(((t=t||self).abp=t.abp||{},t.abp.utils=t.abp.utils||{},t.abp.utils.common={}),t.compare)}(this,(function(t,r){"use strict";r=r&&Object.prototype.hasOwnProperty.call(r,"default")?r.default:r;function e(t,r){var e,n,i,o,a={label:0,sent:function(){if(1&i[0])throw i[1];return i[1]},trys:[],ops:[]};return o={next:u(0),throw:u(1),return:u(2)},"function"==typeof Symbol&&(o[Symbol.iterator]=function(){return this}),o;function u(o){return function(u){return function(o){if(e)throw new TypeError("Generator is already executing.");for(;a;)try{if(e=1,n&&(i=2&o[0]?n.return:o[0]?n.throw||((i=n.return)&&i.call(n),0):n.next)&&!(i=i.call(n,o[1])).done)return i;switch(n=0,i&&(o=[2&o[0],i.value]),o[0]){case 0:case 1:i=o;break;case 4:return a.label++,{value:o[1],done:!1};case 5:a.label++,n=o[1],o=[0];continue;case 7:o=a.ops.pop(),a.trys.pop();continue;default:if(!(i=a.trys,(i=i.length>0&&i[i.length-1])||6!==o[0]&&2!==o[0])){a=0;continue}if(3===o[0]&&(!i||o[1]>i[0]&&o[1]0)&&!(n=o.next()).done;)a.push(n.value)}catch(t){i={error:t}}finally{try{n&&!n.done&&(e=o.return)&&e.call(o)}finally{if(i)throw i.error}}return a}function i(){for(var t=[],r=0;r=this.size)return this.addTail(t);if(r<=0)return this.addHead(t);var e=this.get(r);return this.attach(t,e.previous,e)},t.prototype.addHead=function(t){var r=new o(t);return r.next=this.first,this.first?this.first.previous=r:this.last=r,this.first=r,this.size++,r},t.prototype.addTail=function(t){var r=new o(t);return this.first?(r.previous=this.last,this.last.next=r,this.last=r):(this.first=r,this.last=r),this.size++,r},t.prototype.addManyAfter=function(t,e,n){void 0===n&&(n=r);var i=this.find((function(t){return n(t.value,e)}));return i?this.attachMany(t,i,i.next):this.addManyTail(t)},t.prototype.addManyBefore=function(t,e,n){void 0===n&&(n=r);var i=this.find((function(t){return n(t.value,e)}));return i?this.attachMany(t,i.previous,i):this.addManyHead(t)},t.prototype.addManyByIndex=function(t,r){if(r<0&&(r+=this.size),r<=0)return this.addManyHead(t);if(r>=this.size)return this.addManyTail(t);var e=this.get(r);return this.attachMany(t,e.previous,e)},t.prototype.addManyHead=function(t){var r=this;return t.reduceRight((function(t,e){return t.unshift(r.addHead(e)),t}),[])},t.prototype.addManyTail=function(t){var r=this;return t.map((function(t){return r.addTail(t)}))},t.prototype.drop=function(){var t=this;return{byIndex:function(r){return t.dropByIndex(r)},byValue:function(){for(var r=[],e=0;e=this.size)return[];t=Math.min(t,this.size-r);for(var e=[];t--;){var n=this.get(r);e.push(this.detach(n))}return e},t.prototype.dropManyHead=function(t){if(t<=0)return[];t=Math.min(t,this.size);for(var r=[];t--;)r.unshift(this.dropHead());return r},t.prototype.dropManyTail=function(t){if(t<=0)return[];t=Math.min(t,this.size);for(var r=[];t--;)r.push(this.dropTail());return r},t.prototype.find=function(t){for(var r=this.first,e=0;r;e++,r=r.next)if(t(r,e,this))return r},t.prototype.findIndex=function(t){for(var r=this.first,e=0;r;e++,r=r.next)if(t(r,e,this))return e;return-1},t.prototype.forEach=function(t){for(var r=this.first,e=0;r;e++,r=r.next)t(r,e,this)},t.prototype.get=function(t){return this.find((function(r,e){return t===e}))},t.prototype.indexOf=function(t,e){return void 0===e&&(e=r),this.findIndex((function(r){return e(r.value,t)}))},t.prototype.toArray=function(){var t=new Array(this.size);return this.forEach((function(r,e){return t[e]=r.value})),t},t.prototype.toNodeArray=function(){var t=new Array(this.size);return this.forEach((function(r,e){return t[e]=r})),t},t.prototype.toString=function(t){return void 0===t&&(t=JSON.stringify),this.toArray().map((function(r){return t(r)})).join(" <-> ")},t.prototype[Symbol.iterator]=function(){var t;return e(this,(function(r){switch(r.label){case 0:t=this.first,0,r.label=1;case 1:return t?[4,t.value]:[3,4];case 2:r.sent(),r.label=3;case 3:return t=t.next,[3,1];case 4:return[2]}}))},t}();t.LinkedList=a,t.ListNode=o,Object.defineProperty(t,"__esModule",{value:!0})})); -//# sourceMappingURL=abp-utils.umd.min.js.map \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js.map b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js.map deleted file mode 100644 index 529ba4c447..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/abp/utils/abp-utils.umd.min.js.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"sources":["../../node_modules/tslib/tslib.es6.js","../../projects/utils/src/lib/linked-list.ts"],"names":["__generator","thisArg","body","f","y","t","g","_","label","sent","trys","ops","next","verb","throw","return","Symbol","iterator","this","n","v","op","TypeError","call","done","value","pop","length","push","e","step","Object","create","__read","o","m","r","i","ar","error","__spread","arguments","concat","LinkedList","size","defineProperty","prototype","first","last","attach","previousNode","nextNode","addHead","addTail","node","ListNode","previous","attachMany","values","addManyHead","addManyTail","list","toNodeArray","detach","dropTail","dropHead","add","_this","after","params","_i","_a","addAfter","apply","before","addBefore","byIndex","position","addByIndex","head","tail","addMany","addManyAfter","addManyBefore","addManyByIndex","previousValue","compareFn","compare","find","nextValue","get","reduceRight","nodes","unshift","map","drop","dropByIndex","byValue","dropByValue","byValueAll","dropByValueAll","dropMany","count","dropManyByIndex","dropManyHead","dropManyTail","current","undefined","findIndex","dropped","Math","max","min","predicate","forEach","iteratorFn","index","indexOf","toArray","array","Array","toString","mapperFn","JSON","stringify","join"],"mappings":"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","sourcesContent":["/*! *****************************************************************************\r\nCopyright (c) Microsoft Corporation.\r\n\r\nPermission to use, copy, modify, and/or distribute this software for any\r\npurpose with or without fee is hereby granted.\r\n\r\nTHE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH\r\nREGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY\r\nAND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,\r\nINDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM\r\nLOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR\r\nOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\r\nPERFORMANCE OF THIS SOFTWARE.\r\n***************************************************************************** */\r\n/* global Reflect, Promise */\r\n\r\nvar extendStatics = function(d, b) {\r\n extendStatics = Object.setPrototypeOf ||\r\n ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||\r\n function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };\r\n return extendStatics(d, b);\r\n};\r\n\r\nexport function __extends(d, b) {\r\n extendStatics(d, b);\r\n function __() { this.constructor = d; }\r\n d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());\r\n}\r\n\r\nexport var __assign = function() {\r\n __assign = Object.assign || function __assign(t) {\r\n for (var s, i = 1, n = arguments.length; i < n; i++) {\r\n s = arguments[i];\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];\r\n }\r\n return t;\r\n }\r\n return __assign.apply(this, arguments);\r\n}\r\n\r\nexport function __rest(s, e) {\r\n var t = {};\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)\r\n t[p] = s[p];\r\n if (s != null && typeof Object.getOwnPropertySymbols === \"function\")\r\n for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {\r\n if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))\r\n t[p[i]] = s[p[i]];\r\n }\r\n return t;\r\n}\r\n\r\nexport function __decorate(decorators, target, key, desc) {\r\n var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;\r\n if (typeof Reflect === \"object\" && typeof Reflect.decorate === \"function\") r = Reflect.decorate(decorators, target, key, desc);\r\n else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;\r\n return c > 3 && r && Object.defineProperty(target, key, r), r;\r\n}\r\n\r\nexport function __param(paramIndex, decorator) {\r\n return function (target, key) { decorator(target, key, paramIndex); }\r\n}\r\n\r\nexport function __metadata(metadataKey, metadataValue) {\r\n if (typeof Reflect === \"object\" && typeof Reflect.metadata === \"function\") return Reflect.metadata(metadataKey, metadataValue);\r\n}\r\n\r\nexport function __awaiter(thisArg, _arguments, P, generator) {\r\n function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\r\n return new (P || (P = Promise))(function (resolve, reject) {\r\n function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\r\n function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\r\n function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\r\n step((generator = generator.apply(thisArg, _arguments || [])).next());\r\n });\r\n}\r\n\r\nexport function __generator(thisArg, body) {\r\n var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\r\n return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\r\n function verb(n) { return function (v) { return step([n, v]); }; }\r\n function step(op) {\r\n if (f) throw new TypeError(\"Generator is already executing.\");\r\n while (_) try {\r\n if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\r\n if (y = 0, t) op = [op[0] & 2, t.value];\r\n switch (op[0]) {\r\n case 0: case 1: t = op; break;\r\n case 4: _.label++; return { value: op[1], done: false };\r\n case 5: _.label++; y = op[1]; op = [0]; continue;\r\n case 7: op = _.ops.pop(); _.trys.pop(); continue;\r\n default:\r\n if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\r\n if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\r\n if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\r\n if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\r\n if (t[2]) _.ops.pop();\r\n _.trys.pop(); continue;\r\n }\r\n op = body.call(thisArg, _);\r\n } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\r\n if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\r\n }\r\n}\r\n\r\nexport var __createBinding = Object.create ? (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });\r\n}) : (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n o[k2] = m[k];\r\n});\r\n\r\nexport function __exportStar(m, exports) {\r\n for (var p in m) if (p !== \"default\" && !exports.hasOwnProperty(p)) __createBinding(exports, m, p);\r\n}\r\n\r\nexport function __values(o) {\r\n var s = typeof Symbol === \"function\" && Symbol.iterator, m = s && o[s], i = 0;\r\n if (m) return m.call(o);\r\n if (o && typeof o.length === \"number\") return {\r\n next: function () {\r\n if (o && i >= o.length) o = void 0;\r\n return { value: o && o[i++], done: !o };\r\n }\r\n };\r\n throw new TypeError(s ? \"Object is not iterable.\" : \"Symbol.iterator is not defined.\");\r\n}\r\n\r\nexport function __read(o, n) {\r\n var m = typeof Symbol === \"function\" && o[Symbol.iterator];\r\n if (!m) return o;\r\n var i = m.call(o), r, ar = [], e;\r\n try {\r\n while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);\r\n }\r\n catch (error) { e = { error: error }; }\r\n finally {\r\n try {\r\n if (r && !r.done && (m = i[\"return\"])) m.call(i);\r\n }\r\n finally { if (e) throw e.error; }\r\n }\r\n return ar;\r\n}\r\n\r\nexport function __spread() {\r\n for (var ar = [], i = 0; i < arguments.length; i++)\r\n ar = ar.concat(__read(arguments[i]));\r\n return ar;\r\n}\r\n\r\nexport function __spreadArrays() {\r\n for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length;\r\n for (var r = Array(s), k = 0, i = 0; i < il; i++)\r\n for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++)\r\n r[k] = a[j];\r\n return r;\r\n};\r\n\r\nexport function __await(v) {\r\n return this instanceof __await ? (this.v = v, this) : new __await(v);\r\n}\r\n\r\nexport function __asyncGenerator(thisArg, _arguments, generator) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var g = generator.apply(thisArg, _arguments || []), i, q = [];\r\n return i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i;\r\n function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; }\r\n function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } }\r\n function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); }\r\n function fulfill(value) { resume(\"next\", value); }\r\n function reject(value) { resume(\"throw\", value); }\r\n function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); }\r\n}\r\n\r\nexport function __asyncDelegator(o) {\r\n var i, p;\r\n return i = {}, verb(\"next\"), verb(\"throw\", function (e) { throw e; }), verb(\"return\"), i[Symbol.iterator] = function () { return this; }, i;\r\n function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === \"return\" } : f ? f(v) : v; } : f; }\r\n}\r\n\r\nexport function __asyncValues(o) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var m = o[Symbol.asyncIterator], i;\r\n return m ? m.call(o) : (o = typeof __values === \"function\" ? __values(o) : o[Symbol.iterator](), i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i);\r\n function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }\r\n function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }\r\n}\r\n\r\nexport function __makeTemplateObject(cooked, raw) {\r\n if (Object.defineProperty) { Object.defineProperty(cooked, \"raw\", { value: raw }); } else { cooked.raw = raw; }\r\n return cooked;\r\n};\r\n\r\nvar __setModuleDefault = Object.create ? (function(o, v) {\r\n Object.defineProperty(o, \"default\", { enumerable: true, value: v });\r\n}) : function(o, v) {\r\n o[\"default\"] = v;\r\n};\r\n\r\nexport function __importStar(mod) {\r\n if (mod && mod.__esModule) return mod;\r\n var result = {};\r\n if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);\r\n __setModuleDefault(result, mod);\r\n return result;\r\n}\r\n\r\nexport function __importDefault(mod) {\r\n return (mod && mod.__esModule) ? mod : { default: mod };\r\n}\r\n\r\nexport function __classPrivateFieldGet(receiver, privateMap) {\r\n if (!privateMap.has(receiver)) {\r\n throw new TypeError(\"attempted to get private field on non-instance\");\r\n }\r\n return privateMap.get(receiver);\r\n}\r\n\r\nexport function __classPrivateFieldSet(receiver, privateMap, value) {\r\n if (!privateMap.has(receiver)) {\r\n throw new TypeError(\"attempted to set private field on non-instance\");\r\n }\r\n privateMap.set(receiver, value);\r\n return value;\r\n}\r\n","/* tslint:disable:no-non-null-assertion */\r\n\r\nimport compare from 'just-compare';\r\n\r\nexport class ListNode {\r\n next: ListNode | undefined;\r\n previous: ListNode | undefined;\r\n constructor(public readonly value: T) {}\r\n}\r\n\r\nexport class LinkedList {\r\n private first: ListNode | undefined;\r\n private last: ListNode | undefined;\r\n private size = 0;\r\n\r\n get head(): ListNode | undefined {\r\n return this.first;\r\n }\r\n get tail(): ListNode | undefined {\r\n return this.last;\r\n }\r\n get length(): number {\r\n return this.size;\r\n }\r\n\r\n private attach(\r\n value: T,\r\n previousNode: ListNode | undefined,\r\n nextNode: ListNode | undefined,\r\n ): ListNode {\r\n if (!previousNode) return this.addHead(value);\r\n\r\n if (!nextNode) return this.addTail(value);\r\n\r\n const node = new ListNode(value);\r\n node.previous = previousNode;\r\n previousNode.next = node;\r\n node.next = nextNode;\r\n nextNode.previous = node;\r\n\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n private attachMany(\r\n values: T[],\r\n previousNode: ListNode | undefined,\r\n nextNode: ListNode | undefined,\r\n ): ListNode[] {\r\n if (!values.length) return [];\r\n\r\n if (!previousNode) return this.addManyHead(values);\r\n\r\n if (!nextNode) return this.addManyTail(values);\r\n\r\n const list = new LinkedList();\r\n list.addManyTail(values);\r\n list.first!.previous = previousNode;\r\n previousNode.next = list.first;\r\n list.last!.next = nextNode;\r\n nextNode.previous = list.last;\r\n\r\n this.size += values.length;\r\n\r\n return list.toNodeArray();\r\n }\r\n\r\n private detach(node: ListNode) {\r\n if (!node.previous) return this.dropHead();\r\n\r\n if (!node.next) return this.dropTail();\r\n\r\n node.previous.next = node.next;\r\n node.next.previous = node.previous;\r\n\r\n this.size--;\r\n\r\n return node;\r\n }\r\n\r\n add(value: T) {\r\n return {\r\n after: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addAfter.call(this, value, ...params),\r\n before: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addBefore.call(this, value, ...params),\r\n byIndex: (position: number) => this.addByIndex(value, position),\r\n head: () => this.addHead(value),\r\n tail: () => this.addTail(value),\r\n };\r\n }\r\n\r\n addMany(values: T[]) {\r\n return {\r\n after: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addManyAfter.call(this, values, ...params),\r\n before: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.addManyBefore.call(this, values, ...params),\r\n byIndex: (position: number) => this.addManyByIndex(values, position),\r\n head: () => this.addManyHead(values),\r\n tail: () => this.addManyTail(values),\r\n };\r\n }\r\n\r\n addAfter(value: T, previousValue: T): ListNode;\r\n addAfter(value: T, previousValue: any, compareFn: ListComparisonFn): ListNode;\r\n addAfter(value: T, previousValue: any, compareFn: ListComparisonFn = compare): ListNode {\r\n const previous = this.find(node => compareFn(node.value, previousValue));\r\n\r\n return previous ? this.attach(value, previous, previous.next) : this.addTail(value);\r\n }\r\n\r\n addBefore(value: T, nextValue: T): ListNode;\r\n addBefore(value: T, nextValue: any, compareFn: ListComparisonFn): ListNode;\r\n addBefore(value: T, nextValue: any, compareFn: ListComparisonFn = compare): ListNode {\r\n const next = this.find(node => compareFn(node.value, nextValue));\r\n\r\n return next ? this.attach(value, next.previous, next) : this.addHead(value);\r\n }\r\n\r\n addByIndex(value: T, position: number): ListNode {\r\n if (position < 0) position += this.size;\r\n else if (position >= this.size) return this.addTail(value);\r\n\r\n if (position <= 0) return this.addHead(value);\r\n\r\n const next = this.get(position)!;\r\n\r\n return this.attach(value, next.previous, next);\r\n }\r\n\r\n addHead(value: T): ListNode {\r\n const node = new ListNode(value);\r\n\r\n node.next = this.first;\r\n\r\n if (this.first) this.first.previous = node;\r\n else this.last = node;\r\n\r\n this.first = node;\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n addTail(value: T): ListNode {\r\n const node = new ListNode(value);\r\n\r\n if (this.first) {\r\n node.previous = this.last;\r\n this.last!.next = node;\r\n this.last = node;\r\n } else {\r\n this.first = node;\r\n this.last = node;\r\n }\r\n\r\n this.size++;\r\n\r\n return node;\r\n }\r\n\r\n addManyAfter(values: T[], previousValue: T): ListNode[];\r\n addManyAfter(values: T[], previousValue: any, compareFn: ListComparisonFn): ListNode[];\r\n addManyAfter(\r\n values: T[],\r\n previousValue: any,\r\n compareFn: ListComparisonFn = compare,\r\n ): ListNode[] {\r\n const previous = this.find(node => compareFn(node.value, previousValue));\r\n\r\n return previous ? this.attachMany(values, previous, previous.next) : this.addManyTail(values);\r\n }\r\n\r\n addManyBefore(values: T[], nextValue: T): ListNode[];\r\n addManyBefore(values: T[], nextValue: any, compareFn: ListComparisonFn): ListNode[];\r\n addManyBefore(\r\n values: T[],\r\n nextValue: any,\r\n compareFn: ListComparisonFn = compare,\r\n ): ListNode[] {\r\n const next = this.find(node => compareFn(node.value, nextValue));\r\n\r\n return next ? this.attachMany(values, next.previous, next) : this.addManyHead(values);\r\n }\r\n\r\n addManyByIndex(values: T[], position: number): ListNode[] {\r\n if (position < 0) position += this.size;\r\n\r\n if (position <= 0) return this.addManyHead(values);\r\n\r\n if (position >= this.size) return this.addManyTail(values);\r\n\r\n const next = this.get(position)!;\r\n\r\n return this.attachMany(values, next.previous, next);\r\n }\r\n\r\n addManyHead(values: T[]): ListNode[] {\r\n return values.reduceRight[]>((nodes, value) => {\r\n nodes.unshift(this.addHead(value));\r\n return nodes;\r\n }, []);\r\n }\r\n\r\n addManyTail(values: T[]): ListNode[] {\r\n return values.map(value => this.addTail(value));\r\n }\r\n\r\n drop() {\r\n return {\r\n byIndex: (position: number) => this.dropByIndex(position),\r\n byValue: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.dropByValue.apply(this, params),\r\n byValueAll: (...params: [T] | [any, ListComparisonFn]) =>\r\n this.dropByValueAll.apply(this, params),\r\n head: () => this.dropHead(),\r\n tail: () => this.dropTail(),\r\n };\r\n }\r\n\r\n dropMany(count: number) {\r\n return {\r\n byIndex: (position: number) => this.dropManyByIndex(count, position),\r\n head: () => this.dropManyHead(count),\r\n tail: () => this.dropManyTail(count),\r\n };\r\n }\r\n\r\n dropByIndex(position: number): ListNode | undefined {\r\n if (position < 0) position += this.size;\r\n\r\n const current = this.get(position);\r\n\r\n return current ? this.detach(current) : undefined;\r\n }\r\n\r\n dropByValue(value: T): ListNode | undefined;\r\n dropByValue(value: any, compareFn: ListComparisonFn): ListNode | undefined;\r\n dropByValue(value: any, compareFn: ListComparisonFn = compare): ListNode | undefined {\r\n const position = this.findIndex(node => compareFn(node.value, value));\r\n\r\n return position < 0 ? undefined : this.dropByIndex(position);\r\n }\r\n\r\n dropByValueAll(value: T): ListNode[];\r\n dropByValueAll(value: any, compareFn: ListComparisonFn): ListNode[];\r\n dropByValueAll(value: any, compareFn: ListComparisonFn = compare): ListNode[] {\r\n const dropped: ListNode[] = [];\r\n\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (compareFn(current.value, value)) {\r\n dropped.push(this.dropByIndex(position - dropped.length)!);\r\n }\r\n }\r\n\r\n return dropped;\r\n }\r\n\r\n dropHead(): ListNode | undefined {\r\n const head = this.first;\r\n\r\n if (head) {\r\n this.first = head.next;\r\n\r\n if (this.first) this.first.previous = undefined;\r\n else this.last = undefined;\r\n\r\n this.size--;\r\n\r\n return head;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n dropTail(): ListNode | undefined {\r\n const tail = this.last;\r\n\r\n if (tail) {\r\n this.last = tail.previous;\r\n\r\n if (this.last) this.last.next = undefined;\r\n else this.first = undefined;\r\n\r\n this.size--;\r\n\r\n return tail;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n dropManyByIndex(count: number, position: number): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n if (position < 0) position = Math.max(position + this.size, 0);\r\n else if (position >= this.size) return [];\r\n\r\n count = Math.min(count, this.size - position);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) {\r\n const current = this.get(position);\r\n dropped.push(this.detach(current!)!);\r\n }\r\n\r\n return dropped;\r\n }\r\n\r\n dropManyHead(count: Exclude): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n count = Math.min(count, this.size);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) dropped.unshift(this.dropHead()!);\r\n\r\n return dropped;\r\n }\r\n\r\n dropManyTail(count: Exclude): ListNode[] {\r\n if (count <= 0) return [];\r\n\r\n count = Math.min(count, this.size);\r\n\r\n const dropped: ListNode[] = [];\r\n\r\n while (count--) dropped.push(this.dropTail()!);\r\n\r\n return dropped;\r\n }\r\n\r\n find(predicate: ListIteratorFn): ListNode | undefined {\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (predicate(current, position, this)) return current;\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n findIndex(predicate: ListIteratorFn): number {\r\n for (let current = this.first, position = 0; current; position++, current = current.next) {\r\n if (predicate(current, position, this)) return position;\r\n }\r\n\r\n return -1;\r\n }\r\n\r\n forEach(iteratorFn: ListIteratorFn) {\r\n for (let node = this.first, position = 0; node; position++, node = node.next) {\r\n iteratorFn(node, position, this);\r\n }\r\n }\r\n\r\n get(position: number): ListNode | undefined {\r\n return this.find((_, index) => position === index);\r\n }\r\n\r\n indexOf(value: T): number;\r\n indexOf(value: any, compareFn: ListComparisonFn): number;\r\n indexOf(value: any, compareFn: ListComparisonFn = compare): number {\r\n return this.findIndex(node => compareFn(node.value, value));\r\n }\r\n\r\n toArray(): T[] {\r\n const array = new Array(this.size);\r\n\r\n this.forEach((node, index) => (array[index!] = node.value));\r\n\r\n return array;\r\n }\r\n\r\n toNodeArray(): ListNode[] {\r\n const array = new Array(this.size);\r\n\r\n this.forEach((node, index) => (array[index!] = node));\r\n\r\n return array;\r\n }\r\n\r\n toString(mapperFn: ListMapperFn = JSON.stringify): string {\r\n return this.toArray()\r\n .map(value => mapperFn(value))\r\n .join(' <-> ');\r\n }\r\n\r\n // Cannot use Generator type because of ng-packagr\r\n *[Symbol.iterator](): any {\r\n for (let node = this.first, position = 0; node; position++, node = node.next) {\r\n yield node.value;\r\n }\r\n }\r\n}\r\n\r\nexport type ListMapperFn = (value: T) => any;\r\n\r\nexport type ListComparisonFn = (value1: T, value2: any) => boolean;\r\n\r\nexport type ListIteratorFn = (\r\n node: ListNode,\r\n index?: number,\r\n list?: LinkedList,\r\n) => R;\r\n"]} \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.css.map b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.css.map deleted file mode 100644 index 7e08a21044..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.css.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"sources":["less/datepicker.less","build/build.less"],"names":[],"mappings":"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","sourcesContent":[".datepicker {\n\tpadding: 4px;\n\t.border-radius(@baseBorderRadius);\n\t&-inline {\n\t\twidth: 220px;\n\t}\n\tdirection: ltr;\n\t&-rtl {\n\t\tdirection: rtl;\n\t\t&.dropdown-menu { left: auto; }\n\t\ttable tr td span {\n\t\t\tfloat: right;\n\t\t}\n\t}\n\t&-dropdown {\n\t\ttop: 0;\n\t\tleft: 0;\n\t\t&:before {\n\t\t\tcontent: '';\n\t\t\tdisplay: inline-block;\n\t\t\tborder-left: 7px solid transparent;\n\t\t\tborder-right: 7px solid transparent;\n\t\t\tborder-bottom: 7px solid @grayLight;\n\t\t\tborder-top: 0;\n\t\t\tborder-bottom-color: rgba(0,0,0,.2);\n\t\t\tposition: absolute;\n\t\t}\n\t\t&:after {\n\t\t\tcontent: '';\n\t\t\tdisplay: inline-block;\n\t\t\tborder-left: 6px solid transparent;\n\t\t\tborder-right: 6px solid transparent;\n\t\t\tborder-bottom: 6px solid @white;\n\t\t\tborder-top: 0;\n\t\t\tposition: absolute;\n\t\t}\n\t\t&.datepicker-orient-left:before { left: 6px; }\n\t\t&.datepicker-orient-left:after { left: 7px; }\n\t\t&.datepicker-orient-right:before { right: 6px; }\n\t\t&.datepicker-orient-right:after { right: 7px; }\n\t\t&.datepicker-orient-bottom:before { top: -7px; }\n\t\t&.datepicker-orient-bottom:after { top: -6px; }\n\t\t&.datepicker-orient-top:before {\n\t\t\tbottom: -7px;\n\t\t\tborder-bottom: 0;\n\t\t\tborder-top: 7px solid @grayLight;\n\t\t}\n\t\t&.datepicker-orient-top:after {\n\t\t\tbottom: -6px;\n\t\t\tborder-bottom: 0;\n\t\t\tborder-top: 6px solid @white;\n\t\t}\n\t}\n\ttable {\n\t\tmargin: 0;\n\t\t-webkit-touch-callout: none;\n\t\t-webkit-user-select: none;\n\t\t-khtml-user-select: none;\n\t\t-moz-user-select: none;\n\t\t-ms-user-select: none;\n\t\tuser-select: none;\n\t}\n\ttd, th {\n\t\ttext-align: center;\n\t\twidth: 20px;\n\t\theight: 20px;\n\t\t.border-radius(4px);\n\n\t\tborder: none;\n\t}\n\t// Inline display inside a table presents some problems with\n\t// border and background colors.\n\t.table-striped & table tr {\n\t\ttd, th {\n\t\t\tbackground-color: transparent;\n\t\t}\n\t}\n\ttable tr td {\n\t\t&.day:hover,\n\t\t&.day.focused {\n\t\t\tbackground: @grayLighter;\n\t\t\tcursor: pointer;\n\t\t}\n\t\t&.old,\n\t\t&.new {\n\t\t\tcolor: @grayLight;\n\t\t}\n\t\t&.disabled,\n\t\t&.disabled:hover {\n\t\t\tbackground: none;\n\t\t\tcolor: @grayLight;\n\t\t\tcursor: default;\n\t\t}\n\t\t&.highlighted {\n\t\t\tbackground: @infoBackground;\n\t\t\tborder-radius: 0;\n\t\t}\n\t\t&.today,\n\t\t&.today:hover,\n\t\t&.today.disabled,\n\t\t&.today.disabled:hover {\n\t\t\t@todayBackground: lighten(@orange, 30%);\n\t\t\t.buttonBackground(@todayBackground, spin(@todayBackground, 20));\n\t\t\tcolor: #000;\n\t\t}\n\t\t&.today:hover:hover { // Thank bootstrap 2.0 for this selector...\n\t\t\t// TODO: Bump min BS to 2.1, use @textColor in buttonBackground above\n\t\t\tcolor: #000;\n\t\t}\n\t\t&.today.active:hover {\n\t\t\tcolor: #fff;\n\t\t}\n\t\t&.range,\n\t\t&.range:hover,\n\t\t&.range.disabled,\n\t\t&.range.disabled:hover {\n\t\t\tbackground: @grayLighter;\n\t\t\t.border-radius(0);\n\t\t}\n\t\t&.range.today,\n\t\t&.range.today:hover,\n\t\t&.range.today.disabled,\n\t\t&.range.today.disabled:hover {\n\t\t\t@todayBackground: mix(@orange, @grayLighter, 50%);\n\t\t\t.buttonBackground(@todayBackground, spin(@todayBackground, 20));\n\t\t\t.border-radius(0);\n\t\t}\n\t\t&.selected,\n\t\t&.selected:hover,\n\t\t&.selected.disabled,\n\t\t&.selected.disabled:hover {\n\t\t\t.buttonBackground(lighten(@grayLight, 10), darken(@grayLight, 10));\n\t\t\tcolor: #fff;\n\t\t\ttext-shadow: 0 -1px 0 rgba(0,0,0,.25);\n\t\t}\n\t\t&.active,\n\t\t&.active:hover,\n\t\t&.active.disabled,\n\t\t&.active.disabled:hover {\n\t\t\t.buttonBackground(@btnPrimaryBackground, spin(@btnPrimaryBackground, 20));\n\t\t\tcolor: #fff;\n\t\t\ttext-shadow: 0 -1px 0 rgba(0,0,0,.25);\n\t\t}\n\t\tspan {\n\t\t\tdisplay: block;\n\t\t\twidth: 23%;\n\t\t\theight: 54px;\n\t\t\tline-height: 54px;\n\t\t\tfloat: left;\n\t\t\tmargin: 1%;\n\t\t\tcursor: pointer;\n\t\t\t.border-radius(4px);\n\t\t\t&:hover,\n\t\t\t&.focused {\n\t\t\t\tbackground: @grayLighter;\n\t\t\t}\n\t\t\t&.disabled,\n\t\t\t&.disabled:hover {\n\t\t\t\tbackground: none;\n\t\t\t\tcolor: @grayLight;\n\t\t\t\tcursor: default;\n\t\t\t}\n\t\t\t&.active,\n\t\t\t&.active:hover,\n\t\t\t&.active.disabled,\n\t\t\t&.active.disabled:hover {\n\t\t\t\t.buttonBackground(@btnPrimaryBackground, spin(@btnPrimaryBackground, 20));\n\t\t\t\tcolor: #fff;\n\t\t\t\ttext-shadow: 0 -1px 0 rgba(0,0,0,.25);\n\t\t\t}\n\t\t\t&.old,\n\t\t\t&.new {\n\t\t\t\tcolor: @grayLight;\n\t\t\t}\n\t\t}\n\t}\n\n\t.datepicker-switch {\n\t\twidth: 145px;\n\t}\n\n\t.datepicker-switch,\n\t.prev,\n\t.next,\n\ttfoot tr th {\n\t\tcursor: pointer;\n\t\t&:hover {\n\t\t\tbackground: @grayLighter;\n\t\t}\n\t}\n\n\t.prev, .next {\n\t\t&.disabled {\n\t\t\tvisibility: hidden;\n\t\t}\n\t}\n\n\t// Basic styling for calendar-week cells\n\t.cw {\n\t\tfont-size: 10px;\n\t\twidth: 12px;\n\t\tpadding: 0 2px 0 5px;\n\t\tvertical-align: middle;\n\t}\n}\n.input-append,\n.input-prepend {\n\t&.date .add-on {\n\t\tcursor: pointer;\n\n\t\ti {\n\t\t\tmargin-top: 3px;\n\t\t}\n\t}\n}\n.input-daterange {\n\tinput {\n\t\ttext-align:center;\n\t}\n\tinput:first-child {\n\t\t.border-radius(3px 0 0 3px);\n\t}\n\tinput:last-child {\n\t\t.border-radius(0 3px 3px 0);\n\t}\n\t.add-on {\n\t\tdisplay: inline-block;\n\t\twidth: auto;\n\t\tmin-width: 16px;\n\t\theight: @baseLineHeight;\n\t\tpadding: 4px 5px;\n\t\tfont-weight: normal;\n\t\tline-height: @baseLineHeight;\n\t\ttext-align: center;\n\t\ttext-shadow: 0 1px 0 @white;\n\t\tvertical-align: middle;\n\t\tbackground-color: @grayLighter;\n\t\tborder: 1px solid #ccc;\n\t\tmargin-left: -5px;\n\t\tmargin-right: -5px;\n\t}\n}\n","// Datepicker .less buildfile. Includes select mixins/variables from bootstrap\n// and imports the included datepicker.less to output a minimal datepicker.css\n//\n// Usage:\n// lessc build.less datepicker.css\n//\n// Variables and mixins copied from bootstrap 2.0.2\n\n// Variables\n@grayLight: #999;\n@grayLighter: #eee;\n@white: #fff;\n@linkColor: #08c;\n@btnPrimaryBackground: @linkColor;\n@orange: #f89406;\n@infoBackground: #d9edf7;\n@baseLineHeight: 18px;\n@baseBorderRadius: 4px;\n\n// Mixins\n\n// Border Radius\n.border-radius(@radius: 5px) {\n -webkit-border-radius: @radius;\n -moz-border-radius: @radius;\n border-radius: @radius;\n}\n\n// Button backgrounds\n.buttonBackground(@startColor, @endColor) {\n .gradientBar(@startColor, @endColor);\n .reset-filter();\n &:hover, &:active, &.active, &.disabled, &[disabled] {\n background-color: @endColor;\n }\n &:active,\n &.active {\n background-color: darken(@endColor, 10%) e(\"\\9\");\n }\n}\n\n// Reset filters for IE\n.reset-filter() {\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n}\n\n// Gradient Bar Colors for buttons and alerts\n.gradientBar(@primaryColor, @secondaryColor) {\n #gradient > .vertical(@primaryColor, @secondaryColor);\n border-color: @secondaryColor @secondaryColor darken(@secondaryColor, 15%);\n border-color: rgba(0,0,0,.1) rgba(0,0,0,.1) fadein(rgba(0,0,0,.1), 15%);\n}\n\n// Gradients\n#gradient {\n .vertical(@startColor: #555, @endColor: #333) {\n background-color: mix(@startColor, @endColor, 60%);\n background-image: -moz-linear-gradient(to bottom, @startColor, @endColor); // FF 3.6+\n background-image: -ms-linear-gradient(to bottom, @startColor, @endColor); // IE10\n background-image: -webkit-gradient(linear, 0 0, 0 100%, from(@startColor), to(@endColor)); // Safari 4+, Chrome 2+\n background-image: -webkit-linear-gradient(to bottom, @startColor, @endColor); // Safari 5.1+, Chrome 10+\n background-image: -o-linear-gradient(to bottom, @startColor, @endColor); // Opera 11.10\n background-image: linear-gradient(to bottom, @startColor, @endColor); // The standard\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",@startColor,@endColor)); // IE9 and down\n }\n}\n\n@import \"../less/datepicker.less\";\n"]} \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.css deleted file mode 100644 index eb681513fb..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.css +++ /dev/null @@ -1,7 +0,0 @@ -/*! - * Datepicker for Bootstrap v1.9.0 (https://github.com/uxsolutions/bootstrap-datepicker) - * - * Licensed under the Apache License v2.0 (http://www.apache.org/licenses/LICENSE-2.0) - */ - -.datepicker{padding:4px;-webkit-border-radius:4px;-moz-border-radius:4px;border-radius:4px;direction:ltr}.datepicker-inline{width:220px}.datepicker-rtl{direction:rtl}.datepicker-rtl.dropdown-menu{left:auto}.datepicker-rtl table tr td span{float:right}.datepicker-dropdown{top:0;left:0}.datepicker-dropdown:before{content:'';display:inline-block;border-left:7px solid transparent;border-right:7px solid transparent;border-bottom:7px solid #999;border-top:0;border-bottom-color:rgba(0,0,0,.2);position:absolute}.datepicker-dropdown:after{content:'';display:inline-block;border-left:6px solid transparent;border-right:6px solid transparent;border-bottom:6px solid #fff;border-top:0;position:absolute}.datepicker-dropdown.datepicker-orient-left:before{left:6px}.datepicker-dropdown.datepicker-orient-left:after{left:7px}.datepicker-dropdown.datepicker-orient-right:before{right:6px}.datepicker-dropdown.datepicker-orient-right:after{right:7px}.datepicker-dropdown.datepicker-orient-bottom:before{top:-7px}.datepicker-dropdown.datepicker-orient-bottom:after{top:-6px}.datepicker-dropdown.datepicker-orient-top:before{bottom:-7px;border-bottom:0;border-top:7px solid #999}.datepicker-dropdown.datepicker-orient-top:after{bottom:-6px;border-bottom:0;border-top:6px solid #fff}.datepicker table{margin:0;-webkit-touch-callout:none;-webkit-user-select:none;-khtml-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.datepicker td,.datepicker th{text-align:center;width:20px;height:20px;-webkit-border-radius:4px;-moz-border-radius:4px;border-radius:4px;border:none}.table-striped .datepicker table tr td,.table-striped .datepicker table tr th{background-color:transparent}.datepicker table tr td.day.focused,.datepicker table tr td.day:hover{background:#eee;cursor:pointer}.datepicker table tr td.new,.datepicker table tr td.old{color:#999}.datepicker table tr td.disabled,.datepicker table tr td.disabled:hover{background:0 0;color:#999;cursor:default}.datepicker table tr td.highlighted{background:#d9edf7;border-radius:0}.datepicker table tr td.today,.datepicker table tr td.today.disabled,.datepicker table tr td.today.disabled:hover,.datepicker table tr td.today:hover{background-color:#fde19a;background-image:-moz-linear-gradient(to bottom,#fdd49a,#fdf59a);background-image:-ms-linear-gradient(to bottom,#fdd49a,#fdf59a);background-image:-webkit-gradient(linear,0 0,0 100%,from(#fdd49a),to(#fdf59a));background-image:-webkit-linear-gradient(to bottom,#fdd49a,#fdf59a);background-image:-o-linear-gradient(to bottom,#fdd49a,#fdf59a);background-image:linear-gradient(to bottom,#fdd49a,#fdf59a);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fdd49a', endColorstr='#fdf59a', GradientType=0);border-color:#fdf59a #fdf59a #fbed50;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);color:#000}.datepicker table tr td.today.active,.datepicker table tr td.today.disabled,.datepicker table tr td.today.disabled.active,.datepicker table tr td.today.disabled.disabled,.datepicker table tr td.today.disabled:active,.datepicker table tr td.today.disabled:hover,.datepicker table tr td.today.disabled:hover.active,.datepicker table tr td.today.disabled:hover.disabled,.datepicker table tr td.today.disabled:hover:active,.datepicker table tr td.today.disabled:hover:hover,.datepicker table tr td.today.disabled:hover[disabled],.datepicker table tr td.today.disabled[disabled],.datepicker table tr td.today:active,.datepicker table tr td.today:hover,.datepicker table tr td.today:hover.active,.datepicker table tr td.today:hover.disabled,.datepicker table tr td.today:hover:active,.datepicker table tr td.today:hover:hover,.datepicker table tr td.today:hover[disabled],.datepicker table tr td.today[disabled]{background-color:#fdf59a}.datepicker table tr td.today.active,.datepicker table tr td.today.disabled.active,.datepicker table tr td.today.disabled:active,.datepicker table tr td.today.disabled:hover.active,.datepicker table tr td.today.disabled:hover:active,.datepicker table tr td.today:active,.datepicker table tr td.today:hover.active,.datepicker table tr td.today:hover:active{background-color:#fbf069\9}.datepicker table tr td.today:hover:hover{color:#000}.datepicker table tr td.today.active:hover{color:#fff}.datepicker table tr td.range,.datepicker table tr td.range.disabled,.datepicker table tr td.range.disabled:hover,.datepicker table tr td.range:hover{background:#eee;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0}.datepicker table tr td.range.today,.datepicker table tr td.range.today.disabled,.datepicker table tr td.range.today.disabled:hover,.datepicker table tr td.range.today:hover{background-color:#f3d17a;background-image:-moz-linear-gradient(to bottom,#f3c17a,#f3e97a);background-image:-ms-linear-gradient(to bottom,#f3c17a,#f3e97a);background-image:-webkit-gradient(linear,0 0,0 100%,from(#f3c17a),to(#f3e97a));background-image:-webkit-linear-gradient(to bottom,#f3c17a,#f3e97a);background-image:-o-linear-gradient(to bottom,#f3c17a,#f3e97a);background-image:linear-gradient(to bottom,#f3c17a,#f3e97a);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#f3c17a', endColorstr='#f3e97a', GradientType=0);border-color:#f3e97a #f3e97a #edde34;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);-webkit-border-radius:0;-moz-border-radius:0;border-radius:0}.datepicker table tr td.range.today.active,.datepicker table tr td.range.today.disabled,.datepicker table tr td.range.today.disabled.active,.datepicker table tr td.range.today.disabled.disabled,.datepicker table tr td.range.today.disabled:active,.datepicker table tr td.range.today.disabled:hover,.datepicker table tr td.range.today.disabled:hover.active,.datepicker table tr td.range.today.disabled:hover.disabled,.datepicker table tr td.range.today.disabled:hover:active,.datepicker table tr td.range.today.disabled:hover:hover,.datepicker table tr td.range.today.disabled:hover[disabled],.datepicker table tr td.range.today.disabled[disabled],.datepicker table tr td.range.today:active,.datepicker table tr td.range.today:hover,.datepicker table tr td.range.today:hover.active,.datepicker table tr td.range.today:hover.disabled,.datepicker table tr td.range.today:hover:active,.datepicker table tr td.range.today:hover:hover,.datepicker table tr td.range.today:hover[disabled],.datepicker table tr td.range.today[disabled]{background-color:#f3e97a}.datepicker table tr td.range.today.active,.datepicker table tr td.range.today.disabled.active,.datepicker table tr td.range.today.disabled:active,.datepicker table tr td.range.today.disabled:hover.active,.datepicker table tr td.range.today.disabled:hover:active,.datepicker table tr td.range.today:active,.datepicker table tr td.range.today:hover.active,.datepicker table tr td.range.today:hover:active{background-color:#efe24b\9}.datepicker table tr td.selected,.datepicker table tr td.selected.disabled,.datepicker table tr td.selected.disabled:hover,.datepicker table tr td.selected:hover{background-color:#9e9e9e;background-image:-moz-linear-gradient(to bottom,#b3b3b3,grey);background-image:-ms-linear-gradient(to bottom,#b3b3b3,grey);background-image:-webkit-gradient(linear,0 0,0 100%,from(#b3b3b3),to(grey));background-image:-webkit-linear-gradient(to bottom,#b3b3b3,grey);background-image:-o-linear-gradient(to bottom,#b3b3b3,grey);background-image:linear-gradient(to bottom,#b3b3b3,grey);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#b3b3b3', endColorstr='#808080', GradientType=0);border-color:grey grey #595959;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);color:#fff;text-shadow:0 -1px 0 rgba(0,0,0,.25)}.datepicker table tr td.selected.active,.datepicker table tr td.selected.disabled,.datepicker table tr td.selected.disabled.active,.datepicker table tr td.selected.disabled.disabled,.datepicker table tr td.selected.disabled:active,.datepicker table tr td.selected.disabled:hover,.datepicker table tr td.selected.disabled:hover.active,.datepicker table tr td.selected.disabled:hover.disabled,.datepicker table tr td.selected.disabled:hover:active,.datepicker table tr td.selected.disabled:hover:hover,.datepicker table tr td.selected.disabled:hover[disabled],.datepicker table tr td.selected.disabled[disabled],.datepicker table tr td.selected:active,.datepicker table tr td.selected:hover,.datepicker table tr td.selected:hover.active,.datepicker table tr td.selected:hover.disabled,.datepicker table tr td.selected:hover:active,.datepicker table tr td.selected:hover:hover,.datepicker table tr td.selected:hover[disabled],.datepicker table tr td.selected[disabled]{background-color:grey}.datepicker table tr td.selected.active,.datepicker table tr td.selected.disabled.active,.datepicker table tr td.selected.disabled:active,.datepicker table tr td.selected.disabled:hover.active,.datepicker table tr td.selected.disabled:hover:active,.datepicker table tr td.selected:active,.datepicker table tr td.selected:hover.active,.datepicker table tr td.selected:hover:active{background-color:#666\9}.datepicker table tr td.active,.datepicker table tr td.active.disabled,.datepicker table tr td.active.disabled:hover,.datepicker table tr td.active:hover{background-color:#006dcc;background-image:-moz-linear-gradient(to bottom,#08c,#04c);background-image:-ms-linear-gradient(to bottom,#08c,#04c);background-image:-webkit-gradient(linear,0 0,0 100%,from(#08c),to(#04c));background-image:-webkit-linear-gradient(to bottom,#08c,#04c);background-image:-o-linear-gradient(to bottom,#08c,#04c);background-image:linear-gradient(to bottom,#08c,#04c);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#08c', endColorstr='#0044cc', GradientType=0);border-color:#04c #04c #002a80;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);color:#fff;text-shadow:0 -1px 0 rgba(0,0,0,.25)}.datepicker table tr td.active.active,.datepicker table tr td.active.disabled,.datepicker table tr td.active.disabled.active,.datepicker table tr td.active.disabled.disabled,.datepicker table tr td.active.disabled:active,.datepicker table tr td.active.disabled:hover,.datepicker table tr td.active.disabled:hover.active,.datepicker table tr td.active.disabled:hover.disabled,.datepicker table tr td.active.disabled:hover:active,.datepicker table tr td.active.disabled:hover:hover,.datepicker table tr td.active.disabled:hover[disabled],.datepicker table tr td.active.disabled[disabled],.datepicker table tr td.active:active,.datepicker table tr td.active:hover,.datepicker table tr td.active:hover.active,.datepicker table tr td.active:hover.disabled,.datepicker table tr td.active:hover:active,.datepicker table tr td.active:hover:hover,.datepicker table tr td.active:hover[disabled],.datepicker table tr td.active[disabled]{background-color:#04c}.datepicker table tr td.active.active,.datepicker table tr td.active.disabled.active,.datepicker table tr td.active.disabled:active,.datepicker table tr td.active.disabled:hover.active,.datepicker table tr td.active.disabled:hover:active,.datepicker table tr td.active:active,.datepicker table tr td.active:hover.active,.datepicker table tr td.active:hover:active{background-color:#039\9}.datepicker table tr td span{display:block;width:23%;height:54px;line-height:54px;float:left;margin:1%;cursor:pointer;-webkit-border-radius:4px;-moz-border-radius:4px;border-radius:4px}.datepicker table tr td span.focused,.datepicker table tr td span:hover{background:#eee}.datepicker table tr td span.disabled,.datepicker table tr td span.disabled:hover{background:0 0;color:#999;cursor:default}.datepicker table tr td span.active,.datepicker table tr td span.active.disabled,.datepicker table tr td span.active.disabled:hover,.datepicker table tr td span.active:hover{background-color:#006dcc;background-image:-moz-linear-gradient(to bottom,#08c,#04c);background-image:-ms-linear-gradient(to bottom,#08c,#04c);background-image:-webkit-gradient(linear,0 0,0 100%,from(#08c),to(#04c));background-image:-webkit-linear-gradient(to bottom,#08c,#04c);background-image:-o-linear-gradient(to bottom,#08c,#04c);background-image:linear-gradient(to bottom,#08c,#04c);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#08c', endColorstr='#0044cc', GradientType=0);border-color:#04c #04c #002a80;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);color:#fff;text-shadow:0 -1px 0 rgba(0,0,0,.25)}.datepicker table tr td span.active.active,.datepicker table tr td span.active.disabled,.datepicker table tr td span.active.disabled.active,.datepicker table tr td span.active.disabled.disabled,.datepicker table tr td span.active.disabled:active,.datepicker table tr td span.active.disabled:hover,.datepicker table tr td span.active.disabled:hover.active,.datepicker table tr td span.active.disabled:hover.disabled,.datepicker table tr td span.active.disabled:hover:active,.datepicker table tr td span.active.disabled:hover:hover,.datepicker table tr td span.active.disabled:hover[disabled],.datepicker table tr td span.active.disabled[disabled],.datepicker table tr td span.active:active,.datepicker table tr td span.active:hover,.datepicker table tr td span.active:hover.active,.datepicker table tr td span.active:hover.disabled,.datepicker table tr td span.active:hover:active,.datepicker table tr td span.active:hover:hover,.datepicker table tr td span.active:hover[disabled],.datepicker table tr td span.active[disabled]{background-color:#04c}.datepicker table tr td span.active.active,.datepicker table tr td span.active.disabled.active,.datepicker table tr td span.active.disabled:active,.datepicker table tr td span.active.disabled:hover.active,.datepicker table tr td span.active.disabled:hover:active,.datepicker table tr td span.active:active,.datepicker table tr td span.active:hover.active,.datepicker table tr td span.active:hover:active{background-color:#039\9}.datepicker table tr td span.new,.datepicker table tr td span.old{color:#999}.datepicker .datepicker-switch{width:145px}.datepicker .datepicker-switch,.datepicker .next,.datepicker .prev,.datepicker tfoot tr th{cursor:pointer}.datepicker .datepicker-switch:hover,.datepicker .next:hover,.datepicker .prev:hover,.datepicker tfoot tr th:hover{background:#eee}.datepicker .next.disabled,.datepicker .prev.disabled{visibility:hidden}.datepicker .cw{font-size:10px;width:12px;padding:0 2px 0 5px;vertical-align:middle}.input-append.date .add-on,.input-prepend.date .add-on{cursor:pointer}.input-append.date .add-on i,.input-prepend.date .add-on i{margin-top:3px}.input-daterange input{text-align:center}.input-daterange input:first-child{-webkit-border-radius:3px 0 0 3px;-moz-border-radius:3px 0 0 3px;border-radius:3px 0 0 3px}.input-daterange input:last-child{-webkit-border-radius:0 3px 3px 0;-moz-border-radius:0 3px 3px 0;border-radius:0 3px 3px 0}.input-daterange .add-on{display:inline-block;width:auto;min-width:16px;height:18px;padding:4px 5px;font-weight:400;line-height:18px;text-align:center;text-shadow:0 1px 0 #fff;vertical-align:middle;background-color:#eee;border:1px solid #ccc;margin-left:-5px;margin-right:-5px} \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.js deleted file mode 100644 index 8800106e8f..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/bootstrap-datepicker.min.js +++ /dev/null @@ -1,8 +0,0 @@ -/*! - * Datepicker for Bootstrap v1.9.0 (https://github.com/uxsolutions/bootstrap-datepicker) - * - * Licensed under the Apache License v2.0 (http://www.apache.org/licenses/LICENSE-2.0) - */ - -!function(a){"function"==typeof define&&define.amd?define(["jquery"],a):a("object"==typeof exports?require("jquery"):jQuery)}(function(a,b){function c(){return new Date(Date.UTC.apply(Date,arguments))}function d(){var a=new Date;return c(a.getFullYear(),a.getMonth(),a.getDate())}function e(a,b){return a.getUTCFullYear()===b.getUTCFullYear()&&a.getUTCMonth()===b.getUTCMonth()&&a.getUTCDate()===b.getUTCDate()}function f(c,d){return function(){return d!==b&&a.fn.datepicker.deprecated(d),this[c].apply(this,arguments)}}function g(a){return a&&!isNaN(a.getTime())}function h(b,c){function d(a,b){return b.toLowerCase()}var e,f=a(b).data(),g={},h=new RegExp("^"+c.toLowerCase()+"([A-Z])");c=new RegExp("^"+c.toLowerCase());for(var i in f)c.test(i)&&(e=i.replace(h,d),g[e]=f[i]);return g}function i(b){var c={};if(q[b]||(b=b.split("-")[0],q[b])){var d=q[b];return a.each(p,function(a,b){b in d&&(c[b]=d[b])}),c}}var j=function(){var b={get:function(a){return this.slice(a)[0]},contains:function(a){for(var b=a&&a.valueOf(),c=0,d=this.length;c]/g)||[]).length<=0)return!0;return a(c).length>0}catch(a){return!1}},_process_options:function(b){this._o=a.extend({},this._o,b);var e=this.o=a.extend({},this._o),f=e.language;q[f]||(f=f.split("-")[0],q[f]||(f=o.language)),e.language=f,e.startView=this._resolveViewName(e.startView),e.minViewMode=this._resolveViewName(e.minViewMode),e.maxViewMode=this._resolveViewName(e.maxViewMode),e.startView=Math.max(this.o.minViewMode,Math.min(this.o.maxViewMode,e.startView)),!0!==e.multidate&&(e.multidate=Number(e.multidate)||!1,!1!==e.multidate&&(e.multidate=Math.max(0,e.multidate))),e.multidateSeparator=String(e.multidateSeparator),e.weekStart%=7,e.weekEnd=(e.weekStart+6)%7;var g=r.parseFormat(e.format);e.startDate!==-1/0&&(e.startDate?e.startDate instanceof Date?e.startDate=this._local_to_utc(this._zero_time(e.startDate)):e.startDate=r.parseDate(e.startDate,g,e.language,e.assumeNearbyYear):e.startDate=-1/0),e.endDate!==1/0&&(e.endDate?e.endDate instanceof Date?e.endDate=this._local_to_utc(this._zero_time(e.endDate)):e.endDate=r.parseDate(e.endDate,g,e.language,e.assumeNearbyYear):e.endDate=1/0),e.daysOfWeekDisabled=this._resolveDaysOfWeek(e.daysOfWeekDisabled||[]),e.daysOfWeekHighlighted=this._resolveDaysOfWeek(e.daysOfWeekHighlighted||[]),e.datesDisabled=e.datesDisabled||[],a.isArray(e.datesDisabled)||(e.datesDisabled=e.datesDisabled.split(",")),e.datesDisabled=a.map(e.datesDisabled,function(a){return r.parseDate(a,g,e.language,e.assumeNearbyYear)});var h=String(e.orientation).toLowerCase().split(/\s+/g),i=e.orientation.toLowerCase();if(h=a.grep(h,function(a){return/^auto|left|right|top|bottom$/.test(a)}),e.orientation={x:"auto",y:"auto"},i&&"auto"!==i)if(1===h.length)switch(h[0]){case"top":case"bottom":e.orientation.y=h[0];break;case"left":case"right":e.orientation.x=h[0]}else i=a.grep(h,function(a){return/^left|right$/.test(a)}),e.orientation.x=i[0]||"auto",i=a.grep(h,function(a){return/^top|bottom$/.test(a)}),e.orientation.y=i[0]||"auto";else;if(e.defaultViewDate instanceof Date||"string"==typeof e.defaultViewDate)e.defaultViewDate=r.parseDate(e.defaultViewDate,g,e.language,e.assumeNearbyYear);else if(e.defaultViewDate){var j=e.defaultViewDate.year||(new Date).getFullYear(),k=e.defaultViewDate.month||0,l=e.defaultViewDate.day||1;e.defaultViewDate=c(j,k,l)}else e.defaultViewDate=d()},_applyEvents:function(a){for(var c,d,e,f=0;fe?(this.picker.addClass("datepicker-orient-right"),m+=l-b):this.o.rtl?this.picker.addClass("datepicker-orient-right"):this.picker.addClass("datepicker-orient-left");var o,p=this.o.orientation.y;if("auto"===p&&(o=-f+n-c,p=o<0?"bottom":"top"),this.picker.addClass("datepicker-orient-"+p),"top"===p?n-=c+parseInt(this.picker.css("padding-top")):n+=k,this.o.rtl){var q=e-(m+l);this.picker.css({top:n,right:q,zIndex:i})}else this.picker.css({top:n,left:m,zIndex:i});return this},_allow_update:!0,update:function(){if(!this._allow_update)return this;var b=this.dates.copy(),c=[],d=!1;return arguments.length?(a.each(arguments,a.proxy(function(a,b){b instanceof Date&&(b=this._local_to_utc(b)),c.push(b)},this)),d=!0):(c=this.isInput?this.element.val():this.element.data("date")||this.inputField.val(),c=c&&this.o.multidate?c.split(this.o.multidateSeparator):[c],delete this.element.data().date),c=a.map(c,a.proxy(function(a){return r.parseDate(a,this.o.format,this.o.language,this.o.assumeNearbyYear)},this)),c=a.grep(c,a.proxy(function(a){return!this.dateWithinRange(a)||!a},this),!0),this.dates.replace(c),this.o.updateViewDate&&(this.dates.length?this.viewDate=new Date(this.dates.get(-1)):this.viewDatethis.o.endDate?this.viewDate=new Date(this.o.endDate):this.viewDate=this.o.defaultViewDate),d?(this.setValue(),this.element.change()):this.dates.length&&String(b)!==String(this.dates)&&d&&(this._trigger("changeDate"),this.element.change()),!this.dates.length&&b.length&&(this._trigger("clearDate"),this.element.change()),this.fill(),this},fillDow:function(){if(this.o.showWeekDays){var b=this.o.weekStart,c="";for(this.o.calendarWeeks&&(c+=' ');b";c+="",this.picker.find(".datepicker-days thead").append(c)}},fillMonths:function(){for(var a,b=this._utc_to_local(this.viewDate),c="",d=0;d<12;d++)a=b&&b.getMonth()===d?" focused":"",c+=''+q[this.o.language].monthsShort[d]+"";this.picker.find(".datepicker-months td").html(c)},setRange:function(b){b&&b.length?this.range=a.map(b,function(a){return a.valueOf()}):delete this.range,this.fill()},getClassNames:function(b){var c=[],f=this.viewDate.getUTCFullYear(),g=this.viewDate.getUTCMonth(),h=d();return b.getUTCFullYear()f||b.getUTCFullYear()===f&&b.getUTCMonth()>g)&&c.push("new"),this.focusDate&&b.valueOf()===this.focusDate.valueOf()&&c.push("focused"),this.o.todayHighlight&&e(b,h)&&c.push("today"),-1!==this.dates.contains(b)&&c.push("active"),this.dateWithinRange(b)||c.push("disabled"),this.dateIsDisabled(b)&&c.push("disabled","disabled-date"),-1!==a.inArray(b.getUTCDay(),this.o.daysOfWeekHighlighted)&&c.push("highlighted"),this.range&&(b>this.range[0]&&bh)&&j.push("disabled"),t===r&&j.push("focused"),i!==a.noop&&(l=i(new Date(t,0,1)),l===b?l={}:"boolean"==typeof l?l={enabled:l}:"string"==typeof l&&(l={classes:l}),!1===l.enabled&&j.push("disabled"),l.classes&&(j=j.concat(l.classes.split(/\s+/))),l.tooltip&&(k=l.tooltip)),m+='"+t+"";o.find(".datepicker-switch").text(p+"-"+q),o.find("td").html(m)},fill:function(){var e,f,g=new Date(this.viewDate),h=g.getUTCFullYear(),i=g.getUTCMonth(),j=this.o.startDate!==-1/0?this.o.startDate.getUTCFullYear():-1/0,k=this.o.startDate!==-1/0?this.o.startDate.getUTCMonth():-1/0,l=this.o.endDate!==1/0?this.o.endDate.getUTCFullYear():1/0,m=this.o.endDate!==1/0?this.o.endDate.getUTCMonth():1/0,n=q[this.o.language].today||q.en.today||"",o=q[this.o.language].clear||q.en.clear||"",p=q[this.o.language].titleFormat||q.en.titleFormat,s=d(),t=(!0===this.o.todayBtn||"linked"===this.o.todayBtn)&&s>=this.o.startDate&&s<=this.o.endDate&&!this.weekOfDateIsDisabled(s);if(!isNaN(h)&&!isNaN(i)){this.picker.find(".datepicker-days .datepicker-switch").text(r.formatDate(g,p,this.o.language)),this.picker.find("tfoot .today").text(n).css("display",t?"table-cell":"none"),this.picker.find("tfoot .clear").text(o).css("display",!0===this.o.clearBtn?"table-cell":"none"),this.picker.find("thead .datepicker-title").text(this.o.title).css("display","string"==typeof this.o.title&&""!==this.o.title?"table-cell":"none"),this.updateNavArrows(),this.fillMonths();var u=c(h,i,0),v=u.getUTCDate();u.setUTCDate(v-(u.getUTCDay()-this.o.weekStart+7)%7);var w=new Date(u);u.getUTCFullYear()<100&&w.setUTCFullYear(u.getUTCFullYear()),w.setUTCDate(w.getUTCDate()+42),w=w.valueOf();for(var x,y,z=[];u.valueOf()"),this.o.calendarWeeks)){var A=new Date(+u+(this.o.weekStart-x-7)%7*864e5),B=new Date(Number(A)+(11-A.getUTCDay())%7*864e5),C=new Date(Number(C=c(B.getUTCFullYear(),0,1))+(11-C.getUTCDay())%7*864e5),D=(B-C)/864e5/7+1;z.push(''+D+"")}y=this.getClassNames(u),y.push("day");var E=u.getUTCDate();this.o.beforeShowDay!==a.noop&&(f=this.o.beforeShowDay(this._utc_to_local(u)),f===b?f={}:"boolean"==typeof f?f={enabled:f}:"string"==typeof f&&(f={classes:f}),!1===f.enabled&&y.push("disabled"),f.classes&&(y=y.concat(f.classes.split(/\s+/))),f.tooltip&&(e=f.tooltip),f.content&&(E=f.content)),y=a.isFunction(a.uniqueSort)?a.uniqueSort(y):a.unique(y),z.push(''+E+""),e=null,x===this.o.weekEnd&&z.push(""),u.setUTCDate(u.getUTCDate()+1)}this.picker.find(".datepicker-days tbody").html(z.join(""));var F=q[this.o.language].monthsTitle||q.en.monthsTitle||"Months",G=this.picker.find(".datepicker-months").find(".datepicker-switch").text(this.o.maxViewMode<2?F:h).end().find("tbody span").removeClass("active");if(a.each(this.dates,function(a,b){b.getUTCFullYear()===h&&G.eq(b.getUTCMonth()).addClass("active")}),(hl)&&G.addClass("disabled"),h===j&&G.slice(0,k).addClass("disabled"),h===l&&G.slice(m+1).addClass("disabled"),this.o.beforeShowMonth!==a.noop){var H=this;a.each(G,function(c,d){var e=new Date(h,c,1),f=H.o.beforeShowMonth(e);f===b?f={}:"boolean"==typeof f?f={enabled:f}:"string"==typeof f&&(f={classes:f}),!1!==f.enabled||a(d).hasClass("disabled")||a(d).addClass("disabled"),f.classes&&a(d).addClass(f.classes),f.tooltip&&a(d).prop("title",f.tooltip)})}this._fill_yearsView(".datepicker-years","year",10,h,j,l,this.o.beforeShowYear),this._fill_yearsView(".datepicker-decades","decade",100,h,j,l,this.o.beforeShowDecade),this._fill_yearsView(".datepicker-centuries","century",1e3,h,j,l,this.o.beforeShowCentury)}},updateNavArrows:function(){if(this._allow_update){var a,b,c=new Date(this.viewDate),d=c.getUTCFullYear(),e=c.getUTCMonth(),f=this.o.startDate!==-1/0?this.o.startDate.getUTCFullYear():-1/0,g=this.o.startDate!==-1/0?this.o.startDate.getUTCMonth():-1/0,h=this.o.endDate!==1/0?this.o.endDate.getUTCFullYear():1/0,i=this.o.endDate!==1/0?this.o.endDate.getUTCMonth():1/0,j=1;switch(this.viewMode){case 4:j*=10;case 3:j*=10;case 2:j*=10;case 1:a=Math.floor(d/j)*j<=f,b=Math.floor(d/j)*j+j>h;break;case 0:a=d<=f&&e<=g,b=d>=h&&e>=i}this.picker.find(".prev").toggleClass("disabled",a),this.picker.find(".next").toggleClass("disabled",b)}},click:function(b){b.preventDefault(),b.stopPropagation();var e,f,g,h;e=a(b.target),e.hasClass("datepicker-switch")&&this.viewMode!==this.o.maxViewMode&&this.setViewMode(this.viewMode+1),e.hasClass("today")&&!e.hasClass("day")&&(this.setViewMode(0),this._setDate(d(),"linked"===this.o.todayBtn?null:"view")),e.hasClass("clear")&&this.clearDates(),e.hasClass("disabled")||(e.hasClass("month")||e.hasClass("year")||e.hasClass("decade")||e.hasClass("century"))&&(this.viewDate.setUTCDate(1),f=1,1===this.viewMode?(h=e.parent().find("span").index(e),g=this.viewDate.getUTCFullYear(),this.viewDate.setUTCMonth(h)):(h=0,g=Number(e.text()),this.viewDate.setUTCFullYear(g)),this._trigger(r.viewModes[this.viewMode-1].e,this.viewDate),this.viewMode===this.o.minViewMode?this._setDate(c(g,h,f)):(this.setViewMode(this.viewMode-1),this.fill())),this.picker.is(":visible")&&this._focused_from&&this._focused_from.focus(),delete this._focused_from},dayCellClick:function(b){var c=a(b.currentTarget),d=c.data("date"),e=new Date(d);this.o.updateViewDate&&(e.getUTCFullYear()!==this.viewDate.getUTCFullYear()&&this._trigger("changeYear",this.viewDate),e.getUTCMonth()!==this.viewDate.getUTCMonth()&&this._trigger("changeMonth",this.viewDate)),this._setDate(e)},navArrowsClick:function(b){var c=a(b.currentTarget),d=c.hasClass("prev")?-1:1;0!==this.viewMode&&(d*=12*r.viewModes[this.viewMode].navStep),this.viewDate=this.moveMonth(this.viewDate,d),this._trigger(r.viewModes[this.viewMode].e,this.viewDate),this.fill()},_toggle_multidate:function(a){var b=this.dates.contains(a);if(a||this.dates.clear(),-1!==b?(!0===this.o.multidate||this.o.multidate>1||this.o.toggleActive)&&this.dates.remove(b):!1===this.o.multidate?(this.dates.clear(),this.dates.push(a)):this.dates.push(a),"number"==typeof this.o.multidate)for(;this.dates.length>this.o.multidate;)this.dates.remove(0)},_setDate:function(a,b){b&&"date"!==b||this._toggle_multidate(a&&new Date(a)),(!b&&this.o.updateViewDate||"view"===b)&&(this.viewDate=a&&new Date(a)),this.fill(),this.setValue(),b&&"view"===b||this._trigger("changeDate"),this.inputField.trigger("change"),!this.o.autoclose||b&&"date"!==b||this.hide()},moveDay:function(a,b){var c=new Date(a);return c.setUTCDate(a.getUTCDate()+b),c},moveWeek:function(a,b){return this.moveDay(a,7*b)},moveMonth:function(a,b){if(!g(a))return this.o.defaultViewDate;if(!b)return a;var c,d,e=new Date(a.valueOf()),f=e.getUTCDate(),h=e.getUTCMonth(),i=Math.abs(b);if(b=b>0?1:-1,1===i)d=-1===b?function(){return e.getUTCMonth()===h}:function(){return e.getUTCMonth()!==c},c=h+b,e.setUTCMonth(c),c=(c+12)%12;else{for(var j=0;j0},dateWithinRange:function(a){return a>=this.o.startDate&&a<=this.o.endDate},keydown:function(a){if(!this.picker.is(":visible"))return void(40!==a.keyCode&&27!==a.keyCode||(this.show(),a.stopPropagation()));var b,c,d=!1,e=this.focusDate||this.viewDate;switch(a.keyCode){case 27:this.focusDate?(this.focusDate=null,this.viewDate=this.dates.get(-1)||this.viewDate,this.fill()):this.hide(),a.preventDefault(),a.stopPropagation();break;case 37:case 38:case 39:case 40:if(!this.o.keyboardNavigation||7===this.o.daysOfWeekDisabled.length)break;b=37===a.keyCode||38===a.keyCode?-1:1,0===this.viewMode?a.ctrlKey?(c=this.moveAvailableDate(e,b,"moveYear"))&&this._trigger("changeYear",this.viewDate):a.shiftKey?(c=this.moveAvailableDate(e,b,"moveMonth"))&&this._trigger("changeMonth",this.viewDate):37===a.keyCode||39===a.keyCode?c=this.moveAvailableDate(e,b,"moveDay"):this.weekOfDateIsDisabled(e)||(c=this.moveAvailableDate(e,b,"moveWeek")):1===this.viewMode?(38!==a.keyCode&&40!==a.keyCode||(b*=4),c=this.moveAvailableDate(e,b,"moveMonth")):2===this.viewMode&&(38!==a.keyCode&&40!==a.keyCode||(b*=4),c=this.moveAvailableDate(e,b,"moveYear")),c&&(this.focusDate=this.viewDate=c,this.setValue(),this.fill(),a.preventDefault());break;case 13:if(!this.o.forceParse)break;e=this.focusDate||this.dates.get(-1)||this.viewDate,this.o.keyboardNavigation&&(this._toggle_multidate(e),d=!0),this.focusDate=null,this.viewDate=this.dates.get(-1)||this.viewDate,this.setValue(),this.fill(),this.picker.is(":visible")&&(a.preventDefault(),a.stopPropagation(),this.o.autoclose&&this.hide());break;case 9:this.focusDate=null,this.viewDate=this.dates.get(-1)||this.viewDate,this.fill(),this.hide()}d&&(this.dates.length?this._trigger("changeDate"):this._trigger("clearDate"),this.inputField.trigger("change"))},setViewMode:function(a){this.viewMode=a,this.picker.children("div").hide().filter(".datepicker-"+r.viewModes[this.viewMode].clsName).show(),this.updateNavArrows(),this._trigger("changeViewMode",new Date(this.viewDate))}};var l=function(b,c){a.data(b,"datepicker",this),this.element=a(b),this.inputs=a.map(c.inputs,function(a){return a.jquery?a[0]:a}),delete c.inputs,this.keepEmptyValues=c.keepEmptyValues,delete c.keepEmptyValues,n.call(a(this.inputs),c).on("changeDate",a.proxy(this.dateUpdated,this)),this.pickers=a.map(this.inputs,function(b){return a.data(b,"datepicker")}),this.updateDates()};l.prototype={updateDates:function(){this.dates=a.map(this.pickers,function(a){return a.getUTCDate()}),this.updateRanges()},updateRanges:function(){var b=a.map(this.dates,function(a){return a.valueOf()});a.each(this.pickers,function(a,c){c.setRange(b)})},clearDates:function(){a.each(this.pickers,function(a,b){b.clearDates()})},dateUpdated:function(c){if(!this.updating){this.updating=!0;var d=a.data(c.target,"datepicker");if(d!==b){var e=d.getUTCDate(),f=this.keepEmptyValues,g=a.inArray(c.target,this.inputs),h=g-1,i=g+1,j=this.inputs.length;if(-1!==g){if(a.each(this.pickers,function(a,b){b.getUTCDate()||b!==d&&f||b.setUTCDate(e)}),e=0&&ethis.dates[i])for(;ithis.dates[i];)this.pickers[i++].setUTCDate(e);this.updateDates(),delete this.updating}}}},destroy:function(){a.map(this.pickers,function(a){a.destroy()}),a(this.inputs).off("changeDate",this.dateUpdated),delete this.element.data().datepicker},remove:f("destroy","Method `remove` is deprecated and will be removed in version 2.0. Use `destroy` instead")};var m=a.fn.datepicker,n=function(c){var d=Array.apply(null,arguments);d.shift();var e;if(this.each(function(){var b=a(this),f=b.data("datepicker"),g="object"==typeof c&&c;if(!f){var j=h(this,"date"),m=a.extend({},o,j,g),n=i(m.language),p=a.extend({},o,n,j,g);b.hasClass("input-daterange")||p.inputs?(a.extend(p,{inputs:p.inputs||b.find("input").toArray()}),f=new l(this,p)):f=new k(this,p),b.data("datepicker",f)}"string"==typeof c&&"function"==typeof f[c]&&(e=f[c].apply(f,d))}),e===b||e instanceof k||e instanceof l)return this;if(this.length>1)throw new Error("Using only allowed for the collection of a single element ("+c+" function)");return e};a.fn.datepicker=n;var o=a.fn.datepicker.defaults={assumeNearbyYear:!1,autoclose:!1,beforeShowDay:a.noop,beforeShowMonth:a.noop,beforeShowYear:a.noop,beforeShowDecade:a.noop,beforeShowCentury:a.noop,calendarWeeks:!1,clearBtn:!1,toggleActive:!1,daysOfWeekDisabled:[],daysOfWeekHighlighted:[],datesDisabled:[],endDate:1/0,forceParse:!0,format:"mm/dd/yyyy",keepEmptyValues:!1,keyboardNavigation:!0,language:"en",minViewMode:0,maxViewMode:4,multidate:!1,multidateSeparator:",",orientation:"auto",rtl:!1,startDate:-1/0,startView:0,todayBtn:!1,todayHighlight:!1,updateViewDate:!0,weekStart:0,disableTouchKeyboard:!1,enableOnReadonly:!0,showOnFocus:!0,zIndexOffset:10,container:"body",immediateUpdates:!1,title:"",templates:{leftArrow:"«",rightArrow:"»"},showWeekDays:!0},p=a.fn.datepicker.locale_opts=["format","rtl","weekStart"];a.fn.datepicker.Constructor=k;var q=a.fn.datepicker.dates={en:{days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",clear:"Clear",titleFormat:"MM yyyy"}},r={viewModes:[{names:["days","month"],clsName:"days",e:"changeMonth"},{names:["months","year"],clsName:"months",e:"changeYear",navStep:1},{names:["years","decade"],clsName:"years",e:"changeDecade",navStep:10},{names:["decades","century"],clsName:"decades",e:"changeCentury",navStep:100},{names:["centuries","millennium"],clsName:"centuries",e:"changeMillennium",navStep:1e3}],validParts:/dd?|DD?|mm?|MM?|yy(?:yy)?/g,nonpunctuation:/[^ -\/:-@\u5e74\u6708\u65e5\[-`{-~\t\n\r]+/g,parseFormat:function(a){if("function"==typeof a.toValue&&"function"==typeof a.toDisplay)return a;var b=a.replace(this.validParts,"\0").split("\0"),c=a.match(this.validParts);if(!b||!b.length||!c||0===c.length)throw new Error("Invalid date format.");return{separators:b,parts:c}},parseDate:function(c,e,f,g){function h(a,b){return!0===b&&(b=10),a<100&&(a+=2e3)>(new Date).getFullYear()+b&&(a-=100),a}function i(){var a=this.slice(0,j[n].length),b=j[n].slice(0,a.length);return a.toLowerCase()===b.toLowerCase()}if(!c)return b;if(c instanceof Date)return c;if("string"==typeof e&&(e=r.parseFormat(e)),e.toValue)return e.toValue(c,e,f);var j,l,m,n,o,p={d:"moveDay",m:"moveMonth",w:"moveWeek",y:"moveYear"},s={yesterday:"-1d",today:"+0d",tomorrow:"+1d"};if(c in s&&(c=s[c]),/^[\-+]\d+[dmwy]([\s,]+[\-+]\d+[dmwy])*$/i.test(c)){for(j=c.match(/([\-+]\d+)([dmwy])/gi),c=new Date,n=0;n'+o.templates.leftArrow+''+o.templates.rightArrow+"",contTemplate:'',footTemplate:''};r.template='
'+r.headTemplate+""+r.footTemplate+'
'+r.headTemplate+r.contTemplate+r.footTemplate+'
'+r.headTemplate+r.contTemplate+r.footTemplate+'
'+r.headTemplate+r.contTemplate+r.footTemplate+'
'+r.headTemplate+r.contTemplate+r.footTemplate+"
",a.fn.datepicker.DPGlobal=r,a.fn.datepicker.noConflict=function(){return a.fn.datepicker=m,this},a.fn.datepicker.version="1.9.0",a.fn.datepicker.deprecated=function(a){var b=window.console;b&&b.warn&&b.warn("DEPRECATED: "+a)},a(document).on("focus.datepicker.data-api click.datepicker.data-api",'[data-provide="datepicker"]',function(b){var c=a(this);c.data("datepicker")||(b.preventDefault(),n.call(c,"show"))}),a(function(){n.call(a('[data-provide="datepicker-inline"]'))})}); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker-en-CA.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker-en-CA.min.js deleted file mode 100644 index 0aab38f3a4..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker-en-CA.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-CA"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:0,format:"yyyy-mm-dd"},a.fn.datepicker.deprecated("This filename doesn't follow the convention, use bootstrap-datepicker.en-CA.js instead.")}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar-tn.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar-tn.min.js deleted file mode 100644 index 9d70dc2fa3..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar-tn.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["ar-tn"]={days:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت","الأحد"],daysShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت","أحد"],daysMin:["ح","ن","ث","ع","خ","ج","س","ح"],months:["جانفي","فيفري","مارس","أفريل","ماي","جوان","جويليه","أوت","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthsShort:["جانفي","فيفري","مارس","أفريل","ماي","جوان","جويليه","أوت","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],today:"هذا اليوم",rtl:!0}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar.min.js deleted file mode 100644 index ece41af725..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ar.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ar={days:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت","الأحد"],daysShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت","أحد"],daysMin:["ح","ن","ث","ع","خ","ج","س","ح"],months:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthsShort:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],today:"هذا اليوم",rtl:!0}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.az.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.az.min.js deleted file mode 100644 index aa1edbf4f8..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.az.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.az={days:["Bazar","Bazar ertəsi","Çərşənbə axşamı","Çərşənbə","Cümə axşamı","Cümə","Şənbə"],daysShort:["B.","B.e","Ç.a","Ç.","C.a","C.","Ş."],daysMin:["B.","B.e","Ç.a","Ç.","C.a","C.","Ş."],months:["Yanvar","Fevral","Mart","Aprel","May","İyun","İyul","Avqust","Sentyabr","Oktyabr","Noyabr","Dekabr"],monthsShort:["Yan","Fev","Mar","Apr","May","İyun","İyul","Avq","Sen","Okt","Noy","Dek"],today:"Bu gün",weekStart:1,clear:"Təmizlə",monthsTitle:"Aylar"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bg.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bg.min.js deleted file mode 100644 index 28e8b22dcf..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bg.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.bg={days:["Неделя","Понеделник","Вторник","Сряда","Четвъртък","Петък","Събота"],daysShort:["Нед","Пон","Вто","Сря","Чет","Пет","Съб"],daysMin:["Н","П","В","С","Ч","П","С"],months:["Януари","Февруари","Март","Април","Май","Юни","Юли","Август","Септември","Октомври","Ноември","Декември"],monthsShort:["Ян","Фев","Мар","Апр","Май","Юни","Юли","Авг","Сеп","Окт","Ное","Дек"],today:"днес"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bm.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bm.min.js deleted file mode 100644 index e0796a3ba7..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bm.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.bm={days:["Kari","Ntɛnɛn","Tarata","Araba","Alamisa","Juma","Sibiri"],daysShort:["Kar","Ntɛ","Tar","Ara","Ala","Jum","Sib"],daysMin:["Ka","Nt","Ta","Ar","Al","Ju","Si"],months:["Zanwuyekalo","Fewuruyekalo","Marisikalo","Awirilikalo","Mɛkalo","Zuwɛnkalo","Zuluyekalo","Utikalo","Sɛtanburukalo","ɔkutɔburukalo","Nowanburukalo","Desanburukalo"],monthsShort:["Zan","Few","Mar","Awi","Mɛ","Zuw","Zul","Uti","Sɛt","ɔku","Now","Des"],today:"Bi",monthsTitle:"Kalo",clear:"Ka jɔsi",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bn.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bn.min.js deleted file mode 100644 index f67b5e26e7..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bn.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.bn={days:["রবিবার","সোমবার","মঙ্গলবার","বুধবার","বৃহস্পতিবার","শুক্রবার","শনিবার"],daysShort:["রবিবার","সোমবার","মঙ্গলবার","বুধবার","বৃহস্পতিবার","শুক্রবার","শনিবার"],daysMin:["রবি","সোম","মঙ্গল","বুধ","বৃহস্পতি","শুক্র","শনি"],months:["জানুয়ারী","ফেব্রুয়ারি","মার্চ","এপ্রিল","মে","জুন","জুলাই","অগাস্ট","সেপ্টেম্বর","অক্টোবর","নভেম্বর","ডিসেম্বর"],monthsShort:["জানুয়ারী","ফেব্রুয়ারি","মার্চ","এপ্রিল","মে","জুন","জুলাই","অগাস্ট","সেপ্টেম্বর","অক্টোবর","নভেম্বর","ডিসেম্বর"],today:"আজ",monthsTitle:"মাস",clear:"পরিষ্কার",weekStart:0,format:"mm/dd/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.br.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.br.min.js deleted file mode 100644 index af3e3bd0af..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.br.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.br={days:["Sul","Lun","Meurzh","Merc'her","Yaou","Gwener","Sadorn"],daysShort:["Sul","Lun","Meu.","Mer.","Yao.","Gwe.","Sad."],daysMin:["Su","L","Meu","Mer","Y","G","Sa"],months:["Genver","C'hwevrer","Meurzh","Ebrel","Mae","Mezheven","Gouere","Eost","Gwengolo","Here","Du","Kerzu"],monthsShort:["Genv.","C'hw.","Meur.","Ebre.","Mae","Mezh.","Goue.","Eost","Gwen.","Here","Du","Kerz."],today:"Hiziv",monthsTitle:"Miz",clear:"Dilemel",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bs.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bs.min.js deleted file mode 100644 index cfb06fde79..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.bs.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.bs={days:["Nedjelja","Ponedjeljak","Utorak","Srijeda","Četvrtak","Petak","Subota"],daysShort:["Ned","Pon","Uto","Sri","Čet","Pet","Sub"],daysMin:["N","Po","U","Sr","Č","Pe","Su"],months:["Januar","Februar","Mart","April","Maj","Juni","Juli","August","Septembar","Oktobar","Novembar","Decembar"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Aug","Sep","Okt","Nov","Dec"],today:"Danas",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ca.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ca.min.js deleted file mode 100644 index ac107894c4..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ca.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ca={days:["Diumenge","Dilluns","Dimarts","Dimecres","Dijous","Divendres","Dissabte"],daysShort:["Diu","Dil","Dmt","Dmc","Dij","Div","Dis"],daysMin:["dg","dl","dt","dc","dj","dv","ds"],months:["Gener","Febrer","Març","Abril","Maig","Juny","Juliol","Agost","Setembre","Octubre","Novembre","Desembre"],monthsShort:["Gen","Feb","Mar","Abr","Mai","Jun","Jul","Ago","Set","Oct","Nov","Des"],today:"Avui",monthsTitle:"Mesos",clear:"Esborrar",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cs.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cs.min.js deleted file mode 100644 index 42dfd1a29d..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cs.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.cs={days:["Neděle","Pondělí","Úterý","Středa","Čtvrtek","Pátek","Sobota"],daysShort:["Ned","Pon","Úte","Stř","Čtv","Pát","Sob"],daysMin:["Ne","Po","Út","St","Čt","Pá","So"],months:["Leden","Únor","Březen","Duben","Květen","Červen","Červenec","Srpen","Září","Říjen","Listopad","Prosinec"],monthsShort:["Led","Úno","Bře","Dub","Kvě","Čer","Čnc","Srp","Zář","Říj","Lis","Pro"],today:"Dnes",clear:"Vymazat",monthsTitle:"Měsíc",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cy.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cy.min.js deleted file mode 100644 index f85ea031dd..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.cy.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.cy={days:["Sul","Llun","Mawrth","Mercher","Iau","Gwener","Sadwrn"],daysShort:["Sul","Llu","Maw","Mer","Iau","Gwe","Sad"],daysMin:["Su","Ll","Ma","Me","Ia","Gwe","Sa"],months:["Ionawr","Chewfror","Mawrth","Ebrill","Mai","Mehefin","Gorfennaf","Awst","Medi","Hydref","Tachwedd","Rhagfyr"],monthsShort:["Ion","Chw","Maw","Ebr","Mai","Meh","Gor","Aws","Med","Hyd","Tach","Rha"],today:"Heddiw"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.da.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.da.min.js deleted file mode 100644 index 53c8180528..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.da.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.da={days:["Søndag","Mandag","Tirsdag","Onsdag","Torsdag","Fredag","Lørdag"],daysShort:["Søn","Man","Tir","Ons","Tor","Fre","Lør"],daysMin:["Sø","Ma","Ti","On","To","Fr","Lø"],months:["Januar","Februar","Marts","April","Maj","Juni","Juli","August","September","Oktober","November","December"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Aug","Sep","Okt","Nov","Dec"],today:"I Dag",weekStart:1,clear:"Nulstil",format:"dd/mm/yyyy",monthsTitle:"Måneder"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.de.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.de.min.js deleted file mode 100644 index 1b5d6a2474..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.de.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.de={days:["Sonntag","Montag","Dienstag","Mittwoch","Donnerstag","Freitag","Samstag"],daysShort:["Son","Mon","Die","Mit","Don","Fre","Sam"],daysMin:["So","Mo","Di","Mi","Do","Fr","Sa"],months:["Januar","Februar","März","April","Mai","Juni","Juli","August","September","Oktober","November","Dezember"],monthsShort:["Jan","Feb","Mär","Apr","Mai","Jun","Jul","Aug","Sep","Okt","Nov","Dez"],today:"Heute",monthsTitle:"Monate",clear:"Löschen",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.el.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.el.min.js deleted file mode 100644 index 046e9eb5ef..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.el.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.el={days:["Κυριακή","Δευτέρα","Τρίτη","Τετάρτη","Πέμπτη","Παρασκευή","Σάββατο"],daysShort:["Κυρ","Δευ","Τρι","Τετ","Πεμ","Παρ","Σαβ"],daysMin:["Κυ","Δε","Τρ","Τε","Πε","Πα","Σα"],months:["Ιανουάριος","Φεβρουάριος","Μάρτιος","Απρίλιος","Μάιος","Ιούνιος","Ιούλιος","Αύγουστος","Σεπτέμβριος","Οκτώβριος","Νοέμβριος","Δεκέμβριος"],monthsShort:["Ιαν","Φεβ","Μαρ","Απρ","Μάι","Ιουν","Ιουλ","Αυγ","Σεπ","Οκτ","Νοε","Δεκ"],today:"Σήμερα",clear:"Καθαρισμός",weekStart:1,format:"d/m/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-AU.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-AU.min.js deleted file mode 100644 index b8d5f41cfa..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-AU.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-AU"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:1,format:"d/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-CA.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-CA.min.js deleted file mode 100644 index 7b1070f74d..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-CA.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-CA"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:0,format:"yyyy-mm-dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-GB.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-GB.min.js deleted file mode 100644 index 2966f5414e..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-GB.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-GB"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-IE.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-IE.min.js deleted file mode 100644 index dc8f71c026..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-IE.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-IE"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-NZ.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-NZ.min.js deleted file mode 100644 index c374a8d40c..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-NZ.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-NZ"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:1,format:"d/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-ZA.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-ZA.min.js deleted file mode 100644 index 885a928cba..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.en-ZA.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["en-ZA"]={days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],daysShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],daysMin:["Su","Mo","Tu","We","Th","Fr","Sa"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],monthsShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],today:"Today",monthsTitle:"Months",clear:"Clear",weekStart:1,format:"yyyy/mm/d"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eo.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eo.min.js deleted file mode 100644 index 736db021ae..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eo.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.eo={days:["dimanĉo","lundo","mardo","merkredo","ĵaŭdo","vendredo","sabato"],daysShort:["dim.","lun.","mar.","mer.","ĵaŭ.","ven.","sam."],daysMin:["d","l","ma","me","ĵ","v","s"],months:["januaro","februaro","marto","aprilo","majo","junio","julio","aŭgusto","septembro","oktobro","novembro","decembro"],monthsShort:["jan.","feb.","mar.","apr.","majo","jun.","jul.","aŭg.","sep.","okt.","nov.","dec."],today:"Hodiaŭ",clear:"Nuligi",weekStart:1,format:"yyyy-mm-dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.es.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.es.min.js deleted file mode 100644 index f3cef5d2b9..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.es.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.es={days:["Domingo","Lunes","Martes","Miércoles","Jueves","Viernes","Sábado"],daysShort:["Dom","Lun","Mar","Mié","Jue","Vie","Sáb"],daysMin:["Do","Lu","Ma","Mi","Ju","Vi","Sa"],months:["Enero","Febrero","Marzo","Abril","Mayo","Junio","Julio","Agosto","Septiembre","Octubre","Noviembre","Diciembre"],monthsShort:["Ene","Feb","Mar","Abr","May","Jun","Jul","Ago","Sep","Oct","Nov","Dic"],today:"Hoy",monthsTitle:"Meses",clear:"Borrar",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.et.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.et.min.js deleted file mode 100644 index 34cd9c60e9..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.et.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.et={days:["Pühapäev","Esmaspäev","Teisipäev","Kolmapäev","Neljapäev","Reede","Laupäev"],daysShort:["Pühap","Esmasp","Teisip","Kolmap","Neljap","Reede","Laup"],daysMin:["P","E","T","K","N","R","L"],months:["Jaanuar","Veebruar","Märts","Aprill","Mai","Juuni","Juuli","August","September","Oktoober","November","Detsember"],monthsShort:["Jaan","Veebr","Märts","Apr","Mai","Juuni","Juuli","Aug","Sept","Okt","Nov","Dets"],today:"Täna",clear:"Tühjenda",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eu.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eu.min.js deleted file mode 100644 index c5aa359e48..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.eu.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.eu={days:["Igandea","Astelehena","Asteartea","Asteazkena","Osteguna","Ostirala","Larunbata"],daysShort:["Ig","Al","Ar","Az","Og","Ol","Lr"],daysMin:["Ig","Al","Ar","Az","Og","Ol","Lr"],months:["Urtarrila","Otsaila","Martxoa","Apirila","Maiatza","Ekaina","Uztaila","Abuztua","Iraila","Urria","Azaroa","Abendua"],monthsShort:["Urt","Ots","Mar","Api","Mai","Eka","Uzt","Abu","Ira","Urr","Aza","Abe"],today:"Gaur",monthsTitle:"Hilabeteak",clear:"Ezabatu",weekStart:1,format:"yyyy/mm/dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fa.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fa.min.js deleted file mode 100644 index 8575237a07..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fa.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.fa={days:["یک‌شنبه","دوشنبه","سه‌شنبه","چهارشنبه","پنج‌شنبه","جمعه","شنبه","یک‌شنبه"],daysShort:["یک","دو","سه","چهار","پنج","جمعه","شنبه","یک"],daysMin:["ی","د","س","چ","پ","ج","ش","ی"],months:["ژانویه","فوریه","مارس","آوریل","مه","ژوئن","ژوئیه","اوت","سپتامبر","اکتبر","نوامبر","دسامبر"],monthsShort:["ژان","فور","مار","آور","مه","ژون","ژوی","اوت","سپت","اکت","نوا","دسا"],today:"امروز",clear:"پاک کن",weekStart:1,format:"yyyy/mm/dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fi.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fi.min.js deleted file mode 100644 index 239dfb796c..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fi.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.fi={days:["sunnuntai","maanantai","tiistai","keskiviikko","torstai","perjantai","lauantai"],daysShort:["sun","maa","tii","kes","tor","per","lau"],daysMin:["su","ma","ti","ke","to","pe","la"],months:["tammikuu","helmikuu","maaliskuu","huhtikuu","toukokuu","kesäkuu","heinäkuu","elokuu","syyskuu","lokakuu","marraskuu","joulukuu"],monthsShort:["tam","hel","maa","huh","tou","kes","hei","elo","syy","lok","mar","jou"],today:"tänään",clear:"Tyhjennä",weekStart:1,format:"d.m.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fo.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fo.min.js deleted file mode 100644 index fa24e3a127..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fo.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.fo={days:["Sunnudagur","Mánadagur","Týsdagur","Mikudagur","Hósdagur","Fríggjadagur","Leygardagur"],daysShort:["Sun","Mán","Týs","Mik","Hós","Frí","Ley"],daysMin:["Su","Má","Tý","Mi","Hó","Fr","Le"],months:["Januar","Februar","Marts","Apríl","Mei","Juni","Juli","August","Septembur","Oktobur","Novembur","Desembur"],monthsShort:["Jan","Feb","Mar","Apr","Mei","Jun","Jul","Aug","Sep","Okt","Nov","Des"],today:"Í Dag",clear:"Reinsa"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr-CH.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr-CH.min.js deleted file mode 100644 index 1c6bcdcbfc..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr-CH.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.fr={days:["Dimanche","Lundi","Mardi","Mercredi","Jeudi","Vendredi","Samedi"],daysShort:["Dim","Lun","Mar","Mer","Jeu","Ven","Sam"],daysMin:["D","L","Ma","Me","J","V","S"],months:["Janvier","Février","Mars","Avril","Mai","Juin","Juillet","Août","Septembre","Octobre","Novembre","Décembre"],monthsShort:["Jan","Fév","Mar","Avr","Mai","Jui","Jul","Aou","Sep","Oct","Nov","Déc"],today:"Aujourd'hui",monthsTitle:"Mois",clear:"Effacer",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr.min.js deleted file mode 100644 index 244cfba800..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.fr.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.fr={days:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],daysShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],daysMin:["d","l","ma","me","j","v","s"],months:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthsShort:["janv.","févr.","mars","avril","mai","juin","juil.","août","sept.","oct.","nov.","déc."],today:"Aujourd'hui",monthsTitle:"Mois",clear:"Effacer",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.gl.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.gl.min.js deleted file mode 100644 index 3d92606b3b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.gl.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.gl={days:["Domingo","Luns","Martes","Mércores","Xoves","Venres","Sábado"],daysShort:["Dom","Lun","Mar","Mér","Xov","Ven","Sáb"],daysMin:["Do","Lu","Ma","Me","Xo","Ve","Sa"],months:["Xaneiro","Febreiro","Marzo","Abril","Maio","Xuño","Xullo","Agosto","Setembro","Outubro","Novembro","Decembro"],monthsShort:["Xan","Feb","Mar","Abr","Mai","Xun","Xul","Ago","Sep","Out","Nov","Dec"],today:"Hoxe",clear:"Limpar",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.he.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.he.min.js deleted file mode 100644 index 191cb453a0..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.he.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.he={days:["ראשון","שני","שלישי","רביעי","חמישי","שישי","שבת","ראשון"],daysShort:["א","ב","ג","ד","ה","ו","ש","א"],daysMin:["א","ב","ג","ד","ה","ו","ש","א"],months:["ינואר","פברואר","מרץ","אפריל","מאי","יוני","יולי","אוגוסט","ספטמבר","אוקטובר","נובמבר","דצמבר"],monthsShort:["ינו","פבר","מרץ","אפר","מאי","יונ","יול","אוג","ספט","אוק","נוב","דצמ"],today:"היום",rtl:!0}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hi.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hi.min.js deleted file mode 100644 index 635baffa8b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hi.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.hi={days:["रविवार","सोमवार","मंगलवार","बुधवार","गुरुवार","शुक्रवार","शनिवार"],daysShort:["सूर्य","सोम","मंगल","बुध","गुरु","शुक्र","शनि"],daysMin:["र","सो","मं","बु","गु","शु","श"],months:["जनवरी","फ़रवरी","मार्च","अप्रैल","मई","जून","जुलाई","अगस्त","सितम्बर","अक्टूबर","नवंबर","दिसम्बर"],monthsShort:["जन","फ़रवरी","मार्च","अप्रैल","मई","जून","जुलाई","अगस्त","सितं","अक्टूबर","नवं","दिसम्बर"],today:"आज",monthsTitle:"महीने",clear:"साफ",weekStart:1,format:"dd / mm / yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hr.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hr.min.js deleted file mode 100644 index 8b34bce0fd..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hr.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.hr={days:["Nedjelja","Ponedjeljak","Utorak","Srijeda","Četvrtak","Petak","Subota"],daysShort:["Ned","Pon","Uto","Sri","Čet","Pet","Sub"],daysMin:["Ne","Po","Ut","Sr","Če","Pe","Su"],months:["Siječanj","Veljača","Ožujak","Travanj","Svibanj","Lipanj","Srpanj","Kolovoz","Rujan","Listopad","Studeni","Prosinac"],monthsShort:["Sij","Velj","Ožu","Tra","Svi","Lip","Srp","Kol","Ruj","Lis","Stu","Pro"],today:"Danas"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hu.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hu.min.js deleted file mode 100644 index f9decf9a2c..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hu.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.hu={days:["vasárnap","hétfő","kedd","szerda","csütörtök","péntek","szombat"],daysShort:["vas","hét","ked","sze","csü","pén","szo"],daysMin:["V","H","K","Sze","Cs","P","Szo"],months:["január","február","március","április","május","június","július","augusztus","szeptember","október","november","december"],monthsShort:["jan","feb","már","ápr","máj","jún","júl","aug","sze","okt","nov","dec"],today:"ma",weekStart:1,clear:"töröl",titleFormat:"yyyy. MM",format:"yyyy.mm.dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hy.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hy.min.js deleted file mode 100644 index a1cf653d38..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.hy.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.hy={days:["Կիրակի","Երկուշաբթի","Երեքշաբթի","Չորեքշաբթի","Հինգշաբթի","Ուրբաթ","Շաբաթ"],daysShort:["Կիր","Երկ","Երե","Չոր","Հին","Ուրբ","Շաբ"],daysMin:["Կի","Եկ","Եք","Չո","Հի","Ու","Շա"],months:["Հունվար","Փետրվար","Մարտ","Ապրիլ","Մայիս","Հունիս","Հուլիս","Օգոստոս","Սեպտեմբեր","Հոկտեմբեր","Նոյեմբեր","Դեկտեմբեր"],monthsShort:["Հնվ","Փետ","Մար","Ապր","Մայ","Հուն","Հուլ","Օգս","Սեպ","Հոկ","Նոյ","Դեկ"],today:"Այսօր",clear:"Ջնջել",format:"dd.mm.yyyy",weekStart:1,monthsTitle:"Ամիսնէր"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.id.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.id.min.js deleted file mode 100644 index 7c3220a643..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.id.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.id={days:["Minggu","Senin","Selasa","Rabu","Kamis","Jumat","Sabtu"],daysShort:["Mgu","Sen","Sel","Rab","Kam","Jum","Sab"],daysMin:["Mg","Sn","Sl","Ra","Ka","Ju","Sa"],months:["Januari","Februari","Maret","April","Mei","Juni","Juli","Agustus","September","Oktober","November","Desember"],monthsShort:["Jan","Feb","Mar","Apr","Mei","Jun","Jul","Ags","Sep","Okt","Nov","Des"],today:"Hari Ini",clear:"Kosongkan"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.is.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.is.min.js deleted file mode 100644 index f49bd18cc2..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.is.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.is={days:["Sunnudagur","Mánudagur","Þriðjudagur","Miðvikudagur","Fimmtudagur","Föstudagur","Laugardagur"],daysShort:["Sun","Mán","Þri","Mið","Fim","Fös","Lau"],daysMin:["Su","Má","Þr","Mi","Fi","Fö","La"],months:["Janúar","Febrúar","Mars","Apríl","Maí","Júní","Júlí","Ágúst","September","Október","Nóvember","Desember"],monthsShort:["Jan","Feb","Mar","Apr","Maí","Jún","Júl","Ágú","Sep","Okt","Nóv","Des"],today:"Í Dag"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it-CH.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it-CH.min.js deleted file mode 100644 index 7e1adbb95d..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it-CH.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.it={days:["Domenica","Lunedì","Martedì","Mercoledì","Giovedì","Venerdì","Sabato"],daysShort:["Dom","Lun","Mar","Mer","Gio","Ven","Sab"],daysMin:["Do","Lu","Ma","Me","Gi","Ve","Sa"],months:["Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","Luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"],monthsShort:["Gen","Feb","Mar","Apr","Mag","Giu","Lug","Ago","Set","Ott","Nov","Dic"],today:"Oggi",clear:"Cancella",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it.min.js deleted file mode 100644 index cc30766ffa..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.it.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.it={days:["Domenica","Lunedì","Martedì","Mercoledì","Giovedì","Venerdì","Sabato"],daysShort:["Dom","Lun","Mar","Mer","Gio","Ven","Sab"],daysMin:["Do","Lu","Ma","Me","Gi","Ve","Sa"],months:["Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","Luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"],monthsShort:["Gen","Feb","Mar","Apr","Mag","Giu","Lug","Ago","Set","Ott","Nov","Dic"],today:"Oggi",monthsTitle:"Mesi",clear:"Cancella",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ja.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ja.min.js deleted file mode 100644 index e321f04ffe..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ja.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ja={days:["日曜","月曜","火曜","水曜","木曜","金曜","土曜"],daysShort:["日","月","火","水","木","金","土"],daysMin:["日","月","火","水","木","金","土"],months:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],monthsShort:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],today:"今日",format:"yyyy/mm/dd",titleFormat:"yyyy年mm月",clear:"クリア"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ka.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ka.min.js deleted file mode 100644 index 84f14c0e90..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ka.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ka={days:["კვირა","ორშაბათი","სამშაბათი","ოთხშაბათი","ხუთშაბათი","პარასკევი","შაბათი"],daysShort:["კვი","ორშ","სამ","ოთხ","ხუთ","პარ","შაბ"],daysMin:["კვ","ორ","სა","ოთ","ხუ","პა","შა"],months:["იანვარი","თებერვალი","მარტი","აპრილი","მაისი","ივნისი","ივლისი","აგვისტო","სექტემბერი","ოქტომბერი","ნოემბერი","დეკემბერი"],monthsShort:["იან","თებ","მარ","აპრ","მაი","ივნ","ივლ","აგვ","სექ","ოქტ","ნოე","დეკ"],today:"დღეს",clear:"გასუფთავება",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kh.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kh.min.js deleted file mode 100644 index bf2abc5d82..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kh.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.kh={days:["អាទិត្យ","ចន្ទ","អង្គារ","ពុធ","ព្រហស្បតិ៍","សុក្រ","សៅរ៍"],daysShort:["អា.ទិ","ចន្ទ","អង្គារ","ពុធ","ព្រ.ហ","សុក្រ","សៅរ៍"],daysMin:["អា.ទិ","ចន្ទ","អង្គារ","ពុធ","ព្រ.ហ","សុក្រ","សៅរ៍"],months:["មករា","កុម្ភះ","មិនា","មេសា","ឧសភា","មិថុនា","កក្កដា","សីហា","កញ្ញា","តុលា","វិច្ឆិកា","ធ្នូ"],monthsShort:["មករា","កុម្ភះ","មិនា","មេសា","ឧសភា","មិថុនា","កក្កដា","សីហា","កញ្ញា","តុលា","វិច្ឆិកា","ធ្នូ"],today:"ថ្ងៃនេះ",clear:"សំអាត"},a.fn.datepicker.deprecated('The language code "kh" is deprecated and will be removed in 2.0. For Khmer support use "km" instead.')}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kk.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kk.min.js deleted file mode 100644 index f4e2f3f1a2..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kk.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.kk={days:["Жексенбі","Дүйсенбі","Сейсенбі","Сәрсенбі","Бейсенбі","Жұма","Сенбі"],daysShort:["Жек","Дүй","Сей","Сәр","Бей","Жұм","Сен"],daysMin:["Жк","Дс","Сс","Ср","Бс","Жм","Сн"],months:["Қаңтар","Ақпан","Наурыз","Сәуір","Мамыр","Маусым","Шілде","Тамыз","Қыркүйек","Қазан","Қараша","Желтоқсан"],monthsShort:["Қаң","Ақп","Нау","Сәу","Мам","Мау","Шіл","Там","Қыр","Қаз","Қар","Жел"],today:"Бүгін",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.km.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.km.min.js deleted file mode 100644 index 648d83f84f..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.km.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.km={days:["អាទិត្យ","ចន្ទ","អង្គារ","ពុធ","ព្រហស្បតិ៍","សុក្រ","សៅរ៍"],daysShort:["អា.ទិ","ចន្ទ","អង្គារ","ពុធ","ព្រ.ហ","សុក្រ","សៅរ៍"],daysMin:["អា.ទិ","ចន្ទ","អង្គារ","ពុធ","ព្រ.ហ","សុក្រ","សៅរ៍"],months:["មករា","កុម្ភះ","មិនា","មេសា","ឧសភា","មិថុនា","កក្កដា","សីហា","កញ្ញា","តុលា","វិច្ឆិកា","ធ្នូ"],monthsShort:["មករា","កុម្ភះ","មិនា","មេសា","ឧសភា","មិថុនា","កក្កដា","សីហា","កញ្ញា","តុលា","វិច្ឆិកា","ធ្នូ"],today:"ថ្ងៃនេះ",clear:"សំអាត"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ko.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ko.min.js deleted file mode 100644 index 9751ee5c22..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ko.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ko={days:["일요일","월요일","화요일","수요일","목요일","금요일","토요일"],daysShort:["일","월","화","수","목","금","토"],daysMin:["일","월","화","수","목","금","토"],months:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],monthsShort:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],today:"오늘",clear:"삭제",format:"yyyy-mm-dd",titleFormat:"yyyy년mm월",weekStart:0}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kr.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kr.min.js deleted file mode 100644 index 43393409e0..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.kr.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.kr={days:["일요일","월요일","화요일","수요일","목요일","금요일","토요일"],daysShort:["일","월","화","수","목","금","토"],daysMin:["일","월","화","수","목","금","토"],months:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],monthsShort:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"]},a.fn.datepicker.deprecated('The language code "kr" is deprecated and will be removed in 2.0. For korean support use "ko" instead.')}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lt.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lt.min.js deleted file mode 100644 index da78ea85f3..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lt.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.lt={days:["Sekmadienis","Pirmadienis","Antradienis","Trečiadienis","Ketvirtadienis","Penktadienis","Šeštadienis"],daysShort:["S","Pr","A","T","K","Pn","Š"],daysMin:["Sk","Pr","An","Tr","Ke","Pn","Št"],months:["Sausis","Vasaris","Kovas","Balandis","Gegužė","Birželis","Liepa","Rugpjūtis","Rugsėjis","Spalis","Lapkritis","Gruodis"],monthsShort:["Sau","Vas","Kov","Bal","Geg","Bir","Lie","Rugp","Rugs","Spa","Lap","Gru"],today:"Šiandien",monthsTitle:"Mėnesiai",clear:"Išvalyti",weekStart:1,format:"yyyy-mm-dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lv.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lv.min.js deleted file mode 100644 index 89cea00f8b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.lv.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.lv={days:["Svētdiena","Pirmdiena","Otrdiena","Trešdiena","Ceturtdiena","Piektdiena","Sestdiena"],daysShort:["Sv","P","O","T","C","Pk","S"],daysMin:["Sv","Pr","Ot","Tr","Ce","Pk","Se"],months:["Janvāris","Februāris","Marts","Aprīlis","Maijs","Jūnijs","Jūlijs","Augusts","Septembris","Oktobris","Novembris","Decembris"],monthsShort:["Jan","Feb","Mar","Apr","Mai","Jūn","Jūl","Aug","Sep","Okt","Nov","Dec"],monthsTitle:"Mēneši",today:"Šodien",clear:"Nodzēst",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.me.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.me.min.js deleted file mode 100644 index c65a891646..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.me.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.me={days:["Nedjelja","Ponedjeljak","Utorak","Srijeda","Četvrtak","Petak","Subota"],daysShort:["Ned","Pon","Uto","Sri","Čet","Pet","Sub"],daysMin:["Ne","Po","Ut","Sr","Če","Pe","Su"],months:["Januar","Februar","Mart","April","Maj","Jun","Jul","Avgust","Septembar","Oktobar","Novembar","Decembar"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],today:"Danas",weekStart:1,clear:"Izbriši",format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mk.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mk.min.js deleted file mode 100644 index 46423f7581..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mk.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.mk={days:["Недела","Понеделник","Вторник","Среда","Четврток","Петок","Сабота"],daysShort:["Нед","Пон","Вто","Сре","Чет","Пет","Саб"],daysMin:["Не","По","Вт","Ср","Че","Пе","Са"],months:["Јануари","Февруари","Март","Април","Мај","Јуни","Јули","Август","Септември","Октомври","Ноември","Декември"],monthsShort:["Јан","Фев","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Ное","Дек"],today:"Денес",format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mn.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mn.min.js deleted file mode 100644 index 6ebaec9d86..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.mn.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.mn={days:["Ням","Даваа","Мягмар","Лхагва","Пүрэв","Баасан","Бямба"],daysShort:["Ням","Дав","Мяг","Лха","Пүр","Баа","Бям"],daysMin:["Ня","Да","Мя","Лх","Пү","Ба","Бя"],months:["Хулгана","Үхэр","Бар","Туулай","Луу","Могой","Морь","Хонь","Бич","Тахиа","Нохой","Гахай"],monthsShort:["Хул","Үхэ","Бар","Туу","Луу","Мог","Мор","Хон","Бич","Тах","Нох","Гах"],today:"Өнөөдөр",clear:"Тодорхой",format:"yyyy.mm.dd",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ms.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ms.min.js deleted file mode 100644 index 47efafdc2f..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ms.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ms={days:["Ahad","Isnin","Selasa","Rabu","Khamis","Jumaat","Sabtu"],daysShort:["Aha","Isn","Sel","Rab","Kha","Jum","Sab"],daysMin:["Ah","Is","Se","Ra","Kh","Ju","Sa"],months:["Januari","Februari","Mac","April","Mei","Jun","Julai","Ogos","September","Oktober","November","Disember"],monthsShort:["Jan","Feb","Mar","Apr","Mei","Jun","Jul","Ogo","Sep","Okt","Nov","Dis"],today:"Hari Ini",clear:"Bersihkan"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl-BE.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl-BE.min.js deleted file mode 100644 index 85d3146df1..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl-BE.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["nl-BE"]={days:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],daysShort:["zo","ma","di","wo","do","vr","za"],daysMin:["zo","ma","di","wo","do","vr","za"],months:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthsShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],today:"Vandaag",monthsTitle:"Maanden",clear:"Leegmaken",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl.min.js deleted file mode 100644 index af977b71ea..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.nl.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.nl={days:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],daysShort:["zo","ma","di","wo","do","vr","za"],daysMin:["zo","ma","di","wo","do","vr","za"],months:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthsShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],today:"Vandaag",monthsTitle:"Maanden",clear:"Wissen",weekStart:1,format:"dd-mm-yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.no.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.no.min.js deleted file mode 100644 index 0c5136e441..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.no.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.no={days:["søndag","mandag","tirsdag","onsdag","torsdag","fredag","lørdag"],daysShort:["søn","man","tir","ons","tor","fre","lør"],daysMin:["sø","ma","ti","on","to","fr","lø"],months:["januar","februar","mars","april","mai","juni","juli","august","september","oktober","november","desember"],monthsShort:["jan","feb","mar","apr","mai","jun","jul","aug","sep","okt","nov","des"],today:"i dag",monthsTitle:"Måneder",clear:"Nullstill",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.oc.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.oc.min.js deleted file mode 100644 index 630fa16b96..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.oc.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.oc={days:["Dimenge","Diluns","Dimars","Dimècres","Dijòus","Divendres","Dissabte"],daysShort:["Dim","Dil","Dmr","Dmc","Dij","Div","Dis"],daysMin:["dg","dl","dr","dc","dj","dv","ds"],months:["Genièr","Febrièr","Març","Abrial","Mai","Junh","Julhet","Agost","Setembre","Octobre","Novembre","Decembre"],monthsShort:["Gen","Feb","Mar","Abr","Mai","Jun","Jul","Ago","Set","Oct","Nov","Dec"],today:"Uèi",monthsTitle:"Meses",clear:"Escafar",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pl.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pl.min.js deleted file mode 100644 index ffb30ec8b1..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pl.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.pl={days:["Niedziela","Poniedziałek","Wtorek","Środa","Czwartek","Piątek","Sobota"],daysShort:["Niedz.","Pon.","Wt.","Śr.","Czw.","Piąt.","Sob."],daysMin:["Ndz.","Pn.","Wt.","Śr.","Czw.","Pt.","Sob."],months:["Styczeń","Luty","Marzec","Kwiecień","Maj","Czerwiec","Lipiec","Sierpień","Wrzesień","Październik","Listopad","Grudzień"],monthsShort:["Sty.","Lut.","Mar.","Kwi.","Maj","Cze.","Lip.","Sie.","Wrz.","Paź.","Lis.","Gru."],today:"Dzisiaj",weekStart:1,clear:"Wyczyść",format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt-BR.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt-BR.min.js deleted file mode 100644 index 2d3f8afdac..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt-BR.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["pt-BR"]={days:["Domingo","Segunda","Terça","Quarta","Quinta","Sexta","Sábado"],daysShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],daysMin:["Do","Se","Te","Qu","Qu","Se","Sa"],months:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthsShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],today:"Hoje",monthsTitle:"Meses",clear:"Limpar",format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt.min.js deleted file mode 100644 index e2b4e64d77..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.pt.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.pt={days:["Domingo","Segunda","Terça","Quarta","Quinta","Sexta","Sábado"],daysShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],daysMin:["Do","Se","Te","Qu","Qu","Se","Sa"],months:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthsShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],today:"Hoje",monthsTitle:"Meses",clear:"Limpar",format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ro.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ro.min.js deleted file mode 100644 index 5fff2986df..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ro.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ro={days:["Duminică","Luni","Marţi","Miercuri","Joi","Vineri","Sâmbătă"],daysShort:["Dum","Lun","Mar","Mie","Joi","Vin","Sâm"],daysMin:["Du","Lu","Ma","Mi","Jo","Vi","Sâ"],months:["Ianuarie","Februarie","Martie","Aprilie","Mai","Iunie","Iulie","August","Septembrie","Octombrie","Noiembrie","Decembrie"],monthsShort:["Ian","Feb","Mar","Apr","Mai","Iun","Iul","Aug","Sep","Oct","Nov","Dec"],today:"Astăzi",clear:"Șterge",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs-latin.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs-latin.min.js deleted file mode 100644 index e520c95733..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs-latin.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["rs-latin"]={days:["Nedelja","Ponedeljak","Utorak","Sreda","Četvrtak","Petak","Subota"],daysShort:["Ned","Pon","Uto","Sre","Čet","Pet","Sub"],daysMin:["N","Po","U","Sr","Č","Pe","Su"],months:["Januar","Februar","Mart","April","Maj","Jun","Jul","Avgust","Septembar","Oktobar","Novembar","Decembar"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],today:"Danas",weekStart:1,format:"dd.mm.yyyy"},a.fn.datepicker.deprecated('This language code "rs-latin" is deprecated (invalid serbian language code) and will be removed in 2.0. For Serbian latin support use "sr-latin" instead.')}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs.min.js deleted file mode 100644 index ba95ae298f..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.rs.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.rs={days:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],daysShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],daysMin:["Н","По","У","Ср","Ч","Пе","Су"],months:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthsShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],today:"Данас",weekStart:1,format:"dd.mm.yyyy"},a.fn.datepicker.deprecated('This language code "rs" is deprecated (invalid serbian language code) and will be removed in 2.0. For Serbian support use "sr" instead.')}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ru.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ru.min.js deleted file mode 100644 index 52bc010b97..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ru.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ru={days:["Воскресенье","Понедельник","Вторник","Среда","Четверг","Пятница","Суббота"],daysShort:["Вск","Пнд","Втр","Срд","Чтв","Птн","Суб"],daysMin:["Вс","Пн","Вт","Ср","Чт","Пт","Сб"],months:["Январь","Февраль","Март","Апрель","Май","Июнь","Июль","Август","Сентябрь","Октябрь","Ноябрь","Декабрь"],monthsShort:["Янв","Фев","Мар","Апр","Май","Июн","Июл","Авг","Сен","Окт","Ноя","Дек"],today:"Сегодня",clear:"Очистить",format:"dd.mm.yyyy",weekStart:1,monthsTitle:"Месяцы"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.si.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.si.min.js deleted file mode 100644 index b9746b8fc1..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.si.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.si={days:["ඉරිදා","සඳුදා","අඟහරුවාදා","බදාදා","බ්‍රහස්පතින්දා","සිකුරාදා","සෙනසුරාදා"],daysShort:["ඉරි","සඳු","අඟ","බදා","බ්‍රහ","සිකු","සෙන"],daysMin:["ඉ","ස","අ","බ","බ්‍ර","සි","සෙ"],months:["ජනවාරි","පෙබරවාරි","මාර්තු","අප්‍රේල්","මැයි","ජුනි","ජූලි","අගෝස්තු","සැප්තැම්බර්","ඔක්තෝබර්","නොවැම්බර්","දෙසැම්බර්"],monthsShort:["ජන","පෙබ","මාර්","අප්‍රේ","මැයි","ජුනි","ජූලි","අගෝ","සැප්","ඔක්","නොවැ","දෙසැ"],today:"අද",monthsTitle:"මාස",clear:"මකන්න",weekStart:0,format:"yyyy-mm-dd"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sk.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sk.min.js deleted file mode 100644 index 79a9267fd5..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sk.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sk={days:["Nedeľa","Pondelok","Utorok","Streda","Štvrtok","Piatok","Sobota"],daysShort:["Ned","Pon","Uto","Str","Štv","Pia","Sob"],daysMin:["Ne","Po","Ut","St","Št","Pia","So"],months:["Január","Február","Marec","Apríl","Máj","Jún","Júl","August","September","Október","November","December"],monthsShort:["Jan","Feb","Mar","Apr","Máj","Jún","Júl","Aug","Sep","Okt","Nov","Dec"],today:"Dnes",clear:"Vymazať",weekStart:1,format:"d.m.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sl.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sl.min.js deleted file mode 100644 index 831cf73903..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sl.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sl={days:["Nedelja","Ponedeljek","Torek","Sreda","Četrtek","Petek","Sobota"],daysShort:["Ned","Pon","Tor","Sre","Čet","Pet","Sob"],daysMin:["Ne","Po","To","Sr","Če","Pe","So"],months:["Januar","Februar","Marec","April","Maj","Junij","Julij","Avgust","September","Oktober","November","December"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],today:"Danes",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sq.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sq.min.js deleted file mode 100644 index 8c586055a0..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sq.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sq={days:["E Diel","E Hënë","E Martē","E Mërkurë","E Enjte","E Premte","E Shtunë"],daysShort:["Die","Hën","Mar","Mër","Enj","Pre","Shtu"],daysMin:["Di","Hë","Ma","Më","En","Pr","Sht"],months:["Janar","Shkurt","Mars","Prill","Maj","Qershor","Korrik","Gusht","Shtator","Tetor","Nëntor","Dhjetor"],monthsShort:["Jan","Shk","Mar","Pri","Maj","Qer","Korr","Gu","Sht","Tet","Nën","Dhjet"],monthsTitle:"Muaj",today:"Sot",weekStart:1,format:"dd/mm/yyyy",clear:"Pastro"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr-latin.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr-latin.min.js deleted file mode 100644 index c6b7001ace..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr-latin.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["sr-latin"]={days:["Nedelja","Ponedeljak","Utorak","Sreda","Četvrtak","Petak","Subota"],daysShort:["Ned","Pon","Uto","Sre","Čet","Pet","Sub"],daysMin:["N","Po","U","Sr","Č","Pe","Su"],months:["Januar","Februar","Mart","April","Maj","Jun","Jul","Avgust","Septembar","Oktobar","Novembar","Decembar"],monthsShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],today:"Danas",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr.min.js deleted file mode 100644 index 4e46dbf64b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sr.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sr={days:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],daysShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],daysMin:["Н","По","У","Ср","Ч","Пе","Су"],months:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthsShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],today:"Данас",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sv.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sv.min.js deleted file mode 100644 index 7ab6becb92..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sv.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sv={days:["söndag","måndag","tisdag","onsdag","torsdag","fredag","lördag"],daysShort:["sön","mån","tis","ons","tor","fre","lör"],daysMin:["sö","må","ti","on","to","fr","lö"],months:["januari","februari","mars","april","maj","juni","juli","augusti","september","oktober","november","december"],monthsShort:["jan","feb","mar","apr","maj","jun","jul","aug","sep","okt","nov","dec"],today:"Idag",format:"yyyy-mm-dd",weekStart:1,clear:"Rensa"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sw.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sw.min.js deleted file mode 100644 index 454d3053cb..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.sw.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.sw={days:["Jumapili","Jumatatu","Jumanne","Jumatano","Alhamisi","Ijumaa","Jumamosi"],daysShort:["J2","J3","J4","J5","Alh","Ij","J1"],daysMin:["2","3","4","5","A","I","1"],months:["Januari","Februari","Machi","Aprili","Mei","Juni","Julai","Agosti","Septemba","Oktoba","Novemba","Desemba"],monthsShort:["Jan","Feb","Mac","Apr","Mei","Jun","Jul","Ago","Sep","Okt","Nov","Des"],today:"Leo"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ta.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ta.min.js deleted file mode 100644 index e7909494aa..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.ta.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.ta={days:["ஞாயிறு","திங்கள்","செவ்வாய்","புதன்","வியாழன்","வெள்ளி","சனி"],daysShort:["ஞாயி","திங்","செவ்","புத","வியா","வெள்","சனி"],daysMin:["ஞா","தி","செ","பு","வி","வெ","ச"],months:["ஜனவரி","பிப்ரவரி","மார்ச்","ஏப்ரல்","மே","ஜூன்","ஜூலை","ஆகஸ்டு","செப்டம்பர்","அக்டோபர்","நவம்பர்","டிசம்பர்"],monthsShort:["ஜன","பிப்","மார்","ஏப்","மே","ஜூன்","ஜூலை","ஆக","செப்","அக்","நவ","டிச"],today:"இன்று",monthsTitle:"மாதங்கள்",clear:"நீக்கு",weekStart:1,format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tg.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tg.min.js deleted file mode 100644 index 104b6dd95b..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tg.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.tg={days:["Якшанбе","Душанбе","Сешанбе","Чоршанбе","Панҷшанбе","Ҷумъа","Шанбе"],daysShort:["Яшб","Дшб","Сшб","Чшб","Пшб","Ҷум","Шнб"],daysMin:["Яш","Дш","Сш","Чш","Пш","Ҷм","Шб"],months:["Январ","Феврал","Март","Апрел","Май","Июн","Июл","Август","Сентябр","Октябр","Ноябр","Декабр"],monthsShort:["Янв","Фев","Мар","Апр","Май","Июн","Июл","Авг","Сен","Окт","Ноя","Дек"],today:"Имрӯз",monthsTitle:"Моҳҳо",clear:"Тоза намудан",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.th.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.th.min.js deleted file mode 100644 index 1e398ba8bc..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.th.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.th={days:["อาทิตย์","จันทร์","อังคาร","พุธ","พฤหัส","ศุกร์","เสาร์","อาทิตย์"],daysShort:["อา","จ","อ","พ","พฤ","ศ","ส","อา"],daysMin:["อา","จ","อ","พ","พฤ","ศ","ส","อา"],months:["มกราคม","กุมภาพันธ์","มีนาคม","เมษายน","พฤษภาคม","มิถุนายน","กรกฎาคม","สิงหาคม","กันยายน","ตุลาคม","พฤศจิกายน","ธันวาคม"],monthsShort:["ม.ค.","ก.พ.","มี.ค.","เม.ย.","พ.ค.","มิ.ย.","ก.ค.","ส.ค.","ก.ย.","ต.ค.","พ.ย.","ธ.ค."],today:"วันนี้"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tk.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tk.min.js deleted file mode 100644 index 716edef2ee..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tk.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.tk={days:["Ýekşenbe","Duşenbe","Sişenbe","Çarşenbe","Penşenbe","Anna","Şenbe"],daysShort:["Ýek","Duş","Siş","Çar","Pen","Ann","Şen"],daysMin:["Ýe","Du","Si","Ça","Pe","An","Şe"],months:["Ýanwar","Fewral","Mart","Aprel","Maý","Iýun","Iýul","Awgust","Sentýabr","Oktýabr","Noýabr","Dekabr"],monthsShort:["Ýan","Few","Mar","Apr","Maý","Iýn","Iýl","Awg","Sen","Okt","Noý","Dek"],today:"Bu gün",monthsTitle:"Aýlar",clear:"Aýyr",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tr.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tr.min.js deleted file mode 100644 index 7889b1135d..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.tr.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.tr={days:["Pazar","Pazartesi","Salı","Çarşamba","Perşembe","Cuma","Cumartesi"],daysShort:["Pz","Pzt","Sal","Çrş","Prş","Cu","Cts"],daysMin:["Pz","Pzt","Sa","Çr","Pr","Cu","Ct"],months:["Ocak","Şubat","Mart","Nisan","Mayıs","Haziran","Temmuz","Ağustos","Eylül","Ekim","Kasım","Aralık"],monthsShort:["Oca","Şub","Mar","Nis","May","Haz","Tem","Ağu","Eyl","Eki","Kas","Ara"],today:"Bugün",clear:"Temizle",weekStart:1,format:"dd.mm.yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uk.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uk.min.js deleted file mode 100644 index 41b02e6b28..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uk.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.uk={days:["Неділя","Понеділок","Вівторок","Середа","Четвер","П'ятниця","Субота"],daysShort:["Нед","Пнд","Втр","Срд","Чтв","Птн","Суб"],daysMin:["Нд","Пн","Вт","Ср","Чт","Пт","Сб"],months:["Cічень","Лютий","Березень","Квітень","Травень","Червень","Липень","Серпень","Вересень","Жовтень","Листопад","Грудень"],monthsShort:["Січ","Лют","Бер","Кві","Тра","Чер","Лип","Сер","Вер","Жов","Лис","Гру"],today:"Сьогодні",clear:"Очистити",format:"dd.mm.yyyy",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-cyrl.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-cyrl.min.js deleted file mode 100644 index a0a8f213ce..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-cyrl.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["uz-cyrl"]={days:["Якшанба","Душанба","Сешанба","Чоршанба","Пайшанба","Жума","Шанба"],daysShort:["Якш","Ду","Се","Чор","Пай","Жу","Ша"],daysMin:["Як","Ду","Се","Чо","Па","Жу","Ша"],months:["Январь","Февраль","Март","Апрель","Май","Июнь","Июль","Август","Сентябрь","Октябрь","Ноябрь","Декабрь"],monthsShort:["Янв","Фев","Мар","Апр","Май","Июн","Июл","Авг","Сен","Окт","Ноя","Дек"],today:"Бугун",clear:"Ўчириш",format:"dd.mm.yyyy",weekStart:1,monthsTitle:"Ойлар"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-latn.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-latn.min.js deleted file mode 100644 index 2f58e343ef..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.uz-latn.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["uz-latn"]={days:["Yakshanba","Dushanba","Seshanba","Chorshanba","Payshanba","Juma","Shanba"],daysShort:["Yak","Du","Se","Chor","Pay","Ju","Sha"],daysMin:["Ya","Du","Se","Cho","Pa","Ju","Sha"],months:["Yanvar","Fevral","Mart","Aprel","May","Iyun","Iyul","Avgust","Sentabr","Oktabr","Noyabr","Dekabr"],monthsShort:["Yan","Fev","Mar","Apr","May","Iyn","Iyl","Avg","Sen","Okt","Noy","Dek"],today:"Bugun",clear:"O'chirish",format:"dd.mm.yyyy",weekStart:1,monthsTitle:"Oylar"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.vi.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.vi.min.js deleted file mode 100644 index 3311d23f86..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.vi.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates.vi={days:["Chủ nhật","Thứ hai","Thứ ba","Thứ tư","Thứ năm","Thứ sáu","Thứ bảy"],daysShort:["CN","Thứ 2","Thứ 3","Thứ 4","Thứ 5","Thứ 6","Thứ 7"],daysMin:["CN","T2","T3","T4","T5","T6","T7"],months:["Tháng 1","Tháng 2","Tháng 3","Tháng 4","Tháng 5","Tháng 6","Tháng 7","Tháng 8","Tháng 9","Tháng 10","Tháng 11","Tháng 12"],monthsShort:["Th1","Th2","Th3","Th4","Th5","Th6","Th7","Th8","Th9","Th10","Th11","Th12"],today:"Hôm nay",clear:"Xóa",format:"dd/mm/yyyy"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-CN.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-CN.min.js deleted file mode 100644 index 8e6920b0c8..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-CN.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["zh-CN"]={days:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],daysShort:["周日","周一","周二","周三","周四","周五","周六"],daysMin:["日","一","二","三","四","五","六"],months:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthsShort:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],today:"今天",monthsTitle:"选择月份",clear:"清除",format:"yyyy-mm-dd",titleFormat:"yyyy年mm月",weekStart:1}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-TW.min.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-TW.min.js deleted file mode 100644 index e309c1d7d6..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-datepicker/locales/bootstrap-datepicker.zh-TW.min.js +++ /dev/null @@ -1 +0,0 @@ -!function(a){a.fn.datepicker.dates["zh-TW"]={days:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],daysShort:["週日","週一","週二","週三","週四","週五","週六"],daysMin:["日","一","二","三","四","五","六"],months:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthsShort:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],today:"今天",format:"yyyy年mm月dd日",weekStart:1,clear:"清除"}}(jQuery); \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.css deleted file mode 100644 index 72f7acdfb3..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.css +++ /dev/null @@ -1,410 +0,0 @@ -.daterangepicker { - position: absolute; - color: inherit; - background-color: #fff; - border-radius: 4px; - border: 1px solid #ddd; - width: 278px; - max-width: none; - padding: 0; - margin-top: 7px; - top: 100px; - left: 20px; - z-index: 3001; - display: none; - font-family: arial; - font-size: 15px; - line-height: 1em; -} - -.daterangepicker:before, .daterangepicker:after { - position: absolute; - display: inline-block; - border-bottom-color: rgba(0, 0, 0, 0.2); - content: ''; -} - -.daterangepicker:before { - top: -7px; - border-right: 7px solid transparent; - border-left: 7px solid transparent; - border-bottom: 7px solid #ccc; -} - -.daterangepicker:after { - top: -6px; - border-right: 6px solid transparent; - border-bottom: 6px solid #fff; - border-left: 6px solid transparent; -} - -.daterangepicker.opensleft:before { - right: 9px; -} - -.daterangepicker.opensleft:after { - right: 10px; -} - -.daterangepicker.openscenter:before { - left: 0; - right: 0; - width: 0; - margin-left: auto; - margin-right: auto; -} - -.daterangepicker.openscenter:after { - left: 0; - right: 0; - width: 0; - margin-left: auto; - margin-right: auto; -} - -.daterangepicker.opensright:before { - left: 9px; -} - -.daterangepicker.opensright:after { - left: 10px; -} - -.daterangepicker.drop-up { - margin-top: -7px; -} - -.daterangepicker.drop-up:before { - top: initial; - bottom: -7px; - border-bottom: initial; - border-top: 7px solid #ccc; -} - -.daterangepicker.drop-up:after { - top: initial; - bottom: -6px; - border-bottom: initial; - border-top: 6px solid #fff; -} - -.daterangepicker.single .daterangepicker .ranges, .daterangepicker.single .drp-calendar { - float: none; -} - -.daterangepicker.single .drp-selected { - display: none; -} - -.daterangepicker.show-calendar .drp-calendar { - display: block; -} - -.daterangepicker.show-calendar .drp-buttons { - display: block; -} - -.daterangepicker.auto-apply .drp-buttons { - display: none; -} - -.daterangepicker .drp-calendar { - display: none; - max-width: 270px; -} - -.daterangepicker .drp-calendar.left { - padding: 8px 0 8px 8px; -} - -.daterangepicker .drp-calendar.right { - padding: 8px; -} - -.daterangepicker .drp-calendar.single .calendar-table { - border: none; -} - -.daterangepicker .calendar-table .next span, .daterangepicker .calendar-table .prev span { - color: #fff; - border: solid black; - border-width: 0 2px 2px 0; - border-radius: 0; - display: inline-block; - padding: 3px; -} - -.daterangepicker .calendar-table .next span { - transform: rotate(-45deg); - -webkit-transform: rotate(-45deg); -} - -.daterangepicker .calendar-table .prev span { - transform: rotate(135deg); - -webkit-transform: rotate(135deg); -} - -.daterangepicker .calendar-table th, .daterangepicker .calendar-table td { - white-space: nowrap; - text-align: center; - vertical-align: middle; - min-width: 32px; - width: 32px; - height: 24px; - line-height: 24px; - font-size: 12px; - border-radius: 4px; - border: 1px solid transparent; - white-space: nowrap; - cursor: pointer; -} - -.daterangepicker .calendar-table { - border: 1px solid #fff; - border-radius: 4px; - background-color: #fff; -} - -.daterangepicker .calendar-table table { - width: 100%; - margin: 0; - border-spacing: 0; - border-collapse: collapse; -} - -.daterangepicker td.available:hover, .daterangepicker th.available:hover { - background-color: #eee; - border-color: transparent; - color: inherit; -} - -.daterangepicker td.week, .daterangepicker th.week { - font-size: 80%; - color: #ccc; -} - -.daterangepicker td.off, .daterangepicker td.off.in-range, .daterangepicker td.off.start-date, .daterangepicker td.off.end-date { - background-color: #fff; - border-color: transparent; - color: #999; -} - -.daterangepicker td.in-range { - background-color: #ebf4f8; - border-color: transparent; - color: #000; - border-radius: 0; -} - -.daterangepicker td.start-date { - border-radius: 4px 0 0 4px; -} - -.daterangepicker td.end-date { - border-radius: 0 4px 4px 0; -} - -.daterangepicker td.start-date.end-date { - border-radius: 4px; -} - -.daterangepicker td.active, .daterangepicker td.active:hover { - background-color: #357ebd; - border-color: transparent; - color: #fff; -} - -.daterangepicker th.month { - width: auto; -} - -.daterangepicker td.disabled, .daterangepicker option.disabled { - color: #999; - cursor: not-allowed; - text-decoration: line-through; -} - -.daterangepicker select.monthselect, .daterangepicker select.yearselect { - font-size: 12px; - padding: 1px; - height: auto; - margin: 0; - cursor: default; -} - -.daterangepicker select.monthselect { - margin-right: 2%; - width: 56%; -} - -.daterangepicker select.yearselect { - width: 40%; -} - -.daterangepicker select.hourselect, .daterangepicker select.minuteselect, .daterangepicker select.secondselect, .daterangepicker select.ampmselect { - width: 50px; - margin: 0 auto; - background: #eee; - border: 1px solid #eee; - padding: 2px; - outline: 0; - font-size: 12px; -} - -.daterangepicker .calendar-time { - text-align: center; - margin: 4px auto 0 auto; - line-height: 30px; - position: relative; -} - -.daterangepicker .calendar-time select.disabled { - color: #ccc; - cursor: not-allowed; -} - -.daterangepicker .drp-buttons { - clear: both; - text-align: right; - padding: 8px; - border-top: 1px solid #ddd; - display: none; - line-height: 12px; - vertical-align: middle; -} - -.daterangepicker .drp-selected { - display: inline-block; - font-size: 12px; - padding-right: 8px; -} - -.daterangepicker .drp-buttons .btn { - margin-left: 8px; - font-size: 12px; - font-weight: bold; - padding: 4px 8px; -} - -.daterangepicker.show-ranges.single.rtl .drp-calendar.left { - border-right: 1px solid #ddd; -} - -.daterangepicker.show-ranges.single.ltr .drp-calendar.left { - border-left: 1px solid #ddd; -} - -.daterangepicker.show-ranges.rtl .drp-calendar.right { - border-right: 1px solid #ddd; -} - -.daterangepicker.show-ranges.ltr .drp-calendar.left { - border-left: 1px solid #ddd; -} - -.daterangepicker .ranges { - float: none; - text-align: left; - margin: 0; -} - -.daterangepicker.show-calendar .ranges { - margin-top: 8px; -} - -.daterangepicker .ranges ul { - list-style: none; - margin: 0 auto; - padding: 0; - width: 100%; -} - -.daterangepicker .ranges li { - font-size: 12px; - padding: 8px 12px; - cursor: pointer; -} - -.daterangepicker .ranges li:hover { - background-color: #eee; -} - -.daterangepicker .ranges li.active { - background-color: #08c; - color: #fff; -} - -/* Larger Screen Styling */ -@media (min-width: 564px) { - .daterangepicker { - width: auto; - } - - .daterangepicker .ranges ul { - width: 140px; - } - - .daterangepicker.single .ranges ul { - width: 100%; - } - - .daterangepicker.single .drp-calendar.left { - clear: none; - } - - .daterangepicker.single .ranges, .daterangepicker.single .drp-calendar { - float: left; - } - - .daterangepicker { - direction: ltr; - text-align: left; - } - - .daterangepicker .drp-calendar.left { - clear: left; - margin-right: 0; - } - - .daterangepicker .drp-calendar.left .calendar-table { - border-right: none; - border-top-right-radius: 0; - border-bottom-right-radius: 0; - } - - .daterangepicker .drp-calendar.right { - margin-left: 0; - } - - .daterangepicker .drp-calendar.right .calendar-table { - border-left: none; - border-top-left-radius: 0; - border-bottom-left-radius: 0; - } - - .daterangepicker .drp-calendar.left .calendar-table { - padding-right: 8px; - } - - .daterangepicker .ranges, .daterangepicker .drp-calendar { - float: left; - } -} - -@media (min-width: 730px) { - .daterangepicker .ranges { - width: auto; - } - - .daterangepicker .ranges { - float: left; - } - - .daterangepicker.rtl .ranges { - float: right; - } - - .daterangepicker .drp-calendar.left { - clear: none !important; - } -} diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.js b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.js deleted file mode 100644 index a3becee537..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap-daterangepicker/daterangepicker.js +++ /dev/null @@ -1,1578 +0,0 @@ -/** -* @version: 3.1 -* @author: Dan Grossman http://www.dangrossman.info/ -* @copyright: Copyright (c) 2012-2019 Dan Grossman. All rights reserved. -* @license: Licensed under the MIT license. See http://www.opensource.org/licenses/mit-license.php -* @website: http://www.daterangepicker.com/ -*/ -// Following the UMD template https://github.com/umdjs/umd/blob/master/templates/returnExportsGlobal.js -(function (root, factory) { - if (typeof define === 'function' && define.amd) { - // AMD. Make globaly available as well - define(['moment', 'jquery'], function (moment, jquery) { - if (!jquery.fn) jquery.fn = {}; // webpack server rendering - if (typeof moment !== 'function' && moment.hasOwnProperty('default')) moment = moment['default'] - return factory(moment, jquery); - }); - } else if (typeof module === 'object' && module.exports) { - // Node / Browserify - //isomorphic issue - var jQuery = (typeof window != 'undefined') ? window.jQuery : undefined; - if (!jQuery) { - jQuery = require('jquery'); - if (!jQuery.fn) jQuery.fn = {}; - } - var moment = (typeof window != 'undefined' && typeof window.moment != 'undefined') ? window.moment : require('moment'); - module.exports = factory(moment, jQuery); - } else { - // Browser globals - root.daterangepicker = factory(root.moment, root.jQuery); - } -}(this, function(moment, $) { - var DateRangePicker = function(element, options, cb) { - - //default settings for options - this.parentEl = 'body'; - this.element = $(element); - this.startDate = moment().startOf('day'); - this.endDate = moment().endOf('day'); - this.minDate = false; - this.maxDate = false; - this.maxSpan = false; - this.autoApply = false; - this.singleDatePicker = false; - this.showDropdowns = false; - this.minYear = moment().subtract(100, 'year').format('YYYY'); - this.maxYear = moment().add(100, 'year').format('YYYY'); - this.showWeekNumbers = false; - this.showISOWeekNumbers = false; - this.showCustomRangeLabel = true; - this.timePicker = false; - this.timePicker24Hour = false; - this.timePickerIncrement = 1; - this.timePickerSeconds = false; - this.linkedCalendars = true; - this.autoUpdateInput = true; - this.alwaysShowCalendars = false; - this.ranges = {}; - - this.opens = 'right'; - if (this.element.hasClass('pull-right')) - this.opens = 'left'; - - this.drops = 'down'; - if (this.element.hasClass('dropup')) - this.drops = 'up'; - - this.buttonClasses = 'btn btn-sm'; - this.applyButtonClasses = 'btn-primary'; - this.cancelButtonClasses = 'btn-default'; - - this.locale = { - direction: 'ltr', - format: moment.localeData().longDateFormat('L'), - separator: ' - ', - applyLabel: 'Apply', - cancelLabel: 'Cancel', - weekLabel: 'W', - customRangeLabel: 'Custom Range', - daysOfWeek: moment.weekdaysMin(), - monthNames: moment.monthsShort(), - firstDay: moment.localeData().firstDayOfWeek() - }; - - this.callback = function() { }; - - //some state information - this.isShowing = false; - this.leftCalendar = {}; - this.rightCalendar = {}; - - //custom options from user - if (typeof options !== 'object' || options === null) - options = {}; - - //allow setting options with data attributes - //data-api options will be overwritten with custom javascript options - options = $.extend(this.element.data(), options); - - //html template for the picker UI - if (typeof options.template !== 'string' && !(options.template instanceof $)) - options.template = - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '
' + - '' + - '' + - ' ' + - '
' + - '
'; - - this.parentEl = (options.parentEl && $(options.parentEl).length) ? $(options.parentEl) : $(this.parentEl); - this.container = $(options.template).appendTo(this.parentEl); - - // - // handle all the possible options overriding defaults - // - - if (typeof options.locale === 'object') { - - if (typeof options.locale.direction === 'string') - this.locale.direction = options.locale.direction; - - if (typeof options.locale.format === 'string') - this.locale.format = options.locale.format; - - if (typeof options.locale.separator === 'string') - this.locale.separator = options.locale.separator; - - if (typeof options.locale.daysOfWeek === 'object') - this.locale.daysOfWeek = options.locale.daysOfWeek.slice(); - - if (typeof options.locale.monthNames === 'object') - this.locale.monthNames = options.locale.monthNames.slice(); - - if (typeof options.locale.firstDay === 'number') - this.locale.firstDay = options.locale.firstDay; - - if (typeof options.locale.applyLabel === 'string') - this.locale.applyLabel = options.locale.applyLabel; - - if (typeof options.locale.cancelLabel === 'string') - this.locale.cancelLabel = options.locale.cancelLabel; - - if (typeof options.locale.weekLabel === 'string') - this.locale.weekLabel = options.locale.weekLabel; - - if (typeof options.locale.customRangeLabel === 'string'){ - //Support unicode chars in the custom range name. - var elem = document.createElement('textarea'); - elem.innerHTML = options.locale.customRangeLabel; - var rangeHtml = elem.value; - this.locale.customRangeLabel = rangeHtml; - } - } - this.container.addClass(this.locale.direction); - - if (typeof options.startDate === 'string') - this.startDate = moment(options.startDate, this.locale.format); - - if (typeof options.endDate === 'string') - this.endDate = moment(options.endDate, this.locale.format); - - if (typeof options.minDate === 'string') - this.minDate = moment(options.minDate, this.locale.format); - - if (typeof options.maxDate === 'string') - this.maxDate = moment(options.maxDate, this.locale.format); - - if (typeof options.startDate === 'object') - this.startDate = moment(options.startDate); - - if (typeof options.endDate === 'object') - this.endDate = moment(options.endDate); - - if (typeof options.minDate === 'object') - this.minDate = moment(options.minDate); - - if (typeof options.maxDate === 'object') - this.maxDate = moment(options.maxDate); - - // sanity check for bad options - if (this.minDate && this.startDate.isBefore(this.minDate)) - this.startDate = this.minDate.clone(); - - // sanity check for bad options - if (this.maxDate && this.endDate.isAfter(this.maxDate)) - this.endDate = this.maxDate.clone(); - - if (typeof options.applyButtonClasses === 'string') - this.applyButtonClasses = options.applyButtonClasses; - - if (typeof options.applyClass === 'string') //backwards compat - this.applyButtonClasses = options.applyClass; - - if (typeof options.cancelButtonClasses === 'string') - this.cancelButtonClasses = options.cancelButtonClasses; - - if (typeof options.cancelClass === 'string') //backwards compat - this.cancelButtonClasses = options.cancelClass; - - if (typeof options.maxSpan === 'object') - this.maxSpan = options.maxSpan; - - if (typeof options.dateLimit === 'object') //backwards compat - this.maxSpan = options.dateLimit; - - if (typeof options.opens === 'string') - this.opens = options.opens; - - if (typeof options.drops === 'string') - this.drops = options.drops; - - if (typeof options.showWeekNumbers === 'boolean') - this.showWeekNumbers = options.showWeekNumbers; - - if (typeof options.showISOWeekNumbers === 'boolean') - this.showISOWeekNumbers = options.showISOWeekNumbers; - - if (typeof options.buttonClasses === 'string') - this.buttonClasses = options.buttonClasses; - - if (typeof options.buttonClasses === 'object') - this.buttonClasses = options.buttonClasses.join(' '); - - if (typeof options.showDropdowns === 'boolean') - this.showDropdowns = options.showDropdowns; - - if (typeof options.minYear === 'number') - this.minYear = options.minYear; - - if (typeof options.maxYear === 'number') - this.maxYear = options.maxYear; - - if (typeof options.showCustomRangeLabel === 'boolean') - this.showCustomRangeLabel = options.showCustomRangeLabel; - - if (typeof options.singleDatePicker === 'boolean') { - this.singleDatePicker = options.singleDatePicker; - if (this.singleDatePicker) - this.endDate = this.startDate.clone(); - } - - if (typeof options.timePicker === 'boolean') - this.timePicker = options.timePicker; - - if (typeof options.timePickerSeconds === 'boolean') - this.timePickerSeconds = options.timePickerSeconds; - - if (typeof options.timePickerIncrement === 'number') - this.timePickerIncrement = options.timePickerIncrement; - - if (typeof options.timePicker24Hour === 'boolean') - this.timePicker24Hour = options.timePicker24Hour; - - if (typeof options.autoApply === 'boolean') - this.autoApply = options.autoApply; - - if (typeof options.autoUpdateInput === 'boolean') - this.autoUpdateInput = options.autoUpdateInput; - - if (typeof options.linkedCalendars === 'boolean') - this.linkedCalendars = options.linkedCalendars; - - if (typeof options.isInvalidDate === 'function') - this.isInvalidDate = options.isInvalidDate; - - if (typeof options.isCustomDate === 'function') - this.isCustomDate = options.isCustomDate; - - if (typeof options.alwaysShowCalendars === 'boolean') - this.alwaysShowCalendars = options.alwaysShowCalendars; - - // update day names order to firstDay - if (this.locale.firstDay != 0) { - var iterator = this.locale.firstDay; - while (iterator > 0) { - this.locale.daysOfWeek.push(this.locale.daysOfWeek.shift()); - iterator--; - } - } - - var start, end, range; - - //if no start/end dates set, check if an input element contains initial values - if (typeof options.startDate === 'undefined' && typeof options.endDate === 'undefined') { - if ($(this.element).is(':text')) { - var val = $(this.element).val(), - split = val.split(this.locale.separator); - - start = end = null; - - if (split.length == 2) { - start = moment(split[0], this.locale.format); - end = moment(split[1], this.locale.format); - } else if (this.singleDatePicker && val !== "") { - start = moment(val, this.locale.format); - end = moment(val, this.locale.format); - } - if (start !== null && end !== null) { - this.setStartDate(start); - this.setEndDate(end); - } - } - } - - if (typeof options.ranges === 'object') { - for (range in options.ranges) { - - if (typeof options.ranges[range][0] === 'string') - start = moment(options.ranges[range][0], this.locale.format); - else - start = moment(options.ranges[range][0]); - - if (typeof options.ranges[range][1] === 'string') - end = moment(options.ranges[range][1], this.locale.format); - else - end = moment(options.ranges[range][1]); - - // If the start or end date exceed those allowed by the minDate or maxSpan - // options, shorten the range to the allowable period. - if (this.minDate && start.isBefore(this.minDate)) - start = this.minDate.clone(); - - var maxDate = this.maxDate; - if (this.maxSpan && maxDate && start.clone().add(this.maxSpan).isAfter(maxDate)) - maxDate = start.clone().add(this.maxSpan); - if (maxDate && end.isAfter(maxDate)) - end = maxDate.clone(); - - // If the end of the range is before the minimum or the start of the range is - // after the maximum, don't display this range option at all. - if ((this.minDate && end.isBefore(this.minDate, this.timepicker ? 'minute' : 'day')) - || (maxDate && start.isAfter(maxDate, this.timepicker ? 'minute' : 'day'))) - continue; - - //Support unicode chars in the range names. - var elem = document.createElement('textarea'); - elem.innerHTML = range; - var rangeHtml = elem.value; - - this.ranges[rangeHtml] = [start, end]; - } - - var list = '
    '; - for (range in this.ranges) { - list += '
  • ' + range + '
  • '; - } - if (this.showCustomRangeLabel) { - list += '
  • ' + this.locale.customRangeLabel + '
  • '; - } - list += '
'; - this.container.find('.ranges').prepend(list); - } - - if (typeof cb === 'function') { - this.callback = cb; - } - - if (!this.timePicker) { - this.startDate = this.startDate.startOf('day'); - this.endDate = this.endDate.endOf('day'); - this.container.find('.calendar-time').hide(); - } - - //can't be used together for now - if (this.timePicker && this.autoApply) - this.autoApply = false; - - if (this.autoApply) { - this.container.addClass('auto-apply'); - } - - if (typeof options.ranges === 'object') - this.container.addClass('show-ranges'); - - if (this.singleDatePicker) { - this.container.addClass('single'); - this.container.find('.drp-calendar.left').addClass('single'); - this.container.find('.drp-calendar.left').show(); - this.container.find('.drp-calendar.right').hide(); - if (!this.timePicker && this.autoApply) { - this.container.addClass('auto-apply'); - } - } - - if ((typeof options.ranges === 'undefined' && !this.singleDatePicker) || this.alwaysShowCalendars) { - this.container.addClass('show-calendar'); - } - - this.container.addClass('opens' + this.opens); - - //apply CSS classes and labels to buttons - this.container.find('.applyBtn, .cancelBtn').addClass(this.buttonClasses); - if (this.applyButtonClasses.length) - this.container.find('.applyBtn').addClass(this.applyButtonClasses); - if (this.cancelButtonClasses.length) - this.container.find('.cancelBtn').addClass(this.cancelButtonClasses); - this.container.find('.applyBtn').html(this.locale.applyLabel); - this.container.find('.cancelBtn').html(this.locale.cancelLabel); - - // - // event listeners - // - - this.container.find('.drp-calendar') - .on('click.daterangepicker', '.prev', $.proxy(this.clickPrev, this)) - .on('click.daterangepicker', '.next', $.proxy(this.clickNext, this)) - .on('mousedown.daterangepicker', 'td.available', $.proxy(this.clickDate, this)) - .on('mouseenter.daterangepicker', 'td.available', $.proxy(this.hoverDate, this)) - .on('change.daterangepicker', 'select.yearselect', $.proxy(this.monthOrYearChanged, this)) - .on('change.daterangepicker', 'select.monthselect', $.proxy(this.monthOrYearChanged, this)) - .on('change.daterangepicker', 'select.hourselect,select.minuteselect,select.secondselect,select.ampmselect', $.proxy(this.timeChanged, this)); - - this.container.find('.ranges') - .on('click.daterangepicker', 'li', $.proxy(this.clickRange, this)); - - this.container.find('.drp-buttons') - .on('click.daterangepicker', 'button.applyBtn', $.proxy(this.clickApply, this)) - .on('click.daterangepicker', 'button.cancelBtn', $.proxy(this.clickCancel, this)); - - if (this.element.is('input') || this.element.is('button')) { - this.element.on({ - 'click.daterangepicker': $.proxy(this.show, this), - 'focus.daterangepicker': $.proxy(this.show, this), - 'keyup.daterangepicker': $.proxy(this.elementChanged, this), - 'keydown.daterangepicker': $.proxy(this.keydown, this) //IE 11 compatibility - }); - } else { - this.element.on('click.daterangepicker', $.proxy(this.toggle, this)); - this.element.on('keydown.daterangepicker', $.proxy(this.toggle, this)); - } - - // - // if attached to a text input, set the initial value - // - - this.updateElement(); - - }; - - DateRangePicker.prototype = { - - constructor: DateRangePicker, - - setStartDate: function(startDate) { - if (typeof startDate === 'string') - this.startDate = moment(startDate, this.locale.format); - - if (typeof startDate === 'object') - this.startDate = moment(startDate); - - if (!this.timePicker) - this.startDate = this.startDate.startOf('day'); - - if (this.timePicker && this.timePickerIncrement) - this.startDate.minute(Math.round(this.startDate.minute() / this.timePickerIncrement) * this.timePickerIncrement); - - if (this.minDate && this.startDate.isBefore(this.minDate)) { - this.startDate = this.minDate.clone(); - if (this.timePicker && this.timePickerIncrement) - this.startDate.minute(Math.round(this.startDate.minute() / this.timePickerIncrement) * this.timePickerIncrement); - } - - if (this.maxDate && this.startDate.isAfter(this.maxDate)) { - this.startDate = this.maxDate.clone(); - if (this.timePicker && this.timePickerIncrement) - this.startDate.minute(Math.floor(this.startDate.minute() / this.timePickerIncrement) * this.timePickerIncrement); - } - - if (!this.isShowing) - this.updateElement(); - - this.updateMonthsInView(); - }, - - setEndDate: function(endDate) { - if (typeof endDate === 'string') - this.endDate = moment(endDate, this.locale.format); - - if (typeof endDate === 'object') - this.endDate = moment(endDate); - - if (!this.timePicker) - this.endDate = this.endDate.endOf('day'); - - if (this.timePicker && this.timePickerIncrement) - this.endDate.minute(Math.round(this.endDate.minute() / this.timePickerIncrement) * this.timePickerIncrement); - - if (this.endDate.isBefore(this.startDate)) - this.endDate = this.startDate.clone(); - - if (this.maxDate && this.endDate.isAfter(this.maxDate)) - this.endDate = this.maxDate.clone(); - - if (this.maxSpan && this.startDate.clone().add(this.maxSpan).isBefore(this.endDate)) - this.endDate = this.startDate.clone().add(this.maxSpan); - - this.previousRightTime = this.endDate.clone(); - - this.container.find('.drp-selected').html(this.startDate.format(this.locale.format) + this.locale.separator + this.endDate.format(this.locale.format)); - - if (!this.isShowing) - this.updateElement(); - - this.updateMonthsInView(); - }, - - isInvalidDate: function() { - return false; - }, - - isCustomDate: function() { - return false; - }, - - updateView: function() { - if (this.timePicker) { - this.renderTimePicker('left'); - this.renderTimePicker('right'); - if (!this.endDate) { - this.container.find('.right .calendar-time select').prop('disabled', true).addClass('disabled'); - } else { - this.container.find('.right .calendar-time select').prop('disabled', false).removeClass('disabled'); - } - } - if (this.endDate) - this.container.find('.drp-selected').html(this.startDate.format(this.locale.format) + this.locale.separator + this.endDate.format(this.locale.format)); - this.updateMonthsInView(); - this.updateCalendars(); - this.updateFormInputs(); - }, - - updateMonthsInView: function() { - if (this.endDate) { - - //if both dates are visible already, do nothing - if (!this.singleDatePicker && this.leftCalendar.month && this.rightCalendar.month && - (this.startDate.format('YYYY-MM') == this.leftCalendar.month.format('YYYY-MM') || this.startDate.format('YYYY-MM') == this.rightCalendar.month.format('YYYY-MM')) - && - (this.endDate.format('YYYY-MM') == this.leftCalendar.month.format('YYYY-MM') || this.endDate.format('YYYY-MM') == this.rightCalendar.month.format('YYYY-MM')) - ) { - return; - } - - this.leftCalendar.month = this.startDate.clone().date(2); - if (!this.linkedCalendars && (this.endDate.month() != this.startDate.month() || this.endDate.year() != this.startDate.year())) { - this.rightCalendar.month = this.endDate.clone().date(2); - } else { - this.rightCalendar.month = this.startDate.clone().date(2).add(1, 'month'); - } - - } else { - if (this.leftCalendar.month.format('YYYY-MM') != this.startDate.format('YYYY-MM') && this.rightCalendar.month.format('YYYY-MM') != this.startDate.format('YYYY-MM')) { - this.leftCalendar.month = this.startDate.clone().date(2); - this.rightCalendar.month = this.startDate.clone().date(2).add(1, 'month'); - } - } - if (this.maxDate && this.linkedCalendars && !this.singleDatePicker && this.rightCalendar.month > this.maxDate) { - this.rightCalendar.month = this.maxDate.clone().date(2); - this.leftCalendar.month = this.maxDate.clone().date(2).subtract(1, 'month'); - } - }, - - updateCalendars: function() { - - if (this.timePicker) { - var hour, minute, second; - if (this.endDate) { - hour = parseInt(this.container.find('.left .hourselect').val(), 10); - minute = parseInt(this.container.find('.left .minuteselect').val(), 10); - if (isNaN(minute)) { - minute = parseInt(this.container.find('.left .minuteselect option:last').val(), 10); - } - second = this.timePickerSeconds ? parseInt(this.container.find('.left .secondselect').val(), 10) : 0; - if (!this.timePicker24Hour) { - var ampm = this.container.find('.left .ampmselect').val(); - if (ampm === 'PM' && hour < 12) - hour += 12; - if (ampm === 'AM' && hour === 12) - hour = 0; - } - } else { - hour = parseInt(this.container.find('.right .hourselect').val(), 10); - minute = parseInt(this.container.find('.right .minuteselect').val(), 10); - if (isNaN(minute)) { - minute = parseInt(this.container.find('.right .minuteselect option:last').val(), 10); - } - second = this.timePickerSeconds ? parseInt(this.container.find('.right .secondselect').val(), 10) : 0; - if (!this.timePicker24Hour) { - var ampm = this.container.find('.right .ampmselect').val(); - if (ampm === 'PM' && hour < 12) - hour += 12; - if (ampm === 'AM' && hour === 12) - hour = 0; - } - } - this.leftCalendar.month.hour(hour).minute(minute).second(second); - this.rightCalendar.month.hour(hour).minute(minute).second(second); - } - - this.renderCalendar('left'); - this.renderCalendar('right'); - - //highlight any predefined range matching the current start and end dates - this.container.find('.ranges li').removeClass('active'); - if (this.endDate == null) return; - - this.calculateChosenLabel(); - }, - - renderCalendar: function(side) { - - // - // Build the matrix of dates that will populate the calendar - // - - var calendar = side == 'left' ? this.leftCalendar : this.rightCalendar; - var month = calendar.month.month(); - var year = calendar.month.year(); - var hour = calendar.month.hour(); - var minute = calendar.month.minute(); - var second = calendar.month.second(); - var daysInMonth = moment([year, month]).daysInMonth(); - var firstDay = moment([year, month, 1]); - var lastDay = moment([year, month, daysInMonth]); - var lastMonth = moment(firstDay).subtract(1, 'month').month(); - var lastYear = moment(firstDay).subtract(1, 'month').year(); - var daysInLastMonth = moment([lastYear, lastMonth]).daysInMonth(); - var dayOfWeek = firstDay.day(); - - //initialize a 6 rows x 7 columns array for the calendar - var calendar = []; - calendar.firstDay = firstDay; - calendar.lastDay = lastDay; - - for (var i = 0; i < 6; i++) { - calendar[i] = []; - } - - //populate the calendar with date objects - var startDay = daysInLastMonth - dayOfWeek + this.locale.firstDay + 1; - if (startDay > daysInLastMonth) - startDay -= 7; - - if (dayOfWeek == this.locale.firstDay) - startDay = daysInLastMonth - 6; - - var curDate = moment([lastYear, lastMonth, startDay, 12, minute, second]); - - var col, row; - for (var i = 0, col = 0, row = 0; i < 42; i++, col++, curDate = moment(curDate).add(24, 'hour')) { - if (i > 0 && col % 7 === 0) { - col = 0; - row++; - } - calendar[row][col] = curDate.clone().hour(hour).minute(minute).second(second); - curDate.hour(12); - - if (this.minDate && calendar[row][col].format('YYYY-MM-DD') == this.minDate.format('YYYY-MM-DD') && calendar[row][col].isBefore(this.minDate) && side == 'left') { - calendar[row][col] = this.minDate.clone(); - } - - if (this.maxDate && calendar[row][col].format('YYYY-MM-DD') == this.maxDate.format('YYYY-MM-DD') && calendar[row][col].isAfter(this.maxDate) && side == 'right') { - calendar[row][col] = this.maxDate.clone(); - } - - } - - //make the calendar object available to hoverDate/clickDate - if (side == 'left') { - this.leftCalendar.calendar = calendar; - } else { - this.rightCalendar.calendar = calendar; - } - - // - // Display the calendar - // - - var minDate = side == 'left' ? this.minDate : this.startDate; - var maxDate = this.maxDate; - var selected = side == 'left' ? this.startDate : this.endDate; - var arrow = this.locale.direction == 'ltr' ? {left: 'chevron-left', right: 'chevron-right'} : {left: 'chevron-right', right: 'chevron-left'}; - - var html = ''; - html += ''; - html += ''; - - // add empty cell for week number - if (this.showWeekNumbers || this.showISOWeekNumbers) - html += ''; - - if ((!minDate || minDate.isBefore(calendar.firstDay)) && (!this.linkedCalendars || side == 'left')) { - html += ''; - } else { - html += ''; - } - - var dateHtml = this.locale.monthNames[calendar[1][1].month()] + calendar[1][1].format(" YYYY"); - - if (this.showDropdowns) { - var currentMonth = calendar[1][1].month(); - var currentYear = calendar[1][1].year(); - var maxYear = (maxDate && maxDate.year()) || (this.maxYear); - var minYear = (minDate && minDate.year()) || (this.minYear); - var inMinYear = currentYear == minYear; - var inMaxYear = currentYear == maxYear; - - var monthHtml = '"; - - var yearHtml = ''; - - dateHtml = monthHtml + yearHtml; - } - - html += ''; - if ((!maxDate || maxDate.isAfter(calendar.lastDay)) && (!this.linkedCalendars || side == 'right' || this.singleDatePicker)) { - html += ''; - } else { - html += ''; - } - - html += ''; - html += ''; - - // add week number label - if (this.showWeekNumbers || this.showISOWeekNumbers) - html += ''; - - $.each(this.locale.daysOfWeek, function(index, dayOfWeek) { - html += ''; - }); - - html += ''; - html += ''; - html += ''; - - //adjust maxDate to reflect the maxSpan setting in order to - //grey out end dates beyond the maxSpan - if (this.endDate == null && this.maxSpan) { - var maxLimit = this.startDate.clone().add(this.maxSpan).endOf('day'); - if (!maxDate || maxLimit.isBefore(maxDate)) { - maxDate = maxLimit; - } - } - - for (var row = 0; row < 6; row++) { - html += ''; - - // add week number - if (this.showWeekNumbers) - html += ''; - else if (this.showISOWeekNumbers) - html += ''; - - for (var col = 0; col < 7; col++) { - - var classes = []; - - //highlight today's date - if (calendar[row][col].isSame(new Date(), "day")) - classes.push('today'); - - //highlight weekends - if (calendar[row][col].isoWeekday() > 5) - classes.push('weekend'); - - //grey out the dates in other months displayed at beginning and end of this calendar - if (calendar[row][col].month() != calendar[1][1].month()) - classes.push('off', 'ends'); - - //don't allow selection of dates before the minimum date - if (this.minDate && calendar[row][col].isBefore(this.minDate, 'day')) - classes.push('off', 'disabled'); - - //don't allow selection of dates after the maximum date - if (maxDate && calendar[row][col].isAfter(maxDate, 'day')) - classes.push('off', 'disabled'); - - //don't allow selection of date if a custom function decides it's invalid - if (this.isInvalidDate(calendar[row][col])) - classes.push('off', 'disabled'); - - //highlight the currently selected start date - if (calendar[row][col].format('YYYY-MM-DD') == this.startDate.format('YYYY-MM-DD')) - classes.push('active', 'start-date'); - - //highlight the currently selected end date - if (this.endDate != null && calendar[row][col].format('YYYY-MM-DD') == this.endDate.format('YYYY-MM-DD')) - classes.push('active', 'end-date'); - - //highlight dates in-between the selected dates - if (this.endDate != null && calendar[row][col] > this.startDate && calendar[row][col] < this.endDate) - classes.push('in-range'); - - //apply custom classes for this date - var isCustom = this.isCustomDate(calendar[row][col]); - if (isCustom !== false) { - if (typeof isCustom === 'string') - classes.push(isCustom); - else - Array.prototype.push.apply(classes, isCustom); - } - - var cname = '', disabled = false; - for (var i = 0; i < classes.length; i++) { - cname += classes[i] + ' '; - if (classes[i] == 'disabled') - disabled = true; - } - if (!disabled) - cname += 'available'; - - html += ''; - - } - html += ''; - } - - html += ''; - html += '
' + dateHtml + '
' + this.locale.weekLabel + '' + dayOfWeek + '
' + calendar[row][0].week() + '' + calendar[row][0].isoWeek() + '' + calendar[row][col].date() + '
'; - - this.container.find('.drp-calendar.' + side + ' .calendar-table').html(html); - - }, - - renderTimePicker: function(side) { - - // Don't bother updating the time picker if it's currently disabled - // because an end date hasn't been clicked yet - if (side == 'right' && !this.endDate) return; - - var html, selected, minDate, maxDate = this.maxDate; - - if (this.maxSpan && (!this.maxDate || this.startDate.clone().add(this.maxSpan).isBefore(this.maxDate))) - maxDate = this.startDate.clone().add(this.maxSpan); - - if (side == 'left') { - selected = this.startDate.clone(); - minDate = this.minDate; - } else if (side == 'right') { - selected = this.endDate.clone(); - minDate = this.startDate; - - //Preserve the time already selected - var timeSelector = this.container.find('.drp-calendar.right .calendar-time'); - if (timeSelector.html() != '') { - - selected.hour(!isNaN(selected.hour()) ? selected.hour() : timeSelector.find('.hourselect option:selected').val()); - selected.minute(!isNaN(selected.minute()) ? selected.minute() : timeSelector.find('.minuteselect option:selected').val()); - selected.second(!isNaN(selected.second()) ? selected.second() : timeSelector.find('.secondselect option:selected').val()); - - if (!this.timePicker24Hour) { - var ampm = timeSelector.find('.ampmselect option:selected').val(); - if (ampm === 'PM' && selected.hour() < 12) - selected.hour(selected.hour() + 12); - if (ampm === 'AM' && selected.hour() === 12) - selected.hour(0); - } - - } - - if (selected.isBefore(this.startDate)) - selected = this.startDate.clone(); - - if (maxDate && selected.isAfter(maxDate)) - selected = maxDate.clone(); - - } - - // - // hours - // - - html = ' '; - - // - // minutes - // - - html += ': '; - - // - // seconds - // - - if (this.timePickerSeconds) { - html += ': '; - } - - // - // AM/PM - // - - if (!this.timePicker24Hour) { - html += ''; - } - - this.container.find('.drp-calendar.' + side + ' .calendar-time').html(html); - - }, - - updateFormInputs: function() { - - if (this.singleDatePicker || (this.endDate && (this.startDate.isBefore(this.endDate) || this.startDate.isSame(this.endDate)))) { - this.container.find('button.applyBtn').prop('disabled', false); - } else { - this.container.find('button.applyBtn').prop('disabled', true); - } - - }, - - move: function() { - var parentOffset = { top: 0, left: 0 }, - containerTop, - drops = this.drops; - - var parentRightEdge = $(window).width(); - if (!this.parentEl.is('body')) { - parentOffset = { - top: this.parentEl.offset().top - this.parentEl.scrollTop(), - left: this.parentEl.offset().left - this.parentEl.scrollLeft() - }; - parentRightEdge = this.parentEl[0].clientWidth + this.parentEl.offset().left; - } - - switch (drops) { - case 'auto': - containerTop = this.element.offset().top + this.element.outerHeight() - parentOffset.top; - if (containerTop + this.container.outerHeight() >= this.parentEl[0].scrollHeight) { - containerTop = this.element.offset().top - this.container.outerHeight() - parentOffset.top; - drops = 'up'; - } - break; - case 'up': - containerTop = this.element.offset().top - this.container.outerHeight() - parentOffset.top; - break; - default: - containerTop = this.element.offset().top + this.element.outerHeight() - parentOffset.top; - break; - } - - // Force the container to it's actual width - this.container.css({ - top: 0, - left: 0, - right: 'auto' - }); - var containerWidth = this.container.outerWidth(); - - this.container.toggleClass('drop-up', drops == 'up'); - - if (this.opens == 'left') { - var containerRight = parentRightEdge - this.element.offset().left - this.element.outerWidth(); - if (containerWidth + containerRight > $(window).width()) { - this.container.css({ - top: containerTop, - right: 'auto', - left: 9 - }); - } else { - this.container.css({ - top: containerTop, - right: containerRight, - left: 'auto' - }); - } - } else if (this.opens == 'center') { - var containerLeft = this.element.offset().left - parentOffset.left + this.element.outerWidth() / 2 - - containerWidth / 2; - if (containerLeft < 0) { - this.container.css({ - top: containerTop, - right: 'auto', - left: 9 - }); - } else if (containerLeft + containerWidth > $(window).width()) { - this.container.css({ - top: containerTop, - left: 'auto', - right: 0 - }); - } else { - this.container.css({ - top: containerTop, - left: containerLeft, - right: 'auto' - }); - } - } else { - var containerLeft = this.element.offset().left - parentOffset.left; - if (containerLeft + containerWidth > $(window).width()) { - this.container.css({ - top: containerTop, - left: 'auto', - right: 0 - }); - } else { - this.container.css({ - top: containerTop, - left: containerLeft, - right: 'auto' - }); - } - } - }, - - show: function(e) { - if (this.isShowing) return; - - // Create a click proxy that is private to this instance of datepicker, for unbinding - this._outsideClickProxy = $.proxy(function(e) { this.outsideClick(e); }, this); - - // Bind global datepicker mousedown for hiding and - $(document) - .on('mousedown.daterangepicker', this._outsideClickProxy) - // also support mobile devices - .on('touchend.daterangepicker', this._outsideClickProxy) - // also explicitly play nice with Bootstrap dropdowns, which stopPropagation when clicking them - .on('click.daterangepicker', '[data-toggle=dropdown]', this._outsideClickProxy) - // and also close when focus changes to outside the picker (eg. tabbing between controls) - .on('focusin.daterangepicker', this._outsideClickProxy); - - // Reposition the picker if the window is resized while it's open - $(window).on('resize.daterangepicker', $.proxy(function(e) { this.move(e); }, this)); - - this.oldStartDate = this.startDate.clone(); - this.oldEndDate = this.endDate.clone(); - this.previousRightTime = this.endDate.clone(); - - this.updateView(); - this.container.show(); - this.move(); - this.element.trigger('show.daterangepicker', this); - this.isShowing = true; - }, - - hide: function(e) { - if (!this.isShowing) return; - - //incomplete date selection, revert to last values - if (!this.endDate) { - this.startDate = this.oldStartDate.clone(); - this.endDate = this.oldEndDate.clone(); - } - - //if a new date range was selected, invoke the user callback function - if (!this.startDate.isSame(this.oldStartDate) || !this.endDate.isSame(this.oldEndDate)) - this.callback(this.startDate.clone(), this.endDate.clone(), this.chosenLabel); - - //if picker is attached to a text input, update it - this.updateElement(); - - $(document).off('.daterangepicker'); - $(window).off('.daterangepicker'); - this.container.hide(); - this.element.trigger('hide.daterangepicker', this); - this.isShowing = false; - }, - - toggle: function(e) { - if (this.isShowing) { - this.hide(); - } else { - this.show(); - } - }, - - outsideClick: function(e) { - var target = $(e.target); - // if the page is clicked anywhere except within the daterangerpicker/button - // itself then call this.hide() - if ( - // ie modal dialog fix - e.type == "focusin" || - target.closest(this.element).length || - target.closest(this.container).length || - target.closest('.calendar-table').length - ) return; - this.hide(); - this.element.trigger('outsideClick.daterangepicker', this); - }, - - showCalendars: function() { - this.container.addClass('show-calendar'); - this.move(); - this.element.trigger('showCalendar.daterangepicker', this); - }, - - hideCalendars: function() { - this.container.removeClass('show-calendar'); - this.element.trigger('hideCalendar.daterangepicker', this); - }, - - clickRange: function(e) { - var label = e.target.getAttribute('data-range-key'); - this.chosenLabel = label; - if (label == this.locale.customRangeLabel) { - this.showCalendars(); - } else { - var dates = this.ranges[label]; - this.startDate = dates[0]; - this.endDate = dates[1]; - - if (!this.timePicker) { - this.startDate.startOf('day'); - this.endDate.endOf('day'); - } - - if (!this.alwaysShowCalendars) - this.hideCalendars(); - this.clickApply(); - } - }, - - clickPrev: function(e) { - var cal = $(e.target).parents('.drp-calendar'); - if (cal.hasClass('left')) { - this.leftCalendar.month.subtract(1, 'month'); - if (this.linkedCalendars) - this.rightCalendar.month.subtract(1, 'month'); - } else { - this.rightCalendar.month.subtract(1, 'month'); - } - this.updateCalendars(); - }, - - clickNext: function(e) { - var cal = $(e.target).parents('.drp-calendar'); - if (cal.hasClass('left')) { - this.leftCalendar.month.add(1, 'month'); - } else { - this.rightCalendar.month.add(1, 'month'); - if (this.linkedCalendars) - this.leftCalendar.month.add(1, 'month'); - } - this.updateCalendars(); - }, - - hoverDate: function(e) { - - //ignore dates that can't be selected - if (!$(e.target).hasClass('available')) return; - - var title = $(e.target).attr('data-title'); - var row = title.substr(1, 1); - var col = title.substr(3, 1); - var cal = $(e.target).parents('.drp-calendar'); - var date = cal.hasClass('left') ? this.leftCalendar.calendar[row][col] : this.rightCalendar.calendar[row][col]; - - //highlight the dates between the start date and the date being hovered as a potential end date - var leftCalendar = this.leftCalendar; - var rightCalendar = this.rightCalendar; - var startDate = this.startDate; - if (!this.endDate) { - this.container.find('.drp-calendar tbody td').each(function(index, el) { - - //skip week numbers, only look at dates - if ($(el).hasClass('week')) return; - - var title = $(el).attr('data-title'); - var row = title.substr(1, 1); - var col = title.substr(3, 1); - var cal = $(el).parents('.drp-calendar'); - var dt = cal.hasClass('left') ? leftCalendar.calendar[row][col] : rightCalendar.calendar[row][col]; - - if ((dt.isAfter(startDate) && dt.isBefore(date)) || dt.isSame(date, 'day')) { - $(el).addClass('in-range'); - } else { - $(el).removeClass('in-range'); - } - - }); - } - - }, - - clickDate: function(e) { - - if (!$(e.target).hasClass('available')) return; - - var title = $(e.target).attr('data-title'); - var row = title.substr(1, 1); - var col = title.substr(3, 1); - var cal = $(e.target).parents('.drp-calendar'); - var date = cal.hasClass('left') ? this.leftCalendar.calendar[row][col] : this.rightCalendar.calendar[row][col]; - - // - // this function needs to do a few things: - // * alternate between selecting a start and end date for the range, - // * if the time picker is enabled, apply the hour/minute/second from the select boxes to the clicked date - // * if autoapply is enabled, and an end date was chosen, apply the selection - // * if single date picker mode, and time picker isn't enabled, apply the selection immediately - // * if one of the inputs above the calendars was focused, cancel that manual input - // - - if (this.endDate || date.isBefore(this.startDate, 'day')) { //picking start - if (this.timePicker) { - var hour = parseInt(this.container.find('.left .hourselect').val(), 10); - if (!this.timePicker24Hour) { - var ampm = this.container.find('.left .ampmselect').val(); - if (ampm === 'PM' && hour < 12) - hour += 12; - if (ampm === 'AM' && hour === 12) - hour = 0; - } - var minute = parseInt(this.container.find('.left .minuteselect').val(), 10); - if (isNaN(minute)) { - minute = parseInt(this.container.find('.left .minuteselect option:last').val(), 10); - } - var second = this.timePickerSeconds ? parseInt(this.container.find('.left .secondselect').val(), 10) : 0; - date = date.clone().hour(hour).minute(minute).second(second); - } - this.endDate = null; - this.setStartDate(date.clone()); - } else if (!this.endDate && date.isBefore(this.startDate)) { - //special case: clicking the same date for start/end, - //but the time of the end date is before the start date - this.setEndDate(this.startDate.clone()); - } else { // picking end - if (this.timePicker) { - var hour = parseInt(this.container.find('.right .hourselect').val(), 10); - if (!this.timePicker24Hour) { - var ampm = this.container.find('.right .ampmselect').val(); - if (ampm === 'PM' && hour < 12) - hour += 12; - if (ampm === 'AM' && hour === 12) - hour = 0; - } - var minute = parseInt(this.container.find('.right .minuteselect').val(), 10); - if (isNaN(minute)) { - minute = parseInt(this.container.find('.right .minuteselect option:last').val(), 10); - } - var second = this.timePickerSeconds ? parseInt(this.container.find('.right .secondselect').val(), 10) : 0; - date = date.clone().hour(hour).minute(minute).second(second); - } - this.setEndDate(date.clone()); - if (this.autoApply) { - this.calculateChosenLabel(); - this.clickApply(); - } - } - - if (this.singleDatePicker) { - this.setEndDate(this.startDate); - if (!this.timePicker && this.autoApply) - this.clickApply(); - } - - this.updateView(); - - //This is to cancel the blur event handler if the mouse was in one of the inputs - e.stopPropagation(); - - }, - - calculateChosenLabel: function () { - var customRange = true; - var i = 0; - for (var range in this.ranges) { - if (this.timePicker) { - var format = this.timePickerSeconds ? "YYYY-MM-DD HH:mm:ss" : "YYYY-MM-DD HH:mm"; - //ignore times when comparing dates if time picker seconds is not enabled - if (this.startDate.format(format) == this.ranges[range][0].format(format) && this.endDate.format(format) == this.ranges[range][1].format(format)) { - customRange = false; - this.chosenLabel = this.container.find('.ranges li:eq(' + i + ')').addClass('active').attr('data-range-key'); - break; - } - } else { - //ignore times when comparing dates if time picker is not enabled - if (this.startDate.format('YYYY-MM-DD') == this.ranges[range][0].format('YYYY-MM-DD') && this.endDate.format('YYYY-MM-DD') == this.ranges[range][1].format('YYYY-MM-DD')) { - customRange = false; - this.chosenLabel = this.container.find('.ranges li:eq(' + i + ')').addClass('active').attr('data-range-key'); - break; - } - } - i++; - } - if (customRange) { - if (this.showCustomRangeLabel) { - this.chosenLabel = this.container.find('.ranges li:last').addClass('active').attr('data-range-key'); - } else { - this.chosenLabel = null; - } - this.showCalendars(); - } - }, - - clickApply: function(e) { - this.hide(); - this.element.trigger('apply.daterangepicker', this); - }, - - clickCancel: function(e) { - this.startDate = this.oldStartDate; - this.endDate = this.oldEndDate; - this.hide(); - this.element.trigger('cancel.daterangepicker', this); - }, - - monthOrYearChanged: function(e) { - var isLeft = $(e.target).closest('.drp-calendar').hasClass('left'), - leftOrRight = isLeft ? 'left' : 'right', - cal = this.container.find('.drp-calendar.'+leftOrRight); - - // Month must be Number for new moment versions - var month = parseInt(cal.find('.monthselect').val(), 10); - var year = cal.find('.yearselect').val(); - - if (!isLeft) { - if (year < this.startDate.year() || (year == this.startDate.year() && month < this.startDate.month())) { - month = this.startDate.month(); - year = this.startDate.year(); - } - } - - if (this.minDate) { - if (year < this.minDate.year() || (year == this.minDate.year() && month < this.minDate.month())) { - month = this.minDate.month(); - year = this.minDate.year(); - } - } - - if (this.maxDate) { - if (year > this.maxDate.year() || (year == this.maxDate.year() && month > this.maxDate.month())) { - month = this.maxDate.month(); - year = this.maxDate.year(); - } - } - - if (isLeft) { - this.leftCalendar.month.month(month).year(year); - if (this.linkedCalendars) - this.rightCalendar.month = this.leftCalendar.month.clone().add(1, 'month'); - } else { - this.rightCalendar.month.month(month).year(year); - if (this.linkedCalendars) - this.leftCalendar.month = this.rightCalendar.month.clone().subtract(1, 'month'); - } - this.updateCalendars(); - }, - - timeChanged: function(e) { - - var cal = $(e.target).closest('.drp-calendar'), - isLeft = cal.hasClass('left'); - - var hour = parseInt(cal.find('.hourselect').val(), 10); - var minute = parseInt(cal.find('.minuteselect').val(), 10); - if (isNaN(minute)) { - minute = parseInt(cal.find('.minuteselect option:last').val(), 10); - } - var second = this.timePickerSeconds ? parseInt(cal.find('.secondselect').val(), 10) : 0; - - if (!this.timePicker24Hour) { - var ampm = cal.find('.ampmselect').val(); - if (ampm === 'PM' && hour < 12) - hour += 12; - if (ampm === 'AM' && hour === 12) - hour = 0; - } - - if (isLeft) { - var start = this.startDate.clone(); - start.hour(hour); - start.minute(minute); - start.second(second); - this.setStartDate(start); - if (this.singleDatePicker) { - this.endDate = this.startDate.clone(); - } else if (this.endDate && this.endDate.format('YYYY-MM-DD') == start.format('YYYY-MM-DD') && this.endDate.isBefore(start)) { - this.setEndDate(start.clone()); - } - } else if (this.endDate) { - var end = this.endDate.clone(); - end.hour(hour); - end.minute(minute); - end.second(second); - this.setEndDate(end); - } - - //update the calendars so all clickable dates reflect the new time component - this.updateCalendars(); - - //update the form inputs above the calendars with the new time - this.updateFormInputs(); - - //re-render the time pickers because changing one selection can affect what's enabled in another - this.renderTimePicker('left'); - this.renderTimePicker('right'); - - }, - - elementChanged: function() { - if (!this.element.is('input')) return; - if (!this.element.val().length) return; - - var dateString = this.element.val().split(this.locale.separator), - start = null, - end = null; - - if (dateString.length === 2) { - start = moment(dateString[0], this.locale.format); - end = moment(dateString[1], this.locale.format); - } - - if (this.singleDatePicker || start === null || end === null) { - start = moment(this.element.val(), this.locale.format); - end = start; - } - - if (!start.isValid() || !end.isValid()) return; - - this.setStartDate(start); - this.setEndDate(end); - this.updateView(); - }, - - keydown: function(e) { - //hide on tab or enter - if ((e.keyCode === 9) || (e.keyCode === 13)) { - this.hide(); - } - - //hide on esc and prevent propagation - if (e.keyCode === 27) { - e.preventDefault(); - e.stopPropagation(); - - this.hide(); - } - }, - - updateElement: function() { - if (this.element.is('input') && this.autoUpdateInput) { - var newValue = this.startDate.format(this.locale.format); - if (!this.singleDatePicker) { - newValue += this.locale.separator + this.endDate.format(this.locale.format); - } - if (newValue !== this.element.val()) { - this.element.val(newValue).trigger('change'); - } - } - }, - - remove: function() { - this.container.remove(); - this.element.off('.daterangepicker'); - this.element.removeData(); - } - - }; - - $.fn.daterangepicker = function(options, callback) { - var implementOptions = $.extend(true, {}, $.fn.daterangepicker.defaultOptions, options); - this.each(function() { - var el = $(this); - if (el.data('daterangepicker')) - el.data('daterangepicker').remove(); - el.data('daterangepicker', new DateRangePicker(el, implementOptions, callback)); - }); - return this; - }; - - return DateRangePicker; - -})); diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css deleted file mode 100644 index f16c5be871..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css +++ /dev/null @@ -1,11266 +0,0 @@ -@charset "UTF-8"; -/*! - * Bootstrap v5.1.3 (https://getbootstrap.com/) - * Copyright 2011-2021 The Bootstrap Authors - * Copyright 2011-2021 Twitter, Inc. - * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE) - */ -:root { - --bs-blue: #0d6efd; - --bs-indigo: #6610f2; - --bs-purple: #6f42c1; - --bs-pink: #d63384; - --bs-red: #dc3545; - --bs-orange: #fd7e14; - --bs-yellow: #ffc107; - --bs-green: #198754; - --bs-teal: #20c997; - --bs-cyan: #0dcaf0; - --bs-white: #fff; - --bs-gray: #6c757d; - --bs-gray-dark: #343a40; - --bs-gray-100: #f8f9fa; - --bs-gray-200: #e9ecef; - --bs-gray-300: #dee2e6; - --bs-gray-400: #ced4da; - --bs-gray-500: #adb5bd; - --bs-gray-600: #6c757d; - --bs-gray-700: #495057; - --bs-gray-800: #343a40; - --bs-gray-900: #212529; - --bs-primary: #0d6efd; - --bs-secondary: #6c757d; - --bs-success: #198754; - --bs-info: #0dcaf0; - --bs-warning: #ffc107; - --bs-danger: #dc3545; - --bs-light: #f8f9fa; - --bs-dark: #212529; - --bs-primary-rgb: 13, 110, 253; - --bs-secondary-rgb: 108, 117, 125; - --bs-success-rgb: 25, 135, 84; - --bs-info-rgb: 13, 202, 240; - --bs-warning-rgb: 255, 193, 7; - --bs-danger-rgb: 220, 53, 69; - --bs-light-rgb: 248, 249, 250; - --bs-dark-rgb: 33, 37, 41; - --bs-white-rgb: 255, 255, 255; - --bs-black-rgb: 0, 0, 0; - --bs-body-color-rgb: 33, 37, 41; - --bs-body-bg-rgb: 255, 255, 255; - --bs-font-sans-serif: system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, "Noto Sans", "Liberation Sans", sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji"; - --bs-font-monospace: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace; - --bs-gradient: linear-gradient(180deg, rgba(255, 255, 255, 0.15), rgba(255, 255, 255, 0)); - --bs-body-font-family: var(--bs-font-sans-serif); - --bs-body-font-size: 1rem; - --bs-body-font-weight: 400; - --bs-body-line-height: 1.5; - --bs-body-color: #212529; - --bs-body-bg: #fff; -} - -*, -*::before, -*::after { - box-sizing: border-box; -} - -@media (prefers-reduced-motion: no-preference) { - :root { - scroll-behavior: smooth; - } -} - -body { - margin: 0; - font-family: var(--bs-body-font-family); - font-size: var(--bs-body-font-size); - font-weight: var(--bs-body-font-weight); - line-height: var(--bs-body-line-height); - color: var(--bs-body-color); - text-align: var(--bs-body-text-align); - background-color: var(--bs-body-bg); - -webkit-text-size-adjust: 100%; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); -} - -hr { - margin: 1rem 0; - color: inherit; - background-color: currentColor; - border: 0; - opacity: 0.25; -} - -hr:not([size]) { - height: 1px; -} - -h6, .h6, h5, .h5, h4, .h4, h3, .h3, h2, .h2, h1, .h1 { - margin-top: 0; - margin-bottom: 0.5rem; - font-weight: 500; - line-height: 1.2; -} - -h1, .h1 { - font-size: calc(1.375rem + 1.5vw); -} -@media (min-width: 1200px) { - h1, .h1 { - font-size: 2.5rem; - } -} - -h2, .h2 { - font-size: calc(1.325rem + 0.9vw); -} -@media (min-width: 1200px) { - h2, .h2 { - font-size: 2rem; - } -} - -h3, .h3 { - font-size: calc(1.3rem + 0.6vw); -} -@media (min-width: 1200px) { - h3, .h3 { - font-size: 1.75rem; - } -} - -h4, .h4 { - font-size: calc(1.275rem + 0.3vw); -} -@media (min-width: 1200px) { - h4, .h4 { - font-size: 1.5rem; - } -} - -h5, .h5 { - font-size: 1.25rem; -} - -h6, .h6 { - font-size: 1rem; -} - -p { - margin-top: 0; - margin-bottom: 1rem; -} - -abbr[title], -abbr[data-bs-original-title] { - -webkit-text-decoration: underline dotted; - text-decoration: underline dotted; - cursor: help; - -webkit-text-decoration-skip-ink: none; - text-decoration-skip-ink: none; -} - -address { - margin-bottom: 1rem; - font-style: normal; - line-height: inherit; -} - -ol, -ul { - padding-left: 2rem; -} - -ol, -ul, -dl { - margin-top: 0; - margin-bottom: 1rem; -} - -ol ol, -ul ul, -ol ul, -ul ol { - margin-bottom: 0; -} - -dt { - font-weight: 700; -} - -dd { - margin-bottom: 0.5rem; - margin-left: 0; -} - -blockquote { - margin: 0 0 1rem; -} - -b, -strong { - font-weight: bolder; -} - -small, .small { - font-size: 0.875em; -} - -mark, .mark { - padding: 0.2em; - background-color: #fcf8e3; -} - -sub, -sup { - position: relative; - font-size: 0.75em; - line-height: 0; - vertical-align: baseline; -} - -sub { - bottom: -0.25em; -} - -sup { - top: -0.5em; -} - -a { - color: #0d6efd; - text-decoration: underline; -} -a:hover { - color: #0a58ca; -} - -a:not([href]):not([class]), a:not([href]):not([class]):hover { - color: inherit; - text-decoration: none; -} - -pre, -code, -kbd, -samp { - font-family: var(--bs-font-monospace); - font-size: 1em; - direction: ltr /* rtl:ignore */; - unicode-bidi: bidi-override; -} - -pre { - display: block; - margin-top: 0; - margin-bottom: 1rem; - overflow: auto; - font-size: 0.875em; -} -pre code { - font-size: inherit; - color: inherit; - word-break: normal; -} - -code { - font-size: 0.875em; - color: #d63384; - word-wrap: break-word; -} -a > code { - color: inherit; -} - -kbd { - padding: 0.2rem 0.4rem; - font-size: 0.875em; - color: #fff; - background-color: #212529; - border-radius: 0.2rem; -} -kbd kbd { - padding: 0; - font-size: 1em; - font-weight: 700; -} - -figure { - margin: 0 0 1rem; -} - -img, -svg { - vertical-align: middle; -} - -table { - caption-side: bottom; - border-collapse: collapse; -} - -caption { - padding-top: 0.5rem; - padding-bottom: 0.5rem; - color: #6c757d; - text-align: left; -} - -th { - text-align: inherit; - text-align: -webkit-match-parent; -} - -thead, -tbody, -tfoot, -tr, -td, -th { - border-color: inherit; - border-style: solid; - border-width: 0; -} - -label { - display: inline-block; -} - -button { - border-radius: 0; -} - -button:focus:not(:focus-visible) { - outline: 0; -} - -input, -button, -select, -optgroup, -textarea { - margin: 0; - font-family: inherit; - font-size: inherit; - line-height: inherit; -} - -button, -select { - text-transform: none; -} - -[role=button] { - cursor: pointer; -} - -select { - word-wrap: normal; -} -select:disabled { - opacity: 1; -} - -[list]::-webkit-calendar-picker-indicator { - display: none; -} - -button, -[type=button], -[type=reset], -[type=submit] { - -webkit-appearance: button; -} -button:not(:disabled), -[type=button]:not(:disabled), -[type=reset]:not(:disabled), -[type=submit]:not(:disabled) { - cursor: pointer; -} - -::-moz-focus-inner { - padding: 0; - border-style: none; -} - -textarea { - resize: vertical; -} - -fieldset { - min-width: 0; - padding: 0; - margin: 0; - border: 0; -} - -legend { - float: left; - width: 100%; - padding: 0; - margin-bottom: 0.5rem; - font-size: calc(1.275rem + 0.3vw); - line-height: inherit; -} -@media (min-width: 1200px) { - legend { - font-size: 1.5rem; - } -} -legend + * { - clear: left; -} - -::-webkit-datetime-edit-fields-wrapper, -::-webkit-datetime-edit-text, -::-webkit-datetime-edit-minute, -::-webkit-datetime-edit-hour-field, -::-webkit-datetime-edit-day-field, -::-webkit-datetime-edit-month-field, -::-webkit-datetime-edit-year-field { - padding: 0; -} - -::-webkit-inner-spin-button { - height: auto; -} - -[type=search] { - outline-offset: -2px; - -webkit-appearance: textfield; -} - -/* rtl:raw: -[type="tel"], -[type="url"], -[type="email"], -[type="number"] { - direction: ltr; -} -*/ -::-webkit-search-decoration { - -webkit-appearance: none; -} - -::-webkit-color-swatch-wrapper { - padding: 0; -} - -::-webkit-file-upload-button { - font: inherit; -} - -::file-selector-button { - font: inherit; -} - -::-webkit-file-upload-button { - font: inherit; - -webkit-appearance: button; -} - -output { - display: inline-block; -} - -iframe { - border: 0; -} - -summary { - display: list-item; - cursor: pointer; -} - -progress { - vertical-align: baseline; -} - -[hidden] { - display: none !important; -} - -.lead { - font-size: 1.25rem; - font-weight: 300; -} - -.display-1 { - font-size: calc(1.625rem + 4.5vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-1 { - font-size: 5rem; - } -} - -.display-2 { - font-size: calc(1.575rem + 3.9vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-2 { - font-size: 4.5rem; - } -} - -.display-3 { - font-size: calc(1.525rem + 3.3vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-3 { - font-size: 4rem; - } -} - -.display-4 { - font-size: calc(1.475rem + 2.7vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-4 { - font-size: 3.5rem; - } -} - -.display-5 { - font-size: calc(1.425rem + 2.1vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-5 { - font-size: 3rem; - } -} - -.display-6 { - font-size: calc(1.375rem + 1.5vw); - font-weight: 300; - line-height: 1.2; -} -@media (min-width: 1200px) { - .display-6 { - font-size: 2.5rem; - } -} - -.list-unstyled { - padding-left: 0; - list-style: none; -} - -.list-inline { - padding-left: 0; - list-style: none; -} - -.list-inline-item { - display: inline-block; -} -.list-inline-item:not(:last-child) { - margin-right: 0.5rem; -} - -.initialism { - font-size: 0.875em; - text-transform: uppercase; -} - -.blockquote { - margin-bottom: 1rem; - font-size: 1.25rem; -} -.blockquote > :last-child { - margin-bottom: 0; -} - -.blockquote-footer { - margin-top: -1rem; - margin-bottom: 1rem; - font-size: 0.875em; - color: #6c757d; -} -.blockquote-footer::before { - content: "— "; -} - -.img-fluid { - max-width: 100%; - height: auto; -} - -.img-thumbnail { - padding: 0.25rem; - background-color: #fff; - border: 1px solid #dee2e6; - border-radius: 0.25rem; - max-width: 100%; - height: auto; -} - -.figure { - display: inline-block; -} - -.figure-img { - margin-bottom: 0.5rem; - line-height: 1; -} - -.figure-caption { - font-size: 0.875em; - color: #6c757d; -} - -.container, -.container-fluid, -.container-xxl, -.container-xl, -.container-lg, -.container-md, -.container-sm { - width: 100%; - padding-right: var(--bs-gutter-x, 0.75rem); - padding-left: var(--bs-gutter-x, 0.75rem); - margin-right: auto; - margin-left: auto; -} - -@media (min-width: 576px) { - .container-sm, .container { - max-width: 540px; - } -} -@media (min-width: 768px) { - .container-md, .container-sm, .container { - max-width: 720px; - } -} -@media (min-width: 992px) { - .container-lg, .container-md, .container-sm, .container { - max-width: 960px; - } -} -@media (min-width: 1200px) { - .container-xl, .container-lg, .container-md, .container-sm, .container { - max-width: 1140px; - } -} -@media (min-width: 1400px) { - .container-xxl, .container-xl, .container-lg, .container-md, .container-sm, .container { - max-width: 1320px; - } -} -.row { - --bs-gutter-x: 1.5rem; - --bs-gutter-y: 0; - display: flex; - flex-wrap: wrap; - margin-top: calc(-1 * var(--bs-gutter-y)); - margin-right: calc(-0.5 * var(--bs-gutter-x)); - margin-left: calc(-0.5 * var(--bs-gutter-x)); -} -.row > * { - flex-shrink: 0; - width: 100%; - max-width: 100%; - padding-right: calc(var(--bs-gutter-x) * 0.5); - padding-left: calc(var(--bs-gutter-x) * 0.5); - margin-top: var(--bs-gutter-y); -} - -.col { - flex: 1 0 0%; -} - -.row-cols-auto > * { - flex: 0 0 auto; - width: auto; -} - -.row-cols-1 > * { - flex: 0 0 auto; - width: 100%; -} - -.row-cols-2 > * { - flex: 0 0 auto; - width: 50%; -} - -.row-cols-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; -} - -.row-cols-4 > * { - flex: 0 0 auto; - width: 25%; -} - -.row-cols-5 > * { - flex: 0 0 auto; - width: 20%; -} - -.row-cols-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; -} - -.col-auto { - flex: 0 0 auto; - width: auto; -} - -.col-1 { - flex: 0 0 auto; - width: 8.33333333%; -} - -.col-2 { - flex: 0 0 auto; - width: 16.66666667%; -} - -.col-3 { - flex: 0 0 auto; - width: 25%; -} - -.col-4 { - flex: 0 0 auto; - width: 33.33333333%; -} - -.col-5 { - flex: 0 0 auto; - width: 41.66666667%; -} - -.col-6 { - flex: 0 0 auto; - width: 50%; -} - -.col-7 { - flex: 0 0 auto; - width: 58.33333333%; -} - -.col-8 { - flex: 0 0 auto; - width: 66.66666667%; -} - -.col-9 { - flex: 0 0 auto; - width: 75%; -} - -.col-10 { - flex: 0 0 auto; - width: 83.33333333%; -} - -.col-11 { - flex: 0 0 auto; - width: 91.66666667%; -} - -.col-12 { - flex: 0 0 auto; - width: 100%; -} - -.offset-1 { - margin-left: 8.33333333%; -} - -.offset-2 { - margin-left: 16.66666667%; -} - -.offset-3 { - margin-left: 25%; -} - -.offset-4 { - margin-left: 33.33333333%; -} - -.offset-5 { - margin-left: 41.66666667%; -} - -.offset-6 { - margin-left: 50%; -} - -.offset-7 { - margin-left: 58.33333333%; -} - -.offset-8 { - margin-left: 66.66666667%; -} - -.offset-9 { - margin-left: 75%; -} - -.offset-10 { - margin-left: 83.33333333%; -} - -.offset-11 { - margin-left: 91.66666667%; -} - -.g-0, -.gx-0 { - --bs-gutter-x: 0; -} - -.g-0, -.gy-0 { - --bs-gutter-y: 0; -} - -.g-1, -.gx-1 { - --bs-gutter-x: 0.25rem; -} - -.g-1, -.gy-1 { - --bs-gutter-y: 0.25rem; -} - -.g-2, -.gx-2 { - --bs-gutter-x: 0.5rem; -} - -.g-2, -.gy-2 { - --bs-gutter-y: 0.5rem; -} - -.g-3, -.gx-3 { - --bs-gutter-x: 1rem; -} - -.g-3, -.gy-3 { - --bs-gutter-y: 1rem; -} - -.g-4, -.gx-4 { - --bs-gutter-x: 1.5rem; -} - -.g-4, -.gy-4 { - --bs-gutter-y: 1.5rem; -} - -.g-5, -.gx-5 { - --bs-gutter-x: 3rem; -} - -.g-5, -.gy-5 { - --bs-gutter-y: 3rem; -} - -@media (min-width: 576px) { - .col-sm { - flex: 1 0 0%; - } - - .row-cols-sm-auto > * { - flex: 0 0 auto; - width: auto; - } - - .row-cols-sm-1 > * { - flex: 0 0 auto; - width: 100%; - } - - .row-cols-sm-2 > * { - flex: 0 0 auto; - width: 50%; - } - - .row-cols-sm-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; - } - - .row-cols-sm-4 > * { - flex: 0 0 auto; - width: 25%; - } - - .row-cols-sm-5 > * { - flex: 0 0 auto; - width: 20%; - } - - .row-cols-sm-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; - } - - .col-sm-auto { - flex: 0 0 auto; - width: auto; - } - - .col-sm-1 { - flex: 0 0 auto; - width: 8.33333333%; - } - - .col-sm-2 { - flex: 0 0 auto; - width: 16.66666667%; - } - - .col-sm-3 { - flex: 0 0 auto; - width: 25%; - } - - .col-sm-4 { - flex: 0 0 auto; - width: 33.33333333%; - } - - .col-sm-5 { - flex: 0 0 auto; - width: 41.66666667%; - } - - .col-sm-6 { - flex: 0 0 auto; - width: 50%; - } - - .col-sm-7 { - flex: 0 0 auto; - width: 58.33333333%; - } - - .col-sm-8 { - flex: 0 0 auto; - width: 66.66666667%; - } - - .col-sm-9 { - flex: 0 0 auto; - width: 75%; - } - - .col-sm-10 { - flex: 0 0 auto; - width: 83.33333333%; - } - - .col-sm-11 { - flex: 0 0 auto; - width: 91.66666667%; - } - - .col-sm-12 { - flex: 0 0 auto; - width: 100%; - } - - .offset-sm-0 { - margin-left: 0; - } - - .offset-sm-1 { - margin-left: 8.33333333%; - } - - .offset-sm-2 { - margin-left: 16.66666667%; - } - - .offset-sm-3 { - margin-left: 25%; - } - - .offset-sm-4 { - margin-left: 33.33333333%; - } - - .offset-sm-5 { - margin-left: 41.66666667%; - } - - .offset-sm-6 { - margin-left: 50%; - } - - .offset-sm-7 { - margin-left: 58.33333333%; - } - - .offset-sm-8 { - margin-left: 66.66666667%; - } - - .offset-sm-9 { - margin-left: 75%; - } - - .offset-sm-10 { - margin-left: 83.33333333%; - } - - .offset-sm-11 { - margin-left: 91.66666667%; - } - - .g-sm-0, -.gx-sm-0 { - --bs-gutter-x: 0; - } - - .g-sm-0, -.gy-sm-0 { - --bs-gutter-y: 0; - } - - .g-sm-1, -.gx-sm-1 { - --bs-gutter-x: 0.25rem; - } - - .g-sm-1, -.gy-sm-1 { - --bs-gutter-y: 0.25rem; - } - - .g-sm-2, -.gx-sm-2 { - --bs-gutter-x: 0.5rem; - } - - .g-sm-2, -.gy-sm-2 { - --bs-gutter-y: 0.5rem; - } - - .g-sm-3, -.gx-sm-3 { - --bs-gutter-x: 1rem; - } - - .g-sm-3, -.gy-sm-3 { - --bs-gutter-y: 1rem; - } - - .g-sm-4, -.gx-sm-4 { - --bs-gutter-x: 1.5rem; - } - - .g-sm-4, -.gy-sm-4 { - --bs-gutter-y: 1.5rem; - } - - .g-sm-5, -.gx-sm-5 { - --bs-gutter-x: 3rem; - } - - .g-sm-5, -.gy-sm-5 { - --bs-gutter-y: 3rem; - } -} -@media (min-width: 768px) { - .col-md { - flex: 1 0 0%; - } - - .row-cols-md-auto > * { - flex: 0 0 auto; - width: auto; - } - - .row-cols-md-1 > * { - flex: 0 0 auto; - width: 100%; - } - - .row-cols-md-2 > * { - flex: 0 0 auto; - width: 50%; - } - - .row-cols-md-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; - } - - .row-cols-md-4 > * { - flex: 0 0 auto; - width: 25%; - } - - .row-cols-md-5 > * { - flex: 0 0 auto; - width: 20%; - } - - .row-cols-md-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; - } - - .col-md-auto { - flex: 0 0 auto; - width: auto; - } - - .col-md-1 { - flex: 0 0 auto; - width: 8.33333333%; - } - - .col-md-2 { - flex: 0 0 auto; - width: 16.66666667%; - } - - .col-md-3 { - flex: 0 0 auto; - width: 25%; - } - - .col-md-4 { - flex: 0 0 auto; - width: 33.33333333%; - } - - .col-md-5 { - flex: 0 0 auto; - width: 41.66666667%; - } - - .col-md-6 { - flex: 0 0 auto; - width: 50%; - } - - .col-md-7 { - flex: 0 0 auto; - width: 58.33333333%; - } - - .col-md-8 { - flex: 0 0 auto; - width: 66.66666667%; - } - - .col-md-9 { - flex: 0 0 auto; - width: 75%; - } - - .col-md-10 { - flex: 0 0 auto; - width: 83.33333333%; - } - - .col-md-11 { - flex: 0 0 auto; - width: 91.66666667%; - } - - .col-md-12 { - flex: 0 0 auto; - width: 100%; - } - - .offset-md-0 { - margin-left: 0; - } - - .offset-md-1 { - margin-left: 8.33333333%; - } - - .offset-md-2 { - margin-left: 16.66666667%; - } - - .offset-md-3 { - margin-left: 25%; - } - - .offset-md-4 { - margin-left: 33.33333333%; - } - - .offset-md-5 { - margin-left: 41.66666667%; - } - - .offset-md-6 { - margin-left: 50%; - } - - .offset-md-7 { - margin-left: 58.33333333%; - } - - .offset-md-8 { - margin-left: 66.66666667%; - } - - .offset-md-9 { - margin-left: 75%; - } - - .offset-md-10 { - margin-left: 83.33333333%; - } - - .offset-md-11 { - margin-left: 91.66666667%; - } - - .g-md-0, -.gx-md-0 { - --bs-gutter-x: 0; - } - - .g-md-0, -.gy-md-0 { - --bs-gutter-y: 0; - } - - .g-md-1, -.gx-md-1 { - --bs-gutter-x: 0.25rem; - } - - .g-md-1, -.gy-md-1 { - --bs-gutter-y: 0.25rem; - } - - .g-md-2, -.gx-md-2 { - --bs-gutter-x: 0.5rem; - } - - .g-md-2, -.gy-md-2 { - --bs-gutter-y: 0.5rem; - } - - .g-md-3, -.gx-md-3 { - --bs-gutter-x: 1rem; - } - - .g-md-3, -.gy-md-3 { - --bs-gutter-y: 1rem; - } - - .g-md-4, -.gx-md-4 { - --bs-gutter-x: 1.5rem; - } - - .g-md-4, -.gy-md-4 { - --bs-gutter-y: 1.5rem; - } - - .g-md-5, -.gx-md-5 { - --bs-gutter-x: 3rem; - } - - .g-md-5, -.gy-md-5 { - --bs-gutter-y: 3rem; - } -} -@media (min-width: 992px) { - .col-lg { - flex: 1 0 0%; - } - - .row-cols-lg-auto > * { - flex: 0 0 auto; - width: auto; - } - - .row-cols-lg-1 > * { - flex: 0 0 auto; - width: 100%; - } - - .row-cols-lg-2 > * { - flex: 0 0 auto; - width: 50%; - } - - .row-cols-lg-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; - } - - .row-cols-lg-4 > * { - flex: 0 0 auto; - width: 25%; - } - - .row-cols-lg-5 > * { - flex: 0 0 auto; - width: 20%; - } - - .row-cols-lg-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; - } - - .col-lg-auto { - flex: 0 0 auto; - width: auto; - } - - .col-lg-1 { - flex: 0 0 auto; - width: 8.33333333%; - } - - .col-lg-2 { - flex: 0 0 auto; - width: 16.66666667%; - } - - .col-lg-3 { - flex: 0 0 auto; - width: 25%; - } - - .col-lg-4 { - flex: 0 0 auto; - width: 33.33333333%; - } - - .col-lg-5 { - flex: 0 0 auto; - width: 41.66666667%; - } - - .col-lg-6 { - flex: 0 0 auto; - width: 50%; - } - - .col-lg-7 { - flex: 0 0 auto; - width: 58.33333333%; - } - - .col-lg-8 { - flex: 0 0 auto; - width: 66.66666667%; - } - - .col-lg-9 { - flex: 0 0 auto; - width: 75%; - } - - .col-lg-10 { - flex: 0 0 auto; - width: 83.33333333%; - } - - .col-lg-11 { - flex: 0 0 auto; - width: 91.66666667%; - } - - .col-lg-12 { - flex: 0 0 auto; - width: 100%; - } - - .offset-lg-0 { - margin-left: 0; - } - - .offset-lg-1 { - margin-left: 8.33333333%; - } - - .offset-lg-2 { - margin-left: 16.66666667%; - } - - .offset-lg-3 { - margin-left: 25%; - } - - .offset-lg-4 { - margin-left: 33.33333333%; - } - - .offset-lg-5 { - margin-left: 41.66666667%; - } - - .offset-lg-6 { - margin-left: 50%; - } - - .offset-lg-7 { - margin-left: 58.33333333%; - } - - .offset-lg-8 { - margin-left: 66.66666667%; - } - - .offset-lg-9 { - margin-left: 75%; - } - - .offset-lg-10 { - margin-left: 83.33333333%; - } - - .offset-lg-11 { - margin-left: 91.66666667%; - } - - .g-lg-0, -.gx-lg-0 { - --bs-gutter-x: 0; - } - - .g-lg-0, -.gy-lg-0 { - --bs-gutter-y: 0; - } - - .g-lg-1, -.gx-lg-1 { - --bs-gutter-x: 0.25rem; - } - - .g-lg-1, -.gy-lg-1 { - --bs-gutter-y: 0.25rem; - } - - .g-lg-2, -.gx-lg-2 { - --bs-gutter-x: 0.5rem; - } - - .g-lg-2, -.gy-lg-2 { - --bs-gutter-y: 0.5rem; - } - - .g-lg-3, -.gx-lg-3 { - --bs-gutter-x: 1rem; - } - - .g-lg-3, -.gy-lg-3 { - --bs-gutter-y: 1rem; - } - - .g-lg-4, -.gx-lg-4 { - --bs-gutter-x: 1.5rem; - } - - .g-lg-4, -.gy-lg-4 { - --bs-gutter-y: 1.5rem; - } - - .g-lg-5, -.gx-lg-5 { - --bs-gutter-x: 3rem; - } - - .g-lg-5, -.gy-lg-5 { - --bs-gutter-y: 3rem; - } -} -@media (min-width: 1200px) { - .col-xl { - flex: 1 0 0%; - } - - .row-cols-xl-auto > * { - flex: 0 0 auto; - width: auto; - } - - .row-cols-xl-1 > * { - flex: 0 0 auto; - width: 100%; - } - - .row-cols-xl-2 > * { - flex: 0 0 auto; - width: 50%; - } - - .row-cols-xl-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; - } - - .row-cols-xl-4 > * { - flex: 0 0 auto; - width: 25%; - } - - .row-cols-xl-5 > * { - flex: 0 0 auto; - width: 20%; - } - - .row-cols-xl-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; - } - - .col-xl-auto { - flex: 0 0 auto; - width: auto; - } - - .col-xl-1 { - flex: 0 0 auto; - width: 8.33333333%; - } - - .col-xl-2 { - flex: 0 0 auto; - width: 16.66666667%; - } - - .col-xl-3 { - flex: 0 0 auto; - width: 25%; - } - - .col-xl-4 { - flex: 0 0 auto; - width: 33.33333333%; - } - - .col-xl-5 { - flex: 0 0 auto; - width: 41.66666667%; - } - - .col-xl-6 { - flex: 0 0 auto; - width: 50%; - } - - .col-xl-7 { - flex: 0 0 auto; - width: 58.33333333%; - } - - .col-xl-8 { - flex: 0 0 auto; - width: 66.66666667%; - } - - .col-xl-9 { - flex: 0 0 auto; - width: 75%; - } - - .col-xl-10 { - flex: 0 0 auto; - width: 83.33333333%; - } - - .col-xl-11 { - flex: 0 0 auto; - width: 91.66666667%; - } - - .col-xl-12 { - flex: 0 0 auto; - width: 100%; - } - - .offset-xl-0 { - margin-left: 0; - } - - .offset-xl-1 { - margin-left: 8.33333333%; - } - - .offset-xl-2 { - margin-left: 16.66666667%; - } - - .offset-xl-3 { - margin-left: 25%; - } - - .offset-xl-4 { - margin-left: 33.33333333%; - } - - .offset-xl-5 { - margin-left: 41.66666667%; - } - - .offset-xl-6 { - margin-left: 50%; - } - - .offset-xl-7 { - margin-left: 58.33333333%; - } - - .offset-xl-8 { - margin-left: 66.66666667%; - } - - .offset-xl-9 { - margin-left: 75%; - } - - .offset-xl-10 { - margin-left: 83.33333333%; - } - - .offset-xl-11 { - margin-left: 91.66666667%; - } - - .g-xl-0, -.gx-xl-0 { - --bs-gutter-x: 0; - } - - .g-xl-0, -.gy-xl-0 { - --bs-gutter-y: 0; - } - - .g-xl-1, -.gx-xl-1 { - --bs-gutter-x: 0.25rem; - } - - .g-xl-1, -.gy-xl-1 { - --bs-gutter-y: 0.25rem; - } - - .g-xl-2, -.gx-xl-2 { - --bs-gutter-x: 0.5rem; - } - - .g-xl-2, -.gy-xl-2 { - --bs-gutter-y: 0.5rem; - } - - .g-xl-3, -.gx-xl-3 { - --bs-gutter-x: 1rem; - } - - .g-xl-3, -.gy-xl-3 { - --bs-gutter-y: 1rem; - } - - .g-xl-4, -.gx-xl-4 { - --bs-gutter-x: 1.5rem; - } - - .g-xl-4, -.gy-xl-4 { - --bs-gutter-y: 1.5rem; - } - - .g-xl-5, -.gx-xl-5 { - --bs-gutter-x: 3rem; - } - - .g-xl-5, -.gy-xl-5 { - --bs-gutter-y: 3rem; - } -} -@media (min-width: 1400px) { - .col-xxl { - flex: 1 0 0%; - } - - .row-cols-xxl-auto > * { - flex: 0 0 auto; - width: auto; - } - - .row-cols-xxl-1 > * { - flex: 0 0 auto; - width: 100%; - } - - .row-cols-xxl-2 > * { - flex: 0 0 auto; - width: 50%; - } - - .row-cols-xxl-3 > * { - flex: 0 0 auto; - width: 33.3333333333%; - } - - .row-cols-xxl-4 > * { - flex: 0 0 auto; - width: 25%; - } - - .row-cols-xxl-5 > * { - flex: 0 0 auto; - width: 20%; - } - - .row-cols-xxl-6 > * { - flex: 0 0 auto; - width: 16.6666666667%; - } - - .col-xxl-auto { - flex: 0 0 auto; - width: auto; - } - - .col-xxl-1 { - flex: 0 0 auto; - width: 8.33333333%; - } - - .col-xxl-2 { - flex: 0 0 auto; - width: 16.66666667%; - } - - .col-xxl-3 { - flex: 0 0 auto; - width: 25%; - } - - .col-xxl-4 { - flex: 0 0 auto; - width: 33.33333333%; - } - - .col-xxl-5 { - flex: 0 0 auto; - width: 41.66666667%; - } - - .col-xxl-6 { - flex: 0 0 auto; - width: 50%; - } - - .col-xxl-7 { - flex: 0 0 auto; - width: 58.33333333%; - } - - .col-xxl-8 { - flex: 0 0 auto; - width: 66.66666667%; - } - - .col-xxl-9 { - flex: 0 0 auto; - width: 75%; - } - - .col-xxl-10 { - flex: 0 0 auto; - width: 83.33333333%; - } - - .col-xxl-11 { - flex: 0 0 auto; - width: 91.66666667%; - } - - .col-xxl-12 { - flex: 0 0 auto; - width: 100%; - } - - .offset-xxl-0 { - margin-left: 0; - } - - .offset-xxl-1 { - margin-left: 8.33333333%; - } - - .offset-xxl-2 { - margin-left: 16.66666667%; - } - - .offset-xxl-3 { - margin-left: 25%; - } - - .offset-xxl-4 { - margin-left: 33.33333333%; - } - - .offset-xxl-5 { - margin-left: 41.66666667%; - } - - .offset-xxl-6 { - margin-left: 50%; - } - - .offset-xxl-7 { - margin-left: 58.33333333%; - } - - .offset-xxl-8 { - margin-left: 66.66666667%; - } - - .offset-xxl-9 { - margin-left: 75%; - } - - .offset-xxl-10 { - margin-left: 83.33333333%; - } - - .offset-xxl-11 { - margin-left: 91.66666667%; - } - - .g-xxl-0, -.gx-xxl-0 { - --bs-gutter-x: 0; - } - - .g-xxl-0, -.gy-xxl-0 { - --bs-gutter-y: 0; - } - - .g-xxl-1, -.gx-xxl-1 { - --bs-gutter-x: 0.25rem; - } - - .g-xxl-1, -.gy-xxl-1 { - --bs-gutter-y: 0.25rem; - } - - .g-xxl-2, -.gx-xxl-2 { - --bs-gutter-x: 0.5rem; - } - - .g-xxl-2, -.gy-xxl-2 { - --bs-gutter-y: 0.5rem; - } - - .g-xxl-3, -.gx-xxl-3 { - --bs-gutter-x: 1rem; - } - - .g-xxl-3, -.gy-xxl-3 { - --bs-gutter-y: 1rem; - } - - .g-xxl-4, -.gx-xxl-4 { - --bs-gutter-x: 1.5rem; - } - - .g-xxl-4, -.gy-xxl-4 { - --bs-gutter-y: 1.5rem; - } - - .g-xxl-5, -.gx-xxl-5 { - --bs-gutter-x: 3rem; - } - - .g-xxl-5, -.gy-xxl-5 { - --bs-gutter-y: 3rem; - } -} -.table { - --bs-table-bg: transparent; - --bs-table-accent-bg: transparent; - --bs-table-striped-color: #212529; - --bs-table-striped-bg: rgba(0, 0, 0, 0.05); - --bs-table-active-color: #212529; - --bs-table-active-bg: rgba(0, 0, 0, 0.1); - --bs-table-hover-color: #212529; - --bs-table-hover-bg: rgba(0, 0, 0, 0.075); - width: 100%; - margin-bottom: 1rem; - color: #212529; - vertical-align: top; - border-color: #dee2e6; -} -.table > :not(caption) > * > * { - padding: 0.5rem 0.5rem; - background-color: var(--bs-table-bg); - border-bottom-width: 1px; - box-shadow: inset 0 0 0 9999px var(--bs-table-accent-bg); -} -.table > tbody { - vertical-align: inherit; -} -.table > thead { - vertical-align: bottom; -} -.table > :not(:first-child) { - border-top: 2px solid currentColor; -} - -.caption-top { - caption-side: top; -} - -.table-sm > :not(caption) > * > * { - padding: 0.25rem 0.25rem; -} - -.table-bordered > :not(caption) > * { - border-width: 1px 0; -} -.table-bordered > :not(caption) > * > * { - border-width: 0 1px; -} - -.table-borderless > :not(caption) > * > * { - border-bottom-width: 0; -} -.table-borderless > :not(:first-child) { - border-top-width: 0; -} - -.table-striped > tbody > tr:nth-of-type(odd) > * { - --bs-table-accent-bg: var(--bs-table-striped-bg); - color: var(--bs-table-striped-color); -} - -.table-active { - --bs-table-accent-bg: var(--bs-table-active-bg); - color: var(--bs-table-active-color); -} - -.table-hover > tbody > tr:hover > * { - --bs-table-accent-bg: var(--bs-table-hover-bg); - color: var(--bs-table-hover-color); -} - -.table-primary { - --bs-table-bg: #cfe2ff; - --bs-table-striped-bg: #c5d7f2; - --bs-table-striped-color: #000; - --bs-table-active-bg: #bacbe6; - --bs-table-active-color: #000; - --bs-table-hover-bg: #bfd1ec; - --bs-table-hover-color: #000; - color: #000; - border-color: #bacbe6; -} - -.table-secondary { - --bs-table-bg: #e2e3e5; - --bs-table-striped-bg: #d7d8da; - --bs-table-striped-color: #000; - --bs-table-active-bg: #cbccce; - --bs-table-active-color: #000; - --bs-table-hover-bg: #d1d2d4; - --bs-table-hover-color: #000; - color: #000; - border-color: #cbccce; -} - -.table-success { - --bs-table-bg: #d1e7dd; - --bs-table-striped-bg: #c7dbd2; - --bs-table-striped-color: #000; - --bs-table-active-bg: #bcd0c7; - --bs-table-active-color: #000; - --bs-table-hover-bg: #c1d6cc; - --bs-table-hover-color: #000; - color: #000; - border-color: #bcd0c7; -} - -.table-info { - --bs-table-bg: #cff4fc; - --bs-table-striped-bg: #c5e8ef; - --bs-table-striped-color: #000; - --bs-table-active-bg: #badce3; - --bs-table-active-color: #000; - --bs-table-hover-bg: #bfe2e9; - --bs-table-hover-color: #000; - color: #000; - border-color: #badce3; -} - -.table-warning { - --bs-table-bg: #fff3cd; - --bs-table-striped-bg: #f2e7c3; - --bs-table-striped-color: #000; - --bs-table-active-bg: #e6dbb9; - --bs-table-active-color: #000; - --bs-table-hover-bg: #ece1be; - --bs-table-hover-color: #000; - color: #000; - border-color: #e6dbb9; -} - -.table-danger { - --bs-table-bg: #f8d7da; - --bs-table-striped-bg: #eccccf; - --bs-table-striped-color: #000; - --bs-table-active-bg: #dfc2c4; - --bs-table-active-color: #000; - --bs-table-hover-bg: #e5c7ca; - --bs-table-hover-color: #000; - color: #000; - border-color: #dfc2c4; -} - -.table-light { - --bs-table-bg: #f8f9fa; - --bs-table-striped-bg: #ecedee; - --bs-table-striped-color: #000; - --bs-table-active-bg: #dfe0e1; - --bs-table-active-color: #000; - --bs-table-hover-bg: #e5e6e7; - --bs-table-hover-color: #000; - color: #000; - border-color: #dfe0e1; -} - -.table-dark { - --bs-table-bg: #212529; - --bs-table-striped-bg: #2c3034; - --bs-table-striped-color: #fff; - --bs-table-active-bg: #373b3e; - --bs-table-active-color: #fff; - --bs-table-hover-bg: #323539; - --bs-table-hover-color: #fff; - color: #fff; - border-color: #373b3e; -} - -.table-responsive { - overflow-x: auto; - -webkit-overflow-scrolling: touch; -} - -@media (max-width: 575.98px) { - .table-responsive-sm { - overflow-x: auto; - -webkit-overflow-scrolling: touch; - } -} -@media (max-width: 767.98px) { - .table-responsive-md { - overflow-x: auto; - -webkit-overflow-scrolling: touch; - } -} -@media (max-width: 991.98px) { - .table-responsive-lg { - overflow-x: auto; - -webkit-overflow-scrolling: touch; - } -} -@media (max-width: 1199.98px) { - .table-responsive-xl { - overflow-x: auto; - -webkit-overflow-scrolling: touch; - } -} -@media (max-width: 1399.98px) { - .table-responsive-xxl { - overflow-x: auto; - -webkit-overflow-scrolling: touch; - } -} -.form-label { - margin-bottom: 0.5rem; -} - -.col-form-label { - padding-top: calc(0.375rem + 1px); - padding-bottom: calc(0.375rem + 1px); - margin-bottom: 0; - font-size: inherit; - line-height: 1.5; -} - -.col-form-label-lg { - padding-top: calc(0.5rem + 1px); - padding-bottom: calc(0.5rem + 1px); - font-size: 1.25rem; -} - -.col-form-label-sm { - padding-top: calc(0.25rem + 1px); - padding-bottom: calc(0.25rem + 1px); - font-size: 0.875rem; -} - -.form-text { - margin-top: 0.25rem; - font-size: 0.875em; - color: #6c757d; -} - -.form-control { - display: block; - width: 100%; - padding: 0.375rem 0.75rem; - font-size: 1rem; - font-weight: 400; - line-height: 1.5; - color: #212529; - background-color: #fff; - background-clip: padding-box; - border: 1px solid #ced4da; - -webkit-appearance: none; - -moz-appearance: none; - appearance: none; - border-radius: 0.25rem; - transition: border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .form-control { - transition: none; - } -} -.form-control[type=file] { - overflow: hidden; -} -.form-control[type=file]:not(:disabled):not([readonly]) { - cursor: pointer; -} -.form-control:focus { - color: #212529; - background-color: #fff; - border-color: #86b7fe; - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.form-control::-webkit-date-and-time-value { - height: 1.5em; -} -.form-control::-moz-placeholder { - color: #6c757d; - opacity: 1; -} -.form-control::placeholder { - color: #6c757d; - opacity: 1; -} -.form-control:disabled, .form-control[readonly] { - background-color: #e9ecef; - opacity: 1; -} -.form-control::-webkit-file-upload-button { - padding: 0.375rem 0.75rem; - margin: -0.375rem -0.75rem; - -webkit-margin-end: 0.75rem; - margin-inline-end: 0.75rem; - color: #212529; - background-color: #e9ecef; - pointer-events: none; - border-color: inherit; - border-style: solid; - border-width: 0; - border-inline-end-width: 1px; - border-radius: 0; - -webkit-transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -.form-control::file-selector-button { - padding: 0.375rem 0.75rem; - margin: -0.375rem -0.75rem; - -webkit-margin-end: 0.75rem; - margin-inline-end: 0.75rem; - color: #212529; - background-color: #e9ecef; - pointer-events: none; - border-color: inherit; - border-style: solid; - border-width: 0; - border-inline-end-width: 1px; - border-radius: 0; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .form-control::-webkit-file-upload-button { - -webkit-transition: none; - transition: none; - } - .form-control::file-selector-button { - transition: none; - } -} -.form-control:hover:not(:disabled):not([readonly])::-webkit-file-upload-button { - background-color: #dde0e3; -} -.form-control:hover:not(:disabled):not([readonly])::file-selector-button { - background-color: #dde0e3; -} -.form-control::-webkit-file-upload-button { - padding: 0.375rem 0.75rem; - margin: -0.375rem -0.75rem; - -webkit-margin-end: 0.75rem; - margin-inline-end: 0.75rem; - color: #212529; - background-color: #e9ecef; - pointer-events: none; - border-color: inherit; - border-style: solid; - border-width: 0; - border-inline-end-width: 1px; - border-radius: 0; - -webkit-transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .form-control::-webkit-file-upload-button { - -webkit-transition: none; - transition: none; - } -} -.form-control:hover:not(:disabled):not([readonly])::-webkit-file-upload-button { - background-color: #dde0e3; -} - -.form-control-plaintext { - display: block; - width: 100%; - padding: 0.375rem 0; - margin-bottom: 0; - line-height: 1.5; - color: #212529; - background-color: transparent; - border: solid transparent; - border-width: 1px 0; -} -.form-control-plaintext.form-control-sm, .form-control-plaintext.form-control-lg { - padding-right: 0; - padding-left: 0; -} - -.form-control-sm { - min-height: calc(1.5em + 0.5rem + 2px); - padding: 0.25rem 0.5rem; - font-size: 0.875rem; - border-radius: 0.2rem; -} -.form-control-sm::-webkit-file-upload-button { - padding: 0.25rem 0.5rem; - margin: -0.25rem -0.5rem; - -webkit-margin-end: 0.5rem; - margin-inline-end: 0.5rem; -} -.form-control-sm::file-selector-button { - padding: 0.25rem 0.5rem; - margin: -0.25rem -0.5rem; - -webkit-margin-end: 0.5rem; - margin-inline-end: 0.5rem; -} -.form-control-sm::-webkit-file-upload-button { - padding: 0.25rem 0.5rem; - margin: -0.25rem -0.5rem; - -webkit-margin-end: 0.5rem; - margin-inline-end: 0.5rem; -} - -.form-control-lg { - min-height: calc(1.5em + 1rem + 2px); - padding: 0.5rem 1rem; - font-size: 1.25rem; - border-radius: 0.3rem; -} -.form-control-lg::-webkit-file-upload-button { - padding: 0.5rem 1rem; - margin: -0.5rem -1rem; - -webkit-margin-end: 1rem; - margin-inline-end: 1rem; -} -.form-control-lg::file-selector-button { - padding: 0.5rem 1rem; - margin: -0.5rem -1rem; - -webkit-margin-end: 1rem; - margin-inline-end: 1rem; -} -.form-control-lg::-webkit-file-upload-button { - padding: 0.5rem 1rem; - margin: -0.5rem -1rem; - -webkit-margin-end: 1rem; - margin-inline-end: 1rem; -} - -textarea.form-control { - min-height: calc(1.5em + 0.75rem + 2px); -} -textarea.form-control-sm { - min-height: calc(1.5em + 0.5rem + 2px); -} -textarea.form-control-lg { - min-height: calc(1.5em + 1rem + 2px); -} - -.form-control-color { - width: 3rem; - height: auto; - padding: 0.375rem; -} -.form-control-color:not(:disabled):not([readonly]) { - cursor: pointer; -} -.form-control-color::-moz-color-swatch { - height: 1.5em; - border-radius: 0.25rem; -} -.form-control-color::-webkit-color-swatch { - height: 1.5em; - border-radius: 0.25rem; -} - -.form-select { - display: block; - width: 100%; - padding: 0.375rem 2.25rem 0.375rem 0.75rem; - -moz-padding-start: calc(0.75rem - 3px); - font-size: 1rem; - font-weight: 400; - line-height: 1.5; - color: #212529; - background-color: #fff; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e"); - background-repeat: no-repeat; - background-position: right 0.75rem center; - background-size: 16px 12px; - border: 1px solid #ced4da; - border-radius: 0.25rem; - transition: border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - -webkit-appearance: none; - -moz-appearance: none; - appearance: none; -} -@media (prefers-reduced-motion: reduce) { - .form-select { - transition: none; - } -} -.form-select:focus { - border-color: #86b7fe; - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.form-select[multiple], .form-select[size]:not([size="1"]) { - padding-right: 0.75rem; - background-image: none; -} -.form-select:disabled { - background-color: #e9ecef; -} -.form-select:-moz-focusring { - color: transparent; - text-shadow: 0 0 0 #212529; -} - -.form-select-sm { - padding-top: 0.25rem; - padding-bottom: 0.25rem; - padding-left: 0.5rem; - font-size: 0.875rem; - border-radius: 0.2rem; -} - -.form-select-lg { - padding-top: 0.5rem; - padding-bottom: 0.5rem; - padding-left: 1rem; - font-size: 1.25rem; - border-radius: 0.3rem; -} - -.form-check { - display: block; - min-height: 1.5rem; - padding-left: 1.5em; - margin-bottom: 0.125rem; -} -.form-check .form-check-input { - float: left; - margin-left: -1.5em; -} - -.form-check-input { - width: 1em; - height: 1em; - margin-top: 0.25em; - vertical-align: top; - background-color: #fff; - background-repeat: no-repeat; - background-position: center; - background-size: contain; - border: 1px solid rgba(0, 0, 0, 0.25); - -webkit-appearance: none; - -moz-appearance: none; - appearance: none; - -webkit-print-color-adjust: exact; - color-adjust: exact; -} -.form-check-input[type=checkbox] { - border-radius: 0.25em; -} -.form-check-input[type=radio] { - border-radius: 50%; -} -.form-check-input:active { - filter: brightness(90%); -} -.form-check-input:focus { - border-color: #86b7fe; - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.form-check-input:checked { - background-color: #0d6efd; - border-color: #0d6efd; -} -.form-check-input:checked[type=checkbox] { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3e%3cpath fill='none' stroke='%23fff' stroke-linecap='round' stroke-linejoin='round' stroke-width='3' d='M6 10l3 3l6-6'/%3e%3c/svg%3e"); -} -.form-check-input:checked[type=radio] { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='2' fill='%23fff'/%3e%3c/svg%3e"); -} -.form-check-input[type=checkbox]:indeterminate { - background-color: #0d6efd; - border-color: #0d6efd; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3e%3cpath fill='none' stroke='%23fff' stroke-linecap='round' stroke-linejoin='round' stroke-width='3' d='M6 10h8'/%3e%3c/svg%3e"); -} -.form-check-input:disabled { - pointer-events: none; - filter: none; - opacity: 0.5; -} -.form-check-input[disabled] ~ .form-check-label, .form-check-input:disabled ~ .form-check-label { - opacity: 0.5; -} - -.form-switch { - padding-left: 2.5em; -} -.form-switch .form-check-input { - width: 2em; - margin-left: -2.5em; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='rgba%280, 0, 0, 0.25%29'/%3e%3c/svg%3e"); - background-position: left center; - border-radius: 2em; - transition: background-position 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .form-switch .form-check-input { - transition: none; - } -} -.form-switch .form-check-input:focus { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='%2386b7fe'/%3e%3c/svg%3e"); -} -.form-switch .form-check-input:checked { - background-position: right center; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='%23fff'/%3e%3c/svg%3e"); -} - -.form-check-inline { - display: inline-block; - margin-right: 1rem; -} - -.btn-check { - position: absolute; - clip: rect(0, 0, 0, 0); - pointer-events: none; -} -.btn-check[disabled] + .btn, .btn-check:disabled + .btn { - pointer-events: none; - filter: none; - opacity: 0.65; -} - -.form-range { - width: 100%; - height: 1.5rem; - padding: 0; - background-color: transparent; - -webkit-appearance: none; - -moz-appearance: none; - appearance: none; -} -.form-range:focus { - outline: 0; -} -.form-range:focus::-webkit-slider-thumb { - box-shadow: 0 0 0 1px #fff, 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.form-range:focus::-moz-range-thumb { - box-shadow: 0 0 0 1px #fff, 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.form-range::-moz-focus-outer { - border: 0; -} -.form-range::-webkit-slider-thumb { - width: 1rem; - height: 1rem; - margin-top: -0.25rem; - background-color: #0d6efd; - border: 0; - border-radius: 1rem; - -webkit-transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - -webkit-appearance: none; - appearance: none; -} -@media (prefers-reduced-motion: reduce) { - .form-range::-webkit-slider-thumb { - -webkit-transition: none; - transition: none; - } -} -.form-range::-webkit-slider-thumb:active { - background-color: #b6d4fe; -} -.form-range::-webkit-slider-runnable-track { - width: 100%; - height: 0.5rem; - color: transparent; - cursor: pointer; - background-color: #dee2e6; - border-color: transparent; - border-radius: 1rem; -} -.form-range::-moz-range-thumb { - width: 1rem; - height: 1rem; - background-color: #0d6efd; - border: 0; - border-radius: 1rem; - -moz-transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; - -moz-appearance: none; - appearance: none; -} -@media (prefers-reduced-motion: reduce) { - .form-range::-moz-range-thumb { - -moz-transition: none; - transition: none; - } -} -.form-range::-moz-range-thumb:active { - background-color: #b6d4fe; -} -.form-range::-moz-range-track { - width: 100%; - height: 0.5rem; - color: transparent; - cursor: pointer; - background-color: #dee2e6; - border-color: transparent; - border-radius: 1rem; -} -.form-range:disabled { - pointer-events: none; -} -.form-range:disabled::-webkit-slider-thumb { - background-color: #adb5bd; -} -.form-range:disabled::-moz-range-thumb { - background-color: #adb5bd; -} - -.form-floating { - position: relative; -} -.form-floating > .form-control, -.form-floating > .form-select { - height: calc(3.5rem + 2px); - line-height: 1.25; -} -.form-floating > label { - position: absolute; - top: 0; - left: 0; - height: 100%; - padding: 1rem 0.75rem; - pointer-events: none; - border: 1px solid transparent; - transform-origin: 0 0; - transition: opacity 0.1s ease-in-out, transform 0.1s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .form-floating > label { - transition: none; - } -} -.form-floating > .form-control { - padding: 1rem 0.75rem; -} -.form-floating > .form-control::-moz-placeholder { - color: transparent; -} -.form-floating > .form-control::placeholder { - color: transparent; -} -.form-floating > .form-control:not(:-moz-placeholder-shown) { - padding-top: 1.625rem; - padding-bottom: 0.625rem; -} -.form-floating > .form-control:focus, .form-floating > .form-control:not(:placeholder-shown) { - padding-top: 1.625rem; - padding-bottom: 0.625rem; -} -.form-floating > .form-control:-webkit-autofill { - padding-top: 1.625rem; - padding-bottom: 0.625rem; -} -.form-floating > .form-select { - padding-top: 1.625rem; - padding-bottom: 0.625rem; -} -.form-floating > .form-control:not(:-moz-placeholder-shown) ~ label { - opacity: 0.65; - transform: scale(0.85) translateY(-0.5rem) translateX(0.15rem); -} -.form-floating > .form-control:focus ~ label, -.form-floating > .form-control:not(:placeholder-shown) ~ label, -.form-floating > .form-select ~ label { - opacity: 0.65; - transform: scale(0.85) translateY(-0.5rem) translateX(0.15rem); -} -.form-floating > .form-control:-webkit-autofill ~ label { - opacity: 0.65; - transform: scale(0.85) translateY(-0.5rem) translateX(0.15rem); -} - -.input-group { - position: relative; - display: flex; - flex-wrap: wrap; - align-items: stretch; - width: 100%; -} -.input-group > .form-control, -.input-group > .form-select { - position: relative; - flex: 1 1 auto; - width: 1%; - min-width: 0; -} -.input-group > .form-control:focus, -.input-group > .form-select:focus { - z-index: 3; -} -.input-group .btn { - position: relative; - z-index: 2; -} -.input-group .btn:focus { - z-index: 3; -} - -.input-group-text { - display: flex; - align-items: center; - padding: 0.375rem 0.75rem; - font-size: 1rem; - font-weight: 400; - line-height: 1.5; - color: #212529; - text-align: center; - white-space: nowrap; - background-color: #e9ecef; - border: 1px solid #ced4da; - border-radius: 0.25rem; -} - -.input-group-lg > .form-control, -.input-group-lg > .form-select, -.input-group-lg > .input-group-text, -.input-group-lg > .btn { - padding: 0.5rem 1rem; - font-size: 1.25rem; - border-radius: 0.3rem; -} - -.input-group-sm > .form-control, -.input-group-sm > .form-select, -.input-group-sm > .input-group-text, -.input-group-sm > .btn { - padding: 0.25rem 0.5rem; - font-size: 0.875rem; - border-radius: 0.2rem; -} - -.input-group-lg > .form-select, -.input-group-sm > .form-select { - padding-right: 3rem; -} - -.input-group:not(.has-validation) > :not(:last-child):not(.dropdown-toggle):not(.dropdown-menu), -.input-group:not(.has-validation) > .dropdown-toggle:nth-last-child(n+3) { - border-top-right-radius: 0; - border-bottom-right-radius: 0; -} -.input-group.has-validation > :nth-last-child(n+3):not(.dropdown-toggle):not(.dropdown-menu), -.input-group.has-validation > .dropdown-toggle:nth-last-child(n+4) { - border-top-right-radius: 0; - border-bottom-right-radius: 0; -} -.input-group > :not(:first-child):not(.dropdown-menu):not(.valid-tooltip):not(.valid-feedback):not(.invalid-tooltip):not(.invalid-feedback) { - margin-left: -1px; - border-top-left-radius: 0; - border-bottom-left-radius: 0; -} - -.valid-feedback { - display: none; - width: 100%; - margin-top: 0.25rem; - font-size: 0.875em; - color: #198754; -} - -.valid-tooltip { - position: absolute; - top: 100%; - z-index: 5; - display: none; - max-width: 100%; - padding: 0.25rem 0.5rem; - margin-top: 0.1rem; - font-size: 0.875rem; - color: #fff; - background-color: rgba(25, 135, 84, 0.9); - border-radius: 0.25rem; -} - -.was-validated :valid ~ .valid-feedback, -.was-validated :valid ~ .valid-tooltip, -.is-valid ~ .valid-feedback, -.is-valid ~ .valid-tooltip { - display: block; -} - -.was-validated .form-control:valid, .form-control.is-valid { - border-color: #198754; - padding-right: calc(1.5em + 0.75rem); - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3e%3cpath fill='%23198754' d='M2.3 6.73L.6 4.53c-.4-1.04.46-1.4 1.1-.8l1.1 1.4 3.4-3.8c.6-.63 1.6-.27 1.2.7l-4 4.6c-.43.5-.8.4-1.1.1z'/%3e%3c/svg%3e"); - background-repeat: no-repeat; - background-position: right calc(0.375em + 0.1875rem) center; - background-size: calc(0.75em + 0.375rem) calc(0.75em + 0.375rem); -} -.was-validated .form-control:valid:focus, .form-control.is-valid:focus { - border-color: #198754; - box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25); -} - -.was-validated textarea.form-control:valid, textarea.form-control.is-valid { - padding-right: calc(1.5em + 0.75rem); - background-position: top calc(0.375em + 0.1875rem) right calc(0.375em + 0.1875rem); -} - -.was-validated .form-select:valid, .form-select.is-valid { - border-color: #198754; -} -.was-validated .form-select:valid:not([multiple]):not([size]), .was-validated .form-select:valid:not([multiple])[size="1"], .form-select.is-valid:not([multiple]):not([size]), .form-select.is-valid:not([multiple])[size="1"] { - padding-right: 4.125rem; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e"), url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3e%3cpath fill='%23198754' d='M2.3 6.73L.6 4.53c-.4-1.04.46-1.4 1.1-.8l1.1 1.4 3.4-3.8c.6-.63 1.6-.27 1.2.7l-4 4.6c-.43.5-.8.4-1.1.1z'/%3e%3c/svg%3e"); - background-position: right 0.75rem center, center right 2.25rem; - background-size: 16px 12px, calc(0.75em + 0.375rem) calc(0.75em + 0.375rem); -} -.was-validated .form-select:valid:focus, .form-select.is-valid:focus { - border-color: #198754; - box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25); -} - -.was-validated .form-check-input:valid, .form-check-input.is-valid { - border-color: #198754; -} -.was-validated .form-check-input:valid:checked, .form-check-input.is-valid:checked { - background-color: #198754; -} -.was-validated .form-check-input:valid:focus, .form-check-input.is-valid:focus { - box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25); -} -.was-validated .form-check-input:valid ~ .form-check-label, .form-check-input.is-valid ~ .form-check-label { - color: #198754; -} - -.form-check-inline .form-check-input ~ .valid-feedback { - margin-left: 0.5em; -} - -.was-validated .input-group .form-control:valid, .input-group .form-control.is-valid, -.was-validated .input-group .form-select:valid, -.input-group .form-select.is-valid { - z-index: 1; -} -.was-validated .input-group .form-control:valid:focus, .input-group .form-control.is-valid:focus, -.was-validated .input-group .form-select:valid:focus, -.input-group .form-select.is-valid:focus { - z-index: 3; -} - -.invalid-feedback { - display: none; - width: 100%; - margin-top: 0.25rem; - font-size: 0.875em; - color: #dc3545; -} - -.invalid-tooltip { - position: absolute; - top: 100%; - z-index: 5; - display: none; - max-width: 100%; - padding: 0.25rem 0.5rem; - margin-top: 0.1rem; - font-size: 0.875rem; - color: #fff; - background-color: rgba(220, 53, 69, 0.9); - border-radius: 0.25rem; -} - -.was-validated :invalid ~ .invalid-feedback, -.was-validated :invalid ~ .invalid-tooltip, -.is-invalid ~ .invalid-feedback, -.is-invalid ~ .invalid-tooltip { - display: block; -} - -.was-validated .form-control:invalid, .form-control.is-invalid { - border-color: #dc3545; - padding-right: calc(1.5em + 0.75rem); - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' width='12' height='12' fill='none' stroke='%23dc3545'%3e%3ccircle cx='6' cy='6' r='4.5'/%3e%3cpath stroke-linejoin='round' d='M5.8 3.6h.4L6 6.5z'/%3e%3ccircle cx='6' cy='8.2' r='.6' fill='%23dc3545' stroke='none'/%3e%3c/svg%3e"); - background-repeat: no-repeat; - background-position: right calc(0.375em + 0.1875rem) center; - background-size: calc(0.75em + 0.375rem) calc(0.75em + 0.375rem); -} -.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus { - border-color: #dc3545; - box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25); -} - -.was-validated textarea.form-control:invalid, textarea.form-control.is-invalid { - padding-right: calc(1.5em + 0.75rem); - background-position: top calc(0.375em + 0.1875rem) right calc(0.375em + 0.1875rem); -} - -.was-validated .form-select:invalid, .form-select.is-invalid { - border-color: #dc3545; -} -.was-validated .form-select:invalid:not([multiple]):not([size]), .was-validated .form-select:invalid:not([multiple])[size="1"], .form-select.is-invalid:not([multiple]):not([size]), .form-select.is-invalid:not([multiple])[size="1"] { - padding-right: 4.125rem; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e"), url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' width='12' height='12' fill='none' stroke='%23dc3545'%3e%3ccircle cx='6' cy='6' r='4.5'/%3e%3cpath stroke-linejoin='round' d='M5.8 3.6h.4L6 6.5z'/%3e%3ccircle cx='6' cy='8.2' r='.6' fill='%23dc3545' stroke='none'/%3e%3c/svg%3e"); - background-position: right 0.75rem center, center right 2.25rem; - background-size: 16px 12px, calc(0.75em + 0.375rem) calc(0.75em + 0.375rem); -} -.was-validated .form-select:invalid:focus, .form-select.is-invalid:focus { - border-color: #dc3545; - box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25); -} - -.was-validated .form-check-input:invalid, .form-check-input.is-invalid { - border-color: #dc3545; -} -.was-validated .form-check-input:invalid:checked, .form-check-input.is-invalid:checked { - background-color: #dc3545; -} -.was-validated .form-check-input:invalid:focus, .form-check-input.is-invalid:focus { - box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25); -} -.was-validated .form-check-input:invalid ~ .form-check-label, .form-check-input.is-invalid ~ .form-check-label { - color: #dc3545; -} - -.form-check-inline .form-check-input ~ .invalid-feedback { - margin-left: 0.5em; -} - -.was-validated .input-group .form-control:invalid, .input-group .form-control.is-invalid, -.was-validated .input-group .form-select:invalid, -.input-group .form-select.is-invalid { - z-index: 2; -} -.was-validated .input-group .form-control:invalid:focus, .input-group .form-control.is-invalid:focus, -.was-validated .input-group .form-select:invalid:focus, -.input-group .form-select.is-invalid:focus { - z-index: 3; -} - -.btn { - display: inline-block; - font-weight: 400; - line-height: 1.5; - color: #212529; - text-align: center; - text-decoration: none; - vertical-align: middle; - cursor: pointer; - -webkit-user-select: none; - -moz-user-select: none; - user-select: none; - background-color: transparent; - border: 1px solid transparent; - padding: 0.375rem 0.75rem; - font-size: 1rem; - border-radius: 0.25rem; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .btn { - transition: none; - } -} -.btn:hover { - color: #212529; -} -.btn-check:focus + .btn, .btn:focus { - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} -.btn:disabled, .btn.disabled, fieldset:disabled .btn { - pointer-events: none; - opacity: 0.65; -} - -.btn-primary { - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} -.btn-primary:hover { - color: #fff; - background-color: #0b5ed7; - border-color: #0a58ca; -} -.btn-check:focus + .btn-primary, .btn-primary:focus { - color: #fff; - background-color: #0b5ed7; - border-color: #0a58ca; - box-shadow: 0 0 0 0.25rem rgba(49, 132, 253, 0.5); -} -.btn-check:checked + .btn-primary, .btn-check:active + .btn-primary, .btn-primary:active, .btn-primary.active, .show > .btn-primary.dropdown-toggle { - color: #fff; - background-color: #0a58ca; - border-color: #0a53be; -} -.btn-check:checked + .btn-primary:focus, .btn-check:active + .btn-primary:focus, .btn-primary:active:focus, .btn-primary.active:focus, .show > .btn-primary.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(49, 132, 253, 0.5); -} -.btn-primary:disabled, .btn-primary.disabled { - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} - -.btn-secondary { - color: #fff; - background-color: #6c757d; - border-color: #6c757d; -} -.btn-secondary:hover { - color: #fff; - background-color: #5c636a; - border-color: #565e64; -} -.btn-check:focus + .btn-secondary, .btn-secondary:focus { - color: #fff; - background-color: #5c636a; - border-color: #565e64; - box-shadow: 0 0 0 0.25rem rgba(130, 138, 145, 0.5); -} -.btn-check:checked + .btn-secondary, .btn-check:active + .btn-secondary, .btn-secondary:active, .btn-secondary.active, .show > .btn-secondary.dropdown-toggle { - color: #fff; - background-color: #565e64; - border-color: #51585e; -} -.btn-check:checked + .btn-secondary:focus, .btn-check:active + .btn-secondary:focus, .btn-secondary:active:focus, .btn-secondary.active:focus, .show > .btn-secondary.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(130, 138, 145, 0.5); -} -.btn-secondary:disabled, .btn-secondary.disabled { - color: #fff; - background-color: #6c757d; - border-color: #6c757d; -} - -.btn-success { - color: #fff; - background-color: #198754; - border-color: #198754; -} -.btn-success:hover { - color: #fff; - background-color: #157347; - border-color: #146c43; -} -.btn-check:focus + .btn-success, .btn-success:focus { - color: #fff; - background-color: #157347; - border-color: #146c43; - box-shadow: 0 0 0 0.25rem rgba(60, 153, 110, 0.5); -} -.btn-check:checked + .btn-success, .btn-check:active + .btn-success, .btn-success:active, .btn-success.active, .show > .btn-success.dropdown-toggle { - color: #fff; - background-color: #146c43; - border-color: #13653f; -} -.btn-check:checked + .btn-success:focus, .btn-check:active + .btn-success:focus, .btn-success:active:focus, .btn-success.active:focus, .show > .btn-success.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(60, 153, 110, 0.5); -} -.btn-success:disabled, .btn-success.disabled { - color: #fff; - background-color: #198754; - border-color: #198754; -} - -.btn-info { - color: #000; - background-color: #0dcaf0; - border-color: #0dcaf0; -} -.btn-info:hover { - color: #000; - background-color: #31d2f2; - border-color: #25cff2; -} -.btn-check:focus + .btn-info, .btn-info:focus { - color: #000; - background-color: #31d2f2; - border-color: #25cff2; - box-shadow: 0 0 0 0.25rem rgba(11, 172, 204, 0.5); -} -.btn-check:checked + .btn-info, .btn-check:active + .btn-info, .btn-info:active, .btn-info.active, .show > .btn-info.dropdown-toggle { - color: #000; - background-color: #3dd5f3; - border-color: #25cff2; -} -.btn-check:checked + .btn-info:focus, .btn-check:active + .btn-info:focus, .btn-info:active:focus, .btn-info.active:focus, .show > .btn-info.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(11, 172, 204, 0.5); -} -.btn-info:disabled, .btn-info.disabled { - color: #000; - background-color: #0dcaf0; - border-color: #0dcaf0; -} - -.btn-warning { - color: #000; - background-color: #ffc107; - border-color: #ffc107; -} -.btn-warning:hover { - color: #000; - background-color: #ffca2c; - border-color: #ffc720; -} -.btn-check:focus + .btn-warning, .btn-warning:focus { - color: #000; - background-color: #ffca2c; - border-color: #ffc720; - box-shadow: 0 0 0 0.25rem rgba(217, 164, 6, 0.5); -} -.btn-check:checked + .btn-warning, .btn-check:active + .btn-warning, .btn-warning:active, .btn-warning.active, .show > .btn-warning.dropdown-toggle { - color: #000; - background-color: #ffcd39; - border-color: #ffc720; -} -.btn-check:checked + .btn-warning:focus, .btn-check:active + .btn-warning:focus, .btn-warning:active:focus, .btn-warning.active:focus, .show > .btn-warning.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(217, 164, 6, 0.5); -} -.btn-warning:disabled, .btn-warning.disabled { - color: #000; - background-color: #ffc107; - border-color: #ffc107; -} - -.btn-danger { - color: #fff; - background-color: #dc3545; - border-color: #dc3545; -} -.btn-danger:hover { - color: #fff; - background-color: #bb2d3b; - border-color: #b02a37; -} -.btn-check:focus + .btn-danger, .btn-danger:focus { - color: #fff; - background-color: #bb2d3b; - border-color: #b02a37; - box-shadow: 0 0 0 0.25rem rgba(225, 83, 97, 0.5); -} -.btn-check:checked + .btn-danger, .btn-check:active + .btn-danger, .btn-danger:active, .btn-danger.active, .show > .btn-danger.dropdown-toggle { - color: #fff; - background-color: #b02a37; - border-color: #a52834; -} -.btn-check:checked + .btn-danger:focus, .btn-check:active + .btn-danger:focus, .btn-danger:active:focus, .btn-danger.active:focus, .show > .btn-danger.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(225, 83, 97, 0.5); -} -.btn-danger:disabled, .btn-danger.disabled { - color: #fff; - background-color: #dc3545; - border-color: #dc3545; -} - -.btn-light { - color: #000; - background-color: #f8f9fa; - border-color: #f8f9fa; -} -.btn-light:hover { - color: #000; - background-color: #f9fafb; - border-color: #f9fafb; -} -.btn-check:focus + .btn-light, .btn-light:focus { - color: #000; - background-color: #f9fafb; - border-color: #f9fafb; - box-shadow: 0 0 0 0.25rem rgba(211, 212, 213, 0.5); -} -.btn-check:checked + .btn-light, .btn-check:active + .btn-light, .btn-light:active, .btn-light.active, .show > .btn-light.dropdown-toggle { - color: #000; - background-color: #f9fafb; - border-color: #f9fafb; -} -.btn-check:checked + .btn-light:focus, .btn-check:active + .btn-light:focus, .btn-light:active:focus, .btn-light.active:focus, .show > .btn-light.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(211, 212, 213, 0.5); -} -.btn-light:disabled, .btn-light.disabled { - color: #000; - background-color: #f8f9fa; - border-color: #f8f9fa; -} - -.btn-dark { - color: #fff; - background-color: #212529; - border-color: #212529; -} -.btn-dark:hover { - color: #fff; - background-color: #1c1f23; - border-color: #1a1e21; -} -.btn-check:focus + .btn-dark, .btn-dark:focus { - color: #fff; - background-color: #1c1f23; - border-color: #1a1e21; - box-shadow: 0 0 0 0.25rem rgba(66, 70, 73, 0.5); -} -.btn-check:checked + .btn-dark, .btn-check:active + .btn-dark, .btn-dark:active, .btn-dark.active, .show > .btn-dark.dropdown-toggle { - color: #fff; - background-color: #1a1e21; - border-color: #191c1f; -} -.btn-check:checked + .btn-dark:focus, .btn-check:active + .btn-dark:focus, .btn-dark:active:focus, .btn-dark.active:focus, .show > .btn-dark.dropdown-toggle:focus { - box-shadow: 0 0 0 0.25rem rgba(66, 70, 73, 0.5); -} -.btn-dark:disabled, .btn-dark.disabled { - color: #fff; - background-color: #212529; - border-color: #212529; -} - -.btn-outline-primary { - color: #0d6efd; - border-color: #0d6efd; -} -.btn-outline-primary:hover { - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} -.btn-check:focus + .btn-outline-primary, .btn-outline-primary:focus { - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.5); -} -.btn-check:checked + .btn-outline-primary, .btn-check:active + .btn-outline-primary, .btn-outline-primary:active, .btn-outline-primary.active, .btn-outline-primary.dropdown-toggle.show { - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} -.btn-check:checked + .btn-outline-primary:focus, .btn-check:active + .btn-outline-primary:focus, .btn-outline-primary:active:focus, .btn-outline-primary.active:focus, .btn-outline-primary.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.5); -} -.btn-outline-primary:disabled, .btn-outline-primary.disabled { - color: #0d6efd; - background-color: transparent; -} - -.btn-outline-secondary { - color: #6c757d; - border-color: #6c757d; -} -.btn-outline-secondary:hover { - color: #fff; - background-color: #6c757d; - border-color: #6c757d; -} -.btn-check:focus + .btn-outline-secondary, .btn-outline-secondary:focus { - box-shadow: 0 0 0 0.25rem rgba(108, 117, 125, 0.5); -} -.btn-check:checked + .btn-outline-secondary, .btn-check:active + .btn-outline-secondary, .btn-outline-secondary:active, .btn-outline-secondary.active, .btn-outline-secondary.dropdown-toggle.show { - color: #fff; - background-color: #6c757d; - border-color: #6c757d; -} -.btn-check:checked + .btn-outline-secondary:focus, .btn-check:active + .btn-outline-secondary:focus, .btn-outline-secondary:active:focus, .btn-outline-secondary.active:focus, .btn-outline-secondary.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(108, 117, 125, 0.5); -} -.btn-outline-secondary:disabled, .btn-outline-secondary.disabled { - color: #6c757d; - background-color: transparent; -} - -.btn-outline-success { - color: #198754; - border-color: #198754; -} -.btn-outline-success:hover { - color: #fff; - background-color: #198754; - border-color: #198754; -} -.btn-check:focus + .btn-outline-success, .btn-outline-success:focus { - box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.5); -} -.btn-check:checked + .btn-outline-success, .btn-check:active + .btn-outline-success, .btn-outline-success:active, .btn-outline-success.active, .btn-outline-success.dropdown-toggle.show { - color: #fff; - background-color: #198754; - border-color: #198754; -} -.btn-check:checked + .btn-outline-success:focus, .btn-check:active + .btn-outline-success:focus, .btn-outline-success:active:focus, .btn-outline-success.active:focus, .btn-outline-success.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.5); -} -.btn-outline-success:disabled, .btn-outline-success.disabled { - color: #198754; - background-color: transparent; -} - -.btn-outline-info { - color: #0dcaf0; - border-color: #0dcaf0; -} -.btn-outline-info:hover { - color: #000; - background-color: #0dcaf0; - border-color: #0dcaf0; -} -.btn-check:focus + .btn-outline-info, .btn-outline-info:focus { - box-shadow: 0 0 0 0.25rem rgba(13, 202, 240, 0.5); -} -.btn-check:checked + .btn-outline-info, .btn-check:active + .btn-outline-info, .btn-outline-info:active, .btn-outline-info.active, .btn-outline-info.dropdown-toggle.show { - color: #000; - background-color: #0dcaf0; - border-color: #0dcaf0; -} -.btn-check:checked + .btn-outline-info:focus, .btn-check:active + .btn-outline-info:focus, .btn-outline-info:active:focus, .btn-outline-info.active:focus, .btn-outline-info.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(13, 202, 240, 0.5); -} -.btn-outline-info:disabled, .btn-outline-info.disabled { - color: #0dcaf0; - background-color: transparent; -} - -.btn-outline-warning { - color: #ffc107; - border-color: #ffc107; -} -.btn-outline-warning:hover { - color: #000; - background-color: #ffc107; - border-color: #ffc107; -} -.btn-check:focus + .btn-outline-warning, .btn-outline-warning:focus { - box-shadow: 0 0 0 0.25rem rgba(255, 193, 7, 0.5); -} -.btn-check:checked + .btn-outline-warning, .btn-check:active + .btn-outline-warning, .btn-outline-warning:active, .btn-outline-warning.active, .btn-outline-warning.dropdown-toggle.show { - color: #000; - background-color: #ffc107; - border-color: #ffc107; -} -.btn-check:checked + .btn-outline-warning:focus, .btn-check:active + .btn-outline-warning:focus, .btn-outline-warning:active:focus, .btn-outline-warning.active:focus, .btn-outline-warning.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(255, 193, 7, 0.5); -} -.btn-outline-warning:disabled, .btn-outline-warning.disabled { - color: #ffc107; - background-color: transparent; -} - -.btn-outline-danger { - color: #dc3545; - border-color: #dc3545; -} -.btn-outline-danger:hover { - color: #fff; - background-color: #dc3545; - border-color: #dc3545; -} -.btn-check:focus + .btn-outline-danger, .btn-outline-danger:focus { - box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.5); -} -.btn-check:checked + .btn-outline-danger, .btn-check:active + .btn-outline-danger, .btn-outline-danger:active, .btn-outline-danger.active, .btn-outline-danger.dropdown-toggle.show { - color: #fff; - background-color: #dc3545; - border-color: #dc3545; -} -.btn-check:checked + .btn-outline-danger:focus, .btn-check:active + .btn-outline-danger:focus, .btn-outline-danger:active:focus, .btn-outline-danger.active:focus, .btn-outline-danger.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.5); -} -.btn-outline-danger:disabled, .btn-outline-danger.disabled { - color: #dc3545; - background-color: transparent; -} - -.btn-outline-light { - color: #f8f9fa; - border-color: #f8f9fa; -} -.btn-outline-light:hover { - color: #000; - background-color: #f8f9fa; - border-color: #f8f9fa; -} -.btn-check:focus + .btn-outline-light, .btn-outline-light:focus { - box-shadow: 0 0 0 0.25rem rgba(248, 249, 250, 0.5); -} -.btn-check:checked + .btn-outline-light, .btn-check:active + .btn-outline-light, .btn-outline-light:active, .btn-outline-light.active, .btn-outline-light.dropdown-toggle.show { - color: #000; - background-color: #f8f9fa; - border-color: #f8f9fa; -} -.btn-check:checked + .btn-outline-light:focus, .btn-check:active + .btn-outline-light:focus, .btn-outline-light:active:focus, .btn-outline-light.active:focus, .btn-outline-light.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(248, 249, 250, 0.5); -} -.btn-outline-light:disabled, .btn-outline-light.disabled { - color: #f8f9fa; - background-color: transparent; -} - -.btn-outline-dark { - color: #212529; - border-color: #212529; -} -.btn-outline-dark:hover { - color: #fff; - background-color: #212529; - border-color: #212529; -} -.btn-check:focus + .btn-outline-dark, .btn-outline-dark:focus { - box-shadow: 0 0 0 0.25rem rgba(33, 37, 41, 0.5); -} -.btn-check:checked + .btn-outline-dark, .btn-check:active + .btn-outline-dark, .btn-outline-dark:active, .btn-outline-dark.active, .btn-outline-dark.dropdown-toggle.show { - color: #fff; - background-color: #212529; - border-color: #212529; -} -.btn-check:checked + .btn-outline-dark:focus, .btn-check:active + .btn-outline-dark:focus, .btn-outline-dark:active:focus, .btn-outline-dark.active:focus, .btn-outline-dark.dropdown-toggle.show:focus { - box-shadow: 0 0 0 0.25rem rgba(33, 37, 41, 0.5); -} -.btn-outline-dark:disabled, .btn-outline-dark.disabled { - color: #212529; - background-color: transparent; -} - -.btn-link { - font-weight: 400; - color: #0d6efd; - text-decoration: underline; -} -.btn-link:hover { - color: #0a58ca; -} -.btn-link:disabled, .btn-link.disabled { - color: #6c757d; -} - -.btn-lg, .btn-group-lg > .btn { - padding: 0.5rem 1rem; - font-size: 1.25rem; - border-radius: 0.3rem; -} - -.btn-sm, .btn-group-sm > .btn { - padding: 0.25rem 0.5rem; - font-size: 0.875rem; - border-radius: 0.2rem; -} - -.fade { - transition: opacity 0.15s linear; -} -@media (prefers-reduced-motion: reduce) { - .fade { - transition: none; - } -} -.fade:not(.show) { - opacity: 0; -} - -.collapse:not(.show) { - display: none; -} - -.collapsing { - height: 0; - overflow: hidden; - transition: height 0.35s ease; -} -@media (prefers-reduced-motion: reduce) { - .collapsing { - transition: none; - } -} -.collapsing.collapse-horizontal { - width: 0; - height: auto; - transition: width 0.35s ease; -} -@media (prefers-reduced-motion: reduce) { - .collapsing.collapse-horizontal { - transition: none; - } -} - -.dropup, -.dropend, -.dropdown, -.dropstart { - position: relative; -} - -.dropdown-toggle { - white-space: nowrap; -} -.dropdown-toggle::after { - display: inline-block; - margin-left: 0.255em; - vertical-align: 0.255em; - content: ""; - border-top: 0.3em solid; - border-right: 0.3em solid transparent; - border-bottom: 0; - border-left: 0.3em solid transparent; -} -.dropdown-toggle:empty::after { - margin-left: 0; -} - -.dropdown-menu { - position: absolute; - z-index: 1000; - display: none; - min-width: 10rem; - padding: 0.5rem 0; - margin: 0; - font-size: 1rem; - color: #212529; - text-align: left; - list-style: none; - background-color: #fff; - background-clip: padding-box; - border: 1px solid rgba(0, 0, 0, 0.15); - border-radius: 0.25rem; -} -.dropdown-menu[data-bs-popper] { - top: 100%; - left: 0; - margin-top: 0.125rem; -} - -.dropdown-menu-start { - --bs-position: start; -} -.dropdown-menu-start[data-bs-popper] { - right: auto; - left: 0; -} - -.dropdown-menu-end { - --bs-position: end; -} -.dropdown-menu-end[data-bs-popper] { - right: 0; - left: auto; -} - -@media (min-width: 576px) { - .dropdown-menu-sm-start { - --bs-position: start; - } - .dropdown-menu-sm-start[data-bs-popper] { - right: auto; - left: 0; - } - - .dropdown-menu-sm-end { - --bs-position: end; - } - .dropdown-menu-sm-end[data-bs-popper] { - right: 0; - left: auto; - } -} -@media (min-width: 768px) { - .dropdown-menu-md-start { - --bs-position: start; - } - .dropdown-menu-md-start[data-bs-popper] { - right: auto; - left: 0; - } - - .dropdown-menu-md-end { - --bs-position: end; - } - .dropdown-menu-md-end[data-bs-popper] { - right: 0; - left: auto; - } -} -@media (min-width: 992px) { - .dropdown-menu-lg-start { - --bs-position: start; - } - .dropdown-menu-lg-start[data-bs-popper] { - right: auto; - left: 0; - } - - .dropdown-menu-lg-end { - --bs-position: end; - } - .dropdown-menu-lg-end[data-bs-popper] { - right: 0; - left: auto; - } -} -@media (min-width: 1200px) { - .dropdown-menu-xl-start { - --bs-position: start; - } - .dropdown-menu-xl-start[data-bs-popper] { - right: auto; - left: 0; - } - - .dropdown-menu-xl-end { - --bs-position: end; - } - .dropdown-menu-xl-end[data-bs-popper] { - right: 0; - left: auto; - } -} -@media (min-width: 1400px) { - .dropdown-menu-xxl-start { - --bs-position: start; - } - .dropdown-menu-xxl-start[data-bs-popper] { - right: auto; - left: 0; - } - - .dropdown-menu-xxl-end { - --bs-position: end; - } - .dropdown-menu-xxl-end[data-bs-popper] { - right: 0; - left: auto; - } -} -.dropup .dropdown-menu[data-bs-popper] { - top: auto; - bottom: 100%; - margin-top: 0; - margin-bottom: 0.125rem; -} -.dropup .dropdown-toggle::after { - display: inline-block; - margin-left: 0.255em; - vertical-align: 0.255em; - content: ""; - border-top: 0; - border-right: 0.3em solid transparent; - border-bottom: 0.3em solid; - border-left: 0.3em solid transparent; -} -.dropup .dropdown-toggle:empty::after { - margin-left: 0; -} - -.dropend .dropdown-menu[data-bs-popper] { - top: 0; - right: auto; - left: 100%; - margin-top: 0; - margin-left: 0.125rem; -} -.dropend .dropdown-toggle::after { - display: inline-block; - margin-left: 0.255em; - vertical-align: 0.255em; - content: ""; - border-top: 0.3em solid transparent; - border-right: 0; - border-bottom: 0.3em solid transparent; - border-left: 0.3em solid; -} -.dropend .dropdown-toggle:empty::after { - margin-left: 0; -} -.dropend .dropdown-toggle::after { - vertical-align: 0; -} - -.dropstart .dropdown-menu[data-bs-popper] { - top: 0; - right: 100%; - left: auto; - margin-top: 0; - margin-right: 0.125rem; -} -.dropstart .dropdown-toggle::after { - display: inline-block; - margin-left: 0.255em; - vertical-align: 0.255em; - content: ""; -} -.dropstart .dropdown-toggle::after { - display: none; -} -.dropstart .dropdown-toggle::before { - display: inline-block; - margin-right: 0.255em; - vertical-align: 0.255em; - content: ""; - border-top: 0.3em solid transparent; - border-right: 0.3em solid; - border-bottom: 0.3em solid transparent; -} -.dropstart .dropdown-toggle:empty::after { - margin-left: 0; -} -.dropstart .dropdown-toggle::before { - vertical-align: 0; -} - -.dropdown-divider { - height: 0; - margin: 0.5rem 0; - overflow: hidden; - border-top: 1px solid rgba(0, 0, 0, 0.15); -} - -.dropdown-item { - display: block; - width: 100%; - padding: 0.25rem 1rem; - clear: both; - font-weight: 400; - color: #212529; - text-align: inherit; - text-decoration: none; - white-space: nowrap; - background-color: transparent; - border: 0; -} -.dropdown-item:hover, .dropdown-item:focus { - color: #1e2125; - background-color: #e9ecef; -} -.dropdown-item.active, .dropdown-item:active { - color: #fff; - text-decoration: none; - background-color: #0d6efd; -} -.dropdown-item.disabled, .dropdown-item:disabled { - color: #adb5bd; - pointer-events: none; - background-color: transparent; -} - -.dropdown-menu.show { - display: block; -} - -.dropdown-header { - display: block; - padding: 0.5rem 1rem; - margin-bottom: 0; - font-size: 0.875rem; - color: #6c757d; - white-space: nowrap; -} - -.dropdown-item-text { - display: block; - padding: 0.25rem 1rem; - color: #212529; -} - -.dropdown-menu-dark { - color: #dee2e6; - background-color: #343a40; - border-color: rgba(0, 0, 0, 0.15); -} -.dropdown-menu-dark .dropdown-item { - color: #dee2e6; -} -.dropdown-menu-dark .dropdown-item:hover, .dropdown-menu-dark .dropdown-item:focus { - color: #fff; - background-color: rgba(255, 255, 255, 0.15); -} -.dropdown-menu-dark .dropdown-item.active, .dropdown-menu-dark .dropdown-item:active { - color: #fff; - background-color: #0d6efd; -} -.dropdown-menu-dark .dropdown-item.disabled, .dropdown-menu-dark .dropdown-item:disabled { - color: #adb5bd; -} -.dropdown-menu-dark .dropdown-divider { - border-color: rgba(0, 0, 0, 0.15); -} -.dropdown-menu-dark .dropdown-item-text { - color: #dee2e6; -} -.dropdown-menu-dark .dropdown-header { - color: #adb5bd; -} - -.btn-group, -.btn-group-vertical { - position: relative; - display: inline-flex; - vertical-align: middle; -} -.btn-group > .btn, -.btn-group-vertical > .btn { - position: relative; - flex: 1 1 auto; -} -.btn-group > .btn-check:checked + .btn, -.btn-group > .btn-check:focus + .btn, -.btn-group > .btn:hover, -.btn-group > .btn:focus, -.btn-group > .btn:active, -.btn-group > .btn.active, -.btn-group-vertical > .btn-check:checked + .btn, -.btn-group-vertical > .btn-check:focus + .btn, -.btn-group-vertical > .btn:hover, -.btn-group-vertical > .btn:focus, -.btn-group-vertical > .btn:active, -.btn-group-vertical > .btn.active { - z-index: 1; -} - -.btn-toolbar { - display: flex; - flex-wrap: wrap; - justify-content: flex-start; -} -.btn-toolbar .input-group { - width: auto; -} - -.btn-group > .btn:not(:first-child), -.btn-group > .btn-group:not(:first-child) { - margin-left: -1px; -} -.btn-group > .btn:not(:last-child):not(.dropdown-toggle), -.btn-group > .btn-group:not(:last-child) > .btn { - border-top-right-radius: 0; - border-bottom-right-radius: 0; -} -.btn-group > .btn:nth-child(n+3), -.btn-group > :not(.btn-check) + .btn, -.btn-group > .btn-group:not(:first-child) > .btn { - border-top-left-radius: 0; - border-bottom-left-radius: 0; -} - -.dropdown-toggle-split { - padding-right: 0.5625rem; - padding-left: 0.5625rem; -} -.dropdown-toggle-split::after, .dropup .dropdown-toggle-split::after, .dropend .dropdown-toggle-split::after { - margin-left: 0; -} -.dropstart .dropdown-toggle-split::before { - margin-right: 0; -} - -.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split { - padding-right: 0.375rem; - padding-left: 0.375rem; -} - -.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split { - padding-right: 0.75rem; - padding-left: 0.75rem; -} - -.btn-group-vertical { - flex-direction: column; - align-items: flex-start; - justify-content: center; -} -.btn-group-vertical > .btn, -.btn-group-vertical > .btn-group { - width: 100%; -} -.btn-group-vertical > .btn:not(:first-child), -.btn-group-vertical > .btn-group:not(:first-child) { - margin-top: -1px; -} -.btn-group-vertical > .btn:not(:last-child):not(.dropdown-toggle), -.btn-group-vertical > .btn-group:not(:last-child) > .btn { - border-bottom-right-radius: 0; - border-bottom-left-radius: 0; -} -.btn-group-vertical > .btn ~ .btn, -.btn-group-vertical > .btn-group:not(:first-child) > .btn { - border-top-left-radius: 0; - border-top-right-radius: 0; -} - -.nav { - display: flex; - flex-wrap: wrap; - padding-left: 0; - margin-bottom: 0; - list-style: none; -} - -.nav-link { - display: block; - padding: 0.5rem 1rem; - color: #0d6efd; - text-decoration: none; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .nav-link { - transition: none; - } -} -.nav-link:hover, .nav-link:focus { - color: #0a58ca; -} -.nav-link.disabled { - color: #6c757d; - pointer-events: none; - cursor: default; -} - -.nav-tabs { - border-bottom: 1px solid #dee2e6; -} -.nav-tabs .nav-link { - margin-bottom: -1px; - background: none; - border: 1px solid transparent; - border-top-left-radius: 0.25rem; - border-top-right-radius: 0.25rem; -} -.nav-tabs .nav-link:hover, .nav-tabs .nav-link:focus { - border-color: #e9ecef #e9ecef #dee2e6; - isolation: isolate; -} -.nav-tabs .nav-link.disabled { - color: #6c757d; - background-color: transparent; - border-color: transparent; -} -.nav-tabs .nav-link.active, -.nav-tabs .nav-item.show .nav-link { - color: #495057; - background-color: #fff; - border-color: #dee2e6 #dee2e6 #fff; -} -.nav-tabs .dropdown-menu { - margin-top: -1px; - border-top-left-radius: 0; - border-top-right-radius: 0; -} - -.nav-pills .nav-link { - background: none; - border: 0; - border-radius: 0.25rem; -} -.nav-pills .nav-link.active, -.nav-pills .show > .nav-link { - color: #fff; - background-color: #0d6efd; -} - -.nav-fill > .nav-link, -.nav-fill .nav-item { - flex: 1 1 auto; - text-align: center; -} - -.nav-justified > .nav-link, -.nav-justified .nav-item { - flex-basis: 0; - flex-grow: 1; - text-align: center; -} - -.nav-fill .nav-item .nav-link, -.nav-justified .nav-item .nav-link { - width: 100%; -} - -.tab-content > .tab-pane { - display: none; -} -.tab-content > .active { - display: block; -} - -.navbar { - position: relative; - display: flex; - flex-wrap: wrap; - align-items: center; - justify-content: space-between; - padding-top: 0.5rem; - padding-bottom: 0.5rem; -} -.navbar > .container, -.navbar > .container-fluid, -.navbar > .container-sm, -.navbar > .container-md, -.navbar > .container-lg, -.navbar > .container-xl, -.navbar > .container-xxl { - display: flex; - flex-wrap: inherit; - align-items: center; - justify-content: space-between; -} -.navbar-brand { - padding-top: 0.3125rem; - padding-bottom: 0.3125rem; - margin-right: 1rem; - font-size: 1.25rem; - text-decoration: none; - white-space: nowrap; -} -.navbar-nav { - display: flex; - flex-direction: column; - padding-left: 0; - margin-bottom: 0; - list-style: none; -} -.navbar-nav .nav-link { - padding-right: 0; - padding-left: 0; -} -.navbar-nav .dropdown-menu { - position: static; -} - -.navbar-text { - padding-top: 0.5rem; - padding-bottom: 0.5rem; -} - -.navbar-collapse { - flex-basis: 100%; - flex-grow: 1; - align-items: center; -} - -.navbar-toggler { - padding: 0.25rem 0.75rem; - font-size: 1.25rem; - line-height: 1; - background-color: transparent; - border: 1px solid transparent; - border-radius: 0.25rem; - transition: box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .navbar-toggler { - transition: none; - } -} -.navbar-toggler:hover { - text-decoration: none; -} -.navbar-toggler:focus { - text-decoration: none; - outline: 0; - box-shadow: 0 0 0 0.25rem; -} - -.navbar-toggler-icon { - display: inline-block; - width: 1.5em; - height: 1.5em; - vertical-align: middle; - background-repeat: no-repeat; - background-position: center; - background-size: 100%; -} - -.navbar-nav-scroll { - max-height: var(--bs-scroll-height, 75vh); - overflow-y: auto; -} - -@media (min-width: 576px) { - .navbar-expand-sm { - flex-wrap: nowrap; - justify-content: flex-start; - } - .navbar-expand-sm .navbar-nav { - flex-direction: row; - } - .navbar-expand-sm .navbar-nav .dropdown-menu { - position: absolute; - } - .navbar-expand-sm .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; - } - .navbar-expand-sm .navbar-nav-scroll { - overflow: visible; - } - .navbar-expand-sm .navbar-collapse { - display: flex !important; - flex-basis: auto; - } - .navbar-expand-sm .navbar-toggler { - display: none; - } - .navbar-expand-sm .offcanvas-header { - display: none; - } - .navbar-expand-sm .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; - } - .navbar-expand-sm .offcanvas-top, -.navbar-expand-sm .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; - } - .navbar-expand-sm .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; - } -} -@media (min-width: 768px) { - .navbar-expand-md { - flex-wrap: nowrap; - justify-content: flex-start; - } - .navbar-expand-md .navbar-nav { - flex-direction: row; - } - .navbar-expand-md .navbar-nav .dropdown-menu { - position: absolute; - } - .navbar-expand-md .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; - } - .navbar-expand-md .navbar-nav-scroll { - overflow: visible; - } - .navbar-expand-md .navbar-collapse { - display: flex !important; - flex-basis: auto; - } - .navbar-expand-md .navbar-toggler { - display: none; - } - .navbar-expand-md .offcanvas-header { - display: none; - } - .navbar-expand-md .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; - } - .navbar-expand-md .offcanvas-top, -.navbar-expand-md .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; - } - .navbar-expand-md .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; - } -} -@media (min-width: 992px) { - .navbar-expand-lg { - flex-wrap: nowrap; - justify-content: flex-start; - } - .navbar-expand-lg .navbar-nav { - flex-direction: row; - } - .navbar-expand-lg .navbar-nav .dropdown-menu { - position: absolute; - } - .navbar-expand-lg .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; - } - .navbar-expand-lg .navbar-nav-scroll { - overflow: visible; - } - .navbar-expand-lg .navbar-collapse { - display: flex !important; - flex-basis: auto; - } - .navbar-expand-lg .navbar-toggler { - display: none; - } - .navbar-expand-lg .offcanvas-header { - display: none; - } - .navbar-expand-lg .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; - } - .navbar-expand-lg .offcanvas-top, -.navbar-expand-lg .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; - } - .navbar-expand-lg .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; - } -} -@media (min-width: 1200px) { - .navbar-expand-xl { - flex-wrap: nowrap; - justify-content: flex-start; - } - .navbar-expand-xl .navbar-nav { - flex-direction: row; - } - .navbar-expand-xl .navbar-nav .dropdown-menu { - position: absolute; - } - .navbar-expand-xl .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; - } - .navbar-expand-xl .navbar-nav-scroll { - overflow: visible; - } - .navbar-expand-xl .navbar-collapse { - display: flex !important; - flex-basis: auto; - } - .navbar-expand-xl .navbar-toggler { - display: none; - } - .navbar-expand-xl .offcanvas-header { - display: none; - } - .navbar-expand-xl .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; - } - .navbar-expand-xl .offcanvas-top, -.navbar-expand-xl .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; - } - .navbar-expand-xl .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; - } -} -@media (min-width: 1400px) { - .navbar-expand-xxl { - flex-wrap: nowrap; - justify-content: flex-start; - } - .navbar-expand-xxl .navbar-nav { - flex-direction: row; - } - .navbar-expand-xxl .navbar-nav .dropdown-menu { - position: absolute; - } - .navbar-expand-xxl .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; - } - .navbar-expand-xxl .navbar-nav-scroll { - overflow: visible; - } - .navbar-expand-xxl .navbar-collapse { - display: flex !important; - flex-basis: auto; - } - .navbar-expand-xxl .navbar-toggler { - display: none; - } - .navbar-expand-xxl .offcanvas-header { - display: none; - } - .navbar-expand-xxl .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; - } - .navbar-expand-xxl .offcanvas-top, -.navbar-expand-xxl .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; - } - .navbar-expand-xxl .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; - } -} -.navbar-expand { - flex-wrap: nowrap; - justify-content: flex-start; -} -.navbar-expand .navbar-nav { - flex-direction: row; -} -.navbar-expand .navbar-nav .dropdown-menu { - position: absolute; -} -.navbar-expand .navbar-nav .nav-link { - padding-right: 0.5rem; - padding-left: 0.5rem; -} -.navbar-expand .navbar-nav-scroll { - overflow: visible; -} -.navbar-expand .navbar-collapse { - display: flex !important; - flex-basis: auto; -} -.navbar-expand .navbar-toggler { - display: none; -} -.navbar-expand .offcanvas-header { - display: none; -} -.navbar-expand .offcanvas { - position: inherit; - bottom: 0; - z-index: 1000; - flex-grow: 1; - visibility: visible !important; - background-color: transparent; - border-right: 0; - border-left: 0; - transition: none; - transform: none; -} -.navbar-expand .offcanvas-top, -.navbar-expand .offcanvas-bottom { - height: auto; - border-top: 0; - border-bottom: 0; -} -.navbar-expand .offcanvas-body { - display: flex; - flex-grow: 0; - padding: 0; - overflow-y: visible; -} - -.navbar-light .navbar-brand { - color: rgba(0, 0, 0, 0.9); -} -.navbar-light .navbar-brand:hover, .navbar-light .navbar-brand:focus { - color: rgba(0, 0, 0, 0.9); -} -.navbar-light .navbar-nav .nav-link { - color: rgba(0, 0, 0, 0.55); -} -.navbar-light .navbar-nav .nav-link:hover, .navbar-light .navbar-nav .nav-link:focus { - color: rgba(0, 0, 0, 0.7); -} -.navbar-light .navbar-nav .nav-link.disabled { - color: rgba(0, 0, 0, 0.3); -} -.navbar-light .navbar-nav .show > .nav-link, -.navbar-light .navbar-nav .nav-link.active { - color: rgba(0, 0, 0, 0.9); -} -.navbar-light .navbar-toggler { - color: rgba(0, 0, 0, 0.55); - border-color: rgba(0, 0, 0, 0.1); -} -.navbar-light .navbar-toggler-icon { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%280, 0, 0, 0.55%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e"); -} -.navbar-light .navbar-text { - color: rgba(0, 0, 0, 0.55); -} -.navbar-light .navbar-text a, -.navbar-light .navbar-text a:hover, -.navbar-light .navbar-text a:focus { - color: rgba(0, 0, 0, 0.9); -} - -.navbar-dark .navbar-brand { - color: #fff; -} -.navbar-dark .navbar-brand:hover, .navbar-dark .navbar-brand:focus { - color: #fff; -} -.navbar-dark .navbar-nav .nav-link { - color: rgba(255, 255, 255, 0.55); -} -.navbar-dark .navbar-nav .nav-link:hover, .navbar-dark .navbar-nav .nav-link:focus { - color: rgba(255, 255, 255, 0.75); -} -.navbar-dark .navbar-nav .nav-link.disabled { - color: rgba(255, 255, 255, 0.25); -} -.navbar-dark .navbar-nav .show > .nav-link, -.navbar-dark .navbar-nav .nav-link.active { - color: #fff; -} -.navbar-dark .navbar-toggler { - color: rgba(255, 255, 255, 0.55); - border-color: rgba(255, 255, 255, 0.1); -} -.navbar-dark .navbar-toggler-icon { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%28255, 255, 255, 0.55%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e"); -} -.navbar-dark .navbar-text { - color: rgba(255, 255, 255, 0.55); -} -.navbar-dark .navbar-text a, -.navbar-dark .navbar-text a:hover, -.navbar-dark .navbar-text a:focus { - color: #fff; -} - -.card { - position: relative; - display: flex; - flex-direction: column; - min-width: 0; - word-wrap: break-word; - background-color: #fff; - background-clip: border-box; - border: 1px solid rgba(0, 0, 0, 0.125); - border-radius: 0.25rem; -} -.card > hr { - margin-right: 0; - margin-left: 0; -} -.card > .list-group { - border-top: inherit; - border-bottom: inherit; -} -.card > .list-group:first-child { - border-top-width: 0; - border-top-left-radius: calc(0.25rem - 1px); - border-top-right-radius: calc(0.25rem - 1px); -} -.card > .list-group:last-child { - border-bottom-width: 0; - border-bottom-right-radius: calc(0.25rem - 1px); - border-bottom-left-radius: calc(0.25rem - 1px); -} -.card > .card-header + .list-group, -.card > .list-group + .card-footer { - border-top: 0; -} - -.card-body { - flex: 1 1 auto; - padding: 1rem 1rem; -} - -.card-title { - margin-bottom: 0.5rem; -} - -.card-subtitle { - margin-top: -0.25rem; - margin-bottom: 0; -} - -.card-text:last-child { - margin-bottom: 0; -} - -.card-link + .card-link { - margin-left: 1rem; -} - -.card-header { - padding: 0.5rem 1rem; - margin-bottom: 0; - background-color: rgba(0, 0, 0, 0.03); - border-bottom: 1px solid rgba(0, 0, 0, 0.125); -} -.card-header:first-child { - border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0; -} - -.card-footer { - padding: 0.5rem 1rem; - background-color: rgba(0, 0, 0, 0.03); - border-top: 1px solid rgba(0, 0, 0, 0.125); -} -.card-footer:last-child { - border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px); -} - -.card-header-tabs { - margin-right: -0.5rem; - margin-bottom: -0.5rem; - margin-left: -0.5rem; - border-bottom: 0; -} - -.card-header-pills { - margin-right: -0.5rem; - margin-left: -0.5rem; -} - -.card-img-overlay { - position: absolute; - top: 0; - right: 0; - bottom: 0; - left: 0; - padding: 1rem; - border-radius: calc(0.25rem - 1px); -} - -.card-img, -.card-img-top, -.card-img-bottom { - width: 100%; -} - -.card-img, -.card-img-top { - border-top-left-radius: calc(0.25rem - 1px); - border-top-right-radius: calc(0.25rem - 1px); -} - -.card-img, -.card-img-bottom { - border-bottom-right-radius: calc(0.25rem - 1px); - border-bottom-left-radius: calc(0.25rem - 1px); -} - -.card-group > .card { - margin-bottom: 0.75rem; -} -@media (min-width: 576px) { - .card-group { - display: flex; - flex-flow: row wrap; - } - .card-group > .card { - flex: 1 0 0%; - margin-bottom: 0; - } - .card-group > .card + .card { - margin-left: 0; - border-left: 0; - } - .card-group > .card:not(:last-child) { - border-top-right-radius: 0; - border-bottom-right-radius: 0; - } - .card-group > .card:not(:last-child) .card-img-top, -.card-group > .card:not(:last-child) .card-header { - border-top-right-radius: 0; - } - .card-group > .card:not(:last-child) .card-img-bottom, -.card-group > .card:not(:last-child) .card-footer { - border-bottom-right-radius: 0; - } - .card-group > .card:not(:first-child) { - border-top-left-radius: 0; - border-bottom-left-radius: 0; - } - .card-group > .card:not(:first-child) .card-img-top, -.card-group > .card:not(:first-child) .card-header { - border-top-left-radius: 0; - } - .card-group > .card:not(:first-child) .card-img-bottom, -.card-group > .card:not(:first-child) .card-footer { - border-bottom-left-radius: 0; - } -} - -.accordion-button { - position: relative; - display: flex; - align-items: center; - width: 100%; - padding: 1rem 1.25rem; - font-size: 1rem; - color: #212529; - text-align: left; - background-color: #fff; - border: 0; - border-radius: 0; - overflow-anchor: none; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out, border-radius 0.15s ease; -} -@media (prefers-reduced-motion: reduce) { - .accordion-button { - transition: none; - } -} -.accordion-button:not(.collapsed) { - color: #0c63e4; - background-color: #e7f1ff; - box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.125); -} -.accordion-button:not(.collapsed)::after { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%230c63e4'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e"); - transform: rotate(-180deg); -} -.accordion-button::after { - flex-shrink: 0; - width: 1.25rem; - height: 1.25rem; - margin-left: auto; - content: ""; - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23212529'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e"); - background-repeat: no-repeat; - background-size: 1.25rem; - transition: transform 0.2s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .accordion-button::after { - transition: none; - } -} -.accordion-button:hover { - z-index: 2; -} -.accordion-button:focus { - z-index: 3; - border-color: #86b7fe; - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} - -.accordion-header { - margin-bottom: 0; -} - -.accordion-item { - background-color: #fff; - border: 1px solid rgba(0, 0, 0, 0.125); -} -.accordion-item:first-of-type { - border-top-left-radius: 0.25rem; - border-top-right-radius: 0.25rem; -} -.accordion-item:first-of-type .accordion-button { - border-top-left-radius: calc(0.25rem - 1px); - border-top-right-radius: calc(0.25rem - 1px); -} -.accordion-item:not(:first-of-type) { - border-top: 0; -} -.accordion-item:last-of-type { - border-bottom-right-radius: 0.25rem; - border-bottom-left-radius: 0.25rem; -} -.accordion-item:last-of-type .accordion-button.collapsed { - border-bottom-right-radius: calc(0.25rem - 1px); - border-bottom-left-radius: calc(0.25rem - 1px); -} -.accordion-item:last-of-type .accordion-collapse { - border-bottom-right-radius: 0.25rem; - border-bottom-left-radius: 0.25rem; -} - -.accordion-body { - padding: 1rem 1.25rem; -} - -.accordion-flush .accordion-collapse { - border-width: 0; -} -.accordion-flush .accordion-item { - border-right: 0; - border-left: 0; - border-radius: 0; -} -.accordion-flush .accordion-item:first-child { - border-top: 0; -} -.accordion-flush .accordion-item:last-child { - border-bottom: 0; -} -.accordion-flush .accordion-item .accordion-button { - border-radius: 0; -} - -.breadcrumb { - display: flex; - flex-wrap: wrap; - padding: 0 0; - margin-bottom: 1rem; - list-style: none; -} - -.breadcrumb-item + .breadcrumb-item { - padding-left: 0.5rem; -} -.breadcrumb-item + .breadcrumb-item::before { - float: left; - padding-right: 0.5rem; - color: #6c757d; - content: var(--bs-breadcrumb-divider, "/") /* rtl: var(--bs-breadcrumb-divider, "/") */; -} -.breadcrumb-item.active { - color: #6c757d; -} - -.pagination { - display: flex; - padding-left: 0; - list-style: none; -} - -.page-link { - position: relative; - display: block; - color: #0d6efd; - text-decoration: none; - background-color: #fff; - border: 1px solid #dee2e6; - transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .page-link { - transition: none; - } -} -.page-link:hover { - z-index: 2; - color: #0a58ca; - background-color: #e9ecef; - border-color: #dee2e6; -} -.page-link:focus { - z-index: 3; - color: #0a58ca; - background-color: #e9ecef; - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); -} - -.page-item:not(:first-child) .page-link { - margin-left: -1px; -} -.page-item.active .page-link { - z-index: 3; - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} -.page-item.disabled .page-link { - color: #6c757d; - pointer-events: none; - background-color: #fff; - border-color: #dee2e6; -} - -.page-link { - padding: 0.375rem 0.75rem; -} - -.page-item:first-child .page-link { - border-top-left-radius: 0.25rem; - border-bottom-left-radius: 0.25rem; -} -.page-item:last-child .page-link { - border-top-right-radius: 0.25rem; - border-bottom-right-radius: 0.25rem; -} - -.pagination-lg .page-link { - padding: 0.75rem 1.5rem; - font-size: 1.25rem; -} -.pagination-lg .page-item:first-child .page-link { - border-top-left-radius: 0.3rem; - border-bottom-left-radius: 0.3rem; -} -.pagination-lg .page-item:last-child .page-link { - border-top-right-radius: 0.3rem; - border-bottom-right-radius: 0.3rem; -} - -.pagination-sm .page-link { - padding: 0.25rem 0.5rem; - font-size: 0.875rem; -} -.pagination-sm .page-item:first-child .page-link { - border-top-left-radius: 0.2rem; - border-bottom-left-radius: 0.2rem; -} -.pagination-sm .page-item:last-child .page-link { - border-top-right-radius: 0.2rem; - border-bottom-right-radius: 0.2rem; -} - -.badge { - display: inline-block; - padding: 0.35em 0.65em; - font-size: 0.75em; - font-weight: 700; - line-height: 1; - color: #fff; - text-align: center; - white-space: nowrap; - vertical-align: baseline; - border-radius: 0.25rem; -} -.badge:empty { - display: none; -} - -.btn .badge { - position: relative; - top: -1px; -} - -.alert { - position: relative; - padding: 1rem 1rem; - margin-bottom: 1rem; - border: 1px solid transparent; - border-radius: 0.25rem; -} - -.alert-heading { - color: inherit; -} - -.alert-link { - font-weight: 700; -} - -.alert-dismissible { - padding-right: 3rem; -} -.alert-dismissible .btn-close { - position: absolute; - top: 0; - right: 0; - z-index: 2; - padding: 1.25rem 1rem; -} - -.alert-primary { - color: #084298; - background-color: #cfe2ff; - border-color: #b6d4fe; -} -.alert-primary .alert-link { - color: #06357a; -} - -.alert-secondary { - color: #41464b; - background-color: #e2e3e5; - border-color: #d3d6d8; -} -.alert-secondary .alert-link { - color: #34383c; -} - -.alert-success { - color: #0f5132; - background-color: #d1e7dd; - border-color: #badbcc; -} -.alert-success .alert-link { - color: #0c4128; -} - -.alert-info { - color: #055160; - background-color: #cff4fc; - border-color: #b6effb; -} -.alert-info .alert-link { - color: #04414d; -} - -.alert-warning { - color: #664d03; - background-color: #fff3cd; - border-color: #ffecb5; -} -.alert-warning .alert-link { - color: #523e02; -} - -.alert-danger { - color: #842029; - background-color: #f8d7da; - border-color: #f5c2c7; -} -.alert-danger .alert-link { - color: #6a1a21; -} - -.alert-light { - color: #636464; - background-color: #fefefe; - border-color: #fdfdfe; -} -.alert-light .alert-link { - color: #4f5050; -} - -.alert-dark { - color: #141619; - background-color: #d3d3d4; - border-color: #bcbebf; -} -.alert-dark .alert-link { - color: #101214; -} - -@-webkit-keyframes progress-bar-stripes { - 0% { - background-position-x: 1rem; - } -} - -@keyframes progress-bar-stripes { - 0% { - background-position-x: 1rem; - } -} -.progress { - display: flex; - height: 1rem; - overflow: hidden; - font-size: 0.75rem; - background-color: #e9ecef; - border-radius: 0.25rem; -} - -.progress-bar { - display: flex; - flex-direction: column; - justify-content: center; - overflow: hidden; - color: #fff; - text-align: center; - white-space: nowrap; - background-color: #0d6efd; - transition: width 0.6s ease; -} -@media (prefers-reduced-motion: reduce) { - .progress-bar { - transition: none; - } -} - -.progress-bar-striped { - background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); - background-size: 1rem 1rem; -} - -.progress-bar-animated { - -webkit-animation: 1s linear infinite progress-bar-stripes; - animation: 1s linear infinite progress-bar-stripes; -} -@media (prefers-reduced-motion: reduce) { - .progress-bar-animated { - -webkit-animation: none; - animation: none; - } -} - -.list-group { - display: flex; - flex-direction: column; - padding-left: 0; - margin-bottom: 0; - border-radius: 0.25rem; -} - -.list-group-numbered { - list-style-type: none; - counter-reset: section; -} -.list-group-numbered > li::before { - content: counters(section, ".") ". "; - counter-increment: section; -} - -.list-group-item-action { - width: 100%; - color: #495057; - text-align: inherit; -} -.list-group-item-action:hover, .list-group-item-action:focus { - z-index: 1; - color: #495057; - text-decoration: none; - background-color: #f8f9fa; -} -.list-group-item-action:active { - color: #212529; - background-color: #e9ecef; -} - -.list-group-item { - position: relative; - display: block; - padding: 0.5rem 1rem; - color: #212529; - text-decoration: none; - background-color: #fff; - border: 1px solid rgba(0, 0, 0, 0.125); -} -.list-group-item:first-child { - border-top-left-radius: inherit; - border-top-right-radius: inherit; -} -.list-group-item:last-child { - border-bottom-right-radius: inherit; - border-bottom-left-radius: inherit; -} -.list-group-item.disabled, .list-group-item:disabled { - color: #6c757d; - pointer-events: none; - background-color: #fff; -} -.list-group-item.active { - z-index: 2; - color: #fff; - background-color: #0d6efd; - border-color: #0d6efd; -} -.list-group-item + .list-group-item { - border-top-width: 0; -} -.list-group-item + .list-group-item.active { - margin-top: -1px; - border-top-width: 1px; -} - -.list-group-horizontal { - flex-direction: row; -} -.list-group-horizontal > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; -} -.list-group-horizontal > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; -} -.list-group-horizontal > .list-group-item.active { - margin-top: 0; -} -.list-group-horizontal > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; -} -.list-group-horizontal > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; -} - -@media (min-width: 576px) { - .list-group-horizontal-sm { - flex-direction: row; - } - .list-group-horizontal-sm > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; - } - .list-group-horizontal-sm > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; - } - .list-group-horizontal-sm > .list-group-item.active { - margin-top: 0; - } - .list-group-horizontal-sm > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; - } - .list-group-horizontal-sm > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; - } -} -@media (min-width: 768px) { - .list-group-horizontal-md { - flex-direction: row; - } - .list-group-horizontal-md > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; - } - .list-group-horizontal-md > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; - } - .list-group-horizontal-md > .list-group-item.active { - margin-top: 0; - } - .list-group-horizontal-md > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; - } - .list-group-horizontal-md > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; - } -} -@media (min-width: 992px) { - .list-group-horizontal-lg { - flex-direction: row; - } - .list-group-horizontal-lg > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; - } - .list-group-horizontal-lg > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; - } - .list-group-horizontal-lg > .list-group-item.active { - margin-top: 0; - } - .list-group-horizontal-lg > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; - } - .list-group-horizontal-lg > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; - } -} -@media (min-width: 1200px) { - .list-group-horizontal-xl { - flex-direction: row; - } - .list-group-horizontal-xl > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; - } - .list-group-horizontal-xl > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; - } - .list-group-horizontal-xl > .list-group-item.active { - margin-top: 0; - } - .list-group-horizontal-xl > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; - } - .list-group-horizontal-xl > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; - } -} -@media (min-width: 1400px) { - .list-group-horizontal-xxl { - flex-direction: row; - } - .list-group-horizontal-xxl > .list-group-item:first-child { - border-bottom-left-radius: 0.25rem; - border-top-right-radius: 0; - } - .list-group-horizontal-xxl > .list-group-item:last-child { - border-top-right-radius: 0.25rem; - border-bottom-left-radius: 0; - } - .list-group-horizontal-xxl > .list-group-item.active { - margin-top: 0; - } - .list-group-horizontal-xxl > .list-group-item + .list-group-item { - border-top-width: 1px; - border-left-width: 0; - } - .list-group-horizontal-xxl > .list-group-item + .list-group-item.active { - margin-left: -1px; - border-left-width: 1px; - } -} -.list-group-flush { - border-radius: 0; -} -.list-group-flush > .list-group-item { - border-width: 0 0 1px; -} -.list-group-flush > .list-group-item:last-child { - border-bottom-width: 0; -} - -.list-group-item-primary { - color: #084298; - background-color: #cfe2ff; -} -.list-group-item-primary.list-group-item-action:hover, .list-group-item-primary.list-group-item-action:focus { - color: #084298; - background-color: #bacbe6; -} -.list-group-item-primary.list-group-item-action.active { - color: #fff; - background-color: #084298; - border-color: #084298; -} - -.list-group-item-secondary { - color: #41464b; - background-color: #e2e3e5; -} -.list-group-item-secondary.list-group-item-action:hover, .list-group-item-secondary.list-group-item-action:focus { - color: #41464b; - background-color: #cbccce; -} -.list-group-item-secondary.list-group-item-action.active { - color: #fff; - background-color: #41464b; - border-color: #41464b; -} - -.list-group-item-success { - color: #0f5132; - background-color: #d1e7dd; -} -.list-group-item-success.list-group-item-action:hover, .list-group-item-success.list-group-item-action:focus { - color: #0f5132; - background-color: #bcd0c7; -} -.list-group-item-success.list-group-item-action.active { - color: #fff; - background-color: #0f5132; - border-color: #0f5132; -} - -.list-group-item-info { - color: #055160; - background-color: #cff4fc; -} -.list-group-item-info.list-group-item-action:hover, .list-group-item-info.list-group-item-action:focus { - color: #055160; - background-color: #badce3; -} -.list-group-item-info.list-group-item-action.active { - color: #fff; - background-color: #055160; - border-color: #055160; -} - -.list-group-item-warning { - color: #664d03; - background-color: #fff3cd; -} -.list-group-item-warning.list-group-item-action:hover, .list-group-item-warning.list-group-item-action:focus { - color: #664d03; - background-color: #e6dbb9; -} -.list-group-item-warning.list-group-item-action.active { - color: #fff; - background-color: #664d03; - border-color: #664d03; -} - -.list-group-item-danger { - color: #842029; - background-color: #f8d7da; -} -.list-group-item-danger.list-group-item-action:hover, .list-group-item-danger.list-group-item-action:focus { - color: #842029; - background-color: #dfc2c4; -} -.list-group-item-danger.list-group-item-action.active { - color: #fff; - background-color: #842029; - border-color: #842029; -} - -.list-group-item-light { - color: #636464; - background-color: #fefefe; -} -.list-group-item-light.list-group-item-action:hover, .list-group-item-light.list-group-item-action:focus { - color: #636464; - background-color: #e5e5e5; -} -.list-group-item-light.list-group-item-action.active { - color: #fff; - background-color: #636464; - border-color: #636464; -} - -.list-group-item-dark { - color: #141619; - background-color: #d3d3d4; -} -.list-group-item-dark.list-group-item-action:hover, .list-group-item-dark.list-group-item-action:focus { - color: #141619; - background-color: #bebebf; -} -.list-group-item-dark.list-group-item-action.active { - color: #fff; - background-color: #141619; - border-color: #141619; -} - -.btn-close { - box-sizing: content-box; - width: 1em; - height: 1em; - padding: 0.25em 0.25em; - color: #000; - background: transparent url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23000'%3e%3cpath d='M.293.293a1 1 0 011.414 0L8 6.586 14.293.293a1 1 0 111.414 1.414L9.414 8l6.293 6.293a1 1 0 01-1.414 1.414L8 9.414l-6.293 6.293a1 1 0 01-1.414-1.414L6.586 8 .293 1.707a1 1 0 010-1.414z'/%3e%3c/svg%3e") center/1em auto no-repeat; - border: 0; - border-radius: 0.25rem; - opacity: 0.5; -} -.btn-close:hover { - color: #000; - text-decoration: none; - opacity: 0.75; -} -.btn-close:focus { - outline: 0; - box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25); - opacity: 1; -} -.btn-close:disabled, .btn-close.disabled { - pointer-events: none; - -webkit-user-select: none; - -moz-user-select: none; - user-select: none; - opacity: 0.25; -} - -.btn-close-white { - filter: invert(1) grayscale(100%) brightness(200%); -} - -.toast { - width: 350px; - max-width: 100%; - font-size: 0.875rem; - pointer-events: auto; - background-color: rgba(255, 255, 255, 0.85); - background-clip: padding-box; - border: 1px solid rgba(0, 0, 0, 0.1); - box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15); - border-radius: 0.25rem; -} -.toast.showing { - opacity: 0; -} -.toast:not(.show) { - display: none; -} - -.toast-container { - width: -webkit-max-content; - width: -moz-max-content; - width: max-content; - max-width: 100%; - pointer-events: none; -} -.toast-container > :not(:last-child) { - margin-bottom: 0.75rem; -} - -.toast-header { - display: flex; - align-items: center; - padding: 0.5rem 0.75rem; - color: #6c757d; - background-color: rgba(255, 255, 255, 0.85); - background-clip: padding-box; - border-bottom: 1px solid rgba(0, 0, 0, 0.05); - border-top-left-radius: calc(0.25rem - 1px); - border-top-right-radius: calc(0.25rem - 1px); -} -.toast-header .btn-close { - margin-right: -0.375rem; - margin-left: 0.75rem; -} - -.toast-body { - padding: 0.75rem; - word-wrap: break-word; -} - -.modal { - position: fixed; - top: 0; - left: 0; - z-index: 1055; - display: none; - width: 100%; - height: 100%; - overflow-x: hidden; - overflow-y: auto; - outline: 0; -} - -.modal-dialog { - position: relative; - width: auto; - margin: 0.5rem; - pointer-events: none; -} -.modal.fade .modal-dialog { - transition: transform 0.3s ease-out; - transform: translate(0, -50px); -} -@media (prefers-reduced-motion: reduce) { - .modal.fade .modal-dialog { - transition: none; - } -} -.modal.show .modal-dialog { - transform: none; -} -.modal.modal-static .modal-dialog { - transform: scale(1.02); -} - -.modal-dialog-scrollable { - height: calc(100% - 1rem); -} -.modal-dialog-scrollable .modal-content { - max-height: 100%; - overflow: hidden; -} -.modal-dialog-scrollable .modal-body { - overflow-y: auto; -} - -.modal-dialog-centered { - display: flex; - align-items: center; - min-height: calc(100% - 1rem); -} - -.modal-content { - position: relative; - display: flex; - flex-direction: column; - width: 100%; - pointer-events: auto; - background-color: #fff; - background-clip: padding-box; - border: 1px solid rgba(0, 0, 0, 0.2); - border-radius: 0.3rem; - outline: 0; -} - -.modal-backdrop { - position: fixed; - top: 0; - left: 0; - z-index: 1050; - width: 100vw; - height: 100vh; - background-color: #000; -} -.modal-backdrop.fade { - opacity: 0; -} -.modal-backdrop.show { - opacity: 0.5; -} - -.modal-header { - display: flex; - flex-shrink: 0; - align-items: center; - justify-content: space-between; - padding: 1rem 1rem; - border-bottom: 1px solid #dee2e6; - border-top-left-radius: calc(0.3rem - 1px); - border-top-right-radius: calc(0.3rem - 1px); -} -.modal-header .btn-close { - padding: 0.5rem 0.5rem; - margin: -0.5rem -0.5rem -0.5rem auto; -} - -.modal-title { - margin-bottom: 0; - line-height: 1.5; -} - -.modal-body { - position: relative; - flex: 1 1 auto; - padding: 1rem; -} - -.modal-footer { - display: flex; - flex-wrap: wrap; - flex-shrink: 0; - align-items: center; - justify-content: flex-end; - padding: 0.75rem; - border-top: 1px solid #dee2e6; - border-bottom-right-radius: calc(0.3rem - 1px); - border-bottom-left-radius: calc(0.3rem - 1px); -} -.modal-footer > * { - margin: 0.25rem; -} - -@media (min-width: 576px) { - .modal-dialog { - max-width: 500px; - margin: 1.75rem auto; - } - - .modal-dialog-scrollable { - height: calc(100% - 3.5rem); - } - - .modal-dialog-centered { - min-height: calc(100% - 3.5rem); - } - - .modal-sm { - max-width: 300px; - } -} -@media (min-width: 992px) { - .modal-lg, -.modal-xl { - max-width: 800px; - } -} -@media (min-width: 1200px) { - .modal-xl { - max-width: 1140px; - } -} -.modal-fullscreen { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; -} -.modal-fullscreen .modal-content { - height: 100%; - border: 0; - border-radius: 0; -} -.modal-fullscreen .modal-header { - border-radius: 0; -} -.modal-fullscreen .modal-body { - overflow-y: auto; -} -.modal-fullscreen .modal-footer { - border-radius: 0; -} - -@media (max-width: 575.98px) { - .modal-fullscreen-sm-down { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; - } - .modal-fullscreen-sm-down .modal-content { - height: 100%; - border: 0; - border-radius: 0; - } - .modal-fullscreen-sm-down .modal-header { - border-radius: 0; - } - .modal-fullscreen-sm-down .modal-body { - overflow-y: auto; - } - .modal-fullscreen-sm-down .modal-footer { - border-radius: 0; - } -} -@media (max-width: 767.98px) { - .modal-fullscreen-md-down { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; - } - .modal-fullscreen-md-down .modal-content { - height: 100%; - border: 0; - border-radius: 0; - } - .modal-fullscreen-md-down .modal-header { - border-radius: 0; - } - .modal-fullscreen-md-down .modal-body { - overflow-y: auto; - } - .modal-fullscreen-md-down .modal-footer { - border-radius: 0; - } -} -@media (max-width: 991.98px) { - .modal-fullscreen-lg-down { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; - } - .modal-fullscreen-lg-down .modal-content { - height: 100%; - border: 0; - border-radius: 0; - } - .modal-fullscreen-lg-down .modal-header { - border-radius: 0; - } - .modal-fullscreen-lg-down .modal-body { - overflow-y: auto; - } - .modal-fullscreen-lg-down .modal-footer { - border-radius: 0; - } -} -@media (max-width: 1199.98px) { - .modal-fullscreen-xl-down { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; - } - .modal-fullscreen-xl-down .modal-content { - height: 100%; - border: 0; - border-radius: 0; - } - .modal-fullscreen-xl-down .modal-header { - border-radius: 0; - } - .modal-fullscreen-xl-down .modal-body { - overflow-y: auto; - } - .modal-fullscreen-xl-down .modal-footer { - border-radius: 0; - } -} -@media (max-width: 1399.98px) { - .modal-fullscreen-xxl-down { - width: 100vw; - max-width: none; - height: 100%; - margin: 0; - } - .modal-fullscreen-xxl-down .modal-content { - height: 100%; - border: 0; - border-radius: 0; - } - .modal-fullscreen-xxl-down .modal-header { - border-radius: 0; - } - .modal-fullscreen-xxl-down .modal-body { - overflow-y: auto; - } - .modal-fullscreen-xxl-down .modal-footer { - border-radius: 0; - } -} -.tooltip { - position: absolute; - z-index: 1080; - display: block; - margin: 0; - font-family: var(--bs-font-sans-serif); - font-style: normal; - font-weight: 400; - line-height: 1.5; - text-align: left; - text-align: start; - text-decoration: none; - text-shadow: none; - text-transform: none; - letter-spacing: normal; - word-break: normal; - word-spacing: normal; - white-space: normal; - line-break: auto; - font-size: 0.875rem; - word-wrap: break-word; - opacity: 0; -} -.tooltip.show { - opacity: 0.9; -} -.tooltip .tooltip-arrow { - position: absolute; - display: block; - width: 0.8rem; - height: 0.4rem; -} -.tooltip .tooltip-arrow::before { - position: absolute; - content: ""; - border-color: transparent; - border-style: solid; -} - -.bs-tooltip-top, .bs-tooltip-auto[data-popper-placement^=top] { - padding: 0.4rem 0; -} -.bs-tooltip-top .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=top] .tooltip-arrow { - bottom: 0; -} -.bs-tooltip-top .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=top] .tooltip-arrow::before { - top: -1px; - border-width: 0.4rem 0.4rem 0; - border-top-color: #000; -} - -.bs-tooltip-end, .bs-tooltip-auto[data-popper-placement^=right] { - padding: 0 0.4rem; -} -.bs-tooltip-end .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=right] .tooltip-arrow { - left: 0; - width: 0.4rem; - height: 0.8rem; -} -.bs-tooltip-end .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=right] .tooltip-arrow::before { - right: -1px; - border-width: 0.4rem 0.4rem 0.4rem 0; - border-right-color: #000; -} - -.bs-tooltip-bottom, .bs-tooltip-auto[data-popper-placement^=bottom] { - padding: 0.4rem 0; -} -.bs-tooltip-bottom .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=bottom] .tooltip-arrow { - top: 0; -} -.bs-tooltip-bottom .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=bottom] .tooltip-arrow::before { - bottom: -1px; - border-width: 0 0.4rem 0.4rem; - border-bottom-color: #000; -} - -.bs-tooltip-start, .bs-tooltip-auto[data-popper-placement^=left] { - padding: 0 0.4rem; -} -.bs-tooltip-start .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=left] .tooltip-arrow { - right: 0; - width: 0.4rem; - height: 0.8rem; -} -.bs-tooltip-start .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=left] .tooltip-arrow::before { - left: -1px; - border-width: 0.4rem 0 0.4rem 0.4rem; - border-left-color: #000; -} - -.tooltip-inner { - max-width: 200px; - padding: 0.25rem 0.5rem; - color: #fff; - text-align: center; - background-color: #000; - border-radius: 0.25rem; -} - -.popover { - position: absolute; - top: 0; - left: 0 /* rtl:ignore */; - z-index: 1070; - display: block; - max-width: 276px; - font-family: var(--bs-font-sans-serif); - font-style: normal; - font-weight: 400; - line-height: 1.5; - text-align: left; - text-align: start; - text-decoration: none; - text-shadow: none; - text-transform: none; - letter-spacing: normal; - word-break: normal; - word-spacing: normal; - white-space: normal; - line-break: auto; - font-size: 0.875rem; - word-wrap: break-word; - background-color: #fff; - background-clip: padding-box; - border: 1px solid rgba(0, 0, 0, 0.2); - border-radius: 0.3rem; -} -.popover .popover-arrow { - position: absolute; - display: block; - width: 1rem; - height: 0.5rem; -} -.popover .popover-arrow::before, .popover .popover-arrow::after { - position: absolute; - display: block; - content: ""; - border-color: transparent; - border-style: solid; -} - -.bs-popover-top > .popover-arrow, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow { - bottom: calc(-0.5rem - 1px); -} -.bs-popover-top > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow::before { - bottom: 0; - border-width: 0.5rem 0.5rem 0; - border-top-color: rgba(0, 0, 0, 0.25); -} -.bs-popover-top > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow::after { - bottom: 1px; - border-width: 0.5rem 0.5rem 0; - border-top-color: #fff; -} - -.bs-popover-end > .popover-arrow, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow { - left: calc(-0.5rem - 1px); - width: 0.5rem; - height: 1rem; -} -.bs-popover-end > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow::before { - left: 0; - border-width: 0.5rem 0.5rem 0.5rem 0; - border-right-color: rgba(0, 0, 0, 0.25); -} -.bs-popover-end > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow::after { - left: 1px; - border-width: 0.5rem 0.5rem 0.5rem 0; - border-right-color: #fff; -} - -.bs-popover-bottom > .popover-arrow, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow { - top: calc(-0.5rem - 1px); -} -.bs-popover-bottom > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow::before { - top: 0; - border-width: 0 0.5rem 0.5rem 0.5rem; - border-bottom-color: rgba(0, 0, 0, 0.25); -} -.bs-popover-bottom > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow::after { - top: 1px; - border-width: 0 0.5rem 0.5rem 0.5rem; - border-bottom-color: #fff; -} -.bs-popover-bottom .popover-header::before, .bs-popover-auto[data-popper-placement^=bottom] .popover-header::before { - position: absolute; - top: 0; - left: 50%; - display: block; - width: 1rem; - margin-left: -0.5rem; - content: ""; - border-bottom: 1px solid #f0f0f0; -} - -.bs-popover-start > .popover-arrow, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow { - right: calc(-0.5rem - 1px); - width: 0.5rem; - height: 1rem; -} -.bs-popover-start > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow::before { - right: 0; - border-width: 0.5rem 0 0.5rem 0.5rem; - border-left-color: rgba(0, 0, 0, 0.25); -} -.bs-popover-start > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow::after { - right: 1px; - border-width: 0.5rem 0 0.5rem 0.5rem; - border-left-color: #fff; -} - -.popover-header { - padding: 0.5rem 1rem; - margin-bottom: 0; - font-size: 1rem; - background-color: #f0f0f0; - border-bottom: 1px solid rgba(0, 0, 0, 0.2); - border-top-left-radius: calc(0.3rem - 1px); - border-top-right-radius: calc(0.3rem - 1px); -} -.popover-header:empty { - display: none; -} - -.popover-body { - padding: 1rem 1rem; - color: #212529; -} - -.carousel { - position: relative; -} - -.carousel.pointer-event { - touch-action: pan-y; -} - -.carousel-inner { - position: relative; - width: 100%; - overflow: hidden; -} -.carousel-inner::after { - display: block; - clear: both; - content: ""; -} - -.carousel-item { - position: relative; - display: none; - float: left; - width: 100%; - margin-right: -100%; - -webkit-backface-visibility: hidden; - backface-visibility: hidden; - transition: transform 0.6s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .carousel-item { - transition: none; - } -} - -.carousel-item.active, -.carousel-item-next, -.carousel-item-prev { - display: block; -} - -/* rtl:begin:ignore */ -.carousel-item-next:not(.carousel-item-start), -.active.carousel-item-end { - transform: translateX(100%); -} - -.carousel-item-prev:not(.carousel-item-end), -.active.carousel-item-start { - transform: translateX(-100%); -} - -/* rtl:end:ignore */ -.carousel-fade .carousel-item { - opacity: 0; - transition-property: opacity; - transform: none; -} -.carousel-fade .carousel-item.active, -.carousel-fade .carousel-item-next.carousel-item-start, -.carousel-fade .carousel-item-prev.carousel-item-end { - z-index: 1; - opacity: 1; -} -.carousel-fade .active.carousel-item-start, -.carousel-fade .active.carousel-item-end { - z-index: 0; - opacity: 0; - transition: opacity 0s 0.6s; -} -@media (prefers-reduced-motion: reduce) { - .carousel-fade .active.carousel-item-start, -.carousel-fade .active.carousel-item-end { - transition: none; - } -} - -.carousel-control-prev, -.carousel-control-next { - position: absolute; - top: 0; - bottom: 0; - z-index: 1; - display: flex; - align-items: center; - justify-content: center; - width: 15%; - padding: 0; - color: #fff; - text-align: center; - background: none; - border: 0; - opacity: 0.5; - transition: opacity 0.15s ease; -} -@media (prefers-reduced-motion: reduce) { - .carousel-control-prev, -.carousel-control-next { - transition: none; - } -} -.carousel-control-prev:hover, .carousel-control-prev:focus, -.carousel-control-next:hover, -.carousel-control-next:focus { - color: #fff; - text-decoration: none; - outline: 0; - opacity: 0.9; -} - -.carousel-control-prev { - left: 0; -} - -.carousel-control-next { - right: 0; -} - -.carousel-control-prev-icon, -.carousel-control-next-icon { - display: inline-block; - width: 2rem; - height: 2rem; - background-repeat: no-repeat; - background-position: 50%; - background-size: 100% 100%; -} - -/* rtl:options: { - "autoRename": true, - "stringMap":[ { - "name" : "prev-next", - "search" : "prev", - "replace" : "next" - } ] -} */ -.carousel-control-prev-icon { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23fff'%3e%3cpath d='M11.354 1.646a.5.5 0 0 1 0 .708L5.707 8l5.647 5.646a.5.5 0 0 1-.708.708l-6-6a.5.5 0 0 1 0-.708l6-6a.5.5 0 0 1 .708 0z'/%3e%3c/svg%3e"); -} - -.carousel-control-next-icon { - background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23fff'%3e%3cpath d='M4.646 1.646a.5.5 0 0 1 .708 0l6 6a.5.5 0 0 1 0 .708l-6 6a.5.5 0 0 1-.708-.708L10.293 8 4.646 2.354a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e"); -} - -.carousel-indicators { - position: absolute; - right: 0; - bottom: 0; - left: 0; - z-index: 2; - display: flex; - justify-content: center; - padding: 0; - margin-right: 15%; - margin-bottom: 1rem; - margin-left: 15%; - list-style: none; -} -.carousel-indicators [data-bs-target] { - box-sizing: content-box; - flex: 0 1 auto; - width: 30px; - height: 3px; - padding: 0; - margin-right: 3px; - margin-left: 3px; - text-indent: -999px; - cursor: pointer; - background-color: #fff; - background-clip: padding-box; - border: 0; - border-top: 10px solid transparent; - border-bottom: 10px solid transparent; - opacity: 0.5; - transition: opacity 0.6s ease; -} -@media (prefers-reduced-motion: reduce) { - .carousel-indicators [data-bs-target] { - transition: none; - } -} -.carousel-indicators .active { - opacity: 1; -} - -.carousel-caption { - position: absolute; - right: 15%; - bottom: 1.25rem; - left: 15%; - padding-top: 1.25rem; - padding-bottom: 1.25rem; - color: #fff; - text-align: center; -} - -.carousel-dark .carousel-control-prev-icon, -.carousel-dark .carousel-control-next-icon { - filter: invert(1) grayscale(100); -} -.carousel-dark .carousel-indicators [data-bs-target] { - background-color: #000; -} -.carousel-dark .carousel-caption { - color: #000; -} - -@-webkit-keyframes spinner-border { - to { - transform: rotate(360deg) /* rtl:ignore */; - } -} - -@keyframes spinner-border { - to { - transform: rotate(360deg) /* rtl:ignore */; - } -} -.spinner-border { - display: inline-block; - width: 2rem; - height: 2rem; - vertical-align: -0.125em; - border: 0.25em solid currentColor; - border-right-color: transparent; - border-radius: 50%; - -webkit-animation: 0.75s linear infinite spinner-border; - animation: 0.75s linear infinite spinner-border; -} - -.spinner-border-sm { - width: 1rem; - height: 1rem; - border-width: 0.2em; -} - -@-webkit-keyframes spinner-grow { - 0% { - transform: scale(0); - } - 50% { - opacity: 1; - transform: none; - } -} - -@keyframes spinner-grow { - 0% { - transform: scale(0); - } - 50% { - opacity: 1; - transform: none; - } -} -.spinner-grow { - display: inline-block; - width: 2rem; - height: 2rem; - vertical-align: -0.125em; - background-color: currentColor; - border-radius: 50%; - opacity: 0; - -webkit-animation: 0.75s linear infinite spinner-grow; - animation: 0.75s linear infinite spinner-grow; -} - -.spinner-grow-sm { - width: 1rem; - height: 1rem; -} - -@media (prefers-reduced-motion: reduce) { - .spinner-border, -.spinner-grow { - -webkit-animation-duration: 1.5s; - animation-duration: 1.5s; - } -} -.offcanvas { - position: fixed; - bottom: 0; - z-index: 1045; - display: flex; - flex-direction: column; - max-width: 100%; - visibility: hidden; - background-color: #fff; - background-clip: padding-box; - outline: 0; - transition: transform 0.3s ease-in-out; -} -@media (prefers-reduced-motion: reduce) { - .offcanvas { - transition: none; - } -} - -.offcanvas-backdrop { - position: fixed; - top: 0; - left: 0; - z-index: 1040; - width: 100vw; - height: 100vh; - background-color: #000; -} -.offcanvas-backdrop.fade { - opacity: 0; -} -.offcanvas-backdrop.show { - opacity: 0.5; -} - -.offcanvas-header { - display: flex; - align-items: center; - justify-content: space-between; - padding: 1rem 1rem; -} -.offcanvas-header .btn-close { - padding: 0.5rem 0.5rem; - margin-top: -0.5rem; - margin-right: -0.5rem; - margin-bottom: -0.5rem; -} - -.offcanvas-title { - margin-bottom: 0; - line-height: 1.5; -} - -.offcanvas-body { - flex-grow: 1; - padding: 1rem 1rem; - overflow-y: auto; -} - -.offcanvas-start { - top: 0; - left: 0; - width: 400px; - border-right: 1px solid rgba(0, 0, 0, 0.2); - transform: translateX(-100%); -} - -.offcanvas-end { - top: 0; - right: 0; - width: 400px; - border-left: 1px solid rgba(0, 0, 0, 0.2); - transform: translateX(100%); -} - -.offcanvas-top { - top: 0; - right: 0; - left: 0; - height: 30vh; - max-height: 100%; - border-bottom: 1px solid rgba(0, 0, 0, 0.2); - transform: translateY(-100%); -} - -.offcanvas-bottom { - right: 0; - left: 0; - height: 30vh; - max-height: 100%; - border-top: 1px solid rgba(0, 0, 0, 0.2); - transform: translateY(100%); -} - -.offcanvas.show { - transform: none; -} - -.placeholder { - display: inline-block; - min-height: 1em; - vertical-align: middle; - cursor: wait; - background-color: currentColor; - opacity: 0.5; -} -.placeholder.btn::before { - display: inline-block; - content: ""; -} - -.placeholder-xs { - min-height: 0.6em; -} - -.placeholder-sm { - min-height: 0.8em; -} - -.placeholder-lg { - min-height: 1.2em; -} - -.placeholder-glow .placeholder { - -webkit-animation: placeholder-glow 2s ease-in-out infinite; - animation: placeholder-glow 2s ease-in-out infinite; -} - -@-webkit-keyframes placeholder-glow { - 50% { - opacity: 0.2; - } -} - -@keyframes placeholder-glow { - 50% { - opacity: 0.2; - } -} -.placeholder-wave { - -webkit-mask-image: linear-gradient(130deg, #000 55%, rgba(0, 0, 0, 0.8) 75%, #000 95%); - mask-image: linear-gradient(130deg, #000 55%, rgba(0, 0, 0, 0.8) 75%, #000 95%); - -webkit-mask-size: 200% 100%; - mask-size: 200% 100%; - -webkit-animation: placeholder-wave 2s linear infinite; - animation: placeholder-wave 2s linear infinite; -} - -@-webkit-keyframes placeholder-wave { - 100% { - -webkit-mask-position: -200% 0%; - mask-position: -200% 0%; - } -} - -@keyframes placeholder-wave { - 100% { - -webkit-mask-position: -200% 0%; - mask-position: -200% 0%; - } -} -.clearfix::after { - display: block; - clear: both; - content: ""; -} - -.link-primary { - color: #0d6efd; -} -.link-primary:hover, .link-primary:focus { - color: #0a58ca; -} - -.link-secondary { - color: #6c757d; -} -.link-secondary:hover, .link-secondary:focus { - color: #565e64; -} - -.link-success { - color: #198754; -} -.link-success:hover, .link-success:focus { - color: #146c43; -} - -.link-info { - color: #0dcaf0; -} -.link-info:hover, .link-info:focus { - color: #3dd5f3; -} - -.link-warning { - color: #ffc107; -} -.link-warning:hover, .link-warning:focus { - color: #ffcd39; -} - -.link-danger { - color: #dc3545; -} -.link-danger:hover, .link-danger:focus { - color: #b02a37; -} - -.link-light { - color: #f8f9fa; -} -.link-light:hover, .link-light:focus { - color: #f9fafb; -} - -.link-dark { - color: #212529; -} -.link-dark:hover, .link-dark:focus { - color: #1a1e21; -} - -.ratio { - position: relative; - width: 100%; -} -.ratio::before { - display: block; - padding-top: var(--bs-aspect-ratio); - content: ""; -} -.ratio > * { - position: absolute; - top: 0; - left: 0; - width: 100%; - height: 100%; -} - -.ratio-1x1 { - --bs-aspect-ratio: 100%; -} - -.ratio-4x3 { - --bs-aspect-ratio: 75%; -} - -.ratio-16x9 { - --bs-aspect-ratio: 56.25%; -} - -.ratio-21x9 { - --bs-aspect-ratio: 42.8571428571%; -} - -.fixed-top { - position: fixed; - top: 0; - right: 0; - left: 0; - z-index: 1030; -} - -.fixed-bottom { - position: fixed; - right: 0; - bottom: 0; - left: 0; - z-index: 1030; -} - -.sticky-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; -} - -@media (min-width: 576px) { - .sticky-sm-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; - } -} -@media (min-width: 768px) { - .sticky-md-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; - } -} -@media (min-width: 992px) { - .sticky-lg-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; - } -} -@media (min-width: 1200px) { - .sticky-xl-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; - } -} -@media (min-width: 1400px) { - .sticky-xxl-top { - position: -webkit-sticky; - position: sticky; - top: 0; - z-index: 1020; - } -} -.hstack { - display: flex; - flex-direction: row; - align-items: center; - align-self: stretch; -} - -.vstack { - display: flex; - flex: 1 1 auto; - flex-direction: column; - align-self: stretch; -} - -.visually-hidden, -.visually-hidden-focusable:not(:focus):not(:focus-within) { - position: absolute !important; - width: 1px !important; - height: 1px !important; - padding: 0 !important; - margin: -1px !important; - overflow: hidden !important; - clip: rect(0, 0, 0, 0) !important; - white-space: nowrap !important; - border: 0 !important; -} - -.stretched-link::after { - position: absolute; - top: 0; - right: 0; - bottom: 0; - left: 0; - z-index: 1; - content: ""; -} - -.text-truncate { - overflow: hidden; - text-overflow: ellipsis; - white-space: nowrap; -} - -.vr { - display: inline-block; - align-self: stretch; - width: 1px; - min-height: 1em; - background-color: currentColor; - opacity: 0.25; -} - -.align-baseline { - vertical-align: baseline !important; -} - -.align-top { - vertical-align: top !important; -} - -.align-middle { - vertical-align: middle !important; -} - -.align-bottom { - vertical-align: bottom !important; -} - -.align-text-bottom { - vertical-align: text-bottom !important; -} - -.align-text-top { - vertical-align: text-top !important; -} - -.float-start { - float: left !important; -} - -.float-end { - float: right !important; -} - -.float-none { - float: none !important; -} - -.opacity-0 { - opacity: 0 !important; -} - -.opacity-25 { - opacity: 0.25 !important; -} - -.opacity-50 { - opacity: 0.5 !important; -} - -.opacity-75 { - opacity: 0.75 !important; -} - -.opacity-100 { - opacity: 1 !important; -} - -.overflow-auto { - overflow: auto !important; -} - -.overflow-hidden { - overflow: hidden !important; -} - -.overflow-visible { - overflow: visible !important; -} - -.overflow-scroll { - overflow: scroll !important; -} - -.d-inline { - display: inline !important; -} - -.d-inline-block { - display: inline-block !important; -} - -.d-block { - display: block !important; -} - -.d-grid { - display: grid !important; -} - -.d-table { - display: table !important; -} - -.d-table-row { - display: table-row !important; -} - -.d-table-cell { - display: table-cell !important; -} - -.d-flex { - display: flex !important; -} - -.d-inline-flex { - display: inline-flex !important; -} - -.d-none { - display: none !important; -} - -.shadow { - box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15) !important; -} - -.shadow-sm { - box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075) !important; -} - -.shadow-lg { - box-shadow: 0 1rem 3rem rgba(0, 0, 0, 0.175) !important; -} - -.shadow-none { - box-shadow: none !important; -} - -.position-static { - position: static !important; -} - -.position-relative { - position: relative !important; -} - -.position-absolute { - position: absolute !important; -} - -.position-fixed { - position: fixed !important; -} - -.position-sticky { - position: -webkit-sticky !important; - position: sticky !important; -} - -.top-0 { - top: 0 !important; -} - -.top-50 { - top: 50% !important; -} - -.top-100 { - top: 100% !important; -} - -.bottom-0 { - bottom: 0 !important; -} - -.bottom-50 { - bottom: 50% !important; -} - -.bottom-100 { - bottom: 100% !important; -} - -.start-0 { - left: 0 !important; -} - -.start-50 { - left: 50% !important; -} - -.start-100 { - left: 100% !important; -} - -.end-0 { - right: 0 !important; -} - -.end-50 { - right: 50% !important; -} - -.end-100 { - right: 100% !important; -} - -.translate-middle { - transform: translate(-50%, -50%) !important; -} - -.translate-middle-x { - transform: translateX(-50%) !important; -} - -.translate-middle-y { - transform: translateY(-50%) !important; -} - -.border { - border: 1px solid #dee2e6 !important; -} - -.border-0 { - border: 0 !important; -} - -.border-top { - border-top: 1px solid #dee2e6 !important; -} - -.border-top-0 { - border-top: 0 !important; -} - -.border-end { - border-right: 1px solid #dee2e6 !important; -} - -.border-end-0 { - border-right: 0 !important; -} - -.border-bottom { - border-bottom: 1px solid #dee2e6 !important; -} - -.border-bottom-0 { - border-bottom: 0 !important; -} - -.border-start { - border-left: 1px solid #dee2e6 !important; -} - -.border-start-0 { - border-left: 0 !important; -} - -.border-primary { - border-color: #0d6efd !important; -} - -.border-secondary { - border-color: #6c757d !important; -} - -.border-success { - border-color: #198754 !important; -} - -.border-info { - border-color: #0dcaf0 !important; -} - -.border-warning { - border-color: #ffc107 !important; -} - -.border-danger { - border-color: #dc3545 !important; -} - -.border-light { - border-color: #f8f9fa !important; -} - -.border-dark { - border-color: #212529 !important; -} - -.border-white { - border-color: #fff !important; -} - -.border-1 { - border-width: 1px !important; -} - -.border-2 { - border-width: 2px !important; -} - -.border-3 { - border-width: 3px !important; -} - -.border-4 { - border-width: 4px !important; -} - -.border-5 { - border-width: 5px !important; -} - -.w-25 { - width: 25% !important; -} - -.w-50 { - width: 50% !important; -} - -.w-75 { - width: 75% !important; -} - -.w-100 { - width: 100% !important; -} - -.w-auto { - width: auto !important; -} - -.mw-100 { - max-width: 100% !important; -} - -.vw-100 { - width: 100vw !important; -} - -.min-vw-100 { - min-width: 100vw !important; -} - -.h-25 { - height: 25% !important; -} - -.h-50 { - height: 50% !important; -} - -.h-75 { - height: 75% !important; -} - -.h-100 { - height: 100% !important; -} - -.h-auto { - height: auto !important; -} - -.mh-100 { - max-height: 100% !important; -} - -.vh-100 { - height: 100vh !important; -} - -.min-vh-100 { - min-height: 100vh !important; -} - -.flex-fill { - flex: 1 1 auto !important; -} - -.flex-row { - flex-direction: row !important; -} - -.flex-column { - flex-direction: column !important; -} - -.flex-row-reverse { - flex-direction: row-reverse !important; -} - -.flex-column-reverse { - flex-direction: column-reverse !important; -} - -.flex-grow-0 { - flex-grow: 0 !important; -} - -.flex-grow-1 { - flex-grow: 1 !important; -} - -.flex-shrink-0 { - flex-shrink: 0 !important; -} - -.flex-shrink-1 { - flex-shrink: 1 !important; -} - -.flex-wrap { - flex-wrap: wrap !important; -} - -.flex-nowrap { - flex-wrap: nowrap !important; -} - -.flex-wrap-reverse { - flex-wrap: wrap-reverse !important; -} - -.gap-0 { - gap: 0 !important; -} - -.gap-1 { - gap: 0.25rem !important; -} - -.gap-2 { - gap: 0.5rem !important; -} - -.gap-3 { - gap: 1rem !important; -} - -.gap-4 { - gap: 1.5rem !important; -} - -.gap-5 { - gap: 3rem !important; -} - -.justify-content-start { - justify-content: flex-start !important; -} - -.justify-content-end { - justify-content: flex-end !important; -} - -.justify-content-center { - justify-content: center !important; -} - -.justify-content-between { - justify-content: space-between !important; -} - -.justify-content-around { - justify-content: space-around !important; -} - -.justify-content-evenly { - justify-content: space-evenly !important; -} - -.align-items-start { - align-items: flex-start !important; -} - -.align-items-end { - align-items: flex-end !important; -} - -.align-items-center { - align-items: center !important; -} - -.align-items-baseline { - align-items: baseline !important; -} - -.align-items-stretch { - align-items: stretch !important; -} - -.align-content-start { - align-content: flex-start !important; -} - -.align-content-end { - align-content: flex-end !important; -} - -.align-content-center { - align-content: center !important; -} - -.align-content-between { - align-content: space-between !important; -} - -.align-content-around { - align-content: space-around !important; -} - -.align-content-stretch { - align-content: stretch !important; -} - -.align-self-auto { - align-self: auto !important; -} - -.align-self-start { - align-self: flex-start !important; -} - -.align-self-end { - align-self: flex-end !important; -} - -.align-self-center { - align-self: center !important; -} - -.align-self-baseline { - align-self: baseline !important; -} - -.align-self-stretch { - align-self: stretch !important; -} - -.order-first { - order: -1 !important; -} - -.order-0 { - order: 0 !important; -} - -.order-1 { - order: 1 !important; -} - -.order-2 { - order: 2 !important; -} - -.order-3 { - order: 3 !important; -} - -.order-4 { - order: 4 !important; -} - -.order-5 { - order: 5 !important; -} - -.order-last { - order: 6 !important; -} - -.m-0 { - margin: 0 !important; -} - -.m-1 { - margin: 0.25rem !important; -} - -.m-2 { - margin: 0.5rem !important; -} - -.m-3 { - margin: 1rem !important; -} - -.m-4 { - margin: 1.5rem !important; -} - -.m-5 { - margin: 3rem !important; -} - -.m-auto { - margin: auto !important; -} - -.mx-0 { - margin-right: 0 !important; - margin-left: 0 !important; -} - -.mx-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; -} - -.mx-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; -} - -.mx-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; -} - -.mx-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; -} - -.mx-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; -} - -.mx-auto { - margin-right: auto !important; - margin-left: auto !important; -} - -.my-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; -} - -.my-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; -} - -.my-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; -} - -.my-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; -} - -.my-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; -} - -.my-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; -} - -.my-auto { - margin-top: auto !important; - margin-bottom: auto !important; -} - -.mt-0 { - margin-top: 0 !important; -} - -.mt-1 { - margin-top: 0.25rem !important; -} - -.mt-2 { - margin-top: 0.5rem !important; -} - -.mt-3 { - margin-top: 1rem !important; -} - -.mt-4 { - margin-top: 1.5rem !important; -} - -.mt-5 { - margin-top: 3rem !important; -} - -.mt-auto { - margin-top: auto !important; -} - -.me-0 { - margin-right: 0 !important; -} - -.me-1 { - margin-right: 0.25rem !important; -} - -.me-2 { - margin-right: 0.5rem !important; -} - -.me-3 { - margin-right: 1rem !important; -} - -.me-4 { - margin-right: 1.5rem !important; -} - -.me-5 { - margin-right: 3rem !important; -} - -.me-auto { - margin-right: auto !important; -} - -.mb-0 { - margin-bottom: 0 !important; -} - -.mb-1 { - margin-bottom: 0.25rem !important; -} - -.mb-2 { - margin-bottom: 0.5rem !important; -} - -.mb-3 { - margin-bottom: 1rem !important; -} - -.mb-4 { - margin-bottom: 1.5rem !important; -} - -.mb-5 { - margin-bottom: 3rem !important; -} - -.mb-auto { - margin-bottom: auto !important; -} - -.ms-0 { - margin-left: 0 !important; -} - -.ms-1 { - margin-left: 0.25rem !important; -} - -.ms-2 { - margin-left: 0.5rem !important; -} - -.ms-3 { - margin-left: 1rem !important; -} - -.ms-4 { - margin-left: 1.5rem !important; -} - -.ms-5 { - margin-left: 3rem !important; -} - -.ms-auto { - margin-left: auto !important; -} - -.p-0 { - padding: 0 !important; -} - -.p-1 { - padding: 0.25rem !important; -} - -.p-2 { - padding: 0.5rem !important; -} - -.p-3 { - padding: 1rem !important; -} - -.p-4 { - padding: 1.5rem !important; -} - -.p-5 { - padding: 3rem !important; -} - -.px-0 { - padding-right: 0 !important; - padding-left: 0 !important; -} - -.px-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; -} - -.px-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; -} - -.px-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; -} - -.px-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; -} - -.px-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; -} - -.py-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; -} - -.py-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; -} - -.py-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; -} - -.py-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; -} - -.py-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; -} - -.py-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; -} - -.pt-0 { - padding-top: 0 !important; -} - -.pt-1 { - padding-top: 0.25rem !important; -} - -.pt-2 { - padding-top: 0.5rem !important; -} - -.pt-3 { - padding-top: 1rem !important; -} - -.pt-4 { - padding-top: 1.5rem !important; -} - -.pt-5 { - padding-top: 3rem !important; -} - -.pe-0 { - padding-right: 0 !important; -} - -.pe-1 { - padding-right: 0.25rem !important; -} - -.pe-2 { - padding-right: 0.5rem !important; -} - -.pe-3 { - padding-right: 1rem !important; -} - -.pe-4 { - padding-right: 1.5rem !important; -} - -.pe-5 { - padding-right: 3rem !important; -} - -.pb-0 { - padding-bottom: 0 !important; -} - -.pb-1 { - padding-bottom: 0.25rem !important; -} - -.pb-2 { - padding-bottom: 0.5rem !important; -} - -.pb-3 { - padding-bottom: 1rem !important; -} - -.pb-4 { - padding-bottom: 1.5rem !important; -} - -.pb-5 { - padding-bottom: 3rem !important; -} - -.ps-0 { - padding-left: 0 !important; -} - -.ps-1 { - padding-left: 0.25rem !important; -} - -.ps-2 { - padding-left: 0.5rem !important; -} - -.ps-3 { - padding-left: 1rem !important; -} - -.ps-4 { - padding-left: 1.5rem !important; -} - -.ps-5 { - padding-left: 3rem !important; -} - -.font-monospace { - font-family: var(--bs-font-monospace) !important; -} - -.fs-1 { - font-size: calc(1.375rem + 1.5vw) !important; -} - -.fs-2 { - font-size: calc(1.325rem + 0.9vw) !important; -} - -.fs-3 { - font-size: calc(1.3rem + 0.6vw) !important; -} - -.fs-4 { - font-size: calc(1.275rem + 0.3vw) !important; -} - -.fs-5 { - font-size: 1.25rem !important; -} - -.fs-6 { - font-size: 1rem !important; -} - -.fst-italic { - font-style: italic !important; -} - -.fst-normal { - font-style: normal !important; -} - -.fw-light { - font-weight: 300 !important; -} - -.fw-lighter { - font-weight: lighter !important; -} - -.fw-normal { - font-weight: 400 !important; -} - -.fw-bold { - font-weight: 700 !important; -} - -.fw-bolder { - font-weight: bolder !important; -} - -.lh-1 { - line-height: 1 !important; -} - -.lh-sm { - line-height: 1.25 !important; -} - -.lh-base { - line-height: 1.5 !important; -} - -.lh-lg { - line-height: 2 !important; -} - -.text-start { - text-align: left !important; -} - -.text-end { - text-align: right !important; -} - -.text-center { - text-align: center !important; -} - -.text-decoration-none { - text-decoration: none !important; -} - -.text-decoration-underline { - text-decoration: underline !important; -} - -.text-decoration-line-through { - text-decoration: line-through !important; -} - -.text-lowercase { - text-transform: lowercase !important; -} - -.text-uppercase { - text-transform: uppercase !important; -} - -.text-capitalize { - text-transform: capitalize !important; -} - -.text-wrap { - white-space: normal !important; -} - -.text-nowrap { - white-space: nowrap !important; -} - -/* rtl:begin:remove */ -.text-break { - word-wrap: break-word !important; - word-break: break-word !important; -} - -/* rtl:end:remove */ -.text-primary { - --bs-text-opacity: 1; - color: rgba(var(--bs-primary-rgb), var(--bs-text-opacity)) !important; -} - -.text-secondary { - --bs-text-opacity: 1; - color: rgba(var(--bs-secondary-rgb), var(--bs-text-opacity)) !important; -} - -.text-success { - --bs-text-opacity: 1; - color: rgba(var(--bs-success-rgb), var(--bs-text-opacity)) !important; -} - -.text-info { - --bs-text-opacity: 1; - color: rgba(var(--bs-info-rgb), var(--bs-text-opacity)) !important; -} - -.text-warning { - --bs-text-opacity: 1; - color: rgba(var(--bs-warning-rgb), var(--bs-text-opacity)) !important; -} - -.text-danger { - --bs-text-opacity: 1; - color: rgba(var(--bs-danger-rgb), var(--bs-text-opacity)) !important; -} - -.text-light { - --bs-text-opacity: 1; - color: rgba(var(--bs-light-rgb), var(--bs-text-opacity)) !important; -} - -.text-dark { - --bs-text-opacity: 1; - color: rgba(var(--bs-dark-rgb), var(--bs-text-opacity)) !important; -} - -.text-black { - --bs-text-opacity: 1; - color: rgba(var(--bs-black-rgb), var(--bs-text-opacity)) !important; -} - -.text-white { - --bs-text-opacity: 1; - color: rgba(var(--bs-white-rgb), var(--bs-text-opacity)) !important; -} - -.text-body { - --bs-text-opacity: 1; - color: rgba(var(--bs-body-color-rgb), var(--bs-text-opacity)) !important; -} - -.text-muted { - --bs-text-opacity: 1; - color: #6c757d !important; -} - -.text-black-50 { - --bs-text-opacity: 1; - color: rgba(0, 0, 0, 0.5) !important; -} - -.text-white-50 { - --bs-text-opacity: 1; - color: rgba(255, 255, 255, 0.5) !important; -} - -.text-reset { - --bs-text-opacity: 1; - color: inherit !important; -} - -.text-opacity-25 { - --bs-text-opacity: 0.25; -} - -.text-opacity-50 { - --bs-text-opacity: 0.5; -} - -.text-opacity-75 { - --bs-text-opacity: 0.75; -} - -.text-opacity-100 { - --bs-text-opacity: 1; -} - -.bg-primary { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-primary-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-secondary { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-secondary-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-success { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-success-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-info { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-info-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-warning { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-warning-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-danger { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-danger-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-light { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-light-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-dark { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-dark-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-black { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-black-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-white { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-white-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-body { - --bs-bg-opacity: 1; - background-color: rgba(var(--bs-body-bg-rgb), var(--bs-bg-opacity)) !important; -} - -.bg-transparent { - --bs-bg-opacity: 1; - background-color: transparent !important; -} - -.bg-opacity-10 { - --bs-bg-opacity: 0.1; -} - -.bg-opacity-25 { - --bs-bg-opacity: 0.25; -} - -.bg-opacity-50 { - --bs-bg-opacity: 0.5; -} - -.bg-opacity-75 { - --bs-bg-opacity: 0.75; -} - -.bg-opacity-100 { - --bs-bg-opacity: 1; -} - -.bg-gradient { - background-image: var(--bs-gradient) !important; -} - -.user-select-all { - -webkit-user-select: all !important; - -moz-user-select: all !important; - user-select: all !important; -} - -.user-select-auto { - -webkit-user-select: auto !important; - -moz-user-select: auto !important; - user-select: auto !important; -} - -.user-select-none { - -webkit-user-select: none !important; - -moz-user-select: none !important; - user-select: none !important; -} - -.pe-none { - pointer-events: none !important; -} - -.pe-auto { - pointer-events: auto !important; -} - -.rounded { - border-radius: 0.25rem !important; -} - -.rounded-0 { - border-radius: 0 !important; -} - -.rounded-1 { - border-radius: 0.2rem !important; -} - -.rounded-2 { - border-radius: 0.25rem !important; -} - -.rounded-3 { - border-radius: 0.3rem !important; -} - -.rounded-circle { - border-radius: 50% !important; -} - -.rounded-pill { - border-radius: 50rem !important; -} - -.rounded-top { - border-top-left-radius: 0.25rem !important; - border-top-right-radius: 0.25rem !important; -} - -.rounded-end { - border-top-right-radius: 0.25rem !important; - border-bottom-right-radius: 0.25rem !important; -} - -.rounded-bottom { - border-bottom-right-radius: 0.25rem !important; - border-bottom-left-radius: 0.25rem !important; -} - -.rounded-start { - border-bottom-left-radius: 0.25rem !important; - border-top-left-radius: 0.25rem !important; -} - -.visible { - visibility: visible !important; -} - -.invisible { - visibility: hidden !important; -} - -@media (min-width: 576px) { - .float-sm-start { - float: left !important; - } - - .float-sm-end { - float: right !important; - } - - .float-sm-none { - float: none !important; - } - - .d-sm-inline { - display: inline !important; - } - - .d-sm-inline-block { - display: inline-block !important; - } - - .d-sm-block { - display: block !important; - } - - .d-sm-grid { - display: grid !important; - } - - .d-sm-table { - display: table !important; - } - - .d-sm-table-row { - display: table-row !important; - } - - .d-sm-table-cell { - display: table-cell !important; - } - - .d-sm-flex { - display: flex !important; - } - - .d-sm-inline-flex { - display: inline-flex !important; - } - - .d-sm-none { - display: none !important; - } - - .flex-sm-fill { - flex: 1 1 auto !important; - } - - .flex-sm-row { - flex-direction: row !important; - } - - .flex-sm-column { - flex-direction: column !important; - } - - .flex-sm-row-reverse { - flex-direction: row-reverse !important; - } - - .flex-sm-column-reverse { - flex-direction: column-reverse !important; - } - - .flex-sm-grow-0 { - flex-grow: 0 !important; - } - - .flex-sm-grow-1 { - flex-grow: 1 !important; - } - - .flex-sm-shrink-0 { - flex-shrink: 0 !important; - } - - .flex-sm-shrink-1 { - flex-shrink: 1 !important; - } - - .flex-sm-wrap { - flex-wrap: wrap !important; - } - - .flex-sm-nowrap { - flex-wrap: nowrap !important; - } - - .flex-sm-wrap-reverse { - flex-wrap: wrap-reverse !important; - } - - .gap-sm-0 { - gap: 0 !important; - } - - .gap-sm-1 { - gap: 0.25rem !important; - } - - .gap-sm-2 { - gap: 0.5rem !important; - } - - .gap-sm-3 { - gap: 1rem !important; - } - - .gap-sm-4 { - gap: 1.5rem !important; - } - - .gap-sm-5 { - gap: 3rem !important; - } - - .justify-content-sm-start { - justify-content: flex-start !important; - } - - .justify-content-sm-end { - justify-content: flex-end !important; - } - - .justify-content-sm-center { - justify-content: center !important; - } - - .justify-content-sm-between { - justify-content: space-between !important; - } - - .justify-content-sm-around { - justify-content: space-around !important; - } - - .justify-content-sm-evenly { - justify-content: space-evenly !important; - } - - .align-items-sm-start { - align-items: flex-start !important; - } - - .align-items-sm-end { - align-items: flex-end !important; - } - - .align-items-sm-center { - align-items: center !important; - } - - .align-items-sm-baseline { - align-items: baseline !important; - } - - .align-items-sm-stretch { - align-items: stretch !important; - } - - .align-content-sm-start { - align-content: flex-start !important; - } - - .align-content-sm-end { - align-content: flex-end !important; - } - - .align-content-sm-center { - align-content: center !important; - } - - .align-content-sm-between { - align-content: space-between !important; - } - - .align-content-sm-around { - align-content: space-around !important; - } - - .align-content-sm-stretch { - align-content: stretch !important; - } - - .align-self-sm-auto { - align-self: auto !important; - } - - .align-self-sm-start { - align-self: flex-start !important; - } - - .align-self-sm-end { - align-self: flex-end !important; - } - - .align-self-sm-center { - align-self: center !important; - } - - .align-self-sm-baseline { - align-self: baseline !important; - } - - .align-self-sm-stretch { - align-self: stretch !important; - } - - .order-sm-first { - order: -1 !important; - } - - .order-sm-0 { - order: 0 !important; - } - - .order-sm-1 { - order: 1 !important; - } - - .order-sm-2 { - order: 2 !important; - } - - .order-sm-3 { - order: 3 !important; - } - - .order-sm-4 { - order: 4 !important; - } - - .order-sm-5 { - order: 5 !important; - } - - .order-sm-last { - order: 6 !important; - } - - .m-sm-0 { - margin: 0 !important; - } - - .m-sm-1 { - margin: 0.25rem !important; - } - - .m-sm-2 { - margin: 0.5rem !important; - } - - .m-sm-3 { - margin: 1rem !important; - } - - .m-sm-4 { - margin: 1.5rem !important; - } - - .m-sm-5 { - margin: 3rem !important; - } - - .m-sm-auto { - margin: auto !important; - } - - .mx-sm-0 { - margin-right: 0 !important; - margin-left: 0 !important; - } - - .mx-sm-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; - } - - .mx-sm-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - } - - .mx-sm-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; - } - - .mx-sm-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; - } - - .mx-sm-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; - } - - .mx-sm-auto { - margin-right: auto !important; - margin-left: auto !important; - } - - .my-sm-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; - } - - .my-sm-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; - } - - .my-sm-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; - } - - .my-sm-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; - } - - .my-sm-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; - } - - .my-sm-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; - } - - .my-sm-auto { - margin-top: auto !important; - margin-bottom: auto !important; - } - - .mt-sm-0 { - margin-top: 0 !important; - } - - .mt-sm-1 { - margin-top: 0.25rem !important; - } - - .mt-sm-2 { - margin-top: 0.5rem !important; - } - - .mt-sm-3 { - margin-top: 1rem !important; - } - - .mt-sm-4 { - margin-top: 1.5rem !important; - } - - .mt-sm-5 { - margin-top: 3rem !important; - } - - .mt-sm-auto { - margin-top: auto !important; - } - - .me-sm-0 { - margin-right: 0 !important; - } - - .me-sm-1 { - margin-right: 0.25rem !important; - } - - .me-sm-2 { - margin-right: 0.5rem !important; - } - - .me-sm-3 { - margin-right: 1rem !important; - } - - .me-sm-4 { - margin-right: 1.5rem !important; - } - - .me-sm-5 { - margin-right: 3rem !important; - } - - .me-sm-auto { - margin-right: auto !important; - } - - .mb-sm-0 { - margin-bottom: 0 !important; - } - - .mb-sm-1 { - margin-bottom: 0.25rem !important; - } - - .mb-sm-2 { - margin-bottom: 0.5rem !important; - } - - .mb-sm-3 { - margin-bottom: 1rem !important; - } - - .mb-sm-4 { - margin-bottom: 1.5rem !important; - } - - .mb-sm-5 { - margin-bottom: 3rem !important; - } - - .mb-sm-auto { - margin-bottom: auto !important; - } - - .ms-sm-0 { - margin-left: 0 !important; - } - - .ms-sm-1 { - margin-left: 0.25rem !important; - } - - .ms-sm-2 { - margin-left: 0.5rem !important; - } - - .ms-sm-3 { - margin-left: 1rem !important; - } - - .ms-sm-4 { - margin-left: 1.5rem !important; - } - - .ms-sm-5 { - margin-left: 3rem !important; - } - - .ms-sm-auto { - margin-left: auto !important; - } - - .p-sm-0 { - padding: 0 !important; - } - - .p-sm-1 { - padding: 0.25rem !important; - } - - .p-sm-2 { - padding: 0.5rem !important; - } - - .p-sm-3 { - padding: 1rem !important; - } - - .p-sm-4 { - padding: 1.5rem !important; - } - - .p-sm-5 { - padding: 3rem !important; - } - - .px-sm-0 { - padding-right: 0 !important; - padding-left: 0 !important; - } - - .px-sm-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; - } - - .px-sm-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; - } - - .px-sm-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; - } - - .px-sm-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; - } - - .px-sm-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; - } - - .py-sm-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; - } - - .py-sm-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; - } - - .py-sm-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; - } - - .py-sm-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; - } - - .py-sm-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; - } - - .py-sm-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; - } - - .pt-sm-0 { - padding-top: 0 !important; - } - - .pt-sm-1 { - padding-top: 0.25rem !important; - } - - .pt-sm-2 { - padding-top: 0.5rem !important; - } - - .pt-sm-3 { - padding-top: 1rem !important; - } - - .pt-sm-4 { - padding-top: 1.5rem !important; - } - - .pt-sm-5 { - padding-top: 3rem !important; - } - - .pe-sm-0 { - padding-right: 0 !important; - } - - .pe-sm-1 { - padding-right: 0.25rem !important; - } - - .pe-sm-2 { - padding-right: 0.5rem !important; - } - - .pe-sm-3 { - padding-right: 1rem !important; - } - - .pe-sm-4 { - padding-right: 1.5rem !important; - } - - .pe-sm-5 { - padding-right: 3rem !important; - } - - .pb-sm-0 { - padding-bottom: 0 !important; - } - - .pb-sm-1 { - padding-bottom: 0.25rem !important; - } - - .pb-sm-2 { - padding-bottom: 0.5rem !important; - } - - .pb-sm-3 { - padding-bottom: 1rem !important; - } - - .pb-sm-4 { - padding-bottom: 1.5rem !important; - } - - .pb-sm-5 { - padding-bottom: 3rem !important; - } - - .ps-sm-0 { - padding-left: 0 !important; - } - - .ps-sm-1 { - padding-left: 0.25rem !important; - } - - .ps-sm-2 { - padding-left: 0.5rem !important; - } - - .ps-sm-3 { - padding-left: 1rem !important; - } - - .ps-sm-4 { - padding-left: 1.5rem !important; - } - - .ps-sm-5 { - padding-left: 3rem !important; - } - - .text-sm-start { - text-align: left !important; - } - - .text-sm-end { - text-align: right !important; - } - - .text-sm-center { - text-align: center !important; - } -} -@media (min-width: 768px) { - .float-md-start { - float: left !important; - } - - .float-md-end { - float: right !important; - } - - .float-md-none { - float: none !important; - } - - .d-md-inline { - display: inline !important; - } - - .d-md-inline-block { - display: inline-block !important; - } - - .d-md-block { - display: block !important; - } - - .d-md-grid { - display: grid !important; - } - - .d-md-table { - display: table !important; - } - - .d-md-table-row { - display: table-row !important; - } - - .d-md-table-cell { - display: table-cell !important; - } - - .d-md-flex { - display: flex !important; - } - - .d-md-inline-flex { - display: inline-flex !important; - } - - .d-md-none { - display: none !important; - } - - .flex-md-fill { - flex: 1 1 auto !important; - } - - .flex-md-row { - flex-direction: row !important; - } - - .flex-md-column { - flex-direction: column !important; - } - - .flex-md-row-reverse { - flex-direction: row-reverse !important; - } - - .flex-md-column-reverse { - flex-direction: column-reverse !important; - } - - .flex-md-grow-0 { - flex-grow: 0 !important; - } - - .flex-md-grow-1 { - flex-grow: 1 !important; - } - - .flex-md-shrink-0 { - flex-shrink: 0 !important; - } - - .flex-md-shrink-1 { - flex-shrink: 1 !important; - } - - .flex-md-wrap { - flex-wrap: wrap !important; - } - - .flex-md-nowrap { - flex-wrap: nowrap !important; - } - - .flex-md-wrap-reverse { - flex-wrap: wrap-reverse !important; - } - - .gap-md-0 { - gap: 0 !important; - } - - .gap-md-1 { - gap: 0.25rem !important; - } - - .gap-md-2 { - gap: 0.5rem !important; - } - - .gap-md-3 { - gap: 1rem !important; - } - - .gap-md-4 { - gap: 1.5rem !important; - } - - .gap-md-5 { - gap: 3rem !important; - } - - .justify-content-md-start { - justify-content: flex-start !important; - } - - .justify-content-md-end { - justify-content: flex-end !important; - } - - .justify-content-md-center { - justify-content: center !important; - } - - .justify-content-md-between { - justify-content: space-between !important; - } - - .justify-content-md-around { - justify-content: space-around !important; - } - - .justify-content-md-evenly { - justify-content: space-evenly !important; - } - - .align-items-md-start { - align-items: flex-start !important; - } - - .align-items-md-end { - align-items: flex-end !important; - } - - .align-items-md-center { - align-items: center !important; - } - - .align-items-md-baseline { - align-items: baseline !important; - } - - .align-items-md-stretch { - align-items: stretch !important; - } - - .align-content-md-start { - align-content: flex-start !important; - } - - .align-content-md-end { - align-content: flex-end !important; - } - - .align-content-md-center { - align-content: center !important; - } - - .align-content-md-between { - align-content: space-between !important; - } - - .align-content-md-around { - align-content: space-around !important; - } - - .align-content-md-stretch { - align-content: stretch !important; - } - - .align-self-md-auto { - align-self: auto !important; - } - - .align-self-md-start { - align-self: flex-start !important; - } - - .align-self-md-end { - align-self: flex-end !important; - } - - .align-self-md-center { - align-self: center !important; - } - - .align-self-md-baseline { - align-self: baseline !important; - } - - .align-self-md-stretch { - align-self: stretch !important; - } - - .order-md-first { - order: -1 !important; - } - - .order-md-0 { - order: 0 !important; - } - - .order-md-1 { - order: 1 !important; - } - - .order-md-2 { - order: 2 !important; - } - - .order-md-3 { - order: 3 !important; - } - - .order-md-4 { - order: 4 !important; - } - - .order-md-5 { - order: 5 !important; - } - - .order-md-last { - order: 6 !important; - } - - .m-md-0 { - margin: 0 !important; - } - - .m-md-1 { - margin: 0.25rem !important; - } - - .m-md-2 { - margin: 0.5rem !important; - } - - .m-md-3 { - margin: 1rem !important; - } - - .m-md-4 { - margin: 1.5rem !important; - } - - .m-md-5 { - margin: 3rem !important; - } - - .m-md-auto { - margin: auto !important; - } - - .mx-md-0 { - margin-right: 0 !important; - margin-left: 0 !important; - } - - .mx-md-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; - } - - .mx-md-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - } - - .mx-md-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; - } - - .mx-md-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; - } - - .mx-md-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; - } - - .mx-md-auto { - margin-right: auto !important; - margin-left: auto !important; - } - - .my-md-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; - } - - .my-md-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; - } - - .my-md-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; - } - - .my-md-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; - } - - .my-md-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; - } - - .my-md-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; - } - - .my-md-auto { - margin-top: auto !important; - margin-bottom: auto !important; - } - - .mt-md-0 { - margin-top: 0 !important; - } - - .mt-md-1 { - margin-top: 0.25rem !important; - } - - .mt-md-2 { - margin-top: 0.5rem !important; - } - - .mt-md-3 { - margin-top: 1rem !important; - } - - .mt-md-4 { - margin-top: 1.5rem !important; - } - - .mt-md-5 { - margin-top: 3rem !important; - } - - .mt-md-auto { - margin-top: auto !important; - } - - .me-md-0 { - margin-right: 0 !important; - } - - .me-md-1 { - margin-right: 0.25rem !important; - } - - .me-md-2 { - margin-right: 0.5rem !important; - } - - .me-md-3 { - margin-right: 1rem !important; - } - - .me-md-4 { - margin-right: 1.5rem !important; - } - - .me-md-5 { - margin-right: 3rem !important; - } - - .me-md-auto { - margin-right: auto !important; - } - - .mb-md-0 { - margin-bottom: 0 !important; - } - - .mb-md-1 { - margin-bottom: 0.25rem !important; - } - - .mb-md-2 { - margin-bottom: 0.5rem !important; - } - - .mb-md-3 { - margin-bottom: 1rem !important; - } - - .mb-md-4 { - margin-bottom: 1.5rem !important; - } - - .mb-md-5 { - margin-bottom: 3rem !important; - } - - .mb-md-auto { - margin-bottom: auto !important; - } - - .ms-md-0 { - margin-left: 0 !important; - } - - .ms-md-1 { - margin-left: 0.25rem !important; - } - - .ms-md-2 { - margin-left: 0.5rem !important; - } - - .ms-md-3 { - margin-left: 1rem !important; - } - - .ms-md-4 { - margin-left: 1.5rem !important; - } - - .ms-md-5 { - margin-left: 3rem !important; - } - - .ms-md-auto { - margin-left: auto !important; - } - - .p-md-0 { - padding: 0 !important; - } - - .p-md-1 { - padding: 0.25rem !important; - } - - .p-md-2 { - padding: 0.5rem !important; - } - - .p-md-3 { - padding: 1rem !important; - } - - .p-md-4 { - padding: 1.5rem !important; - } - - .p-md-5 { - padding: 3rem !important; - } - - .px-md-0 { - padding-right: 0 !important; - padding-left: 0 !important; - } - - .px-md-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; - } - - .px-md-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; - } - - .px-md-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; - } - - .px-md-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; - } - - .px-md-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; - } - - .py-md-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; - } - - .py-md-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; - } - - .py-md-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; - } - - .py-md-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; - } - - .py-md-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; - } - - .py-md-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; - } - - .pt-md-0 { - padding-top: 0 !important; - } - - .pt-md-1 { - padding-top: 0.25rem !important; - } - - .pt-md-2 { - padding-top: 0.5rem !important; - } - - .pt-md-3 { - padding-top: 1rem !important; - } - - .pt-md-4 { - padding-top: 1.5rem !important; - } - - .pt-md-5 { - padding-top: 3rem !important; - } - - .pe-md-0 { - padding-right: 0 !important; - } - - .pe-md-1 { - padding-right: 0.25rem !important; - } - - .pe-md-2 { - padding-right: 0.5rem !important; - } - - .pe-md-3 { - padding-right: 1rem !important; - } - - .pe-md-4 { - padding-right: 1.5rem !important; - } - - .pe-md-5 { - padding-right: 3rem !important; - } - - .pb-md-0 { - padding-bottom: 0 !important; - } - - .pb-md-1 { - padding-bottom: 0.25rem !important; - } - - .pb-md-2 { - padding-bottom: 0.5rem !important; - } - - .pb-md-3 { - padding-bottom: 1rem !important; - } - - .pb-md-4 { - padding-bottom: 1.5rem !important; - } - - .pb-md-5 { - padding-bottom: 3rem !important; - } - - .ps-md-0 { - padding-left: 0 !important; - } - - .ps-md-1 { - padding-left: 0.25rem !important; - } - - .ps-md-2 { - padding-left: 0.5rem !important; - } - - .ps-md-3 { - padding-left: 1rem !important; - } - - .ps-md-4 { - padding-left: 1.5rem !important; - } - - .ps-md-5 { - padding-left: 3rem !important; - } - - .text-md-start { - text-align: left !important; - } - - .text-md-end { - text-align: right !important; - } - - .text-md-center { - text-align: center !important; - } -} -@media (min-width: 992px) { - .float-lg-start { - float: left !important; - } - - .float-lg-end { - float: right !important; - } - - .float-lg-none { - float: none !important; - } - - .d-lg-inline { - display: inline !important; - } - - .d-lg-inline-block { - display: inline-block !important; - } - - .d-lg-block { - display: block !important; - } - - .d-lg-grid { - display: grid !important; - } - - .d-lg-table { - display: table !important; - } - - .d-lg-table-row { - display: table-row !important; - } - - .d-lg-table-cell { - display: table-cell !important; - } - - .d-lg-flex { - display: flex !important; - } - - .d-lg-inline-flex { - display: inline-flex !important; - } - - .d-lg-none { - display: none !important; - } - - .flex-lg-fill { - flex: 1 1 auto !important; - } - - .flex-lg-row { - flex-direction: row !important; - } - - .flex-lg-column { - flex-direction: column !important; - } - - .flex-lg-row-reverse { - flex-direction: row-reverse !important; - } - - .flex-lg-column-reverse { - flex-direction: column-reverse !important; - } - - .flex-lg-grow-0 { - flex-grow: 0 !important; - } - - .flex-lg-grow-1 { - flex-grow: 1 !important; - } - - .flex-lg-shrink-0 { - flex-shrink: 0 !important; - } - - .flex-lg-shrink-1 { - flex-shrink: 1 !important; - } - - .flex-lg-wrap { - flex-wrap: wrap !important; - } - - .flex-lg-nowrap { - flex-wrap: nowrap !important; - } - - .flex-lg-wrap-reverse { - flex-wrap: wrap-reverse !important; - } - - .gap-lg-0 { - gap: 0 !important; - } - - .gap-lg-1 { - gap: 0.25rem !important; - } - - .gap-lg-2 { - gap: 0.5rem !important; - } - - .gap-lg-3 { - gap: 1rem !important; - } - - .gap-lg-4 { - gap: 1.5rem !important; - } - - .gap-lg-5 { - gap: 3rem !important; - } - - .justify-content-lg-start { - justify-content: flex-start !important; - } - - .justify-content-lg-end { - justify-content: flex-end !important; - } - - .justify-content-lg-center { - justify-content: center !important; - } - - .justify-content-lg-between { - justify-content: space-between !important; - } - - .justify-content-lg-around { - justify-content: space-around !important; - } - - .justify-content-lg-evenly { - justify-content: space-evenly !important; - } - - .align-items-lg-start { - align-items: flex-start !important; - } - - .align-items-lg-end { - align-items: flex-end !important; - } - - .align-items-lg-center { - align-items: center !important; - } - - .align-items-lg-baseline { - align-items: baseline !important; - } - - .align-items-lg-stretch { - align-items: stretch !important; - } - - .align-content-lg-start { - align-content: flex-start !important; - } - - .align-content-lg-end { - align-content: flex-end !important; - } - - .align-content-lg-center { - align-content: center !important; - } - - .align-content-lg-between { - align-content: space-between !important; - } - - .align-content-lg-around { - align-content: space-around !important; - } - - .align-content-lg-stretch { - align-content: stretch !important; - } - - .align-self-lg-auto { - align-self: auto !important; - } - - .align-self-lg-start { - align-self: flex-start !important; - } - - .align-self-lg-end { - align-self: flex-end !important; - } - - .align-self-lg-center { - align-self: center !important; - } - - .align-self-lg-baseline { - align-self: baseline !important; - } - - .align-self-lg-stretch { - align-self: stretch !important; - } - - .order-lg-first { - order: -1 !important; - } - - .order-lg-0 { - order: 0 !important; - } - - .order-lg-1 { - order: 1 !important; - } - - .order-lg-2 { - order: 2 !important; - } - - .order-lg-3 { - order: 3 !important; - } - - .order-lg-4 { - order: 4 !important; - } - - .order-lg-5 { - order: 5 !important; - } - - .order-lg-last { - order: 6 !important; - } - - .m-lg-0 { - margin: 0 !important; - } - - .m-lg-1 { - margin: 0.25rem !important; - } - - .m-lg-2 { - margin: 0.5rem !important; - } - - .m-lg-3 { - margin: 1rem !important; - } - - .m-lg-4 { - margin: 1.5rem !important; - } - - .m-lg-5 { - margin: 3rem !important; - } - - .m-lg-auto { - margin: auto !important; - } - - .mx-lg-0 { - margin-right: 0 !important; - margin-left: 0 !important; - } - - .mx-lg-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; - } - - .mx-lg-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - } - - .mx-lg-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; - } - - .mx-lg-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; - } - - .mx-lg-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; - } - - .mx-lg-auto { - margin-right: auto !important; - margin-left: auto !important; - } - - .my-lg-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; - } - - .my-lg-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; - } - - .my-lg-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; - } - - .my-lg-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; - } - - .my-lg-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; - } - - .my-lg-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; - } - - .my-lg-auto { - margin-top: auto !important; - margin-bottom: auto !important; - } - - .mt-lg-0 { - margin-top: 0 !important; - } - - .mt-lg-1 { - margin-top: 0.25rem !important; - } - - .mt-lg-2 { - margin-top: 0.5rem !important; - } - - .mt-lg-3 { - margin-top: 1rem !important; - } - - .mt-lg-4 { - margin-top: 1.5rem !important; - } - - .mt-lg-5 { - margin-top: 3rem !important; - } - - .mt-lg-auto { - margin-top: auto !important; - } - - .me-lg-0 { - margin-right: 0 !important; - } - - .me-lg-1 { - margin-right: 0.25rem !important; - } - - .me-lg-2 { - margin-right: 0.5rem !important; - } - - .me-lg-3 { - margin-right: 1rem !important; - } - - .me-lg-4 { - margin-right: 1.5rem !important; - } - - .me-lg-5 { - margin-right: 3rem !important; - } - - .me-lg-auto { - margin-right: auto !important; - } - - .mb-lg-0 { - margin-bottom: 0 !important; - } - - .mb-lg-1 { - margin-bottom: 0.25rem !important; - } - - .mb-lg-2 { - margin-bottom: 0.5rem !important; - } - - .mb-lg-3 { - margin-bottom: 1rem !important; - } - - .mb-lg-4 { - margin-bottom: 1.5rem !important; - } - - .mb-lg-5 { - margin-bottom: 3rem !important; - } - - .mb-lg-auto { - margin-bottom: auto !important; - } - - .ms-lg-0 { - margin-left: 0 !important; - } - - .ms-lg-1 { - margin-left: 0.25rem !important; - } - - .ms-lg-2 { - margin-left: 0.5rem !important; - } - - .ms-lg-3 { - margin-left: 1rem !important; - } - - .ms-lg-4 { - margin-left: 1.5rem !important; - } - - .ms-lg-5 { - margin-left: 3rem !important; - } - - .ms-lg-auto { - margin-left: auto !important; - } - - .p-lg-0 { - padding: 0 !important; - } - - .p-lg-1 { - padding: 0.25rem !important; - } - - .p-lg-2 { - padding: 0.5rem !important; - } - - .p-lg-3 { - padding: 1rem !important; - } - - .p-lg-4 { - padding: 1.5rem !important; - } - - .p-lg-5 { - padding: 3rem !important; - } - - .px-lg-0 { - padding-right: 0 !important; - padding-left: 0 !important; - } - - .px-lg-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; - } - - .px-lg-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; - } - - .px-lg-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; - } - - .px-lg-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; - } - - .px-lg-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; - } - - .py-lg-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; - } - - .py-lg-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; - } - - .py-lg-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; - } - - .py-lg-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; - } - - .py-lg-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; - } - - .py-lg-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; - } - - .pt-lg-0 { - padding-top: 0 !important; - } - - .pt-lg-1 { - padding-top: 0.25rem !important; - } - - .pt-lg-2 { - padding-top: 0.5rem !important; - } - - .pt-lg-3 { - padding-top: 1rem !important; - } - - .pt-lg-4 { - padding-top: 1.5rem !important; - } - - .pt-lg-5 { - padding-top: 3rem !important; - } - - .pe-lg-0 { - padding-right: 0 !important; - } - - .pe-lg-1 { - padding-right: 0.25rem !important; - } - - .pe-lg-2 { - padding-right: 0.5rem !important; - } - - .pe-lg-3 { - padding-right: 1rem !important; - } - - .pe-lg-4 { - padding-right: 1.5rem !important; - } - - .pe-lg-5 { - padding-right: 3rem !important; - } - - .pb-lg-0 { - padding-bottom: 0 !important; - } - - .pb-lg-1 { - padding-bottom: 0.25rem !important; - } - - .pb-lg-2 { - padding-bottom: 0.5rem !important; - } - - .pb-lg-3 { - padding-bottom: 1rem !important; - } - - .pb-lg-4 { - padding-bottom: 1.5rem !important; - } - - .pb-lg-5 { - padding-bottom: 3rem !important; - } - - .ps-lg-0 { - padding-left: 0 !important; - } - - .ps-lg-1 { - padding-left: 0.25rem !important; - } - - .ps-lg-2 { - padding-left: 0.5rem !important; - } - - .ps-lg-3 { - padding-left: 1rem !important; - } - - .ps-lg-4 { - padding-left: 1.5rem !important; - } - - .ps-lg-5 { - padding-left: 3rem !important; - } - - .text-lg-start { - text-align: left !important; - } - - .text-lg-end { - text-align: right !important; - } - - .text-lg-center { - text-align: center !important; - } -} -@media (min-width: 1200px) { - .float-xl-start { - float: left !important; - } - - .float-xl-end { - float: right !important; - } - - .float-xl-none { - float: none !important; - } - - .d-xl-inline { - display: inline !important; - } - - .d-xl-inline-block { - display: inline-block !important; - } - - .d-xl-block { - display: block !important; - } - - .d-xl-grid { - display: grid !important; - } - - .d-xl-table { - display: table !important; - } - - .d-xl-table-row { - display: table-row !important; - } - - .d-xl-table-cell { - display: table-cell !important; - } - - .d-xl-flex { - display: flex !important; - } - - .d-xl-inline-flex { - display: inline-flex !important; - } - - .d-xl-none { - display: none !important; - } - - .flex-xl-fill { - flex: 1 1 auto !important; - } - - .flex-xl-row { - flex-direction: row !important; - } - - .flex-xl-column { - flex-direction: column !important; - } - - .flex-xl-row-reverse { - flex-direction: row-reverse !important; - } - - .flex-xl-column-reverse { - flex-direction: column-reverse !important; - } - - .flex-xl-grow-0 { - flex-grow: 0 !important; - } - - .flex-xl-grow-1 { - flex-grow: 1 !important; - } - - .flex-xl-shrink-0 { - flex-shrink: 0 !important; - } - - .flex-xl-shrink-1 { - flex-shrink: 1 !important; - } - - .flex-xl-wrap { - flex-wrap: wrap !important; - } - - .flex-xl-nowrap { - flex-wrap: nowrap !important; - } - - .flex-xl-wrap-reverse { - flex-wrap: wrap-reverse !important; - } - - .gap-xl-0 { - gap: 0 !important; - } - - .gap-xl-1 { - gap: 0.25rem !important; - } - - .gap-xl-2 { - gap: 0.5rem !important; - } - - .gap-xl-3 { - gap: 1rem !important; - } - - .gap-xl-4 { - gap: 1.5rem !important; - } - - .gap-xl-5 { - gap: 3rem !important; - } - - .justify-content-xl-start { - justify-content: flex-start !important; - } - - .justify-content-xl-end { - justify-content: flex-end !important; - } - - .justify-content-xl-center { - justify-content: center !important; - } - - .justify-content-xl-between { - justify-content: space-between !important; - } - - .justify-content-xl-around { - justify-content: space-around !important; - } - - .justify-content-xl-evenly { - justify-content: space-evenly !important; - } - - .align-items-xl-start { - align-items: flex-start !important; - } - - .align-items-xl-end { - align-items: flex-end !important; - } - - .align-items-xl-center { - align-items: center !important; - } - - .align-items-xl-baseline { - align-items: baseline !important; - } - - .align-items-xl-stretch { - align-items: stretch !important; - } - - .align-content-xl-start { - align-content: flex-start !important; - } - - .align-content-xl-end { - align-content: flex-end !important; - } - - .align-content-xl-center { - align-content: center !important; - } - - .align-content-xl-between { - align-content: space-between !important; - } - - .align-content-xl-around { - align-content: space-around !important; - } - - .align-content-xl-stretch { - align-content: stretch !important; - } - - .align-self-xl-auto { - align-self: auto !important; - } - - .align-self-xl-start { - align-self: flex-start !important; - } - - .align-self-xl-end { - align-self: flex-end !important; - } - - .align-self-xl-center { - align-self: center !important; - } - - .align-self-xl-baseline { - align-self: baseline !important; - } - - .align-self-xl-stretch { - align-self: stretch !important; - } - - .order-xl-first { - order: -1 !important; - } - - .order-xl-0 { - order: 0 !important; - } - - .order-xl-1 { - order: 1 !important; - } - - .order-xl-2 { - order: 2 !important; - } - - .order-xl-3 { - order: 3 !important; - } - - .order-xl-4 { - order: 4 !important; - } - - .order-xl-5 { - order: 5 !important; - } - - .order-xl-last { - order: 6 !important; - } - - .m-xl-0 { - margin: 0 !important; - } - - .m-xl-1 { - margin: 0.25rem !important; - } - - .m-xl-2 { - margin: 0.5rem !important; - } - - .m-xl-3 { - margin: 1rem !important; - } - - .m-xl-4 { - margin: 1.5rem !important; - } - - .m-xl-5 { - margin: 3rem !important; - } - - .m-xl-auto { - margin: auto !important; - } - - .mx-xl-0 { - margin-right: 0 !important; - margin-left: 0 !important; - } - - .mx-xl-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; - } - - .mx-xl-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - } - - .mx-xl-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; - } - - .mx-xl-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; - } - - .mx-xl-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; - } - - .mx-xl-auto { - margin-right: auto !important; - margin-left: auto !important; - } - - .my-xl-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; - } - - .my-xl-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; - } - - .my-xl-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; - } - - .my-xl-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; - } - - .my-xl-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; - } - - .my-xl-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; - } - - .my-xl-auto { - margin-top: auto !important; - margin-bottom: auto !important; - } - - .mt-xl-0 { - margin-top: 0 !important; - } - - .mt-xl-1 { - margin-top: 0.25rem !important; - } - - .mt-xl-2 { - margin-top: 0.5rem !important; - } - - .mt-xl-3 { - margin-top: 1rem !important; - } - - .mt-xl-4 { - margin-top: 1.5rem !important; - } - - .mt-xl-5 { - margin-top: 3rem !important; - } - - .mt-xl-auto { - margin-top: auto !important; - } - - .me-xl-0 { - margin-right: 0 !important; - } - - .me-xl-1 { - margin-right: 0.25rem !important; - } - - .me-xl-2 { - margin-right: 0.5rem !important; - } - - .me-xl-3 { - margin-right: 1rem !important; - } - - .me-xl-4 { - margin-right: 1.5rem !important; - } - - .me-xl-5 { - margin-right: 3rem !important; - } - - .me-xl-auto { - margin-right: auto !important; - } - - .mb-xl-0 { - margin-bottom: 0 !important; - } - - .mb-xl-1 { - margin-bottom: 0.25rem !important; - } - - .mb-xl-2 { - margin-bottom: 0.5rem !important; - } - - .mb-xl-3 { - margin-bottom: 1rem !important; - } - - .mb-xl-4 { - margin-bottom: 1.5rem !important; - } - - .mb-xl-5 { - margin-bottom: 3rem !important; - } - - .mb-xl-auto { - margin-bottom: auto !important; - } - - .ms-xl-0 { - margin-left: 0 !important; - } - - .ms-xl-1 { - margin-left: 0.25rem !important; - } - - .ms-xl-2 { - margin-left: 0.5rem !important; - } - - .ms-xl-3 { - margin-left: 1rem !important; - } - - .ms-xl-4 { - margin-left: 1.5rem !important; - } - - .ms-xl-5 { - margin-left: 3rem !important; - } - - .ms-xl-auto { - margin-left: auto !important; - } - - .p-xl-0 { - padding: 0 !important; - } - - .p-xl-1 { - padding: 0.25rem !important; - } - - .p-xl-2 { - padding: 0.5rem !important; - } - - .p-xl-3 { - padding: 1rem !important; - } - - .p-xl-4 { - padding: 1.5rem !important; - } - - .p-xl-5 { - padding: 3rem !important; - } - - .px-xl-0 { - padding-right: 0 !important; - padding-left: 0 !important; - } - - .px-xl-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; - } - - .px-xl-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; - } - - .px-xl-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; - } - - .px-xl-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; - } - - .px-xl-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; - } - - .py-xl-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; - } - - .py-xl-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; - } - - .py-xl-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; - } - - .py-xl-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; - } - - .py-xl-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; - } - - .py-xl-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; - } - - .pt-xl-0 { - padding-top: 0 !important; - } - - .pt-xl-1 { - padding-top: 0.25rem !important; - } - - .pt-xl-2 { - padding-top: 0.5rem !important; - } - - .pt-xl-3 { - padding-top: 1rem !important; - } - - .pt-xl-4 { - padding-top: 1.5rem !important; - } - - .pt-xl-5 { - padding-top: 3rem !important; - } - - .pe-xl-0 { - padding-right: 0 !important; - } - - .pe-xl-1 { - padding-right: 0.25rem !important; - } - - .pe-xl-2 { - padding-right: 0.5rem !important; - } - - .pe-xl-3 { - padding-right: 1rem !important; - } - - .pe-xl-4 { - padding-right: 1.5rem !important; - } - - .pe-xl-5 { - padding-right: 3rem !important; - } - - .pb-xl-0 { - padding-bottom: 0 !important; - } - - .pb-xl-1 { - padding-bottom: 0.25rem !important; - } - - .pb-xl-2 { - padding-bottom: 0.5rem !important; - } - - .pb-xl-3 { - padding-bottom: 1rem !important; - } - - .pb-xl-4 { - padding-bottom: 1.5rem !important; - } - - .pb-xl-5 { - padding-bottom: 3rem !important; - } - - .ps-xl-0 { - padding-left: 0 !important; - } - - .ps-xl-1 { - padding-left: 0.25rem !important; - } - - .ps-xl-2 { - padding-left: 0.5rem !important; - } - - .ps-xl-3 { - padding-left: 1rem !important; - } - - .ps-xl-4 { - padding-left: 1.5rem !important; - } - - .ps-xl-5 { - padding-left: 3rem !important; - } - - .text-xl-start { - text-align: left !important; - } - - .text-xl-end { - text-align: right !important; - } - - .text-xl-center { - text-align: center !important; - } -} -@media (min-width: 1400px) { - .float-xxl-start { - float: left !important; - } - - .float-xxl-end { - float: right !important; - } - - .float-xxl-none { - float: none !important; - } - - .d-xxl-inline { - display: inline !important; - } - - .d-xxl-inline-block { - display: inline-block !important; - } - - .d-xxl-block { - display: block !important; - } - - .d-xxl-grid { - display: grid !important; - } - - .d-xxl-table { - display: table !important; - } - - .d-xxl-table-row { - display: table-row !important; - } - - .d-xxl-table-cell { - display: table-cell !important; - } - - .d-xxl-flex { - display: flex !important; - } - - .d-xxl-inline-flex { - display: inline-flex !important; - } - - .d-xxl-none { - display: none !important; - } - - .flex-xxl-fill { - flex: 1 1 auto !important; - } - - .flex-xxl-row { - flex-direction: row !important; - } - - .flex-xxl-column { - flex-direction: column !important; - } - - .flex-xxl-row-reverse { - flex-direction: row-reverse !important; - } - - .flex-xxl-column-reverse { - flex-direction: column-reverse !important; - } - - .flex-xxl-grow-0 { - flex-grow: 0 !important; - } - - .flex-xxl-grow-1 { - flex-grow: 1 !important; - } - - .flex-xxl-shrink-0 { - flex-shrink: 0 !important; - } - - .flex-xxl-shrink-1 { - flex-shrink: 1 !important; - } - - .flex-xxl-wrap { - flex-wrap: wrap !important; - } - - .flex-xxl-nowrap { - flex-wrap: nowrap !important; - } - - .flex-xxl-wrap-reverse { - flex-wrap: wrap-reverse !important; - } - - .gap-xxl-0 { - gap: 0 !important; - } - - .gap-xxl-1 { - gap: 0.25rem !important; - } - - .gap-xxl-2 { - gap: 0.5rem !important; - } - - .gap-xxl-3 { - gap: 1rem !important; - } - - .gap-xxl-4 { - gap: 1.5rem !important; - } - - .gap-xxl-5 { - gap: 3rem !important; - } - - .justify-content-xxl-start { - justify-content: flex-start !important; - } - - .justify-content-xxl-end { - justify-content: flex-end !important; - } - - .justify-content-xxl-center { - justify-content: center !important; - } - - .justify-content-xxl-between { - justify-content: space-between !important; - } - - .justify-content-xxl-around { - justify-content: space-around !important; - } - - .justify-content-xxl-evenly { - justify-content: space-evenly !important; - } - - .align-items-xxl-start { - align-items: flex-start !important; - } - - .align-items-xxl-end { - align-items: flex-end !important; - } - - .align-items-xxl-center { - align-items: center !important; - } - - .align-items-xxl-baseline { - align-items: baseline !important; - } - - .align-items-xxl-stretch { - align-items: stretch !important; - } - - .align-content-xxl-start { - align-content: flex-start !important; - } - - .align-content-xxl-end { - align-content: flex-end !important; - } - - .align-content-xxl-center { - align-content: center !important; - } - - .align-content-xxl-between { - align-content: space-between !important; - } - - .align-content-xxl-around { - align-content: space-around !important; - } - - .align-content-xxl-stretch { - align-content: stretch !important; - } - - .align-self-xxl-auto { - align-self: auto !important; - } - - .align-self-xxl-start { - align-self: flex-start !important; - } - - .align-self-xxl-end { - align-self: flex-end !important; - } - - .align-self-xxl-center { - align-self: center !important; - } - - .align-self-xxl-baseline { - align-self: baseline !important; - } - - .align-self-xxl-stretch { - align-self: stretch !important; - } - - .order-xxl-first { - order: -1 !important; - } - - .order-xxl-0 { - order: 0 !important; - } - - .order-xxl-1 { - order: 1 !important; - } - - .order-xxl-2 { - order: 2 !important; - } - - .order-xxl-3 { - order: 3 !important; - } - - .order-xxl-4 { - order: 4 !important; - } - - .order-xxl-5 { - order: 5 !important; - } - - .order-xxl-last { - order: 6 !important; - } - - .m-xxl-0 { - margin: 0 !important; - } - - .m-xxl-1 { - margin: 0.25rem !important; - } - - .m-xxl-2 { - margin: 0.5rem !important; - } - - .m-xxl-3 { - margin: 1rem !important; - } - - .m-xxl-4 { - margin: 1.5rem !important; - } - - .m-xxl-5 { - margin: 3rem !important; - } - - .m-xxl-auto { - margin: auto !important; - } - - .mx-xxl-0 { - margin-right: 0 !important; - margin-left: 0 !important; - } - - .mx-xxl-1 { - margin-right: 0.25rem !important; - margin-left: 0.25rem !important; - } - - .mx-xxl-2 { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - } - - .mx-xxl-3 { - margin-right: 1rem !important; - margin-left: 1rem !important; - } - - .mx-xxl-4 { - margin-right: 1.5rem !important; - margin-left: 1.5rem !important; - } - - .mx-xxl-5 { - margin-right: 3rem !important; - margin-left: 3rem !important; - } - - .mx-xxl-auto { - margin-right: auto !important; - margin-left: auto !important; - } - - .my-xxl-0 { - margin-top: 0 !important; - margin-bottom: 0 !important; - } - - .my-xxl-1 { - margin-top: 0.25rem !important; - margin-bottom: 0.25rem !important; - } - - .my-xxl-2 { - margin-top: 0.5rem !important; - margin-bottom: 0.5rem !important; - } - - .my-xxl-3 { - margin-top: 1rem !important; - margin-bottom: 1rem !important; - } - - .my-xxl-4 { - margin-top: 1.5rem !important; - margin-bottom: 1.5rem !important; - } - - .my-xxl-5 { - margin-top: 3rem !important; - margin-bottom: 3rem !important; - } - - .my-xxl-auto { - margin-top: auto !important; - margin-bottom: auto !important; - } - - .mt-xxl-0 { - margin-top: 0 !important; - } - - .mt-xxl-1 { - margin-top: 0.25rem !important; - } - - .mt-xxl-2 { - margin-top: 0.5rem !important; - } - - .mt-xxl-3 { - margin-top: 1rem !important; - } - - .mt-xxl-4 { - margin-top: 1.5rem !important; - } - - .mt-xxl-5 { - margin-top: 3rem !important; - } - - .mt-xxl-auto { - margin-top: auto !important; - } - - .me-xxl-0 { - margin-right: 0 !important; - } - - .me-xxl-1 { - margin-right: 0.25rem !important; - } - - .me-xxl-2 { - margin-right: 0.5rem !important; - } - - .me-xxl-3 { - margin-right: 1rem !important; - } - - .me-xxl-4 { - margin-right: 1.5rem !important; - } - - .me-xxl-5 { - margin-right: 3rem !important; - } - - .me-xxl-auto { - margin-right: auto !important; - } - - .mb-xxl-0 { - margin-bottom: 0 !important; - } - - .mb-xxl-1 { - margin-bottom: 0.25rem !important; - } - - .mb-xxl-2 { - margin-bottom: 0.5rem !important; - } - - .mb-xxl-3 { - margin-bottom: 1rem !important; - } - - .mb-xxl-4 { - margin-bottom: 1.5rem !important; - } - - .mb-xxl-5 { - margin-bottom: 3rem !important; - } - - .mb-xxl-auto { - margin-bottom: auto !important; - } - - .ms-xxl-0 { - margin-left: 0 !important; - } - - .ms-xxl-1 { - margin-left: 0.25rem !important; - } - - .ms-xxl-2 { - margin-left: 0.5rem !important; - } - - .ms-xxl-3 { - margin-left: 1rem !important; - } - - .ms-xxl-4 { - margin-left: 1.5rem !important; - } - - .ms-xxl-5 { - margin-left: 3rem !important; - } - - .ms-xxl-auto { - margin-left: auto !important; - } - - .p-xxl-0 { - padding: 0 !important; - } - - .p-xxl-1 { - padding: 0.25rem !important; - } - - .p-xxl-2 { - padding: 0.5rem !important; - } - - .p-xxl-3 { - padding: 1rem !important; - } - - .p-xxl-4 { - padding: 1.5rem !important; - } - - .p-xxl-5 { - padding: 3rem !important; - } - - .px-xxl-0 { - padding-right: 0 !important; - padding-left: 0 !important; - } - - .px-xxl-1 { - padding-right: 0.25rem !important; - padding-left: 0.25rem !important; - } - - .px-xxl-2 { - padding-right: 0.5rem !important; - padding-left: 0.5rem !important; - } - - .px-xxl-3 { - padding-right: 1rem !important; - padding-left: 1rem !important; - } - - .px-xxl-4 { - padding-right: 1.5rem !important; - padding-left: 1.5rem !important; - } - - .px-xxl-5 { - padding-right: 3rem !important; - padding-left: 3rem !important; - } - - .py-xxl-0 { - padding-top: 0 !important; - padding-bottom: 0 !important; - } - - .py-xxl-1 { - padding-top: 0.25rem !important; - padding-bottom: 0.25rem !important; - } - - .py-xxl-2 { - padding-top: 0.5rem !important; - padding-bottom: 0.5rem !important; - } - - .py-xxl-3 { - padding-top: 1rem !important; - padding-bottom: 1rem !important; - } - - .py-xxl-4 { - padding-top: 1.5rem !important; - padding-bottom: 1.5rem !important; - } - - .py-xxl-5 { - padding-top: 3rem !important; - padding-bottom: 3rem !important; - } - - .pt-xxl-0 { - padding-top: 0 !important; - } - - .pt-xxl-1 { - padding-top: 0.25rem !important; - } - - .pt-xxl-2 { - padding-top: 0.5rem !important; - } - - .pt-xxl-3 { - padding-top: 1rem !important; - } - - .pt-xxl-4 { - padding-top: 1.5rem !important; - } - - .pt-xxl-5 { - padding-top: 3rem !important; - } - - .pe-xxl-0 { - padding-right: 0 !important; - } - - .pe-xxl-1 { - padding-right: 0.25rem !important; - } - - .pe-xxl-2 { - padding-right: 0.5rem !important; - } - - .pe-xxl-3 { - padding-right: 1rem !important; - } - - .pe-xxl-4 { - padding-right: 1.5rem !important; - } - - .pe-xxl-5 { - padding-right: 3rem !important; - } - - .pb-xxl-0 { - padding-bottom: 0 !important; - } - - .pb-xxl-1 { - padding-bottom: 0.25rem !important; - } - - .pb-xxl-2 { - padding-bottom: 0.5rem !important; - } - - .pb-xxl-3 { - padding-bottom: 1rem !important; - } - - .pb-xxl-4 { - padding-bottom: 1.5rem !important; - } - - .pb-xxl-5 { - padding-bottom: 3rem !important; - } - - .ps-xxl-0 { - padding-left: 0 !important; - } - - .ps-xxl-1 { - padding-left: 0.25rem !important; - } - - .ps-xxl-2 { - padding-left: 0.5rem !important; - } - - .ps-xxl-3 { - padding-left: 1rem !important; - } - - .ps-xxl-4 { - padding-left: 1.5rem !important; - } - - .ps-xxl-5 { - padding-left: 3rem !important; - } - - .text-xxl-start { - text-align: left !important; - } - - .text-xxl-end { - text-align: right !important; - } - - .text-xxl-center { - text-align: center !important; - } -} -@media (min-width: 1200px) { - .fs-1 { - font-size: 2.5rem !important; - } - - .fs-2 { - font-size: 2rem !important; - } - - .fs-3 { - font-size: 1.75rem !important; - } - - .fs-4 { - font-size: 1.5rem !important; - } -} -@media print { - .d-print-inline { - display: inline !important; - } - - .d-print-inline-block { - display: inline-block !important; - } - - .d-print-block { - display: block !important; - } - - .d-print-grid { - display: grid !important; - } - - .d-print-table { - display: table !important; - } - - .d-print-table-row { - display: table-row !important; - } - - .d-print-table-cell { - display: table-cell !important; - } - - .d-print-flex { - display: flex !important; - } - - .d-print-inline-flex { - display: inline-flex !important; - } - - .d-print-none { - display: none !important; - } -} - -/*# sourceMappingURL=bootstrap.css.map */ \ No newline at end of file diff --git a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css.map b/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css.map deleted file mode 100644 index 39c26aaa2c..0000000000 --- a/modules/openiddict/app/OpenIddict.Demo.Server/wwwroot/libs/bootstrap/css/bootstrap.css.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"sources":["bootstrap.css","../../scss/bootstrap.scss","../../scss/_root.scss","../../scss/_reboot.scss","../../scss/vendor/_rfs.scss","../../scss/_variables.scss","../../scss/mixins/_border-radius.scss","../../scss/_type.scss","../../scss/mixins/_lists.scss","../../scss/_images.scss","../../scss/mixins/_image.scss","../../scss/_containers.scss","../../scss/mixins/_container.scss","../../scss/mixins/_breakpoints.scss","../../scss/_grid.scss","../../scss/mixins/_grid.scss","../../scss/_tables.scss","../../scss/mixins/_table-variants.scss","../../scss/forms/_labels.scss","../../scss/forms/_form-text.scss","../../scss/forms/_form-control.scss","../../scss/mixins/_transition.scss","../../scss/mixins/_gradients.scss","../../scss/forms/_form-select.scss","../../scss/forms/_form-check.scss","../../scss/forms/_form-range.scss","../../scss/forms/_floating-labels.scss","../../scss/forms/_input-group.scss","../../scss/mixins/_forms.scss","../../scss/_buttons.scss","../../scss/mixins/_buttons.scss","../../scss/_transitions.scss","../../scss/_dropdown.scss","../../scss/mixins/_caret.scss","../../scss/_button-group.scss","../../scss/_nav.scss","../../scss/_navbar.scss","../../scss/_card.scss","../../scss/_accordion.scss","../../scss/_breadcrumb.scss","../../scss/_pagination.scss","../../scss/mixins/_pagination.scss","../../scss/_badge.scss","../../scss/_alert.scss","../../scss/mixins/_alert.scss","../../scss/_progress.scss","../../scss/_list-group.scss","../../scss/mixins/_list-group.scss","../../scss/_close.scss","../../scss/_toasts.scss","../../scss/_modal.scss","../../scss/mixins/_backdrop.scss","../../scss/_tooltip.scss","../../scss/mixins/_reset-text.scss","../../scss/_popover.scss","../../scss/_carousel.scss","../../scss/mixins/_clearfix.scss","../../scss/_spinners.scss","../../scss/_offcanvas.scss","../../scss/_placeholders.scss","../../scss/helpers/_colored-links.scss","../../scss/helpers/_ratio.scss","../../scss/helpers/_position.scss","../../scss/helpers/_stacks.scss","../../scss/helpers/_visually-hidden.scss","../../scss/mixins/_visually-hidden.scss","../../scss/helpers/_stretched-link.scss","../../scss/helpers/_text-truncation.scss","../../scss/mixins/_text-truncate.scss","../../scss/helpers/_vr.scss","../../scss/mixins/_utilities.scss","../../scss/utilities/_api.scss"],"names":[],"mappings":"AAAA,gBAAgB;ACAhB;;;;;EAAA;ACAA;EAQI,kBAAA;EAAA,oBAAA;EAAA,oBAAA;EAAA,kBAAA;EAAA,iBAAA;EAAA,oBAAA;EAAA,oBAAA;EAAA,mBAAA;EAAA,kBAAA;EAAA,kBAAA;EAAA,gBAAA;EAAA,kBAAA;EAAA,uBAAA;EAIA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAAA,sBAAA;EAIA,qBAAA;EAAA,uBAAA;EAAA,qBAAA;EAAA,kBAAA;EAAA,qBAAA;EAAA,oBAAA;EAAA,mBAAA;EAAA,kBAAA;EAIA,8BAAA;EAAA,iCAAA;EAAA,6BAAA;EAAA,2BAAA;EAAA,6BAAA;EAAA,4BAAA;EAAA,6BAAA;EAAA,yBAAA;EAGF,6BAAA;EACA,uBAAA;EACA,+BAAA;EACA,+BAAA;EAMA,qNAAA;EACA,yGAAA;EACA,yFAAA;EAQA,gDAAA;EACA,yBAAA;EACA,0BAAA;EACA,0BAAA;EACA,wBAAA;EAIA,kBAAA;AFSF;;AG5CA;;;EAGE,sBAAA;AH+CF;;AGhCI;EANJ;IAOM,uBAAA;EHoCJ;AACF;;AGvBA;EACE,SAAA;EACA,uCAAA;ECmPI,mCALI;ED5OR,uCAAA;EACA,uCAAA;EACA,2BAAA;EACA,qCAAA;EACA,mCAAA;EACA,8BAAA;EACA,6CAAA;AH0BF;;AGhBA;EACE,cAAA;EACA,cE+kB4B;EF9kB5B,8BAAA;EACA,SAAA;EACA,aE8kB4B;AL3jB9B;;AGhBA;EACE,WEwb4B;ALra9B;;AGTA;EACE,aAAA;EACA,qBEohB4B;EFjhB5B,gBEohB4B;EFnhB5B,gBEohB4B;AL1gB9B;;AGNA;ECwMQ,iCAAA;AJ9LR;AI4BI;EDtCJ;IC+MQ,iBAAA;EJjMN;AACF;;AGVA;ECmMQ,iCAAA;AJrLR;AImBI;EDjCJ;IC0MQ,eAAA;EJxLN;AACF;;AGdA;EC8LQ,+BAAA;AJ5KR;AIUI;ED5BJ;ICqMQ,kBAAA;EJ/KN;AACF;;AGlBA;ECyLQ,iCAAA;AJnKR;AICI;EDvBJ;ICgMQ,iBAAA;EJtKN;AACF;;AGtBA;ECgLM,kBALI;AJjJV;;AGrBA;EC2KM,eALI;AJ7IV;;AGdA;EACE,aAAA;EACA,mBEkU0B;ALjT5B;;AGNA;;EAEE,yCAAA;EAAA,iCAAA;EACA,YAAA;EACA,sCAAA;EAAA,8BAAA;AHSF;;AGHA;EACE,mBAAA;EACA,kBAAA;EACA,oBAAA;AHMF;;AGAA;;EAEE,kBAAA;AHGF;;AGAA;;;EAGE,aAAA;EACA,mBAAA;AHGF;;AGAA;;;;EAIE,gBAAA;AHGF;;AGAA;EACE,gBEuZ4B;ALpZ9B;;AGEA;EACE,qBAAA;EACA,cAAA;AHCF;;AGKA;EACE,gBAAA;AHFF;;AGUA;;EAEE,mBEgY4B;ALvY9B;;AGeA;EC4EM,kBALI;AJlFV;;AGkBA;EACE,cE4b4B;EF3b5B,yBEmc4B;ALld9B;;AGwBA;;EAEE,kBAAA;ECwDI,iBALI;EDjDR,cAAA;EACA,wBAAA;AHrBF;;AGwBA;EAAM,eAAA;AHpBN;;AGqBA;EAAM,WAAA;AHjBN;;AGsBA;EACE,cEpNQ;EFqNR,0BEkMwC;ALrN1C;AGqBE;EACE,cEiMsC;ALpN1C;;AG8BE;EAEE,cAAA;EACA,qBAAA;AH5BJ;;AGmCA;;;;EAIE,qCE6S4B;ED/RxB,cALI;EDPR,+BAAA;EACA,2BAAA;AHhCF;;AGuCA;EACE,cAAA;EACA,aAAA;EACA,mBAAA;EACA,cAAA;ECAI,kBALI;AJ9BV;AGwCE;ECLI,kBALI;EDYN,cAAA;EACA,kBAAA;AHtCJ;;AG0CA;ECZM,kBALI;EDmBR,cE1QQ;EF2QR,qBAAA;AHvCF;AG0CE;EACE,cAAA;AHxCJ;;AG4CA;EACE,sBAAA;ECxBI,kBALI;ED+BR,WEvTS;EFwTT,yBE/SS;ECEP,qBAAA;ANqQJ;AG2CE;EACE,UAAA;EC/BE,cALI;EDsCN,gBE0Q0B;ALnT9B;;AGkDA;EACE,gBAAA;AH/CF;;AGqDA;;EAEE,sBAAA;AHlDF;;AG0DA;EACE,oBAAA;EACA,yBAAA;AHvDF;;AG0DA;EACE,mBEwU4B;EFvU5B,sBEuU4B;EFtU5B,cE1VS;EF2VT,gBAAA;AHvDF;;AG8DA;EAEE,mBAAA;EACA,gCAAA;AH5DF;;AG+DA;;;;;;EAME,qBAAA;EACA,mBAAA;EACA,eAAA;AH5DF;;AGoEA;EACE,qBAAA;AHjEF;;AGuEA;EAEE,gBAAA;AHrEF;;AG6EA;EACE,UAAA;AH1EF;;AG+EA;;;;;EAKE,SAAA;EACA,oBAAA;EC9HI,kBALI;EDqIR,oBAAA;AH5EF;;AGgFA;;EAEE,oBAAA;AH7EF;;AGkFA;EACE,eAAA;AH/EF;;AGkFA;EAGE,iBAAA;AHjFF;AGoFE;EACE,UAAA;AHlFJ;;AGyFA;EACE,aAAA;AHtFF;;AG8FA;;;;EAIE,0BAAA;AH3FF;AG8FI;;;;EACE,eAAA;AHzFN;;AGgGA;EACE,UAAA;EACA,kBAAA;AH7FF;;AGkGA;EACE,gBAAA;AH/FF;;AGyGA;EACE,YAAA;EACA,UAAA;EACA,SAAA;EACA,SAAA;AHtGF;;AG8GA;EACE,WAAA;EACA,WAAA;EACA,UAAA;EACA,qBE6J4B;EDhXtB,iCAAA;EDsNN,oBAAA;AH5GF;AI5QI;EDiXJ;ICxMQ,iBAAA;EJuGN;AACF;AGyGE;EACE,WAAA;AHvGJ;;AG8GA;;;;;;;EAOE,UAAA;AH3GF;;AG8GA;EACE,YAAA;AH3GF;;AGoHA;EACE,oBAAA;EACA,6BAAA;AHjHF;;AGyHA;;;;;;;CAAA;AAWA;EACE,wBAAA;AHzHF;;AG8HA;EACE,UAAA;AH3HF;;AGiIA;EACE,aAAA;AH9HF;;AG6HA;EACE,aAAA;AH9HF;;AGoIA;EACE,aAAA;EACA,0BAAA;AHjIF;;AGsIA;EACE,qBAAA;AHnIF;;AGwIA;EACE,SAAA;AHrIF;;AG4IA;EACE,kBAAA;EACA,eAAA;AHzIF;;AGiJA;EACE,wBAAA;AH9IF;;AGsJA;EACE,wBAAA;AHnJF;;AOhcA;EHyQM,kBALI;EGlQR,gBFumB4B;ALpK9B;;AO9bE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;AL1I9B;AIhWI;EGpGF;IH6QM,eAAA;EJ2LN;AACF;;AOzcE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;AL/H9B;AI3WI;EGpGF;IH6QM,iBAAA;EJsMN;AACF;;AOpdE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;ALpH9B;AItXI;EGpGF;IH6QM,eAAA;EJiNN;AACF;;AO/dE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;ALzG9B;AIjYI;EGpGF;IH6QM,iBAAA;EJ4NN;AACF;;AO1eE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;AL9F9B;AI5YI;EGpGF;IH6QM,eAAA;EJuON;AACF;;AOrfE;EHsQM,iCAAA;EGpQJ,gBF0lBkB;EEzlBlB,gBF2kB0B;ALnF9B;AIvZI;EGpGF;IH6QM,iBAAA;EJkPN;AACF;;AO1eA;ECrDE,eAAA;EACA,gBAAA;ARmiBF;;AO1eA;EC1DE,eAAA;EACA,gBAAA;ARwiBF;;AO5eA;EACE,qBAAA;AP+eF;AO7eE;EACE,oBF8lB0B;AL/G9B;;AOreA;EHsNM,kBALI;EG/MR,yBAAA;APweF;;AOpeA;EACE,mBFgSO;EDjFH,kBALI;AJ8RV;AOreE;EACE,gBAAA;APueJ;;AOneA;EACE,iBAAA;EACA,mBFsRO;EDjFH,kBALI;EG9LR,cFpFS;AL0jBX;AOpeE;EACE,aAAA;APseJ;;ASpkBA;ECIE,eAAA;EAGA,YAAA;AVkkBF;;ASnkBA;EACE,gBJs9CkC;EIr9ClC,sBJPS;EIQT,yBAAA;EHGE,sBAAA;EIRF,eAAA;EAGA,YAAA;AV2kBF;;AS7jBA;EAEE,qBAAA;AT+jBF;;AS5jBA;EACE,qBAAA;EACA,cAAA;AT+jBF;;AS5jBA;EL+PM,kBALI;EKxPR,cJ1BS;ALylBX;;AWjmBE;;;;;;;ECHA,WAAA;EACA,0CAAA;EACA,yCAAA;EACA,kBAAA;EACA,iBAAA;AZ8mBF;;AatjBI;EF5CE;IACE,gBNide;ELqJrB;AACF;Aa5jBI;EF5CE;IACE,gBNide;EL0JrB;AACF;AajkBI;EF5CE;IACE,gBNide;EL+JrB;AACF;AatkBI;EF5CE;IACE,iBNide;ELoKrB;AACF;Aa3kBI;EF5CE;IACE,iBNide;ELyKrB;AACF;Ac1oBE;ECAA,qBAAA;EACA,gBAAA;EACA,aAAA;EACA,eAAA;EAEA,yCAAA;EACA,6CAAA;EACA,4CAAA;Af4oBF;AchpBI;ECaF,cAAA;EACA,WAAA;EACA,eAAA;EACA,6CAAA;EACA,4CAAA;EACA,8BAAA;AfsoBF;;AevlBM;EACE,YAAA;Af0lBR;;AevlBM;EApCJ,cAAA;EACA,WAAA;Af+nBF;;AejnBE;EACE,cAAA;EACA,WAAA;AfonBJ;;AetnBE;EACE,cAAA;EACA,UAAA;AfynBJ;;Ae3nBE;EACE,cAAA;EACA,qBAAA;Af8nBJ;;AehoBE;EACE,cAAA;EACA,UAAA;AfmoBJ;;AeroBE;EACE,cAAA;EACA,UAAA;AfwoBJ;;Ae1oBE;EACE,cAAA;EACA,qBAAA;Af6oBJ;;Ae9mBM;EAhDJ,cAAA;EACA,WAAA;AfkqBF;;Ae7mBU;EAhEN,cAAA;EACA,kBAAA;AfirBJ;;AelnBU;EAhEN,cAAA;EACA,mBAAA;AfsrBJ;;AevnBU;EAhEN,cAAA;EACA,UAAA;Af2rBJ;;Ae5nBU;EAhEN,cAAA;EACA,mBAAA;AfgsBJ;;AejoBU;EAhEN,cAAA;EACA,mBAAA;AfqsBJ;;AetoBU;EAhEN,cAAA;EACA,UAAA;Af0sBJ;;Ae3oBU;EAhEN,cAAA;EACA,mBAAA;Af+sBJ;;AehpBU;EAhEN,cAAA;EACA,mBAAA;AfotBJ;;AerpBU;EAhEN,cAAA;EACA,UAAA;AfytBJ;;Ae1pBU;EAhEN,cAAA;EACA,mBAAA;Af8tBJ;;Ae/pBU;EAhEN,cAAA;EACA,mBAAA;AfmuBJ;;AepqBU;EAhEN,cAAA;EACA,WAAA;AfwuBJ;;AejqBY;EAxDV,wBAAA;Af6tBF;;AerqBY;EAxDV,yBAAA;AfiuBF;;AezqBY;EAxDV,gBAAA;AfquBF;;Ae7qBY;EAxDV,yBAAA;AfyuBF;;AejrBY;EAxDV,yBAAA;Af6uBF;;AerrBY;EAxDV,gBAAA;AfivBF;;AezrBY;EAxDV,yBAAA;AfqvBF;;Ae7rBY;EAxDV,yBAAA;AfyvBF;;AejsBY;EAxDV,gBAAA;Af6vBF;;AersBY;EAxDV,yBAAA;AfiwBF;;AezsBY;EAxDV,yBAAA;AfqwBF;;AelsBQ;;EAEE,gBAAA;AfqsBV;;AelsBQ;;EAEE,gBAAA;AfqsBV;;Ae5sBQ;;EAEE,sBAAA;Af+sBV;;Ae5sBQ;;EAEE,sBAAA;Af+sBV;;AettBQ;;EAEE,qBAAA;AfytBV;;AettBQ;;EAEE,qBAAA;AfytBV;;AehuBQ;;EAEE,mBAAA;AfmuBV;;AehuBQ;;EAEE,mBAAA;AfmuBV;;Ae1uBQ;;EAEE,qBAAA;Af6uBV;;Ae1uBQ;;EAEE,qBAAA;Af6uBV;;AepvBQ;;EAEE,mBAAA;AfuvBV;;AepvBQ;;EAEE,mBAAA;AfuvBV;;AajzBI;EEUE;IACE,YAAA;Ef2yBN;;EexyBI;IApCJ,cAAA;IACA,WAAA;Efg1BA;;Eel0BA;IACE,cAAA;IACA,WAAA;Efq0BF;;Eev0BA;IACE,cAAA;IACA,UAAA;Ef00BF;;Ee50BA;IACE,cAAA;IACA,qBAAA;Ef+0BF;;Eej1BA;IACE,cAAA;IACA,UAAA;Efo1BF;;Eet1BA;IACE,cAAA;IACA,UAAA;Efy1BF;;Ee31BA;IACE,cAAA;IACA,qBAAA;Ef81BF;;Ee/zBI;IAhDJ,cAAA;IACA,WAAA;Efm3BA;;Ee9zBQ;IAhEN,cAAA;IACA,kBAAA;Efk4BF;;Een0BQ;IAhEN,cAAA;IACA,mBAAA;Efu4BF;;Eex0BQ;IAhEN,cAAA;IACA,UAAA;Ef44BF;;Ee70BQ;IAhEN,cAAA;IACA,mBAAA;Efi5BF;;Eel1BQ;IAhEN,cAAA;IACA,mBAAA;Efs5BF;;Eev1BQ;IAhEN,cAAA;IACA,UAAA;Ef25BF;;Ee51BQ;IAhEN,cAAA;IACA,mBAAA;Efg6BF;;Eej2BQ;IAhEN,cAAA;IACA,mBAAA;Efq6BF;;Eet2BQ;IAhEN,cAAA;IACA,UAAA;Ef06BF;;Ee32BQ;IAhEN,cAAA;IACA,mBAAA;Ef+6BF;;Eeh3BQ;IAhEN,cAAA;IACA,mBAAA;Efo7BF;;Eer3BQ;IAhEN,cAAA;IACA,WAAA;Efy7BF;;Eel3BU;IAxDV,cAAA;Ef86BA;;Eet3BU;IAxDV,wBAAA;Efk7BA;;Ee13BU;IAxDV,yBAAA;Efs7BA;;Ee93BU;IAxDV,gBAAA;Ef07BA;;Eel4BU;IAxDV,yBAAA;Ef87BA;;Eet4BU;IAxDV,yBAAA;Efk8BA;;Ee14BU;IAxDV,gBAAA;Efs8BA;;Ee94BU;IAxDV,yBAAA;Ef08BA;;Eel5BU;IAxDV,yBAAA;Ef88BA;;Eet5BU;IAxDV,gBAAA;Efk9BA;;Ee15BU;IAxDV,yBAAA;Efs9BA;;Ee95BU;IAxDV,yBAAA;Ef09BA;;Eev5BM;;IAEE,gBAAA;Ef05BR;;Eev5BM;;IAEE,gBAAA;Ef05BR;;Eej6BM;;IAEE,sBAAA;Efo6BR;;Eej6BM;;IAEE,sBAAA;Efo6BR;;Ee36BM;;IAEE,qBAAA;Ef86BR;;Ee36BM;;IAEE,qBAAA;Ef86BR;;Eer7BM;;IAEE,mBAAA;Efw7BR;;Eer7BM;;IAEE,mBAAA;Efw7BR;;Ee/7BM;;IAEE,qBAAA;Efk8BR;;Ee/7BM;;IAEE,qBAAA;Efk8BR;;Eez8BM;;IAEE,mBAAA;Ef48BR;;Eez8BM;;IAEE,mBAAA;Ef48BR;AACF;AavgCI;EEUE;IACE,YAAA;EfggCN;;Ee7/BI;IApCJ,cAAA;IACA,WAAA;EfqiCA;;EevhCA;IACE,cAAA;IACA,WAAA;Ef0hCF;;Ee5hCA;IACE,cAAA;IACA,UAAA;Ef+hCF;;EejiCA;IACE,cAAA;IACA,qBAAA;EfoiCF;;EetiCA;IACE,cAAA;IACA,UAAA;EfyiCF;;Ee3iCA;IACE,cAAA;IACA,UAAA;Ef8iCF;;EehjCA;IACE,cAAA;IACA,qBAAA;EfmjCF;;EephCI;IAhDJ,cAAA;IACA,WAAA;EfwkCA;;EenhCQ;IAhEN,cAAA;IACA,kBAAA;EfulCF;;EexhCQ;IAhEN,cAAA;IACA,mBAAA;Ef4lCF;;Ee7hCQ;IAhEN,cAAA;IACA,UAAA;EfimCF;;EeliCQ;IAhEN,cAAA;IACA,mBAAA;EfsmCF;;EeviCQ;IAhEN,cAAA;IACA,mBAAA;Ef2mCF;;Ee5iCQ;IAhEN,cAAA;IACA,UAAA;EfgnCF;;EejjCQ;IAhEN,cAAA;IACA,mBAAA;EfqnCF;;EetjCQ;IAhEN,cAAA;IACA,mBAAA;Ef0nCF;;Ee3jCQ;IAhEN,cAAA;IACA,UAAA;Ef+nCF;;EehkCQ;IAhEN,cAAA;IACA,mBAAA;EfooCF;;EerkCQ;IAhEN,cAAA;IACA,mBAAA;EfyoCF;;Ee1kCQ;IAhEN,cAAA;IACA,WAAA;Ef8oCF;;EevkCU;IAxDV,cAAA;EfmoCA;;Ee3kCU;IAxDV,wBAAA;EfuoCA;;Ee/kCU;IAxDV,yBAAA;Ef2oCA;;EenlCU;IAxDV,gBAAA;Ef+oCA;;EevlCU;IAxDV,yBAAA;EfmpCA;;Ee3lCU;IAxDV,yBAAA;EfupCA;;Ee/lCU;IAxDV,gBAAA;Ef2pCA;;EenmCU;IAxDV,yBAAA;Ef+pCA;;EevmCU;IAxDV,yBAAA;EfmqCA;;Ee3mCU;IAxDV,gBAAA;EfuqCA;;Ee/mCU;IAxDV,yBAAA;Ef2qCA;;EennCU;IAxDV,yBAAA;Ef+qCA;;Ee5mCM;;IAEE,gBAAA;Ef+mCR;;Ee5mCM;;IAEE,gBAAA;Ef+mCR;;EetnCM;;IAEE,sBAAA;EfynCR;;EetnCM;;IAEE,sBAAA;EfynCR;;EehoCM;;IAEE,qBAAA;EfmoCR;;EehoCM;;IAEE,qBAAA;EfmoCR;;Ee1oCM;;IAEE,mBAAA;Ef6oCR;;Ee1oCM;;IAEE,mBAAA;Ef6oCR;;EeppCM;;IAEE,qBAAA;EfupCR;;EeppCM;;IAEE,qBAAA;EfupCR;;Ee9pCM;;IAEE,mBAAA;EfiqCR;;Ee9pCM;;IAEE,mBAAA;EfiqCR;AACF;Aa5tCI;EEUE;IACE,YAAA;EfqtCN;;EeltCI;IApCJ,cAAA;IACA,WAAA;Ef0vCA;;Ee5uCA;IACE,cAAA;IACA,WAAA;Ef+uCF;;EejvCA;IACE,cAAA;IACA,UAAA;EfovCF;;EetvCA;IACE,cAAA;IACA,qBAAA;EfyvCF;;Ee3vCA;IACE,cAAA;IACA,UAAA;Ef8vCF;;EehwCA;IACE,cAAA;IACA,UAAA;EfmwCF;;EerwCA;IACE,cAAA;IACA,qBAAA;EfwwCF;;EezuCI;IAhDJ,cAAA;IACA,WAAA;Ef6xCA;;EexuCQ;IAhEN,cAAA;IACA,kBAAA;Ef4yCF;;Ee7uCQ;IAhEN,cAAA;IACA,mBAAA;EfizCF;;EelvCQ;IAhEN,cAAA;IACA,UAAA;EfszCF;;EevvCQ;IAhEN,cAAA;IACA,mBAAA;Ef2zCF;;Ee5vCQ;IAhEN,cAAA;IACA,mBAAA;Efg0CF;;EejwCQ;IAhEN,cAAA;IACA,UAAA;Efq0CF;;EetwCQ;IAhEN,cAAA;IACA,mBAAA;Ef00CF;;Ee3wCQ;IAhEN,cAAA;IACA,mBAAA;Ef+0CF;;EehxCQ;IAhEN,cAAA;IACA,UAAA;Efo1CF;;EerxCQ;IAhEN,cAAA;IACA,mBAAA;Efy1CF;;Ee1xCQ;IAhEN,cAAA;IACA,mBAAA;Ef81CF;;Ee/xCQ;IAhEN,cAAA;IACA,WAAA;Efm2CF;;Ee5xCU;IAxDV,cAAA;Efw1CA;;EehyCU;IAxDV,wBAAA;Ef41CA;;EepyCU;IAxDV,yBAAA;Efg2CA;;EexyCU;IAxDV,gBAAA;Efo2CA;;Ee5yCU;IAxDV,yBAAA;Efw2CA;;EehzCU;IAxDV,yBAAA;Ef42CA;;EepzCU;IAxDV,gBAAA;Efg3CA;;EexzCU;IAxDV,yBAAA;Efo3CA;;Ee5zCU;IAxDV,yBAAA;Efw3CA;;Eeh0CU;IAxDV,gBAAA;Ef43CA;;Eep0CU;IAxDV,yBAAA;Efg4CA;;Eex0CU;IAxDV,yBAAA;Efo4CA;;Eej0CM;;IAEE,gBAAA;Efo0CR;;Eej0CM;;IAEE,gBAAA;Efo0CR;;Ee30CM;;IAEE,sBAAA;Ef80CR;;Ee30CM;;IAEE,sBAAA;Ef80CR;;Eer1CM;;IAEE,qBAAA;Efw1CR;;Eer1CM;;IAEE,qBAAA;Efw1CR;;Ee/1CM;;IAEE,mBAAA;Efk2CR;;Ee/1CM;;IAEE,mBAAA;Efk2CR;;Eez2CM;;IAEE,qBAAA;Ef42CR;;Eez2CM;;IAEE,qBAAA;Ef42CR;;Een3CM;;IAEE,mBAAA;Efs3CR;;Een3CM;;IAEE,mBAAA;Efs3CR;AACF;Aaj7CI;EEUE;IACE,YAAA;Ef06CN;;Eev6CI;IApCJ,cAAA;IACA,WAAA;Ef+8CA;;Eej8CA;IACE,cAAA;IACA,WAAA;Efo8CF;;Eet8CA;IACE,cAAA;IACA,UAAA;Efy8CF;;Ee38CA;IACE,cAAA;IACA,qBAAA;Ef88CF;;Eeh9CA;IACE,cAAA;IACA,UAAA;Efm9CF;;Eer9CA;IACE,cAAA;IACA,UAAA;Efw9CF;;Ee19CA;IACE,cAAA;IACA,qBAAA;Ef69CF;;Ee97CI;IAhDJ,cAAA;IACA,WAAA;Efk/CA;;Ee77CQ;IAhEN,cAAA;IACA,kBAAA;EfigDF;;Eel8CQ;IAhEN,cAAA;IACA,mBAAA;EfsgDF;;Eev8CQ;IAhEN,cAAA;IACA,UAAA;Ef2gDF;;Ee58CQ;IAhEN,cAAA;IACA,mBAAA;EfghDF;;Eej9CQ;IAhEN,cAAA;IACA,mBAAA;EfqhDF;;Eet9CQ;IAhEN,cAAA;IACA,UAAA;Ef0hDF;;Ee39CQ;IAhEN,cAAA;IACA,mBAAA;Ef+hDF;;Eeh+CQ;IAhEN,cAAA;IACA,mBAAA;EfoiDF;;Eer+CQ;IAhEN,cAAA;IACA,UAAA;EfyiDF;;Ee1+CQ;IAhEN,cAAA;IACA,mBAAA;Ef8iDF;;Ee/+CQ;IAhEN,cAAA;IACA,mBAAA;EfmjDF;;Eep/CQ;IAhEN,cAAA;IACA,WAAA;EfwjDF;;Eej/CU;IAxDV,cAAA;Ef6iDA;;Eer/CU;IAxDV,wBAAA;EfijDA;;Eez/CU;IAxDV,yBAAA;EfqjDA;;Ee7/CU;IAxDV,gBAAA;EfyjDA;;EejgDU;IAxDV,yBAAA;Ef6jDA;;EergDU;IAxDV,yBAAA;EfikDA;;EezgDU;IAxDV,gBAAA;EfqkDA;;Ee7gDU;IAxDV,yBAAA;EfykDA;;EejhDU;IAxDV,yBAAA;Ef6kDA;;EerhDU;IAxDV,gBAAA;EfilDA;;EezhDU;IAxDV,yBAAA;EfqlDA;;Ee7hDU;IAxDV,yBAAA;EfylDA;;EethDM;;IAEE,gBAAA;EfyhDR;;EethDM;;IAEE,gBAAA;EfyhDR;;EehiDM;;IAEE,sBAAA;EfmiDR;;EehiDM;;IAEE,sBAAA;EfmiDR;;Ee1iDM;;IAEE,qBAAA;Ef6iDR;;Ee1iDM;;IAEE,qBAAA;Ef6iDR;;EepjDM;;IAEE,mBAAA;EfujDR;;EepjDM;;IAEE,mBAAA;EfujDR;;Ee9jDM;;IAEE,qBAAA;EfikDR;;Ee9jDM;;IAEE,qBAAA;EfikDR;;EexkDM;;IAEE,mBAAA;Ef2kDR;;EexkDM;;IAEE,mBAAA;Ef2kDR;AACF;AatoDI;EEUE;IACE,YAAA;Ef+nDN;;Ee5nDI;IApCJ,cAAA;IACA,WAAA;EfoqDA;;EetpDA;IACE,cAAA;IACA,WAAA;EfypDF;;Ee3pDA;IACE,cAAA;IACA,UAAA;Ef8pDF;;EehqDA;IACE,cAAA;IACA,qBAAA;EfmqDF;;EerqDA;IACE,cAAA;IACA,UAAA;EfwqDF;;Ee1qDA;IACE,cAAA;IACA,UAAA;Ef6qDF;;Ee/qDA;IACE,cAAA;IACA,qBAAA;EfkrDF;;EenpDI;IAhDJ,cAAA;IACA,WAAA;EfusDA;;EelpDQ;IAhEN,cAAA;IACA,kBAAA;EfstDF;;EevpDQ;IAhEN,cAAA;IACA,mBAAA;Ef2tDF;;Ee5pDQ;IAhEN,cAAA;IACA,UAAA;EfguDF;;EejqDQ;IAhEN,cAAA;IACA,mBAAA;EfquDF;;EetqDQ;IAhEN,cAAA;IACA,mBAAA;Ef0uDF;;Ee3qDQ;IAhEN,cAAA;IACA,UAAA;Ef+uDF;;EehrDQ;IAhEN,cAAA;IACA,mBAAA;EfovDF;;EerrDQ;IAhEN,cAAA;IACA,mBAAA;EfyvDF;;Ee1rDQ;IAhEN,cAAA;IACA,UAAA;Ef8vDF;;Ee/rDQ;IAhEN,cAAA;IACA,mBAAA;EfmwDF;;EepsDQ;IAhEN,cAAA;IACA,mBAAA;EfwwDF;;EezsDQ;IAhEN,cAAA;IACA,WAAA;Ef6wDF;;EetsDU;IAxDV,cAAA;EfkwDA;;Ee1sDU;IAxDV,wBAAA;EfswDA;;Ee9sDU;IAxDV,yBAAA;Ef0wDA;;EeltDU;IAxDV,gBAAA;Ef8wDA;;EettDU;IAxDV,yBAAA;EfkxDA;;Ee1tDU;IAxDV,yBAAA;EfsxDA;;Ee9tDU;IAxDV,gBAAA;Ef0xDA;;EeluDU;IAxDV,yBAAA;Ef8xDA;;EetuDU;IAxDV,yBAAA;EfkyDA;;Ee1uDU;IAxDV,gBAAA;EfsyDA;;Ee9uDU;IAxDV,yBAAA;Ef0yDA;;EelvDU;IAxDV,yBAAA;Ef8yDA;;Ee3uDM;;IAEE,gBAAA;Ef8uDR;;Ee3uDM;;IAEE,gBAAA;Ef8uDR;;EervDM;;IAEE,sBAAA;EfwvDR;;EervDM;;IAEE,sBAAA;EfwvDR;;Ee/vDM;;IAEE,qBAAA;EfkwDR;;Ee/vDM;;IAEE,qBAAA;EfkwDR;;EezwDM;;IAEE,mBAAA;Ef4wDR;;EezwDM;;IAEE,mBAAA;Ef4wDR;;EenxDM;;IAEE,qBAAA;EfsxDR;;EenxDM;;IAEE,qBAAA;EfsxDR;;Ee7xDM;;IAEE,mBAAA;EfgyDR;;Ee7xDM;;IAEE,mBAAA;EfgyDR;AACF;AgBt5DA;EACE,0BAAA;EACA,iCAAA;EACA,iCAAA;EACA,0CAAA;EACA,gCAAA;EACA,wCAAA;EACA,+BAAA;EACA,yCAAA;EAEA,WAAA;EACA,mBXuWO;EWtWP,cXCS;EWAT,mBXkqB4B;EWjqB5B,qBXPS;AL85DX;AgBh5DE;EACE,sBAAA;EACA,oCAAA;EACA,wBXye0B;EWxe1B,wDAAA;AhBk5DJ;AgB/4DE;EACE,uBAAA;AhBi5DJ;AgB94DE;EACE,sBAAA;AhBg5DJ;AgB54DE;EACE,kCAAA;AhB84DJ;;AgBr4DA;EACE,iBAAA;AhBw4DF;;AgB93DE;EACE,wBAAA;AhBi4DJ;;AgBl3DE;EACE,mBAAA;AhBq3DJ;AgBl3DI;EACE,mBAAA;AhBo3DN;;AgB72DE;EACE,sBAAA;AhBg3DJ;AgB72DE;EACE,mBAAA;AhB+2DJ;;AgBt2DE;EACE,gDAAA;EACA,oCAAA;AhBy2DJ;;AgBj2DA;EACE,+CAAA;EACA,mCAAA;AhBo2DF;;AgB51DE;EACE,8CAAA;EACA,kCAAA;AhB+1DJ;;AiB39DE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBw9DJ;;AiBv+DE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBo+DJ;;AiBn/DE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBg/DJ;;AiB//DE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjB4/DJ;;AiB3gEE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBwgEJ;;AiBvhEE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBohEJ;;AiBniEE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjBgiEJ;;AiB/iEE;EAME,sBAAA;EACA,8BAAA;EACA,8BAAA;EACA,6BAAA;EACA,6BAAA;EACA,4BAAA;EACA,4BAAA;EAEA,WAbQ;EAcR,qBAAA;AjB4iEJ;;AgBx6DI;EACE,gBAAA;EACA,iCAAA;AhB26DN;;Aat/DI;EGyEA;IACE,gBAAA;IACA,iCAAA;EhBi7DJ;AACF;Aa7/DI;EGyEA;IACE,gBAAA;IACA,iCAAA;EhBu7DJ;AACF;AangEI;EGyEA;IACE,gBAAA;IACA,iCAAA;EhB67DJ;AACF;AazgEI;EGyEA;IACE,gBAAA;IACA,iCAAA;EhBm8DJ;AACF;Aa/gEI;EGyEA;IACE,gBAAA;IACA,iCAAA;EhBy8DJ;AACF;AkB7lEA;EACE,qBbwzBsC;ALuyCxC;;AkBtlEA;EACE,iCAAA;EACA,oCAAA;EACA,gBAAA;EdoRI,kBALI;Ec3QR,gBbgkB4B;ALuhD9B;;AkBnlEA;EACE,+BAAA;EACA,kCAAA;Ed0QI,kBALI;AJk1DV;;AkBnlEA;EACE,gCAAA;EACA,mCAAA;EdoQI,mBALI;AJw1DV;;AmBpnEA;EACE,mBdgzBsC;EDhhBlC,kBALI;EevRR,cdKS;ALgnEX;;AoB1nEA;EACE,cAAA;EACA,WAAA;EACA,yBAAA;EhB8RI,eALI;EgBtRR,gBfqkB4B;EepkB5B,gBf0kB4B;EezkB5B,cfKS;EeJT,sBfLS;EeMT,4BAAA;EACA,yBAAA;EACA,wBAAA;EAAA,qBAAA;EAAA,gBAAA;EdGE,sBAAA;EeHE,wEDMJ;ApBwnEF;AqB1nEM;EDhBN;ICiBQ,gBAAA;ErB6nEN;AACF;AoB3nEE;EACE,gBAAA;ApB6nEJ;AoB3nEI;EACE,eAAA;ApB6nEN;AoBxnEE;EACE,cfjBO;EekBP,sBf3BO;Ee4BP,qBf8zBoC;Ee7zBpC,UAAA;EAKE,kDfusB0B;AL+6ChC;AoB/mEE;EAEE,aAAA;ApBgnEJ;AoB5mEE;EACE,cf1CO;Ee4CP,UAAA;ApB6mEJ;AoBhnEE;EACE,cf1CO;Ee4CP,UAAA;ApB6mEJ;AoBrmEE;EAEE,yBf1DO;Ee6DP,UAAA;ApBomEJ;AoBhmEE;EACE,yBAAA;EACA,0BAAA;EACA,2Bf0pB0B;Ee1pB1B,0Bf0pB0B;EezpB1B,cf9DO;EiBbT,yBjBMS;EeuEP,oBAAA;EACA,qBAAA;EACA,mBAAA;EACA,eAAA;EACA,4Bfgb0B;Ee/a1B,gBAAA;ECtEE,6IDuEF;ECvEE,qIDuEF;ApBkmEJ;AoB9mEE;EACE,yBAAA;EACA,0BAAA;EACA,2Bf0pB0B;Ee1pB1B,0Bf0pB0B;EezpB1B,cf9DO;EiBbT,yBjBMS;EeuEP,oBAAA;EACA,qBAAA;EACA,mBAAA;EACA,eAAA;EACA,4Bfgb0B;Ee/a1B,gBAAA;ECtEE,qIDuEF;ApBkmEJ;AqBrqEM;EDuDJ;ICtDM,wBAAA;IAAA,gBAAA;ErBwqEN;EoBlnEA;ICtDM,gBAAA;ErBwqEN;AACF;AoBpmEE;EACE,yBf+5B8B;ALusClC;AoBvmEE;EACE,yBf+5B8B;ALusClC;AoBnmEE;EACE,yBAAA;EACA,0BAAA;EACA,2BfuoB0B;EevoB1B,0BfuoB0B;EetoB1B,cfjFO;EiBbT,yBjBMS;Ee0FP,oBAAA;EACA,qBAAA;EACA,mBAAA;EACA,eAAA;EACA,4Bf6Z0B;Ee5Z1B,gBAAA;ECzFE,6ID0FF;EC1FE,qID0FF;ApBqmEJ;AqB3rEM;ED0EJ;ICzEM,wBAAA;IAAA,gBAAA;ErB8rEN;AACF;AoBvmEE;EACE,yBf44B8B;AL6tClC;;AoBhmEA;EACE,cAAA;EACA,WAAA;EACA,mBAAA;EACA,gBAAA;EACA,gBfyd4B;Eexd5B,cf5GS;Ee6GT,6BAAA;EACA,yBAAA;EACA,mBAAA;ApBmmEF;AoBjmEE;EAEE,gBAAA;EACA,eAAA;ApBkmEJ;;AoBvlEA;EACE,sCfguBsC;Ee/tBtC,uBAAA;EhBmJI,mBALI;EE7QN,qBAAA;AN2tEJ;AoBxlEE;EACE,uBAAA;EACA,wBAAA;EACA,0Bf2lB0B;Ee3lB1B,yBf2lB0B;AL+/C9B;AoB7lEE;EACE,uBAAA;EACA,wBAAA;EACA,0Bf2lB0B;Ee3lB1B,yBf2lB0B;AL+/C9B;AoBvlEE;EACE,uBAAA;EACA,wBAAA;EACA,0BfqlB0B;EerlB1B,yBfqlB0B;ALogD9B;;AoBrlEA;EACE,oCf8sBsC;Ee7sBtC,oBAAA;EhBgII,kBALI;EE7QN,qBAAA;AN4uEJ;AoBtlEE;EACE,oBAAA;EACA,qBAAA;EACA,wBf4kB0B;Ee5kB1B,uBf4kB0B;AL4gD9B;AoB3lEE;EACE,oBAAA;EACA,qBAAA;EACA,wBf4kB0B;Ee5kB1B,uBf4kB0B;AL4gD9B;AoBrlEE;EACE,oBAAA;EACA,qBAAA;EACA,wBfskB0B;EetkB1B,uBfskB0B;ALihD9B;;AoB/kEE;EACE,uCfqrBoC;AL65CxC;AoB/kEE;EACE,sCfkrBoC;AL+5CxC;AoB9kEE;EACE,oCf+qBoC;ALi6CxC;;AoB3kEA;EACE,Wf6qBsC;Ee5qBtC,YAAA;EACA,iBf4hB4B;ALkjD9B;AoB5kEE;EACE,eAAA;ApB8kEJ;AoB3kEE;EACE,aAAA;Ed/LA,sBAAA;AN6wEJ;AoB1kEE;EACE,aAAA;EdpMA,sBAAA;ANixEJ;;AuB/xEA;EACE,cAAA;EACA,WAAA;EACA,0CAAA;EAEA,uCAAA;EnB2RI,eALI;EmBnRR,gBlBkkB4B;EkBjkB5B,gBlBukB4B;EkBtkB5B,clBES;EkBDT,sBlBRS;EkBST,iPAAA;EACA,4BAAA;EACA,yClBg7BkC;EkB/6BlC,0BlBg7BkC;EkB/6BlC,yBAAA;EjBFE,sBAAA;EeHE,wEEQJ;EACA,wBAAA;EAAA,qBAAA;EAAA,gBAAA;AvB+xEF;AqBpyEM;EEfN;IFgBQ,gBAAA;ErBuyEN;AACF;AuBlyEE;EACE,qBlBs0BoC;EkBr0BpC,UAAA;EAKE,kDlBi7B4B;AL+2ClC;AuB5xEE;EAEE,sBlBgsB0B;EkB/rB1B,sBAAA;AvB6xEJ;AuB1xEE;EAEE,yBlBpCO;AL+zEX;AuBtxEE;EACE,kBAAA;EACA,0BAAA;AvBwxEJ;;AuBpxEA;EACE,oBlByrB4B;EkBxrB5B,uBlBwrB4B;EkBvrB5B,oBlBwrB4B;ED/cxB,mBALI;EE7QN,qBAAA;ANk0EJ;;AuBpxEA;EACE,mBlBqrB4B;EkBprB5B,sBlBorB4B;EkBnrB5B,kBlBorB4B;EDndxB,kBALI;EE7QN,qBAAA;AN00EJ;;AwBz1EA;EACE,cAAA;EACA,kBnBq3BwC;EmBp3BxC,mBnBq3BwC;EmBp3BxC,uBnBq3BwC;ALu+C1C;AwB11EE;EACE,WAAA;EACA,mBAAA;AxB41EJ;;AwBx1EA;EACE,UnBy2BwC;EmBx2BxC,WnBw2BwC;EmBv2BxC,kBAAA;EACA,mBAAA;EACA,sBnBbS;EmBcT,4BAAA;EACA,2BAAA;EACA,wBAAA;EACA,qCnB42BwC;EmB32BxC,wBAAA;EAAA,qBAAA;EAAA,gBAAA;EACA,iCAAA;EAAA,mBAAA;AxB21EF;AwBx1EE;ElBXE,qBAAA;ANs2EJ;AwBv1EE;EAEE,kBnBm2BsC;ALq/C1C;AwBr1EE;EACE,uBnB01BsC;AL6/C1C;AwBp1EE;EACE,qBnBszBoC;EmBrzBpC,UAAA;EACA,kDnBmsB4B;ALmpDhC;AwBn1EE;EACE,yBnBZM;EmBaN,qBnBbM;ALk2EV;AwBn1EI;EAII,+OAAA;AxBk1ER;AwB90EI;EAII,uJAAA;AxB60ER;AwBx0EE;EACE,yBnBjCM;EmBkCN,qBnBlCM;EmBuCJ,yOAAA;AxBs0EN;AwBl0EE;EACE,oBAAA;EACA,YAAA;EACA,YnBk0BuC;ALkgD3C;AwB7zEI;EACE,YnB0zBqC;ALqgD3C;;AwBjzEA;EACE,mBnBqzBgC;AL+/ClC;AwBlzEE;EACE,UnBizB8B;EmBhzB9B,mBAAA;EACA,wKAAA;EACA,gCAAA;ElB9FA,kBAAA;EeHE,iDGmGF;AxBozEJ;AqBn5EM;EGyFJ;IHxFM,gBAAA;ErBs5EN;AACF;AwBvzEI;EACE,0JAAA;AxByzEN;AwBtzEI;EACE,iCnBgzB4B;EmB3yB1B,uJAAA;AxBozER;;AwB9yEA;EACE,qBAAA;EACA,kBnBmxBgC;AL8hDlC;;AwB9yEA;EACE,kBAAA;EACA,sBAAA;EACA,oBAAA;AxBizEF;AwB7yEI;EACE,oBAAA;EACA,YAAA;EACA,anBqoBwB;AL0qD9B;;AyB77EA;EACE,WAAA;EACA,cAAA;EACA,UAAA;EACA,6BAAA;EACA,wBAAA;EAAA,qBAAA;EAAA,gBAAA;AzBg8EF;AyB97EE;EACE,UAAA;AzBg8EJ;AyB57EI;EAA0B,kEpB89Ba;ALi+C3C;AyB97EI;EAA0B,kEpB69Ba;ALo+C3C;AyB97EE;EACE,SAAA;AzBg8EJ;AyB77EE;EACE,WpB+8BuC;EoB98BvC,YpB88BuC;EoB78BvC,oBAAA;EHzBF,yBjBkCQ;EoBPN,SpB88BuC;EC19BvC,mBAAA;EeHE,oHIkBF;EJlBE,4GIkBF;EACA,wBAAA;EAAA,gBAAA;AzB87EJ;AqB78EM;EIMJ;IJLM,wBAAA;IAAA,gBAAA;ErBg9EN;AACF;AyBj8EI;EHjCF,yBjB8+ByC;ALu/C3C;AyB/7EE;EACE,WpBw7B8B;EoBv7B9B,cpBw7B8B;EoBv7B9B,kBAAA;EACA,epBu7B8B;EoBt7B9B,yBpBpCO;EoBqCP,yBAAA;EnB7BA,mBAAA;AN+9EJ;AyB77EE;EACE,WpBo7BuC;EoBn7BvC,YpBm7BuC;EiBt+BzC,yBjBkCQ;EoBmBN,SpBo7BuC;EC19BvC,mBAAA;EeHE,iHI4CF;EJ5CE,4GI4CF;EACA,qBAAA;EAAA,gBAAA;AzB87EJ;AqBv+EM;EIiCJ;IJhCM,qBAAA;IAAA,gBAAA;ErB0+EN;AACF;AyBj8EI;EH3DF,yBjB8+ByC;ALihD3C;AyB/7EE;EACE,WpB85B8B;EoB75B9B,cpB85B8B;EoB75B9B,kBAAA;EACA,epB65B8B;EoB55B9B,yBpB9DO;EoB+DP,yBAAA;EnBvDA,mBAAA;ANy/EJ;AyB77EE;EACE,oBAAA;AzB+7EJ;AyB77EI;EACE,yBpBtEK;ALqgFX;AyB57EI;EACE,yBpB1EK;ALwgFX;;A0BrhFA;EACE,kBAAA;A1BwhFF;A0BthFE;;EAEE,0BrBy/B8B;EqBx/B9B,iBrBy/B8B;AL+hDlC;A0BrhFE;EACE,kBAAA;EACA,MAAA;EACA,OAAA;EACA,YAAA;EACA,qBAAA;EACA,oBAAA;EACA,6BAAA;EACA,qBAAA;ELDE,gEKEF;A1BuhFJ;AqBrhFM;EKXJ;ILYM,gBAAA;ErBwhFN;AACF;A0BxhFE;EACE,qBAAA;A1B0hFJ;A0BxhFI;EACE,kBAAA;A1B0hFN;A0B3hFI;EACE,kBAAA;A1B0hFN;A0BvhFI;EAEE,qBrBm+B4B;EqBl+B5B,wBrBm+B4B;ALqjDlC;A0B3hFI;EAEE,qBrBm+B4B;EqBl+B5B,wBrBm+B4B;ALqjDlC;A0BrhFI;EACE,qBrB89B4B;EqB79B5B,wBrB89B4B;ALyjDlC;A0BnhFE;EACE,qBrBw9B8B;EqBv9B9B,wBrBw9B8B;AL6jDlC;A0B/gFI;EACE,arBk9B4B;EqBj9B5B,8DrBk9B4B;ALikDlC;A0BrhFI;;;EACE,arBk9B4B;EqBj9B5B,8DrBk9B4B;ALikDlC;A0B9gFI;EACE,arB28B4B;EqB18B5B,8DrB28B4B;ALqkDlC;;A2BtkFA;EACE,kBAAA;EACA,aAAA;EACA,eAAA;EACA,oBAAA;EACA,WAAA;A3BykFF;A2BvkFE;;EAEE,kBAAA;EACA,cAAA;EACA,SAAA;EACA,YAAA;A3BykFJ;A2BrkFE;;EAEE,UAAA;A3BukFJ;A2BjkFE;EACE,kBAAA;EACA,UAAA;A3BmkFJ;A2BjkFI;EACE,UAAA;A3BmkFN;;A2BxjFA;EACE,aAAA;EACA,mBAAA;EACA,yBAAA;EvBsPI,eALI;EuB/OR,gBtB8hB4B;EsB7hB5B,gBtBmiB4B;EsBliB5B,ctBlCS;EsBmCT,kBAAA;EACA,mBAAA;EACA,yBtB5CS;EsB6CT,yBAAA;ErBpCE,sBAAA;ANgmFJ;;A2BljFA;;;;EAIE,oBAAA;EvBgOI,kBALI;EE7QN,qBAAA;ANymFJ;;A2BljFA;;;;EAIE,uBAAA;EvBuNI,mBALI;EE7QN,qBAAA;ANknFJ;;A2BljFA;;EAEE,mBAAA;A3BqjFF;;A2BxiFI;;ErB/DA,0BAAA;EACA,6BAAA;AN4mFJ;A2BviFI;;ErBtEA,0BAAA;EACA,6BAAA;ANinFJ;A2BjiFE;EACE,iBAAA;ErBpEA,yBAAA;EACA,4BAAA;ANwmFJ;;A4BjoFE;EACE,aAAA;EACA,WAAA;EACA,mBvByxBoC;EDhhBlC,kBALI;EwBjQN,cvB0/BqB;ALyoDzB;;A4BhoFE;EACE,kBAAA;EACA,SAAA;EACA,UAAA;EACA,aAAA;EACA,eAAA;EACA,uBAAA;EACA,kBAAA;ExB4PE,mBALI;EwBpPN,WAvBc;EAwBd,wCAvBiB;EtBHjB,sBAAA;AN6pFJ;;A4B9nFI;;;;EAEE,cAAA;A5BmoFN;;A4BjrFI;EAoDE,qBvB+9BmB;EuB59BjB,oCvB+yBgC;EuB9yBhC,4PAAA;EACA,4BAAA;EACA,2DAAA;EACA,gEAAA;A5B+nFR;A4B5nFM;EACE,qBvBo9BiB;EuBn9BjB,iDA/Ca;A5B6qFrB;;A4B9rFI;EAyEI,oCvB6xBgC;EuB5xBhC,kFAAA;A5BynFR;;A4BnsFI;EAiFE,qBvBk8BmB;ALorDzB;A4BnnFQ;EAEE,uBvB42B8B;EuB32B9B,6dAAA;EACA,+DAAA;EACA,2EAAA;A5BonFV;A4BhnFM;EACE,qBvBq7BiB;EuBp7BjB,iDA9Ea;A5BgsFrB;;A4BjtFI;EAsGE,qBvB66BmB;ALksDzB;A4B7mFM;EACE,yBvB06BiB;ALqsDzB;A4B5mFM;EACE,iDA5Fa;A5B0sFrB;A4B3mFM;EACE,cvBk6BiB;AL2sDzB;;A4BxmFI;EACE,kBAAA;A5B2mFN;;A4BluFI;;;EA+HI,UAAA;A5BymFR;A4BrmFM;;;EACE,UAAA;A5BymFR;;A4B1tFE;EACE,aAAA;EACA,WAAA;EACA,mBvByxBoC;EDhhBlC,kBALI;EwBjQN,cvB0/BqB;ALkuDzB;;A4BztFE;EACE,kBAAA;EACA,SAAA;EACA,UAAA;EACA,aAAA;EACA,eAAA;EACA,uBAAA;EACA,kBAAA;ExB4PE,mBALI;EwBpPN,WAvBc;EAwBd,wCAvBiB;EtBHjB,sBAAA;ANsvFJ;;A4BvtFI;;;;EAEE,cAAA;A5B4tFN;;A4B1wFI;EAoDE,qBvB+9BmB;EuB59BjB,oCvB+yBgC;EuB9yBhC,4UAAA;EACA,4BAAA;EACA,2DAAA;EACA,gEAAA;A5BwtFR;A4BrtFM;EACE,qBvBo9BiB;EuBn9BjB,iDA/Ca;A5BswFrB;;A4BvxFI;EAyEI,oCvB6xBgC;EuB5xBhC,kFAAA;A5BktFR;;A4B5xFI;EAiFE,qBvBk8BmB;AL6wDzB;A4B5sFQ;EAEE,uBvB42B8B;EuB32B9B,6iBAAA;EACA,+DAAA;EACA,2EAAA;A5B6sFV;A4BzsFM;EACE,qBvBq7BiB;EuBp7BjB,iDA9Ea;A5ByxFrB;;A4B1yFI;EAsGE,qBvB66BmB;AL2xDzB;A4BtsFM;EACE,yBvB06BiB;AL8xDzB;A4BrsFM;EACE,iDA5Fa;A5BmyFrB;A4BpsFM;EACE,cvBk6BiB;ALoyDzB;;A4BjsFI;EACE,kBAAA;A5BosFN;;A4B3zFI;;;EAiII,UAAA;A5BgsFR;A4B9rFM;;;EACE,UAAA;A5BksFR;;A6Bx0FA;EACE,qBAAA;EAEA,gBxBwkB4B;EwBvkB5B,gBxB6kB4B;EwB5kB5B,cxBQS;EwBPT,kBAAA;EACA,qBAAA;EAEA,sBAAA;EACA,eAAA;EACA,yBAAA;EAAA,sBAAA;EAAA,iBAAA;EACA,6BAAA;EACA,6BAAA;EC8GA,yBAAA;E1BsKI,eALI;EE7QN,sBAAA;EeHE,qIQGJ;A7B20FF;AqB10FM;EQhBN;IRiBQ,gBAAA;ErB60FN;AACF;A6B90FE;EACE,cxBLO;ALq1FX;A6B50FE;EAEE,UAAA;EACA,kDxBotB4B;ALynEhC;A6B/zFE;EAGE,oBAAA;EACA,axB0uB0B;ALqlE9B;;A6BnzFE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;ALoyFf;A8B31FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9B82FjB;A8B11FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,iDAAA;A9Bu1FN;A8Bn1FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9Bs3FlB;A8B70FI;EAKI,iDAAA;A9B20FR;A8Bt0FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;AL4zFf;;A6Bj1FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;ALk0Ff;A8Bz3FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9B44FjB;A8Bx3FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,kDAAA;A9Bq3FN;A8Bj3FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9Bo5FlB;A8B32FI;EAKI,kDAAA;A9By2FR;A8Bp2FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;AL01Ff;;A6B/2FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;ALg2Ff;A8Bv5FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9B06FjB;A8Bt5FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,iDAAA;A9Bm5FN;A8B/4FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9Bk7FlB;A8Bz4FI;EAKI,iDAAA;A9Bu4FR;A8Bl4FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;ALw3Ff;;A6B74FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;AL83Ff;A8Br7FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9Bw8FjB;A8Bp7FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,iDAAA;A9Bi7FN;A8B76FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9Bg9FlB;A8Bv6FI;EAKI,iDAAA;A9Bq6FR;A8Bh6FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;ALs5Ff;;A6B36FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;AL45Ff;A8Bn9FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9Bs+FjB;A8Bl9FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,gDAAA;A9B+8FN;A8B38FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9B8+FlB;A8Br8FI;EAKI,gDAAA;A9Bm8FR;A8B97FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;ALo7Ff;;A6Bz8FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;AL07Ff;A8Bj/FE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9BogGjB;A8Bh/FE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,gDAAA;A9B6+FN;A8Bz+FE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9B4gGlB;A8Bn+FI;EAKI,gDAAA;A9Bi+FR;A8B59FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;ALk9Ff;;A6Bv+FE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;ALw9Ff;A8B/gGE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9BkiGjB;A8B9gGE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,kDAAA;A9B2gGN;A8BvgGE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9B0iGlB;A8BjgGI;EAKI,kDAAA;A9B+/FR;A8B1/FE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;ALg/Ff;;A6BrgGE;ECvCA,WAXQ;ERLR,yBjB4Ea;EyB1Db,qBzB0Da;ALs/Ff;A8B7iGE;EACE,WAdY;ERRd,yBQMmB;EAkBjB,qBAjBa;A9BgkGjB;A8B5iGE;EAEE,WArBY;ERRd,yBQMmB;EAyBjB,qBAxBa;EA6BX,+CAAA;A9ByiGN;A8BriGE;EAKE,WAlCa;EAmCb,yBArCkB;EAwClB,qBAvCc;A9BwkGlB;A8B/hGI;EAKI,+CAAA;A9B6hGR;A8BxhGE;EAEE,WAjDe;EAkDf,yBzBYW;EyBTX,qBzBSW;AL8gGf;;A6B7hGE;ECmBA,czBJa;EyBKb,qBzBLa;ALmhGf;A8B5gGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;ALwhGf;A8B3gGE;EAEE,iDAAA;A9B4gGJ;A8BzgGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;ALgiGf;A8BrgGI;EAKI,iDAAA;A9BmgGR;A8B9/FE;EAEE,czBvCW;EyBwCX,6BAAA;A9B+/FJ;;A6BtjGE;ECmBA,czBJa;EyBKb,qBzBLa;AL4iGf;A8BriGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;ALijGf;A8BpiGE;EAEE,kDAAA;A9BqiGJ;A8BliGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;ALyjGf;A8B9hGI;EAKI,kDAAA;A9B4hGR;A8BvhGE;EAEE,czBvCW;EyBwCX,6BAAA;A9BwhGJ;;A6B/kGE;ECmBA,czBJa;EyBKb,qBzBLa;ALqkGf;A8B9jGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;AL0kGf;A8B7jGE;EAEE,gDAAA;A9B8jGJ;A8B3jGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;ALklGf;A8BvjGI;EAKI,gDAAA;A9BqjGR;A8BhjGE;EAEE,czBvCW;EyBwCX,6BAAA;A9BijGJ;;A6BxmGE;ECmBA,czBJa;EyBKb,qBzBLa;AL8lGf;A8BvlGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;ALmmGf;A8BtlGE;EAEE,iDAAA;A9BulGJ;A8BplGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;AL2mGf;A8BhlGI;EAKI,iDAAA;A9B8kGR;A8BzkGE;EAEE,czBvCW;EyBwCX,6BAAA;A9B0kGJ;;A6BjoGE;ECmBA,czBJa;EyBKb,qBzBLa;ALunGf;A8BhnGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;AL4nGf;A8B/mGE;EAEE,gDAAA;A9BgnGJ;A8B7mGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;ALooGf;A8BzmGI;EAKI,gDAAA;A9BumGR;A8BlmGE;EAEE,czBvCW;EyBwCX,6BAAA;A9BmmGJ;;A6B1pGE;ECmBA,czBJa;EyBKb,qBzBLa;ALgpGf;A8BzoGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;ALqpGf;A8BxoGE;EAEE,gDAAA;A9ByoGJ;A8BtoGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;AL6pGf;A8BloGI;EAKI,gDAAA;A9BgoGR;A8B3nGE;EAEE,czBvCW;EyBwCX,6BAAA;A9B4nGJ;;A6BnrGE;ECmBA,czBJa;EyBKb,qBzBLa;ALyqGf;A8BlqGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;AL8qGf;A8BjqGE;EAEE,kDAAA;A9BkqGJ;A8B/pGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;ALsrGf;A8B3pGI;EAKI,kDAAA;A9BypGR;A8BppGE;EAEE,czBvCW;EyBwCX,6BAAA;A9BqpGJ;;A6B5sGE;ECmBA,czBJa;EyBKb,qBzBLa;ALksGf;A8B3rGE;EACE,WATY;EAUZ,yBzBTW;EyBUX,qBzBVW;ALusGf;A8B1rGE;EAEE,+CAAA;A9B2rGJ;A8BxrGE;EAKE,WArBa;EAsBb,yBzBxBW;EyByBX,qBzBzBW;AL+sGf;A8BprGI;EAKI,+CAAA;A9BkrGR;A8B7qGE;EAEE,czBvCW;EyBwCX,6BAAA;A9B8qGJ;;A6BztGA;EACE,gBxBigB4B;EwBhgB5B,cxBzCQ;EwB0CR,0BxB6WwC;AL+2F1C;A6B1tGE;EACE,cxB4WsC;ALg3F1C;A6BptGE;EAEE,cxB/EO;ALoyGX;;A6B1sGA;ECuBE,oBAAA;E1BsKI,kBALI;EE7QN,qBAAA;ANqyGJ;;A6B5sGA;ECmBE,uBAAA;E1BsKI,mBALI;EE7QN,qBAAA;AN2yGJ;;A+B9zGA;EVgBM,gCUfJ;A/Bi0GF;AqB9yGM;EUpBN;IVqBQ,gBAAA;ErBizGN;AACF;A+Bp0GE;EACE,UAAA;A/Bs0GJ;;A+Bh0GE;EACE,aAAA;A/Bm0GJ;;A+B/zGA;EACE,SAAA;EACA,gBAAA;EVDI,6BUEJ;A/Bk0GF;AqBh0GM;EULN;IVMQ,gBAAA;ErBm0GN;AACF;A+Br0GE;EACE,QAAA;EACA,YAAA;EVNE,4BUOF;A/Bu0GJ;AqB10GM;EUAJ;IVCM,gBAAA;ErB60GN;AACF;;AgCl2GA;;;;EAIE,kBAAA;AhCq2GF;;AgCl2GA;EACE,mBAAA;AhCq2GF;AiCh1GI;EACE,qBAAA;EACA,oB5BqgBwB;E4BpgBxB,uB5BmgBwB;E4BlgBxB,WAAA;EAhCJ,uBAAA;EACA,qCAAA;EACA,gBAAA;EACA,oCAAA;AjCm3GF;AiC9zGI;EACE,cAAA;AjCg0GN;;AgC32GA;EACE,kBAAA;EACA,a3ByhCkC;E2BxhClC,aAAA;EACA,gB3B+mCkC;E2B9mClC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CA,gBAAA;ErCuwIJ;EqCrwII;IACE,cAAA;IACA,cAAA;ErCuwIN;EqClwIM;I/BpJJ,0BAAA;IACA,6BAAA;ENy5IF;EqCnwIQ;;IAGE,0BAAA;ErCowIV;EqClwIQ;;IAGE,6BAAA;ErCmwIV;EqC/vIM;I/BrJJ,yBAAA;IACA,4BAAA;ENu5IF;EqChwIQ;;IAGE,yBAAA;ErCiwIV;EqC/vIQ;;IAGE,4BAAA;ErCgwIV;AACF;;AsC98IA;EACE,kBAAA;EACA,aAAA;EACA,mBAAA;EACA,WAAA;EACA,qBAAA;ElC4RI,eALI;EkCrRR,cjCMS;EiCLT,gBAAA;EACA,sBjCLS;EiCMT,SAAA;EhCKE,gBAAA;EgCHF,qBAAA;EjBAI,+JiBCJ;AtCi9IF;AqB98IM;EiBhBN;IjBiBQ,gBAAA;ErBi9IN;AACF;AsCp9IE;EACE,cjCyvCsC;EiCxvCtC,yBjCuvCsC;EiCtvCtC,+CAAA;AtCs9IJ;AsCp9II;EACE,iSAAA;EACA,0BjC4vCoC;AL0tG1C;AsCj9IE;EACE,cAAA;EACA,cjCivCsC;EiChvCtC,ejCgvCsC;EiC/uCtC,iBAAA;EACA,WAAA;EACA,iSAAA;EACA,4BAAA;EACA,wBjC2uCsC;EgBlwCpC,sCiBwBF;AtCm9IJ;AqBv+IM;EiBWJ;IjBVM,gBAAA;ErB0+IN;AACF;AsCr9IE;EACE,UAAA;AtCu9IJ;AsCp9IE;EACE,UAAA;EACA,qBjCizBoC;EiChzBpC,UAAA;EACA,kDjC8rB4B;ALwxHhC;;AsCl9IA;EACE,gBAAA;AtCq9IF;;AsCl9IA;EACE,sBjCpDS;EiCqDT,sCAAA;AtCq9IF;AsCn9IE;EhCnCE,+BAAA;EACA,gCAAA;ANy/IJ;AsCp9II;EhCtCA,2CAAA;EACA,4CAAA;AN6/IJ;AsCn9IE;EACE,aAAA;AtCq9IJ;AsCj9IE;EhClCE,mCAAA;EACA,kCAAA;ANs/IJ;AsCj9IM;EhCtCF,+CAAA;EACA,8CAAA;AN0/IJ;AsCh9II;EhC3CA,mCAAA;EACA,kCAAA;AN8/IJ;;AsC98IA;EACE,qBAAA;AtCi9IF;;AsCx8IE;EACE,eAAA;AtC28IJ;AsCx8IE;EACE,eAAA;EACA,cAAA;EhCxFA,gBAAA;ANmiJJ;AsCx8II;EAAgB,aAAA;AtC28IpB;AsC18II;EAAe,gBAAA;AtC68InB;AsC38II;EhC9FA,gBAAA;AN4iJJ;;AuC/jJA;EACE,aAAA;EACA,eAAA;EACA,YAAA;EACA,mBlCw/CkC;EkCt/ClC,gBAAA;AvCikJF;;AuC1jJE;EACE,oBlC6+CgC;ALglGpC;AuC3jJI;EACE,WAAA;EACA,qBlCy+C8B;EkCx+C9B,clCLK;EkCML,uFAAA;AvC6jJN;AuCzjJE;EACE,clCXO;ALskJX;;AwCplJA;EACE,aAAA;EhCGA,eAAA;EACA,gBAAA;ARqlJF;;AwCrlJA;EACE,kBAAA;EACA,cAAA;EACA,cnC8BQ;EmC7BR,qBAAA;EACA,sBnCFS;EmCGT,yBAAA;EnBKI,qImBJJ;AxCwlJF;AqBhlJM;EmBfN;InBgBQ,gBAAA;ErBmlJN;AACF;AwC3lJE;EACE,UAAA;EACA,cnC+asC;EmC7atC,yBnCRO;EmCSP,qBnCRO;ALomJX;AwCzlJE;EACE,UAAA;EACA,cnCuasC;EmCtatC,yBnCfO;EmCgBP,UnC4qCgC;EmC3qChC,kDnCstB4B;ALq4HhC;;AwCtlJE;EACE,iBnC+pCgC;AL07GpC;AwCtlJE;EACE,UAAA;EACA,WnC9BO;EiBJT,yBjBkCQ;EmCEN,qBnCFM;AL0lJV;AwCrlJE;EACE,cnC9BO;EmC+BP,oBAAA;EACA,sBnCtCO;EmCuCP,qBnCpCO;AL2nJX;;AyCloJE;EACE,yBAAA;AzCqoJJ;;AyC9nJQ;EnCqCJ,+BAAA;EACA,kCAAA;AN6lJJ;AyC7nJQ;EnCiBJ,gCAAA;EACA,mCAAA;AN+mJJ;;AyC/oJE;EACE,uBAAA;ErCgSE,kBALI;AJw3IV;AyC5oJQ;EnCqCJ,8BAAA;EACA,iCAAA;AN0mJJ;AyC1oJQ;EnCiBJ,+BAAA;EACA,kCAAA;AN4nJJ;;AyC5pJE;EACE,uBAAA;ErCgSE,mBALI;AJq4IV;AyCzpJQ;EnCqCJ,8BAAA;EACA,iCAAA;ANunJJ;AyCvpJQ;EnCiBJ,+BAAA;EACA,kCAAA;ANyoJJ;;A0CxqJA;EACE,qBAAA;EACA,sBAAA;EtC8RI,iBALI;EsCvRR,gBrCukB4B;EqCtkB5B,cAAA;EACA,WrCHS;EqCIT,kBAAA;EACA,mBAAA;EACA,wBAAA;EpCKE,sBAAA;ANuqJJ;A0CvqJE;EACE,aAAA;A1CyqJJ;;A0CpqJA;EACE,kBAAA;EACA,SAAA;A1CuqJF;;A2C9rJA;EACE,kBAAA;EACA,kBAAA;EACA,mBtCk6C8B;EsCj6C9B,6BAAA;ErCWE,sBAAA;ANurJJ;;A2C7rJA;EAEE,cAAA;A3C+rJF;;A2C3rJA;EACE,gBtC4jB4B;ALkoI9B;;A2CtrJA;EACE,mBtCm5C8B;ALsyGhC;A2CtrJE;EACE,kBAAA;EACA,MAAA;EACA,QAAA;EACA,UAAA;EACA,qBAAA;A3CwrJJ;;A2CzqJE;EClDA,cD8Cc;ErB5Cd,yBqB0CmB;EC1CnB,qBD2Ce;A3CorJjB;A4C7tJE;EACE,cAAA;A5C+tJJ;;A2ClrJE;EClDA,cD8Cc;ErB5Cd,yBqB0CmB;EC1CnB,qBD2Ce;A3C6rJjB;A4CtuJE;EACE,cAAA;A5CwuJJ;;A2C3rJE;EClDA,cD8Cc;ErB5Cd,yBqB0CmB;EC1CnB,qBD2Ce;A3CssJjB;A4C/uJE;EACE,cAAA;A5CivJJ;;A2CpsJE;EClDA,cDgDgB;ErB9ChB,yBqB0CmB;EC1CnB,qBD2Ce;A3C+sJjB;A4CxvJE;EACE,cAAA;A5C0vJJ;;A2C7sJE;EClDA,cDgDgB;ErB9ChB,yBqB0CmB;EC1CnB,qBD2Ce;A3CwtJjB;A4CjwJE;EACE,cAAA;A5CmwJJ;;A2CttJE;EClDA,cD8Cc;ErB5Cd,yBqB0CmB;EC1CnB,qBD2Ce;A3CiuJjB;A4C1wJE;EACE,cAAA;A5C4wJJ;;A2C/tJE;EClDA,cDgDgB;ErB9ChB,yBqB0CmB;EC1CnB,qBD2Ce;A3C0uJjB;A4CnxJE;EACE,cAAA;A5CqxJJ;;A2CxuJE;EClDA,cD8Cc;ErB5Cd,yBqB0CmB;EC1CnB,qBD2Ce;A3CmvJjB;A4C5xJE;EACE,cAAA;A5C8xJJ;;A6CjyJE;EACE;IAAK,2BxCk7C2B;ELm3GlC;AACF;;A6CvyJE;EACE;IAAK,2BxCk7C2B;ELm3GlC;AACF;A6CjyJA;EACE,aAAA;EACA,YxC26CkC;EwC16ClC,gBAAA;EzCwRI,kBALI;EyCjRR,yBxCLS;ECSP,sBAAA;ANgyJJ;;A6C/xJA;EACE,aAAA;EACA,sBAAA;EACA,uBAAA;EACA,gBAAA;EACA,WxCjBS;EwCkBT,kBAAA;EACA,mBAAA;EACA,yBxCUQ;EgBtBJ,2BwBaJ;A7CkyJF;AqB3yJM;EwBAN;IxBCQ,gBAAA;ErB8yJN;AACF;;A6CpyJA;EvBYE,qMAAA;EuBVA,0BAAA;A7CuyJF;;A6CnyJE;EACE,0DAAA;EAAA,kDAAA;A7CsyJJ;A6CnyJM;EAJJ;IAKM,uBAAA;IAAA,eAAA;E7CsyJN;AACF;;A8C90JA;EACE,aAAA;EACA,sBAAA;EAGA,eAAA;EACA,gBAAA;ExCSE,sBAAA;ANu0JJ;;A8C50JA;EACE,qBAAA;EACA,sBAAA;A9C+0JF;A8C70JE;EAEE,oCAAA;EACA,0BAAA;A9C80JJ;;A8Cp0JA;EACE,WAAA;EACA,czClBS;EyCmBT,mBAAA;A9Cu0JF;A8Cp0JE;EAEE,UAAA;EACA,czCzBO;EyC0BP,qBAAA;EACA,yBzCjCO;ALs2JX;A8Cl0JE;EACE,czC7BO;EyC8BP,yBzCrCO;ALy2JX;;A8C3zJA;EACE,kBAAA;EACA,cAAA;EACA,oBAAA;EACA,czC3CS;EyC4CT,qBAAA;EACA,sBzCtDS;EyCuDT,sCAAA;A9C8zJF;A8C5zJE;ExCrCE,+BAAA;EACA,gCAAA;ANo2JJ;A8C5zJE;ExC3BE,mCAAA;EACA,kCAAA;AN01JJ;A8C5zJE;EAEE,czC7DO;EyC8DP,oBAAA;EACA,sBzCrEO;ALk4JX;A8CzzJE;EACE,UAAA;EACA,WzC3EO;EyC4EP,yBzC9CM;EyC+CN,qBzC/CM;AL02JV;A8CxzJE;EACE,mBAAA;A9C0zJJ;A8CxzJI;EACE,gBAAA;EACA,qBzCwawB;ALk5I9B;;A8C5yJI;EACE,mBAAA;A9C+yJN;A8C5yJQ;ExCrCJ,kCAAA;EAZA,0BAAA;ANi2JJ;A8C3yJQ;ExCtDJ,gCAAA;EAYA,4BAAA;ANy1JJ;A8C1yJQ;EACE,aAAA;A9C4yJV;A8CzyJQ;EACE,qBzCuYoB;EyCtYpB,oBAAA;A9C2yJV;A8CzyJU;EACE,iBAAA;EACA,sBzCkYkB;ALy6I9B;;Aa/2JI;EiC4CA;IACE,mBAAA;E9Cu0JJ;E8Cp0JM;IxCrCJ,kCAAA;IAZA,0BAAA;ENy3JF;E8Cn0JM;IxCtDJ,gCAAA;IAYA,4BAAA;ENi3JF;E8Cl0JM;IACE,aAAA;E9Co0JR;E8Cj0JM;IACE,qBzCuYoB;IyCtYpB,oBAAA;E9Cm0JR;E8Cj0JQ;IACE,iBAAA;IACA,sBzCkYkB;ELi8I5B;AACF;Aax4JI;EiC4CA;IACE,mBAAA;E9C+1JJ;E8C51JM;IxCrCJ,kCAAA;IAZA,0BAAA;ENi5JF;E8C31JM;IxCtDJ,gCAAA;IAYA,4BAAA;ENy4JF;E8C11JM;IACE,aAAA;E9C41JR;E8Cz1JM;IACE,qBzCuYoB;IyCtYpB,oBAAA;E9C21JR;E8Cz1JQ;IACE,iBAAA;IACA,sBzCkYkB;ELy9I5B;AACF;Aah6JI;EiC4CA;IACE,mBAAA;E9Cu3JJ;E8Cp3JM;IxCrCJ,kCAAA;IAZA,0BAAA;ENy6JF;E8Cn3JM;IxCtDJ,gCAAA;IAYA,4BAAA;ENi6JF;E8Cl3JM;IACE,aAAA;E9Co3JR;E8Cj3JM;IACE,qBzCuYoB;IyCtYpB,oBAAA;E9Cm3JR;E8Cj3JQ;IACE,iBAAA;IACA,sBzCkYkB;ELi/I5B;AACF;Aax7JI;EiC4CA;IACE,mBAAA;E9C+4JJ;E8C54JM;IxCrCJ,kCAAA;IAZA,0BAAA;ENi8JF;E8C34JM;IxCtDJ,gCAAA;IAYA,4BAAA;ENy7JF;E8C14JM;IACE,aAAA;E9C44JR;E8Cz4JM;IACE,qBzCuYoB;IyCtYpB,oBAAA;E9C24JR;E8Cz4JQ;IACE,iBAAA;IACA,sBzCkYkB;ELygJ5B;AACF;Aah9JI;EiC4CA;IACE,mBAAA;E9Cu6JJ;E8Cp6JM;IxCrCJ,kCAAA;IAZA,0BAAA;ENy9JF;E8Cn6JM;IxCtDJ,gCAAA;IAYA,4BAAA;ENi9JF;E8Cl6JM;IACE,aAAA;E9Co6JR;E8Cj6JM;IACE,qBzCuYoB;IyCtYpB,oBAAA;E9Cm6JR;E8Cj6JQ;IACE,iBAAA;IACA,sBzCkYkB;ELiiJ5B;AACF;A8Ct5JA;ExC9HI,gBAAA;ANuhKJ;A8Ct5JE;EACE,qBAAA;A9Cw5JJ;A8Ct5JI;EACE,sBAAA;A9Cw5JN;;A+C5iKE;EACE,cDiKyB;EChKzB,yBD+JsB;A9Cg5J1B;A+C5iKM;EAEE,cD2JqB;EC1JrB,yBAAA;A/C6iKR;A+C1iKM;EACE,W1CRG;E0CSH,yBDqJqB;ECpJrB,qBDoJqB;A9Cw5J7B;;A+C1jKE;EACE,cDiKyB;EChKzB,yBD+JsB;A9C85J1B;A+C1jKM;EAEE,cD2JqB;EC1JrB,yBAAA;A/C2jKR;A+CxjKM;EACE,W1CRG;E0CSH,yBDqJqB;ECpJrB,qBDoJqB;A9Cs6J7B;;A+CxkKE;EACE,cDiKyB;EChKzB,yBD+JsB;A9C46J1B;A+CxkKM;EAEE,cD2JqB;EC1JrB,yBAAA;A/CykKR;A+CtkKM;EACE,W1CRG;E0CSH,yBDqJqB;ECpJrB,qBDoJqB;A9Co7J7B;;A+CtlKE;EACE,cDmK2B;EClK3B,yBD+JsB;A9C07J1B;A+CtlKM;EAEE,cD6JuB;EC5JvB,yBAAA;A/CulKR;A+CplKM;EACE,W1CRG;E0CSH,yBDuJuB;ECtJvB,qBDsJuB;A9Cg8J/B;;A+CpmKE;EACE,cDmK2B;EClK3B,yBD+JsB;A9Cw8J1B;A+CpmKM;EAEE,cD6JuB;EC5JvB,yBAAA;A/CqmKR;A+ClmKM;EACE,W1CRG;E0CSH,yBDuJuB;ECtJvB,qBDsJuB;A9C88J/B;;A+ClnKE;EACE,cDiKyB;EChKzB,yBD+JsB;A9Cs9J1B;A+ClnKM;EAEE,cD2JqB;EC1JrB,yBAAA;A/CmnKR;A+ChnKM;EACE,W1CRG;E0CSH,yBDqJqB;ECpJrB,qBDoJqB;A9C89J7B;;A+ChoKE;EACE,cDmK2B;EClK3B,yBD+JsB;A9Co+J1B;A+ChoKM;EAEE,cD6JuB;EC5JvB,yBAAA;A/CioKR;A+C9nKM;EACE,W1CRG;E0CSH,yBDuJuB;ECtJvB,qBDsJuB;A9C0+J/B;;A+C9oKE;EACE,cDiKyB;EChKzB,yBD+JsB;A9Ck/J1B;A+C9oKM;EAEE,cD2JqB;EC1JrB,yBAAA;A/C+oKR;A+C5oKM;EACE,W1CRG;E0CSH,yBDqJqB;ECpJrB,qB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BAAA;AtE+/MZ;;AsEtgNQ;EAOI,gCAAA;AtEmgNZ;;AsE1gNQ;EAOI,gCAAA;AtEugNZ;;AsE9gNQ;EAOI,gCAAA;AtE2gNZ;;AsElhNQ;EAOI,gCAAA;AtE+gNZ;;AsEthNQ;EAOI,gCAAA;AtEmhNZ;;AsE1hNQ;EAOI,gCAAA;AtEuhNZ;;AsE9hNQ;EAOI,gCAAA;AtE2hNZ;;AsEliNQ;EAOI,gCAAA;AtE+hNZ;;AsEtiNQ;EAOI,6BAAA;AtEmiNZ;;AsE1iNQ;EAOI,4BAAA;AtEuiNZ;;AsE9iNQ;EAOI,4BAAA;AtE2iNZ;;AsEljNQ;EAOI,4BAAA;AtE+iNZ;;AsEtjNQ;EAOI,4BAAA;AtEmjNZ;;AsE1jNQ;EAOI,4BAAA;AtEujNZ;;AsE9jNQ;EAOI,qBAAA;AtE2jNZ;;AsElkNQ;EAOI,qBAAA;AtE+jNZ;;AsEtkNQ;EAOI,qBAAA;AtEmkNZ;;AsE1kNQ;EAOI,sBAAA;AtEukNZ;;AsE9kNQ;EAOI,sBAAA;AtE2kNZ;;AsEllNQ;EAOI,0BAAA;AtE+kNZ;;AsEtlNQ;EAOI,uBAAA;AtEmlNZ;;AsE1lNQ;EAOI,2BAAA;AtEulNZ;;AsE9lNQ;EAOI,sBAAA;AtE2lNZ;;AsElmNQ;EAOI,sBAAA;AtE+lNZ;;AsEtmNQ;EAOI,sBAAA;AtEmmNZ;;AsE1mNQ;EAOI,uBAAA;AtEumNZ;;AsE9mNQ;EAOI,uBAAA;AtE2mNZ;;AsElnNQ;EAOI,2BAAA;AtE+mNZ;;AsEtnNQ;EAOI,wBAAA;AtEmnNZ;;AsE1nNQ;EAOI,4BAAA;AtEunNZ;;AsE9nNQ;EAOI,yBAAA;AtE2nNZ;;AsEloNQ;EAOI,8BAAA;AtE+nNZ;;AsEtoNQ;EAOI,iCAAA;AtEmoNZ;;AsE1oNQ;EAOI,sCAAA;AtEuoNZ;;AsE9oNQ;EAOI,yCAAA;AtE2oNZ;;AsElpNQ;EAOI,uBAAA;AtE+oNZ;;AsEtpNQ;EAOI,uBAAA;AtEmpNZ;;AsE1pNQ;EAOI,yBAAA;AtEupNZ;;AsE9pNQ;EAOI,yBAAA;AtE2pNZ;;AsElqNQ;EAOI,0BAAA;AtE+pNZ;;AsEtqNQ;EAOI,4BAAA;AtEmqNZ;;AsE1qNQ;EAOI,kCAAA;AtEuqNZ;;AsE9qNQ;EAOI,iBAAA;AtE2qNZ;;AsElrNQ;EAOI,uBAAA;AtE+qNZ;;AsEtrNQ;EAOI,sBAAA;AtEmrNZ;;AsE1rNQ;EAOI,oBAAA;AtEurNZ;;AsE9rNQ;EAOI,sBAAA;AtE2rNZ;;AsElsNQ;EAOI,oBAAA;AtE+rNZ;;AsEtsNQ;EAOI,sCAAA;AtEmsNZ;;AsE1sNQ;EAOI,oCAAA;AtEusNZ;;AsE9sNQ;EAOI,kCAAA;AtE2sNZ;;AsEltNQ;EAOI,yCAAA;AtE+sNZ;;AsEttNQ;EAOI,wCAAA;AtEmtNZ;;AsE1tNQ;EAOI,wCAAA;AtEutNZ;;AsE9tNQ;EAOI,kCAAA;AtE2tNZ;;AsEluNQ;EAOI,gCAAA;AtE+tNZ;;AsEtuNQ;EAOI,8BAAA;AtEmuNZ;;AsE1uNQ;EAOI,gCAAA;AtEuuNZ;;AsE9uNQ;EAOI,+BAAA;AtE2uNZ;;AsElvNQ;EAOI,oCAAA;AtE+uNZ;;AsEtvNQ;EAOI,kCAAA;AtEmvNZ;;AsE1vNQ;EAOI,gCAAA;AtEuvNZ;;AsE9vNQ;EAOI,uCAAA;AtE2vNZ;;AsElwNQ;EAOI,sCAAA;AtE+vNZ;;AsEtwNQ;EAOI,iCAAA;AtEmwNZ;;AsE1wNQ;EAOI,2BAAA;AtEuwNZ;;AsE9wNQ;EAOI,iCAAA;AtE2wNZ;;AsElxNQ;EAOI,+BAAA;AtE+wNZ;;AsEtxNQ;EAOI,6BAAA;AtEmxNZ;;AsE1xNQ;EAOI,+BAAA;AtEuxNZ;;AsE9xNQ;EAOI,8BAAA;AtE2xNZ;;AsElyNQ;EAOI,oBAAA;AtE+xNZ;;AsEtyNQ;EAOI,mBAAA;AtEmyNZ;;AsE1yNQ;EAOI,mBAAA;AtEuyNZ;;AsE9yNQ;EAOI,mBAAA;AtE2yNZ;;AsElzNQ;EAOI,mBAAA;AtE+yNZ;;AsEtzNQ;EAOI,mBAAA;AtEmzNZ;;AsE1zNQ;EAOI,mBAAA;AtEuzNZ;;AsE9zNQ;EAOI,mBAAA;AtE2zNZ;;AsEl0NQ;EAOI,oBAAA;AtE+zNZ;;AsEt0NQ;EAOI,0BAAA;AtEm0NZ;;AsE10NQ;EAOI,yBAAA;AtEu0NZ;;AsE90NQ;EAOI,uBAAA;AtE20NZ;;AsEl1NQ;EAOI,yBAAA;AtE+0NZ;;AsEt1NQ;EAOI,uBAAA;AtEm1NZ;;AsE11N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OI,uBAAA;EtEooPV;;EsE3oPM;IAOI,uBAAA;EtEwoPV;;EsE/oPM;IAOI,yBAAA;EtE4oPV;;EsEnpPM;IAOI,yBAAA;EtEgpPV;;EsEvpPM;IAOI,0BAAA;EtEopPV;;EsE3pPM;IAOI,4BAAA;EtEwpPV;;EsE/pPM;IAOI,kCAAA;EtE4pPV;;EsEnqPM;IAOI,iBAAA;EtEgqPV;;EsEvqPM;IAOI,uBAAA;EtEoqPV;;EsE3qPM;IAOI,sBAAA;EtEwqPV;;EsE/qPM;IAOI,oBAAA;EtE4qPV;;EsEnrPM;IAOI,sBAAA;EtEgrPV;;EsEvrPM;IAOI,oBAAA;EtEorPV;;EsE3rPM;IAOI,sCAAA;EtEwrPV;;EsE/rPM;IAOI,oCAAA;EtE4rPV;;EsEnsPM;IAOI,kCAAA;EtEgsPV;;EsEvsPM;IAOI,yCAAA;EtEosPV;;EsE3sPM;IAOI,wCAAA;EtEwsPV;;EsE/sPM;IAOI,wCAAA;EtE4sPV;;EsEntPM;IAOI,kCAAA;EtEgtPV;;EsEvtPM;IAOI,gCAAA;EtEotPV;;EsE3tPM;IAOI,8BAAA;EtEwtPV;;EsE/tPM;IAOI,gCAAA;EtE4tPV;;EsEnuPM;IAOI,+BAAA;EtEguPV;;EsEvuPM;IAOI,oCAAA;EtEouPV;;EsE3uPM;IAOI,kCAAA;EtEwuPV;;EsE/uPM;IAOI,gCAAA;EtE4uPV;;EsEnvPM;IAOI,uCAAA;EtEgvPV;;EsEvvPM;IAOI,sCAAA;EtEovPV;;EsE3vPM;IAOI,iCAAA;EtEwvPV;;EsE/vPM;IAOI,2BAAA;EtE4vPV;;EsEnwPM;IAOI,iCAAA;EtEgwPV;;EsEvwPM;IAOI,+BAAA;EtEowPV;;EsE3wPM;IAOI,6BAAA;EtEwwPV;;EsE/wPM;IAOI,+BAAA;EtE4wPV;;EsEnxPM;IAOI,8BAAA;EtEgxPV;;EsEvxPM;IAOI,oBAAA;EtEoxPV;;EsE3xPM;IAOI,mBAAA;EtEwxPV;;EsE/xPM;IAOI,mBAAA;EtE4xPV;;EsEnyPM;IAOI,mBAAA;EtEgyPV;;EsEvyPM;IAOI,mBAAA;EtEoyPV;;EsE3yPM;IAOI,mBAAA;EtEwyPV;;EsE/yPM;IAOI,mBAAA;EtE4yPV;;EsEnzP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tEsnQV;;EsE7nQM;IAOI,gCAAA;EtE0nQV;;EsEjoQM;IAOI,8BAAA;EtE8nQV;;EsEroQM;IAOI,gCAAA;EtEkoQV;;EsEzoQM;IAOI,8BAAA;EtEsoQV;;EsE7oQM;IAOI,4BAAA;EtE0oQV;;EsEjpQM;IAOI,kCAAA;EtE8oQV;;EsErpQM;IAOI,iCAAA;EtEkpQV;;EsEzpQM;IAOI,+BAAA;EtEspQV;;EsE7pQM;IAOI,iCAAA;EtE0pQV;;EsEjqQM;IAOI,+BAAA;EtE8pQV;;EsErqQM;IAOI,0BAAA;EtEkqQV;;EsEzqQM;IAOI,gCAAA;EtEsqQV;;EsE7qQM;IAOI,+BAAA;EtE0qQV;;EsEjrQM;IAOI,6BAAA;EtE8qQV;;EsErrQM;IAOI,+BAAA;EtEkrQV;;EsEzrQM;IAOI,6BAAA;EtEsrQV;;EsE7rQM;IAOI,2BAAA;EtE0rQV;;EsEjsQM;IAOI,4BAAA;EtE8rQV;;EsErsQM;IAOI,6BAAA;EtEksQV;AACF;Aa1sQI;EyDAI;IAOI,sBAAA;EtEusQV;;EsE9sQM;IAOI,uBAAA;EtE2sQV;;EsEltQM;IAOI,sBAAA;EtE+sQV;;EsEttQM;IAOI,0BAAA;EtEmtQV;;EsE1tQM;IAOI,gCAAA;EtEutQV;;EsE9tQM;IAOI,yBAAA;EtE2tQV;;EsEluQM;IAOI,wBAAA;EtE+tQV;;EsEtuQM;IAOI,yBAAA;EtEmuQV;;EsE1uQM;IAOI,6BAAA;EtEuuQV;;EsE9uQM;IAOI,8BAAA;EtE2uQV;;EsElvQM;IAOI,wBAAA;EtE+uQV;;EsEtvQM;IAOI,+BAAA;EtEmvQV;;EsE1vQM;IAOI,wBAAA;EtEuvQV;;EsE9vQM;IAOI,yBAAA;EtE2vQV;;EsElwQM;IAOI,8BAAA;EtE+vQV;;EsEtwQM;IAOI,iCAAA;EtEmwQV;;EsE1wQM;IAOI,sCAAA;EtEuwQV;;EsE9wQM;IAOI,yCAAA;EtE2wQV;;EsElxQM;IAOI,uBAAA;EtE+wQV;;EsEtxQM;IAOI,uBAAA;EtEmxQV;;EsE1xQM;IAOI,yBAAA;EtEuxQV;;EsE9xQM;IAOI,yBAAA;EtE2xQV;;EsElyQM;IAOI,0BAAA;EtE+xQV;;EsEtyQM;IAOI,4BAAA;EtEmyQV;;EsE1yQM;IAOI,kCAAA;EtEuyQV;;EsE9yQM;IAOI,iBAAA;EtE2yQV;;EsElzQM;IAOI,uBAAA;EtE+yQV;;EsEtzQM;IAOI,sBAAA;EtEmzQV;;EsE1zQM;IAOI,oBAAA;EtEuzQV;;EsE9zQM;IAOI,sBAAA;EtE2zQV;;EsEl0QM;IAOI,oBAAA;EtE+zQV;;EsEt0QM;IAOI,sCAAA;EtEm0QV;;EsE10QM;IAOI,oCAAA;EtEu0QV;;EsE90QM;IAOI,kCAAA;EtE20QV;;EsEl1QM;IAOI,yCAAA;EtE+0QV;;EsEt1QM;IAOI,wCAAA;EtEm1QV;;EsE11QM;IAOI,wCAAA;EtEu1QV;;EsE91QM;IAOI,kCAAA;EtE21QV;;EsEl2QM;IAOI,gCAAA;EtE+1QV;;EsEt2QM;IAOI,8BAAA;EtEm2QV;;EsE12QM;IAOI,gCAAA;EtEu2QV;;EsE92QM;IAOI,+BAAA;EtE22QV;;EsEl3QM;IAOI,oCAAA;EtE+2QV;;EsEt3QM;IAOI,kCAAA;EtEm3QV;;EsE13QM;IAOI,gCAAA;EtEu3QV;;EsE93QM;IAOI,uCAAA;EtE23QV;;EsEl4QM;IAOI,sCAAA;EtE+3QV;;EsEt4QM;IAOI,iCAAA;EtEm4QV;;EsE14QM;IAOI,2BAAA;EtEu4QV;;EsE94QM;IAOI,iCAAA;EtE24QV;;EsEl5QM;IAOI,+BAAA;EtE+4QV;;EsEt5QM;IAOI,6BAAA;EtEm5QV;;EsE15QM;IAOI,+BAAA;EtEu5QV;;EsE95QM;IAOI,8BAAA;EtE25QV;;EsEl6QM;IAOI,oBAAA;EtE+5QV;;EsEt6QM;IAOI,mBAAA;EtEm6QV;;EsE16QM;IAOI,mBAAA;EtEu6QV;;EsE96QM;IAOI,mBAAA;EtE26QV;;EsEl7QM;IAOI,mBAAA;EtE+6QV;;EsEt7QM;IAOI,mBAAA;EtEm7QV;;EsE17QM;IAOI,mBAAA;EtEu7QV;;EsE97QM;IAOI,mBAAA;EtE27QV;;EsEl8QM;IAOI,oBAAA;EtE+7QV;;EsEt8QM;IAOI,0BAAA;EtEm8QV;;EsE18QM;IAOI,yBAAA;EtEu8QV;;EsE98QM;IAOI,uBAAA;EtE28QV;;EsE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A;EtEqxRV;;EsE5xRM;IAOI,kCAAA;EtEyxRV;;EsEhyRM;IAOI,iCAAA;EtE6xRV;;EsEpyRM;IAOI,+BAAA;EtEiyRV;;EsExyRM;IAOI,iCAAA;EtEqyRV;;EsE5yRM;IAOI,+BAAA;EtEyyRV;;EsEhzRM;IAOI,0BAAA;EtE6yRV;;EsEpzRM;IAOI,gCAAA;EtEizRV;;EsExzRM;IAOI,+BAAA;EtEqzRV;;EsE5zRM;IAOI,6BAAA;EtEyzRV;;EsEh0RM;IAOI,+BAAA;EtE6zRV;;EsEp0RM;IAOI,6BAAA;EtEi0RV;;EsEx0RM;IAOI,2BAAA;EtEq0RV;;EsE50RM;IAOI,4BAAA;EtEy0RV;;EsEh1RM;IAOI,6BAAA;EtE60RV;AACF;Aar1RI;EyDAI;IAOI,sBAAA;EtEk1RV;;EsEz1RM;IAOI,uBAAA;EtEs1RV;;EsE71RM;IAOI,sBAAA;EtE01RV;;EsEj2RM;IAOI,0BAAA;EtE81RV;;EsEr2RM;IAOI,gCAAA;EtEk2RV;;EsEz2RM;IAOI,yBAAA;EtEs2RV;;EsE72RM;IAOI,wBAAA;EtE02RV;;EsEj3RM;IAOI,yBAAA;EtE82RV;;EsEr3RM;IAOI,6BAAA;EtEk3RV;;EsEz3RM;IAOI,8BAAA;EtEs3RV;;EsE73RM;IAOI,wBAAA;EtE03RV;;EsEj4RM;IAOI,+BAAA;EtE83RV;;EsEr4RM;IAOI,wBAAA;EtEk4RV;;EsEz4RM;IAOI,yBAAA;EtEs4RV;;EsE74RM;IAOI,8BAAA;EtE04RV;;EsEj5RM;IAOI,iCAAA;EtE84RV;;EsEr5RM;IAOI,sCAAA;EtEk5RV;;EsEz5RM;IAOI,yCAAA;EtEs5RV;;EsE75RM;IAOI,uBAAA;EtE05RV;;EsEj6RM;IAOI,uBAAA;EtE85RV;;EsEr6RM;IAOI,yBAAA;EtEk6RV;;EsEz6RM;IAOI,yBAAA;EtEs6RV;;EsE76RM;IAOI,0BAAA;EtE06RV;;EsEj7RM;IAOI,4BAAA;EtE86RV;;EsEr7RM;IAOI,kCAAA;EtEk7RV;;EsEz7RM;IAOI,iBAAA;EtEs7RV;;EsE77RM;IAOI,uBAAA;EtE07RV;;EsEj8RM;IAOI,sBAAA;EtE87RV;;EsEr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BAAA;EtEo7SV;;EsE37SM;IAOI,0BAAA;EtEw7SV;;EsE/7SM;IAOI,gCAAA;EtE47SV;;EsEn8SM;IAOI,+BAAA;EtEg8SV;;EsEv8SM;IAOI,6BAAA;EtEo8SV;;EsE38SM;IAOI,+BAAA;EtEw8SV;;EsE/8SM;IAOI,6BAAA;EtE48SV;;EsEn9SM;IAOI,2BAAA;EtEg9SV;;EsEv9SM;IAOI,4BAAA;EtEo9SV;;EsE39SM;IAOI,6BAAA;EtEw9SV;AACF;Aah+SI;EyDAI;IAOI,sBAAA;EtE69SV;;EsEp+SM;IAOI,uBAAA;EtEi+SV;;EsEx+SM;IAOI,sBAAA;EtEq+SV;;EsE5+SM;IAOI,0BAAA;EtEy+SV;;EsEh/SM;IAOI,gCAAA;EtE6+SV;;EsEp/SM;IAOI,yBAAA;EtEi/SV;;EsEx/SM;IAOI,wBAAA;EtEq/SV;;EsE5/SM;IAOI,yBAAA;EtEy/SV;;EsEhgTM;IAOI,6BAAA;EtE6/SV;;EsEpgTM;IAOI,8BAAA;EtEigTV;;EsExgTM;IAOI,wBAAA;EtEqgTV;;EsE5gTM;IAOI,+BAAA;EtEygTV;;EsEhhTM;IAOI,wBAAA;EtE6gTV;;EsEphTM;IAOI,yBAAA;EtEihTV;;EsExhTM;IAOI,8BAAA;EtEqhTV;;EsE5hTM;IAOI,iCAAA;EtEyhTV;;EsEhiTM;IAOI,sCAAA;EtE6hTV;;EsEpiTM;IAOI,yCAAA;EtEiiTV;;EsExiTM;IAOI,uBAAA;EtEqiTV;;EsE5iTM;IAOI,uBAAA;EtEyiTV;;EsEhjTM;IAOI,yBAAA;EtE6iTV;;EsEpjTM;IAOI,yBAAA;EtEijTV;;EsExjTM;IAOI,0BAAA;EtEqjTV;;EsE5jTM;IAOI,4BAAA;EtEyjTV;;EsEhkTM;IAOI,kCAAA;EtE6jTV;;EsEpkTM;IAOI,iBAAA;EtEikTV;;EsExkTM;IAOI,uBAAA;EtEqkTV;;EsE5kTM;IAOI,sBAAA;EtEykTV;;EsEhlTM;IAOI,oBAAA;EtE6kTV;;EsEplTM;IAOI,sBAAA;EtEilTV;;EsExlTM;IAOI,oBAAA;EtEqlTV;;EsE5lTM;IAOI,sCAAA;EtEylTV;;EsEhmTM;IAOI,oCAAA;EtE6lTV;;E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I,+BAAA;EtEmlUV;;EsE1lUM;IAOI,6BAAA;EtEulUV;;EsE9lUM;IAOI,2BAAA;EtE2lUV;;EsElmUM;IAOI,4BAAA;EtE+lUV;;EsEtmUM;IAOI,6BAAA;EtEmmUV;AACF;Aa3mUI;EyDAI;IAOI,sBAAA;EtEwmUV;;EsE/mUM;IAOI,uBAAA;EtE4mUV;;EsEnnUM;IAOI,sBAAA;EtEgnUV;;EsEvnUM;IAOI,0BAAA;EtEonUV;;EsE3nUM;IAOI,gCAAA;EtEwnUV;;EsE/nUM;IAOI,yBAAA;EtE4nUV;;EsEnoUM;IAOI,wBAAA;EtEgoUV;;EsEvoUM;IAOI,yBAAA;EtEooUV;;EsE3oUM;IAOI,6BAAA;EtEwoUV;;EsE/oUM;IAOI,8BAAA;EtE4oUV;;EsEnpUM;IAOI,wBAAA;EtEgpUV;;EsEvpUM;IAOI,+BAAA;EtEopUV;;EsE3pUM;IAOI,wBAAA;EtEwpUV;;EsE/pUM;IAOI,yBAAA;EtE4pUV;;EsEnqUM;IAOI,8BAAA;EtEgqUV;;EsEvqUM;IAOI,iCAAA;EtEoqUV;;EsE3qUM;IAOI,sCAAA;EtEwqUV;;EsE/qUM;IAOI,yCAAA;EtE4qUV;;EsEnrUM;IAOI,uBAAA;EtEgrUV;;EsEvrUM;IAOI,uBAAA;EtEorUV;;EsE3rUM;IAOI,yBAAA;EtEwrUV;;EsE/rUM;IAOI,yBAAA;EtE4rUV;;EsEnsUM;IAOI,0BAAA;EtEgsUV;;EsEvsUM;IAOI,4BAAA;EtEosUV;;EsE3sUM;IAOI,kCAAA;EtEwsUV;;EsE/sUM;IAOI,iBAAA;EtE4sUV;;EsEntUM;IAOI,uBAAA;EtEgtUV;;EsEvtUM;IAOI,sBAAA;EtEotUV;;EsE3tUM;IAOI,oBAAA;EtEwtUV;;EsE/tUM;IAOI,sBAAA;EtE4tUV;;EsEnuUM;IAOI,oBAAA;EtEguUV;;EsEvuUM;IAOI,sCAAA;EtEouUV;;EsE3uUM;IAOI,oCAAA;EtEwuUV;;EsE/uUM;IAOI,kCAAA;EtE4uUV;;EsEnvUM;IAOI,yCAAA;EtEgvUV;;EsEvvUM;IAOI,wCAAA;EtEovUV;;EsE3vUM;IAOI,wCAAA;EtEwvUV;;EsE/vUM;IAOI,kCAAA;EtE4vUV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","file":"bootstrap.css","sourcesContent":["@charset \"UTF-8\";\n/*!\n * Bootstrap v5.1.3 (https://getbootstrap.com/)\n * Copyright 2011-2021 The Bootstrap Authors\n * Copyright 2011-2021 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n */\n:root {\n --bs-blue: #0d6efd;\n --bs-indigo: #6610f2;\n --bs-purple: #6f42c1;\n --bs-pink: #d63384;\n --bs-red: #dc3545;\n --bs-orange: #fd7e14;\n --bs-yellow: #ffc107;\n --bs-green: #198754;\n --bs-teal: #20c997;\n --bs-cyan: #0dcaf0;\n --bs-white: #fff;\n --bs-gray: #6c757d;\n --bs-gray-dark: #343a40;\n --bs-gray-100: #f8f9fa;\n --bs-gray-200: #e9ecef;\n --bs-gray-300: #dee2e6;\n --bs-gray-400: #ced4da;\n --bs-gray-500: #adb5bd;\n --bs-gray-600: #6c757d;\n --bs-gray-700: #495057;\n --bs-gray-800: #343a40;\n --bs-gray-900: #212529;\n --bs-primary: #0d6efd;\n --bs-secondary: #6c757d;\n --bs-success: #198754;\n --bs-info: #0dcaf0;\n --bs-warning: #ffc107;\n --bs-danger: #dc3545;\n --bs-light: #f8f9fa;\n --bs-dark: #212529;\n --bs-primary-rgb: 13, 110, 253;\n --bs-secondary-rgb: 108, 117, 125;\n --bs-success-rgb: 25, 135, 84;\n --bs-info-rgb: 13, 202, 240;\n --bs-warning-rgb: 255, 193, 7;\n --bs-danger-rgb: 220, 53, 69;\n --bs-light-rgb: 248, 249, 250;\n --bs-dark-rgb: 33, 37, 41;\n --bs-white-rgb: 255, 255, 255;\n --bs-black-rgb: 0, 0, 0;\n --bs-body-color-rgb: 33, 37, 41;\n --bs-body-bg-rgb: 255, 255, 255;\n --bs-font-sans-serif: system-ui, -apple-system, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, \"Noto Sans\", \"Liberation Sans\", sans-serif, \"Apple Color Emoji\", \"Segoe UI Emoji\", \"Segoe UI Symbol\", \"Noto Color Emoji\";\n --bs-font-monospace: SFMono-Regular, Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace;\n --bs-gradient: linear-gradient(180deg, rgba(255, 255, 255, 0.15), rgba(255, 255, 255, 0));\n --bs-body-font-family: var(--bs-font-sans-serif);\n --bs-body-font-size: 1rem;\n --bs-body-font-weight: 400;\n --bs-body-line-height: 1.5;\n --bs-body-color: #212529;\n --bs-body-bg: #fff;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: border-box;\n}\n\n@media (prefers-reduced-motion: no-preference) {\n :root {\n scroll-behavior: smooth;\n }\n}\n\nbody {\n margin: 0;\n font-family: var(--bs-body-font-family);\n font-size: var(--bs-body-font-size);\n font-weight: var(--bs-body-font-weight);\n line-height: var(--bs-body-line-height);\n color: var(--bs-body-color);\n text-align: var(--bs-body-text-align);\n background-color: var(--bs-body-bg);\n -webkit-text-size-adjust: 100%;\n -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\n}\n\nhr {\n margin: 1rem 0;\n color: inherit;\n background-color: currentColor;\n border: 0;\n opacity: 0.25;\n}\n\nhr:not([size]) {\n height: 1px;\n}\n\nh6, .h6, h5, .h5, h4, .h4, h3, .h3, h2, .h2, h1, .h1 {\n margin-top: 0;\n margin-bottom: 0.5rem;\n font-weight: 500;\n line-height: 1.2;\n}\n\nh1, .h1 {\n font-size: calc(1.375rem + 1.5vw);\n}\n@media (min-width: 1200px) {\n h1, .h1 {\n font-size: 2.5rem;\n }\n}\n\nh2, .h2 {\n font-size: calc(1.325rem + 0.9vw);\n}\n@media (min-width: 1200px) {\n h2, .h2 {\n font-size: 2rem;\n }\n}\n\nh3, .h3 {\n font-size: calc(1.3rem + 0.6vw);\n}\n@media (min-width: 1200px) {\n h3, .h3 {\n font-size: 1.75rem;\n }\n}\n\nh4, .h4 {\n font-size: calc(1.275rem + 0.3vw);\n}\n@media (min-width: 1200px) {\n h4, .h4 {\n font-size: 1.5rem;\n }\n}\n\nh5, .h5 {\n font-size: 1.25rem;\n}\n\nh6, .h6 {\n font-size: 1rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-bs-original-title] {\n text-decoration: underline dotted;\n cursor: help;\n text-decoration-skip-ink: none;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul {\n padding-left: 2rem;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: 700;\n}\n\ndd {\n margin-bottom: 0.5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall, .small {\n font-size: 0.875em;\n}\n\nmark, .mark {\n padding: 0.2em;\n background-color: #fcf8e3;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 0.75em;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -0.25em;\n}\n\nsup {\n top: -0.5em;\n}\n\na {\n color: #0d6efd;\n text-decoration: underline;\n}\na:hover {\n color: #0a58ca;\n}\n\na:not([href]):not([class]), a:not([href]):not([class]):hover {\n color: inherit;\n text-decoration: none;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: var(--bs-font-monospace);\n font-size: 1em;\n direction: ltr /* rtl:ignore */;\n unicode-bidi: bidi-override;\n}\n\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n font-size: 0.875em;\n}\npre code {\n font-size: inherit;\n color: inherit;\n word-break: normal;\n}\n\ncode {\n font-size: 0.875em;\n color: #d63384;\n word-wrap: break-word;\n}\na > code {\n color: inherit;\n}\n\nkbd {\n padding: 0.2rem 0.4rem;\n font-size: 0.875em;\n color: #fff;\n background-color: #212529;\n border-radius: 0.2rem;\n}\nkbd kbd {\n padding: 0;\n font-size: 1em;\n font-weight: 700;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg,\nsvg {\n vertical-align: middle;\n}\n\ntable {\n caption-side: bottom;\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n color: #6c757d;\n text-align: left;\n}\n\nth {\n text-align: inherit;\n text-align: -webkit-match-parent;\n}\n\nthead,\ntbody,\ntfoot,\ntr,\ntd,\nth {\n border-color: inherit;\n border-style: solid;\n border-width: 0;\n}\n\nlabel {\n display: inline-block;\n}\n\nbutton {\n border-radius: 0;\n}\n\nbutton:focus:not(:focus-visible) {\n outline: 0;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\n[role=button] {\n cursor: pointer;\n}\n\nselect {\n word-wrap: normal;\n}\nselect:disabled {\n opacity: 1;\n}\n\n[list]::-webkit-calendar-picker-indicator {\n display: none;\n}\n\nbutton,\n[type=button],\n[type=reset],\n[type=submit] {\n -webkit-appearance: button;\n}\nbutton:not(:disabled),\n[type=button]:not(:disabled),\n[type=reset]:not(:disabled),\n[type=submit]:not(:disabled) {\n cursor: pointer;\n}\n\n::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ntextarea {\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n float: left;\n width: 100%;\n padding: 0;\n margin-bottom: 0.5rem;\n font-size: calc(1.275rem + 0.3vw);\n line-height: inherit;\n}\n@media (min-width: 1200px) {\n legend {\n font-size: 1.5rem;\n }\n}\nlegend + * {\n clear: left;\n}\n\n::-webkit-datetime-edit-fields-wrapper,\n::-webkit-datetime-edit-text,\n::-webkit-datetime-edit-minute,\n::-webkit-datetime-edit-hour-field,\n::-webkit-datetime-edit-day-field,\n::-webkit-datetime-edit-month-field,\n::-webkit-datetime-edit-year-field {\n padding: 0;\n}\n\n::-webkit-inner-spin-button {\n height: auto;\n}\n\n[type=search] {\n outline-offset: -2px;\n -webkit-appearance: textfield;\n}\n\n/* rtl:raw:\n[type=\"tel\"],\n[type=\"url\"],\n[type=\"email\"],\n[type=\"number\"] {\n direction: ltr;\n}\n*/\n::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-color-swatch-wrapper {\n padding: 0;\n}\n\n::file-selector-button {\n font: inherit;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\niframe {\n border: 0;\n}\n\nsummary {\n display: list-item;\n cursor: pointer;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[hidden] {\n display: none !important;\n}\n\n.lead {\n font-size: 1.25rem;\n font-weight: 300;\n}\n\n.display-1 {\n font-size: calc(1.625rem + 4.5vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-1 {\n font-size: 5rem;\n }\n}\n\n.display-2 {\n font-size: calc(1.575rem + 3.9vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-2 {\n font-size: 4.5rem;\n }\n}\n\n.display-3 {\n font-size: calc(1.525rem + 3.3vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-3 {\n font-size: 4rem;\n }\n}\n\n.display-4 {\n font-size: calc(1.475rem + 2.7vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-4 {\n font-size: 3.5rem;\n }\n}\n\n.display-5 {\n font-size: calc(1.425rem + 2.1vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-5 {\n font-size: 3rem;\n }\n}\n\n.display-6 {\n font-size: calc(1.375rem + 1.5vw);\n font-weight: 300;\n line-height: 1.2;\n}\n@media (min-width: 1200px) {\n .display-6 {\n font-size: 2.5rem;\n }\n}\n\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline-item {\n display: inline-block;\n}\n.list-inline-item:not(:last-child) {\n margin-right: 0.5rem;\n}\n\n.initialism {\n font-size: 0.875em;\n text-transform: uppercase;\n}\n\n.blockquote {\n margin-bottom: 1rem;\n font-size: 1.25rem;\n}\n.blockquote > :last-child {\n margin-bottom: 0;\n}\n\n.blockquote-footer {\n margin-top: -1rem;\n margin-bottom: 1rem;\n font-size: 0.875em;\n color: #6c757d;\n}\n.blockquote-footer::before {\n content: \"— \";\n}\n\n.img-fluid {\n max-width: 100%;\n height: auto;\n}\n\n.img-thumbnail {\n padding: 0.25rem;\n background-color: #fff;\n border: 1px solid #dee2e6;\n border-radius: 0.25rem;\n max-width: 100%;\n height: auto;\n}\n\n.figure {\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: 0.5rem;\n line-height: 1;\n}\n\n.figure-caption {\n font-size: 0.875em;\n color: #6c757d;\n}\n\n.container,\n.container-fluid,\n.container-xxl,\n.container-xl,\n.container-lg,\n.container-md,\n.container-sm {\n width: 100%;\n padding-right: var(--bs-gutter-x, 0.75rem);\n padding-left: var(--bs-gutter-x, 0.75rem);\n margin-right: auto;\n margin-left: auto;\n}\n\n@media (min-width: 576px) {\n .container-sm, .container {\n max-width: 540px;\n }\n}\n@media (min-width: 768px) {\n .container-md, .container-sm, .container {\n max-width: 720px;\n }\n}\n@media (min-width: 992px) {\n .container-lg, .container-md, .container-sm, .container {\n max-width: 960px;\n }\n}\n@media (min-width: 1200px) {\n .container-xl, .container-lg, .container-md, .container-sm, .container {\n max-width: 1140px;\n }\n}\n@media (min-width: 1400px) {\n .container-xxl, .container-xl, .container-lg, .container-md, .container-sm, .container {\n max-width: 1320px;\n }\n}\n.row {\n --bs-gutter-x: 1.5rem;\n --bs-gutter-y: 0;\n display: flex;\n flex-wrap: wrap;\n margin-top: calc(-1 * var(--bs-gutter-y));\n margin-right: calc(-0.5 * var(--bs-gutter-x));\n margin-left: calc(-0.5 * var(--bs-gutter-x));\n}\n.row > * {\n flex-shrink: 0;\n width: 100%;\n max-width: 100%;\n padding-right: calc(var(--bs-gutter-x) * 0.5);\n padding-left: calc(var(--bs-gutter-x) * 0.5);\n margin-top: var(--bs-gutter-y);\n}\n\n.col {\n flex: 1 0 0%;\n}\n\n.row-cols-auto > * {\n flex: 0 0 auto;\n width: auto;\n}\n\n.row-cols-1 > * {\n flex: 0 0 auto;\n width: 100%;\n}\n\n.row-cols-2 > * {\n flex: 0 0 auto;\n width: 50%;\n}\n\n.row-cols-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n}\n\n.row-cols-4 > * {\n flex: 0 0 auto;\n width: 25%;\n}\n\n.row-cols-5 > * {\n flex: 0 0 auto;\n width: 20%;\n}\n\n.row-cols-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n}\n\n.col-auto {\n flex: 0 0 auto;\n width: auto;\n}\n\n.col-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n}\n\n.col-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n}\n\n.col-3 {\n flex: 0 0 auto;\n width: 25%;\n}\n\n.col-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n}\n\n.col-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n}\n\n.col-6 {\n flex: 0 0 auto;\n width: 50%;\n}\n\n.col-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n}\n\n.col-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n}\n\n.col-9 {\n flex: 0 0 auto;\n width: 75%;\n}\n\n.col-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n}\n\n.col-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n}\n\n.col-12 {\n flex: 0 0 auto;\n width: 100%;\n}\n\n.offset-1 {\n margin-left: 8.33333333%;\n}\n\n.offset-2 {\n margin-left: 16.66666667%;\n}\n\n.offset-3 {\n margin-left: 25%;\n}\n\n.offset-4 {\n margin-left: 33.33333333%;\n}\n\n.offset-5 {\n margin-left: 41.66666667%;\n}\n\n.offset-6 {\n margin-left: 50%;\n}\n\n.offset-7 {\n margin-left: 58.33333333%;\n}\n\n.offset-8 {\n margin-left: 66.66666667%;\n}\n\n.offset-9 {\n margin-left: 75%;\n}\n\n.offset-10 {\n margin-left: 83.33333333%;\n}\n\n.offset-11 {\n margin-left: 91.66666667%;\n}\n\n.g-0,\n.gx-0 {\n --bs-gutter-x: 0;\n}\n\n.g-0,\n.gy-0 {\n --bs-gutter-y: 0;\n}\n\n.g-1,\n.gx-1 {\n --bs-gutter-x: 0.25rem;\n}\n\n.g-1,\n.gy-1 {\n --bs-gutter-y: 0.25rem;\n}\n\n.g-2,\n.gx-2 {\n --bs-gutter-x: 0.5rem;\n}\n\n.g-2,\n.gy-2 {\n --bs-gutter-y: 0.5rem;\n}\n\n.g-3,\n.gx-3 {\n --bs-gutter-x: 1rem;\n}\n\n.g-3,\n.gy-3 {\n --bs-gutter-y: 1rem;\n}\n\n.g-4,\n.gx-4 {\n --bs-gutter-x: 1.5rem;\n}\n\n.g-4,\n.gy-4 {\n --bs-gutter-y: 1.5rem;\n}\n\n.g-5,\n.gx-5 {\n --bs-gutter-x: 3rem;\n}\n\n.g-5,\n.gy-5 {\n --bs-gutter-y: 3rem;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n flex: 1 0 0%;\n }\n\n .row-cols-sm-auto > * {\n flex: 0 0 auto;\n width: auto;\n }\n\n .row-cols-sm-1 > * {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .row-cols-sm-2 > * {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .row-cols-sm-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n }\n\n .row-cols-sm-4 > * {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .row-cols-sm-5 > * {\n flex: 0 0 auto;\n width: 20%;\n }\n\n .row-cols-sm-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n }\n\n .col-sm-auto {\n flex: 0 0 auto;\n width: auto;\n }\n\n .col-sm-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n }\n\n .col-sm-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n }\n\n .col-sm-3 {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .col-sm-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n }\n\n .col-sm-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n }\n\n .col-sm-6 {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .col-sm-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n }\n\n .col-sm-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n }\n\n .col-sm-9 {\n flex: 0 0 auto;\n width: 75%;\n }\n\n .col-sm-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n }\n\n .col-sm-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n }\n\n .col-sm-12 {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .offset-sm-0 {\n margin-left: 0;\n }\n\n .offset-sm-1 {\n margin-left: 8.33333333%;\n }\n\n .offset-sm-2 {\n margin-left: 16.66666667%;\n }\n\n .offset-sm-3 {\n margin-left: 25%;\n }\n\n .offset-sm-4 {\n margin-left: 33.33333333%;\n }\n\n .offset-sm-5 {\n margin-left: 41.66666667%;\n }\n\n .offset-sm-6 {\n margin-left: 50%;\n }\n\n .offset-sm-7 {\n margin-left: 58.33333333%;\n }\n\n .offset-sm-8 {\n margin-left: 66.66666667%;\n }\n\n .offset-sm-9 {\n margin-left: 75%;\n }\n\n .offset-sm-10 {\n margin-left: 83.33333333%;\n }\n\n .offset-sm-11 {\n margin-left: 91.66666667%;\n }\n\n .g-sm-0,\n.gx-sm-0 {\n --bs-gutter-x: 0;\n }\n\n .g-sm-0,\n.gy-sm-0 {\n --bs-gutter-y: 0;\n }\n\n .g-sm-1,\n.gx-sm-1 {\n --bs-gutter-x: 0.25rem;\n }\n\n .g-sm-1,\n.gy-sm-1 {\n --bs-gutter-y: 0.25rem;\n }\n\n .g-sm-2,\n.gx-sm-2 {\n --bs-gutter-x: 0.5rem;\n }\n\n .g-sm-2,\n.gy-sm-2 {\n --bs-gutter-y: 0.5rem;\n }\n\n .g-sm-3,\n.gx-sm-3 {\n --bs-gutter-x: 1rem;\n }\n\n .g-sm-3,\n.gy-sm-3 {\n --bs-gutter-y: 1rem;\n }\n\n .g-sm-4,\n.gx-sm-4 {\n --bs-gutter-x: 1.5rem;\n }\n\n .g-sm-4,\n.gy-sm-4 {\n --bs-gutter-y: 1.5rem;\n }\n\n .g-sm-5,\n.gx-sm-5 {\n --bs-gutter-x: 3rem;\n }\n\n .g-sm-5,\n.gy-sm-5 {\n --bs-gutter-y: 3rem;\n }\n}\n@media (min-width: 768px) {\n .col-md {\n flex: 1 0 0%;\n }\n\n .row-cols-md-auto > * {\n flex: 0 0 auto;\n width: auto;\n }\n\n .row-cols-md-1 > * {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .row-cols-md-2 > * {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .row-cols-md-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n }\n\n .row-cols-md-4 > * {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .row-cols-md-5 > * {\n flex: 0 0 auto;\n width: 20%;\n }\n\n .row-cols-md-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n }\n\n .col-md-auto {\n flex: 0 0 auto;\n width: auto;\n }\n\n .col-md-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n }\n\n .col-md-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n }\n\n .col-md-3 {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .col-md-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n }\n\n .col-md-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n }\n\n .col-md-6 {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .col-md-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n }\n\n .col-md-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n }\n\n .col-md-9 {\n flex: 0 0 auto;\n width: 75%;\n }\n\n .col-md-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n }\n\n .col-md-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n }\n\n .col-md-12 {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .offset-md-0 {\n margin-left: 0;\n }\n\n .offset-md-1 {\n margin-left: 8.33333333%;\n }\n\n .offset-md-2 {\n margin-left: 16.66666667%;\n }\n\n .offset-md-3 {\n margin-left: 25%;\n }\n\n .offset-md-4 {\n margin-left: 33.33333333%;\n }\n\n .offset-md-5 {\n margin-left: 41.66666667%;\n }\n\n .offset-md-6 {\n margin-left: 50%;\n }\n\n .offset-md-7 {\n margin-left: 58.33333333%;\n }\n\n .offset-md-8 {\n margin-left: 66.66666667%;\n }\n\n .offset-md-9 {\n margin-left: 75%;\n }\n\n .offset-md-10 {\n margin-left: 83.33333333%;\n }\n\n .offset-md-11 {\n margin-left: 91.66666667%;\n }\n\n .g-md-0,\n.gx-md-0 {\n --bs-gutter-x: 0;\n }\n\n .g-md-0,\n.gy-md-0 {\n --bs-gutter-y: 0;\n }\n\n .g-md-1,\n.gx-md-1 {\n --bs-gutter-x: 0.25rem;\n }\n\n .g-md-1,\n.gy-md-1 {\n --bs-gutter-y: 0.25rem;\n }\n\n .g-md-2,\n.gx-md-2 {\n --bs-gutter-x: 0.5rem;\n }\n\n .g-md-2,\n.gy-md-2 {\n --bs-gutter-y: 0.5rem;\n }\n\n .g-md-3,\n.gx-md-3 {\n --bs-gutter-x: 1rem;\n }\n\n .g-md-3,\n.gy-md-3 {\n --bs-gutter-y: 1rem;\n }\n\n .g-md-4,\n.gx-md-4 {\n --bs-gutter-x: 1.5rem;\n }\n\n .g-md-4,\n.gy-md-4 {\n --bs-gutter-y: 1.5rem;\n }\n\n .g-md-5,\n.gx-md-5 {\n --bs-gutter-x: 3rem;\n }\n\n .g-md-5,\n.gy-md-5 {\n --bs-gutter-y: 3rem;\n }\n}\n@media (min-width: 992px) {\n .col-lg {\n flex: 1 0 0%;\n }\n\n .row-cols-lg-auto > * {\n flex: 0 0 auto;\n width: auto;\n }\n\n .row-cols-lg-1 > * {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .row-cols-lg-2 > * {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .row-cols-lg-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n }\n\n .row-cols-lg-4 > * {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .row-cols-lg-5 > * {\n flex: 0 0 auto;\n width: 20%;\n }\n\n .row-cols-lg-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n }\n\n .col-lg-auto {\n flex: 0 0 auto;\n width: auto;\n }\n\n .col-lg-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n }\n\n .col-lg-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n }\n\n .col-lg-3 {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .col-lg-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n }\n\n .col-lg-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n }\n\n .col-lg-6 {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .col-lg-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n }\n\n .col-lg-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n }\n\n .col-lg-9 {\n flex: 0 0 auto;\n width: 75%;\n }\n\n .col-lg-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n }\n\n .col-lg-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n }\n\n .col-lg-12 {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .offset-lg-0 {\n margin-left: 0;\n }\n\n .offset-lg-1 {\n margin-left: 8.33333333%;\n }\n\n .offset-lg-2 {\n margin-left: 16.66666667%;\n }\n\n .offset-lg-3 {\n margin-left: 25%;\n }\n\n .offset-lg-4 {\n margin-left: 33.33333333%;\n }\n\n .offset-lg-5 {\n margin-left: 41.66666667%;\n }\n\n .offset-lg-6 {\n margin-left: 50%;\n }\n\n .offset-lg-7 {\n margin-left: 58.33333333%;\n }\n\n .offset-lg-8 {\n margin-left: 66.66666667%;\n }\n\n .offset-lg-9 {\n margin-left: 75%;\n }\n\n .offset-lg-10 {\n margin-left: 83.33333333%;\n }\n\n .offset-lg-11 {\n margin-left: 91.66666667%;\n }\n\n .g-lg-0,\n.gx-lg-0 {\n --bs-gutter-x: 0;\n }\n\n .g-lg-0,\n.gy-lg-0 {\n --bs-gutter-y: 0;\n }\n\n .g-lg-1,\n.gx-lg-1 {\n --bs-gutter-x: 0.25rem;\n }\n\n .g-lg-1,\n.gy-lg-1 {\n --bs-gutter-y: 0.25rem;\n }\n\n .g-lg-2,\n.gx-lg-2 {\n --bs-gutter-x: 0.5rem;\n }\n\n .g-lg-2,\n.gy-lg-2 {\n --bs-gutter-y: 0.5rem;\n }\n\n .g-lg-3,\n.gx-lg-3 {\n --bs-gutter-x: 1rem;\n }\n\n .g-lg-3,\n.gy-lg-3 {\n --bs-gutter-y: 1rem;\n }\n\n .g-lg-4,\n.gx-lg-4 {\n --bs-gutter-x: 1.5rem;\n }\n\n .g-lg-4,\n.gy-lg-4 {\n --bs-gutter-y: 1.5rem;\n }\n\n .g-lg-5,\n.gx-lg-5 {\n --bs-gutter-x: 3rem;\n }\n\n .g-lg-5,\n.gy-lg-5 {\n --bs-gutter-y: 3rem;\n }\n}\n@media (min-width: 1200px) {\n .col-xl {\n flex: 1 0 0%;\n }\n\n .row-cols-xl-auto > * {\n flex: 0 0 auto;\n width: auto;\n }\n\n .row-cols-xl-1 > * {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .row-cols-xl-2 > * {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .row-cols-xl-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n }\n\n .row-cols-xl-4 > * {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .row-cols-xl-5 > * {\n flex: 0 0 auto;\n width: 20%;\n }\n\n .row-cols-xl-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n }\n\n .col-xl-auto {\n flex: 0 0 auto;\n width: auto;\n }\n\n .col-xl-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n }\n\n .col-xl-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n }\n\n .col-xl-3 {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .col-xl-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n }\n\n .col-xl-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n }\n\n .col-xl-6 {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .col-xl-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n }\n\n .col-xl-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n }\n\n .col-xl-9 {\n flex: 0 0 auto;\n width: 75%;\n }\n\n .col-xl-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n }\n\n .col-xl-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n }\n\n .col-xl-12 {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .offset-xl-0 {\n margin-left: 0;\n }\n\n .offset-xl-1 {\n margin-left: 8.33333333%;\n }\n\n .offset-xl-2 {\n margin-left: 16.66666667%;\n }\n\n .offset-xl-3 {\n margin-left: 25%;\n }\n\n .offset-xl-4 {\n margin-left: 33.33333333%;\n }\n\n .offset-xl-5 {\n margin-left: 41.66666667%;\n }\n\n .offset-xl-6 {\n margin-left: 50%;\n }\n\n .offset-xl-7 {\n margin-left: 58.33333333%;\n }\n\n .offset-xl-8 {\n margin-left: 66.66666667%;\n }\n\n .offset-xl-9 {\n margin-left: 75%;\n }\n\n .offset-xl-10 {\n margin-left: 83.33333333%;\n }\n\n .offset-xl-11 {\n margin-left: 91.66666667%;\n }\n\n .g-xl-0,\n.gx-xl-0 {\n --bs-gutter-x: 0;\n }\n\n .g-xl-0,\n.gy-xl-0 {\n --bs-gutter-y: 0;\n }\n\n .g-xl-1,\n.gx-xl-1 {\n --bs-gutter-x: 0.25rem;\n }\n\n .g-xl-1,\n.gy-xl-1 {\n --bs-gutter-y: 0.25rem;\n }\n\n .g-xl-2,\n.gx-xl-2 {\n --bs-gutter-x: 0.5rem;\n }\n\n .g-xl-2,\n.gy-xl-2 {\n --bs-gutter-y: 0.5rem;\n }\n\n .g-xl-3,\n.gx-xl-3 {\n --bs-gutter-x: 1rem;\n }\n\n .g-xl-3,\n.gy-xl-3 {\n --bs-gutter-y: 1rem;\n }\n\n .g-xl-4,\n.gx-xl-4 {\n --bs-gutter-x: 1.5rem;\n }\n\n .g-xl-4,\n.gy-xl-4 {\n --bs-gutter-y: 1.5rem;\n }\n\n .g-xl-5,\n.gx-xl-5 {\n --bs-gutter-x: 3rem;\n }\n\n .g-xl-5,\n.gy-xl-5 {\n --bs-gutter-y: 3rem;\n }\n}\n@media (min-width: 1400px) {\n .col-xxl {\n flex: 1 0 0%;\n }\n\n .row-cols-xxl-auto > * {\n flex: 0 0 auto;\n width: auto;\n }\n\n .row-cols-xxl-1 > * {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .row-cols-xxl-2 > * {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .row-cols-xxl-3 > * {\n flex: 0 0 auto;\n width: 33.3333333333%;\n }\n\n .row-cols-xxl-4 > * {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .row-cols-xxl-5 > * {\n flex: 0 0 auto;\n width: 20%;\n }\n\n .row-cols-xxl-6 > * {\n flex: 0 0 auto;\n width: 16.6666666667%;\n }\n\n .col-xxl-auto {\n flex: 0 0 auto;\n width: auto;\n }\n\n .col-xxl-1 {\n flex: 0 0 auto;\n width: 8.33333333%;\n }\n\n .col-xxl-2 {\n flex: 0 0 auto;\n width: 16.66666667%;\n }\n\n .col-xxl-3 {\n flex: 0 0 auto;\n width: 25%;\n }\n\n .col-xxl-4 {\n flex: 0 0 auto;\n width: 33.33333333%;\n }\n\n .col-xxl-5 {\n flex: 0 0 auto;\n width: 41.66666667%;\n }\n\n .col-xxl-6 {\n flex: 0 0 auto;\n width: 50%;\n }\n\n .col-xxl-7 {\n flex: 0 0 auto;\n width: 58.33333333%;\n }\n\n .col-xxl-8 {\n flex: 0 0 auto;\n width: 66.66666667%;\n }\n\n .col-xxl-9 {\n flex: 0 0 auto;\n width: 75%;\n }\n\n .col-xxl-10 {\n flex: 0 0 auto;\n width: 83.33333333%;\n }\n\n .col-xxl-11 {\n flex: 0 0 auto;\n width: 91.66666667%;\n }\n\n .col-xxl-12 {\n flex: 0 0 auto;\n width: 100%;\n }\n\n .offset-xxl-0 {\n margin-left: 0;\n }\n\n .offset-xxl-1 {\n margin-left: 8.33333333%;\n }\n\n .offset-xxl-2 {\n margin-left: 16.66666667%;\n }\n\n .offset-xxl-3 {\n margin-left: 25%;\n }\n\n .offset-xxl-4 {\n margin-left: 33.33333333%;\n }\n\n .offset-xxl-5 {\n margin-left: 41.66666667%;\n }\n\n .offset-xxl-6 {\n margin-left: 50%;\n }\n\n .offset-xxl-7 {\n margin-left: 58.33333333%;\n }\n\n .offset-xxl-8 {\n margin-left: 66.66666667%;\n }\n\n .offset-xxl-9 {\n margin-left: 75%;\n }\n\n .offset-xxl-10 {\n margin-left: 83.33333333%;\n }\n\n .offset-xxl-11 {\n margin-left: 91.66666667%;\n }\n\n .g-xxl-0,\n.gx-xxl-0 {\n --bs-gutter-x: 0;\n }\n\n .g-xxl-0,\n.gy-xxl-0 {\n --bs-gutter-y: 0;\n }\n\n .g-xxl-1,\n.gx-xxl-1 {\n --bs-gutter-x: 0.25rem;\n }\n\n .g-xxl-1,\n.gy-xxl-1 {\n --bs-gutter-y: 0.25rem;\n }\n\n .g-xxl-2,\n.gx-xxl-2 {\n --bs-gutter-x: 0.5rem;\n }\n\n .g-xxl-2,\n.gy-xxl-2 {\n --bs-gutter-y: 0.5rem;\n }\n\n .g-xxl-3,\n.gx-xxl-3 {\n --bs-gutter-x: 1rem;\n }\n\n .g-xxl-3,\n.gy-xxl-3 {\n --bs-gutter-y: 1rem;\n }\n\n .g-xxl-4,\n.gx-xxl-4 {\n --bs-gutter-x: 1.5rem;\n }\n\n .g-xxl-4,\n.gy-xxl-4 {\n --bs-gutter-y: 1.5rem;\n }\n\n .g-xxl-5,\n.gx-xxl-5 {\n --bs-gutter-x: 3rem;\n }\n\n .g-xxl-5,\n.gy-xxl-5 {\n --bs-gutter-y: 3rem;\n }\n}\n.table {\n --bs-table-bg: transparent;\n --bs-table-accent-bg: transparent;\n --bs-table-striped-color: #212529;\n --bs-table-striped-bg: rgba(0, 0, 0, 0.05);\n --bs-table-active-color: #212529;\n --bs-table-active-bg: rgba(0, 0, 0, 0.1);\n --bs-table-hover-color: #212529;\n --bs-table-hover-bg: rgba(0, 0, 0, 0.075);\n width: 100%;\n margin-bottom: 1rem;\n color: #212529;\n vertical-align: top;\n border-color: #dee2e6;\n}\n.table > :not(caption) > * > * {\n padding: 0.5rem 0.5rem;\n background-color: var(--bs-table-bg);\n border-bottom-width: 1px;\n box-shadow: inset 0 0 0 9999px var(--bs-table-accent-bg);\n}\n.table > tbody {\n vertical-align: inherit;\n}\n.table > thead {\n vertical-align: bottom;\n}\n.table > :not(:first-child) {\n border-top: 2px solid currentColor;\n}\n\n.caption-top {\n caption-side: top;\n}\n\n.table-sm > :not(caption) > * > * {\n padding: 0.25rem 0.25rem;\n}\n\n.table-bordered > :not(caption) > * {\n border-width: 1px 0;\n}\n.table-bordered > :not(caption) > * > * {\n border-width: 0 1px;\n}\n\n.table-borderless > :not(caption) > * > * {\n border-bottom-width: 0;\n}\n.table-borderless > :not(:first-child) {\n border-top-width: 0;\n}\n\n.table-striped > tbody > tr:nth-of-type(odd) > * {\n --bs-table-accent-bg: var(--bs-table-striped-bg);\n color: var(--bs-table-striped-color);\n}\n\n.table-active {\n --bs-table-accent-bg: var(--bs-table-active-bg);\n color: var(--bs-table-active-color);\n}\n\n.table-hover > tbody > tr:hover > * {\n --bs-table-accent-bg: var(--bs-table-hover-bg);\n color: var(--bs-table-hover-color);\n}\n\n.table-primary {\n --bs-table-bg: #cfe2ff;\n --bs-table-striped-bg: #c5d7f2;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #bacbe6;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #bfd1ec;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #bacbe6;\n}\n\n.table-secondary {\n --bs-table-bg: #e2e3e5;\n --bs-table-striped-bg: #d7d8da;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #cbccce;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #d1d2d4;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #cbccce;\n}\n\n.table-success {\n --bs-table-bg: #d1e7dd;\n --bs-table-striped-bg: #c7dbd2;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #bcd0c7;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #c1d6cc;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #bcd0c7;\n}\n\n.table-info {\n --bs-table-bg: #cff4fc;\n --bs-table-striped-bg: #c5e8ef;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #badce3;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #bfe2e9;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #badce3;\n}\n\n.table-warning {\n --bs-table-bg: #fff3cd;\n --bs-table-striped-bg: #f2e7c3;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #e6dbb9;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #ece1be;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #e6dbb9;\n}\n\n.table-danger {\n --bs-table-bg: #f8d7da;\n --bs-table-striped-bg: #eccccf;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #dfc2c4;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #e5c7ca;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #dfc2c4;\n}\n\n.table-light {\n --bs-table-bg: #f8f9fa;\n --bs-table-striped-bg: #ecedee;\n --bs-table-striped-color: #000;\n --bs-table-active-bg: #dfe0e1;\n --bs-table-active-color: #000;\n --bs-table-hover-bg: #e5e6e7;\n --bs-table-hover-color: #000;\n color: #000;\n border-color: #dfe0e1;\n}\n\n.table-dark {\n --bs-table-bg: #212529;\n --bs-table-striped-bg: #2c3034;\n --bs-table-striped-color: #fff;\n --bs-table-active-bg: #373b3e;\n --bs-table-active-color: #fff;\n --bs-table-hover-bg: #323539;\n --bs-table-hover-color: #fff;\n color: #fff;\n border-color: #373b3e;\n}\n\n.table-responsive {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n}\n\n@media (max-width: 575.98px) {\n .table-responsive-sm {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n }\n}\n@media (max-width: 767.98px) {\n .table-responsive-md {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n }\n}\n@media (max-width: 991.98px) {\n .table-responsive-lg {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n }\n}\n@media (max-width: 1199.98px) {\n .table-responsive-xl {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n }\n}\n@media (max-width: 1399.98px) {\n .table-responsive-xxl {\n overflow-x: auto;\n -webkit-overflow-scrolling: touch;\n }\n}\n.form-label {\n margin-bottom: 0.5rem;\n}\n\n.col-form-label {\n padding-top: calc(0.375rem + 1px);\n padding-bottom: calc(0.375rem + 1px);\n margin-bottom: 0;\n font-size: inherit;\n line-height: 1.5;\n}\n\n.col-form-label-lg {\n padding-top: calc(0.5rem + 1px);\n padding-bottom: calc(0.5rem + 1px);\n font-size: 1.25rem;\n}\n\n.col-form-label-sm {\n padding-top: calc(0.25rem + 1px);\n padding-bottom: calc(0.25rem + 1px);\n font-size: 0.875rem;\n}\n\n.form-text {\n margin-top: 0.25rem;\n font-size: 0.875em;\n color: #6c757d;\n}\n\n.form-control {\n display: block;\n width: 100%;\n padding: 0.375rem 0.75rem;\n font-size: 1rem;\n font-weight: 400;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid #ced4da;\n appearance: none;\n border-radius: 0.25rem;\n transition: border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-control {\n transition: none;\n }\n}\n.form-control[type=file] {\n overflow: hidden;\n}\n.form-control[type=file]:not(:disabled):not([readonly]) {\n cursor: pointer;\n}\n.form-control:focus {\n color: #212529;\n background-color: #fff;\n border-color: #86b7fe;\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.form-control::-webkit-date-and-time-value {\n height: 1.5em;\n}\n.form-control::placeholder {\n color: #6c757d;\n opacity: 1;\n}\n.form-control:disabled, .form-control[readonly] {\n background-color: #e9ecef;\n opacity: 1;\n}\n.form-control::file-selector-button {\n padding: 0.375rem 0.75rem;\n margin: -0.375rem -0.75rem;\n margin-inline-end: 0.75rem;\n color: #212529;\n background-color: #e9ecef;\n pointer-events: none;\n border-color: inherit;\n border-style: solid;\n border-width: 0;\n border-inline-end-width: 1px;\n border-radius: 0;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-control::file-selector-button {\n transition: none;\n }\n}\n.form-control:hover:not(:disabled):not([readonly])::file-selector-button {\n background-color: #dde0e3;\n}\n.form-control::-webkit-file-upload-button {\n padding: 0.375rem 0.75rem;\n margin: -0.375rem -0.75rem;\n margin-inline-end: 0.75rem;\n color: #212529;\n background-color: #e9ecef;\n pointer-events: none;\n border-color: inherit;\n border-style: solid;\n border-width: 0;\n border-inline-end-width: 1px;\n border-radius: 0;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-control::-webkit-file-upload-button {\n transition: none;\n }\n}\n.form-control:hover:not(:disabled):not([readonly])::-webkit-file-upload-button {\n background-color: #dde0e3;\n}\n\n.form-control-plaintext {\n display: block;\n width: 100%;\n padding: 0.375rem 0;\n margin-bottom: 0;\n line-height: 1.5;\n color: #212529;\n background-color: transparent;\n border: solid transparent;\n border-width: 1px 0;\n}\n.form-control-plaintext.form-control-sm, .form-control-plaintext.form-control-lg {\n padding-right: 0;\n padding-left: 0;\n}\n\n.form-control-sm {\n min-height: calc(1.5em + 0.5rem + 2px);\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n.form-control-sm::file-selector-button {\n padding: 0.25rem 0.5rem;\n margin: -0.25rem -0.5rem;\n margin-inline-end: 0.5rem;\n}\n.form-control-sm::-webkit-file-upload-button {\n padding: 0.25rem 0.5rem;\n margin: -0.25rem -0.5rem;\n margin-inline-end: 0.5rem;\n}\n\n.form-control-lg {\n min-height: calc(1.5em + 1rem + 2px);\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n.form-control-lg::file-selector-button {\n padding: 0.5rem 1rem;\n margin: -0.5rem -1rem;\n margin-inline-end: 1rem;\n}\n.form-control-lg::-webkit-file-upload-button {\n padding: 0.5rem 1rem;\n margin: -0.5rem -1rem;\n margin-inline-end: 1rem;\n}\n\ntextarea.form-control {\n min-height: calc(1.5em + 0.75rem + 2px);\n}\ntextarea.form-control-sm {\n min-height: calc(1.5em + 0.5rem + 2px);\n}\ntextarea.form-control-lg {\n min-height: calc(1.5em + 1rem + 2px);\n}\n\n.form-control-color {\n width: 3rem;\n height: auto;\n padding: 0.375rem;\n}\n.form-control-color:not(:disabled):not([readonly]) {\n cursor: pointer;\n}\n.form-control-color::-moz-color-swatch {\n height: 1.5em;\n border-radius: 0.25rem;\n}\n.form-control-color::-webkit-color-swatch {\n height: 1.5em;\n border-radius: 0.25rem;\n}\n\n.form-select {\n display: block;\n width: 100%;\n padding: 0.375rem 2.25rem 0.375rem 0.75rem;\n -moz-padding-start: calc(0.75rem - 3px);\n font-size: 1rem;\n font-weight: 400;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e\");\n background-repeat: no-repeat;\n background-position: right 0.75rem center;\n background-size: 16px 12px;\n border: 1px solid #ced4da;\n border-radius: 0.25rem;\n transition: border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n appearance: none;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-select {\n transition: none;\n }\n}\n.form-select:focus {\n border-color: #86b7fe;\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.form-select[multiple], .form-select[size]:not([size=\"1\"]) {\n padding-right: 0.75rem;\n background-image: none;\n}\n.form-select:disabled {\n background-color: #e9ecef;\n}\n.form-select:-moz-focusring {\n color: transparent;\n text-shadow: 0 0 0 #212529;\n}\n\n.form-select-sm {\n padding-top: 0.25rem;\n padding-bottom: 0.25rem;\n padding-left: 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.form-select-lg {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n padding-left: 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.form-check {\n display: block;\n min-height: 1.5rem;\n padding-left: 1.5em;\n margin-bottom: 0.125rem;\n}\n.form-check .form-check-input {\n float: left;\n margin-left: -1.5em;\n}\n\n.form-check-input {\n width: 1em;\n height: 1em;\n margin-top: 0.25em;\n vertical-align: top;\n background-color: #fff;\n background-repeat: no-repeat;\n background-position: center;\n background-size: contain;\n border: 1px solid rgba(0, 0, 0, 0.25);\n appearance: none;\n color-adjust: exact;\n}\n.form-check-input[type=checkbox] {\n border-radius: 0.25em;\n}\n.form-check-input[type=radio] {\n border-radius: 50%;\n}\n.form-check-input:active {\n filter: brightness(90%);\n}\n.form-check-input:focus {\n border-color: #86b7fe;\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.form-check-input:checked {\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.form-check-input:checked[type=checkbox] {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3e%3cpath fill='none' stroke='%23fff' stroke-linecap='round' stroke-linejoin='round' stroke-width='3' d='M6 10l3 3l6-6'/%3e%3c/svg%3e\");\n}\n.form-check-input:checked[type=radio] {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='2' fill='%23fff'/%3e%3c/svg%3e\");\n}\n.form-check-input[type=checkbox]:indeterminate {\n background-color: #0d6efd;\n border-color: #0d6efd;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3e%3cpath fill='none' stroke='%23fff' stroke-linecap='round' stroke-linejoin='round' stroke-width='3' d='M6 10h8'/%3e%3c/svg%3e\");\n}\n.form-check-input:disabled {\n pointer-events: none;\n filter: none;\n opacity: 0.5;\n}\n.form-check-input[disabled] ~ .form-check-label, .form-check-input:disabled ~ .form-check-label {\n opacity: 0.5;\n}\n\n.form-switch {\n padding-left: 2.5em;\n}\n.form-switch .form-check-input {\n width: 2em;\n margin-left: -2.5em;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='rgba%280, 0, 0, 0.25%29'/%3e%3c/svg%3e\");\n background-position: left center;\n border-radius: 2em;\n transition: background-position 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-switch .form-check-input {\n transition: none;\n }\n}\n.form-switch .form-check-input:focus {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='%2386b7fe'/%3e%3c/svg%3e\");\n}\n.form-switch .form-check-input:checked {\n background-position: right center;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3e%3ccircle r='3' fill='%23fff'/%3e%3c/svg%3e\");\n}\n\n.form-check-inline {\n display: inline-block;\n margin-right: 1rem;\n}\n\n.btn-check {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n.btn-check[disabled] + .btn, .btn-check:disabled + .btn {\n pointer-events: none;\n filter: none;\n opacity: 0.65;\n}\n\n.form-range {\n width: 100%;\n height: 1.5rem;\n padding: 0;\n background-color: transparent;\n appearance: none;\n}\n.form-range:focus {\n outline: 0;\n}\n.form-range:focus::-webkit-slider-thumb {\n box-shadow: 0 0 0 1px #fff, 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.form-range:focus::-moz-range-thumb {\n box-shadow: 0 0 0 1px #fff, 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.form-range::-moz-focus-outer {\n border: 0;\n}\n.form-range::-webkit-slider-thumb {\n width: 1rem;\n height: 1rem;\n margin-top: -0.25rem;\n background-color: #0d6efd;\n border: 0;\n border-radius: 1rem;\n transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n appearance: none;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-range::-webkit-slider-thumb {\n transition: none;\n }\n}\n.form-range::-webkit-slider-thumb:active {\n background-color: #b6d4fe;\n}\n.form-range::-webkit-slider-runnable-track {\n width: 100%;\n height: 0.5rem;\n color: transparent;\n cursor: pointer;\n background-color: #dee2e6;\n border-color: transparent;\n border-radius: 1rem;\n}\n.form-range::-moz-range-thumb {\n width: 1rem;\n height: 1rem;\n background-color: #0d6efd;\n border: 0;\n border-radius: 1rem;\n transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n appearance: none;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-range::-moz-range-thumb {\n transition: none;\n }\n}\n.form-range::-moz-range-thumb:active {\n background-color: #b6d4fe;\n}\n.form-range::-moz-range-track {\n width: 100%;\n height: 0.5rem;\n color: transparent;\n cursor: pointer;\n background-color: #dee2e6;\n border-color: transparent;\n border-radius: 1rem;\n}\n.form-range:disabled {\n pointer-events: none;\n}\n.form-range:disabled::-webkit-slider-thumb {\n background-color: #adb5bd;\n}\n.form-range:disabled::-moz-range-thumb {\n background-color: #adb5bd;\n}\n\n.form-floating {\n position: relative;\n}\n.form-floating > .form-control,\n.form-floating > .form-select {\n height: calc(3.5rem + 2px);\n line-height: 1.25;\n}\n.form-floating > label {\n position: absolute;\n top: 0;\n left: 0;\n height: 100%;\n padding: 1rem 0.75rem;\n pointer-events: none;\n border: 1px solid transparent;\n transform-origin: 0 0;\n transition: opacity 0.1s ease-in-out, transform 0.1s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .form-floating > label {\n transition: none;\n }\n}\n.form-floating > .form-control {\n padding: 1rem 0.75rem;\n}\n.form-floating > .form-control::placeholder {\n color: transparent;\n}\n.form-floating > .form-control:focus, .form-floating > .form-control:not(:placeholder-shown) {\n padding-top: 1.625rem;\n padding-bottom: 0.625rem;\n}\n.form-floating > .form-control:-webkit-autofill {\n padding-top: 1.625rem;\n padding-bottom: 0.625rem;\n}\n.form-floating > .form-select {\n padding-top: 1.625rem;\n padding-bottom: 0.625rem;\n}\n.form-floating > .form-control:focus ~ label,\n.form-floating > .form-control:not(:placeholder-shown) ~ label,\n.form-floating > .form-select ~ label {\n opacity: 0.65;\n transform: scale(0.85) translateY(-0.5rem) translateX(0.15rem);\n}\n.form-floating > .form-control:-webkit-autofill ~ label {\n opacity: 0.65;\n transform: scale(0.85) translateY(-0.5rem) translateX(0.15rem);\n}\n\n.input-group {\n position: relative;\n display: flex;\n flex-wrap: wrap;\n align-items: stretch;\n width: 100%;\n}\n.input-group > .form-control,\n.input-group > .form-select {\n position: relative;\n flex: 1 1 auto;\n width: 1%;\n min-width: 0;\n}\n.input-group > .form-control:focus,\n.input-group > .form-select:focus {\n z-index: 3;\n}\n.input-group .btn {\n position: relative;\n z-index: 2;\n}\n.input-group .btn:focus {\n z-index: 3;\n}\n\n.input-group-text {\n display: flex;\n align-items: center;\n padding: 0.375rem 0.75rem;\n font-size: 1rem;\n font-weight: 400;\n line-height: 1.5;\n color: #212529;\n text-align: center;\n white-space: nowrap;\n background-color: #e9ecef;\n border: 1px solid #ced4da;\n border-radius: 0.25rem;\n}\n\n.input-group-lg > .form-control,\n.input-group-lg > .form-select,\n.input-group-lg > .input-group-text,\n.input-group-lg > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.input-group-sm > .form-control,\n.input-group-sm > .form-select,\n.input-group-sm > .input-group-text,\n.input-group-sm > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.input-group-lg > .form-select,\n.input-group-sm > .form-select {\n padding-right: 3rem;\n}\n\n.input-group:not(.has-validation) > :not(:last-child):not(.dropdown-toggle):not(.dropdown-menu),\n.input-group:not(.has-validation) > .dropdown-toggle:nth-last-child(n+3) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.input-group.has-validation > :nth-last-child(n+3):not(.dropdown-toggle):not(.dropdown-menu),\n.input-group.has-validation > .dropdown-toggle:nth-last-child(n+4) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.input-group > :not(:first-child):not(.dropdown-menu):not(.valid-tooltip):not(.valid-feedback):not(.invalid-tooltip):not(.invalid-feedback) {\n margin-left: -1px;\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.valid-feedback {\n display: none;\n width: 100%;\n margin-top: 0.25rem;\n font-size: 0.875em;\n color: #198754;\n}\n\n.valid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n max-width: 100%;\n padding: 0.25rem 0.5rem;\n margin-top: 0.1rem;\n font-size: 0.875rem;\n color: #fff;\n background-color: rgba(25, 135, 84, 0.9);\n border-radius: 0.25rem;\n}\n\n.was-validated :valid ~ .valid-feedback,\n.was-validated :valid ~ .valid-tooltip,\n.is-valid ~ .valid-feedback,\n.is-valid ~ .valid-tooltip {\n display: block;\n}\n\n.was-validated .form-control:valid, .form-control.is-valid {\n border-color: #198754;\n padding-right: calc(1.5em + 0.75rem);\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3e%3cpath fill='%23198754' d='M2.3 6.73L.6 4.53c-.4-1.04.46-1.4 1.1-.8l1.1 1.4 3.4-3.8c.6-.63 1.6-.27 1.2.7l-4 4.6c-.43.5-.8.4-1.1.1z'/%3e%3c/svg%3e\");\n background-repeat: no-repeat;\n background-position: right calc(0.375em + 0.1875rem) center;\n background-size: calc(0.75em + 0.375rem) calc(0.75em + 0.375rem);\n}\n.was-validated .form-control:valid:focus, .form-control.is-valid:focus {\n border-color: #198754;\n box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25);\n}\n\n.was-validated textarea.form-control:valid, textarea.form-control.is-valid {\n padding-right: calc(1.5em + 0.75rem);\n background-position: top calc(0.375em + 0.1875rem) right calc(0.375em + 0.1875rem);\n}\n\n.was-validated .form-select:valid, .form-select.is-valid {\n border-color: #198754;\n}\n.was-validated .form-select:valid:not([multiple]):not([size]), .was-validated .form-select:valid:not([multiple])[size=\"1\"], .form-select.is-valid:not([multiple]):not([size]), .form-select.is-valid:not([multiple])[size=\"1\"] {\n padding-right: 4.125rem;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e\"), url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3e%3cpath fill='%23198754' d='M2.3 6.73L.6 4.53c-.4-1.04.46-1.4 1.1-.8l1.1 1.4 3.4-3.8c.6-.63 1.6-.27 1.2.7l-4 4.6c-.43.5-.8.4-1.1.1z'/%3e%3c/svg%3e\");\n background-position: right 0.75rem center, center right 2.25rem;\n background-size: 16px 12px, calc(0.75em + 0.375rem) calc(0.75em + 0.375rem);\n}\n.was-validated .form-select:valid:focus, .form-select.is-valid:focus {\n border-color: #198754;\n box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25);\n}\n\n.was-validated .form-check-input:valid, .form-check-input.is-valid {\n border-color: #198754;\n}\n.was-validated .form-check-input:valid:checked, .form-check-input.is-valid:checked {\n background-color: #198754;\n}\n.was-validated .form-check-input:valid:focus, .form-check-input.is-valid:focus {\n box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.25);\n}\n.was-validated .form-check-input:valid ~ .form-check-label, .form-check-input.is-valid ~ .form-check-label {\n color: #198754;\n}\n\n.form-check-inline .form-check-input ~ .valid-feedback {\n margin-left: 0.5em;\n}\n\n.was-validated .input-group .form-control:valid, .input-group .form-control.is-valid,\n.was-validated .input-group .form-select:valid,\n.input-group .form-select.is-valid {\n z-index: 1;\n}\n.was-validated .input-group .form-control:valid:focus, .input-group .form-control.is-valid:focus,\n.was-validated .input-group .form-select:valid:focus,\n.input-group .form-select.is-valid:focus {\n z-index: 3;\n}\n\n.invalid-feedback {\n display: none;\n width: 100%;\n margin-top: 0.25rem;\n font-size: 0.875em;\n color: #dc3545;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n max-width: 100%;\n padding: 0.25rem 0.5rem;\n margin-top: 0.1rem;\n font-size: 0.875rem;\n color: #fff;\n background-color: rgba(220, 53, 69, 0.9);\n border-radius: 0.25rem;\n}\n\n.was-validated :invalid ~ .invalid-feedback,\n.was-validated :invalid ~ .invalid-tooltip,\n.is-invalid ~ .invalid-feedback,\n.is-invalid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-control:invalid, .form-control.is-invalid {\n border-color: #dc3545;\n padding-right: calc(1.5em + 0.75rem);\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' width='12' height='12' fill='none' stroke='%23dc3545'%3e%3ccircle cx='6' cy='6' r='4.5'/%3e%3cpath stroke-linejoin='round' d='M5.8 3.6h.4L6 6.5z'/%3e%3ccircle cx='6' cy='8.2' r='.6' fill='%23dc3545' stroke='none'/%3e%3c/svg%3e\");\n background-repeat: no-repeat;\n background-position: right calc(0.375em + 0.1875rem) center;\n background-size: calc(0.75em + 0.375rem) calc(0.75em + 0.375rem);\n}\n.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus {\n border-color: #dc3545;\n box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25);\n}\n\n.was-validated textarea.form-control:invalid, textarea.form-control.is-invalid {\n padding-right: calc(1.5em + 0.75rem);\n background-position: top calc(0.375em + 0.1875rem) right calc(0.375em + 0.1875rem);\n}\n\n.was-validated .form-select:invalid, .form-select.is-invalid {\n border-color: #dc3545;\n}\n.was-validated .form-select:invalid:not([multiple]):not([size]), .was-validated .form-select:invalid:not([multiple])[size=\"1\"], .form-select.is-invalid:not([multiple]):not([size]), .form-select.is-invalid:not([multiple])[size=\"1\"] {\n padding-right: 4.125rem;\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23343a40' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='M2 5l6 6 6-6'/%3e%3c/svg%3e\"), url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' width='12' height='12' fill='none' stroke='%23dc3545'%3e%3ccircle cx='6' cy='6' r='4.5'/%3e%3cpath stroke-linejoin='round' d='M5.8 3.6h.4L6 6.5z'/%3e%3ccircle cx='6' cy='8.2' r='.6' fill='%23dc3545' stroke='none'/%3e%3c/svg%3e\");\n background-position: right 0.75rem center, center right 2.25rem;\n background-size: 16px 12px, calc(0.75em + 0.375rem) calc(0.75em + 0.375rem);\n}\n.was-validated .form-select:invalid:focus, .form-select.is-invalid:focus {\n border-color: #dc3545;\n box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .form-check-input:invalid, .form-check-input.is-invalid {\n border-color: #dc3545;\n}\n.was-validated .form-check-input:invalid:checked, .form-check-input.is-invalid:checked {\n background-color: #dc3545;\n}\n.was-validated .form-check-input:invalid:focus, .form-check-input.is-invalid:focus {\n box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.25);\n}\n.was-validated .form-check-input:invalid ~ .form-check-label, .form-check-input.is-invalid ~ .form-check-label {\n color: #dc3545;\n}\n\n.form-check-inline .form-check-input ~ .invalid-feedback {\n margin-left: 0.5em;\n}\n\n.was-validated .input-group .form-control:invalid, .input-group .form-control.is-invalid,\n.was-validated .input-group .form-select:invalid,\n.input-group .form-select.is-invalid {\n z-index: 2;\n}\n.was-validated .input-group .form-control:invalid:focus, .input-group .form-control.is-invalid:focus,\n.was-validated .input-group .form-select:invalid:focus,\n.input-group .form-select.is-invalid:focus {\n z-index: 3;\n}\n\n.btn {\n display: inline-block;\n font-weight: 400;\n line-height: 1.5;\n color: #212529;\n text-align: center;\n text-decoration: none;\n vertical-align: middle;\n cursor: pointer;\n user-select: none;\n background-color: transparent;\n border: 1px solid transparent;\n padding: 0.375rem 0.75rem;\n font-size: 1rem;\n border-radius: 0.25rem;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .btn {\n transition: none;\n }\n}\n.btn:hover {\n color: #212529;\n}\n.btn-check:focus + .btn, .btn:focus {\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n.btn:disabled, .btn.disabled, fieldset:disabled .btn {\n pointer-events: none;\n opacity: 0.65;\n}\n\n.btn-primary {\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.btn-primary:hover {\n color: #fff;\n background-color: #0b5ed7;\n border-color: #0a58ca;\n}\n.btn-check:focus + .btn-primary, .btn-primary:focus {\n color: #fff;\n background-color: #0b5ed7;\n border-color: #0a58ca;\n box-shadow: 0 0 0 0.25rem rgba(49, 132, 253, 0.5);\n}\n.btn-check:checked + .btn-primary, .btn-check:active + .btn-primary, .btn-primary:active, .btn-primary.active, .show > .btn-primary.dropdown-toggle {\n color: #fff;\n background-color: #0a58ca;\n border-color: #0a53be;\n}\n.btn-check:checked + .btn-primary:focus, .btn-check:active + .btn-primary:focus, .btn-primary:active:focus, .btn-primary.active:focus, .show > .btn-primary.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(49, 132, 253, 0.5);\n}\n.btn-primary:disabled, .btn-primary.disabled {\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n\n.btn-secondary {\n color: #fff;\n background-color: #6c757d;\n border-color: #6c757d;\n}\n.btn-secondary:hover {\n color: #fff;\n background-color: #5c636a;\n border-color: #565e64;\n}\n.btn-check:focus + .btn-secondary, .btn-secondary:focus {\n color: #fff;\n background-color: #5c636a;\n border-color: #565e64;\n box-shadow: 0 0 0 0.25rem rgba(130, 138, 145, 0.5);\n}\n.btn-check:checked + .btn-secondary, .btn-check:active + .btn-secondary, .btn-secondary:active, .btn-secondary.active, .show > .btn-secondary.dropdown-toggle {\n color: #fff;\n background-color: #565e64;\n border-color: #51585e;\n}\n.btn-check:checked + .btn-secondary:focus, .btn-check:active + .btn-secondary:focus, .btn-secondary:active:focus, .btn-secondary.active:focus, .show > .btn-secondary.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(130, 138, 145, 0.5);\n}\n.btn-secondary:disabled, .btn-secondary.disabled {\n color: #fff;\n background-color: #6c757d;\n border-color: #6c757d;\n}\n\n.btn-success {\n color: #fff;\n background-color: #198754;\n border-color: #198754;\n}\n.btn-success:hover {\n color: #fff;\n background-color: #157347;\n border-color: #146c43;\n}\n.btn-check:focus + .btn-success, .btn-success:focus {\n color: #fff;\n background-color: #157347;\n border-color: #146c43;\n box-shadow: 0 0 0 0.25rem rgba(60, 153, 110, 0.5);\n}\n.btn-check:checked + .btn-success, .btn-check:active + .btn-success, .btn-success:active, .btn-success.active, .show > .btn-success.dropdown-toggle {\n color: #fff;\n background-color: #146c43;\n border-color: #13653f;\n}\n.btn-check:checked + .btn-success:focus, .btn-check:active + .btn-success:focus, .btn-success:active:focus, .btn-success.active:focus, .show > .btn-success.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(60, 153, 110, 0.5);\n}\n.btn-success:disabled, .btn-success.disabled {\n color: #fff;\n background-color: #198754;\n border-color: #198754;\n}\n\n.btn-info {\n color: #000;\n background-color: #0dcaf0;\n border-color: #0dcaf0;\n}\n.btn-info:hover {\n color: #000;\n background-color: #31d2f2;\n border-color: #25cff2;\n}\n.btn-check:focus + .btn-info, .btn-info:focus {\n color: #000;\n background-color: #31d2f2;\n border-color: #25cff2;\n box-shadow: 0 0 0 0.25rem rgba(11, 172, 204, 0.5);\n}\n.btn-check:checked + .btn-info, .btn-check:active + .btn-info, .btn-info:active, .btn-info.active, .show > .btn-info.dropdown-toggle {\n color: #000;\n background-color: #3dd5f3;\n border-color: #25cff2;\n}\n.btn-check:checked + .btn-info:focus, .btn-check:active + .btn-info:focus, .btn-info:active:focus, .btn-info.active:focus, .show > .btn-info.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(11, 172, 204, 0.5);\n}\n.btn-info:disabled, .btn-info.disabled {\n color: #000;\n background-color: #0dcaf0;\n border-color: #0dcaf0;\n}\n\n.btn-warning {\n color: #000;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n.btn-warning:hover {\n color: #000;\n background-color: #ffca2c;\n border-color: #ffc720;\n}\n.btn-check:focus + .btn-warning, .btn-warning:focus {\n color: #000;\n background-color: #ffca2c;\n border-color: #ffc720;\n box-shadow: 0 0 0 0.25rem rgba(217, 164, 6, 0.5);\n}\n.btn-check:checked + .btn-warning, .btn-check:active + .btn-warning, .btn-warning:active, .btn-warning.active, .show > .btn-warning.dropdown-toggle {\n color: #000;\n background-color: #ffcd39;\n border-color: #ffc720;\n}\n.btn-check:checked + .btn-warning:focus, .btn-check:active + .btn-warning:focus, .btn-warning:active:focus, .btn-warning.active:focus, .show > .btn-warning.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(217, 164, 6, 0.5);\n}\n.btn-warning:disabled, .btn-warning.disabled {\n color: #000;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-danger {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n.btn-danger:hover {\n color: #fff;\n background-color: #bb2d3b;\n border-color: #b02a37;\n}\n.btn-check:focus + .btn-danger, .btn-danger:focus {\n color: #fff;\n background-color: #bb2d3b;\n border-color: #b02a37;\n box-shadow: 0 0 0 0.25rem rgba(225, 83, 97, 0.5);\n}\n.btn-check:checked + .btn-danger, .btn-check:active + .btn-danger, .btn-danger:active, .btn-danger.active, .show > .btn-danger.dropdown-toggle {\n color: #fff;\n background-color: #b02a37;\n border-color: #a52834;\n}\n.btn-check:checked + .btn-danger:focus, .btn-check:active + .btn-danger:focus, .btn-danger:active:focus, .btn-danger.active:focus, .show > .btn-danger.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(225, 83, 97, 0.5);\n}\n.btn-danger:disabled, .btn-danger.disabled {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-light {\n color: #000;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n.btn-light:hover {\n color: #000;\n background-color: #f9fafb;\n border-color: #f9fafb;\n}\n.btn-check:focus + .btn-light, .btn-light:focus {\n color: #000;\n background-color: #f9fafb;\n border-color: #f9fafb;\n box-shadow: 0 0 0 0.25rem rgba(211, 212, 213, 0.5);\n}\n.btn-check:checked + .btn-light, .btn-check:active + .btn-light, .btn-light:active, .btn-light.active, .show > .btn-light.dropdown-toggle {\n color: #000;\n background-color: #f9fafb;\n border-color: #f9fafb;\n}\n.btn-check:checked + .btn-light:focus, .btn-check:active + .btn-light:focus, .btn-light:active:focus, .btn-light.active:focus, .show > .btn-light.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(211, 212, 213, 0.5);\n}\n.btn-light:disabled, .btn-light.disabled {\n color: #000;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-dark {\n color: #fff;\n background-color: #212529;\n border-color: #212529;\n}\n.btn-dark:hover {\n color: #fff;\n background-color: #1c1f23;\n border-color: #1a1e21;\n}\n.btn-check:focus + .btn-dark, .btn-dark:focus {\n color: #fff;\n background-color: #1c1f23;\n border-color: #1a1e21;\n box-shadow: 0 0 0 0.25rem rgba(66, 70, 73, 0.5);\n}\n.btn-check:checked + .btn-dark, .btn-check:active + .btn-dark, .btn-dark:active, .btn-dark.active, .show > .btn-dark.dropdown-toggle {\n color: #fff;\n background-color: #1a1e21;\n border-color: #191c1f;\n}\n.btn-check:checked + .btn-dark:focus, .btn-check:active + .btn-dark:focus, .btn-dark:active:focus, .btn-dark.active:focus, .show > .btn-dark.dropdown-toggle:focus {\n box-shadow: 0 0 0 0.25rem rgba(66, 70, 73, 0.5);\n}\n.btn-dark:disabled, .btn-dark.disabled {\n color: #fff;\n background-color: #212529;\n border-color: #212529;\n}\n\n.btn-outline-primary {\n color: #0d6efd;\n border-color: #0d6efd;\n}\n.btn-outline-primary:hover {\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.btn-check:focus + .btn-outline-primary, .btn-outline-primary:focus {\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.5);\n}\n.btn-check:checked + .btn-outline-primary, .btn-check:active + .btn-outline-primary, .btn-outline-primary:active, .btn-outline-primary.active, .btn-outline-primary.dropdown-toggle.show {\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.btn-check:checked + .btn-outline-primary:focus, .btn-check:active + .btn-outline-primary:focus, .btn-outline-primary:active:focus, .btn-outline-primary.active:focus, .btn-outline-primary.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.5);\n}\n.btn-outline-primary:disabled, .btn-outline-primary.disabled {\n color: #0d6efd;\n background-color: transparent;\n}\n\n.btn-outline-secondary {\n color: #6c757d;\n border-color: #6c757d;\n}\n.btn-outline-secondary:hover {\n color: #fff;\n background-color: #6c757d;\n border-color: #6c757d;\n}\n.btn-check:focus + .btn-outline-secondary, .btn-outline-secondary:focus {\n box-shadow: 0 0 0 0.25rem rgba(108, 117, 125, 0.5);\n}\n.btn-check:checked + .btn-outline-secondary, .btn-check:active + .btn-outline-secondary, .btn-outline-secondary:active, .btn-outline-secondary.active, .btn-outline-secondary.dropdown-toggle.show {\n color: #fff;\n background-color: #6c757d;\n border-color: #6c757d;\n}\n.btn-check:checked + .btn-outline-secondary:focus, .btn-check:active + .btn-outline-secondary:focus, .btn-outline-secondary:active:focus, .btn-outline-secondary.active:focus, .btn-outline-secondary.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(108, 117, 125, 0.5);\n}\n.btn-outline-secondary:disabled, .btn-outline-secondary.disabled {\n color: #6c757d;\n background-color: transparent;\n}\n\n.btn-outline-success {\n color: #198754;\n border-color: #198754;\n}\n.btn-outline-success:hover {\n color: #fff;\n background-color: #198754;\n border-color: #198754;\n}\n.btn-check:focus + .btn-outline-success, .btn-outline-success:focus {\n box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.5);\n}\n.btn-check:checked + .btn-outline-success, .btn-check:active + .btn-outline-success, .btn-outline-success:active, .btn-outline-success.active, .btn-outline-success.dropdown-toggle.show {\n color: #fff;\n background-color: #198754;\n border-color: #198754;\n}\n.btn-check:checked + .btn-outline-success:focus, .btn-check:active + .btn-outline-success:focus, .btn-outline-success:active:focus, .btn-outline-success.active:focus, .btn-outline-success.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(25, 135, 84, 0.5);\n}\n.btn-outline-success:disabled, .btn-outline-success.disabled {\n color: #198754;\n background-color: transparent;\n}\n\n.btn-outline-info {\n color: #0dcaf0;\n border-color: #0dcaf0;\n}\n.btn-outline-info:hover {\n color: #000;\n background-color: #0dcaf0;\n border-color: #0dcaf0;\n}\n.btn-check:focus + .btn-outline-info, .btn-outline-info:focus {\n box-shadow: 0 0 0 0.25rem rgba(13, 202, 240, 0.5);\n}\n.btn-check:checked + .btn-outline-info, .btn-check:active + .btn-outline-info, .btn-outline-info:active, .btn-outline-info.active, .btn-outline-info.dropdown-toggle.show {\n color: #000;\n background-color: #0dcaf0;\n border-color: #0dcaf0;\n}\n.btn-check:checked + .btn-outline-info:focus, .btn-check:active + .btn-outline-info:focus, .btn-outline-info:active:focus, .btn-outline-info.active:focus, .btn-outline-info.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(13, 202, 240, 0.5);\n}\n.btn-outline-info:disabled, .btn-outline-info.disabled {\n color: #0dcaf0;\n background-color: transparent;\n}\n\n.btn-outline-warning {\n color: #ffc107;\n border-color: #ffc107;\n}\n.btn-outline-warning:hover {\n color: #000;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n.btn-check:focus + .btn-outline-warning, .btn-outline-warning:focus {\n box-shadow: 0 0 0 0.25rem rgba(255, 193, 7, 0.5);\n}\n.btn-check:checked + .btn-outline-warning, .btn-check:active + .btn-outline-warning, .btn-outline-warning:active, .btn-outline-warning.active, .btn-outline-warning.dropdown-toggle.show {\n color: #000;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n.btn-check:checked + .btn-outline-warning:focus, .btn-check:active + .btn-outline-warning:focus, .btn-outline-warning:active:focus, .btn-outline-warning.active:focus, .btn-outline-warning.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(255, 193, 7, 0.5);\n}\n.btn-outline-warning:disabled, .btn-outline-warning.disabled {\n color: #ffc107;\n background-color: transparent;\n}\n\n.btn-outline-danger {\n color: #dc3545;\n border-color: #dc3545;\n}\n.btn-outline-danger:hover {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n.btn-check:focus + .btn-outline-danger, .btn-outline-danger:focus {\n box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.5);\n}\n.btn-check:checked + .btn-outline-danger, .btn-check:active + .btn-outline-danger, .btn-outline-danger:active, .btn-outline-danger.active, .btn-outline-danger.dropdown-toggle.show {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n.btn-check:checked + .btn-outline-danger:focus, .btn-check:active + .btn-outline-danger:focus, .btn-outline-danger:active:focus, .btn-outline-danger.active:focus, .btn-outline-danger.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(220, 53, 69, 0.5);\n}\n.btn-outline-danger:disabled, .btn-outline-danger.disabled {\n color: #dc3545;\n background-color: transparent;\n}\n\n.btn-outline-light {\n color: #f8f9fa;\n border-color: #f8f9fa;\n}\n.btn-outline-light:hover {\n color: #000;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n.btn-check:focus + .btn-outline-light, .btn-outline-light:focus {\n box-shadow: 0 0 0 0.25rem rgba(248, 249, 250, 0.5);\n}\n.btn-check:checked + .btn-outline-light, .btn-check:active + .btn-outline-light, .btn-outline-light:active, .btn-outline-light.active, .btn-outline-light.dropdown-toggle.show {\n color: #000;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n.btn-check:checked + .btn-outline-light:focus, .btn-check:active + .btn-outline-light:focus, .btn-outline-light:active:focus, .btn-outline-light.active:focus, .btn-outline-light.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(248, 249, 250, 0.5);\n}\n.btn-outline-light:disabled, .btn-outline-light.disabled {\n color: #f8f9fa;\n background-color: transparent;\n}\n\n.btn-outline-dark {\n color: #212529;\n border-color: #212529;\n}\n.btn-outline-dark:hover {\n color: #fff;\n background-color: #212529;\n border-color: #212529;\n}\n.btn-check:focus + .btn-outline-dark, .btn-outline-dark:focus {\n box-shadow: 0 0 0 0.25rem rgba(33, 37, 41, 0.5);\n}\n.btn-check:checked + .btn-outline-dark, .btn-check:active + .btn-outline-dark, .btn-outline-dark:active, .btn-outline-dark.active, .btn-outline-dark.dropdown-toggle.show {\n color: #fff;\n background-color: #212529;\n border-color: #212529;\n}\n.btn-check:checked + .btn-outline-dark:focus, .btn-check:active + .btn-outline-dark:focus, .btn-outline-dark:active:focus, .btn-outline-dark.active:focus, .btn-outline-dark.dropdown-toggle.show:focus {\n box-shadow: 0 0 0 0.25rem rgba(33, 37, 41, 0.5);\n}\n.btn-outline-dark:disabled, .btn-outline-dark.disabled {\n color: #212529;\n background-color: transparent;\n}\n\n.btn-link {\n font-weight: 400;\n color: #0d6efd;\n text-decoration: underline;\n}\n.btn-link:hover {\n color: #0a58ca;\n}\n.btn-link:disabled, .btn-link.disabled {\n color: #6c757d;\n}\n\n.btn-lg, .btn-group-lg > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.btn-sm, .btn-group-sm > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.fade {\n transition: opacity 0.15s linear;\n}\n@media (prefers-reduced-motion: reduce) {\n .fade {\n transition: none;\n }\n}\n.fade:not(.show) {\n opacity: 0;\n}\n\n.collapse:not(.show) {\n display: none;\n}\n\n.collapsing {\n height: 0;\n overflow: hidden;\n transition: height 0.35s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .collapsing {\n transition: none;\n }\n}\n.collapsing.collapse-horizontal {\n width: 0;\n height: auto;\n transition: width 0.35s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .collapsing.collapse-horizontal {\n transition: none;\n }\n}\n\n.dropup,\n.dropend,\n.dropdown,\n.dropstart {\n position: relative;\n}\n\n.dropdown-toggle {\n white-space: nowrap;\n}\n.dropdown-toggle::after {\n display: inline-block;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid;\n border-right: 0.3em solid transparent;\n border-bottom: 0;\n border-left: 0.3em solid transparent;\n}\n.dropdown-toggle:empty::after {\n margin-left: 0;\n}\n\n.dropdown-menu {\n position: absolute;\n z-index: 1000;\n display: none;\n min-width: 10rem;\n padding: 0.5rem 0;\n margin: 0;\n font-size: 1rem;\n color: #212529;\n text-align: left;\n list-style: none;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n.dropdown-menu[data-bs-popper] {\n top: 100%;\n left: 0;\n margin-top: 0.125rem;\n}\n\n.dropdown-menu-start {\n --bs-position: start;\n}\n.dropdown-menu-start[data-bs-popper] {\n right: auto;\n left: 0;\n}\n\n.dropdown-menu-end {\n --bs-position: end;\n}\n.dropdown-menu-end[data-bs-popper] {\n right: 0;\n left: auto;\n}\n\n@media (min-width: 576px) {\n .dropdown-menu-sm-start {\n --bs-position: start;\n }\n .dropdown-menu-sm-start[data-bs-popper] {\n right: auto;\n left: 0;\n }\n\n .dropdown-menu-sm-end {\n --bs-position: end;\n }\n .dropdown-menu-sm-end[data-bs-popper] {\n right: 0;\n left: auto;\n }\n}\n@media (min-width: 768px) {\n .dropdown-menu-md-start {\n --bs-position: start;\n }\n .dropdown-menu-md-start[data-bs-popper] {\n right: auto;\n left: 0;\n }\n\n .dropdown-menu-md-end {\n --bs-position: end;\n }\n .dropdown-menu-md-end[data-bs-popper] {\n right: 0;\n left: auto;\n }\n}\n@media (min-width: 992px) {\n .dropdown-menu-lg-start {\n --bs-position: start;\n }\n .dropdown-menu-lg-start[data-bs-popper] {\n right: auto;\n left: 0;\n }\n\n .dropdown-menu-lg-end {\n --bs-position: end;\n }\n .dropdown-menu-lg-end[data-bs-popper] {\n right: 0;\n left: auto;\n }\n}\n@media (min-width: 1200px) {\n .dropdown-menu-xl-start {\n --bs-position: start;\n }\n .dropdown-menu-xl-start[data-bs-popper] {\n right: auto;\n left: 0;\n }\n\n .dropdown-menu-xl-end {\n --bs-position: end;\n }\n .dropdown-menu-xl-end[data-bs-popper] {\n right: 0;\n left: auto;\n }\n}\n@media (min-width: 1400px) {\n .dropdown-menu-xxl-start {\n --bs-position: start;\n }\n .dropdown-menu-xxl-start[data-bs-popper] {\n right: auto;\n left: 0;\n }\n\n .dropdown-menu-xxl-end {\n --bs-position: end;\n }\n .dropdown-menu-xxl-end[data-bs-popper] {\n right: 0;\n left: auto;\n }\n}\n.dropup .dropdown-menu[data-bs-popper] {\n top: auto;\n bottom: 100%;\n margin-top: 0;\n margin-bottom: 0.125rem;\n}\n.dropup .dropdown-toggle::after {\n display: inline-block;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0;\n border-right: 0.3em solid transparent;\n border-bottom: 0.3em solid;\n border-left: 0.3em solid transparent;\n}\n.dropup .dropdown-toggle:empty::after {\n margin-left: 0;\n}\n\n.dropend .dropdown-menu[data-bs-popper] {\n top: 0;\n right: auto;\n left: 100%;\n margin-top: 0;\n margin-left: 0.125rem;\n}\n.dropend .dropdown-toggle::after {\n display: inline-block;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid transparent;\n border-right: 0;\n border-bottom: 0.3em solid transparent;\n border-left: 0.3em solid;\n}\n.dropend .dropdown-toggle:empty::after {\n margin-left: 0;\n}\n.dropend .dropdown-toggle::after {\n vertical-align: 0;\n}\n\n.dropstart .dropdown-menu[data-bs-popper] {\n top: 0;\n right: 100%;\n left: auto;\n margin-top: 0;\n margin-right: 0.125rem;\n}\n.dropstart .dropdown-toggle::after {\n display: inline-block;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n}\n.dropstart .dropdown-toggle::after {\n display: none;\n}\n.dropstart .dropdown-toggle::before {\n display: inline-block;\n margin-right: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid transparent;\n border-right: 0.3em solid;\n border-bottom: 0.3em solid transparent;\n}\n.dropstart .dropdown-toggle:empty::after {\n margin-left: 0;\n}\n.dropstart .dropdown-toggle::before {\n vertical-align: 0;\n}\n\n.dropdown-divider {\n height: 0;\n margin: 0.5rem 0;\n overflow: hidden;\n border-top: 1px solid rgba(0, 0, 0, 0.15);\n}\n\n.dropdown-item {\n display: block;\n width: 100%;\n padding: 0.25rem 1rem;\n clear: both;\n font-weight: 400;\n color: #212529;\n text-align: inherit;\n text-decoration: none;\n white-space: nowrap;\n background-color: transparent;\n border: 0;\n}\n.dropdown-item:hover, .dropdown-item:focus {\n color: #1e2125;\n background-color: #e9ecef;\n}\n.dropdown-item.active, .dropdown-item:active {\n color: #fff;\n text-decoration: none;\n background-color: #0d6efd;\n}\n.dropdown-item.disabled, .dropdown-item:disabled {\n color: #adb5bd;\n pointer-events: none;\n background-color: transparent;\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n.dropdown-header {\n display: block;\n padding: 0.5rem 1rem;\n margin-bottom: 0;\n font-size: 0.875rem;\n color: #6c757d;\n white-space: nowrap;\n}\n\n.dropdown-item-text {\n display: block;\n padding: 0.25rem 1rem;\n color: #212529;\n}\n\n.dropdown-menu-dark {\n color: #dee2e6;\n background-color: #343a40;\n border-color: rgba(0, 0, 0, 0.15);\n}\n.dropdown-menu-dark .dropdown-item {\n color: #dee2e6;\n}\n.dropdown-menu-dark .dropdown-item:hover, .dropdown-menu-dark .dropdown-item:focus {\n color: #fff;\n background-color: rgba(255, 255, 255, 0.15);\n}\n.dropdown-menu-dark .dropdown-item.active, .dropdown-menu-dark .dropdown-item:active {\n color: #fff;\n background-color: #0d6efd;\n}\n.dropdown-menu-dark .dropdown-item.disabled, .dropdown-menu-dark .dropdown-item:disabled {\n color: #adb5bd;\n}\n.dropdown-menu-dark .dropdown-divider {\n border-color: rgba(0, 0, 0, 0.15);\n}\n.dropdown-menu-dark .dropdown-item-text {\n color: #dee2e6;\n}\n.dropdown-menu-dark .dropdown-header {\n color: #adb5bd;\n}\n\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-flex;\n vertical-align: middle;\n}\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n flex: 1 1 auto;\n}\n.btn-group > .btn-check:checked + .btn,\n.btn-group > .btn-check:focus + .btn,\n.btn-group > .btn:hover,\n.btn-group > .btn:focus,\n.btn-group > .btn:active,\n.btn-group > .btn.active,\n.btn-group-vertical > .btn-check:checked + .btn,\n.btn-group-vertical > .btn-check:focus + .btn,\n.btn-group-vertical > .btn:hover,\n.btn-group-vertical > .btn:focus,\n.btn-group-vertical > .btn:active,\n.btn-group-vertical > .btn.active {\n z-index: 1;\n}\n\n.btn-toolbar {\n display: flex;\n flex-wrap: wrap;\n justify-content: flex-start;\n}\n.btn-toolbar .input-group {\n width: auto;\n}\n\n.btn-group > .btn:not(:first-child),\n.btn-group > .btn-group:not(:first-child) {\n margin-left: -1px;\n}\n.btn-group > .btn:not(:last-child):not(.dropdown-toggle),\n.btn-group > .btn-group:not(:last-child) > .btn {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.btn-group > .btn:nth-child(n+3),\n.btn-group > :not(.btn-check) + .btn,\n.btn-group > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.dropdown-toggle-split {\n padding-right: 0.5625rem;\n padding-left: 0.5625rem;\n}\n.dropdown-toggle-split::after, .dropup .dropdown-toggle-split::after, .dropend .dropdown-toggle-split::after {\n margin-left: 0;\n}\n.dropstart .dropdown-toggle-split::before {\n margin-right: 0;\n}\n\n.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split {\n padding-right: 0.375rem;\n padding-left: 0.375rem;\n}\n\n.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split {\n padding-right: 0.75rem;\n padding-left: 0.75rem;\n}\n\n.btn-group-vertical {\n flex-direction: column;\n align-items: flex-start;\n justify-content: center;\n}\n.btn-group-vertical > .btn,\n.btn-group-vertical > .btn-group {\n width: 100%;\n}\n.btn-group-vertical > .btn:not(:first-child),\n.btn-group-vertical > .btn-group:not(:first-child) {\n margin-top: -1px;\n}\n.btn-group-vertical > .btn:not(:last-child):not(.dropdown-toggle),\n.btn-group-vertical > .btn-group:not(:last-child) > .btn {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn ~ .btn,\n.btn-group-vertical > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.nav {\n display: flex;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: 0.5rem 1rem;\n color: #0d6efd;\n text-decoration: none;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .nav-link {\n transition: none;\n }\n}\n.nav-link:hover, .nav-link:focus {\n color: #0a58ca;\n}\n.nav-link.disabled {\n color: #6c757d;\n pointer-events: none;\n cursor: default;\n}\n\n.nav-tabs {\n border-bottom: 1px solid #dee2e6;\n}\n.nav-tabs .nav-link {\n margin-bottom: -1px;\n background: none;\n border: 1px solid transparent;\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n.nav-tabs .nav-link:hover, .nav-tabs .nav-link:focus {\n border-color: #e9ecef #e9ecef #dee2e6;\n isolation: isolate;\n}\n.nav-tabs .nav-link.disabled {\n color: #6c757d;\n background-color: transparent;\n border-color: transparent;\n}\n.nav-tabs .nav-link.active,\n.nav-tabs .nav-item.show .nav-link {\n color: #495057;\n background-color: #fff;\n border-color: #dee2e6 #dee2e6 #fff;\n}\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.nav-pills .nav-link {\n background: none;\n border: 0;\n border-radius: 0.25rem;\n}\n.nav-pills .nav-link.active,\n.nav-pills .show > .nav-link {\n color: #fff;\n background-color: #0d6efd;\n}\n\n.nav-fill > .nav-link,\n.nav-fill .nav-item {\n flex: 1 1 auto;\n text-align: center;\n}\n\n.nav-justified > .nav-link,\n.nav-justified .nav-item {\n flex-basis: 0;\n flex-grow: 1;\n text-align: center;\n}\n\n.nav-fill .nav-item .nav-link,\n.nav-justified .nav-item .nav-link {\n width: 100%;\n}\n\n.tab-content > .tab-pane {\n display: none;\n}\n.tab-content > .active {\n display: block;\n}\n\n.navbar {\n position: relative;\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n}\n.navbar > .container,\n.navbar > .container-fluid,\n.navbar > .container-sm,\n.navbar > .container-md,\n.navbar > .container-lg,\n.navbar > .container-xl,\n.navbar > .container-xxl {\n display: flex;\n flex-wrap: inherit;\n align-items: center;\n justify-content: space-between;\n}\n.navbar-brand {\n padding-top: 0.3125rem;\n padding-bottom: 0.3125rem;\n margin-right: 1rem;\n font-size: 1.25rem;\n text-decoration: none;\n white-space: nowrap;\n}\n.navbar-nav {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n.navbar-nav .nav-link {\n padding-right: 0;\n padding-left: 0;\n}\n.navbar-nav .dropdown-menu {\n position: static;\n}\n\n.navbar-text {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n}\n\n.navbar-collapse {\n flex-basis: 100%;\n flex-grow: 1;\n align-items: center;\n}\n\n.navbar-toggler {\n padding: 0.25rem 0.75rem;\n font-size: 1.25rem;\n line-height: 1;\n background-color: transparent;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n transition: box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .navbar-toggler {\n transition: none;\n }\n}\n.navbar-toggler:hover {\n text-decoration: none;\n}\n.navbar-toggler:focus {\n text-decoration: none;\n outline: 0;\n box-shadow: 0 0 0 0.25rem;\n}\n\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n background-repeat: no-repeat;\n background-position: center;\n background-size: 100%;\n}\n\n.navbar-nav-scroll {\n max-height: var(--bs-scroll-height, 75vh);\n overflow-y: auto;\n}\n\n@media (min-width: 576px) {\n .navbar-expand-sm {\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-sm .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-sm .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n }\n .navbar-expand-sm .navbar-nav-scroll {\n overflow: visible;\n }\n .navbar-expand-sm .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n }\n .navbar-expand-sm .navbar-toggler {\n display: none;\n }\n .navbar-expand-sm .offcanvas-header {\n display: none;\n }\n .navbar-expand-sm .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n }\n .navbar-expand-sm .offcanvas-top,\n.navbar-expand-sm .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n }\n .navbar-expand-sm .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n }\n}\n@media (min-width: 768px) {\n .navbar-expand-md {\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-md .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-md .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n }\n .navbar-expand-md .navbar-nav-scroll {\n overflow: visible;\n }\n .navbar-expand-md .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n }\n .navbar-expand-md .navbar-toggler {\n display: none;\n }\n .navbar-expand-md .offcanvas-header {\n display: none;\n }\n .navbar-expand-md .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n }\n .navbar-expand-md .offcanvas-top,\n.navbar-expand-md .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n }\n .navbar-expand-md .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n }\n}\n@media (min-width: 992px) {\n .navbar-expand-lg {\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-lg .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-lg .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n }\n .navbar-expand-lg .navbar-nav-scroll {\n overflow: visible;\n }\n .navbar-expand-lg .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n }\n .navbar-expand-lg .navbar-toggler {\n display: none;\n }\n .navbar-expand-lg .offcanvas-header {\n display: none;\n }\n .navbar-expand-lg .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n }\n .navbar-expand-lg .offcanvas-top,\n.navbar-expand-lg .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n }\n .navbar-expand-lg .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n }\n}\n@media (min-width: 1200px) {\n .navbar-expand-xl {\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-xl .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-xl .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n }\n .navbar-expand-xl .navbar-nav-scroll {\n overflow: visible;\n }\n .navbar-expand-xl .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n }\n .navbar-expand-xl .navbar-toggler {\n display: none;\n }\n .navbar-expand-xl .offcanvas-header {\n display: none;\n }\n .navbar-expand-xl .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n }\n .navbar-expand-xl .offcanvas-top,\n.navbar-expand-xl .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n }\n .navbar-expand-xl .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n }\n}\n@media (min-width: 1400px) {\n .navbar-expand-xxl {\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-xxl .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-xxl .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-xxl .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n }\n .navbar-expand-xxl .navbar-nav-scroll {\n overflow: visible;\n }\n .navbar-expand-xxl .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n }\n .navbar-expand-xxl .navbar-toggler {\n display: none;\n }\n .navbar-expand-xxl .offcanvas-header {\n display: none;\n }\n .navbar-expand-xxl .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n }\n .navbar-expand-xxl .offcanvas-top,\n.navbar-expand-xxl .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n }\n .navbar-expand-xxl .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n }\n}\n.navbar-expand {\n flex-wrap: nowrap;\n justify-content: flex-start;\n}\n.navbar-expand .navbar-nav {\n flex-direction: row;\n}\n.navbar-expand .navbar-nav .dropdown-menu {\n position: absolute;\n}\n.navbar-expand .navbar-nav .nav-link {\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n}\n.navbar-expand .navbar-nav-scroll {\n overflow: visible;\n}\n.navbar-expand .navbar-collapse {\n display: flex !important;\n flex-basis: auto;\n}\n.navbar-expand .navbar-toggler {\n display: none;\n}\n.navbar-expand .offcanvas-header {\n display: none;\n}\n.navbar-expand .offcanvas {\n position: inherit;\n bottom: 0;\n z-index: 1000;\n flex-grow: 1;\n visibility: visible !important;\n background-color: transparent;\n border-right: 0;\n border-left: 0;\n transition: none;\n transform: none;\n}\n.navbar-expand .offcanvas-top,\n.navbar-expand .offcanvas-bottom {\n height: auto;\n border-top: 0;\n border-bottom: 0;\n}\n.navbar-expand .offcanvas-body {\n display: flex;\n flex-grow: 0;\n padding: 0;\n overflow-y: visible;\n}\n\n.navbar-light .navbar-brand {\n color: rgba(0, 0, 0, 0.9);\n}\n.navbar-light .navbar-brand:hover, .navbar-light .navbar-brand:focus {\n color: rgba(0, 0, 0, 0.9);\n}\n.navbar-light .navbar-nav .nav-link {\n color: rgba(0, 0, 0, 0.55);\n}\n.navbar-light .navbar-nav .nav-link:hover, .navbar-light .navbar-nav .nav-link:focus {\n color: rgba(0, 0, 0, 0.7);\n}\n.navbar-light .navbar-nav .nav-link.disabled {\n color: rgba(0, 0, 0, 0.3);\n}\n.navbar-light .navbar-nav .show > .nav-link,\n.navbar-light .navbar-nav .nav-link.active {\n color: rgba(0, 0, 0, 0.9);\n}\n.navbar-light .navbar-toggler {\n color: rgba(0, 0, 0, 0.55);\n border-color: rgba(0, 0, 0, 0.1);\n}\n.navbar-light .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%280, 0, 0, 0.55%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e\");\n}\n.navbar-light .navbar-text {\n color: rgba(0, 0, 0, 0.55);\n}\n.navbar-light .navbar-text a,\n.navbar-light .navbar-text a:hover,\n.navbar-light .navbar-text a:focus {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-dark .navbar-brand {\n color: #fff;\n}\n.navbar-dark .navbar-brand:hover, .navbar-dark .navbar-brand:focus {\n color: #fff;\n}\n.navbar-dark .navbar-nav .nav-link {\n color: rgba(255, 255, 255, 0.55);\n}\n.navbar-dark .navbar-nav .nav-link:hover, .navbar-dark .navbar-nav .nav-link:focus {\n color: rgba(255, 255, 255, 0.75);\n}\n.navbar-dark .navbar-nav .nav-link.disabled {\n color: rgba(255, 255, 255, 0.25);\n}\n.navbar-dark .navbar-nav .show > .nav-link,\n.navbar-dark .navbar-nav .nav-link.active {\n color: #fff;\n}\n.navbar-dark .navbar-toggler {\n color: rgba(255, 255, 255, 0.55);\n border-color: rgba(255, 255, 255, 0.1);\n}\n.navbar-dark .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%28255, 255, 255, 0.55%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e\");\n}\n.navbar-dark .navbar-text {\n color: rgba(255, 255, 255, 0.55);\n}\n.navbar-dark .navbar-text a,\n.navbar-dark .navbar-text a:hover,\n.navbar-dark .navbar-text a:focus {\n color: #fff;\n}\n\n.card {\n position: relative;\n display: flex;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: border-box;\n border: 1px solid rgba(0, 0, 0, 0.125);\n border-radius: 0.25rem;\n}\n.card > hr {\n margin-right: 0;\n margin-left: 0;\n}\n.card > .list-group {\n border-top: inherit;\n border-bottom: inherit;\n}\n.card > .list-group:first-child {\n border-top-width: 0;\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n.card > .list-group:last-child {\n border-bottom-width: 0;\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n.card > .card-header + .list-group,\n.card > .list-group + .card-footer {\n border-top: 0;\n}\n\n.card-body {\n flex: 1 1 auto;\n padding: 1rem 1rem;\n}\n\n.card-title {\n margin-bottom: 0.5rem;\n}\n\n.card-subtitle {\n margin-top: -0.25rem;\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link + .card-link {\n margin-left: 1rem;\n}\n\n.card-header {\n padding: 0.5rem 1rem;\n margin-bottom: 0;\n background-color: rgba(0, 0, 0, 0.03);\n border-bottom: 1px solid rgba(0, 0, 0, 0.125);\n}\n.card-header:first-child {\n border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0;\n}\n\n.card-footer {\n padding: 0.5rem 1rem;\n background-color: rgba(0, 0, 0, 0.03);\n border-top: 1px solid rgba(0, 0, 0, 0.125);\n}\n.card-footer:last-child {\n border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px);\n}\n\n.card-header-tabs {\n margin-right: -0.5rem;\n margin-bottom: -0.5rem;\n margin-left: -0.5rem;\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -0.5rem;\n margin-left: -0.5rem;\n}\n\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: 1rem;\n border-radius: calc(0.25rem - 1px);\n}\n\n.card-img,\n.card-img-top,\n.card-img-bottom {\n width: 100%;\n}\n\n.card-img,\n.card-img-top {\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n\n.card-img,\n.card-img-bottom {\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n\n.card-group > .card {\n margin-bottom: 0.75rem;\n}\n@media (min-width: 576px) {\n .card-group {\n display: flex;\n flex-flow: row wrap;\n }\n .card-group > .card {\n flex: 1 0 0%;\n margin-bottom: 0;\n }\n .card-group > .card + .card {\n margin-left: 0;\n border-left: 0;\n }\n .card-group > .card:not(:last-child) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n }\n .card-group > .card:not(:last-child) .card-img-top,\n.card-group > .card:not(:last-child) .card-header {\n border-top-right-radius: 0;\n }\n .card-group > .card:not(:last-child) .card-img-bottom,\n.card-group > .card:not(:last-child) .card-footer {\n border-bottom-right-radius: 0;\n }\n .card-group > .card:not(:first-child) {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n }\n .card-group > .card:not(:first-child) .card-img-top,\n.card-group > .card:not(:first-child) .card-header {\n border-top-left-radius: 0;\n }\n .card-group > .card:not(:first-child) .card-img-bottom,\n.card-group > .card:not(:first-child) .card-footer {\n border-bottom-left-radius: 0;\n }\n}\n\n.accordion-button {\n position: relative;\n display: flex;\n align-items: center;\n width: 100%;\n padding: 1rem 1.25rem;\n font-size: 1rem;\n color: #212529;\n text-align: left;\n background-color: #fff;\n border: 0;\n border-radius: 0;\n overflow-anchor: none;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out, border-radius 0.15s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .accordion-button {\n transition: none;\n }\n}\n.accordion-button:not(.collapsed) {\n color: #0c63e4;\n background-color: #e7f1ff;\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.125);\n}\n.accordion-button:not(.collapsed)::after {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%230c63e4'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e\");\n transform: rotate(-180deg);\n}\n.accordion-button::after {\n flex-shrink: 0;\n width: 1.25rem;\n height: 1.25rem;\n margin-left: auto;\n content: \"\";\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23212529'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e\");\n background-repeat: no-repeat;\n background-size: 1.25rem;\n transition: transform 0.2s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .accordion-button::after {\n transition: none;\n }\n}\n.accordion-button:hover {\n z-index: 2;\n}\n.accordion-button:focus {\n z-index: 3;\n border-color: #86b7fe;\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n\n.accordion-header {\n margin-bottom: 0;\n}\n\n.accordion-item {\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.125);\n}\n.accordion-item:first-of-type {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n.accordion-item:first-of-type .accordion-button {\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n.accordion-item:not(:first-of-type) {\n border-top: 0;\n}\n.accordion-item:last-of-type {\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n.accordion-item:last-of-type .accordion-button.collapsed {\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n.accordion-item:last-of-type .accordion-collapse {\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.accordion-body {\n padding: 1rem 1.25rem;\n}\n\n.accordion-flush .accordion-collapse {\n border-width: 0;\n}\n.accordion-flush .accordion-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n}\n.accordion-flush .accordion-item:first-child {\n border-top: 0;\n}\n.accordion-flush .accordion-item:last-child {\n border-bottom: 0;\n}\n.accordion-flush .accordion-item .accordion-button {\n border-radius: 0;\n}\n\n.breadcrumb {\n display: flex;\n flex-wrap: wrap;\n padding: 0 0;\n margin-bottom: 1rem;\n list-style: none;\n}\n\n.breadcrumb-item + .breadcrumb-item {\n padding-left: 0.5rem;\n}\n.breadcrumb-item + .breadcrumb-item::before {\n float: left;\n padding-right: 0.5rem;\n color: #6c757d;\n content: var(--bs-breadcrumb-divider, \"/\") /* rtl: var(--bs-breadcrumb-divider, \"/\") */;\n}\n.breadcrumb-item.active {\n color: #6c757d;\n}\n\n.pagination {\n display: flex;\n padding-left: 0;\n list-style: none;\n}\n\n.page-link {\n position: relative;\n display: block;\n color: #0d6efd;\n text-decoration: none;\n background-color: #fff;\n border: 1px solid #dee2e6;\n transition: color 0.15s ease-in-out, background-color 0.15s ease-in-out, border-color 0.15s ease-in-out, box-shadow 0.15s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .page-link {\n transition: none;\n }\n}\n.page-link:hover {\n z-index: 2;\n color: #0a58ca;\n background-color: #e9ecef;\n border-color: #dee2e6;\n}\n.page-link:focus {\n z-index: 3;\n color: #0a58ca;\n background-color: #e9ecef;\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n}\n\n.page-item:not(:first-child) .page-link {\n margin-left: -1px;\n}\n.page-item.active .page-link {\n z-index: 3;\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.page-item.disabled .page-link {\n color: #6c757d;\n pointer-events: none;\n background-color: #fff;\n border-color: #dee2e6;\n}\n\n.page-link {\n padding: 0.375rem 0.75rem;\n}\n\n.page-item:first-child .page-link {\n border-top-left-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n.page-item:last-child .page-link {\n border-top-right-radius: 0.25rem;\n border-bottom-right-radius: 0.25rem;\n}\n\n.pagination-lg .page-link {\n padding: 0.75rem 1.5rem;\n font-size: 1.25rem;\n}\n.pagination-lg .page-item:first-child .page-link {\n border-top-left-radius: 0.3rem;\n border-bottom-left-radius: 0.3rem;\n}\n.pagination-lg .page-item:last-child .page-link {\n border-top-right-radius: 0.3rem;\n border-bottom-right-radius: 0.3rem;\n}\n\n.pagination-sm .page-link {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n}\n.pagination-sm .page-item:first-child .page-link {\n border-top-left-radius: 0.2rem;\n border-bottom-left-radius: 0.2rem;\n}\n.pagination-sm .page-item:last-child .page-link {\n border-top-right-radius: 0.2rem;\n border-bottom-right-radius: 0.2rem;\n}\n\n.badge {\n display: inline-block;\n padding: 0.35em 0.65em;\n font-size: 0.75em;\n font-weight: 700;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: 0.25rem;\n}\n.badge:empty {\n display: none;\n}\n\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n.alert {\n position: relative;\n padding: 1rem 1rem;\n margin-bottom: 1rem;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.alert-heading {\n color: inherit;\n}\n\n.alert-link {\n font-weight: 700;\n}\n\n.alert-dismissible {\n padding-right: 3rem;\n}\n.alert-dismissible .btn-close {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2;\n padding: 1.25rem 1rem;\n}\n\n.alert-primary {\n color: #084298;\n background-color: #cfe2ff;\n border-color: #b6d4fe;\n}\n.alert-primary .alert-link {\n color: #06357a;\n}\n\n.alert-secondary {\n color: #41464b;\n background-color: #e2e3e5;\n border-color: #d3d6d8;\n}\n.alert-secondary .alert-link {\n color: #34383c;\n}\n\n.alert-success {\n color: #0f5132;\n background-color: #d1e7dd;\n border-color: #badbcc;\n}\n.alert-success .alert-link {\n color: #0c4128;\n}\n\n.alert-info {\n color: #055160;\n background-color: #cff4fc;\n border-color: #b6effb;\n}\n.alert-info .alert-link {\n color: #04414d;\n}\n\n.alert-warning {\n color: #664d03;\n background-color: #fff3cd;\n border-color: #ffecb5;\n}\n.alert-warning .alert-link {\n color: #523e02;\n}\n\n.alert-danger {\n color: #842029;\n background-color: #f8d7da;\n border-color: #f5c2c7;\n}\n.alert-danger .alert-link {\n color: #6a1a21;\n}\n\n.alert-light {\n color: #636464;\n background-color: #fefefe;\n border-color: #fdfdfe;\n}\n.alert-light .alert-link {\n color: #4f5050;\n}\n\n.alert-dark {\n color: #141619;\n background-color: #d3d3d4;\n border-color: #bcbebf;\n}\n.alert-dark .alert-link {\n color: #101214;\n}\n\n@keyframes progress-bar-stripes {\n 0% {\n background-position-x: 1rem;\n }\n}\n.progress {\n display: flex;\n height: 1rem;\n overflow: hidden;\n font-size: 0.75rem;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.progress-bar {\n display: flex;\n flex-direction: column;\n justify-content: center;\n overflow: hidden;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n background-color: #0d6efd;\n transition: width 0.6s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .progress-bar {\n transition: none;\n }\n}\n\n.progress-bar-striped {\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 1rem 1rem;\n}\n\n.progress-bar-animated {\n animation: 1s linear infinite progress-bar-stripes;\n}\n@media (prefers-reduced-motion: reduce) {\n .progress-bar-animated {\n animation: none;\n }\n}\n\n.list-group {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n border-radius: 0.25rem;\n}\n\n.list-group-numbered {\n list-style-type: none;\n counter-reset: section;\n}\n.list-group-numbered > li::before {\n content: counters(section, \".\") \". \";\n counter-increment: section;\n}\n\n.list-group-item-action {\n width: 100%;\n color: #495057;\n text-align: inherit;\n}\n.list-group-item-action:hover, .list-group-item-action:focus {\n z-index: 1;\n color: #495057;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n.list-group-item-action:active {\n color: #212529;\n background-color: #e9ecef;\n}\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 0.5rem 1rem;\n color: #212529;\n text-decoration: none;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.125);\n}\n.list-group-item:first-child {\n border-top-left-radius: inherit;\n border-top-right-radius: inherit;\n}\n.list-group-item:last-child {\n border-bottom-right-radius: inherit;\n border-bottom-left-radius: inherit;\n}\n.list-group-item.disabled, .list-group-item:disabled {\n color: #6c757d;\n pointer-events: none;\n background-color: #fff;\n}\n.list-group-item.active {\n z-index: 2;\n color: #fff;\n background-color: #0d6efd;\n border-color: #0d6efd;\n}\n.list-group-item + .list-group-item {\n border-top-width: 0;\n}\n.list-group-item + .list-group-item.active {\n margin-top: -1px;\n border-top-width: 1px;\n}\n\n.list-group-horizontal {\n flex-direction: row;\n}\n.list-group-horizontal > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n}\n.list-group-horizontal > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n}\n.list-group-horizontal > .list-group-item.active {\n margin-top: 0;\n}\n.list-group-horizontal > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n}\n.list-group-horizontal > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n}\n\n@media (min-width: 576px) {\n .list-group-horizontal-sm {\n flex-direction: row;\n }\n .list-group-horizontal-sm > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n }\n .list-group-horizontal-sm > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n }\n .list-group-horizontal-sm > .list-group-item.active {\n margin-top: 0;\n }\n .list-group-horizontal-sm > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n }\n .list-group-horizontal-sm > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n }\n}\n@media (min-width: 768px) {\n .list-group-horizontal-md {\n flex-direction: row;\n }\n .list-group-horizontal-md > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n }\n .list-group-horizontal-md > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n }\n .list-group-horizontal-md > .list-group-item.active {\n margin-top: 0;\n }\n .list-group-horizontal-md > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n }\n .list-group-horizontal-md > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n }\n}\n@media (min-width: 992px) {\n .list-group-horizontal-lg {\n flex-direction: row;\n }\n .list-group-horizontal-lg > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n }\n .list-group-horizontal-lg > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n }\n .list-group-horizontal-lg > .list-group-item.active {\n margin-top: 0;\n }\n .list-group-horizontal-lg > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n }\n .list-group-horizontal-lg > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n }\n}\n@media (min-width: 1200px) {\n .list-group-horizontal-xl {\n flex-direction: row;\n }\n .list-group-horizontal-xl > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n }\n .list-group-horizontal-xl > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n }\n .list-group-horizontal-xl > .list-group-item.active {\n margin-top: 0;\n }\n .list-group-horizontal-xl > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n }\n .list-group-horizontal-xl > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n }\n}\n@media (min-width: 1400px) {\n .list-group-horizontal-xxl {\n flex-direction: row;\n }\n .list-group-horizontal-xxl > .list-group-item:first-child {\n border-bottom-left-radius: 0.25rem;\n border-top-right-radius: 0;\n }\n .list-group-horizontal-xxl > .list-group-item:last-child {\n border-top-right-radius: 0.25rem;\n border-bottom-left-radius: 0;\n }\n .list-group-horizontal-xxl > .list-group-item.active {\n margin-top: 0;\n }\n .list-group-horizontal-xxl > .list-group-item + .list-group-item {\n border-top-width: 1px;\n border-left-width: 0;\n }\n .list-group-horizontal-xxl > .list-group-item + .list-group-item.active {\n margin-left: -1px;\n border-left-width: 1px;\n }\n}\n.list-group-flush {\n border-radius: 0;\n}\n.list-group-flush > .list-group-item {\n border-width: 0 0 1px;\n}\n.list-group-flush > .list-group-item:last-child {\n border-bottom-width: 0;\n}\n\n.list-group-item-primary {\n color: #084298;\n background-color: #cfe2ff;\n}\n.list-group-item-primary.list-group-item-action:hover, .list-group-item-primary.list-group-item-action:focus {\n color: #084298;\n background-color: #bacbe6;\n}\n.list-group-item-primary.list-group-item-action.active {\n color: #fff;\n background-color: #084298;\n border-color: #084298;\n}\n\n.list-group-item-secondary {\n color: #41464b;\n background-color: #e2e3e5;\n}\n.list-group-item-secondary.list-group-item-action:hover, .list-group-item-secondary.list-group-item-action:focus {\n color: #41464b;\n background-color: #cbccce;\n}\n.list-group-item-secondary.list-group-item-action.active {\n color: #fff;\n background-color: #41464b;\n border-color: #41464b;\n}\n\n.list-group-item-success {\n color: #0f5132;\n background-color: #d1e7dd;\n}\n.list-group-item-success.list-group-item-action:hover, .list-group-item-success.list-group-item-action:focus {\n color: #0f5132;\n background-color: #bcd0c7;\n}\n.list-group-item-success.list-group-item-action.active {\n color: #fff;\n background-color: #0f5132;\n border-color: #0f5132;\n}\n\n.list-group-item-info {\n color: #055160;\n background-color: #cff4fc;\n}\n.list-group-item-info.list-group-item-action:hover, .list-group-item-info.list-group-item-action:focus {\n color: #055160;\n background-color: #badce3;\n}\n.list-group-item-info.list-group-item-action.active {\n color: #fff;\n background-color: #055160;\n border-color: #055160;\n}\n\n.list-group-item-warning {\n color: #664d03;\n background-color: #fff3cd;\n}\n.list-group-item-warning.list-group-item-action:hover, .list-group-item-warning.list-group-item-action:focus {\n color: #664d03;\n background-color: #e6dbb9;\n}\n.list-group-item-warning.list-group-item-action.active {\n color: #fff;\n background-color: #664d03;\n border-color: #664d03;\n}\n\n.list-group-item-danger {\n color: #842029;\n background-color: #f8d7da;\n}\n.list-group-item-danger.list-group-item-action:hover, .list-group-item-danger.list-group-item-action:focus {\n color: #842029;\n background-color: #dfc2c4;\n}\n.list-group-item-danger.list-group-item-action.active {\n color: #fff;\n background-color: #842029;\n border-color: #842029;\n}\n\n.list-group-item-light {\n color: #636464;\n background-color: #fefefe;\n}\n.list-group-item-light.list-group-item-action:hover, .list-group-item-light.list-group-item-action:focus {\n color: #636464;\n background-color: #e5e5e5;\n}\n.list-group-item-light.list-group-item-action.active {\n color: #fff;\n background-color: #636464;\n border-color: #636464;\n}\n\n.list-group-item-dark {\n color: #141619;\n background-color: #d3d3d4;\n}\n.list-group-item-dark.list-group-item-action:hover, .list-group-item-dark.list-group-item-action:focus {\n color: #141619;\n background-color: #bebebf;\n}\n.list-group-item-dark.list-group-item-action.active {\n color: #fff;\n background-color: #141619;\n border-color: #141619;\n}\n\n.btn-close {\n box-sizing: content-box;\n width: 1em;\n height: 1em;\n padding: 0.25em 0.25em;\n color: #000;\n background: transparent url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23000'%3e%3cpath d='M.293.293a1 1 0 011.414 0L8 6.586 14.293.293a1 1 0 111.414 1.414L9.414 8l6.293 6.293a1 1 0 01-1.414 1.414L8 9.414l-6.293 6.293a1 1 0 01-1.414-1.414L6.586 8 .293 1.707a1 1 0 010-1.414z'/%3e%3c/svg%3e\") center/1em auto no-repeat;\n border: 0;\n border-radius: 0.25rem;\n opacity: 0.5;\n}\n.btn-close:hover {\n color: #000;\n text-decoration: none;\n opacity: 0.75;\n}\n.btn-close:focus {\n outline: 0;\n box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);\n opacity: 1;\n}\n.btn-close:disabled, .btn-close.disabled {\n pointer-events: none;\n user-select: none;\n opacity: 0.25;\n}\n\n.btn-close-white {\n filter: invert(1) grayscale(100%) brightness(200%);\n}\n\n.toast {\n width: 350px;\n max-width: 100%;\n font-size: 0.875rem;\n pointer-events: auto;\n background-color: rgba(255, 255, 255, 0.85);\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.1);\n box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n.toast.showing {\n opacity: 0;\n}\n.toast:not(.show) {\n display: none;\n}\n\n.toast-container {\n width: max-content;\n max-width: 100%;\n pointer-events: none;\n}\n.toast-container > :not(:last-child) {\n margin-bottom: 0.75rem;\n}\n\n.toast-header {\n display: flex;\n align-items: center;\n padding: 0.5rem 0.75rem;\n color: #6c757d;\n background-color: rgba(255, 255, 255, 0.85);\n background-clip: padding-box;\n border-bottom: 1px solid rgba(0, 0, 0, 0.05);\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n.toast-header .btn-close {\n margin-right: -0.375rem;\n margin-left: 0.75rem;\n}\n\n.toast-body {\n padding: 0.75rem;\n word-wrap: break-word;\n}\n\n.modal {\n position: fixed;\n top: 0;\n left: 0;\n z-index: 1055;\n display: none;\n width: 100%;\n height: 100%;\n overflow-x: hidden;\n overflow-y: auto;\n outline: 0;\n}\n\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 0.5rem;\n pointer-events: none;\n}\n.modal.fade .modal-dialog {\n transition: transform 0.3s ease-out;\n transform: translate(0, -50px);\n}\n@media (prefers-reduced-motion: reduce) {\n .modal.fade .modal-dialog {\n transition: none;\n }\n}\n.modal.show .modal-dialog {\n transform: none;\n}\n.modal.modal-static .modal-dialog {\n transform: scale(1.02);\n}\n\n.modal-dialog-scrollable {\n height: calc(100% - 1rem);\n}\n.modal-dialog-scrollable .modal-content {\n max-height: 100%;\n overflow: hidden;\n}\n.modal-dialog-scrollable .modal-body {\n overflow-y: auto;\n}\n\n.modal-dialog-centered {\n display: flex;\n align-items: center;\n min-height: calc(100% - 1rem);\n}\n\n.modal-content {\n position: relative;\n display: flex;\n flex-direction: column;\n width: 100%;\n pointer-events: auto;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n outline: 0;\n}\n\n.modal-backdrop {\n position: fixed;\n top: 0;\n left: 0;\n z-index: 1050;\n width: 100vw;\n height: 100vh;\n background-color: #000;\n}\n.modal-backdrop.fade {\n opacity: 0;\n}\n.modal-backdrop.show {\n opacity: 0.5;\n}\n\n.modal-header {\n display: flex;\n flex-shrink: 0;\n align-items: center;\n justify-content: space-between;\n padding: 1rem 1rem;\n border-bottom: 1px solid #dee2e6;\n border-top-left-radius: calc(0.3rem - 1px);\n border-top-right-radius: calc(0.3rem - 1px);\n}\n.modal-header .btn-close {\n padding: 0.5rem 0.5rem;\n margin: -0.5rem -0.5rem -0.5rem auto;\n}\n\n.modal-title {\n margin-bottom: 0;\n line-height: 1.5;\n}\n\n.modal-body {\n position: relative;\n flex: 1 1 auto;\n padding: 1rem;\n}\n\n.modal-footer {\n display: flex;\n flex-wrap: wrap;\n flex-shrink: 0;\n align-items: center;\n justify-content: flex-end;\n padding: 0.75rem;\n border-top: 1px solid #dee2e6;\n border-bottom-right-radius: calc(0.3rem - 1px);\n border-bottom-left-radius: calc(0.3rem - 1px);\n}\n.modal-footer > * {\n margin: 0.25rem;\n}\n\n@media (min-width: 576px) {\n .modal-dialog {\n max-width: 500px;\n margin: 1.75rem auto;\n }\n\n .modal-dialog-scrollable {\n height: calc(100% - 3.5rem);\n }\n\n .modal-dialog-centered {\n min-height: calc(100% - 3.5rem);\n }\n\n .modal-sm {\n max-width: 300px;\n }\n}\n@media (min-width: 992px) {\n .modal-lg,\n.modal-xl {\n max-width: 800px;\n }\n}\n@media (min-width: 1200px) {\n .modal-xl {\n max-width: 1140px;\n }\n}\n.modal-fullscreen {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n}\n.modal-fullscreen .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n}\n.modal-fullscreen .modal-header {\n border-radius: 0;\n}\n.modal-fullscreen .modal-body {\n overflow-y: auto;\n}\n.modal-fullscreen .modal-footer {\n border-radius: 0;\n}\n\n@media (max-width: 575.98px) {\n .modal-fullscreen-sm-down {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n }\n .modal-fullscreen-sm-down .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n }\n .modal-fullscreen-sm-down .modal-header {\n border-radius: 0;\n }\n .modal-fullscreen-sm-down .modal-body {\n overflow-y: auto;\n }\n .modal-fullscreen-sm-down .modal-footer {\n border-radius: 0;\n }\n}\n@media (max-width: 767.98px) {\n .modal-fullscreen-md-down {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n }\n .modal-fullscreen-md-down .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n }\n .modal-fullscreen-md-down .modal-header {\n border-radius: 0;\n }\n .modal-fullscreen-md-down .modal-body {\n overflow-y: auto;\n }\n .modal-fullscreen-md-down .modal-footer {\n border-radius: 0;\n }\n}\n@media (max-width: 991.98px) {\n .modal-fullscreen-lg-down {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n }\n .modal-fullscreen-lg-down .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n }\n .modal-fullscreen-lg-down .modal-header {\n border-radius: 0;\n }\n .modal-fullscreen-lg-down .modal-body {\n overflow-y: auto;\n }\n .modal-fullscreen-lg-down .modal-footer {\n border-radius: 0;\n }\n}\n@media (max-width: 1199.98px) {\n .modal-fullscreen-xl-down {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n }\n .modal-fullscreen-xl-down .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n }\n .modal-fullscreen-xl-down .modal-header {\n border-radius: 0;\n }\n .modal-fullscreen-xl-down .modal-body {\n overflow-y: auto;\n }\n .modal-fullscreen-xl-down .modal-footer {\n border-radius: 0;\n }\n}\n@media (max-width: 1399.98px) {\n .modal-fullscreen-xxl-down {\n width: 100vw;\n max-width: none;\n height: 100%;\n margin: 0;\n }\n .modal-fullscreen-xxl-down .modal-content {\n height: 100%;\n border: 0;\n border-radius: 0;\n }\n .modal-fullscreen-xxl-down .modal-header {\n border-radius: 0;\n }\n .modal-fullscreen-xxl-down .modal-body {\n overflow-y: auto;\n }\n .modal-fullscreen-xxl-down .modal-footer {\n border-radius: 0;\n }\n}\n.tooltip {\n position: absolute;\n z-index: 1080;\n display: block;\n margin: 0;\n font-family: var(--bs-font-sans-serif);\n font-style: normal;\n font-weight: 400;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n opacity: 0;\n}\n.tooltip.show {\n opacity: 0.9;\n}\n.tooltip .tooltip-arrow {\n position: absolute;\n display: block;\n width: 0.8rem;\n height: 0.4rem;\n}\n.tooltip .tooltip-arrow::before {\n position: absolute;\n content: \"\";\n border-color: transparent;\n border-style: solid;\n}\n\n.bs-tooltip-top, .bs-tooltip-auto[data-popper-placement^=top] {\n padding: 0.4rem 0;\n}\n.bs-tooltip-top .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=top] .tooltip-arrow {\n bottom: 0;\n}\n.bs-tooltip-top .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=top] .tooltip-arrow::before {\n top: -1px;\n border-width: 0.4rem 0.4rem 0;\n border-top-color: #000;\n}\n\n.bs-tooltip-end, .bs-tooltip-auto[data-popper-placement^=right] {\n padding: 0 0.4rem;\n}\n.bs-tooltip-end .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=right] .tooltip-arrow {\n left: 0;\n width: 0.4rem;\n height: 0.8rem;\n}\n.bs-tooltip-end .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=right] .tooltip-arrow::before {\n right: -1px;\n border-width: 0.4rem 0.4rem 0.4rem 0;\n border-right-color: #000;\n}\n\n.bs-tooltip-bottom, .bs-tooltip-auto[data-popper-placement^=bottom] {\n padding: 0.4rem 0;\n}\n.bs-tooltip-bottom .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=bottom] .tooltip-arrow {\n top: 0;\n}\n.bs-tooltip-bottom .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=bottom] .tooltip-arrow::before {\n bottom: -1px;\n border-width: 0 0.4rem 0.4rem;\n border-bottom-color: #000;\n}\n\n.bs-tooltip-start, .bs-tooltip-auto[data-popper-placement^=left] {\n padding: 0 0.4rem;\n}\n.bs-tooltip-start .tooltip-arrow, .bs-tooltip-auto[data-popper-placement^=left] .tooltip-arrow {\n right: 0;\n width: 0.4rem;\n height: 0.8rem;\n}\n.bs-tooltip-start .tooltip-arrow::before, .bs-tooltip-auto[data-popper-placement^=left] .tooltip-arrow::before {\n left: -1px;\n border-width: 0.4rem 0 0.4rem 0.4rem;\n border-left-color: #000;\n}\n\n.tooltip-inner {\n max-width: 200px;\n padding: 0.25rem 0.5rem;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 0.25rem;\n}\n\n.popover {\n position: absolute;\n top: 0;\n left: 0 /* rtl:ignore */;\n z-index: 1070;\n display: block;\n max-width: 276px;\n font-family: var(--bs-font-sans-serif);\n font-style: normal;\n font-weight: 400;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n}\n.popover .popover-arrow {\n position: absolute;\n display: block;\n width: 1rem;\n height: 0.5rem;\n}\n.popover .popover-arrow::before, .popover .popover-arrow::after {\n position: absolute;\n display: block;\n content: \"\";\n border-color: transparent;\n border-style: solid;\n}\n\n.bs-popover-top > .popover-arrow, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow {\n bottom: calc(-0.5rem - 1px);\n}\n.bs-popover-top > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow::before {\n bottom: 0;\n border-width: 0.5rem 0.5rem 0;\n border-top-color: rgba(0, 0, 0, 0.25);\n}\n.bs-popover-top > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=top] > .popover-arrow::after {\n bottom: 1px;\n border-width: 0.5rem 0.5rem 0;\n border-top-color: #fff;\n}\n\n.bs-popover-end > .popover-arrow, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow {\n left: calc(-0.5rem - 1px);\n width: 0.5rem;\n height: 1rem;\n}\n.bs-popover-end > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow::before {\n left: 0;\n border-width: 0.5rem 0.5rem 0.5rem 0;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n.bs-popover-end > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=right] > .popover-arrow::after {\n left: 1px;\n border-width: 0.5rem 0.5rem 0.5rem 0;\n border-right-color: #fff;\n}\n\n.bs-popover-bottom > .popover-arrow, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow {\n top: calc(-0.5rem - 1px);\n}\n.bs-popover-bottom > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow::before {\n top: 0;\n border-width: 0 0.5rem 0.5rem 0.5rem;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n}\n.bs-popover-bottom > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=bottom] > .popover-arrow::after {\n top: 1px;\n border-width: 0 0.5rem 0.5rem 0.5rem;\n border-bottom-color: #fff;\n}\n.bs-popover-bottom .popover-header::before, .bs-popover-auto[data-popper-placement^=bottom] .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 1rem;\n margin-left: -0.5rem;\n content: \"\";\n border-bottom: 1px solid #f0f0f0;\n}\n\n.bs-popover-start > .popover-arrow, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow {\n right: calc(-0.5rem - 1px);\n width: 0.5rem;\n height: 1rem;\n}\n.bs-popover-start > .popover-arrow::before, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow::before {\n right: 0;\n border-width: 0.5rem 0 0.5rem 0.5rem;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n.bs-popover-start > .popover-arrow::after, .bs-popover-auto[data-popper-placement^=left] > .popover-arrow::after {\n right: 1px;\n border-width: 0.5rem 0 0.5rem 0.5rem;\n border-left-color: #fff;\n}\n\n.popover-header {\n padding: 0.5rem 1rem;\n margin-bottom: 0;\n font-size: 1rem;\n background-color: #f0f0f0;\n border-bottom: 1px solid rgba(0, 0, 0, 0.2);\n border-top-left-radius: calc(0.3rem - 1px);\n border-top-right-radius: calc(0.3rem - 1px);\n}\n.popover-header:empty {\n display: none;\n}\n\n.popover-body {\n padding: 1rem 1rem;\n color: #212529;\n}\n\n.carousel {\n position: relative;\n}\n\n.carousel.pointer-event {\n touch-action: pan-y;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n.carousel-inner::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.carousel-item {\n position: relative;\n display: none;\n float: left;\n width: 100%;\n margin-right: -100%;\n backface-visibility: hidden;\n transition: transform 0.6s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .carousel-item {\n transition: none;\n }\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n/* rtl:begin:ignore */\n.carousel-item-next:not(.carousel-item-start),\n.active.carousel-item-end {\n transform: translateX(100%);\n}\n\n.carousel-item-prev:not(.carousel-item-end),\n.active.carousel-item-start {\n transform: translateX(-100%);\n}\n\n/* rtl:end:ignore */\n.carousel-fade .carousel-item {\n opacity: 0;\n transition-property: opacity;\n transform: none;\n}\n.carousel-fade .carousel-item.active,\n.carousel-fade .carousel-item-next.carousel-item-start,\n.carousel-fade .carousel-item-prev.carousel-item-end {\n z-index: 1;\n opacity: 1;\n}\n.carousel-fade .active.carousel-item-start,\n.carousel-fade .active.carousel-item-end {\n z-index: 0;\n opacity: 0;\n transition: opacity 0s 0.6s;\n}\n@media (prefers-reduced-motion: reduce) {\n .carousel-fade .active.carousel-item-start,\n.carousel-fade .active.carousel-item-end {\n transition: none;\n }\n}\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n z-index: 1;\n display: flex;\n align-items: center;\n justify-content: center;\n width: 15%;\n padding: 0;\n color: #fff;\n text-align: center;\n background: none;\n border: 0;\n opacity: 0.5;\n transition: opacity 0.15s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .carousel-control-prev,\n.carousel-control-next {\n transition: none;\n }\n}\n.carousel-control-prev:hover, .carousel-control-prev:focus,\n.carousel-control-next:hover,\n.carousel-control-next:focus {\n color: #fff;\n text-decoration: none;\n outline: 0;\n opacity: 0.9;\n}\n\n.carousel-control-prev {\n left: 0;\n}\n\n.carousel-control-next {\n right: 0;\n}\n\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: 2rem;\n height: 2rem;\n background-repeat: no-repeat;\n background-position: 50%;\n background-size: 100% 100%;\n}\n\n/* rtl:options: {\n \"autoRename\": true,\n \"stringMap\":[ {\n \"name\" : \"prev-next\",\n \"search\" : \"prev\",\n \"replace\" : \"next\"\n } ]\n} */\n.carousel-control-prev-icon {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23fff'%3e%3cpath d='M11.354 1.646a.5.5 0 0 1 0 .708L5.707 8l5.647 5.646a.5.5 0 0 1-.708.708l-6-6a.5.5 0 0 1 0-.708l6-6a.5.5 0 0 1 .708 0z'/%3e%3c/svg%3e\");\n}\n\n.carousel-control-next-icon {\n background-image: url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23fff'%3e%3cpath d='M4.646 1.646a.5.5 0 0 1 .708 0l6 6a.5.5 0 0 1 0 .708l-6 6a.5.5 0 0 1-.708-.708L10.293 8 4.646 2.354a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e\");\n}\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 2;\n display: flex;\n justify-content: center;\n padding: 0;\n margin-right: 15%;\n margin-bottom: 1rem;\n margin-left: 15%;\n list-style: none;\n}\n.carousel-indicators [data-bs-target] {\n box-sizing: content-box;\n flex: 0 1 auto;\n width: 30px;\n height: 3px;\n padding: 0;\n margin-right: 3px;\n margin-left: 3px;\n text-indent: -999px;\n cursor: pointer;\n background-color: #fff;\n background-clip: padding-box;\n border: 0;\n border-top: 10px solid transparent;\n border-bottom: 10px solid transparent;\n opacity: 0.5;\n transition: opacity 0.6s ease;\n}\n@media (prefers-reduced-motion: reduce) {\n .carousel-indicators [data-bs-target] {\n transition: none;\n }\n}\n.carousel-indicators .active {\n opacity: 1;\n}\n\n.carousel-caption {\n position: absolute;\n right: 15%;\n bottom: 1.25rem;\n left: 15%;\n padding-top: 1.25rem;\n padding-bottom: 1.25rem;\n color: #fff;\n text-align: center;\n}\n\n.carousel-dark .carousel-control-prev-icon,\n.carousel-dark .carousel-control-next-icon {\n filter: invert(1) grayscale(100);\n}\n.carousel-dark .carousel-indicators [data-bs-target] {\n background-color: #000;\n}\n.carousel-dark .carousel-caption {\n color: #000;\n}\n\n@keyframes spinner-border {\n to {\n transform: rotate(360deg) /* rtl:ignore */;\n }\n}\n.spinner-border {\n display: inline-block;\n width: 2rem;\n height: 2rem;\n vertical-align: -0.125em;\n border: 0.25em solid currentColor;\n border-right-color: transparent;\n border-radius: 50%;\n animation: 0.75s linear infinite spinner-border;\n}\n\n.spinner-border-sm {\n width: 1rem;\n height: 1rem;\n border-width: 0.2em;\n}\n\n@keyframes spinner-grow {\n 0% {\n transform: scale(0);\n }\n 50% {\n opacity: 1;\n transform: none;\n }\n}\n.spinner-grow {\n display: inline-block;\n width: 2rem;\n height: 2rem;\n vertical-align: -0.125em;\n background-color: currentColor;\n border-radius: 50%;\n opacity: 0;\n animation: 0.75s linear infinite spinner-grow;\n}\n\n.spinner-grow-sm {\n width: 1rem;\n height: 1rem;\n}\n\n@media (prefers-reduced-motion: reduce) {\n .spinner-border,\n.spinner-grow {\n animation-duration: 1.5s;\n }\n}\n.offcanvas {\n position: fixed;\n bottom: 0;\n z-index: 1045;\n display: flex;\n flex-direction: column;\n max-width: 100%;\n visibility: hidden;\n background-color: #fff;\n background-clip: padding-box;\n outline: 0;\n transition: transform 0.3s ease-in-out;\n}\n@media (prefers-reduced-motion: reduce) {\n .offcanvas {\n transition: none;\n }\n}\n\n.offcanvas-backdrop {\n position: fixed;\n top: 0;\n left: 0;\n z-index: 1040;\n width: 100vw;\n height: 100vh;\n background-color: #000;\n}\n.offcanvas-backdrop.fade {\n opacity: 0;\n}\n.offcanvas-backdrop.show {\n opacity: 0.5;\n}\n\n.offcanvas-header {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 1rem 1rem;\n}\n.offcanvas-header .btn-close {\n padding: 0.5rem 0.5rem;\n margin-top: -0.5rem;\n margin-right: -0.5rem;\n margin-bottom: -0.5rem;\n}\n\n.offcanvas-title {\n margin-bottom: 0;\n line-height: 1.5;\n}\n\n.offcanvas-body {\n flex-grow: 1;\n padding: 1rem 1rem;\n overflow-y: auto;\n}\n\n.offcanvas-start {\n top: 0;\n left: 0;\n width: 400px;\n border-right: 1px solid rgba(0, 0, 0, 0.2);\n transform: translateX(-100%);\n}\n\n.offcanvas-end {\n top: 0;\n right: 0;\n width: 400px;\n border-left: 1px solid rgba(0, 0, 0, 0.2);\n transform: translateX(100%);\n}\n\n.offcanvas-top {\n top: 0;\n right: 0;\n left: 0;\n height: 30vh;\n max-height: 100%;\n border-bottom: 1px solid rgba(0, 0, 0, 0.2);\n transform: translateY(-100%);\n}\n\n.offcanvas-bottom {\n right: 0;\n left: 0;\n height: 30vh;\n max-height: 100%;\n border-top: 1px solid rgba(0, 0, 0, 0.2);\n transform: translateY(100%);\n}\n\n.offcanvas.show {\n transform: none;\n}\n\n.placeholder {\n display: inline-block;\n min-height: 1em;\n vertical-align: middle;\n cursor: wait;\n background-color: currentColor;\n opacity: 0.5;\n}\n.placeholder.btn::before {\n display: inline-block;\n content: \"\";\n}\n\n.placeholder-xs {\n min-height: 0.6em;\n}\n\n.placeholder-sm {\n min-height: 0.8em;\n}\n\n.placeholder-lg {\n min-height: 1.2em;\n}\n\n.placeholder-glow .placeholder {\n animation: placeholder-glow 2s ease-in-out infinite;\n}\n\n@keyframes placeholder-glow {\n 50% {\n opacity: 0.2;\n }\n}\n.placeholder-wave {\n mask-image: linear-gradient(130deg, #000 55%, rgba(0, 0, 0, 0.8) 75%, #000 95%);\n mask-size: 200% 100%;\n animation: placeholder-wave 2s linear infinite;\n}\n\n@keyframes placeholder-wave {\n 100% {\n mask-position: -200% 0%;\n }\n}\n.clearfix::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.link-primary {\n color: #0d6efd;\n}\n.link-primary:hover, .link-primary:focus {\n color: #0a58ca;\n}\n\n.link-secondary {\n color: #6c757d;\n}\n.link-secondary:hover, .link-secondary:focus {\n color: #565e64;\n}\n\n.link-success {\n color: #198754;\n}\n.link-success:hover, .link-success:focus {\n color: #146c43;\n}\n\n.link-info {\n color: #0dcaf0;\n}\n.link-info:hover, .link-info:focus {\n color: #3dd5f3;\n}\n\n.link-warning {\n color: #ffc107;\n}\n.link-warning:hover, .link-warning:focus {\n color: #ffcd39;\n}\n\n.link-danger {\n color: #dc3545;\n}\n.link-danger:hover, .link-danger:focus {\n color: #b02a37;\n}\n\n.link-light {\n color: #f8f9fa;\n}\n.link-light:hover, .link-light:focus {\n color: #f9fafb;\n}\n\n.link-dark {\n color: #212529;\n}\n.link-dark:hover, .link-dark:focus {\n color: #1a1e21;\n}\n\n.ratio {\n position: relative;\n width: 100%;\n}\n.ratio::before {\n display: block;\n padding-top: var(--bs-aspect-ratio);\n content: \"\";\n}\n.ratio > * {\n position: absolute;\n top: 0;\n left: 0;\n width: 100%;\n height: 100%;\n}\n\n.ratio-1x1 {\n --bs-aspect-ratio: 100%;\n}\n\n.ratio-4x3 {\n --bs-aspect-ratio: 75%;\n}\n\n.ratio-16x9 {\n --bs-aspect-ratio: 56.25%;\n}\n\n.ratio-21x9 {\n --bs-aspect-ratio: 42.8571428571%;\n}\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1030;\n}\n\n.sticky-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n}\n\n@media (min-width: 576px) {\n .sticky-sm-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n@media (min-width: 768px) {\n .sticky-md-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n@media (min-width: 992px) {\n .sticky-lg-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n@media (min-width: 1200px) {\n .sticky-xl-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n@media (min-width: 1400px) {\n .sticky-xxl-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n.hstack {\n display: flex;\n flex-direction: row;\n align-items: center;\n align-self: stretch;\n}\n\n.vstack {\n display: flex;\n flex: 1 1 auto;\n flex-direction: column;\n align-self: stretch;\n}\n\n.visually-hidden,\n.visually-hidden-focusable:not(:focus):not(:focus-within) {\n position: absolute !important;\n width: 1px !important;\n height: 1px !important;\n padding: 0 !important;\n margin: -1px !important;\n overflow: hidden !important;\n clip: rect(0, 0, 0, 0) !important;\n white-space: nowrap !important;\n border: 0 !important;\n}\n\n.stretched-link::after {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1;\n content: \"\";\n}\n\n.text-truncate {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n\n.vr {\n display: inline-block;\n align-self: stretch;\n width: 1px;\n min-height: 1em;\n background-color: currentColor;\n opacity: 0.25;\n}\n\n.align-baseline {\n vertical-align: baseline !important;\n}\n\n.align-top {\n vertical-align: top !important;\n}\n\n.align-middle {\n vertical-align: middle !important;\n}\n\n.align-bottom {\n vertical-align: bottom !important;\n}\n\n.align-text-bottom {\n vertical-align: text-bottom !important;\n}\n\n.align-text-top {\n vertical-align: text-top !important;\n}\n\n.float-start {\n float: left !important;\n}\n\n.float-end {\n float: right !important;\n}\n\n.float-none {\n float: none !important;\n}\n\n.opacity-0 {\n opacity: 0 !important;\n}\n\n.opacity-25 {\n opacity: 0.25 !important;\n}\n\n.opacity-50 {\n opacity: 0.5 !important;\n}\n\n.opacity-75 {\n opacity: 0.75 !important;\n}\n\n.opacity-100 {\n opacity: 1 !important;\n}\n\n.overflow-auto {\n overflow: auto !important;\n}\n\n.overflow-hidden {\n overflow: hidden !important;\n}\n\n.overflow-visible {\n overflow: visible !important;\n}\n\n.overflow-scroll {\n overflow: scroll !important;\n}\n\n.d-inline {\n display: inline !important;\n}\n\n.d-inline-block {\n display: inline-block !important;\n}\n\n.d-block {\n display: block !important;\n}\n\n.d-grid {\n display: grid !important;\n}\n\n.d-table {\n display: table !important;\n}\n\n.d-table-row {\n display: table-row !important;\n}\n\n.d-table-cell {\n display: table-cell !important;\n}\n\n.d-flex {\n display: flex !important;\n}\n\n.d-inline-flex {\n display: inline-flex !important;\n}\n\n.d-none {\n display: none !important;\n}\n\n.shadow {\n box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15) !important;\n}\n\n.shadow-sm {\n box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075) !important;\n}\n\n.shadow-lg {\n box-shadow: 0 1rem 3rem rgba(0, 0, 0, 0.175) !important;\n}\n\n.shadow-none {\n box-shadow: none !important;\n}\n\n.position-static {\n position: static !important;\n}\n\n.position-relative {\n position: relative !important;\n}\n\n.position-absolute {\n position: absolute !important;\n}\n\n.position-fixed {\n position: fixed !important;\n}\n\n.position-sticky {\n position: sticky !important;\n}\n\n.top-0 {\n top: 0 !important;\n}\n\n.top-50 {\n top: 50% !important;\n}\n\n.top-100 {\n top: 100% !important;\n}\n\n.bottom-0 {\n bottom: 0 !important;\n}\n\n.bottom-50 {\n bottom: 50% !important;\n}\n\n.bottom-100 {\n bottom: 100% !important;\n}\n\n.start-0 {\n left: 0 !important;\n}\n\n.start-50 {\n left: 50% !important;\n}\n\n.start-100 {\n left: 100% !important;\n}\n\n.end-0 {\n right: 0 !important;\n}\n\n.end-50 {\n right: 50% !important;\n}\n\n.end-100 {\n right: 100% !important;\n}\n\n.translate-middle {\n transform: translate(-50%, -50%) !important;\n}\n\n.translate-middle-x {\n transform: translateX(-50%) !important;\n}\n\n.translate-middle-y {\n transform: translateY(-50%) !important;\n}\n\n.border {\n border: 1px solid #dee2e6 !important;\n}\n\n.border-0 {\n border: 0 !important;\n}\n\n.border-top {\n border-top: 1px solid #dee2e6 !important;\n}\n\n.border-top-0 {\n border-top: 0 !important;\n}\n\n.border-end {\n border-right: 1px solid #dee2e6 !important;\n}\n\n.border-end-0 {\n border-right: 0 !important;\n}\n\n.border-bottom {\n border-bottom: 1px solid #dee2e6 !important;\n}\n\n.border-bottom-0 {\n border-bottom: 0 !important;\n}\n\n.border-start {\n border-left: 1px solid #dee2e6 !important;\n}\n\n.border-start-0 {\n border-left: 0 !important;\n}\n\n.border-primary {\n border-color: #0d6efd !important;\n}\n\n.border-secondary {\n border-color: #6c757d !important;\n}\n\n.border-success {\n border-color: #198754 !important;\n}\n\n.border-info {\n border-color: #0dcaf0 !important;\n}\n\n.border-warning {\n border-color: #ffc107 !important;\n}\n\n.border-danger {\n border-color: #dc3545 !important;\n}\n\n.border-light {\n border-color: #f8f9fa !important;\n}\n\n.border-dark {\n border-color: #212529 !important;\n}\n\n.border-white {\n border-color: #fff !important;\n}\n\n.border-1 {\n border-width: 1px !important;\n}\n\n.border-2 {\n border-width: 2px !important;\n}\n\n.border-3 {\n border-width: 3px !important;\n}\n\n.border-4 {\n border-width: 4px !important;\n}\n\n.border-5 {\n border-width: 5px !important;\n}\n\n.w-25 {\n width: 25% !important;\n}\n\n.w-50 {\n width: 50% !important;\n}\n\n.w-75 {\n width: 75% !important;\n}\n\n.w-100 {\n width: 100% !important;\n}\n\n.w-auto {\n width: auto !important;\n}\n\n.mw-100 {\n max-width: 100% !important;\n}\n\n.vw-100 {\n width: 100vw !important;\n}\n\n.min-vw-100 {\n min-width: 100vw !important;\n}\n\n.h-25 {\n height: 25% !important;\n}\n\n.h-50 {\n height: 50% !important;\n}\n\n.h-75 {\n height: 75% !important;\n}\n\n.h-100 {\n height: 100% !important;\n}\n\n.h-auto {\n height: auto !important;\n}\n\n.mh-100 {\n max-height: 100% !important;\n}\n\n.vh-100 {\n height: 100vh !important;\n}\n\n.min-vh-100 {\n min-height: 100vh !important;\n}\n\n.flex-fill {\n flex: 1 1 auto !important;\n}\n\n.flex-row {\n flex-direction: row !important;\n}\n\n.flex-column {\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n flex-direction: column-reverse !important;\n}\n\n.flex-grow-0 {\n flex-grow: 0 !important;\n}\n\n.flex-grow-1 {\n flex-grow: 1 !important;\n}\n\n.flex-shrink-0 {\n flex-shrink: 0 !important;\n}\n\n.flex-shrink-1 {\n flex-shrink: 1 !important;\n}\n\n.flex-wrap {\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n}\n\n.gap-0 {\n gap: 0 !important;\n}\n\n.gap-1 {\n gap: 0.25rem !important;\n}\n\n.gap-2 {\n gap: 0.5rem !important;\n}\n\n.gap-3 {\n gap: 1rem !important;\n}\n\n.gap-4 {\n gap: 1.5rem !important;\n}\n\n.gap-5 {\n gap: 3rem !important;\n}\n\n.justify-content-start {\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n justify-content: center !important;\n}\n\n.justify-content-between {\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n justify-content: space-around !important;\n}\n\n.justify-content-evenly {\n justify-content: space-evenly !important;\n}\n\n.align-items-start {\n align-items: flex-start !important;\n}\n\n.align-items-end {\n align-items: flex-end !important;\n}\n\n.align-items-center {\n align-items: center !important;\n}\n\n.align-items-baseline {\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n align-items: stretch !important;\n}\n\n.align-content-start {\n align-content: flex-start !important;\n}\n\n.align-content-end {\n align-content: flex-end !important;\n}\n\n.align-content-center {\n align-content: center !important;\n}\n\n.align-content-between {\n align-content: space-between !important;\n}\n\n.align-content-around {\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n align-content: stretch !important;\n}\n\n.align-self-auto {\n align-self: auto !important;\n}\n\n.align-self-start {\n align-self: flex-start !important;\n}\n\n.align-self-end {\n align-self: flex-end !important;\n}\n\n.align-self-center {\n align-self: center !important;\n}\n\n.align-self-baseline {\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n align-self: stretch !important;\n}\n\n.order-first {\n order: -1 !important;\n}\n\n.order-0 {\n order: 0 !important;\n}\n\n.order-1 {\n order: 1 !important;\n}\n\n.order-2 {\n order: 2 !important;\n}\n\n.order-3 {\n order: 3 !important;\n}\n\n.order-4 {\n order: 4 !important;\n}\n\n.order-5 {\n order: 5 !important;\n}\n\n.order-last {\n order: 6 !important;\n}\n\n.m-0 {\n margin: 0 !important;\n}\n\n.m-1 {\n margin: 0.25rem !important;\n}\n\n.m-2 {\n margin: 0.5rem !important;\n}\n\n.m-3 {\n margin: 1rem !important;\n}\n\n.m-4 {\n margin: 1.5rem !important;\n}\n\n.m-5 {\n margin: 3rem !important;\n}\n\n.m-auto {\n margin: auto !important;\n}\n\n.mx-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n}\n\n.mx-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n}\n\n.mx-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n}\n\n.mx-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n}\n\n.mx-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n}\n\n.mx-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n}\n\n.mx-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n}\n\n.my-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n}\n\n.my-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n}\n\n.my-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n}\n\n.my-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n}\n\n.my-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n}\n\n.my-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n}\n\n.my-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n}\n\n.mt-0 {\n margin-top: 0 !important;\n}\n\n.mt-1 {\n margin-top: 0.25rem !important;\n}\n\n.mt-2 {\n margin-top: 0.5rem !important;\n}\n\n.mt-3 {\n margin-top: 1rem !important;\n}\n\n.mt-4 {\n margin-top: 1.5rem !important;\n}\n\n.mt-5 {\n margin-top: 3rem !important;\n}\n\n.mt-auto {\n margin-top: auto !important;\n}\n\n.me-0 {\n margin-right: 0 !important;\n}\n\n.me-1 {\n margin-right: 0.25rem !important;\n}\n\n.me-2 {\n margin-right: 0.5rem !important;\n}\n\n.me-3 {\n margin-right: 1rem !important;\n}\n\n.me-4 {\n margin-right: 1.5rem !important;\n}\n\n.me-5 {\n margin-right: 3rem !important;\n}\n\n.me-auto {\n margin-right: auto !important;\n}\n\n.mb-0 {\n margin-bottom: 0 !important;\n}\n\n.mb-1 {\n margin-bottom: 0.25rem !important;\n}\n\n.mb-2 {\n margin-bottom: 0.5rem !important;\n}\n\n.mb-3 {\n margin-bottom: 1rem !important;\n}\n\n.mb-4 {\n margin-bottom: 1.5rem !important;\n}\n\n.mb-5 {\n margin-bottom: 3rem !important;\n}\n\n.mb-auto {\n margin-bottom: auto !important;\n}\n\n.ms-0 {\n margin-left: 0 !important;\n}\n\n.ms-1 {\n margin-left: 0.25rem !important;\n}\n\n.ms-2 {\n margin-left: 0.5rem !important;\n}\n\n.ms-3 {\n margin-left: 1rem !important;\n}\n\n.ms-4 {\n margin-left: 1.5rem !important;\n}\n\n.ms-5 {\n margin-left: 3rem !important;\n}\n\n.ms-auto {\n margin-left: auto !important;\n}\n\n.p-0 {\n padding: 0 !important;\n}\n\n.p-1 {\n padding: 0.25rem !important;\n}\n\n.p-2 {\n padding: 0.5rem !important;\n}\n\n.p-3 {\n padding: 1rem !important;\n}\n\n.p-4 {\n padding: 1.5rem !important;\n}\n\n.p-5 {\n padding: 3rem !important;\n}\n\n.px-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n}\n\n.px-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n}\n\n.px-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n}\n\n.px-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n}\n\n.px-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n}\n\n.px-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n}\n\n.py-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n}\n\n.py-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n}\n\n.py-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n}\n\n.py-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n}\n\n.py-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n}\n\n.py-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n}\n\n.pt-0 {\n padding-top: 0 !important;\n}\n\n.pt-1 {\n padding-top: 0.25rem !important;\n}\n\n.pt-2 {\n padding-top: 0.5rem !important;\n}\n\n.pt-3 {\n padding-top: 1rem !important;\n}\n\n.pt-4 {\n padding-top: 1.5rem !important;\n}\n\n.pt-5 {\n padding-top: 3rem !important;\n}\n\n.pe-0 {\n padding-right: 0 !important;\n}\n\n.pe-1 {\n padding-right: 0.25rem !important;\n}\n\n.pe-2 {\n padding-right: 0.5rem !important;\n}\n\n.pe-3 {\n padding-right: 1rem !important;\n}\n\n.pe-4 {\n padding-right: 1.5rem !important;\n}\n\n.pe-5 {\n padding-right: 3rem !important;\n}\n\n.pb-0 {\n padding-bottom: 0 !important;\n}\n\n.pb-1 {\n padding-bottom: 0.25rem !important;\n}\n\n.pb-2 {\n padding-bottom: 0.5rem !important;\n}\n\n.pb-3 {\n padding-bottom: 1rem !important;\n}\n\n.pb-4 {\n padding-bottom: 1.5rem !important;\n}\n\n.pb-5 {\n padding-bottom: 3rem !important;\n}\n\n.ps-0 {\n padding-left: 0 !important;\n}\n\n.ps-1 {\n padding-left: 0.25rem !important;\n}\n\n.ps-2 {\n padding-left: 0.5rem !important;\n}\n\n.ps-3 {\n padding-left: 1rem !important;\n}\n\n.ps-4 {\n padding-left: 1.5rem !important;\n}\n\n.ps-5 {\n padding-left: 3rem !important;\n}\n\n.font-monospace {\n font-family: var(--bs-font-monospace) !important;\n}\n\n.fs-1 {\n font-size: calc(1.375rem + 1.5vw) !important;\n}\n\n.fs-2 {\n font-size: calc(1.325rem + 0.9vw) !important;\n}\n\n.fs-3 {\n font-size: calc(1.3rem + 0.6vw) !important;\n}\n\n.fs-4 {\n font-size: calc(1.275rem + 0.3vw) !important;\n}\n\n.fs-5 {\n font-size: 1.25rem !important;\n}\n\n.fs-6 {\n font-size: 1rem !important;\n}\n\n.fst-italic {\n font-style: italic !important;\n}\n\n.fst-normal {\n font-style: normal !important;\n}\n\n.fw-light {\n font-weight: 300 !important;\n}\n\n.fw-lighter {\n font-weight: lighter !important;\n}\n\n.fw-normal {\n font-weight: 400 !important;\n}\n\n.fw-bold {\n font-weight: 700 !important;\n}\n\n.fw-bolder {\n font-weight: bolder !important;\n}\n\n.lh-1 {\n line-height: 1 !important;\n}\n\n.lh-sm {\n line-height: 1.25 !important;\n}\n\n.lh-base {\n line-height: 1.5 !important;\n}\n\n.lh-lg {\n line-height: 2 !important;\n}\n\n.text-start {\n text-align: left !important;\n}\n\n.text-end {\n text-align: right !important;\n}\n\n.text-center {\n text-align: center !important;\n}\n\n.text-decoration-none {\n text-decoration: none !important;\n}\n\n.text-decoration-underline {\n text-decoration: underline !important;\n}\n\n.text-decoration-line-through {\n text-decoration: line-through !important;\n}\n\n.text-lowercase {\n text-transform: lowercase !important;\n}\n\n.text-uppercase {\n text-transform: uppercase !important;\n}\n\n.text-capitalize {\n text-transform: capitalize !important;\n}\n\n.text-wrap {\n white-space: normal !important;\n}\n\n.text-nowrap {\n white-space: nowrap !important;\n}\n\n/* rtl:begin:remove */\n.text-break {\n word-wrap: break-word !important;\n word-break: break-word !important;\n}\n\n/* rtl:end:remove */\n.text-primary {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-primary-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-secondary {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-secondary-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-success {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-success-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-info {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-info-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-warning {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-warning-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-danger {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-danger-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-light {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-light-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-dark {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-dark-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-black {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-black-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-white {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-white-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-body {\n --bs-text-opacity: 1;\n color: rgba(var(--bs-body-color-rgb), var(--bs-text-opacity)) !important;\n}\n\n.text-muted {\n --bs-text-opacity: 1;\n color: #6c757d !important;\n}\n\n.text-black-50 {\n --bs-text-opacity: 1;\n color: rgba(0, 0, 0, 0.5) !important;\n}\n\n.text-white-50 {\n --bs-text-opacity: 1;\n color: rgba(255, 255, 255, 0.5) !important;\n}\n\n.text-reset {\n --bs-text-opacity: 1;\n color: inherit !important;\n}\n\n.text-opacity-25 {\n --bs-text-opacity: 0.25;\n}\n\n.text-opacity-50 {\n --bs-text-opacity: 0.5;\n}\n\n.text-opacity-75 {\n --bs-text-opacity: 0.75;\n}\n\n.text-opacity-100 {\n --bs-text-opacity: 1;\n}\n\n.bg-primary {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-primary-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-secondary {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-secondary-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-success {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-success-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-info {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-info-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-warning {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-warning-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-danger {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-danger-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-light {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-light-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-dark {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-dark-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-black {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-black-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-white {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-white-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-body {\n --bs-bg-opacity: 1;\n background-color: rgba(var(--bs-body-bg-rgb), var(--bs-bg-opacity)) !important;\n}\n\n.bg-transparent {\n --bs-bg-opacity: 1;\n background-color: transparent !important;\n}\n\n.bg-opacity-10 {\n --bs-bg-opacity: 0.1;\n}\n\n.bg-opacity-25 {\n --bs-bg-opacity: 0.25;\n}\n\n.bg-opacity-50 {\n --bs-bg-opacity: 0.5;\n}\n\n.bg-opacity-75 {\n --bs-bg-opacity: 0.75;\n}\n\n.bg-opacity-100 {\n --bs-bg-opacity: 1;\n}\n\n.bg-gradient {\n background-image: var(--bs-gradient) !important;\n}\n\n.user-select-all {\n user-select: all !important;\n}\n\n.user-select-auto {\n user-select: auto !important;\n}\n\n.user-select-none {\n user-select: none !important;\n}\n\n.pe-none {\n pointer-events: none !important;\n}\n\n.pe-auto {\n pointer-events: auto !important;\n}\n\n.rounded {\n border-radius: 0.25rem !important;\n}\n\n.rounded-0 {\n border-radius: 0 !important;\n}\n\n.rounded-1 {\n border-radius: 0.2rem !important;\n}\n\n.rounded-2 {\n border-radius: 0.25rem !important;\n}\n\n.rounded-3 {\n border-radius: 0.3rem !important;\n}\n\n.rounded-circle {\n border-radius: 50% !important;\n}\n\n.rounded-pill {\n border-radius: 50rem !important;\n}\n\n.rounded-top {\n border-top-left-radius: 0.25rem !important;\n border-top-right-radius: 0.25rem !important;\n}\n\n.rounded-end {\n border-top-right-radius: 0.25rem !important;\n border-bottom-right-radius: 0.25rem !important;\n}\n\n.rounded-bottom {\n border-bottom-right-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-start {\n border-bottom-left-radius: 0.25rem !important;\n border-top-left-radius: 0.25rem !important;\n}\n\n.visible {\n visibility: visible !important;\n}\n\n.invisible {\n visibility: hidden !important;\n}\n\n@media (min-width: 576px) {\n .float-sm-start {\n float: left !important;\n }\n\n .float-sm-end {\n float: right !important;\n }\n\n .float-sm-none {\n float: none !important;\n }\n\n .d-sm-inline {\n display: inline !important;\n }\n\n .d-sm-inline-block {\n display: inline-block !important;\n }\n\n .d-sm-block {\n display: block !important;\n }\n\n .d-sm-grid {\n display: grid !important;\n }\n\n .d-sm-table {\n display: table !important;\n }\n\n .d-sm-table-row {\n display: table-row !important;\n }\n\n .d-sm-table-cell {\n display: table-cell !important;\n }\n\n .d-sm-flex {\n display: flex !important;\n }\n\n .d-sm-inline-flex {\n display: inline-flex !important;\n }\n\n .d-sm-none {\n display: none !important;\n }\n\n .flex-sm-fill {\n flex: 1 1 auto !important;\n }\n\n .flex-sm-row {\n flex-direction: row !important;\n }\n\n .flex-sm-column {\n flex-direction: column !important;\n }\n\n .flex-sm-row-reverse {\n flex-direction: row-reverse !important;\n }\n\n .flex-sm-column-reverse {\n flex-direction: column-reverse !important;\n }\n\n .flex-sm-grow-0 {\n flex-grow: 0 !important;\n }\n\n .flex-sm-grow-1 {\n flex-grow: 1 !important;\n }\n\n .flex-sm-shrink-0 {\n flex-shrink: 0 !important;\n }\n\n .flex-sm-shrink-1 {\n flex-shrink: 1 !important;\n }\n\n .flex-sm-wrap {\n flex-wrap: wrap !important;\n }\n\n .flex-sm-nowrap {\n flex-wrap: nowrap !important;\n }\n\n .flex-sm-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n\n .gap-sm-0 {\n gap: 0 !important;\n }\n\n .gap-sm-1 {\n gap: 0.25rem !important;\n }\n\n .gap-sm-2 {\n gap: 0.5rem !important;\n }\n\n .gap-sm-3 {\n gap: 1rem !important;\n }\n\n .gap-sm-4 {\n gap: 1.5rem !important;\n }\n\n .gap-sm-5 {\n gap: 3rem !important;\n }\n\n .justify-content-sm-start {\n justify-content: flex-start !important;\n }\n\n .justify-content-sm-end {\n justify-content: flex-end !important;\n }\n\n .justify-content-sm-center {\n justify-content: center !important;\n }\n\n .justify-content-sm-between {\n justify-content: space-between !important;\n }\n\n .justify-content-sm-around {\n justify-content: space-around !important;\n }\n\n .justify-content-sm-evenly {\n justify-content: space-evenly !important;\n }\n\n .align-items-sm-start {\n align-items: flex-start !important;\n }\n\n .align-items-sm-end {\n align-items: flex-end !important;\n }\n\n .align-items-sm-center {\n align-items: center !important;\n }\n\n .align-items-sm-baseline {\n align-items: baseline !important;\n }\n\n .align-items-sm-stretch {\n align-items: stretch !important;\n }\n\n .align-content-sm-start {\n align-content: flex-start !important;\n }\n\n .align-content-sm-end {\n align-content: flex-end !important;\n }\n\n .align-content-sm-center {\n align-content: center !important;\n }\n\n .align-content-sm-between {\n align-content: space-between !important;\n }\n\n .align-content-sm-around {\n align-content: space-around !important;\n }\n\n .align-content-sm-stretch {\n align-content: stretch !important;\n }\n\n .align-self-sm-auto {\n align-self: auto !important;\n }\n\n .align-self-sm-start {\n align-self: flex-start !important;\n }\n\n .align-self-sm-end {\n align-self: flex-end !important;\n }\n\n .align-self-sm-center {\n align-self: center !important;\n }\n\n .align-self-sm-baseline {\n align-self: baseline !important;\n }\n\n .align-self-sm-stretch {\n align-self: stretch !important;\n }\n\n .order-sm-first {\n order: -1 !important;\n }\n\n .order-sm-0 {\n order: 0 !important;\n }\n\n .order-sm-1 {\n order: 1 !important;\n }\n\n .order-sm-2 {\n order: 2 !important;\n }\n\n .order-sm-3 {\n order: 3 !important;\n }\n\n .order-sm-4 {\n order: 4 !important;\n }\n\n .order-sm-5 {\n order: 5 !important;\n }\n\n .order-sm-last {\n order: 6 !important;\n }\n\n .m-sm-0 {\n margin: 0 !important;\n }\n\n .m-sm-1 {\n margin: 0.25rem !important;\n }\n\n .m-sm-2 {\n margin: 0.5rem !important;\n }\n\n .m-sm-3 {\n margin: 1rem !important;\n }\n\n .m-sm-4 {\n margin: 1.5rem !important;\n }\n\n .m-sm-5 {\n margin: 3rem !important;\n }\n\n .m-sm-auto {\n margin: auto !important;\n }\n\n .mx-sm-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n\n .mx-sm-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n\n .mx-sm-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n\n .mx-sm-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n\n .mx-sm-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n\n .mx-sm-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n\n .mx-sm-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n\n .my-sm-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n\n .my-sm-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n\n .my-sm-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n\n .my-sm-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n\n .my-sm-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n\n .my-sm-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n\n .my-sm-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n\n .mt-sm-0 {\n margin-top: 0 !important;\n }\n\n .mt-sm-1 {\n margin-top: 0.25rem !important;\n }\n\n .mt-sm-2 {\n margin-top: 0.5rem !important;\n }\n\n .mt-sm-3 {\n margin-top: 1rem !important;\n }\n\n .mt-sm-4 {\n margin-top: 1.5rem !important;\n }\n\n .mt-sm-5 {\n margin-top: 3rem !important;\n }\n\n .mt-sm-auto {\n margin-top: auto !important;\n }\n\n .me-sm-0 {\n margin-right: 0 !important;\n }\n\n .me-sm-1 {\n margin-right: 0.25rem !important;\n }\n\n .me-sm-2 {\n margin-right: 0.5rem !important;\n }\n\n .me-sm-3 {\n margin-right: 1rem !important;\n }\n\n .me-sm-4 {\n margin-right: 1.5rem !important;\n }\n\n .me-sm-5 {\n margin-right: 3rem !important;\n }\n\n .me-sm-auto {\n margin-right: auto !important;\n }\n\n .mb-sm-0 {\n margin-bottom: 0 !important;\n }\n\n .mb-sm-1 {\n margin-bottom: 0.25rem !important;\n }\n\n .mb-sm-2 {\n margin-bottom: 0.5rem !important;\n }\n\n .mb-sm-3 {\n margin-bottom: 1rem !important;\n }\n\n .mb-sm-4 {\n margin-bottom: 1.5rem !important;\n }\n\n .mb-sm-5 {\n margin-bottom: 3rem !important;\n }\n\n .mb-sm-auto {\n margin-bottom: auto !important;\n }\n\n .ms-sm-0 {\n margin-left: 0 !important;\n }\n\n .ms-sm-1 {\n margin-left: 0.25rem !important;\n }\n\n .ms-sm-2 {\n margin-left: 0.5rem !important;\n }\n\n .ms-sm-3 {\n margin-left: 1rem !important;\n }\n\n .ms-sm-4 {\n margin-left: 1.5rem !important;\n }\n\n .ms-sm-5 {\n margin-left: 3rem !important;\n }\n\n .ms-sm-auto {\n margin-left: auto !important;\n }\n\n .p-sm-0 {\n padding: 0 !important;\n }\n\n .p-sm-1 {\n padding: 0.25rem !important;\n }\n\n .p-sm-2 {\n padding: 0.5rem !important;\n }\n\n .p-sm-3 {\n padding: 1rem !important;\n }\n\n .p-sm-4 {\n padding: 1.5rem !important;\n }\n\n .p-sm-5 {\n padding: 3rem !important;\n }\n\n .px-sm-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n\n .px-sm-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n\n .px-sm-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n\n .px-sm-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n\n .px-sm-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n\n .px-sm-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n\n .py-sm-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n\n .py-sm-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n\n .py-sm-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n\n .py-sm-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n\n .py-sm-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n\n .py-sm-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n\n .pt-sm-0 {\n padding-top: 0 !important;\n }\n\n .pt-sm-1 {\n padding-top: 0.25rem !important;\n }\n\n .pt-sm-2 {\n padding-top: 0.5rem !important;\n }\n\n .pt-sm-3 {\n padding-top: 1rem !important;\n }\n\n .pt-sm-4 {\n padding-top: 1.5rem !important;\n }\n\n .pt-sm-5 {\n padding-top: 3rem !important;\n }\n\n .pe-sm-0 {\n padding-right: 0 !important;\n }\n\n .pe-sm-1 {\n padding-right: 0.25rem !important;\n }\n\n .pe-sm-2 {\n padding-right: 0.5rem !important;\n }\n\n .pe-sm-3 {\n padding-right: 1rem !important;\n }\n\n .pe-sm-4 {\n padding-right: 1.5rem !important;\n }\n\n .pe-sm-5 {\n padding-right: 3rem !important;\n }\n\n .pb-sm-0 {\n padding-bottom: 0 !important;\n }\n\n .pb-sm-1 {\n padding-bottom: 0.25rem !important;\n }\n\n .pb-sm-2 {\n padding-bottom: 0.5rem !important;\n }\n\n .pb-sm-3 {\n padding-bottom: 1rem !important;\n }\n\n .pb-sm-4 {\n padding-bottom: 1.5rem !important;\n }\n\n .pb-sm-5 {\n padding-bottom: 3rem !important;\n }\n\n .ps-sm-0 {\n padding-left: 0 !important;\n }\n\n .ps-sm-1 {\n padding-left: 0.25rem !important;\n }\n\n .ps-sm-2 {\n padding-left: 0.5rem !important;\n }\n\n .ps-sm-3 {\n padding-left: 1rem !important;\n }\n\n .ps-sm-4 {\n padding-left: 1.5rem !important;\n }\n\n .ps-sm-5 {\n padding-left: 3rem !important;\n }\n\n .text-sm-start {\n text-align: left !important;\n }\n\n .text-sm-end {\n text-align: right !important;\n }\n\n .text-sm-center {\n text-align: center !important;\n }\n}\n@media (min-width: 768px) {\n .float-md-start {\n float: left !important;\n }\n\n .float-md-end {\n float: right !important;\n }\n\n .float-md-none {\n float: none !important;\n }\n\n .d-md-inline {\n display: inline !important;\n }\n\n .d-md-inline-block {\n display: inline-block !important;\n }\n\n .d-md-block {\n display: block !important;\n }\n\n .d-md-grid {\n display: grid !important;\n }\n\n .d-md-table {\n display: table !important;\n }\n\n .d-md-table-row {\n display: table-row !important;\n }\n\n .d-md-table-cell {\n display: table-cell !important;\n }\n\n .d-md-flex {\n display: flex !important;\n }\n\n .d-md-inline-flex {\n display: inline-flex !important;\n }\n\n .d-md-none {\n display: none !important;\n }\n\n .flex-md-fill {\n flex: 1 1 auto !important;\n }\n\n .flex-md-row {\n flex-direction: row !important;\n }\n\n .flex-md-column {\n flex-direction: column !important;\n }\n\n .flex-md-row-reverse {\n flex-direction: row-reverse !important;\n }\n\n .flex-md-column-reverse {\n flex-direction: column-reverse !important;\n }\n\n .flex-md-grow-0 {\n flex-grow: 0 !important;\n }\n\n .flex-md-grow-1 {\n flex-grow: 1 !important;\n }\n\n .flex-md-shrink-0 {\n flex-shrink: 0 !important;\n }\n\n .flex-md-shrink-1 {\n flex-shrink: 1 !important;\n }\n\n .flex-md-wrap {\n flex-wrap: wrap !important;\n }\n\n .flex-md-nowrap {\n flex-wrap: nowrap !important;\n }\n\n .flex-md-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n\n .gap-md-0 {\n gap: 0 !important;\n }\n\n .gap-md-1 {\n gap: 0.25rem !important;\n }\n\n .gap-md-2 {\n gap: 0.5rem !important;\n }\n\n .gap-md-3 {\n gap: 1rem !important;\n }\n\n .gap-md-4 {\n gap: 1.5rem !important;\n }\n\n .gap-md-5 {\n gap: 3rem !important;\n }\n\n .justify-content-md-start {\n justify-content: flex-start !important;\n }\n\n .justify-content-md-end {\n justify-content: flex-end !important;\n }\n\n .justify-content-md-center {\n justify-content: center !important;\n }\n\n .justify-content-md-between {\n justify-content: space-between !important;\n }\n\n .justify-content-md-around {\n justify-content: space-around !important;\n }\n\n .justify-content-md-evenly {\n justify-content: space-evenly !important;\n }\n\n .align-items-md-start {\n align-items: flex-start !important;\n }\n\n .align-items-md-end {\n align-items: flex-end !important;\n }\n\n .align-items-md-center {\n align-items: center !important;\n }\n\n .align-items-md-baseline {\n align-items: baseline !important;\n }\n\n .align-items-md-stretch {\n align-items: stretch !important;\n }\n\n .align-content-md-start {\n align-content: flex-start !important;\n }\n\n .align-content-md-end {\n align-content: flex-end !important;\n }\n\n .align-content-md-center {\n align-content: center !important;\n }\n\n .align-content-md-between {\n align-content: space-between !important;\n }\n\n .align-content-md-around {\n align-content: space-around !important;\n }\n\n .align-content-md-stretch {\n align-content: stretch !important;\n }\n\n .align-self-md-auto {\n align-self: auto !important;\n }\n\n .align-self-md-start {\n align-self: flex-start !important;\n }\n\n .align-self-md-end {\n align-self: flex-end !important;\n }\n\n .align-self-md-center {\n align-self: center !important;\n }\n\n .align-self-md-baseline {\n align-self: baseline !important;\n }\n\n .align-self-md-stretch {\n align-self: stretch !important;\n }\n\n .order-md-first {\n order: -1 !important;\n }\n\n .order-md-0 {\n order: 0 !important;\n }\n\n .order-md-1 {\n order: 1 !important;\n }\n\n .order-md-2 {\n order: 2 !important;\n }\n\n .order-md-3 {\n order: 3 !important;\n }\n\n .order-md-4 {\n order: 4 !important;\n }\n\n .order-md-5 {\n order: 5 !important;\n }\n\n .order-md-last {\n order: 6 !important;\n }\n\n .m-md-0 {\n margin: 0 !important;\n }\n\n .m-md-1 {\n margin: 0.25rem !important;\n }\n\n .m-md-2 {\n margin: 0.5rem !important;\n }\n\n .m-md-3 {\n margin: 1rem !important;\n }\n\n .m-md-4 {\n margin: 1.5rem !important;\n }\n\n .m-md-5 {\n margin: 3rem !important;\n }\n\n .m-md-auto {\n margin: auto !important;\n }\n\n .mx-md-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n\n .mx-md-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n\n .mx-md-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n\n .mx-md-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n\n .mx-md-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n\n .mx-md-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n\n .mx-md-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n\n .my-md-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n\n .my-md-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n\n .my-md-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n\n .my-md-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n\n .my-md-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n\n .my-md-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n\n .my-md-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n\n .mt-md-0 {\n margin-top: 0 !important;\n }\n\n .mt-md-1 {\n margin-top: 0.25rem !important;\n }\n\n .mt-md-2 {\n margin-top: 0.5rem !important;\n }\n\n .mt-md-3 {\n margin-top: 1rem !important;\n }\n\n .mt-md-4 {\n margin-top: 1.5rem !important;\n }\n\n .mt-md-5 {\n margin-top: 3rem !important;\n }\n\n .mt-md-auto {\n margin-top: auto !important;\n }\n\n .me-md-0 {\n margin-right: 0 !important;\n }\n\n .me-md-1 {\n margin-right: 0.25rem !important;\n }\n\n .me-md-2 {\n margin-right: 0.5rem !important;\n }\n\n .me-md-3 {\n margin-right: 1rem !important;\n }\n\n .me-md-4 {\n margin-right: 1.5rem !important;\n }\n\n .me-md-5 {\n margin-right: 3rem !important;\n }\n\n .me-md-auto {\n margin-right: auto !important;\n }\n\n .mb-md-0 {\n margin-bottom: 0 !important;\n }\n\n .mb-md-1 {\n margin-bottom: 0.25rem !important;\n }\n\n .mb-md-2 {\n margin-bottom: 0.5rem !important;\n }\n\n .mb-md-3 {\n margin-bottom: 1rem !important;\n }\n\n .mb-md-4 {\n margin-bottom: 1.5rem !important;\n }\n\n .mb-md-5 {\n margin-bottom: 3rem !important;\n }\n\n .mb-md-auto {\n margin-bottom: auto !important;\n }\n\n .ms-md-0 {\n margin-left: 0 !important;\n }\n\n .ms-md-1 {\n margin-left: 0.25rem !important;\n }\n\n .ms-md-2 {\n margin-left: 0.5rem !important;\n }\n\n .ms-md-3 {\n margin-left: 1rem !important;\n }\n\n .ms-md-4 {\n margin-left: 1.5rem !important;\n }\n\n .ms-md-5 {\n margin-left: 3rem !important;\n }\n\n .ms-md-auto {\n margin-left: auto !important;\n }\n\n .p-md-0 {\n padding: 0 !important;\n }\n\n .p-md-1 {\n padding: 0.25rem !important;\n }\n\n .p-md-2 {\n padding: 0.5rem !important;\n }\n\n .p-md-3 {\n padding: 1rem !important;\n }\n\n .p-md-4 {\n padding: 1.5rem !important;\n }\n\n .p-md-5 {\n padding: 3rem !important;\n }\n\n .px-md-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n\n .px-md-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n\n .px-md-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n\n .px-md-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n\n .px-md-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n\n .px-md-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n\n .py-md-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n\n .py-md-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n\n .py-md-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n\n .py-md-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n\n .py-md-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n\n .py-md-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n\n .pt-md-0 {\n padding-top: 0 !important;\n }\n\n .pt-md-1 {\n padding-top: 0.25rem !important;\n }\n\n .pt-md-2 {\n padding-top: 0.5rem !important;\n }\n\n .pt-md-3 {\n padding-top: 1rem !important;\n }\n\n .pt-md-4 {\n padding-top: 1.5rem !important;\n }\n\n .pt-md-5 {\n padding-top: 3rem !important;\n }\n\n .pe-md-0 {\n padding-right: 0 !important;\n }\n\n .pe-md-1 {\n padding-right: 0.25rem !important;\n }\n\n .pe-md-2 {\n padding-right: 0.5rem !important;\n }\n\n .pe-md-3 {\n padding-right: 1rem !important;\n }\n\n .pe-md-4 {\n padding-right: 1.5rem !important;\n }\n\n .pe-md-5 {\n padding-right: 3rem !important;\n }\n\n .pb-md-0 {\n padding-bottom: 0 !important;\n }\n\n .pb-md-1 {\n padding-bottom: 0.25rem !important;\n }\n\n .pb-md-2 {\n padding-bottom: 0.5rem !important;\n }\n\n .pb-md-3 {\n padding-bottom: 1rem !important;\n }\n\n .pb-md-4 {\n padding-bottom: 1.5rem !important;\n }\n\n .pb-md-5 {\n padding-bottom: 3rem !important;\n }\n\n .ps-md-0 {\n padding-left: 0 !important;\n }\n\n .ps-md-1 {\n padding-left: 0.25rem !important;\n }\n\n .ps-md-2 {\n padding-left: 0.5rem !important;\n }\n\n .ps-md-3 {\n padding-left: 1rem !important;\n }\n\n .ps-md-4 {\n padding-left: 1.5rem !important;\n }\n\n .ps-md-5 {\n padding-left: 3rem !important;\n }\n\n .text-md-start {\n text-align: left !important;\n }\n\n .text-md-end {\n text-align: right !important;\n }\n\n .text-md-center {\n text-align: center !important;\n }\n}\n@media (min-width: 992px) {\n .float-lg-start {\n float: left !important;\n }\n\n .float-lg-end {\n float: right !important;\n }\n\n .float-lg-none {\n float: none !important;\n }\n\n .d-lg-inline {\n display: inline !important;\n }\n\n .d-lg-inline-block {\n display: inline-block !important;\n }\n\n .d-lg-block {\n display: block !important;\n }\n\n .d-lg-grid {\n display: grid !important;\n }\n\n .d-lg-table {\n display: table !important;\n }\n\n .d-lg-table-row {\n display: table-row !important;\n }\n\n .d-lg-table-cell {\n display: table-cell !important;\n }\n\n .d-lg-flex {\n display: flex !important;\n }\n\n .d-lg-inline-flex {\n display: inline-flex !important;\n }\n\n .d-lg-none {\n display: none !important;\n }\n\n .flex-lg-fill {\n flex: 1 1 auto !important;\n }\n\n .flex-lg-row {\n flex-direction: row !important;\n }\n\n .flex-lg-column {\n flex-direction: column !important;\n }\n\n .flex-lg-row-reverse {\n flex-direction: row-reverse !important;\n }\n\n .flex-lg-column-reverse {\n flex-direction: column-reverse !important;\n }\n\n .flex-lg-grow-0 {\n flex-grow: 0 !important;\n }\n\n .flex-lg-grow-1 {\n flex-grow: 1 !important;\n }\n\n .flex-lg-shrink-0 {\n flex-shrink: 0 !important;\n }\n\n .flex-lg-shrink-1 {\n flex-shrink: 1 !important;\n }\n\n .flex-lg-wrap {\n flex-wrap: wrap !important;\n }\n\n .flex-lg-nowrap {\n flex-wrap: nowrap !important;\n }\n\n .flex-lg-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n\n .gap-lg-0 {\n gap: 0 !important;\n }\n\n .gap-lg-1 {\n gap: 0.25rem !important;\n }\n\n .gap-lg-2 {\n gap: 0.5rem !important;\n }\n\n .gap-lg-3 {\n gap: 1rem !important;\n }\n\n .gap-lg-4 {\n gap: 1.5rem !important;\n }\n\n .gap-lg-5 {\n gap: 3rem !important;\n }\n\n .justify-content-lg-start {\n justify-content: flex-start !important;\n }\n\n .justify-content-lg-end {\n justify-content: flex-end !important;\n }\n\n .justify-content-lg-center {\n justify-content: center !important;\n }\n\n .justify-content-lg-between {\n justify-content: space-between !important;\n }\n\n .justify-content-lg-around {\n justify-content: space-around !important;\n }\n\n .justify-content-lg-evenly {\n justify-content: space-evenly !important;\n }\n\n .align-items-lg-start {\n align-items: flex-start !important;\n }\n\n .align-items-lg-end {\n align-items: flex-end !important;\n }\n\n .align-items-lg-center {\n align-items: center !important;\n }\n\n .align-items-lg-baseline {\n align-items: baseline !important;\n }\n\n .align-items-lg-stretch {\n align-items: stretch !important;\n }\n\n .align-content-lg-start {\n align-content: flex-start !important;\n }\n\n .align-content-lg-end {\n align-content: flex-end !important;\n }\n\n .align-content-lg-center {\n align-content: center !important;\n }\n\n .align-content-lg-between {\n align-content: space-between !important;\n }\n\n .align-content-lg-around {\n align-content: space-around !important;\n }\n\n .align-content-lg-stretch {\n align-content: stretch !important;\n }\n\n .align-self-lg-auto {\n align-self: auto !important;\n }\n\n .align-self-lg-start {\n align-self: flex-start !important;\n }\n\n .align-self-lg-end {\n align-self: flex-end !important;\n }\n\n .align-self-lg-center {\n align-self: center !important;\n }\n\n .align-self-lg-baseline {\n align-self: baseline !important;\n }\n\n .align-self-lg-stretch {\n align-self: stretch !important;\n }\n\n .order-lg-first {\n order: -1 !important;\n }\n\n .order-lg-0 {\n order: 0 !important;\n }\n\n .order-lg-1 {\n order: 1 !important;\n }\n\n .order-lg-2 {\n order: 2 !important;\n }\n\n .order-lg-3 {\n order: 3 !important;\n }\n\n .order-lg-4 {\n order: 4 !important;\n }\n\n .order-lg-5 {\n order: 5 !important;\n }\n\n .order-lg-last {\n order: 6 !important;\n }\n\n .m-lg-0 {\n margin: 0 !important;\n }\n\n .m-lg-1 {\n margin: 0.25rem !important;\n }\n\n .m-lg-2 {\n margin: 0.5rem !important;\n }\n\n .m-lg-3 {\n margin: 1rem !important;\n }\n\n .m-lg-4 {\n margin: 1.5rem !important;\n }\n\n .m-lg-5 {\n margin: 3rem !important;\n }\n\n .m-lg-auto {\n margin: auto !important;\n }\n\n .mx-lg-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n\n .mx-lg-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n\n .mx-lg-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n\n .mx-lg-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n\n .mx-lg-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n\n .mx-lg-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n\n .mx-lg-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n\n .my-lg-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n\n .my-lg-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n\n .my-lg-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n\n .my-lg-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n\n .my-lg-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n\n .my-lg-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n\n .my-lg-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n\n .mt-lg-0 {\n margin-top: 0 !important;\n }\n\n .mt-lg-1 {\n margin-top: 0.25rem !important;\n }\n\n .mt-lg-2 {\n margin-top: 0.5rem !important;\n }\n\n .mt-lg-3 {\n margin-top: 1rem !important;\n }\n\n .mt-lg-4 {\n margin-top: 1.5rem !important;\n }\n\n .mt-lg-5 {\n margin-top: 3rem !important;\n }\n\n .mt-lg-auto {\n margin-top: auto !important;\n }\n\n .me-lg-0 {\n margin-right: 0 !important;\n }\n\n .me-lg-1 {\n margin-right: 0.25rem !important;\n }\n\n .me-lg-2 {\n margin-right: 0.5rem !important;\n }\n\n .me-lg-3 {\n margin-right: 1rem !important;\n }\n\n .me-lg-4 {\n margin-right: 1.5rem !important;\n }\n\n .me-lg-5 {\n margin-right: 3rem !important;\n }\n\n .me-lg-auto {\n margin-right: auto !important;\n }\n\n .mb-lg-0 {\n margin-bottom: 0 !important;\n }\n\n .mb-lg-1 {\n margin-bottom: 0.25rem !important;\n }\n\n .mb-lg-2 {\n margin-bottom: 0.5rem !important;\n }\n\n .mb-lg-3 {\n margin-bottom: 1rem !important;\n }\n\n .mb-lg-4 {\n margin-bottom: 1.5rem !important;\n }\n\n .mb-lg-5 {\n margin-bottom: 3rem !important;\n }\n\n .mb-lg-auto {\n margin-bottom: auto !important;\n }\n\n .ms-lg-0 {\n margin-left: 0 !important;\n }\n\n .ms-lg-1 {\n margin-left: 0.25rem !important;\n }\n\n .ms-lg-2 {\n margin-left: 0.5rem !important;\n }\n\n .ms-lg-3 {\n margin-left: 1rem !important;\n }\n\n .ms-lg-4 {\n margin-left: 1.5rem !important;\n }\n\n .ms-lg-5 {\n margin-left: 3rem !important;\n }\n\n .ms-lg-auto {\n margin-left: auto !important;\n }\n\n .p-lg-0 {\n padding: 0 !important;\n }\n\n .p-lg-1 {\n padding: 0.25rem !important;\n }\n\n .p-lg-2 {\n padding: 0.5rem !important;\n }\n\n .p-lg-3 {\n padding: 1rem !important;\n }\n\n .p-lg-4 {\n padding: 1.5rem !important;\n }\n\n .p-lg-5 {\n padding: 3rem !important;\n }\n\n .px-lg-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n\n .px-lg-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n\n .px-lg-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n\n .px-lg-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n\n .px-lg-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n\n .px-lg-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n\n .py-lg-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n\n .py-lg-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n\n .py-lg-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n\n .py-lg-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n\n .py-lg-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n\n .py-lg-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n\n .pt-lg-0 {\n padding-top: 0 !important;\n }\n\n .pt-lg-1 {\n padding-top: 0.25rem !important;\n }\n\n .pt-lg-2 {\n padding-top: 0.5rem !important;\n }\n\n .pt-lg-3 {\n padding-top: 1rem !important;\n }\n\n .pt-lg-4 {\n padding-top: 1.5rem !important;\n }\n\n .pt-lg-5 {\n padding-top: 3rem !important;\n }\n\n .pe-lg-0 {\n padding-right: 0 !important;\n }\n\n .pe-lg-1 {\n padding-right: 0.25rem !important;\n }\n\n .pe-lg-2 {\n padding-right: 0.5rem !important;\n }\n\n .pe-lg-3 {\n padding-right: 1rem !important;\n }\n\n .pe-lg-4 {\n padding-right: 1.5rem !important;\n }\n\n .pe-lg-5 {\n padding-right: 3rem !important;\n }\n\n .pb-lg-0 {\n padding-bottom: 0 !important;\n }\n\n .pb-lg-1 {\n padding-bottom: 0.25rem !important;\n }\n\n .pb-lg-2 {\n padding-bottom: 0.5rem !important;\n }\n\n .pb-lg-3 {\n padding-bottom: 1rem !important;\n }\n\n .pb-lg-4 {\n padding-bottom: 1.5rem !important;\n }\n\n .pb-lg-5 {\n padding-bottom: 3rem !important;\n }\n\n .ps-lg-0 {\n padding-left: 0 !important;\n }\n\n .ps-lg-1 {\n padding-left: 0.25rem !important;\n }\n\n .ps-lg-2 {\n padding-left: 0.5rem !important;\n }\n\n .ps-lg-3 {\n padding-left: 1rem !important;\n }\n\n .ps-lg-4 {\n padding-left: 1.5rem !important;\n }\n\n .ps-lg-5 {\n padding-left: 3rem !important;\n }\n\n .text-lg-start {\n text-align: left !important;\n }\n\n .text-lg-end {\n text-align: right !important;\n }\n\n .text-lg-center {\n text-align: center !important;\n }\n}\n@media (min-width: 1200px) {\n .float-xl-start {\n float: left !important;\n }\n\n .float-xl-end {\n float: right !important;\n }\n\n .float-xl-none {\n float: none !important;\n }\n\n .d-xl-inline {\n display: inline !important;\n }\n\n .d-xl-inline-block {\n display: inline-block !important;\n }\n\n .d-xl-block {\n display: block !important;\n }\n\n .d-xl-grid {\n display: grid !important;\n }\n\n .d-xl-table {\n display: table !important;\n }\n\n .d-xl-table-row {\n display: table-row !important;\n }\n\n .d-xl-table-cell {\n display: table-cell !important;\n }\n\n .d-xl-flex {\n display: flex !important;\n }\n\n .d-xl-inline-flex {\n display: inline-flex !important;\n }\n\n .d-xl-none {\n display: none !important;\n }\n\n .flex-xl-fill {\n flex: 1 1 auto !important;\n }\n\n .flex-xl-row {\n flex-direction: row !important;\n }\n\n .flex-xl-column {\n flex-direction: column !important;\n }\n\n .flex-xl-row-reverse {\n flex-direction: row-reverse !important;\n }\n\n .flex-xl-column-reverse {\n flex-direction: column-reverse !important;\n }\n\n .flex-xl-grow-0 {\n flex-grow: 0 !important;\n }\n\n .flex-xl-grow-1 {\n flex-grow: 1 !important;\n }\n\n .flex-xl-shrink-0 {\n flex-shrink: 0 !important;\n }\n\n .flex-xl-shrink-1 {\n flex-shrink: 1 !important;\n }\n\n .flex-xl-wrap {\n flex-wrap: wrap !important;\n }\n\n .flex-xl-nowrap {\n flex-wrap: nowrap !important;\n }\n\n .flex-xl-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n\n .gap-xl-0 {\n gap: 0 !important;\n }\n\n .gap-xl-1 {\n gap: 0.25rem !important;\n }\n\n .gap-xl-2 {\n gap: 0.5rem !important;\n }\n\n .gap-xl-3 {\n gap: 1rem !important;\n }\n\n .gap-xl-4 {\n gap: 1.5rem !important;\n }\n\n .gap-xl-5 {\n gap: 3rem !important;\n }\n\n .justify-content-xl-start {\n justify-content: flex-start !important;\n }\n\n .justify-content-xl-end {\n justify-content: flex-end !important;\n }\n\n .justify-content-xl-center {\n justify-content: center !important;\n }\n\n .justify-content-xl-between {\n justify-content: space-between !important;\n }\n\n .justify-content-xl-around {\n justify-content: space-around !important;\n }\n\n .justify-content-xl-evenly {\n justify-content: space-evenly !important;\n }\n\n .align-items-xl-start {\n align-items: flex-start !important;\n }\n\n .align-items-xl-end {\n align-items: flex-end !important;\n }\n\n .align-items-xl-center {\n align-items: center !important;\n }\n\n .align-items-xl-baseline {\n align-items: baseline !important;\n }\n\n .align-items-xl-stretch {\n align-items: stretch !important;\n }\n\n .align-content-xl-start {\n align-content: flex-start !important;\n }\n\n .align-content-xl-end {\n align-content: flex-end !important;\n }\n\n .align-content-xl-center {\n align-content: center !important;\n }\n\n .align-content-xl-between {\n align-content: space-between !important;\n }\n\n .align-content-xl-around {\n align-content: space-around !important;\n }\n\n .align-content-xl-stretch {\n align-content: stretch !important;\n }\n\n .align-self-xl-auto {\n align-self: auto !important;\n }\n\n .align-self-xl-start {\n align-self: flex-start !important;\n }\n\n .align-self-xl-end {\n align-self: flex-end !important;\n }\n\n .align-self-xl-center {\n align-self: center !important;\n }\n\n .align-self-xl-baseline {\n align-self: baseline !important;\n }\n\n .align-self-xl-stretch {\n align-self: stretch !important;\n }\n\n .order-xl-first {\n order: -1 !important;\n }\n\n .order-xl-0 {\n order: 0 !important;\n }\n\n .order-xl-1 {\n order: 1 !important;\n }\n\n .order-xl-2 {\n order: 2 !important;\n }\n\n .order-xl-3 {\n order: 3 !important;\n }\n\n .order-xl-4 {\n order: 4 !important;\n }\n\n .order-xl-5 {\n order: 5 !important;\n }\n\n .order-xl-last {\n order: 6 !important;\n }\n\n .m-xl-0 {\n margin: 0 !important;\n }\n\n .m-xl-1 {\n margin: 0.25rem !important;\n }\n\n .m-xl-2 {\n margin: 0.5rem !important;\n }\n\n .m-xl-3 {\n margin: 1rem !important;\n }\n\n .m-xl-4 {\n margin: 1.5rem !important;\n }\n\n .m-xl-5 {\n margin: 3rem !important;\n }\n\n .m-xl-auto {\n margin: auto !important;\n }\n\n .mx-xl-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n\n .mx-xl-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n\n .mx-xl-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n\n .mx-xl-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n\n .mx-xl-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n\n .mx-xl-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n\n .mx-xl-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n\n .my-xl-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n\n .my-xl-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n\n .my-xl-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n\n .my-xl-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n\n .my-xl-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n\n .my-xl-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n\n .my-xl-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n\n .mt-xl-0 {\n margin-top: 0 !important;\n }\n\n .mt-xl-1 {\n margin-top: 0.25rem !important;\n }\n\n .mt-xl-2 {\n margin-top: 0.5rem !important;\n }\n\n .mt-xl-3 {\n margin-top: 1rem !important;\n }\n\n .mt-xl-4 {\n margin-top: 1.5rem !important;\n }\n\n .mt-xl-5 {\n margin-top: 3rem !important;\n }\n\n .mt-xl-auto {\n margin-top: auto !important;\n }\n\n .me-xl-0 {\n margin-right: 0 !important;\n }\n\n .me-xl-1 {\n margin-right: 0.25rem !important;\n }\n\n .me-xl-2 {\n margin-right: 0.5rem !important;\n }\n\n .me-xl-3 {\n margin-right: 1rem !important;\n }\n\n .me-xl-4 {\n margin-right: 1.5rem !important;\n }\n\n .me-xl-5 {\n margin-right: 3rem !important;\n }\n\n .me-xl-auto {\n margin-right: auto !important;\n }\n\n .mb-xl-0 {\n margin-bottom: 0 !important;\n }\n\n .mb-xl-1 {\n margin-bottom: 0.25rem !important;\n }\n\n .mb-xl-2 {\n margin-bottom: 0.5rem !important;\n }\n\n .mb-xl-3 {\n margin-bottom: 1rem !important;\n }\n\n .mb-xl-4 {\n margin-bottom: 1.5rem !important;\n }\n\n .mb-xl-5 {\n margin-bottom: 3rem !important;\n }\n\n .mb-xl-auto {\n margin-bottom: auto !important;\n }\n\n .ms-xl-0 {\n margin-left: 0 !important;\n }\n\n .ms-xl-1 {\n margin-left: 0.25rem !important;\n }\n\n .ms-xl-2 {\n margin-left: 0.5rem !important;\n }\n\n .ms-xl-3 {\n margin-left: 1rem !important;\n }\n\n .ms-xl-4 {\n margin-left: 1.5rem !important;\n }\n\n .ms-xl-5 {\n margin-left: 3rem !important;\n }\n\n .ms-xl-auto {\n margin-left: auto !important;\n }\n\n .p-xl-0 {\n padding: 0 !important;\n }\n\n .p-xl-1 {\n padding: 0.25rem !important;\n }\n\n .p-xl-2 {\n padding: 0.5rem !important;\n }\n\n .p-xl-3 {\n padding: 1rem !important;\n }\n\n .p-xl-4 {\n padding: 1.5rem !important;\n }\n\n .p-xl-5 {\n padding: 3rem !important;\n }\n\n .px-xl-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n\n .px-xl-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n\n .px-xl-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n\n .px-xl-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n\n .px-xl-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n\n .px-xl-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n\n .py-xl-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n\n .py-xl-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n\n .py-xl-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n\n .py-xl-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n\n .py-xl-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n\n .py-xl-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n\n .pt-xl-0 {\n padding-top: 0 !important;\n }\n\n .pt-xl-1 {\n padding-top: 0.25rem !important;\n }\n\n .pt-xl-2 {\n padding-top: 0.5rem !important;\n }\n\n .pt-xl-3 {\n padding-top: 1rem !important;\n }\n\n .pt-xl-4 {\n padding-top: 1.5rem !important;\n }\n\n .pt-xl-5 {\n padding-top: 3rem !important;\n }\n\n .pe-xl-0 {\n padding-right: 0 !important;\n }\n\n .pe-xl-1 {\n padding-right: 0.25rem !important;\n }\n\n .pe-xl-2 {\n padding-right: 0.5rem !important;\n }\n\n .pe-xl-3 {\n padding-right: 1rem !important;\n }\n\n .pe-xl-4 {\n padding-right: 1.5rem !important;\n }\n\n .pe-xl-5 {\n padding-right: 3rem !important;\n }\n\n .pb-xl-0 {\n padding-bottom: 0 !important;\n }\n\n .pb-xl-1 {\n padding-bottom: 0.25rem !important;\n }\n\n .pb-xl-2 {\n padding-bottom: 0.5rem !important;\n }\n\n .pb-xl-3 {\n padding-bottom: 1rem !important;\n }\n\n .pb-xl-4 {\n padding-bottom: 1.5rem !important;\n }\n\n .pb-xl-5 {\n padding-bottom: 3rem !important;\n }\n\n .ps-xl-0 {\n padding-left: 0 !important;\n }\n\n .ps-xl-1 {\n padding-left: 0.25rem !important;\n }\n\n .ps-xl-2 {\n padding-left: 0.5rem !important;\n }\n\n .ps-xl-3 {\n padding-left: 1rem !important;\n }\n\n .ps-xl-4 {\n padding-left: 1.5rem !important;\n }\n\n .ps-xl-5 {\n padding-left: 3rem !important;\n }\n\n .text-xl-start {\n text-align: left !important;\n }\n\n .text-xl-end {\n text-align: right !important;\n }\n\n .text-xl-center {\n text-align: center !important;\n }\n}\n@media (min-width: 1400px) {\n .float-xxl-start {\n float: left !important;\n }\n\n .float-xxl-end {\n float: right !important;\n }\n\n .float-xxl-none {\n float: none !important;\n }\n\n .d-xxl-inline {\n display: inline !important;\n }\n\n .d-xxl-inline-block {\n display: inline-block !important;\n }\n\n .d-xxl-block {\n display: block !important;\n }\n\n .d-xxl-grid {\n display: grid !important;\n }\n\n .d-xxl-table {\n display: table !important;\n }\n\n .d-xxl-table-row {\n display: table-row !important;\n }\n\n .d-xxl-table-cell {\n display: table-cell !important;\n }\n\n .d-xxl-flex {\n display: flex !important;\n }\n\n .d-xxl-inline-flex {\n display: inline-flex !important;\n }\n\n .d-xxl-none {\n display: none !important;\n }\n\n .flex-xxl-fill {\n flex: 1 1 auto !important;\n }\n\n .flex-xxl-row {\n flex-direction: row !important;\n }\n\n .flex-xxl-column {\n flex-direction: column !important;\n }\n\n .flex-xxl-row-reverse {\n flex-direction: row-reverse !important;\n }\n\n .flex-xxl-column-reverse {\n flex-direction: column-reverse !important;\n }\n\n .flex-xxl-grow-0 {\n flex-grow: 0 !important;\n }\n\n .flex-xxl-grow-1 {\n flex-grow: 1 !important;\n }\n\n .flex-xxl-shrink-0 {\n flex-shrink: 0 !important;\n }\n\n .flex-xxl-shrink-1 {\n flex-shrink: 1 !important;\n }\n\n .flex-xxl-wrap {\n flex-wrap: wrap !important;\n }\n\n .flex-xxl-nowrap {\n flex-wrap: nowrap !important;\n }\n\n .flex-xxl-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n\n .gap-xxl-0 {\n gap: 0 !important;\n }\n\n .gap-xxl-1 {\n gap: 0.25rem !important;\n }\n\n .gap-xxl-2 {\n gap: 0.5rem !important;\n }\n\n .gap-xxl-3 {\n gap: 1rem !important;\n }\n\n .gap-xxl-4 {\n gap: 1.5rem !important;\n }\n\n .gap-xxl-5 {\n gap: 3rem !important;\n }\n\n .justify-content-xxl-start {\n justify-content: flex-start !important;\n }\n\n .justify-content-xxl-end {\n justify-content: flex-end !important;\n }\n\n .justify-content-xxl-center {\n justify-content: center !important;\n }\n\n .justify-content-xxl-between {\n justify-content: space-between !important;\n }\n\n .justify-content-xxl-around {\n justify-content: space-around !important;\n }\n\n .justify-content-xxl-evenly {\n justify-content: space-evenly !important;\n }\n\n .align-items-xxl-start {\n align-items: flex-start !important;\n }\n\n .align-items-xxl-end {\n align-items: flex-end !important;\n }\n\n .align-items-xxl-center {\n align-items: center !important;\n }\n\n .align-items-xxl-baseline {\n align-items: baseline !important;\n }\n\n .align-items-xxl-stretch {\n align-items: stretch !important;\n }\n\n .align-content-xxl-start {\n align-content: flex-start !important;\n }\n\n .align-content-xxl-end {\n align-content: flex-end !important;\n }\n\n .align-content-xxl-center {\n align-content: center !important;\n }\n\n .align-content-xxl-between {\n align-content: space-between !important;\n }\n\n .align-content-xxl-around {\n align-content: space-around !important;\n }\n\n .align-content-xxl-stretch {\n align-content: stretch !important;\n }\n\n .align-self-xxl-auto {\n align-self: auto !important;\n }\n\n .align-self-xxl-start {\n align-self: flex-start !important;\n }\n\n .align-self-xxl-end {\n align-self: flex-end !important;\n }\n\n .align-self-xxl-center {\n align-self: center !important;\n }\n\n .align-self-xxl-baseline {\n align-self: baseline !important;\n }\n\n .align-self-xxl-stretch {\n align-self: stretch !important;\n }\n\n .order-xxl-first {\n order: -1 !important;\n }\n\n .order-xxl-0 {\n order: 0 !important;\n }\n\n .order-xxl-1 {\n order: 1 !important;\n }\n\n .order-xxl-2 {\n order: 2 !important;\n }\n\n .order-xxl-3 {\n order: 3 !important;\n }\n\n .order-xxl-4 {\n order: 4 !important;\n }\n\n .order-xxl-5 {\n order: 5 !important;\n }\n\n .order-xxl-last {\n order: 6 !important;\n }\n\n .m-xxl-0 {\n margin: 0 !important;\n }\n\n .m-xxl-1 {\n margin: 0.25rem !important;\n }\n\n .m-xxl-2 {\n margin: 0.5rem !important;\n }\n\n .m-xxl-3 {\n margin: 1rem !important;\n }\n\n .m-xxl-4 {\n margin: 1.5rem !important;\n }\n\n .m-xxl-5 {\n margin: 3rem !important;\n }\n\n .m-xxl-auto {\n margin: auto !important;\n }\n\n .mx-xxl-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n\n .mx-xxl-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n\n .mx-xxl-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n\n .mx-xxl-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n\n .mx-xxl-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n\n .mx-xxl-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n\n .mx-xxl-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n\n .my-xxl-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n\n .my-xxl-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n\n .my-xxl-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n\n .my-xxl-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n\n .my-xxl-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n\n .my-xxl-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n\n .my-xxl-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n\n .mt-xxl-0 {\n margin-top: 0 !important;\n }\n\n .mt-xxl-1 {\n margin-top: 0.25rem !important;\n }\n\n .mt-xxl-2 {\n margin-top: 0.5rem !important;\n }\n\n .mt-xxl-3 {\n margin-top: 1rem !important;\n }\n\n .mt-xxl-4 {\n margin-top: 1.5rem !important;\n }\n\n .mt-xxl-5 {\n margin-top: 3rem !important;\n }\n\n .mt-xxl-auto {\n margin-top: auto !important;\n }\n\n .me-xxl-0 {\n margin-right: 0 !important;\n }\n\n .me-xxl-1 {\n margin-right: 0.25rem !important;\n }\n\n .me-xxl-2 {\n margin-right: 0.5rem !important;\n }\n\n .me-xxl-3 {\n margin-right: 1rem !important;\n }\n\n .me-xxl-4 {\n margin-right: 1.5rem !important;\n }\n\n .me-xxl-5 {\n margin-right: 3rem !important;\n }\n\n .me-xxl-auto {\n margin-right: auto !important;\n }\n\n .mb-xxl-0 {\n margin-bottom: 0 !important;\n }\n\n .mb-xxl-1 {\n margin-bottom: 0.25rem !important;\n }\n\n .mb-xxl-2 {\n margin-bottom: 0.5rem !important;\n }\n\n .mb-xxl-3 {\n margin-bottom: 1rem !important;\n }\n\n .mb-xxl-4 {\n margin-bottom: 1.5rem !important;\n }\n\n .mb-xxl-5 {\n margin-bottom: 3rem !important;\n }\n\n .mb-xxl-auto {\n margin-bottom: auto !important;\n }\n\n .ms-xxl-0 {\n margin-left: 0 !important;\n }\n\n .ms-xxl-1 {\n margin-left: 0.25rem !important;\n }\n\n .ms-xxl-2 {\n margin-left: 0.5rem !important;\n }\n\n .ms-xxl-3 {\n margin-left: 1rem !important;\n }\n\n .ms-xxl-4 {\n margin-left: 1.5rem !important;\n }\n\n .ms-xxl-5 {\n margin-left: 3rem !important;\n }\n\n .ms-xxl-auto {\n margin-left: auto !important;\n }\n\n .p-xxl-0 {\n padding: 0 !important;\n }\n\n .p-xxl-1 {\n padding: 0.25rem !important;\n }\n\n .p-xxl-2 {\n padding: 0.5rem !important;\n }\n\n .p-xxl-3 {\n padding: 1rem !important;\n }\n\n .p-xxl-4 {\n padding: 1.5rem !important;\n }\n\n .p-xxl-5 {\n padding: 3rem !important;\n }\n\n .px-xxl-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n\n .px-xxl-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n\n .px-xxl-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n\n .px-xxl-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n\n .px-xxl-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n\n .px-xxl-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n\n .py-xxl-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n\n .py-xxl-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n\n .py-xxl-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n\n .py-xxl-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n\n .py-xxl-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n\n .py-xxl-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n\n .pt-xxl-0 {\n padding-top: 0 !important;\n }\n\n .pt-xxl-1 {\n padding-top: 0.25rem !important;\n }\n\n .pt-xxl-2 {\n padding-top: 0.5rem !important;\n }\n\n .pt-xxl-3 {\n padding-top: 1rem !important;\n }\n\n .pt-xxl-4 {\n padding-top: 1.5rem !important;\n }\n\n .pt-xxl-5 {\n padding-top: 3rem !important;\n }\n\n .pe-xxl-0 {\n padding-right: 0 !important;\n }\n\n .pe-xxl-1 {\n padding-right: 0.25rem !important;\n }\n\n .pe-xxl-2 {\n padding-right: 0.5rem !important;\n }\n\n .pe-xxl-3 {\n padding-right: 1rem !important;\n }\n\n .pe-xxl-4 {\n padding-right: 1.5rem !important;\n }\n\n .pe-xxl-5 {\n padding-right: 3rem !important;\n }\n\n .pb-xxl-0 {\n padding-bottom: 0 !important;\n }\n\n .pb-xxl-1 {\n padding-bottom: 0.25rem !important;\n }\n\n .pb-xxl-2 {\n padding-bottom: 0.5rem !important;\n }\n\n .pb-xxl-3 {\n padding-bottom: 1rem !important;\n }\n\n .pb-xxl-4 {\n padding-bottom: 1.5rem !important;\n }\n\n .pb-xxl-5 {\n padding-bottom: 3rem !important;\n }\n\n .ps-xxl-0 {\n padding-left: 0 !important;\n }\n\n .ps-xxl-1 {\n padding-left: 0.25rem !important;\n }\n\n .ps-xxl-2 {\n padding-left: 0.5rem !important;\n }\n\n .ps-xxl-3 {\n padding-left: 1rem !important;\n }\n\n .ps-xxl-4 {\n padding-left: 1.5rem !important;\n }\n\n .ps-xxl-5 {\n padding-left: 3rem !important;\n }\n\n .text-xxl-start {\n text-align: left !important;\n }\n\n .text-xxl-end {\n text-align: right !important;\n }\n\n .text-xxl-center {\n text-align: center !important;\n }\n}\n@media (min-width: 1200px) {\n .fs-1 {\n font-size: 2.5rem !important;\n }\n\n .fs-2 {\n font-size: 2rem !important;\n }\n\n .fs-3 {\n font-size: 1.75rem !important;\n }\n\n .fs-4 {\n font-size: 1.5rem !important;\n }\n}\n@media print {\n .d-print-inline {\n display: inline !important;\n }\n\n .d-print-inline-block {\n display: inline-block !important;\n }\n\n .d-print-block {\n display: block !important;\n }\n\n .d-print-grid {\n display: grid !important;\n }\n\n .d-print-table {\n display: table !important;\n }\n\n .d-print-table-row {\n display: table-row !important;\n }\n\n .d-print-table-cell {\n display: table-cell !important;\n }\n\n .d-print-flex {\n display: flex !important;\n }\n\n .d-print-inline-flex {\n display: inline-flex !important;\n }\n\n .d-print-none {\n display: none !important;\n }\n}\n\n/*# sourceMappingURL=bootstrap.css.map */\n","/*!\n * Bootstrap v5.1.3 (https://getbootstrap.com/)\n * Copyright 2011-2021 The Bootstrap Authors\n * Copyright 2011-2021 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n */\n\n// scss-docs-start import-stack\n// Configuration\n@import \"functions\";\n@import \"variables\";\n@import \"mixins\";\n@import \"utilities\";\n\n// Layout & components\n@import \"root\";\n@import \"reboot\";\n@import \"type\";\n@import \"images\";\n@import \"containers\";\n@import \"grid\";\n@import \"tables\";\n@import \"forms\";\n@import \"buttons\";\n@import \"transitions\";\n@import \"dropdown\";\n@import \"button-group\";\n@import \"nav\";\n@import \"navbar\";\n@import \"card\";\n@import \"accordion\";\n@import \"breadcrumb\";\n@import \"pagination\";\n@import \"badge\";\n@import \"alert\";\n@import \"progress\";\n@import \"list-group\";\n@import \"close\";\n@import \"toasts\";\n@import \"modal\";\n@import \"tooltip\";\n@import \"popover\";\n@import \"carousel\";\n@import \"spinners\";\n@import \"offcanvas\";\n@import \"placeholders\";\n\n// Helpers\n@import \"helpers\";\n\n// Utilities\n@import \"utilities/api\";\n// scss-docs-end import-stack\n",":root {\n // Note: Custom variable values only support SassScript inside `#{}`.\n\n // Colors\n //\n // Generate palettes for full colors, grays, and theme colors.\n\n @each $color, $value in $colors {\n --#{$variable-prefix}#{$color}: #{$value};\n }\n\n @each $color, $value in $grays {\n --#{$variable-prefix}gray-#{$color}: #{$value};\n }\n\n @each $color, $value in $theme-colors {\n --#{$variable-prefix}#{$color}: #{$value};\n }\n\n @each $color, $value in $theme-colors-rgb {\n --#{$variable-prefix}#{$color}-rgb: #{$value};\n }\n\n --#{$variable-prefix}white-rgb: #{to-rgb($white)};\n --#{$variable-prefix}black-rgb: #{to-rgb($black)};\n --#{$variable-prefix}body-color-rgb: #{to-rgb($body-color)};\n --#{$variable-prefix}body-bg-rgb: #{to-rgb($body-bg)};\n\n // Fonts\n\n // Note: Use `inspect` for lists so that quoted items keep the quotes.\n // See https://github.com/sass/sass/issues/2383#issuecomment-336349172\n --#{$variable-prefix}font-sans-serif: #{inspect($font-family-sans-serif)};\n --#{$variable-prefix}font-monospace: #{inspect($font-family-monospace)};\n --#{$variable-prefix}gradient: #{$gradient};\n\n // Root and body\n // stylelint-disable custom-property-empty-line-before\n // scss-docs-start root-body-variables\n @if $font-size-root != null {\n --#{$variable-prefix}root-font-size: #{$font-size-root};\n }\n --#{$variable-prefix}body-font-family: #{$font-family-base};\n --#{$variable-prefix}body-font-size: #{$font-size-base};\n --#{$variable-prefix}body-font-weight: #{$font-weight-base};\n --#{$variable-prefix}body-line-height: #{$line-height-base};\n --#{$variable-prefix}body-color: #{$body-color};\n @if $body-text-align != null {\n --#{$variable-prefix}body-text-align: #{$body-text-align};\n }\n --#{$variable-prefix}body-bg: #{$body-bg};\n // scss-docs-end root-body-variables\n // stylelint-enable custom-property-empty-line-before\n}\n","// stylelint-disable declaration-no-important, selector-no-qualifying-type, property-no-vendor-prefix\n\n\n// Reboot\n//\n// Normalization of HTML elements, manually forked from Normalize.css to remove\n// styles targeting irrelevant browsers while applying new styles.\n//\n// Normalize is licensed MIT. https://github.com/necolas/normalize.css\n\n\n// Document\n//\n// Change from `box-sizing: content-box` so that `width` is not affected by `padding` or `border`.\n\n*,\n*::before,\n*::after {\n box-sizing: border-box;\n}\n\n\n// Root\n//\n// Ability to the value of the root font sizes, affecting the value of `rem`.\n// null by default, thus nothing is generated.\n\n:root {\n @if $font-size-root != null {\n font-size: var(--#{$variable-prefix}root-font-size);\n }\n\n @if $enable-smooth-scroll {\n @media (prefers-reduced-motion: no-preference) {\n scroll-behavior: smooth;\n }\n }\n}\n\n\n// Body\n//\n// 1. Remove the margin in all browsers.\n// 2. As a best practice, apply a default `background-color`.\n// 3. Prevent adjustments of font size after orientation changes in iOS.\n// 4. Change the default tap highlight to be completely transparent in iOS.\n\n// scss-docs-start reboot-body-rules\nbody {\n margin: 0; // 1\n font-family: var(--#{$variable-prefix}body-font-family);\n @include font-size(var(--#{$variable-prefix}body-font-size));\n font-weight: var(--#{$variable-prefix}body-font-weight);\n line-height: var(--#{$variable-prefix}body-line-height);\n color: var(--#{$variable-prefix}body-color);\n text-align: var(--#{$variable-prefix}body-text-align);\n background-color: var(--#{$variable-prefix}body-bg); // 2\n -webkit-text-size-adjust: 100%; // 3\n -webkit-tap-highlight-color: rgba($black, 0); // 4\n}\n// scss-docs-end reboot-body-rules\n\n\n// Content grouping\n//\n// 1. Reset Firefox's gray color\n// 2. Set correct height and prevent the `size` attribute to make the `hr` look like an input field\n\nhr {\n margin: $hr-margin-y 0;\n color: $hr-color; // 1\n background-color: currentColor;\n border: 0;\n opacity: $hr-opacity;\n}\n\nhr:not([size]) {\n height: $hr-height; // 2\n}\n\n\n// Typography\n//\n// 1. Remove top margins from headings\n// By default, `

`-`

` all receive top and bottom margins. We nuke the top\n// margin for easier control within type scales as it avoids margin collapsing.\n\n%heading {\n margin-top: 0; // 1\n margin-bottom: $headings-margin-bottom;\n font-family: $headings-font-family;\n font-style: $headings-font-style;\n font-weight: $headings-font-weight;\n line-height: $headings-line-height;\n color: $headings-color;\n}\n\nh1 {\n @extend %heading;\n @include font-size($h1-font-size);\n}\n\nh2 {\n @extend %heading;\n @include font-size($h2-font-size);\n}\n\nh3 {\n @extend %heading;\n @include font-size($h3-font-size);\n}\n\nh4 {\n @extend %heading;\n @include font-size($h4-font-size);\n}\n\nh5 {\n @extend %heading;\n @include font-size($h5-font-size);\n}\n\nh6 {\n @extend %heading;\n @include font-size($h6-font-size);\n}\n\n\n// Reset margins on paragraphs\n//\n// Similarly, the top margin on `

`s get reset. However, we also reset the\n// bottom margin to use `rem` units instead of `em`.\n\np {\n margin-top: 0;\n margin-bottom: $paragraph-margin-bottom;\n}\n\n\n// Abbreviations\n//\n// 1. Duplicate behavior to the data-bs-* attribute for our tooltip plugin\n// 2. Add the correct text decoration in Chrome, Edge, Opera, and Safari.\n// 3. Add explicit cursor to indicate changed behavior.\n// 4. Prevent the text-decoration to be skipped.\n\nabbr[title],\nabbr[data-bs-original-title] { // 1\n text-decoration: underline dotted; // 2\n cursor: help; // 3\n text-decoration-skip-ink: none; // 4\n}\n\n\n// Address\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\n\n// Lists\n\nol,\nul {\n padding-left: 2rem;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: $dt-font-weight;\n}\n\n// 1. Undo browser default\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0; // 1\n}\n\n\n// Blockquote\n\nblockquote {\n margin: 0 0 1rem;\n}\n\n\n// Strong\n//\n// Add the correct font weight in Chrome, Edge, and Safari\n\nb,\nstrong {\n font-weight: $font-weight-bolder;\n}\n\n\n// Small\n//\n// Add the correct font size in all browsers\n\nsmall {\n @include font-size($small-font-size);\n}\n\n\n// Mark\n\nmark {\n padding: $mark-padding;\n background-color: $mark-bg;\n}\n\n\n// Sub and Sup\n//\n// Prevent `sub` and `sup` elements from affecting the line height in\n// all browsers.\n\nsub,\nsup {\n position: relative;\n @include font-size($sub-sup-font-size);\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub { bottom: -.25em; }\nsup { top: -.5em; }\n\n\n// Links\n\na {\n color: $link-color;\n text-decoration: $link-decoration;\n\n &:hover {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n }\n}\n\n// And undo these styles for placeholder links/named anchors (without href).\n// It would be more straightforward to just use a[href] in previous block, but that\n// causes specificity issues in many other styles that are too complex to fix.\n// See https://github.com/twbs/bootstrap/issues/19402\n\na:not([href]):not([class]) {\n &,\n &:hover {\n color: inherit;\n text-decoration: none;\n }\n}\n\n\n// Code\n\npre,\ncode,\nkbd,\nsamp {\n font-family: $font-family-code;\n @include font-size(1em); // Correct the odd `em` font sizing in all browsers.\n direction: ltr #{\"/* rtl:ignore */\"};\n unicode-bidi: bidi-override;\n}\n\n// 1. Remove browser default top margin\n// 2. Reset browser default of `1em` to use `rem`s\n// 3. Don't allow content to break outside\n\npre {\n display: block;\n margin-top: 0; // 1\n margin-bottom: 1rem; // 2\n overflow: auto; // 3\n @include font-size($code-font-size);\n color: $pre-color;\n\n // Account for some code outputs that place code tags in pre tags\n code {\n @include font-size(inherit);\n color: inherit;\n word-break: normal;\n }\n}\n\ncode {\n @include font-size($code-font-size);\n color: $code-color;\n word-wrap: break-word;\n\n // Streamline the style when inside anchors to avoid broken underline and more\n a > & {\n color: inherit;\n }\n}\n\nkbd {\n padding: $kbd-padding-y $kbd-padding-x;\n @include font-size($kbd-font-size);\n color: $kbd-color;\n background-color: $kbd-bg;\n @include border-radius($border-radius-sm);\n\n kbd {\n padding: 0;\n @include font-size(1em);\n font-weight: $nested-kbd-font-weight;\n }\n}\n\n\n// Figures\n//\n// Apply a consistent margin strategy (matches our type styles).\n\nfigure {\n margin: 0 0 1rem;\n}\n\n\n// Images and content\n\nimg,\nsvg {\n vertical-align: middle;\n}\n\n\n// Tables\n//\n// Prevent double borders\n\ntable {\n caption-side: bottom;\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: $table-cell-padding-y;\n padding-bottom: $table-cell-padding-y;\n color: $table-caption-color;\n text-align: left;\n}\n\n// 1. Removes font-weight bold by inheriting\n// 2. Matches default `` alignment by inheriting `text-align`.\n// 3. Fix alignment for Safari\n\nth {\n font-weight: $table-th-font-weight; // 1\n text-align: inherit; // 2\n text-align: -webkit-match-parent; // 3\n}\n\nthead,\ntbody,\ntfoot,\ntr,\ntd,\nth {\n border-color: inherit;\n border-style: solid;\n border-width: 0;\n}\n\n\n// Forms\n//\n// 1. Allow labels to use `margin` for spacing.\n\nlabel {\n display: inline-block; // 1\n}\n\n// Remove the default `border-radius` that macOS Chrome adds.\n// See https://github.com/twbs/bootstrap/issues/24093\n\nbutton {\n // stylelint-disable-next-line property-disallowed-list\n border-radius: 0;\n}\n\n// Explicitly remove focus outline in Chromium when it shouldn't be\n// visible (e.g. as result of mouse click or touch tap). It already\n// should be doing this automatically, but seems to currently be\n// confused and applies its very visible two-tone outline anyway.\n\nbutton:focus:not(:focus-visible) {\n outline: 0;\n}\n\n// 1. Remove the margin in Firefox and Safari\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0; // 1\n font-family: inherit;\n @include font-size(inherit);\n line-height: inherit;\n}\n\n// Remove the inheritance of text transform in Firefox\nbutton,\nselect {\n text-transform: none;\n}\n// Set the cursor for non-`