diff --git a/blog/2023-08-26-welcome/index.md b/blog/2023-08-26-welcome/index.md deleted file mode 100644 index b32e6fd..0000000 --- a/blog/2023-08-26-welcome/index.md +++ /dev/null @@ -1,111 +0,0 @@ ---- -slug: coderabbit-deep-dive -title: AI and the Future of Code Reviews - A Deep Dive into CodeRabbit -description: AI and the Future of Code Reviews - A Deep Dive into CodeRabbit -authors: [gur, vishu] -tags: ["Rate limits", "Openai", "Prioritization"] -image: /img/blogs/founder_blog_meta.jpeg -hide_table_of_contents: false ---- - -<head> - <meta charSet="utf-8" /> - <link rel="apple-touch-icon" sizes="180x180" href="/icons/apple-touch-icon.png" /> - <link rel="icon" type="image/png" sizes="32x32" href="/img/favIcon.png" /> - <link rel="icon" type="image/png" sizes="16x16" href="/img/favIcon.png"/> - <meta content="/icons/apple-touch-icon.png" itemprop="image" /> - <link rel="icon" href="/icons/favicon-32x32.ico"></link> - - <link rel="manifest" href="/icons/site.webmanifest"></link> - - <title>AI and the Future of Code Reviews - A Deep Dive into CodeRabbit</title> - <meta name="title" content="CodeRabbit: Bringing AI to Code Reviews" /> - - <meta property="og:type" content="article" /> - <meta property="og:url" content="https://blog.coderabbit.ai/blog/coderabbit-deep-dive" /> - <meta property="og:title" content="AI and the Future of Code Reviews: A Deep Dive into CodeRabbit" /> - <meta property="og:image" content="https://docs.coderabbit.ai/img/blogs/founder_blog_meta.jpeg" /> - - <meta name="twitter:image" content="https://blog.coderabbit.ai/img/blogs/founder_blog_meta.jpeg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="AI and the Future of Code Reviews: A Deep Dive into CodeRabbit" /> -</head> - -<!-- import ShareButton from '../../src/components/ShareButton/ShareButton'; -import Header from '../../src/components/Header/Header'; -import Layout from '../../src/pages/page'; --> - -<!-- <Header></Header> -<Layout></Layout> --> - -We are witnessing an inflection point in the software development industry. Developers around the world have been realizing the incredible possibilities that AI can bring. The introduction of [GitHub Copilot](https://github.com/features/copilot) and [ChatGPT](https://chat.openai.com/auth/login) have revolutionized software development. They have been the [fastest-growing tools](https://aibusiness.com/companies/one-year-on-github-copilot-adoption-soars) in the history of software development. - -While on the code generation side, many tools have emerged, the code review process has remained largely unchanged. We continue to use the same tools and processes that were used 10 years ago. The code is still manually reviewed, which is slow, error-prone, and expensive. To address this, we are building [CodeRabbit](https://coderabbit.ai/), an AI-powered code reviewer that is part of the code merge and CI/CD process. With CodeRabbit our vision is to speed up the code merge process by an order of magnitude, while also improving the quality of the code that goes beyond what is possible with human reviewers alone and existing linting tools. - -<!--truncate--> - -## Impediments to shipping quality software @Speed - -An average developer spends most of their time between writing and reviewing the code. Typically, the development process involves branching off from the main code base, developing a new feature or fixing a bug, and then merging the code back into the mainline. To write software, developers use modern editors such as Visual Studio Code which include sophisticated language servers, static analyzers and linters. These tools are being rapidly augmented by AI-powered extensions such as GitHub Copilot. Local development tools are just one part of the equation. - -Relying on local tools alone is not sufficient to prevent quality issues, as they are inconsistent across the developers which makes it hard to enforce standards. To ensure quality, the code is merged collaboratively in the form of [pull requests (PR)](https://docs.github.com/en/pull-requests) in platforms such as GitHub/GitLab. As soon as the PR is opened, the CI/CD process kicks in. The code is linted, compiled and tested. Most importantly, the code is reviewed by a peer who checks for the intention of changes, in addition to looking for coding standards, security vulnerabilities, and other issues. The reviews require a broader context to not just understand the changes but also evaluate the impact on the larger codebase. The reviewer approves the PR, and the code is merged into the main codebase. The code review is required not just for the quality of the code but also for meeting compliance and regulatory requirements. - -While the ideal code review process sounds smooth and efficient, the reality is often riddled with challenges and inefficiencies. Specifically, the manual review is often the slowest part of the development process. It is not uncommon for a **PR** to take days or even weeks to get merged. Here's a brief glimpse into the challenges: - -**Team Slowdown:** The waiting period for code reviews and merges affects not just individual developers but the whole team. Project timelines get stretched, leading to delays in launching new features or fixing critical bugs. - -**Context Switching:** Developers often lose context when they switch from coding to waiting for a review. Getting back into the code takes time and mental energy, which hampers productivity. - -**Rubber-Stamp Reviews:** In dysfunctional teams, the code review process can become a mere formality. Reviewers might approve code without thorough inspection, allowing bugs and vulnerabilities to slip through. - -**Personality Clashes:** Sometimes, friction between the developer and the reviewer goes beyond code quality, leading to nitpicking and unnecessary delays. This can create a toxic work environment, affecting the team's morale. - -**Job Dissatisfaction:** Continual delays and inefficiencies in the code merge process can often demoralize developers to the point where they consider switching jobs, affecting the company's retention rates. - -In summary, the status-quo is not ideal, and it is evident from the software bugs, security vulnerabilities, and the service outages that frequently plague the software industry. - -## Merging code 10x faster with CodeRabbit - -CodeRabbit is an AI-powered code reviewer that significantly speeds up the code review process while also improving the quality of the code. It works seamlessly within the pull request workflow and collaborates with the developer and the reviewer to ensure code quality. It goes beyond existing linters and static code analysis tools in uncovering issues and suggesting improvements by providing a human-like understanding of the objective of the code. - -With CodeRabbit, developers get context aware feedback within minutes, which enables them to make improvements based on best practices and get their code ready to be merged faster. CodeRabbit also helps reviewers by providing them with confidence and speed to approve the code faster. Reviewers can use CodeRabbit's auto-generated walkthrough and suggestions as a starting point for their review. Peer reviewer can have a three-way collaboration including the developer, and CodeRabbit, which can significantly enrich the review experience while saving them time and effort. - -CodeRabbit is built on top of the generative AI to provide the following key capabilities: - -**Summarization:** CodeRabbit summarizes the code changes in the PR and provides a high-level overview. This helps the reviewer and product team to quickly understand the changes and the impact on the product. - -**Incremental Reviews:** CodeRabbit thoroughly reviews the code after each commit and provides incremental feedback to the developer. It uncovers issues and suggests improvements by commenting on the code like a human reviewer. - -**Chat about changes:** CodeRabbit provides conversational capability that allows developers and reviewers to ask questions, generate code, and get feedback in the context of changes. - -## Designing CodeRabbit - -The review process is multi-stage and shown in the figure below. CodeRabbit's workflow is triggered when a developer opens a pull request or commits code to an existing pull request. This is followed by various summarization and review stages. - - - -CodeRabbit is not just a simple wrapper that does pass-through to the LLM models. To circumvent context size limits, CodeRabbit uses an innovative, multi-LLM and multi-stage approach to scale reviews for larger change sets. Unlike AI-based code completion tools, code reviews are a much more complex problem. The reviewer context is much broader than the developer context, as the reviewer needs to uncover not just obvious issues but also understand the larger context of the pull request and changes across multiple files. Below is a glimpse into the challenges we faced and the solutions we came up with: - -**Context window size:** The LLM models have limited context windows, for instance,`gpt-3.5-turbo` has a context window of 4K or 16K tokens and `gpt-4` has a context window of 8K tokens. This is often insufficient to pack larger change sets. To circumvent this, we provide various summaries while reviewing changes to each file and by smartly prioritizing context that is packed in each request. - -**Inputting and outputting structured content:** LLMs are particularly bad at understanding and generating structured content and mathematical computation. We had to design new input formats, that are closer to how humans understand changes, instead of using the standard unified diff format. We also had to provide few-shot examples to the LLMs to get the desired results. - -**Noise:** LLMs are terrible at differentiating between noise and signal. For instance, if you ask LLMs for 20 suggestions, you will get them, but only a few of them will be useful. This is particularly true for code reviews. We had to design a multi-stage review process that reinforces the signal and filters out the noise. - -**Costs:** While advanced models like `gpt-4` are great in performing complex tasks, they are several orders of magnitude more expensive than models like `gpt-3.5-turbo`. We had to design a multi-model approach that uses simpler models for summarizations, while complex models are used for tasks such as reviewing code. In addition, simpler models act as a triage filter that identifies the changes that need to be thoroughly reviewed by more complex models. - -**Inaccuracies:** LLMs are not perfect and often return inaccurate results, and they sometimes even ignore instructions and completely fabricate a response. Rather than keep fighting the LLMs we wrote layers of sanity checks to fix or hide the inaccuracies from the user. - -**Data privacy:** The biggest concern from our users is whether their code is being stored and used to train the models. We made sure that all queries to LLMs are ephemeral, and the data is discarded right away from our service. At the same time, it's challenging to provide stateful incremental reviews without storing the data. We had to design a system that stores all state within the pull request itself and not in our service for maximum privacy. - - - -## Conclusion - -Building on top of LLMs is a new space, and we can draw parallels to how early software such as MS-DOS were built on top of IBM PC and Intel microprocessors. Even with limited memory, [killer applications](https://www.pcmag.com/news/the-ibm-pcs-killer-apps-where-are-they-now) were built. The context size limits of LLMs are similar to the memory limits of early PCs. Innovation is required to build sophisticated applications on top of LLMs that give the impression of a much larger context, just like early [3D games](<https://en.wikipedia.org/wiki/Doom_(1993_video_game)>) used innovative techniques to run even on modest PCs. It's quite likely that immense value will be captured by the applications while underlying LLMs and AI infrastructure such as vector databases will continue to get commoditized. In addition, the line between the actual model training and the prompting continues to be blurred. Prompts with few-shot examples and fine-tuning can make a big difference in the quality of results and is an area that will differentiate products that build on top of LLMs. - -At CodeRabbit, we are at the forefront of this innovation by building an AI-first developer tools company from the ground up. We are approaching this problem from first principles, as the techniques being used bear little resemblance to the existing tools like linters and static code analysis tools. We are witnessing an inflection point as AI has crossed the practicality threshold, despite its limitations. Furthermore, we believe that we can keep innovating around the limitations and bring sophisticated products that push the boundaries of what is possible with AI. We are excited about our roadmap and hope to unlock immense value for our customers in the near future. - -<!-- <ShareButton platform="twitter" text="Twitter" url='CodeRabbit: Bringing AI to Code Reviews&hashtags=CodeRabbitAI'/> - -<ShareButton platform="facebook" url="CodeRabbit: Bringing AI to Code Reviews" text="LinkedIn" /> --> diff --git a/blog/2023-10-05-ai-code-reviews-reclaims/2023-10-05-ai-code-reviews-reclaims.md b/blog/2023-10-05-ai-code-reviews-reclaims/2023-10-05-ai-code-reviews-reclaims.md deleted file mode 100644 index 75a178b..0000000 --- a/blog/2023-10-05-ai-code-reviews-reclaims/2023-10-05-ai-code-reviews-reclaims.md +++ /dev/null @@ -1,152 +0,0 @@ ---- -slug: ai-code-reviews-reclaims -title: How AI Code Review Reclaims Your Team's Time -description: How AI Code Review Reclaims Your Team's Time -authors: [simone] -tags: ["Rate limits", "Openai", "Prioritization"] -image: https://coderabbit.uw.r.appspot.com/blog/assets/images/BlogImage2-5d9344142d7354ac5b8c9928e8ee6208.png ---- - -<head> - <meta charSet="utf-8" /> - <link rel="apple-touch-icon" sizes="180x180" href="/icons/apple-touch-icon.png" /> - <link rel="icon" type="image/png" sizes="32x32" href="/icons/favicon-32x32.png" /> - <link rel="icon" type="image/png" sizes="16x16" href="/icons/favicon-16x16.png"/> - <meta content="/icons/apple-touch-icon.png" itemprop="image" /> - <link rel="icon" href="/icons/favicon-32x32.ico"></link> - - <link rel="manifest" href="/icons/site.webmanifest"></link> - - <title>How AI Code Review Reclaims Your Team's Time</title> - <meta name="title" content="CodeRabbit: Bringing AI to Code Reviews" /> - - <meta property="og:type" content="article" /> - <meta property="og:url" content="https://coderabbit.ai/blog/ai-code-reviews-reclaims" /> - <meta property="og:title" content="How AI Code Review Reclaims Your Team's Time" /> -<meta property="og:image" content="img/blogs/BlogImage2.png" /> - - <meta name="twitter:image" content="https://coderabbit.uw.r.appspot.com/blog/assets/images/BlogImage2-5d9344142d7354ac5b8c9928e8ee6208.png" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="How AI Code Review Reclaims Your Team's Time" /> -</head> - -<!-- import ShareButton from '../src/components/ShareButton/ShareButton'; --> - -### Introduction - -In the era of building and improving products fast, engineering managers encounter fresh challenges that render traditional strategies outdated. The amount of time spent trying to make sure that teams not only build products fast, but also without breaking too much stuff or introducing security vulnerabilities is significant. - -One of the most time-intensive tasks involves conducting code reviews – these crucial checkpoints serve as guardians shielding your codebase from potential chaos. Additionally, code reviews are an essential part of [compliance](https://mitratech.com/en_gb/governance-risk-compliance/what-is-enterprise-compliance/); which is often a requirement when working in an enterprise. Despite their significance, they can also turn into obstacles, occasionally stalling the deployment process. The question at hand is: How can we navigate through this impediment while upholding top-notch code quality? - -Introducing AI-powered code reviews! Picture your team's pull requests getting reviewed as soon as they're made. That's the magic of AI code review tools. For teams, this means you don't have to wait for hours to get feedback. Reviewers can still offer more feedback later. It also means your teams can stay on track, creating and releasing features without the usual delays of waiting for code reviews. - -We'll discuss the regular stages of software projects and the impact of AI code reviewers like [CodeRabbit](https://coderabbit.ai) in this digital era. You'll gain a detailed insight into how these tools are changing the game, making code reviews faster, smarter, and surprisingly, more human-like. - -<!--truncate--> - -### The Typical Software Lifecycle Process - - - -Ah, the software lifecycle—the process where we turn ideas into lines of code that build our products. If you're an engineering manager, you're already well-versed in the dogma: planning, coding, testing, deploying, and maintaining. It's a continuous cycle with its own set of challenges. - -So, where do code reviews fit into this? They help us make sure that we know what we are shipping to our users by having different people cross-check each others’ work.You can't skip them; they serve as a critical validation point, ensuring that the code you're churning out works and is optimized and secure. Code reviews are the gatekeepers that scrutinize your code before it gets the VIP pass to merge into the main branch. - -But let's be real. Traditionally, this process has been manual, slow (with delays between opening pull requests and having them reviewed), subjective, and, yes, prone to human error. But if there's anything the advent of AI code review tools shows us, there is an opportunity to reclaim some of the time we spend doing code reviews.. - -In the upcoming sections, we'll dive deeper into how the traditional and often cumbersome process of code reviews is changing with AI. - -### The Traditional Code Review Method - - - -In the conventional approach, code reviews followed this pattern: one developer wrote the code and then passed it on to another person for evaluation. The reviewer took their time to meticulously inspect the code submitted by the developer. This involved examining lines of code and making notes, comments, questions, and identifying any problems. This process typically unfolded as follows: - -- A developer creates a Pull Request (PR) and outlines the changes made, requesting a review. -- The reviewer, who might be another developer or an engineering manager, assesses the code, looking for specific aspects such as: - - Ensuring that the PR changes align with the scope of the associated ticket(s). - - Confirming the accuracy of business logic implementation. - - Maintaining or improving code quality by reverting unnecessary changes and upholding code quality standards. - - Verifying that the changes do not introduce security vulnerabilities. -- The reviewer either approves or rejects the PR. -- If approved, the PR can be merged. -- If rejected, the reviewer provides feedback on the required updates for approval. - -This process has been a fundamental part of modern coding. It relies on the availability of both the reviewer to provide feedback and the developer to make changes based on that feedback. - -However, manual code reviews can be likened to a risky game with your code's quality, somewhat resembling playing Russian Roulette. Even with a highly skilled team, personal opinions and fatigue can occasionally lead to overlooked mistakes. Additionally, the pressure of other tasks can make code reviews seem necessary but frustrating. - -Yet, can we truly afford to skip or rush this step? No, not without inviting bugs and bottlenecks down the road. Thankfully, technological advancements, such as AI code review tools, show us a better, more efficient way to review code without having to rely solely on the availability of a human reviewer. - -### Challenges of Code Reviews in Teams - -Consider this scenario: You've created exceptional code, much like a perfectly blended smoothie, ready to delight users. However, before you can serve it, you'd like a team member to evaluate it. This step is crucial because, even when you put forth your best effort, some issues might go unnoticed. These issues can later evolve into significant problems, such as critical bugs, system crashes, or vulnerabilities. Now, imagine that this team member resides in a different time zone, perhaps asleep or preoccupied with other tasks. It's akin to attempting to share your smoothie at a party where everyone struggles to find the right moment for a sip. - -So, what's the solution? You could attempt to enforce a strict schedule for everyone or request team members to work during unconventional hours. However, this approach can lead to exhaustion and unhappiness. Instead, why not harness technology to address this challenge? This is where AI-powered code review tools come into play. They operate continuously, regardless of time zones, sleep patterns, or changing moods. They're consistently available to assess your code's quality without obstructing your project's progress. - -The following sections will delve into how these AI platforms streamline code reviews, making them more manageable and remarkably efficient. Spoiler alert: Your perception of code quality and team productivity is about to undergo a transformation. - -### Why Manual Reviews Slow You Down: A Look at Productivity Metrics - -In code reviews, problems can happen even when everyone works in the same place. Sometimes, teams just agree without really checking. People might not get along, causing delays and making things tense. Plus, even if we try really hard, some issues can slip by us and turn into big, expensive problems like bugs or system crashes. So, we need better ways to catch these problems early. - -Let's look at some numbers because engineering managers really like facts and figures. Studies tell us that developers spend around 20-30% of their time [doing code reviews](https://about.gitlab.com/blog/2023/09/03/the-code-review-struggle-is-real-heres-what-you-need-to-know/). There's even a study [here](https://smartbear.com/learn/code-review/best-practices-for-peer-code-review/#:~:text=Review%20fewer%20than%20400%20lines%20of%20code%20at%20a%20time,-A%20SmartBear%20study&text=The%20brain%20can%20only%20effectively,70%2D90%25%20defect%20discovery) that shows our brains struggle to review more than about 400 lines of code at once, making it harder to spot mistakes. - -We all know time is super important. It doesn't just impact how much money the project makes, but it also affects how much your team gets paid and, in the big picture, how well the company does overall. When a big chunk of your developers' time is used up reviewing code, it's not just a tech thing anymore – it's a big deal for the whole business. - -Think about it this way: these hours aren't spent on making cool new stuff, fixing problems, or coming up with fresh ideas. Instead, they're used up carefully looking at code that's already there, trying to find mistakes, things that could work better, and stuff that doesn't fit. This is often where things slow down and work takes longer. While making sure the code is great is important, doing it manually uses up resources that could be used better elsewhere. - -This isn't just about shipping faster—although who doesn't want to do that? It's also about optimizing your team's time so they can focus on what they do best: creating amazing software. If an AI code review tool can handle the initial pass, highlighting potential issues with the code, the developer can resolve initial feedback faster and your human experts can spend their time solving more complex, higher-level problems. - -In the next section, we'll understand how AI-powered code reviewers offer a more efficient, context-aware, and timely alternative to the traditional approach. Because let's face it, it's high time our methods evolved to match the pace of modern development cycles of rapid development and iteration. - -### AI-Powered Code Reviews: This Changes Everything - - -AI, or Artificial Intelligence, might sound like a trendy word, but in the world of reviewing computer code, it's not just a passing trend – it's a real game-changer. When we talk about AI in code review tools, we're not just talking about existing linters or static code analysis tools. Instead, we're referring to smart feedback that understands the context of your team's coding rules and the particular project you're working on. - -But there's more to it. These AI-powered systems can chat with you, making the review process feel like a collaboration rather than a machine. This means you can ask questions, seek clarifications, and even discuss the best approaches, all in real time. It's like having your most experienced developer, who knows your code inside and out, ready for reviews 24/7. - -Let's clarify a common misunderstanding: AI-based code reviewers are not the same as code generators. Code generators like [GitHub Copilot](https://github.com/features/copilot) assist you in writing code, while AI code reviewers are meant to assess and improve it. They are two related tools, each with its own unique features and advantages. - -In summary, AI-powered code reviews provide faster and reliable feedback without sacrificing quality or depth. This enhances your team's productivity and allows you to push the boundaries of what's possible in your development process. You can learn more by checking this out: [AI and the Future of Code Reviews: A Deep Dive into CodeRabbit.](https://coderabbit.ai/blog/coderabbit-deep-dive) - -In the final part, we'll wrap up by explaining why using AI for code reviews could be a smart strategy you may not have realized you needed. Get ready to embrace the future, everyone. It's becoming highly efficient. Also, AI code reviews can assist you in meeting compliance requirements in corporate environments. - -### Conclusion: The Future is Now - -Why is now the best time? Well, in simpler terms, before GPT, the automated tools we had were limited to linting or static code analysis. - -As we come to the end of this digital journey, we've seen how software is made, the challenges of checking code manually, and the exciting potential of using AI for code reviews. Now, if you're a smart engineering manager looking to keep your team fast, efficient, and creative, what should you keep in mind? - -First, it's pretty clear that code reviews are changing fast. We're no longer stuck with just people's schedules and opinions. With AI helping out, we're heading towards a future where code reviews are faster, smarter, more detailed, and surprisingly, more like how humans do it. - -Second, don't underestimate how this change affects your whole process of making software. Quicker reviews mean you can make changes and improvements faster, making your team more flexible and ready to jump on opportunities. - -Lastly, remember that technology isn't just about using new tools; it's about using them right to make things better. AI-powered code reviews are super quick, super accurate, and super thorough, making them a great choice for any team. Additionally, AI review tools often see problems that people might miss or not notice. - -So, does AI fix all your code review problems? Well, not every single one, but it's a really good start. The future is here, and it's knocking at your door. Time to let it in. And with that, we're done with this journey. May your code stay clean, your reviews be speedy, and your software launches be smooth. Here's to building a smarter and more efficient future! - -### Next Steps: How to save time and improve code quality with AI-Powered Code Reviews - -You've come quite a way, and you're probably feeling excited—or at least intrigued enough to take some action. So, what's the plan? Here's a simple checklist to help you start your journey with AI-powered code reviews: - -1. **Research Options**: Not all AI platforms are the same. Explore their features, limits, and costs. Of course, [CodeRabbit](https://coderabbit.ai) is a strong option, but go with what suits you. - -2. **Talk to Your Team**: Get input from your developers and reviewers. Knowing their challenges can guide you in picking the right tool. - -3. **Start small**: Begin with a limited scope or team. This helps you understand the impact of AI on your process. - -4. **Review results**: After the initial phase, check the results. Look at factors such as efficiency and quality to gauge its effectiveness. - -5. **Expand Gradually**: Happy with the results? Excellent! Now, introduce AI-powered code reviews to the whole team and make it a regular practice. - -6. **Stay Updated**: AI keeps evolving, and so should your approach. Keep up with new features and capabilities to keep improving your review process. - -This isn't just a temporary trend; it's a significant shift in how we view code quality and team efficiency. So take that leap and discover how AI can take your performance to the next level. - -With that, we conclude today's topic. If you have questions or thoughts, feel free to share them in the comments section. Let's continue the discussion there. Cheers! - -<!-- <ShareButton platform="twitter" text="Twitter" url='CodeRabbit: Bringing AI to Code Reviews&hashtags=CodeRabbitAI'/> --> - -<!-- <ShareButton platform="facebook" url="CodeRabbit: Bringing AI to Code Reviews" text="LinkedIn" /> --> diff --git a/blog/2023-11-13-boosting-engineering-efficiency.md b/blog/2023-11-13-boosting-engineering-efficiency.md deleted file mode 100644 index 9924634..0000000 --- a/blog/2023-11-13-boosting-engineering-efficiency.md +++ /dev/null @@ -1,112 +0,0 @@ ---- -slug: boosting-engineering-efficiency -title: Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams -description: In a world where the office is just a step away from your bed, we dive into the challenges and triumphs of maintaining code quality across continents. -authors: [dotlabs] -image: https://coderabbit.uw.r.appspot.com/blog/assets/images/blog4-568a2e78ef284966039a9ca8d2c48d21.jpeg -tags: ["Rate limits", "Openai", "Prioritization"] -hide_table_of_contents: false -aiDisclaimer: true ---- - -<head> - <meta charSet="utf-8" /> - <link rel="apple-touch-icon" sizes="180x180" href="/icons/apple-touch-icon.png" /> - <link rel="icon" type="image/png" sizes="32x32" href="/icons/favicon-32x32.png" /> - <link rel="icon" type="image/png" sizes="16x16" href="/icons/favicon-16x16.png"/> - <meta content="/icons/apple-touch-icon.png" itemprop="image" /> - <link rel="icon" href="/icons/favicon-32x32.ico"></link> - - <link rel="manifest" href="/icons/site.webmanifest"></link> - - <title>Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams</title> - <meta name="title" content="Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams" /> - - <meta property="og:type" content="article" /> - <meta property="og:url" content="https://blog.coderabbit.ai/blog/boosting-engineering-efficiency" /> - <meta property="og:title" content="Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams" /> - <meta property="og:image" content='https://docs.coderabbit.ai/img/blogs/blog4.jpeg' /> - - <meta name="twitter:image" content='https://docs.coderabbit.ai/img/blogs/blog4.jpeg' /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams" /> -</head> - -<!-- import ShareButton from '../src/components/ShareButton/ShareButton'; --> - -## Introduction - -Welcome to the future, where morning commute involves going from bed to home office. The dress code is "business on top, pajamas down below." In this new world of remote work, tech teams worldwide are getting good at video calls and wishing for strong Wi-Fi like strong coffee. But here's the question: How do we maintain engineering efficiency when Joe from frontend is in Mexico, and DevOps Dave just started his day in Dublin? -This setup presents a unique challenge: ensuring that code reviews, which are essential for code quality, are consistent, timely, and efficient. Have you ever missed a code review because it was late at night? We've all been there. Are you waiting for days to get feedback because your reviewer is in a different time zone? Oh, the frustration! -Introducing the helpful algorithm: AI-driven code reviews. They're like a reliable friend who never sleeps (because they're code) and knows all the coding rules. This article explores how these intelligent bots fill the gaps in our fast-paced, sometimes slow, new world. - -```mdx-code-block -import Tabs from '@theme/Tabs'; -import TabItem from '@theme/TabItem'; -``` - -<!--truncate--> - -## Direct Correlation: Remote Engineering Challenges & AI Solutions - -Remember the good old days when you could easily ask a quick question to a colleague by just going to their desk? Those days are gone, just like floppy disks and dial-up internet. Nowadays, with remote work, we have traded cubicles for couches and water cooler chats for solo trips to the fridge. Let's address the three significant challenges of remote engineering and explore how AI's modern technology can provide a solution. - -**Communication Gaps:** We've all sent that "quick query" across the ocean and received a response when the moon's high in our sky. Time zones, while fantastic for the travel and holiday industry, can be the bane of a remote engineer's existence. The lag between question and answer and the lack of in-person interaction can make collaborating feel like you're screaming into a digital void. - -- **AI Solution:** AI doesn't need sleep (lucky them). They're the 24/7 store of the coding world, always open and ready to assist. Offering real-time feedback, irrespective of whether it's midday in Mumbai or twilight in Toronto, AI ensures that time zones remain a challenge only for your travel plans. - -**Delayed Reviews & Feedback Loops:** Here's a familiar scenario: You push code, sit back, and wait. And wait. And wait some more. Your code is in the ether, waiting for a review that's as elusive as a unicorn. The elongated feedback loops in remote settings can sometimes feel like a seemingly endless game of ping pong, where the ball... disappears. - -- **AI Solution:** Fancy a game-changer? AI provides immediate feedback. With algorithms working at the speed of computers, the waiting game is dramatically reduced. You push, AI reviews, and voila! Feedback's ready, hotter than a freshly brewed espresso. - -**Code Consistency & Quality:** Have you ever noticed how everyone's homemade bread looks and tastes slightly different? The same goes for code written by engineers scattered across various locales. Influenced by unique experiences and environments, each individual brings slight variances in coding style and approach. - -- **AI Solution:** Call AI the master baker, consistently churning out the perfect loaf every time. AI-driven code review tools maintain a unified standard, ensuring that whether it's Peter in Paris or Lila in Lagos, the quality and consistency of code remain top-notch. - -## Real-World Applications & Pitfalls - -In a world where data is king, we enjoy hearing success stories (especially when they include pie charts!). However, there are challenges to overcome when it comes to incorporating AI code reviews in a remote environment. Let's explore the real-life stories of AI experts and the significant obstacles they have overcome. - -### Common Pitfalls & Solutions - -**Over-reliance on AI:** Just as one wouldn't ask a Roomba to do a deep spring cleaning, leaning too much on AI for code reviews can miss out on the nuanced human touch. Solution: Tech Titans Inc. struck a balance by using AI for preliminary checks and human eyes for final reviews, ensuring that the code was technically sound and made logical sense in the grander scheme. - -**Resistance to Change:** Implementing new tools often meets resistance, especially if developers feel their expertise is being questioned. Startup Sensations Ltd. faced a mini rebellion of sorts. Solution: They organized workshops emphasizing AI as a tool to aid, not replace. Showcasing its strengths and limitations bridged the trust gap, smoothing the integration. - -**Misunderstanding AI Feedback:** Sometimes, AI can flag something as an error, even if it's a deliberate choice by the coder. This can lead to confusion and wasted effort trying to "fix" what isn't broken. Solution: Both companies implemented clear guidelines on understanding and acting upon AI feedback, ensuring developers knew when to consider and contest. - -## Actionable Takeaways - -Navigating the intricate maze of code reviewing can be daunting. But fret not! There are some practical steps and considerations to help steer the ship. And speaking of guiding lights, let's first mention a noteworthy tool that's caught the industry's attention. - -### CodeRabbit – An AI Code Reviewer - -Heard of CodeRabbit? It's this nifty AI tool that's gaining traction. Without all the bells and whistles – it simply reviews your code once pull requests are made. It's a straightforward, no-fuss tool designed to streamline the review process, especially for remote teams. - -### Steps for Effective Integration and Adoption - -1. **Orientation:** It's crucial to acquaint your team with any new tool. With something like CodeRabbit, a simple hands-on session or tutorial might suffice. -2. **Pilot Testing:** Test the waters first. Let's start with one project or a subset of your team to gauge the tool's efficiency and user-friendliness. -3. **Constructive Feedback:** Encourage an open line of communication. Ensure your team provides feedback about the tool's strengths and areas needing tweaks. - -### Balancing AI Assistance with Human Touch - -No matter how advanced our tools get, there's an underlying essence of human insight that can't be entirely replicated. To ensure the balance: - -1. **Sequential Reviews:** Let AI, like CodeRabbit, serve as the preliminary filter. The team should do subsequent, deeper reviews to capture nuances. -2. **Regular Updates:** Keep the AI tool informed. Feedback from human reviewers refines its algorithm, making it more intuitive with time. -3. **Encourage Team Discussions:** After automated reviews, foster team discussions. This ensures the code isn't just machine-compliant but also logically sound and efficient from a human perspective. - -## Conclusion - -Ah, the outcome! We've ventured deep into the rabbit hole (no pun intended with CodeRabbit) of AI's transformative role in remote engineering. From the highs of streamlined code reviews to the essential human-AI harmony, it's evident that AI doesn't just knock on the doors of modern engineering—it's barging in, holding a battering ram of innovation. - -Remember when remote work was a cute little option, often tucked away in the "benefits" section of a job posting? Well, it's not just mainstream now; it's the modus operandi for countless teams globally. As this mode of work continues to snowball, the technological advancements, especially ones like AI-driven code reviewers, aren't merely luxury add-ons. They are becoming vital cogs in the well-oiled machine that a remote engineering team aspires to be. - -As we stand on the brink of yet more seismic shifts in the way we work and collaborate, it's exhilarating to think of the untapped potential of tools and technologies still on the horizon. The canvas of remote work is vast, and we've only just started splashing it with color. Here's to a brighter, more innovative, and yes, more automated future, but always with a sprinkle of irreplaceable human magic. - -**_Cheers to the codes that bind us, both human and binary._** - -<!-- <ShareButton platform="twitter" text="Twitter" url='Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization&hashtags=CodeRabbitAI'/> - -<ShareButton platform="facebook" url="Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization" text="LinkedIn" /> --> diff --git a/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/index.md b/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/index.md deleted file mode 100644 index 4247d4d..0000000 --- a/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/index.md +++ /dev/null @@ -1,88 +0,0 @@ ---- -slug: how-we-built-cost-effective-generative-ai-application -title: How we built a cost-effective Generative AI application -description: Building a Generative AI application is expensive. Here's how we make it cost effective and improve user experience. -authors: [gur] -tags: ["Rate limits", "Openai", "Prioritization"] -hide_table_of_contents: false -aiDisclaimer: true ---- - -# How we built a cost-effective Generative AI application - -Since its inception, CodeRabbit has experienced steady growth in its user base, comprising developers and organizations. Installed on thousands of repositories, CodeRabbit reviews several thousand pull requests (PRs) daily. We have [previously discussed](/blog/coderabbit-openai-rate-limits) our use of an innovative client-side request prioritization technique to navigate OpenAI rate limits. In this blog post, we will explore how we manage to deliver continuous, in-depth code analysis cost-effectively, while also providing a robust, free plan to open source projects. - -<!--truncate--> - -## CodeRabbit's Product Offering and LLM Consumption - -CodeRabbit is an AI-first PR Review tool that uses GPT APIs for various functionalities. CodeRabbit offers the following tiers of service: - -- CodeRabbit Pro: A paid service providing in-depth code reviews for private repositories. It's priced according to the number of developers, starting with a full-featured 7-day free trial. -- CodeRabbit for Open Source: A free service offering in-depth code reviews for open source (public) repositories. -- CodeRabbit Free: A free plan for private repositories, providing summarization of code changes in a PR. - -Our vision is to offer an affordable, AI-driven code review service to developers and organizations of all sizes while supporting the open source community. We are particularly mindful of open source projects, understanding the challenges in reviewing community contributions. Our goal is to reduce the burden of code reviews for open source maintainers by improving submission quality before the review process begins. - -CodeRabbit's review process is automatically triggered when a PR is opened in GitHub or GitLab. Each review involves a complex workflow that builds context and reviews each file using large language models (LLMs). Code review is a complex task that requires an in-depth understanding of the changes and the existing codebase. High-quality review comments necessitate state-of-the-art language models such as gpt-4. However, these models are significantly more expensive than simpler models, as shown by the [10x-30x price difference](https://openai.com/pricing) between gpt-3.5-turbo and gpt-4 models. - -| Model | Context Size | Cost per 1k Input Tokens | Cost per 1k Output Tokens | -| ------------- | ------------ | ------------------------ | ------------------------- | -| GPT-4 | Up to 32k | $0.06 | $0.12 | -| GPT-4 | Up to 8k | $0.03 | $0.06 | -| GPT-3.5 Turbo | Up to 16k | $0.003 | $0.004 | -| GPT-3.5 Turbo | Up to 4k | $0.0015 | $0.002 | - -> gpt-4 model is 10-30x more expensive than gpt-3.5-turbo model - -Our primary cost driver is using OpenAI's API to generate code review comments. We will share our cost optimization strategies in the following sections. Without these optimizations, our free offering to open source projects would not be feasible. - -Let's take a look at the strategies that helped us optimize the cost and improve user experience. - ---- - -## 1. Dual-models: Summarize & Triage Using Simpler Models - -For less complex tasks such as summarizing code diffs, simpler models such as gpt-3.5-turbo are adequate. As an initial optimization, we use a mix of models, as detailed in [our earlier blog post](/blog/coderabbit-deep-dive). We use gpt-3.5-turbo to compress large code diffs into concise summaries, which are then processed by gpt-4 for reviewing each file. This dual-model approach significantly reduces costs and enhances review quality, enabling us to manage PRs with numerous files and extensive code differences. - -Additionally, we implemented triage logic to skip trivial changes from the review process. We use the simpler model to classify each diff as either trivial or complex, as part of the same prompt used for code diff summarization. Low-risk changes such as documentation updates, variable renames, and so on, are thus excluded from the thorough review process. This strategy has proven effective, as simpler models can accurately identify trivial changes. - -By using this dual-model approach for summarization and filtering out trivial changes, we save almost 50% on costs. - - -## 2. Rate-limiting: Enforcing Fair Usage - -Upon launching our free service for open source projects, we noticed individual developers using it as a coding co-pilot by making hundreds of incremental commits for continuous feedback. CodeRabbit, designed for thorough code reviews unlike tools such as GitHub Copilot, incurs high costs when used in this manner. Therefore, we implemented hourly rate-limits on the number of files and commits reviewed per user, to control excessive usage without compromising user experience. These limits vary across different product tiers. For example, we set more aggressive limits for open source users compared to trial and paid users. - -To implement these rate-limits, we evaluated various options for Serverless environments. We opted for [FluxNinja Aperture](https://fluxninja.com/) for its simplicity and policy sophistication. We were already using Aperture for managing [OpenAI rate limits](coderabbit-openai-rate-limits), making it a natural choice for our rate-limiting needs as well. - -In FluxNinja Aperture, policies are decoupled from application logic through labels, enabling new policy additions without altering application code. We apply labels in FluxNinja Aperture, wrap the review workload with its SDK, and write policies that enforce limits on those labels. For example, we enforce a 3 reviews per hour limit (1 review every 20 minutes) for open source users, allowing a burst of 2 back-to-back reviews, as shown in the screenshots below. - -Integration with FluxNinja Aperture SDK - - -Rate limiting commits per hour for open source users - - -Wait time feedback to the user in a comment - -Given the high cost and capacity constraints of state-of-the-art models such as gpt-4, rate-limiting is an essential requirement for any AI application. By implementing fair-usage rate limits, we are saving almost 20% on our costs. - - -Rate limit metrics for open source users - -## 3. Caching: Avoid Re-generating Similar Review Comments - -We believe that building user habits around AI involves seamlessly augmenting existing workflows. Therefore, AI code reviews must be continuous: they should trigger as soon as a PR is opened and incrementally update the summary and generate review comments as more commits are added. - -However, this approach can become expensive and generate repetitive feedback, as similar review comments are re-generated for each commit. We observed that most incremental commits involve minor adjustments or bug fixes in the initial implementation. To address this, we implemented a caching layer to avoid re-generating similar review comments for incremental commits. - -Fortunately, Aperture also provides a simple caching mechanism for summaries from previous commits, using the same API call where we implemented rate limits. During each incremental review, we use the simpler model for a semantic comparison of the code changes described in both summaries. If the changes are similar, we skip the review for those files to prevent re-generating similar review comments. This method differs from vector similarity-based caching techniques, as we use an LLM model for comparing summaries. Vector similarity-based approaches wouldn't be effective in our case, as the summaries require semantic comparison. We have integrated this method into the same prompt used for code diff summarization and triage. - -By using the more cost-effective gpt-3.5-turbo model as an advanced similarity filter before invoking the more expensive gpt-4 model for the same file, we have saved almost 20% of our costs by avoiding the generation of similar review comments. - ---- - -## Conclusion - -In this blog post, we briefly discussed how state-of-the-art LLMs such as gpt-4 can be expensive in production. We also shared our strategy of using a combination of simpler models, rate limits, and caching to optimize operational costs. We hope our experiences can assist other AI startups in optimizing their costs and developing cost-effective AI applications. diff --git a/blog/2024-01-05-modern-ai-stack-for-developer-productivity/index.md b/blog/2024-01-05-modern-ai-stack-for-developer-productivity/index.md deleted file mode 100644 index 8b1dce4..0000000 --- a/blog/2024-01-05-modern-ai-stack-for-developer-productivity/index.md +++ /dev/null @@ -1,85 +0,0 @@ ---- -slug: modern-ai-stack-for-developer-productivity -title: Modern AI stack for developer productivity -description: Elevate your development workflow with three pillars of developer productivity tools powered by Artificial Intelligence -image: banner.jpg -authors: [pradeep] -tags: - [ - "developer productivity", - "developer tools", - "ai tools", - "ai developer tools", - "technology trend", - ] -hide_table_of_contents: false -aiDisclaimer: true ---- - -The 'modern AI stack for developer productivity' refers to a comprehensive set of AI-powered developer tools that improve developer productivity in building software. In 2023, Large Language Models (LLMs) caused significant disruption, leading to a rapid increase in the adoption of artificial intelligence within the development lifecycle, particularly in the realm of 'developer productivity tools'. A significant majority of software development projects are now leveraging some form of AI, specifically Generative AI to transform traditional development workflows into more intelligent, efficient, and automated processes. - -The modern AI stack for developer productivity is reshaping the landscape of software development, making tasks that were once time-consuming or complex more manageable and automated. From helping with the research or code writing to reviewing code and ensuring quality, the modern AI stack is a testament to how AI is not just an add-on but an integral component in the software development process. - -Are you leveraging the full potential of the modern AI tech stack in your projects? This article might help you to get that perspective needed to understand how it might elevate your work to the next level. - -<!--truncate--> - -## Three Pillars of the **Modern AI Stack for Developer Productivity** - -There are three key components in the modern AI stack for developer productivity that are useful in different stages of the development lifecycle. These three stages are the research or knowledge gathering stage, the coding stage, and the final code review stage. Let’s discuss each of these stages in detail and how AI tools can help improve developer productivity in each. - -### Knowledge - -The Knowledge pillar is central to the modern AI stack. It involves AI systems helping developers gather and synthesize knowledge, usually in the form of a chat or question-and-answer session. A prime example in this space is [ChatGPT](https://chat.openai.com/) - -- [ChatGPT](https://chat.openai.com/) is the leading AI assistant to quickly answer developers' questions on syntax, frameworks, debugging, etc. -- It acts like a supercharged search engine, saving developers time from having to dig through documentation or StackOverflow. -- ChatGPT can also explain concepts, provide code examples and suggestions, and identify knowledge gaps. Over time, these models will get better at technical reasoning with more training data. -- [StackOverflow Community Search](https://stackoverflow.co/labs/search/) is another product in this category which instantly summarizes the solution. - -This transformation is crucial in developing environments where quick access to information and rapid problem-solving are essential. - -#### Challenges - -One of the main challenges is ensuring the accuracy and reliability of the answers. AI systems might sometimes generate plausible but incorrect or biased responses. - -### Code Generation - -Code generation through AI marks a significant leap in software development. AI models, trained on vast code repositories, can now assist in generating code snippets and at times the entire modules. This speeds up the coding process. The evolution of this pillar is a testament to AI's growing understanding of programming languages and logic, offering a collaborative tool that augments the developer's capabilities rather than replacing them. - -- AI models like OpenAI’s GPT-4 Code Interpreter are leading this segment. -- They aid in writing code, offering suggestions, and even generating entire code blocks based on user input. -- They are particularly beneficial in increasing development speed and making coding more accessible to non-experts. -- [GitHub Copilot](https://github.com/features/copilot) introduces this experience in the IDE (such as VS Code) where you code. It enhances coding efficiency by rapidly suggesting code blocks and functions directly within the editor. This helps developers generate boilerplate code, complete repetitive tasks and implement common patterns much faster. - -#### Challenges - -The limitations include dependency on the training data, which may not always represent the most efficient or modern coding practices. Ethically, there are concerns about code originality and the potential for inadvertently generating vulnerable or buggy code. - -### Code Review - -AI’s role in code review is about ensuring quality, compliance, and optimization. Unlike traditional code reviews, which are time-consuming and prone to human oversight, AI-driven code reviews are swift and more thorough. AI models can scan code for patterns, anomalies, and compliance with coding standards, offering insights and suggestions for improvements. This pillar has evolved from basic syntax checking to sophisticated analysis, significantly enhancing the code quality. - -- Automated code review tools, like [CodeRabbit](https://coderabbit.ai/), help in identifying bugs, evaluating whether the PR achieves its objectives, and ensuring adherence to coding standards. The in-line comments make it easier to use and put things in motion. -- These tools can analyze code more thoroughly and quickly than human reviewers, leading to higher quality software. This frees up developer time as well as improves code quality before reaching production. -- Over time, CodeRabbit could fine-tune to a team's specific code review checklist and feedback provided in comments to provide even more accurate suggestions and extend this access to organization knowledge via code reviews naturally. - -#### Challenges - -If there is not enough information about the requirements in the issues, the PR assessment against the requirement might not provide the accurate picture as you would expect. - -## Prioritize knowledge and review over generation - -While most people would be attracted by the promises code generation offers, I believe it will not have as big an impact on developer productivity as the other two - Knowledge and Code Review. - -Code Generation tools may save some time in writing standard code, understanding and fine-tuning the output remains crucial. But the risk of overreliance on AI for code generation can lead to code inaccuracies and legal issues with AI-generated code. The real productivity gains come from improving organizational knowledge and code review process to ensure high standards of code quality. - -As [StackOverflow rightly mentioned](https://stackoverflow.blog/2023/12/29/the-hardest-part-of-building-software-is-not-coding-its-requirements/) - -> The hardest part of building software is not coding, it is requirements - -Software is more than just code; it's about meeting the users' need. The knowledge and code review pillar tightly align with this goal. Which is why I urge you to prioritize Knowledge and Code Review tools in your modern AI stack. - -## Conclusion - -The integration of these three pillars - Knowledge, Code Generation, and Code Review - forms a robust foundation in the AI-driven development process. Each pillar complements the others, creating a synergistic environment where developers are empowered with advanced tools and insights, leading to more efficient, innovative, and error-free software development. diff --git a/blog/2023-10-05-ai-code-reviews-reclaims/ai-powered.png b/blog/ai-code-reviews-reclaims-2023-10-05/ai-powered.png similarity index 100% rename from blog/2023-10-05-ai-code-reviews-reclaims/ai-powered.png rename to blog/ai-code-reviews-reclaims-2023-10-05/ai-powered.png diff --git a/blog/ai-code-reviews-reclaims-2023-10-05/blog.md b/blog/ai-code-reviews-reclaims-2023-10-05/blog.md new file mode 100644 index 0000000..158cf0c --- /dev/null +++ b/blog/ai-code-reviews-reclaims-2023-10-05/blog.md @@ -0,0 +1,269 @@ +--- +slug: ai-code-reviews-reclaims +title: How AI Code Review Reclaims Your Team's Time +description: How AI Code Review Reclaims Your Team's Time +authors: [simone] +tags: ["AI", "Code Review", "Productivity"] +image: ./preview.png +--- + +### Introduction + +In the era of building and improving products fast, engineering managers +encounter fresh challenges that render traditional strategies outdated. The +amount of time spent trying to make sure that teams not only build products +fast, but also without breaking too much stuff or introducing security +vulnerabilities, is significant. + +One of the most time-intensive tasks involves conducting code reviews – these +crucial checkpoints serve as guardians, shielding your codebase from potential +chaos. Additionally, code reviews are an essential part of +[compliance](https://mitratech.com/en_gb/governance-risk-compliance/what-is-enterprise-compliance/); +which is often a requirement when working in an enterprise. Despite their +significance, they can also turn into obstacles, occasionally stalling the +deployment process. The question at hand is: How can we navigate through this +impediment while upholding top-notch code quality? + +Introducing AI-powered code reviews! Picture your team's pull requests getting +reviewed as soon as they're made. That's the magic of AI code review tools. For +teams, this means you don't have to wait for hours to get feedback. Reviewers +can still offer more feedback later. It also means your teams can stay on track, +creating and releasing features, without the usual delays of waiting for code +reviews. + +We'll discuss the regular stages of software projects and the impact of AI code +reviewers like [CodeRabbit](https://coderabbit.ai) in this digital era. You'll +gain a detailed insight into how these tools are changing the game, making code +reviews faster, smarter, and surprisingly, more human-like. + +<!--truncate--> + +### The Typical Software Lifecycle Process + + + +Ah, the software lifecycle—the process where we turn ideas into lines of code +that build our products. If you're an engineering manager, you're already +well-versed in the dogma: planning, coding, testing, deploying, and maintaining. +It's a continuous cycle with its own set of challenges. + +So, where do code reviews fit into this? They help us make sure that we know +what we are shipping to our users by having different people cross-check each +other's work. You can't skip them; they serve as a critical validation point, +ensuring that the code you're churning out works and is optimized and secure. +Code reviews are the gatekeepers that scrutinize your code before it gets the +VIP pass to merge into the main branch. + +But let's be real. Traditionally, this process has been manual, slow (with +delays between opening pull requests and having them reviewed), subjective, and, +yes, prone to human error. But if there's anything the advent of AI code review +tools shows us, there is an opportunity to reclaim some of the time we spend +doing code reviews. + +In the upcoming sections, we'll dive deeper into how the traditional and often +cumbersome process of code reviews is changing with AI. + +### The Traditional Code Review Method + + + +In the conventional approach, code reviews followed this pattern: one developer +wrote the code and then passed it on to another person for evaluation. The +reviewer took their time to meticulously inspect the code submitted by the +developer. This involved examining lines of code and making notes, comments, +questions, and identifying any problems. This process typically unfolds as +follows: + +- A developer creates a Pull Request (PR) and outlines the changes made, + requesting a review. +- The reviewer, who might be another developer or an engineering manager, + assesses the code, looking for specific aspects such as: + - Ensuring that the PR changes align with the scope of the associated + ticket(s). + - Confirming the accuracy of business logic implementation. + - Maintaining or improving code quality by reverting unnecessary changes and + upholding code quality standards. + - Verifying that the changes do not introduce security vulnerabilities. +- The reviewer either approves or rejects the PR. +- If approved, the PR can be merged. +- If rejected, the reviewer provides feedback on the required updates for + approval. + +This process has been a fundamental part of modern coding. It relies on the +availability of both the reviewer to provide feedback and the developer to make +changes based on that feedback. + +However, manual code reviews can be likened to a risky game with your code's +quality, somewhat resembling playing Russian Roulette. Even with a highly +skilled team, opinions and fatigue can occasionally lead to overlooked mistakes. +Additionally, the pressure of other tasks can make code reviews seem necessary +but frustrating. + +Yet, can we truly afford to skip or rush this step? No, not without inviting +bugs and bottlenecks down the road. Thankfully, technological advancements, such +as AI code review tools, show us a better, more efficient way to review code +without having to rely solely on the availability of a human reviewer. + +### Challenges of Code Reviews in Teams + +Consider this scenario: You've created exceptional code, much like a perfectly +blended smoothie, ready to delight users. However, before you can serve it, +you'd like a team member to evaluate it. This step is crucial because, even when +you put forth your best effort, some issues might go unnoticed. These issues can +later evolve into significant problems, such as critical bugs, system crashes, +or vulnerabilities. Now, imagine that this team member resides in a different +time zone, perhaps asleep or preoccupied with other tasks. It's akin to +attempting to share your smoothie at a party, where everyone struggles to find +the right moment for a sip. + +So, what's the solution? You could attempt to enforce a strict schedule for +everyone or request team members to work during unconventional hours. However, +this approach can lead to exhaustion and unhappiness. Instead, why not harness +technology to address this challenge? This is where AI-powered code review tools +come into play. They operate continuously, regardless of time zones, sleep +patterns, or changing moods. They're consistently available to assess your +code's quality without obstructing your project's progress. + +The following sections will delve into how these AI platforms streamline code +reviews, making them more manageable and remarkably efficient. Spoiler alert: +Your perception of code quality and team productivity is about to undergo a +transformation. + +### Why Manual Reviews Slow You Down: A Look at Productivity Metrics + +In code reviews, problems can happen even when everyone works in the same place. +Sometimes, teams just agree without really checking. People might not get along, +causing delays and making things tense. Plus, even if we try really hard, some +issues can slip by us and turn into big, expensive problems like bugs or system +crashes. So, we need better ways to catch these problems early. + +Let's look at some numbers because engineering managers really like facts and +figures. Studies tell us that developers spend around 20-30% of their time +[doing code reviews](https://about.gitlab.com/blog/2023/09/03/the-code-review-struggle-is-real-heres-what-you-need-to-know/). +There's even a study +[here](https://smartbear.com/learn/code-review/best-practices-for-peer-code-review/) +that shows our brains struggle to review more than about 400 lines of code at +once, making it harder to spot mistakes. + +We all know time is super important. It doesn't just impact how much money the +project makes, but it also affects how much your team gets paid and, in the big +picture, how well the company does overall. When a big chunk of your developers' +time is used up reviewing code, it's not just a tech thing anymore – it's a big +deal for the whole business. + +Think about it this way: these hours aren't spent on making cool new stuff, +resolving problems, or coming up with fresh ideas. Instead, they're used up +carefully looking at code that's already there, trying to find mistakes, things +that could work better, and stuff that doesn't fit. This is often where things +slow down and work takes longer. While making sure the code is great is +important, doing it manually uses up resources that could be used better +elsewhere. + +This isn't just about shipping faster—although who doesn't want to do that? It's +also about optimizing your team's time so they can focus on what they do best: +create remarkable software. If an AI code review tool can handle the initial +pass, highlighting potential issues with the code, the developer can resolve +initial feedback faster and your human experts can spend their time solving more +complex, higher-level problems. + +In the next section, we'll understand how AI-powered code reviewers offer a more +efficient, context-aware, and timely alternative to the traditional approach. +Because let's face it, it's time our methods evolved to match the pace of modern +development cycles of rapid development and iteration. + +### AI-Powered Code Reviews: This Changes Everything + + AI, or Artificial Intelligence, might sound like a +trendy word, but in the world of reviewing computer code, it's not just a +passing trend – it's a real game-changer. When we talk about AI in code review +tools, we're not just talking about existing linters or static code analysis +tools. Instead, we're referring to smart feedback that understands the context +of your team's coding rules and the particular project you're working on. + +But there's more to it. These AI-powered systems can chat with you, making the +review process feel like a collaboration rather than a machine. This means you +can ask questions, seek clarifications, and even discuss the best approaches, +all in real time. It's like having your most experienced developer, who knows +your code inside and out, ready for reviews 24/7. + +Let's clarify a common misunderstanding: AI-based code reviewers are not the +same as code generators. Code generators like +[GitHub Copilot](https://github.com/features/copilot) assist you in writing +code, while AI code reviewers are meant to assess and improve it. They are two +related tools, each with its own unique features and advantages. + +In summary, AI-powered code reviews provide faster and reliable feedback without +sacrificing quality or depth. This enhances your team's productivity and allows +you to push the boundaries of what's possible in your development process. You +can learn more by checking this out: +[AI and the Future of Code Reviews: A Deep Dive into CodeRabbit.](../coderabbit-deep-dive-2023-08-26/blog.md) + +In the final part, we'll wrap up by explaining why using AI for code reviews +could be a smart strategy you may not have realized you needed. Get ready to +embrace the future, everyone. It's becoming highly efficient. Also, AI code +reviews can assist you in meeting compliance requirements in corporate +environments. + +### Conclusion: The Future is Now + +Why is now the best time? Well, in simpler terms, before GPT, the automated +tools we had were limited to linting or static code analysis. + +As we come to the end of this digital journey, we've seen how software is made, +the challenges of checking code manually, and the exciting potential of using AI +for code reviews. Now, if you're a smart engineering manager looking to keep +your team fast, efficient, and creative, what should you keep in mind? + +First, it's pretty clear that code reviews are changing fast. We're no longer +stuck with just people's schedules and opinions. With AI helping out, we're +heading towards a future where code reviews are faster, smarter, more detailed, +and surprisingly, more like how humans do it. + +Second, don't underestimate how this change affects your whole process of making +software. Quicker reviews mean you can speed up changes and improvements, making +your team more flexible and ready to jump on opportunities. + +Lastly, remember that technology isn't just about using new tools; it's about +using them right to improve things. AI-powered code reviews are super quick, +super accurate, and super thorough, making them a great choice for any team. +Additionally, AI review tools often see problems that people might miss or not +notice. + +So, does AI fix all your code review problems? Well, not each one, but it's an +excellent start. The future is here, and it's knocking at your door. Time to let +it in. And with that, we're done with this journey. May your code stay clean, +your reviews be speedy, and your software launches be smooth. Here's to building +a smarter and more efficient future! + +### Next Steps: How to save time and improve code quality with AI-Powered Code Reviews + +You've come quite a way, and you're probably feeling excited—or at least +intrigued enough to take some action. So, what's the plan? Here's a simple +checklist to help you start your journey with AI-powered code reviews: + +1. **Research Options**: Not all AI platforms are the same. Explore their + features, limits, and costs. Of course, [CodeRabbit](https://coderabbit.ai) + is a strong option, but go with what suits you. + +2. **Talk to Your Team**: Get input from your developers and reviewers. Knowing + their challenges can guide you in picking the right tool. + +3. **Start small**: Begin with a limited scope or team. This helps you + understand the impact of AI on your process. + +4. **Review results**: After the initial phase, check the results. Look at + factors such as efficiency and quality to gauge its effectiveness. + +5. **Expand Gradually**: Happy with the results? Excellent! Now, introduce + AI-powered code reviews to the whole team and make it a regular practice. + +6. **Stay Updated**: AI continues to evolve, and so should your approach. Keep + up with new features and capabilities to keep improving your review process. + +This isn't just a temporary trend; it's a significant shift in how we view code +quality and team efficiency. So take that leap and discover how AI can take your +performance to the next level. + +With that, we conclude today's topic. If you have questions or thoughts, feel +free to share them in the comments section. Let's continue the discussion there. +Cheers! diff --git a/blog/2023-10-05-ai-code-reviews-reclaims/engineer.png b/blog/ai-code-reviews-reclaims-2023-10-05/engineer.png similarity index 100% rename from blog/2023-10-05-ai-code-reviews-reclaims/engineer.png rename to blog/ai-code-reviews-reclaims-2023-10-05/engineer.png diff --git a/static/img/blogs/Blog2.png b/blog/ai-code-reviews-reclaims-2023-10-05/preview.png similarity index 100% rename from static/img/blogs/Blog2.png rename to blog/ai-code-reviews-reclaims-2023-10-05/preview.png diff --git a/blog/2023-10-05-ai-code-reviews-reclaims/software-lifecycle.png b/blog/ai-code-reviews-reclaims-2023-10-05/software-lifecycle.png similarity index 100% rename from blog/2023-10-05-ai-code-reviews-reclaims/software-lifecycle.png rename to blog/ai-code-reviews-reclaims-2023-10-05/software-lifecycle.png diff --git a/blog/boosting-engineering-efficiency-2023-11-13/blog.md b/blog/boosting-engineering-efficiency-2023-11-13/blog.md new file mode 100644 index 0000000..c310d46 --- /dev/null +++ b/blog/boosting-engineering-efficiency-2023-11-13/blog.md @@ -0,0 +1,165 @@ +--- +slug: boosting-engineering-efficiency +title: Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams +description: + In a world where the office is just a step away from your bed, we dive into + the challenges and triumphs of maintaining code quality across continents. +authors: [dotlabs] +image: ./preview.jpeg +tags: ["AI", "Code Reviews", "Remote Work"] +hide_table_of_contents: false +aiDisclaimer: true +--- + +## Introduction + +Welcome to the future, where a morning commute involves going from bed to home +office. The dress code is "business on top, pajamas down below." In this new +world of remote work, tech teams worldwide are getting good at video calls and +wishing for strong Wi-Fi like strong coffee. But here's the question: How do we +maintain engineering efficiency when Joe from frontend is in Mexico, and DevOps +Dave just started his day in Dublin? This setup presents a unique challenge: +ensuring that code reviews, which are essential for code quality, are +consistent, timely, and efficient. Have you ever missed a code review because it +was late at night? We've all been there. Are you waiting for days to get +feedback because your reviewer is in a different time zone? Oh, the frustration! +Introducing the helpful algorithm: AI-driven code reviews. They're like a +reliable friend who never sleeps (because they're code) and knows all the coding +rules. This article explores how these intelligent bots fill the gaps in our +fast-paced, sometimes slow, new world. + +<!--truncate--> + +## Direct Correlation: Remote Engineering Challenges & AI Solutions + +Remember the good old days when you could easily ask a quick question to a +colleague by just going to their desk? Those days are gone, just like floppy +disks and dial-up internet. Nowadays, with remote work, we have traded cubicles +for couches and water cooler chats for solo trips to the fridge. Let's address +the three significant challenges of remote engineering and explore how AI's +modern technology can provide a solution. + +**Communication Gaps:** We've all sent that "quick query" across the ocean and +received a response when the moon's high in our sky. Time zones, while fantastic +for the travel and holiday industry, can be the bane of a remote engineer's +existence. The lag between question and answer and the lack of in-person +interaction can make collaborating feel like you're screaming into a digital +void. + +- **AI Solution:** AI doesn't need sleep (lucky them). They're the 24/7 store of + the coding world, always open and ready to assist. Offering real-time + feedback, irrespective of whether it's midday in Mumbai or twilight in + Toronto, AI ensures that time zones remain a challenge only for your travel + plans. + +**Delayed Reviews & Feedback Loops:** Here's a familiar scenario: You push code, +sit back, and wait. And wait. And wait, some more. Your code is in the ether, +waiting for a review that's as elusive as a unicorn. The elongated feedback +loops in remote settings can sometimes feel like a seemingly endless game of +ping pong, where the ball... disappears. + +- **AI Solution:** Fancy a game-changer? AI provides immediate feedback. With + algorithms working at the speed of computers, the waiting game is dramatically + reduced. You push, AI reviews, and voilà! Feedback's ready, hotter than a + freshly brewed espresso. + +**Code Consistency & Quality:** Have you ever noticed how everyone's homemade +bread looks and tastes slightly different? The same goes for code written by +engineers scattered across various locales. Influenced by unique experiences and +environments, each individual brings slight variances in coding style and +approach. + +- **AI Solution:** Call AI the master baker, consistently churning out the + perfect loaf every time. AI-driven code review tools maintain a unified + standard, ensuring that whether it's Peter in Paris or Lila in Lagos, the + quality and consistency of code remain top-notch. + +## Real-World Applications & Pitfalls + +In a world where data is king, we enjoy hearing success stories (especially when +they include pie charts!). However, there are challenges to overcome when it +comes to incorporating AI code reviews in a remote environment. Let's explore +the real-life stories of AI experts and the significant obstacles they have +overcome. + +### Common Pitfalls & Solutions + +**Over-reliance on AI:** Just as one wouldn't ask a Roomba to do a deep +spring-cleaning, leaning too much on AI for code reviews can miss out on the +nuanced human touch. Solution: Tech Titans Inc. struck a balance by using AI for +preliminary checks and human eyes for final reviews, ensuring that the code was +technically sound and made logical sense in the grander scheme. + +**Resistance to Change:** Implementing new tools often meets resistance, +especially if developers feel their expertise is being questioned. Startup +Sensations Ltd. faced a mini rebellion of sorts. Solution: They organized +workshops emphasizing AI as a tool to aid, not replace. Showcasing its strengths +and limitations bridged the trust gap, smoothing the integration. + +**Misunderstanding AI Feedback:** Sometimes, AI can flag something as an error, +even if it's a deliberate choice by the coder. This can lead to confusion and +wasted effort trying to "fix" what isn't broken. Solution: Both companies +implemented clear guidelines on understanding and acting upon AI feedback, +ensuring developers knew when to consider and contest. + +## Actionable Takeaways + +Navigating the intricate maze of code reviewing can be daunting. But fret not! +There are some practical steps and considerations to help steer the ship. And +speaking of guiding lights, let's first mention a noteworthy tool that's caught +the industry's attention. + +### CodeRabbit – An AI Code Reviewer + +Heard of CodeRabbit? It's this nifty AI tool that's gaining traction. Without +all the bells and whistles – it simply reviews your code once pull requests are +made. It's a straightforward, no-fuss tool designed to streamline the review +process, especially for remote teams. + +### Steps for Effective Integration and Adoption + +1. **Orientation:** It's crucial to acquaint your team with any new tool. With + something like CodeRabbit, a simple hands-on session or tutorial might + suffice. +2. **Pilot Testing:** Test the waters first. Let's start with one project or a + subset of your team to gauge the tool's efficiency and user-friendliness. +3. **Constructive Feedback:** Encourage an open line of communication. Ensure + your team provides feedback about the tool's strengths and areas needing + tweaks. + +### Balancing AI Assistance with Human Touch + +No matter how advanced our tools get, there's an underlying essence of human +insight that can't be entirely replicated. To ensure the balance: + +1. **Sequential Reviews:** Let AI, like CodeRabbit, serve as the preliminary + filter. The team should do subsequent, deeper reviews to capture nuances. +2. **Regular Updates:** Keep the AI tool informed. Feedback from human reviewers + refines its algorithm, making it more intuitive with time. +3. **Encourage Team Discussions:** After automated reviews, foster team + discussions. This ensures the code isn't just machine-compliant, but also + logically sound and efficient from a human perspective. + +## Conclusion + +Ah, the outcome! We've ventured deep into the rabbit hole (no pun intended with +CodeRabbit) of AI's transformative role in remote engineering. From the highs of +streamlined code reviews to the essential human-AI harmony, it's evident that AI +doesn't just knock on the doors of modern engineering—it's barging in, holding a +battering ram of innovation. + +Remember when remote work was a cute little option, often tucked away in the +"benefits" section of a job posting? Well, it's not just mainstream now; it's +the modus operandi for countless teams globally. As this mode of work continues +to snowball, the technological advancements, especially ones like AI-driven code +reviewers, aren't merely luxury add-ons. They are becoming vital cogs in the +well-oiled machine that a remote engineering team aspires to be. + +As we stand on the brink of yet more seismic shifts in the way we work and +collaborate, it's exhilarating to think of the untapped potential of tools and +technologies still on the horizon. The canvas of remote work is vast, and we've +only just started splashing it with color. Here's to a brighter, more +innovative, and yes, more automated future, but always with a sprinkle of +irreplaceable human magic. + +**_Cheers to the codes that bind us, both human and binary._** diff --git a/static/img/blogs/blog4.jpeg b/blog/boosting-engineering-efficiency-2023-11-13/preview.jpeg similarity index 100% rename from static/img/blogs/blog4.jpeg rename to blog/boosting-engineering-efficiency-2023-11-13/preview.jpeg diff --git a/blog/coderabbit-deep-dive-2023-08-26/blog.md b/blog/coderabbit-deep-dive-2023-08-26/blog.md new file mode 100644 index 0000000..3987f9a --- /dev/null +++ b/blog/coderabbit-deep-dive-2023-08-26/blog.md @@ -0,0 +1,207 @@ +--- +slug: coderabbit-deep-dive +title: AI and the Future of Code Reviews - A Deep Dive into CodeRabbit +description: AI and the Future of Code Reviews - A Deep Dive into CodeRabbit +authors: [gur, vishu] +tags: ["CodeRabbit", "AI", "Code Reviews"] +image: ./preview.jpeg +hide_table_of_contents: false +--- + +We are witnessing an inflection point in the software development industry. +Developers around the world have been realizing the incredible possibilities +that AI can bring. The introduction of +[GitHub Copilot](https://github.com/features/copilot) and +[ChatGPT](https://chat.openai.com/auth/login) have revolutionized software +development. They have been the +[fastest-growing tools](https://aibusiness.com/companies/one-year-on-github-copilot-adoption-soars) +in the history of software development. + +While on the code generation side, many tools have emerged, the code review +process has remained largely unchanged. We continue to use the same tools and +processes that were used 10 years ago. The code is still manually reviewed, +which is slow, error-prone, and expensive. To address this, we are building +[CodeRabbit](https://coderabbit.ai/), an AI-powered code reviewer that is part +of the code merge and CI/CD process. With CodeRabbit our vision is to speed up +the code merge process by an order of magnitude, while also improving the +quality of the code that goes beyond what is possible with human reviewers alone +and existing linting tools. + +<!--truncate--> + +## Impediments to shipping quality software @Speed + +An average developer spends most of their time between writing and reviewing the +code. Typically, the development process involves branching off from the main +code base, developing a new feature or fixing a bug, and then merging the code +back into the mainline. To write software, developers use modern editors such as +Visual Studio Code which include sophisticated language servers, static +analyzers and linters. These tools are being rapidly augmented by AI-powered +extensions such as GitHub Copilot. Local development tools are just one part of +the equation. + +Relying on local tools alone is not sufficient to prevent quality issues, as +they are inconsistent across the developers, which makes it difficult to enforce +standards. To ensure quality, the code is merged collaboratively in the form of +[pull requests (PR)](https://docs.github.com/en/pull-requests) in platforms such +as GitHub/GitLab. As soon as the PR is opened, the CI/CD process kicks in. The +code is linted, compiled and tested. Most importantly, the code is reviewed by a +peer who checks for the intention of changes, in addition to looking for coding +standards, security vulnerabilities, and other issues. The reviews require a +broader context to not just understand the changes but also evaluate the impact +on the larger codebase. The reviewer approves the PR, and the code is merged +into the main codebase. The code review is required not just for the quality of +the code but also for meeting compliance and regulatory requirements. + +While the ideal code review process sounds smooth and efficient, the reality is +often riddled with challenges and inefficiencies. Specifically, the manual +review is often the slowest part of the development process. It is not uncommon +for a **PR** to take days or even weeks to get merged. Here's a brief glimpse +into the challenges: + +**Team Slowdown:** The waiting period for code reviews and merges affects not +just individual developers but the whole team. Project timelines get stretched, +leading to delays in launching new features or fixing critical bugs. + +**Context Switching:** Developers often lose context when they switch from +coding to waiting for a review. Getting back into the code takes time and mental +energy, which hampers productivity. + +**Rubber-Stamp Reviews:** In dysfunctional teams, the code review process can +become a mere formality. Reviewers might approve code without thorough +inspection, allowing bugs and vulnerabilities to slip through. + +**Personality Clashes:** Sometimes, friction between the developer and the +reviewer goes beyond code quality, leading to nitpicking and unnecessary delays. +This can create a toxic work environment, affecting the team's morale. + +**Job Dissatisfaction:** Continual delays and inefficiencies in the code merge +process can often demoralize developers to the point where they consider +switching jobs, affecting the company's retention rates. + +In summary, the status-quo is not ideal, and it is evident from the software +bugs, security vulnerabilities, and the service outages that frequently plague +the software industry. + +## Merging code 10x faster with CodeRabbit + +CodeRabbit is an AI-powered code reviewer that significantly speeds up the code +review process while also improving the quality of the code. It works seamlessly +within the pull request workflow and collaborates with the developer and the +reviewer to ensure code quality. It goes beyond existing linters and static code +analysis tools in uncovering issues and suggesting improvements by providing a +human-like understanding of the objective of the code. + +With CodeRabbit, developers get context-aware feedback within minutes, which +enables them to make improvements based on best practices and get their code +ready to be merged faster. CodeRabbit also helps reviewers by providing them +with confidence and speed to approve the code faster. Reviewers can use +CodeRabbit's auto-generated walkthrough and suggestions as a starting point for +their review. Peer reviewer can have a three-way collaboration including the +developer, and CodeRabbit, which can significantly enrich the review experience +while saving them time and effort. + +CodeRabbit is built on top of the generative AI to provide the following key +capabilities: + +**Summarization:** CodeRabbit summarizes the code changes in the PR and provides +a high-level overview. This helps the reviewer and product team to quickly +understand the changes and the impact on the product. + +**Incremental Reviews:** CodeRabbit thoroughly reviews the code after each +commit and provides incremental feedback to the developer. It uncovers issues +and suggests improvements by commenting on the code like a human reviewer. + +**Chat about changes:** CodeRabbit provides conversational capability that +allows developers and reviewers to ask questions, generate code, and get +feedback in the context of changes. + +## Designing CodeRabbit + +The review process is multi-stage and shown in the figure below. CodeRabbit's +workflow is triggered when a developer opens a pull request or commits code to +an existing pull request. This is followed by various summarization and review +stages. + + + +CodeRabbit is not just a simple wrapper that does pass-through to the LLM +models. To circumvent context size limits, CodeRabbit uses an innovative, +multi-LLM and multi-stage approach to scale reviews for larger change sets. +Unlike AI-based code completion tools, code reviews are a much more complex +problem. The reviewer context is much broader than the developer context, as the +reviewer needs to uncover not just obvious issues but also understand the larger +context of the pull request and changes across multiple files. Below is a +glimpse into the challenges we faced and the solutions we came up with: + +**Context window size:** The LLM models have limited context windows, for +instance, `gpt-3.5-turbo` has a context window of 4K or 16K tokens and `gpt-4` +has a context window of 8K tokens. This is often insufficient to pack larger +change sets. To circumvent this, we provide various summaries while reviewing +changes to each file and by smartly prioritizing context that is packed in each +request. + +**Inputting and outputting structured content:** LLMs are particularly bad at +understanding and generating structured content and mathematical computation. We +had to design new input formats, that are closer to how humans understand +changes, instead of using the standard unified diff format. We also had to +provide few-shot examples to the LLMs to get the desired results. + +**Noise:** LLMs are terrible at differentiating between noise and signal. For +instance, if you ask LLMs for 20 suggestions, you will get them, but only a few +of them will be useful. This is particularly true for code reviews. We had to +design a multi-stage review process that reinforces the signal and filters out +the noise. + +**Costs:** While advanced models like `gpt-4` are great in performing complex +tasks, they are several orders of magnitude more expensive than models like +`gpt-3.5-turbo`. We had to design a multimodel approach that uses simpler models +for summarizations, while complex models are used for tasks such as reviewing +code. In addition, simpler models act as a triage filter that identifies the +changes that need to be thoroughly reviewed by more complex models. + +**Inaccuracies:** LLMs are not perfect and often return inaccurate results, and +they sometimes even ignore instructions and completely fabricate a response. +Rather than keep fighting the LLMs, we wrote layers of sanity checks to fix or +hide the inaccuracies from the user. + +**Data privacy:** The biggest concern from our users is whether their code is +being stored and used to train the models. We made sure that all queries to LLMs +are ephemeral, and the data is discarded right away from our service. At the +same time, it's challenging to provide stateful incremental reviews without +storing the data. We had to design a system that stores all state within the +pull request itself and not in our service for maximum privacy. + + + +## Conclusion + +Building on top of LLMs is a new space, and we can draw parallels to how early +software such as MS-DOS were built on top of IBM PC and Intel microprocessors. +Even with limited memory, +[killer applications](https://www.pcmag.com/news/the-ibm-pcs-killer-apps-where-are-they-now) +were built. The context size limits of LLMs are similar to the memory limits of +early PCs. Innovation is required to build sophisticated applications on top of +LLMs that give the impression of a much larger context, just like early +[3D games](<https://en.wikipedia.org/wiki/Doom_(1993_video_game)>) used +innovative techniques to run even on modest PCs. It's quite likely that immense +value will be captured by the applications while underlying LLMs and AI +infrastructure such as vector databases will continue to get commoditized. In +addition, the line between the actual model training and the prompting continues +to be blurred. Prompts with few-shot examples and fine-tuning can make a big +difference in the quality of results and is an area that will differentiate +products that build on top of LLMs. + +At CodeRabbit, we are at the forefront of this innovation by building an +AI-first developer tools company from the ground up. We are approaching this +problem from first principles, as the techniques being used bear little +resemblance to the existing tools like linters and static code analysis tools. +We are witnessing an inflection point as AI has crossed the practicality +threshold, despite its limitations. Furthermore, we believe that we can keep +innovating around the limitations and bring sophisticated products that push the +boundaries of what is possible with AI. We are excited about our roadmap and +hope to unlock immense value for our customers in the near future. + +<!-- <ShareButton platform="twitter" text="Twitter" url='CodeRabbit: Bringing AI to Code Reviews&hashtags=CodeRabbitAI'/> + +<ShareButton platform="facebook" url="CodeRabbit: Bringing AI to Code Reviews" text="LinkedIn" /> --> diff --git a/blog/2023-08-26-welcome/coderabbit-openai-rate-limit-exceed.png b/blog/coderabbit-deep-dive-2023-08-26/coderabbit-openai-rate-limit-exceed.png similarity index 100% rename from blog/2023-08-26-welcome/coderabbit-openai-rate-limit-exceed.png rename to blog/coderabbit-deep-dive-2023-08-26/coderabbit-openai-rate-limit-exceed.png diff --git a/blog/2023-08-26-welcome/CodeRabbitSecurity.jpg b/blog/coderabbit-deep-dive-2023-08-26/coderabbit-security.jpg similarity index 100% rename from blog/2023-08-26-welcome/CodeRabbitSecurity.jpg rename to blog/coderabbit-deep-dive-2023-08-26/coderabbit-security.jpg diff --git a/static/img/blogs/founder_blog_meta.jpeg b/blog/coderabbit-deep-dive-2023-08-26/preview.jpeg similarity index 100% rename from static/img/blogs/founder_blog_meta.jpeg rename to blog/coderabbit-deep-dive-2023-08-26/preview.jpeg diff --git a/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/blog.md b/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/blog.md new file mode 100644 index 0000000..5924e84 --- /dev/null +++ b/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/blog.md @@ -0,0 +1,172 @@ +--- +slug: how-we-built-cost-effective-generative-ai-application +title: How we built a cost-effective Generative AI application +description: + Building a Generative AI application is expensive. Here's how we make it cost + effective and improve user experience. +authors: [gur] +tags: ["AI", "Cost Optimization", "Generative AI", "Code Review"] +hide_table_of_contents: false +aiDisclaimer: true +--- + +# How we built a cost-effective Generative AI application + +Since its inception, CodeRabbit has experienced steady growth in its user base, +comprising developers and organizations. Installed on thousands of repositories, +CodeRabbit reviews several thousand pull requests (PRs) daily. We have +[previously discussed](/blog/coderabbit-openai-rate-limits) our use of an +innovative client-side request prioritization technique to navigate OpenAI rate +limits. In this blog post, we will explore how we manage to deliver continuous, +in-depth code analysis cost-effectively, while also providing a robust, free +plan to open-source projects. + +<!--truncate--> + +## CodeRabbit's Product Offering and LLM Consumption + +CodeRabbit is an AI-first PR Review tool that uses GPT APIs for various +functionalities. CodeRabbit offers the following tiers of service: + +- CodeRabbit Pro: A paid service providing in-depth code reviews for private + repositories. It's priced according to the number of developers, starting with + a full-featured 7-day free trial. +- CodeRabbit for Open Source: A free service offering in-depth code reviews for + open source (public) repositories. +- CodeRabbit Free: A free plan for private repositories, providing summarization + of code changes in a PR. + +Our vision is to offer an affordable, AI-driven code review service to +developers and organizations of all sizes while supporting the open-source +community. We are particularly mindful of open-source projects, understanding +the challenges in reviewing community contributions. Our goal is to reduce the +burden of code reviews for open-source maintainers by improving submission +quality before the review process begins. + +CodeRabbit's review process is automatically triggered when a PR is opened in +GitHub or GitLab. Each review involves a complex workflow that builds context +and reviews each file using large language models (LLMs). Code review is a +complex task that requires an in-depth understanding of the changes and the +existing codebase. High-quality review comments necessitate state-of-the-art +language models such as gpt-4. However, these models are significantly more +expensive than simpler models, as shown by the +[10x-30x price difference](https://openai.com/pricing) between gpt-3.5-turbo and +gpt-4 models. + +| Model | Context Size | Cost per 1k Input Tokens | Cost per 1k Output Tokens | +| ------------- | ------------ | ------------------------ | ------------------------- | +| GPT-4 | Up to 32k | $0.06 | $0.12 | +| GPT-4 | Up to 8k | $0.03 | $0.06 | +| GPT-3.5 Turbo | Up to 16k | $0.003 | $0.004 | +| GPT-3.5 Turbo | Up to 4k | $0.0015 | $0.002 | + +> gpt-4 model is 10-30x more expensive than gpt-3.5-turbo model + +Our primary cost driver is using OpenAI's API to generate code review comments. +We will share our cost optimization strategies in the following sections. +Without these optimizations, our free offering to open-source projects would not +be feasible. + +Let's take a look at the strategies that helped us optimize the cost and improve +user experience. + +--- + +## 1. Dual-models: Summarize & Triage Using Simpler Models + +For less complex tasks such as summarizing code diffs, simpler models such as +gpt-3.5-turbo are adequate. As an initial optimization, we use a mix of models, +as detailed in [our earlier blog post](/blog/coderabbit-deep-dive). We use +gpt-3.5-turbo to compress large code diffs into concise summaries, which are +then processed by gpt-4 for reviewing each file. This dual-model approach +significantly reduces costs and enhances review quality, enabling us to manage +PRs with numerous files and extensive code differences. + +Additionally, we implemented triage logic to skip trivial changes from the +review process. We use the simpler model to classify each diff as either trivial +or complex, as part of the same prompt used for code diff summarization. +Low-risk changes such as documentation updates, variable renames, and so on, are +thus excluded from the thorough review process. This strategy has proven +effective, as simpler models can accurately identify trivial changes. + +By using this dual-model approach for summarization and filtering out trivial +changes, we save almost 50% on costs. + +## 2. Rate-limiting: Enforcing Fair Usage + +Upon launching our free service for open-source projects, we noticed individual +developers using it as a coding co-pilot by making hundreds of incremental +commits for continuous feedback. CodeRabbit, designed for thorough code reviews +unlike tools such as GitHub Copilot, incurs high costs when used in this manner. +Therefore, we implemented hourly rate-limits on the number of files and commits +reviewed per user, to control excessive usage without compromising user +experience. These limits vary across different product tiers. For example, we +set more aggressive limits for open-source users compared to trial and paid +users. + +To implement these rate-limits, we evaluated various options for Serverless +environments. We opted for [FluxNinja Aperture](https://fluxninja.com/) for its +simplicity and policy sophistication. We were already using Aperture for +managing [OpenAI rate limits](coderabbit-openai-rate-limits), making it a +natural choice for our rate-limiting needs as well. + +In FluxNinja Aperture, policies are decoupled from application logic through +labels, enabling new policy additions without altering application code. We +apply labels in FluxNinja Aperture, wrap the review workload with its SDK, and +write policies that enforce limits on those labels. For example, we enforce a 3 +reviews per hour limit (1 review every 20 minutes) for open-source users, +allowing a burst of 2 back-to-back reviews, as shown in the screenshots below. + +Integration with FluxNinja Aperture SDK + + +_Rate-limiting commits per hour for open-source users_ + + +_Wait time feedback to the user in a comment_ + +Given the high cost and capacity constraints of state-of-the-art models such as +gpt-4, rate-limiting is an essential requirement for any AI application. By +implementing fair-usage rate limits, we are saving almost 20% on our costs. + + +_Rate limit metrics for open-source users_ + +## 3. Caching: Avoid Re-generating Similar Review Comments + +We believe that building user habits around AI involves seamlessly augmenting +existing workflows. Therefore, AI code reviews must be continuous: they should +trigger as soon as a PR is opened and incrementally update the summary and +generate review comments as more commits are added. + +However, this approach can become expensive and generate repetitive feedback, as +similar review comments are re-generated for each commit. We observed that most +incremental commits involve minor adjustments or bug fixes in the initial +implementation. To address this, we implemented a caching layer to avoid +re-generating similar review comments for incremental commits. + +Fortunately, Aperture also provides a simple caching mechanism for summaries +from previous commits, using the same API call where we implemented rate limits. +During each incremental review, we use the simpler model for a semantic +comparison of the code changes described in both summaries. If the changes are +similar, we skip the review for those files to prevent re-generating similar +review comments. This method differs from vector similarity-based caching +techniques, as we use an LLM model for comparing summaries. Vector +similarity-based approaches wouldn't be effective in our case, as the summaries +require semantic comparison. We have integrated this method into the same prompt +used for code diff summarization and triage. + +By using the more cost-effective gpt-3.5-turbo model as an advanced similarity +filter before invoking the more expensive gpt-4 model for the same file, we have +saved almost 20% of our costs by avoiding the generation of similar review +comments. + +--- + +## Conclusion + +In this blog post, we briefly discussed how state-of-the-art LLMs such as gpt-4 +can be expensive in production. We also shared our strategy of using a +combination of simpler models, rate limits, and caching to optimize operational +costs. We hope our experiences can assist other AI startups in optimizing their +costs and developing cost-effective AI applications. diff --git a/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/generative-ai-request-flow-cost-saving.png b/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/generative-ai-request-flow-cost-saving.png similarity index 100% rename from blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/generative-ai-request-flow-cost-saving.png rename to blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/generative-ai-request-flow-cost-saving.png diff --git a/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/rate-limit-message-screenshot.png b/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/rate-limit-message-screenshot.png similarity index 100% rename from blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/rate-limit-message-screenshot.png rename to blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/rate-limit-message-screenshot.png diff --git a/blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/rate-limits-metrics-screenshot.png b/blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/rate-limits-metrics-screenshot.png similarity index 100% rename from blog/2023-12-23-how-we-built-cost-effective-generative-ai-application/rate-limits-metrics-screenshot.png rename to blog/how-we-built-cost-effective-generative-ai-application-2023-12-23/rate-limits-metrics-screenshot.png diff --git a/blog/img/CodeRabbitDesign.jpg b/blog/img/coderabbit-design.jpg similarity index 100% rename from blog/img/CodeRabbitDesign.jpg rename to blog/img/coderabbit-design.jpg diff --git a/blog/modern-ai-stack-for-developer-productivity-2024-01-05/blog.md b/blog/modern-ai-stack-for-developer-productivity-2024-01-05/blog.md new file mode 100644 index 0000000..c5d55ee --- /dev/null +++ b/blog/modern-ai-stack-for-developer-productivity-2024-01-05/blog.md @@ -0,0 +1,153 @@ +--- +slug: modern-ai-stack-for-developer-productivity +title: Modern AI stack for developer productivity +description: + Elevate your development workflow with three pillars of developer productivity + tools powered by Artificial Intelligence +image: ./preview.jpg +authors: [pradeep] +tags: ["AI", "Developer Tools", "Code Generation", "Code Review", "Knowledge"] +hide_table_of_contents: false +aiDisclaimer: true +--- + +The 'modern AI stack for developer productivity' refers to a comprehensive set +of AI-powered developer tools that improve developer productivity in building +software. In 2023, Large Language Models (LLMs) caused significant disruption, +leading to a rapid increase in the adoption of artificial intelligence within +the development lifecycle, particularly in the realm of 'developer productivity +tools'. A significant majority of software development projects are now +leveraging some form of AI, specifically Generative AI, to transform traditional +development workflows into more intelligent, efficient, and automated processes. + +The modern AI stack for developer productivity is reshaping the landscape of +software development, making once time-consuming tasks or complex more +manageable and automated. From helping with the research or code writing to +reviewing code and ensuring quality, the modern AI stack is a testament to how +AI is not just an add-on but an integral component in the software development +process. + +Are you leveraging the full potential of the modern AI tech stack in your +projects? This article might help you to get that perspective needed to +understand how it might elevate your work to the next level. + +<!--truncate--> + +## Three Pillars of the **Modern AI Stack for Developer Productivity** + +There are three key components in the modern AI stack for developer productivity +that are useful in different stages of the development lifecycle. These three +stages are the research or knowledge gathering stage, the coding stage, and the +final code review stage. Let’s discuss each of these stages in detail and how AI +tools can help improve developer productivity in each. + +### Knowledge + +The Knowledge pillar is central to the modern AI stack. It involves AI systems +helping developers gather and synthesize knowledge, usually in the form of a +chat or question-and-answer session. A prime example in this space is +[ChatGPT](https://chat.openai.com/) + +- [ChatGPT](https://chat.openai.com/) is the leading AI assistant to quickly + answer developers' questions on syntax, frameworks, debugging, etc. +- It acts like a supercharged search engine, saving developers time from having + to dig through documentation or StackOverflow. +- ChatGPT can also explain concepts, provide code examples and suggestions, and + identify knowledge gaps. Over time, these models will get better at technical + reasoning with more training data. +- [StackOverflow Community Search](https://stackoverflow.co/labs/search/) is + another product in this category which instantly summarizes the solution. + +This transformation is crucial in developing environments where quick access to +information and rapid problem-solving are essential. + +#### Challenges + +One of the main challenges is ensuring the accuracy and reliability of the +answers. AI systems might sometimes generate plausible but incorrect or biased +responses. + +### Code Generation + +Code generation through AI marks a significant leap in software development. AI +models, trained on vast code repositories, can now assist in generating code +snippets and at times the entire modules. This accelerates the coding process. +The evolution of this pillar is a testament to AI's growing understanding of +programming languages and logic, offering a collaborative tool that augments the +developer's capabilities rather than replacing them. + +- AI models like OpenAI’s GPT-4 Code Interpreter are leading this segment. +- They aid in writing code, offering suggestions, and even generating entire + code blocks based on user input. +- They are particularly beneficial in increasing development speed and making + coding more accessible to non-experts. +- [GitHub Copilot](https://github.com/features/copilot) introduces this + experience in the IDE (such as VS Code) where you code. It enhances coding + efficiency by rapidly suggesting code blocks and functions directly within the + editor. This helps developers generate boilerplate code, complete repetitive + tasks and implement common patterns much faster. + +#### Challenges + +The limitations include dependency on the training data, which may not always +represent the most efficient or modern coding practices. Ethically, there are +concerns about code originality and the potential for inadvertently generating +vulnerable or buggy code. + +### Code Review + +AI’s role in code review is about ensuring quality, compliance, and +optimization. Unlike traditional code reviews, which are time-consuming and +prone to human oversight, AI-driven code reviews are swift and more thorough. AI +models can scan code for patterns, anomalies, and compliance with coding +standards, offering insights and suggestions for improvements. This pillar has +evolved from basic syntax checking to sophisticated analysis, significantly +enhancing the code quality. + +- Automated code review tools, like [CodeRabbit](https://coderabbit.ai/), help + in identifying bugs, evaluating whether the PR achieves its objectives, and + ensuring adherence to coding standards. The in-line comments make it easier to + use and put things in motion. +- These tools can analyze code more thoroughly and quickly than human reviewers, + leading to higher quality software. This frees up developer time as well as + improves code quality before reaching production. +- Over time, CodeRabbit could fine-tune to a team's specific code review + checklist and feedback provided in comments to provide even more accurate + suggestions and extend this access to organization knowledge via code reviews + naturally. + +#### Challenges + +If there is not enough information about the requirements in the issues, the PR +assessment against the requirement might not provide the accurate picture as you +would expect. + +## Prioritize knowledge and review over generation + +While most people would be attracted by the promises code generation offers, I +believe it will not have as big an impact on developer productivity as the other +two - Knowledge and Code Review. + +Code Generation tools may save some time in writing standard code, understanding +and fine-tuning the output remains crucial. But the risk of overreliance on AI +for code generation can lead to code inaccuracies and legal issues with +AI-generated code. The real productivity gains come from improving +organizational knowledge and code review process to ensure high standards of +code quality. + +As +[StackOverflow rightly mentioned](https://stackoverflow.blog/2023/12/29/the-hardest-part-of-building-software-is-not-coding-its-requirements/) + +> The hardest part of building software is not coding, it is requirements + +Software is more than just code; it's about meeting the users' need. The +knowledge and code review pillar tightly align with this goal. Which is why I +urge you to prioritize Knowledge and Code Review tools in your modern AI stack. + +## Conclusion + +The integration of these three pillars - Knowledge, Code Generation, and Code +Review - forms a robust foundation in the AI-driven development process. Each +pillar complements the others, creating a synergistic environment where +developers are empowered with advanced tools and insights, leading to more +efficient, innovative, and error-free software development. diff --git a/blog/2024-01-05-modern-ai-stack-for-developer-productivity/banner.jpg b/blog/modern-ai-stack-for-developer-productivity-2024-01-05/preview.jpg similarity index 100% rename from blog/2024-01-05-modern-ai-stack-for-developer-productivity/banner.jpg rename to blog/modern-ai-stack-for-developer-productivity-2024-01-05/preview.jpg diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/2023-10-23-coderabbit-openai-rate-limits.md b/blog/openai-rate-limits-2023-10-23/blog.md similarity index 82% rename from blog/2023-10-23-coderabbit-openai-rate-limits/2023-10-23-coderabbit-openai-rate-limits.md rename to blog/openai-rate-limits-2023-10-23/blog.md index e985a85..ddfa265 100644 --- a/blog/2023-10-23-coderabbit-openai-rate-limits/2023-10-23-coderabbit-openai-rate-limits.md +++ b/blog/openai-rate-limits-2023-10-23/blog.md @@ -1,53 +1,28 @@ --- slug: coderabbit-openai-rate-limits -title: Squeezing Water from Stone - Managing OpenAI Rate Limits with Request Prioritization -description: How CodeRabbit uses Aperture to manage OpenAI rate limits with request prioritization +title: + Squeezing Water from Stone - Managing OpenAI Rate Limits with Request + Prioritization +description: + How CodeRabbit uses Aperture to manage OpenAI rate limits with request + prioritization authors: [gur, sumanvs, nato] -image: https://coderabbit.ai/blog/assets/images/Blog3-4188b2a6acf85932803da8983b14607c.png -tags: [rate-limits, quota-management, prioritization, aperture, openai] +image: ./preview.png +tags: ["AI", "OpenAI", "Rate Limits", "Aperture"] hide_table_of_contents: false aiDisclaimer: true --- -<head> - <meta charSet="utf-8" /> - <link rel="apple-touch-icon" sizes="180x180" href="/icons/apple-touch-icon.png" /> - <link rel="icon" type="image/png" sizes="32x32" href="/icons/favicon-32x32.png" /> - <link rel="icon" type="image/png" sizes="16x16" href="/icons/favicon-16x16.png"/> - <meta content="/icons/apple-touch-icon.png" itemprop="image" /> - <link rel="icon" href="/icons/favicon-32x32.ico"></link> - - <link rel="manifest" href="/icons/site.webmanifest"></link> - - <title>Squeezing Water from Stone: Managing OpenAI Rate Limits with Request - Prioritization</title> - <meta name="title" content="Squeezing Water from Stone: Managing OpenAI Rate Limits with Request - Prioritization" /> - - <meta property="og:type" content="article" /> - <meta property="og:url" content="https://coderabbit.ai/blog/coderabbit-openai-rate-limits" /> - <meta property="og:title" content="Squeezing Water from Stone: Managing OpenAI Rate Limits with Request - Prioritization" /> -<meta property="og:image" content="https://coderabbit.ai/blog/assets/images/Blog3-4188b2a6acf85932803da8983b14607c.png" /> - - <meta name="twitter:image" content="https://coderabbit.ai/blog/assets/images/Blog3-4188b2a6acf85932803da8983b14607c.png" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="Squeezing Water from Stone: Managing OpenAI Rate Limits with Request - Prioritization" /> -</head> - -<!-- import ShareButton from '../src/components/ShareButton/ShareButton'; --> - ```mdx-code-block import Tabs from '@theme/Tabs'; import TabItem from '@theme/TabItem'; ``` Since CodeRabbit launched a couple of months ago, it has received an -enthusiastic response and hundreds of sign-ups. CodeRabbit has been -installed in over 1300 GitHub organizations and typically reviews more than 2000 -pull requests per day. Furthermore, the usage continues to flourish; we -are experiencing a healthy week-over-week growth. +enthusiastic response and hundreds of sign-ups. CodeRabbit has been installed in +over 1300 GitHub organizations and typically reviews more than 2000 pull +requests per day. Furthermore, the usage continues to flourish; we are +experiencing a healthy week-over-week growth. While this rapid growth is encouraging, we've encountered challenges with OpenAI's stringent rate limits, particularly for the newer `gpt-4` model that @@ -90,12 +65,12 @@ developers on the quality of their code. The feedback is provided in the form of comments on the pull request, allowing the developers to enhance the code based on the provided suggestions in the follow-up commits. - + CodeRabbit employs a combination of the `gpt-3.5-turbo` and `gpt-4` family of models. For simpler tasks such as summarization, we use the more economical -`gpt-3.5-turbo` model, whereas intricate tasks such as in-depth code -reviews are performed by the slow and expensive `gpt-4` model. +`gpt-3.5-turbo` model, whereas intricate tasks such as in-depth code reviews are +performed by the slow and expensive `gpt-4` model. Our usage pattern is such that each file in a [pull request is summarized and reviewed concurrently](https://coderabbit.ai/blog/coderabbit-deep-dive). @@ -140,7 +115,7 @@ the nature of requests. We were introduced to the [FluxNinja Aperture](https://www.fluxninja.com/) load management platform by one of our advisors. -[Aperture](https://github.com/fluxninja/aperture) is an open source load +[Aperture](https://github.com/fluxninja/aperture) is an open-source load management platform that offers advanced rate-limiting, request prioritization, and quota management features. Essentially, Aperture serves as a global token bucket, facilitating client-side rate limits and business-attribute-based @@ -175,13 +150,13 @@ context to Aperture, we also attach the following labels to each request: tier. For example, the reasoning could that the user is a `paid_user`, `trial_user` or a `open_source_user`. Requests to OpenAI are prioritized based on these labels. -- `priority`: Requests are ranked according a priority number provided in this - label. For instance, requests from `paid_user` are given precedence over those - from `trial_user` and `open_source_user`. The base priority is incremented for - each file reviewed, enabling pull requests that are further along in the - review process to complete more quickly than newly submitted ones. - Additionally, chat messages are assigned a much higher priority compared to - review tasks. +- `priority`: Requests are ranked according to a priority number provided in + this label. For instance, requests from `paid_user` are given precedence over + those from `trial_user` and `open_source_user`. The base priority is + incremented for each file reviewed, enabling pull requests that are further + along in the review process to complete more quickly than newly submitted + ones. Additionally, chat messages are assigned a much higher priority compared + to review tasks.  @@ -252,22 +227,22 @@ context to Aperture, we also attach the following labels to each request: Aperture offers a foundational "blueprint" for [managing quotas](https://docs.fluxninja.com/reference/blueprints/quota-scheduling/base), -comprising of two main components: +comprising two main components: - Rate limiter: OpenAI employs a token bucket algorithm to impose rate limits, and that is directly compatible with Aperture's rate limiter. For example, in the tokens per minute policy for `gpt-4`, we have allocated a burst capacity of `40000 tokens`, and a refill rate of `40000 tokens per minute`. The bucket begins to refill the moment the tokens are withdrawn, aligning with OpenAI's - rate limiting mechanism. This ensures our outbound request and token rate + rate-limiting mechanism. This ensures our outbound request and token rate remains synchronized with OpenAI's enforced limits. - Scheduler: Aperture has a [weighted fair queuing](https://docs.fluxninja.com/concepts/scheduler/) scheduler that prioritizes the requests based on multiple factors such as the number of tokens, priority levels and workload labels. -By fine-tuning these two components in Aperture, we are able to go as fast as we -can, with optimal user experience, while ensuring that we don't exceed the rate +By fine-tuning these two components in Aperture, we can go as fast as we can, +with optimal user experience, while ensuring that we don't exceed the rate limits. <details> @@ -433,7 +408,3 @@ and with Aperture, FluxNinja is well positioned to be the leader in this space. As CodeRabbit continues to build and add additional components such as vector databases, which are also computationally expensive, we are confident that Aperture will continue to help us offer a reliable experience to our users. - -<!-- <ShareButton platform="twitter" text="Twitter" url='Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization&hashtags=CodeRabbitAI'/> - -<ShareButton platform="facebook" url="Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization" text="LinkedIn" /> --> diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/flow-analytics-dark.png b/blog/openai-rate-limits-2023-10-23/flow-analytics-dark.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/flow-analytics-dark.png rename to blog/openai-rate-limits-2023-10-23/flow-analytics-dark.png diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/flow-analytics-light.png b/blog/openai-rate-limits-2023-10-23/flow-analytics-light.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/flow-analytics-light.png rename to blog/openai-rate-limits-2023-10-23/flow-analytics-light.png diff --git a/static/img/blogs/Blog3.png b/blog/openai-rate-limits-2023-10-23/preview.png similarity index 100% rename from static/img/blogs/Blog3.png rename to blog/openai-rate-limits-2023-10-23/preview.png diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/priorities-dark.png b/blog/openai-rate-limits-2023-10-23/priorities-dark.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/priorities-dark.png rename to blog/openai-rate-limits-2023-10-23/priorities-dark.png diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/priorities-light.png b/blog/openai-rate-limits-2023-10-23/priorities-light.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/priorities-light.png rename to blog/openai-rate-limits-2023-10-23/priorities-light.png diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/request-flow.svg b/blog/openai-rate-limits-2023-10-23/request-flow.svg similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/request-flow.svg rename to blog/openai-rate-limits-2023-10-23/request-flow.svg diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/token-rate-dark.png b/blog/openai-rate-limits-2023-10-23/token-rate-dark.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/token-rate-dark.png rename to blog/openai-rate-limits-2023-10-23/token-rate-dark.png diff --git a/blog/2023-10-23-coderabbit-openai-rate-limits/token-rate-light.png b/blog/openai-rate-limits-2023-10-23/token-rate-light.png similarity index 100% rename from blog/2023-10-23-coderabbit-openai-rate-limits/token-rate-light.png rename to blog/openai-rate-limits-2023-10-23/token-rate-light.png diff --git a/docs/about/features.md b/docs/about/features.md index b931a26..7eb7020 100644 --- a/docs/about/features.md +++ b/docs/about/features.md @@ -1,61 +1,60 @@ --- title: CodeRabbit in Action sidebar_label: CodeRabbit in Action -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: Learn how CodeRabbit works in a pull request review. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> +### 1. Pull Request Summary {#pull-request-summary} - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> +Generated upon the creation of a pull request and subsequently updated with each +incremental request. - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> +High-Level Summary: This offers a concise overview of the changes in the pull +request. It helps the team, including those without technical expertise, to +quickly understand the changes and the impact on the product. -### 1. Pull Request Summary[](https://coderabbit.ai/docs/coderabbit-in-action#pull-request-summary) + -Generated upon the creation of a pull request and subsequently updated with each incremental request. +Walkthrough: A detailed code walkthrough to understand the changes in each file +that is part of the pull request, followed by a celebratory poem about the +changes. -High-Level Summary: This offers a concise overview of the changes in the pull request. It helps the team, including those without technical expertise, to quickly understand the changes and the impact on the product. + - +### 2. Code Review feedback {#code-review-feedback} -Walkthrough: A detailed code walkthrough to understand the changes in each file that is part of the pull request, followed by a celebratory poem about the changes. +Review comments: Review feedback posts as pull request, review comments on the +lines of the code that changed under each file. Any code suggestions are given +in a Diff format, which either be copied or committed within the pull request +with a single click. - + -### 2. Code Review feedback[](https://coderabbit.ai/docs/coderabbit-in-action#code-review-feedback) +### 3. Chat with CodeRabbit {#chat-with-coderabbit} -Review comments: Review feedback posts as pull request review comments on the lines of the code that changed under each file. Any code suggestions are given in a Diff format which either be copied or committed within the pull request with a single click. +CodeRabbit provides conversational capability that allows developers and the +reviewers to ask questions, generate code, and get feedback in the context of +changes. Just comment on the CodeRabbit review to start the conversation. +CodeRabbit learns from your interactions and gets smarter over time. The more +you chat, the better it gets. - + -### 3. Chat with CodeRabbit[](https://coderabbit.ai/docs/coderabbit-in-action#chat-with-coderabbit) +### 4. Issue Validation {#issue-validation} -CodeRabbit provides conversational capability that allows developers and the reviewers to ask questions, generate code, and get feedback in the context of changes. Just comment on the CodeRabbit review to start the conversation. CodeRabbit learns from your interactions and gets smarter over time. The more you chat, the better it gets. +Pull request changes are validated against the linked GitHub or GitLab issue and +identifies all other issues which might be affected by this change. - + -### 4. Issue Validation[](https://coderabbit.ai/docs/coderabbit-in-action#issue-validation) +### 5. Pull Request review status {#pull-request-review-status} -Pull request changes are validated against the linked GitHub or GitLab issue and identifies all other issues which might be effected by this change. +Review status is generated for each review, including a separate one for each +incremental commit. Displays the commit IDs that were reviewed, the files +examined and ignored, as well as the actionable feedback and additional comments +generated for each review. - + -### 5. Pull Request review status[](https://coderabbit.ai/docs/coderabbit-in-action#pull-request-summary-1) - -Review status is generated for each review including a separate one for each incremental commit. Displays the commit IDs that were reviewed, the files examined and ignored, as well as the actionable feedback and additional comments generated for each review. - - - -For information on how to get started with CodeRabbit, visit the [Get Started page](/get-started/signup) +For information on how to get started with CodeRabbit, visit +the [Get Started page](/get-started/signup) diff --git a/docs/about/pricing.md b/docs/about/pricing.md index 6efa443..99fb071 100644 --- a/docs/about/pricing.md +++ b/docs/about/pricing.md @@ -1,36 +1,25 @@ --- title: Plans sidebar_label: Plans -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: + Learn about the plans, pricing, and subscription management of CodeRabbit. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - -This section covers the plans, pricing, and subscription management of CodeRabbit. +This section covers the plans, pricing, and subscription management of +CodeRabbit. ## **Understanding Your Options** -- **Transparent Pricing**: CodeRabbit offers a per-seat pricing model that scales with your team size, ensuring you pay for what you need. -- **7-Day Free Trial**: All plans start with a generous 7-day free trial for CodeRabbit Pro for the entire organization, ensuring a commitment-free experience -- **No Credit Card Required**: You won't need a credit card to start your free trial. -- **CodeRabbit Seats** - Every developer who submits a pull request is counted as a separate seat. Seats can be purchased for all or for a limited number of developers. +- **Transparent Pricing**: CodeRabbit offers a per-seat pricing model that + scales with your team size, ensuring you pay for what you need. +- **7-Day Free Trial**: All plans start with a generous 7-day free trial for + CodeRabbit Pro for the entire organization, ensuring a commitment-free + experience +- **No Credit Card Required**: You won't need a credit card to start your free + trial. +- **CodeRabbit Seats** Every developer who submits a pull request is counted as + a separate seat. Seats can be purchased for all or for a limited number of + developers. --- @@ -68,7 +57,7 @@ These are the hourly usage limits for each developer per repository: ### Features - Starts with a 7-day free trial of the Pro plan. -- unlimited access on both public and private repositories. +- Unlimited access for both public and private repositories. - Summarization pull requests on private repositories. - Reviews pull requests on public repositories. @@ -86,16 +75,19 @@ These are the hourly usage limits for each developer per repository: ### Pro Plan -- GitHub/GitLab organization owners can purchase or make changes to the subscription. -- You can choose to manually purchase seats and assign them to developers, or have them assigned automatically as developers create pull requests. -- During the trial period, seat assignment is automatic, but the number of seats can be adjusted when purchasing the subscription. +- GitHub/GitLab organization owners can purchase or introduce changes to the + subscription. +- You can choose to manually purchase seats and assign them to developers, or + have them assigned automatically as developers create pull requests. +- During the trial period, seat assignment is automatic, but the number of seats + can be adjusted when purchasing the subscription. - - + + ### Free Plan - Seats are assigned to new developers immediately - - + + diff --git a/docs/about/support.md b/docs/about/support.md index 3b09bfa..5cfa83e 100644 --- a/docs/about/support.md +++ b/docs/about/support.md @@ -1,79 +1,73 @@ --- title: Support sidebar_label: Support -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: Get help with CodeRabbit and find answers to common questions. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - -{" "} - -<meta property="og:type" content="website" /> -<meta property="og:url" content="https://coderabbit.ai/" /> -<meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> -<meta property="og:description" content="Accelerate Code Reviews with AI" /> -<meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - -Welcome to CodeRabbit's Support! Please refer this section if you encounter any issues or have questions. Our support team will respond back as soon as possible. +Welcome to CodeRabbit's Support! Please refer to this section if you encounter +any issues or have questions. Our support team will respond back as soon as +possible. ### **Common Issues and Answers** -These are the most common questions our support team receives, and you might find an answer here +These are the most common questions our support team receives, and you might +find an answer here ### Can I switch between different organizations on CodeRabbit? -Yes, you can switch between different organizations on CodeRabbit. To do so, click on the organization name in the top right corner of the CodeRabbit UI. +Yes, you can switch between different organizations on CodeRabbit. To do so, +click on the organization name in the top-right corner of the CodeRabbit UI. -<div align="center"></div> -<div align="center"></div> + + ### Can CodeRabbit subscription be used across multiple organizations? -Subscription seat are tied to the specific GitHub/GitLab organization under which they are purchased and cannot be used under another organization. +Subscription seats are tied to the specific GitHub/GitLab organization under +which they are purchased and cannot be used under another organization. ### Can CodeRabbit review my existing PRs after integrating it? -CodeRabbit would by default only review new PRs or existing PRs which have a new commits after the app is installed. -You can however use @coderabbitai review command on the PR to trigger a review of existing PRs. +CodeRabbit would by default only review new PRs or existing PRs which have a new +commit after the app is installed. You can, however, use the +`@coderabbitai review` command on the PR to trigger a review of existing PRs. ### Who can add the repositories on CodeRabbit? -You need to be GitHub/GitLab admin to add the repositories. +You need to be a GitHub/GitLab admin to add the repositories. -### Do I need own OpenAI key with CodeRabbit Pro? +### Do I need my own OpenAI key with CodeRabbit Pro? -OpenAI cost is part of the subscription.There is no additional cost for OpenAI. +OpenAI cost is part of the subscription. There is no additional cost for OpenAI. -### What is the difference between CodeRabbit OSS ai-pr-reviewer and CodeRabbit Pro ? +### What is the difference between CodeRabbit OSS and CodeRabbit Pro? -ai-pr-reviewer is our Open Source Software (OSS) for pull request reviews. With CodeRabbit OSS, you need your own OpenAI key, and you will incur OpenAI costs. -On the other hand, with a CodeRabbit Pro subscription, the OpenAI cost is included. Additionally, CodeRabbit Pro offers advanced prompts and superior noise reduction features, which are not present in CodeRabbit OSS. +[`ai-pr-reviewer`](https://github.com/coderabbitai/ai-pr-reviewer) project is +our Open-Source Software (OSS) for pull request reviews. With CodeRabbit OSS, +you need your own OpenAI key, and you will incur OpenAI costs. On the other +hand, with a CodeRabbit Pro subscription, the OpenAI cost is included. +Additionally, CodeRabbit Pro offers advanced prompts and superior noise +reduction features, which are not present in CodeRabbit OSS. -### Can I use both CodeRabbit OSS and CodeRabbit Pro together ? +### Can I use both CodeRabbit OSS and CodeRabbit Pro together? -You can, but this will result in duplicate reviews. We suggest you use only one of the two. +You can, but this will result in duplicate reviews. We suggest you use only one +of the two. ### **Opening a Support Ticket** -To get assistance from our support team, open a ticket using the help icon on the CodeRabbit UI: +To get assistance from our support team, open a ticket using the help icon on +the CodeRabbit UI: -Complete the support ticket by providing your name, email, a description of your issue, and attaching any necessary files. If you are reporting a bug , please provide the GitHub or GitLab organization name. +Complete the support ticket by providing your name, email, a description of your +issue, and attaching any necessary files. If you are reporting a bug, please +provide the GitHub or GitLab organization name.   -:::tip -To see more common issues faced by CodeRabbit users, visit our FAQ section for detailed answers and solutions to frequently encountered problems. +:::tip To see more common issues faced by CodeRabbit users, visit our FAQ +section for detailed answers and solutions to frequently encountered problems. ::: ### **Community Collaboration** diff --git a/docs/faq/faq.md b/docs/faq/faq.md index ae20a2c..d6ce78a 100644 --- a/docs/faq/faq.md +++ b/docs/faq/faq.md @@ -1,66 +1,70 @@ --- title: FAQs sidebar_label: FAQs -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: Frequently asked questions about CodeRabbit. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - #### **1. How accurate is CodeRabbit's review?** -Early adoption results for CodeRabbit have been highly promising, demonstrating significant accuracy in code reviews. However, it's crucial to understand that AI is an evolving field, and absolute 100% accuracy can't be guaranteed. Our technology is continuously learning and improving, aiming for the highest possible accuracy in reviews. +Early adoption results for CodeRabbit have been highly promising, demonstrating +significant accuracy in code reviews. However, it's crucial to understand that +AI is an evolving field, and absolute 100% accuracy can't be guaranteed. Our +technology is continuously learning and improving, aiming for the highest +possible accuracy in reviews. #### **2. Which programming languages does CodeRabbit support?** -CodeRabbit is designed to work with all programming languages. However, the proficiency of our AI models might vary between languages, which could slightly affect the accuracy of the review. +CodeRabbit is designed to work with all programming languages. However, the +proficiency of our AI models might vary between languages, which could slightly +affect the accuracy of the review. #### **3. Does CodeRabbit store my code or use it for training language models?** -We train our system using open source projects. For private repositories, neither CodeRabbit nor OpenAI LLMs use your code for training purposes. +We train our system using open source projects. For private repositories, +neither CodeRabbit nor OpenAI LLMs use your code for training purposes. #### **4. What Large Language Models does CodeRabbit use?** -CodeRabbit currently utilizes Open AI's GPT 4 and GPT 3.5. We're researching and testing upcoming LLMs to ensure we're offering the most precise reviews possible. +CodeRabbit currently utilizes Open AI's GPT 4 and GPT 3.5. We're researching and +testing upcoming LLMs to ensure we're offering the most precise reviews +possible. #### **5. Can I customize CodeRabbit?** -Reviews are customizable. For information, check out our [Get Started page](/get-started/signup). +Reviews are customizable. For information, check out our +[Get Started page](/get-started/signup). #### **6. Can I choose a language other than English for the reviews?** -CodeRabbit supports most widely-used languages. You can configure this in the repository settings. +CodeRabbit supports most widely used languages. You can configure this in the +repository settings. #### **7. What access does CodeRabbit need to my repositories?** -CodeRabbit requests minimal access to perform code reviews and post comments on Pull Requests. On GitHub, it requires read access to metadata, code, discussions, issues, and read/write access to the pull requests. On GitLab, it requires read access to the repository, and the CodeRabbit Bot user requires a developer role. +CodeRabbit requests minimal access to perform code reviews and post comments on +Pull Requests. On GitHub, it requires read access to metadata, code, +discussions, issues, and read/write access to the pull requests. On GitLab, it +requires read access to the repository, and the CodeRabbit Bot user requires a +developer role. #### **8. How can I add or remove users for my subscription?** -To manage users, log in to CodeRabbit and navigate to subscriptions. You can add or remove users as needed. +To manage users, log in to CodeRabbit and navigate to subscriptions. You can add +or remove users as needed. #### **9. How can I interact with the CodeRabbit bot?** -To interact with CodeRabbit's bot, reply to the CodeRabbit Comment. If there are team members collaborating on pull requests, the bot stays silent by default but can be engaged by tagging **@Coderabbitai**. This feature allows you to provide context, generate test cases, or ask for specific code suggestions, all within the context of your code lines or entire files. +To interact with CodeRabbit's bot, reply to the CodeRabbit Comment. If there are +team members collaborating on pull requests, the bot stays silent by default but +can be engaged by tagging **@Coderabbitai**. This feature allows you to provide +context, generate test cases, or ask for specific code suggestions, all within +the context of your code lines or entire files. #### **10. Can individual developers use CodeRabbit?** -Absolutely! Whether you're an individual developer or part of an organization, CodeRabbit can be your coding assistant, providing you with invaluable suggestions. +Absolutely! Whether you're an individual developer or part of an organization, +CodeRabbit can be your coding assistant, providing you with invaluable +suggestions. #### **11. Which branches are the pull requests reviewed on?** @@ -78,14 +82,21 @@ There are hourly rate limits for each developer per repository: - Number of reviews : 3 back to back reviews followed by 4 reviews/hour - Number of conversations: 25 back to back messages followed by 50 messages/hr -In-trial and open-source plans have lower rate limits than the paid plan. In all cases, we re-allow further reviews/conversations after a brief timeout. +In-trial and open-source plans have lower rate limits than the paid plan. In all +cases, we re-allow further reviews/conversations after a brief timeout. #### **14. I can't add CodeRabbit to my GitLab Repositories?** -If there are any access restrictions by domain, then you will need to add `coderabbit.ai` as an allowed domain. +If there are any access restrictions by domain, then you will need to add +`coderabbit.ai` as an allowed domain. :::note -We are continually innovating and enhancing our application with new capabilities. Stay tuned and follow us for updates as new exciting features are built. We're committed to making your experience with CodeRabbit even better. + +We are continually innovating and enhancing our application with new +capabilities. Stay tuned and follow us for updates as new exciting features are +built. We're committed to making your experience with CodeRabbit even better. + ::: -If you have further questions or need additional information, don't hesitate to reach out to us at [contact@coderabbit.ai](mailto:contact@coderabbit.ai). +If you have further questions or need additional information, don't hesitate to +reach out to us at [contact@coderabbit.ai](mailto:contact@coderabbit.ai). diff --git a/docs/get-started/add-repo.md b/docs/get-started/add-repo.md index 352d6f5..59d8ec5 100644 --- a/docs/get-started/add-repo.md +++ b/docs/get-started/add-repo.md @@ -1,41 +1,29 @@ --- title: Add Repositories sidebar_label: Add Repositories -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: Learn how to add CodeRabbit to your GitHub or GitLab repositories. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - Learn how to add CodeRabbit to your GitHub or GitLab repositories. -To add additional repositories after the sign-up, go to the repositories page within the CodeRabbit UI. +To add additional repositories after the sign-up, go to the repositories page +within the CodeRabbit UI. -Click on the "**Add repositories**" button. Upon clicking, you'll be redirected to GitHub. +Click on the "**Add repositories**" button. Upon clicking, you'll be redirected +to GitHub.   -Upon successful installation, you will be automatically redirected back to the CodeRabbit UI. Here, you can view the list of repositories that CodeRabbit now has access to. +Upon successful installation, you will be automatically redirected back to the +CodeRabbit UI. Here, you can view the list of repositories that CodeRabbit now +has access to. :::note -For **GitLab** the flow is slightly different. All the repositories display by default and you can toggle and enable the ones where the CodeRabbit app should be installed. +For **GitLab**, the flow is slightly different. All the repositories display by +default, and you can toggle and enable the ones where the CodeRabbit app should +be installed.   @@ -44,4 +32,8 @@ For **GitLab** the flow is slightly different. All the repositories display by d ### **Need help?** -If you require assistance, our support team is here to help. Simply click on the help icon within the CodeRabbit user interface. For more detailed information, please refer to the "Support" section. Additionally, consider joining the CodeRabbit **Discord** community to connect with other users and access a wealth of knowledge about using CodeRabbit effectively. +If you require assistance, our support team is here to help. Simply click on the +help icon within the CodeRabbit user interface. For more detailed information, +please refer to the "Support" section. Additionally, consider joining the +CodeRabbit **Discord** community to connect with other users and access a wealth +of knowledge about using CodeRabbit effectively. diff --git a/docs/get-started/analytics.md b/docs/get-started/analytics.md index e6cc34f..c9e847c 100644 --- a/docs/get-started/analytics.md +++ b/docs/get-started/analytics.md @@ -1,43 +1,35 @@ --- title: CodeRabbit Dashboard sidebar_label: CodeRabbit Dashboard +description: + CodeRabbit Dashboard displays organization's pull request activity and value + provided by CodeRabbit reviews. slug: /dashboard -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> +CodeRabbit Dashboard displays organization's pull request activity and value +provided by CodeRabbit reviews. This includes the number of pull requests +reviewed, actionable items, optional comments and more. - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> +The dashboard displays the following information: - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> +- **Pull Requests Overview:** View the number of pull requests reviewed by + CodeRabbit per week, month, and year. +- **CodeRabbit's Activity:** Understand the metrics related to the number of + reviews conducted by CodeRabbit, actionable items, and optional suggestions. -CodeRabbit Dashboard displays organization's pull request activity and value provided by CodeRabbit reviews. This includes the number of pull requests reviewed, actionable items, optional comments and more. - -Dashboard displays the following information: - -- **Pull Requests Overview:** View the number of pull requests reviewed by CodeRabbit per week, month, and year. -- **CodeRabbit's Activity:** Understand the metrics related to the number of reviews conducted by CodeRabbit, actionable items, and optional suggestions. - - - + + Access the list of recent pull requests reviewed. - - + + ### **Need help?** -If you require assistance, our support team is here to help. Simply click on the help icon within the CodeRabbit user interface. For more detailed information, please refer to the "Support" section. Additionally, consider joining the CodeRabbit Discord community to connect with other users and access a wealth of knowledge about using CodeRabbit effectively. +If you require assistance, our support team is here to help. Simply click on the +help icon within the CodeRabbit user interface. For more detailed information, +please refer to the "Support" section. Additionally, consider joining the +CodeRabbit Discord community to connect with other users and access a wealth of +knowledge about using CodeRabbit effectively. diff --git a/docs/get-started/signup.md b/docs/get-started/signup.md index 6a4af0c..1a53e9e 100644 --- a/docs/get-started/signup.md +++ b/docs/get-started/signup.md @@ -1,56 +1,56 @@ --- title: Sign Up sidebar_label: Sign Up -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: + Learn how to sign up for CodeRabbit and get started with your first code + review. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - ### **Sign Up for CodeRabbit** -Signing up for CodeRabbit is quick and easy, allowing you to get started in just a few seconds. Whether you're an individual developer or part of a team, you can start for free and upgrade to a paid plan after a no-commitment trial. For more information about CodeRabbit's subscription plan options, please refer to the pricing page. +Signing up for CodeRabbit is quick and easy, allowing you to get started in just +a few seconds. Whether you're an individual developer or part of a team, you can +start for free and upgrade to a paid plan after a no-commitment trial. For more +information about CodeRabbit's subscription plan options, please refer to the +pricing page. ### **Step 1: Getting Started** -**Login with GitHub or GitLab**: Log in with your GitHub or GitLab account at [https://coderabbit.ai/login](https://coderabbit.ai/login) +**Login with GitHub or GitLab**: Log in with your GitHub or GitLab account at +[https://coderabbit.ai/login](https://coderabbit.ai/login)   ### **Step 2: Select Organization** -On the GitHub page, you will be prompted to choose the organization where you want to install the CodeRabbit app. Select the organization to proceed. +On the GitHub page, you will be prompted to choose the organization where you +want to install the CodeRabbit app. Select the organization to proceed.  ### **Step 3: Authorize CodeRabbit** -After selecting the organization, you will be directed to a GitHub repositories page where you will install and authorize the CodeRabbit GitHub app. You can choose to grant access to all your organization's repositories or select specific repositories. +After selecting the organization, you will be directed to a GitHub repositories +page where you will install and authorize the CodeRabbit GitHub app. You can +choose to grant access to all your organization's repositories or select +specific repositories.  -After you have installed the CodeRabbit app, the reviews will start automatically with the new pull requests or incremental commits to existing pull requests. To trigger reviews on existing pull requests, post "@coderabbitai review" as a comment on the pull request. +After you have installed the CodeRabbit app, the reviews will start +automatically with the new pull requests or incremental commits to existing pull +requests. To trigger reviews on existing pull requests, post "@coderabbitai +review" as a comment on the pull request. -:::tip -The automatic code review behavior can be changed to "On-Demand". To make this change, go to the repository settings in the UI or modify the appropriate setting in the YAML file to disable reviews. -::: +:::tip The automatic code review behavior can be changed to "On-Demand". To make +this change, go to the repository settings in the UI or modify the appropriate +setting in the YAML file to disable reviews. ::: ### **Need help?** -If you require assistance, our support team is here to help. Simply click on the help icon within the CodeRabbit user interface. For more detailed information, please refer to the "Support" section. Additionally, consider joining the CodeRabbit Discord community to connect with other users and access a wealth of knowledge about using CodeRabbit effectively. +If you require assistance, our support team is here to help. Simply click on the +help icon within the CodeRabbit user interface. For more detailed information, +please refer to the "Support" section. Additionally, consider joining the +CodeRabbit Discord community to connect with other users and access a wealth of +knowledge about using CodeRabbit effectively. diff --git a/docs/guides/coderabbit-commands.md b/docs/guides/coderabbit-commands.md index 3e780a5..f5ec0e0 100644 --- a/docs/guides/coderabbit-commands.md +++ b/docs/guides/coderabbit-commands.md @@ -1,53 +1,47 @@ --- title: CodeRabbit Commands -description: Efficiently manage your PR reviews with our intuitive commands. Use these commands to request on-demand code reviews in addition to the default automatic reviews. sidebar_label: CodeRabbit Commands -image: "/preview_meta.jpg" +description: Learn how to manage your PR reviews with CodeRabbit commands. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit Commands" /> - <meta name="description" content="Efficiently manage your PR reviews with our intuitive commands. Use these commands to request on-demand code reviews in addition to the default automatic reviews." /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit Commands" /> - <meta property="og:description" content="Efficiently manage your PR reviews with our intuitive commands. Use these commands to request on-demand code reviews in addition to the default automatic reviews." /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit Commands" /> - <meta name="twitter:description" content="Efficiently manage your PR reviews with our intuitive commands. Use these commands to request on-demand code reviews in addition to the default automatic reviews." /> -</head> - Manage your PR reviews with the following commands: -By default, CodeRabbit automatically reviews all pull requests. Additionally, for each pull request, it will review all incremental commits. However, this behavior can be overridden using the following commands: +By default, CodeRabbit automatically reviews all pull requests. Additionally, +for each pull request, it will review all incremental commits. However, this +behavior can be overridden using the following commands: - **Pause Reviews**: - Use `@coderabbitai pause` in a PR comment to halt ongoing reviews. - **Resume Reviews**: - Enter `@coderabbitai resume` in a PR comment to continue paused reviews. - **On-Demand Reviews**: - - Disable automatic reviews for your repository to switch to on-demand reviews. - - Use `@coderabbitai review` in a PR comment. This command will override all review filters that might be set up in the repository settings and will initiate a one-time review. + - Disable automatic reviews for your repository to switch to on-demand + reviews. + - Use `@coderabbitai review` in a PR comment. This command will override all + review filters that might be set up in the repository settings and will + initiate a one-time review. - **Skip Specific PR**: - - To exclude a specific PR from review, include `@coderabbitai ignore` in the PR description. + - To exclude a specific PR from review, include `@coderabbitai ignore` in the + PR description. - **Resolve Command**: - - Use `@coderabbitai resolve` to mark all the CodeRabbit review comments as resolved all at once. + - Use `@coderabbitai resolve` to mark all the CodeRabbit review comments as + resolved all at once. - **Help Command**: - - You can at any time post `@coderabbitai help` in a PR comment to get the list of all valid commands. + - You can at any time post `@coderabbitai help` in a PR comment to get the + list of all valid commands. :::note -Ensure you input these commands as PR comments. For direct bot interactions, enter your input in the review comments of a code diff or file. + +Ensure you input these commands as PR comments. For direct bot interactions, +enter your input in the review comments of a code diff or file. + ::: ### Feedback -If you have suggestions for additional commands or improvements, we would love to hear from you! Please submit your feedback to our support team. +If you have suggestions for additional commands or improvements, we would love +to hear from you! Please submit your feedback to our support team. diff --git a/docs/guides/customize-coderabbit.md b/docs/guides/customize-coderabbit.md index be1596a..c370f7b 100644 --- a/docs/guides/customize-coderabbit.md +++ b/docs/guides/customize-coderabbit.md @@ -1,31 +1,14 @@ --- title: Customize CodeRabbit sidebar_label: Customize CodeRabbit -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" -show-title: false +description: + CodeRabbit offers various customization options to tailor the reviews to your + specific requirements. Customizations can be made using one of the below + options. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> - - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - CodeRabbit offers various customization options to tailor the reviews to your -specific requirements. Customizations can be made using one of the below options -: +requirements. Customizations can be made using one of the below options : 1. **Customization via CodeRabbit YAML File** _(Recommended)_ 2. **Customization via CodeRabbit UI** @@ -35,7 +18,8 @@ Customization defined in the YAML file overrides the settings in the UI. ### 1. Customize CodeRabbit using a YAML File[](https://coderabbit.ai/docs/get-started/customize-coderabbit) You can add a `.coderabbit.yaml` configuration file to your repositories. Below -is a sample YAML file that can be used as a starting point and change as needed: +is a sample YAML file that can be used as a starting point and changed as +needed: #### version 2: `Current` @@ -71,65 +55,69 @@ reviews: - "feat/.*" tools: ast-grep: - rules_folder: "custom-rules-folder-name" - utils_folder: "custom-utils-folder-name" + rules_directory: "custom-rules-directory-name" + utils_directory: "custom-utils-directory-name" chat: auto_reply: true ``` :::note -`.coderabbit.yaml` file should be placed at the root directory of the + +`.coderabbit.yaml` file should be placed in the root directory of the repository. + ::: YAML settings: -1. **language**: Set the language for reviews using the ISO language code. For +1. **`language`**: Set the language for reviews using the ISO language code. For example, `"fr"` stands for French (default:`en`). -2. **early_access**: Enroll in the early access program to take advantage of +2. **`early_access`**: Enroll in the early access program to take advantage of forthcoming features before their general release (default:`false`). -3. **reviews**: Configurations for the code reviews. - - **request_changes_workflow**: Enable Request Changes review workflow for +3. **`reviews`**: Configurations for the code reviews. + - **`request_changes_workflow`**: Enable request changes review workflow for CodeRabbit reviews. (default: `false`). - - **high_level_summary**: CodeRabbit generates a high level summary of the + - **`high_level_summary`**: CodeRabbit generates a high-level summary of the changes (default:`true`). - - **poem**: Indicates whether a creative poem should be included in the + - **`poem`**: Indicates whether a creative poem should be included in the review (default:`true`). - - **review_status**: Indicates the status of the review (default:`true`). - - **collapse_walkthrough**: Collapses the walkthrough comment + - **`review_status`**: Indicates the status of the review (default:`true`). + - **`collapse_walkthrough`**: Collapses the walkthrough comment (default:`false`). - - **path_filters**: Specifies file patterns to exclude or include for a + - **`path_filters`**: Specifies file patterns to exclude or include for a review, such as `!dist/**` and `src/**.tsx`, using glob notation. - - **path_instructions**: Provides specific additional guidelines for code + - **`path_instructions`**: Provides specific additional guidelines for code review based on file paths. In the given example, JavaScript files are singled out for checks against the Google JavaScript style guide. File path accepts glob pattern - - **auto_review**: Manages settings for automated code reviews, such as: - - **enabled**: Automated code review (default: `true`). - - **ignore_title_keywords**: Review will be ignored if a pull request title - contains one of the list of keywords (e.g., `"WIP"`, `"DO NOT MERGE"`). - - **labels**: Review will be triggered if a pull request contains one of + - **`auto_review`**: Manages settings for automated code reviews, such as: + - **`enabled`**: Automated code review (default: `true`). + - **`ignore_title_keywords`**: Review will be ignored if a pull request + title contains one of the list of keywords (e.g., `"WIP"`, + `"DO NOT MERGE"`). + - **`labels`**: Review will be triggered if a pull request contains one of the list of labels. - - **drafts**: Determines whether draft pull requests are reviewed (default: - `true`). - - **base_branches**: A list of base branches where the reviews will occur + - **`drafts`**: Determines whether draft pull requests are reviewed + (default: `true`). + - **`base_branches`**: A list of base branches where the reviews will occur apart from the default branch. Accepts regex pattern. - - **tools**: Configurations for the tools used in the review. - - **ast-grep**: Configurations for the ast-grep tool. - - **rules_folder**: The folder name where the custom ast-grep rules are - stored. - - **utils_folder**: The folder name where the custom ast-grep utils are - stored. -4. **chat**: Defines the behavior of CodeRabbit's bot in conversations. - - **auto_reply**: The bot automatically replies without the need of the user - tagging it ( default: `true` ). + - **`tools`**: Configurations for the tools used in the review. + - **`ast-grep`**: Configurations for the `ast-grep` tool. + - **`rules_directory`**: The directory name where the custom `ast-grep` + rules are stored. + - **`utils_directory`**: The directory name where the custom `ast-grep` + utils are stored. +4. **`chat`**: Defines the behavior of CodeRabbit's bot in conversations. + - **`auto_reply`**: The bot automatically replies without the need of the + user tagging it (default: `true`). Refer: [CodeRabbit Configuration Schema](https://coderabbit.ai/integrations/coderabbit-overrides.v2.json). <details> + <summary> version 1 (deprecated) </summary> #### version 1: `deprecated` (Please use version [version 2](/guides/customize-coderabbit)) @@ -170,47 +158,45 @@ settings: tools: # tools configuration for ast-grep ast-grep: - rules_folder: "custom-rules-folder-name" - utils_folder: "custom-utils-folder-name" + rules_directory: "custom-rules-directory-name" + utils_directory: "custom-utils-directory-name" ``` -<!--  --> - This configuration file consists of the following settings: -1. **enable_draft_pr_reviews**: Set to **false** to disable draft pull +1. **`enable_draft_pr_reviews`**: Set to **`false`** to disable draft pull request(PR) reviews. -2. **additional_branches_to_be_reviewed**: Define additional branches to be +2. **`additional_branches_to_be_reviewed`**: Define additional branches to be reviewed besides the default branch. -3. **disable_high_level_summary**: If set to **true**, disables high-level +3. **`disable_high_level_summary`**: If set to **`true`**, disables high-level summary generation. -4. **path_based_instructions**: Allows you to specify instructions based on file - paths. In this example, instructions for Python and JavaScript files are +4. **`path_based_instructions`**: Allows you to specify instructions based on + file paths. In this example, instructions for Python and JavaScript files are provided, encouraging adherence to the Google style guide. -5. **ignored_pr_titles**: Specifies ignored PR titles, in this case, "WIP" (Work - in Progress). -6. **review_language**: Sets the review language to French ("fr"). -7. **disable_poem**: If set to **false**, enables the "poem" feature. -8. **early_access_program**: Determines whether to enable the early access - program (set to **false** in this case). -9. **exclude_file_patterns**: Specifies patterns for excluding certain files +5. **`ignored_pr_titles`**: Specifies ignored PR titles, in this case, "WIP" + (Work in Progress). +6. **`review_language`**: Sets the review language to French (`fr`). +7. **`disable_poem`**: If set to **`false`**, enables the "poem" feature. +8. **`early_access_program`**: Determines whether to enable the early access + program (set to **`false`** in this case). +9. **`exclude_file_patterns`**: Specifies patterns for excluding certain files from review, such as `!dist/**` and `!**.md`. -10. **limit_reviews_by_label**: Limits reviews by label, targeting "first_bug" +10. **`limit_reviews_by_label`**: Limits reviews by label, targeting "first_bug" label reviews. -11. **disable_review**: Totally disables automatic code reviews for the +11. **`disable_review`**: Totally disables automatic code reviews for the repository. -12. **disable_review_status**: This is the comment posted for each incremental +12. **`disable_review_status`**: This is the comment posted for each incremental review status. This removes the review status comment. Reviews will still take place. However, optional comments added to the review status will not be posted. -13. **collapse_walkthrough_comment**: Specifies whether to collapse walkthrough - comments on the review. -14. **tools**: Configurations for the tools used in the review. - - **ast-grep**: Configurations for the ast-grep tool. - - **rules_folder**: The folder name where the custom ast-grep rules are - stored. - - **utils_folder**: The folder name where the custom ast-grep utils are - stored. +13. **`collapse_walkthrough_comment`**: Specifies whether to collapse + walkthrough comments on the review. +14. **`tools`**: Configurations for the tools used in the review. + - **`ast-grep`**: Configurations for the `ast-grep` tool. + - **`rules_directory`**: The directory name where the custom `ast-grep` + rules are stored. + - **`utils_directory`**: The directory name where the custom `ast-grep` + utils are stored. Refer: [CodeRabbit configuration schema](https://coderabbit.ai/integrations/coderabbit-overrides.json). @@ -230,15 +216,15 @@ Reviews can also be customized through the UI under repository settings: **Path-based instructions :** Provide additional review guidelines based on the file paths using glob patterns. -For further guidance, please refer this +For further guidance, please refer to this section [Prompt Customization](/guides/prompt-customization) **Language Selection:** Select the natural language in which you want the review feedback. CodeRabbit supports most of the widely used languages. The default language is English. -**Disable High Level Summary:** This allows disabling high level summary added -with the pull request description. +**Disable High-Level Summary:** This allows disabling the high-level summary +added with the pull request description. --- @@ -249,7 +235,7 @@ with the pull request description. **Disable Reviews:** Disables automatic code reviews for the repository. Reviews can be initiated on-demand using CodeRabbit commands. -**Enable Draft Pull request Reviews:** Select whether CodeRabbit should review +**Enable draft pull request reviews:** Select whether CodeRabbit should review the draft pull requests. **Configure reviews using pull request labels:** Select specific pull request diff --git a/docs/guides/prompt-customization.md b/docs/guides/prompt-customization.md index db1db8a..b96563c 100644 --- a/docs/guides/prompt-customization.md +++ b/docs/guides/prompt-customization.md @@ -1,50 +1,44 @@ --- title: Prompt Customization sidebar_label: Prompt Customization -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: + CodeRabbit offers various customization options to tailor the reviews to your + specific requirements. Customizations can be made using one of the below + options. --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> +### Path-based instructions {#path-based-instructions} - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> +This section explains how to add custom code review instructions for the entire +project or specific file paths in your project using glob patterns. Developers +can provide tailored review guidelines based on the file paths. These +instructions are needed only if you want the reviewer to follow specific +instructions besides the standard review. - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> +Adding file path prompts allows developers to specify custom instructions for +different parts of the codebase. For example, you may want to enforce a style +guide by file types or directories. -### Path-based instructions[](https://coderabbit.ai/docs/prompt-customization#path-based-instructions) +### Sample Usage {#sample-usage} -This section explains how to add custom code review instructions for the entire project or specific file paths in your project using glob patterns. Developers can provide tailored review guidelines based on the file paths. These instructions are needed only if you want the reviewer to follow specific instructions besides the standard review. +- **`path`**: `**/*.js` -Adding file path prompts allows developers to specify custom instructions for different parts of the codebase. For example, you may want to enforce style guide by file types or directories. + **`instructions`**: Review the JavaScript code against the Google JavaScript + style guide and point out any mismatches -### Sample Usage[](https://coderabbit.ai/docs/prompt-customization#sample-usage) +- **`path`**: `tests/**.*` -**path:** `**/*.js` - -**instructions:** Review the JavaScript code against the Google JavaScript style guide and point out any mismatches - -**path:** `tests/**.*` - -**instructions:** Review the following unit test code written using the Mocha test library. -Ensure that: -The code adheres to best practices associated with Mocha. -Descriptive test names are used to clearly convey the intent of each test. + **`instructions`**: Review the following unit test code written using the + Mocha test library. Ensure that: The code adheres to best practices associated + with Mocha. Descriptive test names are used to clearly convey the intent of + each test. :::note - Paths accept glob patterns. -- Instructions generally work well for specific additional instructions. However, they are not that effective if you are instructing AI not to do something. +- Instructions generally work well for specific additional instructions. + However, they are not that effective if you are instructing AI not to do + something. - Test the review feedback on pull requests and tailor as necessary. ::: @@ -52,19 +46,33 @@ Descriptive test names are used to clearly convey the intent of each test. ## Abstract Syntax Tree (AST) instructions :::note -**Deep dive into AST patterns and ast-grep rules** - - AST patterns [wikipedia](https://en.wikipedia.org/wiki/Abstract_syntax_tree) - - ast-grep [official documentation](https://ast-grep.github.io/guide/rule-config.html) for detailed guides. + +**Deep dive into AST patterns and `ast-grep` rules** + +- Abstract Syntax Tree (AST) + [Wikipedia article](https://en.wikipedia.org/wiki/Abstract_syntax_tree) +- `ast-grep` + [official documentation](https://ast-grep.github.io/guide/rule-config.html) + for detailed guides. + ::: - -This section explains how to add custom code review instructions using ast-grep rules. ast-grep is a tool used for searching code using abstract syntax trees (AST) patterns. -By default, you can add ast-grep rules by following these steps: -1. Create a folder that keeps all the ast-grep rules in your project directory. -2. Add individual `.yaml` files for each ast-grep rule within the newly created folder. -3. Ensure that each `.yaml` file contains the necessary ast-grep rule configurations. -4. Ensure that all rules contains a `message` property, that will be used in the review process. -5. Add the rules folder to the `.coderabbit.yml` file under `tools.ast-grep` configuration. +This section explains how to add custom code review instructions using +`ast-grep` rules. `ast-grep` is a tool used for searching code using abstract +syntax trees (AST) patterns. + +By default, you can add `ast-grep` rules by following these steps: + +1. Create a directory that keeps all the `ast-grep` rules in your project + directory. +2. Add individual `.yaml` files for each `ast-grep` rule within the newly + created directory. +3. Ensure that each `.yaml` file contains the necessary `ast-grep` rule + configurations. +4. Ensure that all rules contains a `message` property, that will be used in the + review process. +5. Add the rules' directory to the `.coderabbit.yml` file under `tools.ast-grep` + configuration. ```yaml #... @@ -72,58 +80,77 @@ reviews: #... tools: ast-grep: - rules_folder: "custom-name" + rules_directory: "custom-name" #... ``` ### The rule object -Rule object is the core concept of ast-grep's rule system and every other feature is built on top of it. +Rule object is the core concept of `ast-grep` rule system and every other +feature is built on top of it. + +Below is the full list of fields in a rule object. Every rule field is optional +and can be omitted, but at least one field should be present in a rule. A node +will match a rule if and only if it satisfies all fields in the rule object. -Below is the full list of fields in a rule object. Every rule field is optional and can be omitted but at least one field should be present in a rule. A node will match a rule if and only if it satisfies all fields in the rule object. ```yaml rule: # atomic rule - pattern: 'search.pattern' - kind: 'tree_sitter_node_kind' - regex: 'rust|regex' + pattern: "search.pattern" + kind: "tree_sitter_node_kind" + regex: "rust|regex" # relational rule - inside: { pattern: 'sub.rule' } - has: { kind: 'sub_rule' } - follows: { regex: 'can|use|any' } - precedes: { kind: 'multi_keys', pattern: 'in.sub' } + inside: { pattern: "sub.rule" } + has: { kind: "sub_rule" } + follows: { regex: "can|use|any" } + precedes: { kind: "multi_keys", pattern: "in.sub" } # composite rule - all: [ {pattern: 'match.all'}, {kind: 'match_all'} ] - any: [ {pattern: 'match.any'}, {kind: 'match_any'} ] - not: { pattern: 'not.this' } - matches: 'utility-rule' + all: [{ pattern: "match.all" }, { kind: "match_all" }] + any: [{ pattern: "match.any" }, { kind: "match_any" }] + not: { pattern: "not.this" } + matches: "utility-rule" ``` ### Three Rule Categories + To summarize the rule object fields above, we have three categories of rules: - **Atomic Rule:** the most basic rule that checks if AST nodes matches. - **Relational Rule:** rules that check if a node is surrounded by another node. -- **Composite Rule:** rules that combine sub-rules together using logical operators. +- **Composite Rule:** rules that combine sub-rules together using logical + operators. -These three categories of rules can be composed together to create more complex rules. +These three categories of rules can be composed together to create more complex +rules. -The rule object is inspired by the CSS selectors but with more composability and expressiveness. -Thinking about how selectors in CSS works can help you understand the rule object! +The rule object is inspired by the CSS selectors but with more composability and +expressiveness. Thinking about how selectors in CSS works can help you +understand the rule object! -> Read ast-grep [documentation](https://ast-grep.github.io/guide/rule-config.html) for detailed guides. +> Read `ast-grep` > +> [documentation](https://ast-grep.github.io/guide/rule-config.html) for +> detailed guides. #### Atomic rule -Atomic rule defines the most basic matching rule that determines whether one syntax node matches the rule or not. There are three kinds of atomic rule: `pattern`, `kind` and `regex`. -> Official documentation guide on [Atomic Rule](https://ast-grep.github.io/guide/rule-config/atomic-rule.html) +Atomic rule defines the most basic matching rule that determines whether one +syntax node matches the rule or not. There are three kinds of atomic rule: +`pattern`, `kind` and `regex`. + +> Official documentation guide on +> [Atomic Rule](https://ast-grep.github.io/guide/rule-config/atomic-rule.html) #### Relational rule -Relational rule defines the relationship between two syntax nodes. There are four kinds of relational rule: `inside`, `has`, `follows` and `precedes`. -All four relational rules accept a sub-rule object as their value. The sub-rule will match the surrounding node while the relational rule itself will match the target node. +Relational rule defines the relationship between two syntax nodes. There are +four kinds of relational rule: `inside`, `has`, `follows` and `precedes`. + +All four relational rules accept a sub-rule object as their value. The sub-rule +will match the surrounding node, while the relational rule itself will match the +target node. -> Official documentation guide on [Relational Rule](https://ast-grep.github.io/guide/rule-config/relational-rule.html) +> Official documentation guide on +> [Relational Rule](https://ast-grep.github.io/guide/rule-config/relational-rule.html) ```yaml rule: @@ -134,11 +161,14 @@ rule: ``` #### Composite rule -Composite rule defines the logical relationship between multiple sub-rules. There are three kinds of composite rule: `all`, `any` and `not`. -**all** +A composite rule defines the logical relationship between multiple sub-rules. +There are three kinds of composite rule: `all`, `any` and `not`. + +**`all`** The `all` rule matches if all sub-rules match. + ```yaml rule: all: @@ -146,9 +176,10 @@ rule: - kind: expression_statement ``` -**any** +**`any`** `any` rule matches if any sub-rule matches. + ```yaml rule: any: @@ -157,7 +188,7 @@ rule: - pattern: let a = $A ``` -**not** +**`not`** `not` applies negation to a sub-rule. It matches if the sub-rule does not match. @@ -168,16 +199,22 @@ rule: pattern: console.log('Hello World') ``` -> Official documentation guide on [Composite Rule](https://ast-grep.github.io/guide/rule-config/composite-rule.html) - +> Official documentation guide on +> [Composite Rule](https://ast-grep.github.io/guide/rule-config/composite-rule.html) ### Reusing rule as utility -ast-grep chooses to use YAML for rule representation. While this decision makes writing rules easier, it does impose some limitations on the rule authoring. One of the limitations is that rule objects cannot be reused. + +`ast-grep` chooses to use YAML for rule representation. While this decision +makes writing rules easier, it does impose some limitations on the rule +authoring. One of the limitations is that rule objects cannot be reused. #### Local utility rule -Local utility rules are defined in the utils field of the config file. utils is a string-keyed dictionary. -For example, the following config file defines a local utility rule `is-literal`: +Local utility rules are defined in the utils field of the config file. Utils is +a string-keyed dictionary. + +For example, the following config file defines a local utility rule +`is-literal`: ```yaml utils: @@ -191,10 +228,13 @@ rule: ``` #### Global utility rule -Global utility rules are defined in a separate file. But they are available across all rule configurations in the project. -To create global utility rules, you need to have the `rules` folder created on the root of your project and another -`utils` directory inside the root of your project. +Global utility rules are defined in a separate file. But they are available +across all rule configurations in the project. + +To create global utility rules, you need to have the `rules` directory created +on the root of your project and another `utils` directory inside the root of +your project. ```yaml my-awesome-project # project root @@ -204,7 +244,8 @@ my-awesome-project # project root | |- is-literal.yml ``` ->Also, you need to add the `rules` and `utils` folders to the `.coderabbit.yml` file under `tools.ast-grep` configuration. +> Also, you need to add the `rules` and `utils` directories to the +> `.coderabbit.yml` file under `tools.ast-grep` configuration. ```yaml #... @@ -212,8 +253,8 @@ reviews: #... tools: ast-grep: - rules_folder: "rules" - utils_folder: "utils" + rules_directory: "rules" + utils_directory: "utils" #... ``` @@ -223,20 +264,22 @@ id: is-literal language: TypeScript rule: any: - - kind: 'false' + - kind: "false" - kind: undefined - - kind: 'null' - - kind: 'true' + - kind: "null" + - kind: "true" - kind: regex - kind: number - kind: string ``` -> Official documentation guide on [Utility Rule](https://ast-grep.github.io/guide/rule-config/utility-rule.html) +> Official documentation guide on +> [Utility Rule](https://ast-grep.github.io/guide/rule-config/utility-rule.html) ### Multiple Languages Support -CodeRabbit supports multiple programming languages for defining ast-grep rules. +CodeRabbit supports multiple programming languages for defining `ast-grep` +rules. - JavaScript - Typescript @@ -248,10 +291,12 @@ CodeRabbit supports multiple programming languages for defining ast-grep rules. - Python - C -Below are examples of ast-grep rules in different languages: +Below are examples of `ast-grep` rules in different languages: #### JavaScript + **Importing files without an extension is not allowed** + ```yaml id: find-import-file language: js @@ -271,7 +316,8 @@ rule: regex: "^import$" ``` -**No console.log allowed except console.error on the catch block** +**No console.log allowed except `console.error` on the catch block** + ```yaml id: no-console-except-error language: typescript @@ -286,17 +332,22 @@ rule: - pattern: console.$METHOD($$$) constraints: METHOD: - regex: 'log|debug|warn' + regex: "log|debug|warn" ``` #### C -In C, there is no built-in support for object-oriented programming, but some programmers use structs and function pointers to simulate classes and methods. + +In C, there is no built-in support for object-oriented programming, but some +programmers use structs and function pointers to simulate classes and methods. However, this style can have some drawbacks, such as: -- extra memory allocation and reallocation for the struct and the function pointer. -- indirection overhead when calling the function pointer. -A possible alternative is to use a plain function call with the struct pointer as the first argument. +- Extra memory allocation and reallocation for the struct and the function + pointer. +- Indirection overhead when calling the function pointer. + +A possible alternative is to use a plain function call with the struct pointer +as the first argument. ```yaml id: method_receiver @@ -307,8 +358,7 @@ transform: MAYBE_COMMA: replace: source: $$$ARGS - replace: '^.+' - by: ', ' -fix: - $METHOD(&$R$MAYBE_COMMA$$$ARGS) + replace: "^.+" + by: ", " +fix: $METHOD(&$R$MAYBE_COMMA$$$ARGS) ``` diff --git a/docs/integrations/self-hosted-gitlab.md b/docs/integrations/self-hosted-gitlab.md index 27e0f52..b4653b5 100644 --- a/docs/integrations/self-hosted-gitlab.md +++ b/docs/integrations/self-hosted-gitlab.md @@ -1,58 +1,51 @@ --- -title: CodeRabbit in Self Managed GitLab -description: Integrate CodeRabbit with your Self Managed GitLab instance. -sidebar_label: Self Managed GitLab -image: "/preview_meta.jpg" +title: CodeRabbit for Self-Managed GitLab +description: Integrate CodeRabbit with your Self-Managed GitLab instance. +sidebar_label: Self-Managed GitLab --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit in Self Managed GitLab" /> - <meta name="description" content="Integrate CodeRabbit in your own hosted GitLab instance." /> +This page guides you through the process of integrating your Self-Managed GitLab +with CodeRabbit. - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit in Self Managed GitLab" /> - <meta property="og:description" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit in Self Managed GitLab" /> - <meta name="twitter:description" content="CodeRabbit: AI-powered Code Reviews" /> -</head> - -This page guides you through the process of integrating your Self-Managed GitLab with CodeRabbit. - -To initiate the integration, we require specific information. This is essential for the initial setup of CodeRabbit within your domain. Once this setup is complete, you can log in directly using the OAuth2 flow. +To initiate the integration, we require specific information. This is essential +for the initial setup of CodeRabbit within your domain. Once this setup is +complete, you can log in directly using the OAuth2 flow. ### **Step 1: Getting Started** -**Visit CodeRabbit:** Land on to our [Login](https://coderabbit.ai/login) page and select Self-Hosted GitLab +**Visit CodeRabbit:** Land on to our [Login](https://coderabbit.ai/login) page +and select Self-Hosted GitLab  ### Step 2: Enter your Self Managed GitLab URL -On this page, enter the URL of your self managed GitLab instance and click submit. Once, you submit, we check our database for a record of your organization. +On this page, enter the URL of your self managed GitLab instance and click +submit. Once, you submit, we check our database for a record of your +organization.  ### **Step 3: Enter Admin Personal Access Token (First time only)** -If this is the first time you are signing up with your instance, we need an admin access token for setting up the CodeRabbit. +If this is the first time you are signing up with your instance, we need an +admin access token for setting up the CodeRabbit. #### **Generating Admin Personal Access token** -GitLab offers an option to generate a personal access token for adding a new user and setting up the application in the self-managed instance. To generate the token, please follow the process outlined below: +GitLab offers an option to generate a personal access token for adding a new +user and setting up the application in the self-managed instance. To generate +the token, please follow the process outlined below: 1. Login to your self-hosted instance. Ensure sure you have admin rights. 2. On the left sidebar, select your avatar. 3. Select Edit profile. 4. On the left sidebar, select Access Tokens. 5. Select Add new token. -6. Enter a name and expiry date for the token. We need this for the initial setup, so the minimum expiry time is sufficient. -7. If you do not enter an expiry date, the expiry date is automatically set to 365 days later than the current date. +6. Enter a name and expiry date for the token. We need this for the initial + setup, so the minimum expiry time is sufficient. +7. If you do not enter an expiry date, the expiry date is automatically set to + 365 days later than the current date. 8. Make sure, you select the scope: `api` 9. Select Create personal access token. 10. Please note down this token as this will be visible one time only @@ -63,11 +56,13 @@ GitLab offers an option to generate a personal access token for adding a new use - Submit the access token. - We will handle the setup process for you. -- On subsequent visits, your setup will be automatically detected, allowing for direct login. -  +- On subsequent visits, your setup will be automatically detected, allowing for + direct login.  ### **Step 5: Whitelist CodeRabbit IP address** -Use this CodeRabbit IP if your instance requires IP whitelisting `35.222.179.152/32` +Use this CodeRabbit IP if your instance requires IP whitelisting +`35.222.179.152/32` -- Furthermore, please refer to our Get Started Guide to make the most of CodeRabbit [here](../get-started/add-repo.md). +- Furthermore, please refer to our Get Started Guide to make the most of + CodeRabbit [here](../get-started/add-repo.md). diff --git a/docs/introduction/introduction.md b/docs/introduction/introduction.md index 3b9a505..0a8fa4a 100644 --- a/docs/introduction/introduction.md +++ b/docs/introduction/introduction.md @@ -2,54 +2,67 @@ id: introduction title: What is CodeRabbit? sidebar_label: Introduction -description: Accelerate Code Reviews with AI -image: "/preview_meta.jpg" +description: + CodeRabbit is an innovative, AI-first code reviewer. It provides context-aware + review feedback on a pull request within minutes, thereby significantly + reducing the time and effort associated with manual code reviews. slug: "/" --- -<head> - <meta charSet="utf-8" /> - <meta name="title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="description" content="Accelerate Code Reviews with AI" /> +**CodeRabbit** is an innovative, AI-first code reviewer. It provides +context-aware review feedback on a pull request within minutes, thereby +significantly reducing the time and effort associated with manual code reviews. +Secondly, it brings a different perspective to the reviews and finds issues +often missed by the human eye. Developers can chat with the bot within the code, +which allows them to provide additional context, ask questions, or have the bot +generate code. It learns from your suggestions and gets better overtime. - <meta property="og:type" content="website" /> - <meta property="og:url" content="https://coderabbit.ai/" /> - <meta property="og:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta property="og:description" content="Accelerate Code Reviews with AI" /> - <meta property="og:image" content="/preview_meta.jpg" /> - - <meta name="twitter:image" content="https://coderabbit.ai/preview_meta.jpg" /> - <meta name="twitter:card" content="summary_large_image" /> - <meta name="twitter:title" content="CodeRabbit: AI-powered Code Reviews" /> - <meta name="twitter:description" content="Accelerate Code Reviews with AI" /> -</head> - -**CodeRabbit** is an innovative, AI-first code reviewer. It provides context aware review feedback on a pull request within minutes, thereby significantly reducing the time and effort associated with manual code reviews. Secondly, it brings a different perspective to the reviews and finds issues often missed by the human eye. Developers can chat with the bot within the code, which allows them to provide additional context, ask questions, or have the bot generate code. It learns from your suggestions and gets better overtime. - -**CodeRabbit** seamlessly integrates with GitHub and GitLab repositories, performing continuous, incremental reviews for each commit within a pull request. Review feedback is sent back to the pull requests and can be directly committed. +**CodeRabbit** seamlessly integrates with GitHub and GitLab repositories, +performing continuous, incremental reviews for each commit within a pull +request. Review feedback is sent back to the pull requests and can be directly +committed. ### How does CodeRabbit work? -**CodeRabbit** integrates into code repositories using GitHub or GitLab webhooks and monitors events related to Pull Request (PR) and Merge Request (MR) changes. A comprehensive review is performed when a PR or MR is created, and for incremental commits and comments addressed to the bot. The feedback is then sent directly back to the PR or MR. +**CodeRabbit** integrates into code repositories using GitHub or GitLab webhooks +and monitors events related to Pull Request (PR) and Merge Request (MR) changes. +A comprehensive review is performed when a PR or MR is created, and for +incremental commits and comments addressed to the bot. The feedback is then sent +directly back to the PR or MR.  ### Data, Privacy, and Security -**CodeRabbit** does not use data collected during code reviews to train or influence the models. Queries to the Large Language Model (LLM) are ephemeral. Neither we nor the LLM we use share any data collected during the code review process with other third parties. +**CodeRabbit** does not use data collected during code reviews to train or +influence the models. Queries to the Large Language Model (LLM) are ephemeral. +Neither we nor the LLM we use share any data collected during the code review +process with other third parties. -Does CodeRabbit store my Data? We store embeddings of your conversations, which are used to improve future reviews for your organization. +Does CodeRabbit store my Data? We store embeddings of your conversations, which +are used to improve future reviews for your organization. -Compliance and Data Privacy: Your data is kept confidential, isolated by organization, and used only to improve your organization reviews. Data storage complies with SOC2 Type II, GDPR, and HIPAA standards. +Compliance and Data Privacy: Your data is kept confidential, isolated by the +organization, and used only to improve your organization reviews. Data storage +complies with SOC2 Type II, GDPR, and HIPAA standards. -Opting Out: You can choose to opt out of data storage at any time. Opting out won't affect your access but will limit the personalization of the reviews. +Opting Out: You can choose to opt out of data storage at any time. Opting out +won't affect your access but will limit the personalization of the reviews. ### Do you need CodeRabbit with the AI code generators or co-pilot? -Code reviews remain essential, whether the code is written by a human or a bot. This is mainly because the perspective of the reviewer differs from that of the code generator, whether human or machine. This distinction is precisely why human peer reviews have been effective for so long. While AI-powered code-generation tools hold immense potential, it's important to recognize that these generators are still in their early stages and may not be equipped to auto-generate meaningful code for moderately complex applications. +Code reviews remain essential, whether the code is written by a human or a bot. +This is mainly because the perspective of the reviewer differs from that of the +code generator, whether human or machine. This distinction is precisely why +human peer reviews have been effective for so long. While AI-powered +code-generation tools hold immense potential, it's important to recognize that +these generators are still in their early stages and may not be equipped to +auto-generate meaningful code for moderately complex applications. ### How is CodeRabbit different from existing code review tools? -Existing code review tools are good at linting and static code analysis; however, they lack context-aware, human-like review feedback. +Existing code review tools are good at linting and static code analysis; +however, they lack context-aware, human-like review feedback. -For information on how to get started with **CodeRabbit**, please visit the [Get Started page](./get-started/signup). +For information on how to get started with **CodeRabbit**, please visit the +[Get Started page](./get-started/signup). diff --git a/docusaurus.config.ts b/docusaurus.config.ts index a408bae..d84bb16 100644 --- a/docusaurus.config.ts +++ b/docusaurus.config.ts @@ -135,7 +135,7 @@ const config: Config = { }, // Declare some json-ld structured data ], - image: "img/docusaurus-social-card.jpg", + image: "img/preview.png", navbar: { title: "", hideOnScroll: true, diff --git a/src/components/HomepageFeatures/index.tsx b/src/components/HomepageFeatures/index.tsx index d67d1d7..f20b9b2 100644 --- a/src/components/HomepageFeatures/index.tsx +++ b/src/components/HomepageFeatures/index.tsx @@ -3,184 +3,178 @@ import clsx from "clsx"; import styles from "./styles.module.css"; type FeatureItem = { - title: string; - // Svg: React.ComponentType<React.ComponentProps<"svg">>; - description: JSX.Element; - img: string; - redirectTo: string; - chips: string[]; - date: string; - author: { name: string; img: string }[]; - authorImg: string; + title: string; + // Svg: React.ComponentType<React.ComponentProps<"svg">>; + description: JSX.Element; + img: string; + redirectTo: string; + chips: string[]; + date: string; + author: { name: string; img: string }[]; + authorImg: string; }; const FeatureList: FeatureItem[] = [ - // { - // title: "Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams", - // img: "img/blogs/blog4.jpeg", - // description: ( - // <> - // In a world where the office is just a step away from your bed, - // we dive into the challenges and triumphs of maintaining code - // quality across continents. - // </> - // ), - // redirectTo: "/blog/boosting-engineering-efficiency", - // chips: ["AI", "Remote teams", "Code Reviews"], - // date: "Nov 13, 2023", - // author: [ - // { - // name: "This Dot Labs", - // img: "https://images.crunchbase.com/image/upload/c_lpad,h_256,w_256,f_auto,q_auto:eco,dpr_1/og7xjpegm86zqz3mfo3s", - // }, - // ], - // authorImg: "img/blogs/blog4.jpeg", - // }, - // { - // title: "Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization", - // img: headImg3, - // description: ( - // <> - // How CodeRabbit uses Aperture to manage OpenAI rate limits with - // request prioritization - // </> - // ), - // redirectTo: "/blog/coderabbit-openai-rate-limits", - // chips: ["Rate limits", "Openai", "Prioritization"], - // date: "Oct 23, 2023", - // author: [ - // { name: "Gur Singh", img: gurImg }, - // { name: "Suman Kumar", img: sumanImg }, - // { - // name: "Nathan Gendron", - // img: "https://avatars.githubusercontent.com/u/10495562?v=4", - // }, - // ], - // authorImg: headImg, - // }, - // { - // title: "How AI Code Review reclaims your team’s time", - // img: headImg2, - // description: ( - // <> - // In the era of building and improving products fast, engineering - // managers encounter fresh challenges that render traditional - // strategies outdated. - // </> - // ), - // redirectTo: "/blog/ai-code-reviews-reclaims", - // chips: ["AI", "GitHub", "Code Reviews"], - // date: "Oct 5, 2023", - // author: [ - // { - // name: "Simone Cuomo", - // img: "https://media.licdn.com/dms/image/D4E03AQGnCY6ve8yozA/profile-displayphoto-shrink_400_400/0/1673905808955?e=1701907200&v=beta&t=tRqKsp-V6sHrf7wKUrw8YbLOZSF5DFXYbMsrRZW0Z2Y", - // }, - // ], - // authorImg: headImg, - // }, - // { - // title: "AI and the Future of Code Reviews: A Deep Dive Into CodeRabbit", - // img: headImg, - // description: ( - // <> - // We are witnessing an inflection point in the software - // development industry. Developers around the world have been - // realizing the incredible possibilities that AI can bring - // </> - // ), - // redirectTo: "/blog/coderabbit-deep-dive", - // chips: ["AI", "GitHub", "Code Reviews"], - // date: "Sept 4, 2023", - // author: [ - // { name: "Gur Singh", img: gurImg }, - // { name: "Vishu Kaur", img: vishuImg }, - // ], - // authorImg: headImg, - // }, + // { + // title: "Boosting Engineering Efficiency Using AI Code Reviews for Remote Teams", + // img: "img/blog/blog4.jpeg", + // description: ( + // <> + // In a world where the office is just a step away from your bed, + // we dive into the challenges and triumphs of maintaining code + // quality across continents. + // </> + // ), + // redirectTo: "/blog/boosting-engineering-efficiency", + // chips: ["AI", "Remote teams", "Code Reviews"], + // date: "Nov 13, 2023", + // author: [ + // { + // name: "This Dot Labs", + // img: "https://images.crunchbase.com/image/upload/c_lpad,h_256,w_256,f_auto,q_auto:eco,dpr_1/og7xjpegm86zqz3mfo3s", + // }, + // ], + // authorImg: "img/blog/blog4.jpeg", + // }, + // { + // title: "Squeezing Water from Stone: Managing OpenAI Rate Limits with Request Prioritization", + // img: headImg3, + // description: ( + // <> + // How CodeRabbit uses Aperture to manage OpenAI rate limits with + // request prioritization + // </> + // ), + // redirectTo: "/blog/coderabbit-openai-rate-limits", + // chips: ["Rate limits", "OpenAI", "Prioritization"], + // date: "Oct 23, 2023", + // author: [ + // { name: "Gur Singh", img: gurImg }, + // { name: "Suman Kumar", img: sumanImg }, + // { + // name: "Nathan Gendron", + // img: "https://avatars.githubusercontent.com/u/10495562?v=4", + // }, + // ], + // authorImg: headImg, + // }, + // { + // title: "How AI Code Review reclaims your team’s time", + // img: headImg2, + // description: ( + // <> + // In the era of building and improving products fast, engineering + // managers encounter fresh challenges that render traditional + // strategies outdated. + // </> + // ), + // redirectTo: "/blog/ai-code-reviews-reclaims", + // chips: ["AI", "GitHub", "Code Reviews"], + // date: "Oct 5, 2023", + // author: [ + // { + // name: "Simone Cuomo", + // img: "https://media.licdn.com/dms/image/D4E03AQGnCY6ve8yozA/profile-displayphoto-shrink_400_400/0/1673905808955?e=1701907200&v=beta&t=tRqKsp-V6sHrf7wKUrw8YbLOZSF5DFXYbMsrRZW0Z2Y", + // }, + // ], + // authorImg: headImg, + // }, + // { + // title: "AI and the Future of Code Reviews: A Deep Dive Into CodeRabbit", + // img: headImg, + // description: ( + // <> + // We are witnessing an inflection point in the software + // development industry. Developers around the world have been + // realizing the incredible possibilities that AI can bring + // </> + // ), + // redirectTo: "/blog/coderabbit-deep-dive", + // chips: ["AI", "GitHub", "Code Reviews"], + // date: "Sept 4, 2023", + // author: [ + // { name: "Gur Singh", img: gurImg }, + // { name: "Vishu Kaur", img: vishuImg }, + // ], + // authorImg: headImg, + // }, ]; function Feature({ - img, - title, - description, - redirectTo, - chips, - author, - date, - authorImg, + img, + title, + description, + redirectTo, + chips, + author, + date, + authorImg, }) { - return ( - <div className={[clsx("col col--3"), styles.featuresDiv].join(" ")}> - <Link to={redirectTo} className={styles.featuresLink}> - <div className="text--center"> - <img className={styles.featureSvg} src={img} /> - </div> - <div className={styles.featuresChipsDiv}> - {chips.map((chip) => ( - <span className={styles.featuresChips}>{chip}</span> - ))} - </div> - <div - className={[ - "padding-horiz--md", - styles.cardTextMaxHeight, - styles.padding2rem, - ].join(" ")} - > - <h3 className={styles.cardHeader}>{title}</h3> - <p className={styles.featuresPara}>{description}</p> - </div> - <div> - <span className={styles.dateText}>{date}</span> - </div> - <div className={styles.chipsDiv}> - {author.map((author) => ( - <div className={styles.authorDiv}> - <img - src={author.img} - className={styles.authorImg} - /> - <div className={styles.authorNameDiv}> - <span className={styles.authorText}> - {author.name} - </span> - </div> - </div> - ))} - </div> - </Link> + return ( + <div className={[clsx("col col--3"), styles.featuresDiv].join(" ")}> + <Link to={redirectTo} className={styles.featuresLink}> + <div className="text--center"> + <img className={styles.featureSvg} src={img} /> </div> - ); + <div className={styles.featuresChipsDiv}> + {chips.map((chip) => ( + <span className={styles.featuresChips}>{chip}</span> + ))} + </div> + <div + className={[ + "padding-horiz--md", + styles.cardTextMaxHeight, + styles.padding2rem, + ].join(" ")}> + <h3 className={styles.cardHeader}>{title}</h3> + <p className={styles.featuresPara}>{description}</p> + </div> + <div> + <span className={styles.dateText}>{date}</span> + </div> + <div className={styles.chipsDiv}> + {author.map((author) => ( + <div className={styles.authorDiv}> + <img src={author.img} className={styles.authorImg} /> + <div className={styles.authorNameDiv}> + <span className={styles.authorText}>{author.name}</span> + </div> + </div> + ))} + </div> + </Link> + </div> + ); } export default function HomepageFeatures(): JSX.Element { - return ( - <section className={styles.features}> - <div className="container"> - <div className="row"> - {FeatureList.map((props, idx) => ( - <Feature key={idx} {...props} /> - ))} - </div> - </div> - </section> + return ( + <section className={styles.features}> + <div className="container"> + <div className="row"> + {FeatureList.map((props, idx) => ( + <Feature key={idx} {...props} /> + ))} + </div> + </div> + </section> - // <div className="col--12 mainDiv"> - // <div className={styles.blogHeaderDiv}> - // <span className={styles.blogHeader}>Blog</span> - // <br /> - // <span className={styles.blogSubHeading}> - // {" "} - // Stay updated with the newest trends and insights in software - // development and the evolving world of AI.{" "} - // </span> - // </div> - // <div className={styles.flexContainer}> - // {FeatureList.map((props, idx) => ( - // <Feature key={idx} {...props} /> - // ))} - // </div> - // </div> - ); + // <div className="col--12 mainDiv"> + // <div className={styles.blogHeaderDiv}> + // <span className={styles.blogHeader}>Blog</span> + // <br /> + // <span className={styles.blogSubHeading}> + // {" "} + // Stay updated with the newest trends and insights in software + // development and the evolving world of AI.{" "} + // </span> + // </div> + // <div className={styles.flexContainer}> + // {FeatureList.map((props, idx) => ( + // <Feature key={idx} {...props} /> + // ))} + // </div> + // </div> + ); } diff --git a/static/img/blogs/BlogImage2.png b/static/img/blogs/BlogImage2.png deleted file mode 100644 index 994afe1..0000000 Binary files a/static/img/blogs/BlogImage2.png and /dev/null differ diff --git a/static/img/docusaurus-social-card.jpg b/static/img/docusaurus-social-card.jpg deleted file mode 100644 index ffcb448..0000000 Binary files a/static/img/docusaurus-social-card.jpg and /dev/null differ diff --git a/static/img/docusaurus.png b/static/img/docusaurus.png deleted file mode 100644 index f458149..0000000 Binary files a/static/img/docusaurus.png and /dev/null differ diff --git a/static/img/logo.svg b/static/img/logo.svg deleted file mode 100644 index 9db6d0d..0000000 --- a/static/img/logo.svg +++ /dev/null @@ -1 +0,0 @@ -<svg width="200" height="200" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path fill="#FFF" d="M99 52h84v34H99z"/><path d="M23 163c-7.398 0-13.843-4.027-17.303-10A19.886 19.886 0 0 0 3 163c0 11.046 8.954 20 20 20h20v-20H23z" fill="#3ECC5F"/><path d="M112.98 57.376L183 53V43c0-11.046-8.954-20-20-20H73l-2.5-4.33c-1.112-1.925-3.889-1.925-5 0L63 23l-2.5-4.33c-1.111-1.925-3.889-1.925-5 0L53 23l-2.5-4.33c-1.111-1.925-3.889-1.925-5 0L43 23c-.022 0-.042.003-.065.003l-4.142-4.141c-1.57-1.571-4.252-.853-4.828 1.294l-1.369 5.104-5.192-1.392c-2.148-.575-4.111 1.389-3.535 3.536l1.39 5.193-5.102 1.367c-2.148.576-2.867 3.259-1.296 4.83l4.142 4.142c0 .021-.003.042-.003.064l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 53l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 63l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 73l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 83l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 93l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 103l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 113l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 123l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 133l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 143l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 153l-4.33 2.5c-1.925 1.111-1.925 3.889 0 5L23 163c0 11.046 8.954 20 20 20h120c11.046 0 20-8.954 20-20V83l-70.02-4.376A10.645 10.645 0 0 1 103 68c0-5.621 4.37-10.273 9.98-10.624" fill="#3ECC5F"/><path fill="#3ECC5F" d="M143 183h30v-40h-30z"/><path d="M193 158c-.219 0-.428.037-.639.064-.038-.15-.074-.301-.116-.451A5 5 0 0 0 190.32 148a4.96 4.96 0 0 0-3.016 1.036 26.531 26.531 0 0 0-.335-.336 4.955 4.955 0 0 0 1.011-2.987 5 5 0 0 0-9.599-1.959c-.148-.042-.297-.077-.445-.115.027-.211.064-.42.064-.639a5 5 0 0 0-5-5 5 5 0 0 0-5 5c0 .219.037.428.064.639-.148.038-.297.073-.445.115a4.998 4.998 0 0 0-9.599 1.959c0 1.125.384 2.151 1.011 2.987-3.717 3.632-6.031 8.693-6.031 14.3 0 11.046 8.954 20 20 20 9.339 0 17.16-6.41 19.361-15.064.211.027.42.064.639.064a5 5 0 0 0 5-5 5 5 0 0 0-5-5" fill="#44D860"/><path fill="#3ECC5F" d="M153 123h30v-20h-30z"/><path d="M193 115.5a2.5 2.5 0 1 0 0-5c-.109 0-.214.019-.319.032-.02-.075-.037-.15-.058-.225a2.501 2.501 0 0 0-.963-4.807c-.569 0-1.088.197-1.508.518a6.653 6.653 0 0 0-.168-.168c.314-.417.506-.931.506-1.494a2.5 2.5 0 0 0-4.8-.979A9.987 9.987 0 0 0 183 103c-5.522 0-10 4.478-10 10s4.478 10 10 10c.934 0 1.833-.138 2.69-.377a2.5 2.5 0 0 0 4.8-.979c0-.563-.192-1.077-.506-1.494.057-.055.113-.111.168-.168.42.321.939.518 1.508.518a2.5 2.5 0 0 0 .963-4.807c.021-.074.038-.15.058-.225.105.013.21.032.319.032" fill="#44D860"/><path d="M63 55.5a2.5 2.5 0 0 1-2.5-2.5c0-4.136-3.364-7.5-7.5-7.5s-7.5 3.364-7.5 7.5a2.5 2.5 0 1 1-5 0c0-6.893 5.607-12.5 12.5-12.5S65.5 46.107 65.5 53a2.5 2.5 0 0 1-2.5 2.5" fill="#000"/><path d="M103 183h60c11.046 0 20-8.954 20-20V93h-60c-11.046 0-20 8.954-20 20v70z" fill="#FFFF50"/><path d="M168.02 124h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2m0 20h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2m0 20h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2m0-49.814h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2m0 19.814h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2m0 20h-50.04a1 1 0 1 1 0-2h50.04a1 1 0 1 1 0 2M183 61.611c-.012 0-.022-.006-.034-.005-3.09.105-4.552 3.196-5.842 5.923-1.346 2.85-2.387 4.703-4.093 4.647-1.889-.068-2.969-2.202-4.113-4.46-1.314-2.594-2.814-5.536-5.963-5.426-3.046.104-4.513 2.794-5.807 5.167-1.377 2.528-2.314 4.065-4.121 3.994-1.927-.07-2.951-1.805-4.136-3.813-1.321-2.236-2.848-4.75-5.936-4.664-2.994.103-4.465 2.385-5.763 4.4-1.373 2.13-2.335 3.428-4.165 3.351-1.973-.07-2.992-1.51-4.171-3.177-1.324-1.873-2.816-3.993-5.895-3.89-2.928.1-4.399 1.97-5.696 3.618-1.232 1.564-2.194 2.802-4.229 2.724a1 1 0 0 0-.072 2c3.017.101 4.545-1.8 5.872-3.487 1.177-1.496 2.193-2.787 4.193-2.855 1.926-.082 2.829 1.115 4.195 3.045 1.297 1.834 2.769 3.914 5.731 4.021 3.103.104 4.596-2.215 5.918-4.267 1.182-1.834 2.202-3.417 4.15-3.484 1.793-.067 2.769 1.35 4.145 3.681 1.297 2.197 2.766 4.686 5.787 4.796 3.125.108 4.634-2.62 5.949-5.035 1.139-2.088 2.214-4.06 4.119-4.126 1.793-.042 2.728 1.595 4.111 4.33 1.292 2.553 2.757 5.445 5.825 5.556l.169.003c3.064 0 4.518-3.075 5.805-5.794 1.139-2.41 2.217-4.68 4.067-4.773v-2z" fill="#000"/><path fill="#3ECC5F" d="M83 183h40v-40H83z"/><path d="M143 158c-.219 0-.428.037-.639.064-.038-.15-.074-.301-.116-.451A5 5 0 0 0 140.32 148a4.96 4.96 0 0 0-3.016 1.036 26.531 26.531 0 0 0-.335-.336 4.955 4.955 0 0 0 1.011-2.987 5 5 0 0 0-9.599-1.959c-.148-.042-.297-.077-.445-.115.027-.211.064-.42.064-.639a5 5 0 0 0-5-5 5 5 0 0 0-5 5c0 .219.037.428.064.639-.148.038-.297.073-.445.115a4.998 4.998 0 0 0-9.599 1.959c0 1.125.384 2.151 1.011 2.987-3.717 3.632-6.031 8.693-6.031 14.3 0 11.046 8.954 20 20 20 9.339 0 17.16-6.41 19.361-15.064.211.027.42.064.639.064a5 5 0 0 0 5-5 5 5 0 0 0-5-5" fill="#44D860"/><path fill="#3ECC5F" d="M83 123h40v-20H83z"/><path d="M133 115.5a2.5 2.5 0 1 0 0-5c-.109 0-.214.019-.319.032-.02-.075-.037-.15-.058-.225a2.501 2.501 0 0 0-.963-4.807c-.569 0-1.088.197-1.508.518a6.653 6.653 0 0 0-.168-.168c.314-.417.506-.931.506-1.494a2.5 2.5 0 0 0-4.8-.979A9.987 9.987 0 0 0 123 103c-5.522 0-10 4.478-10 10s4.478 10 10 10c.934 0 1.833-.138 2.69-.377a2.5 2.5 0 0 0 4.8-.979c0-.563-.192-1.077-.506-1.494.057-.055.113-.111.168-.168.42.321.939.518 1.508.518a2.5 2.5 0 0 0 .963-4.807c.021-.074.038-.15.058-.225.105.013.21.032.319.032" fill="#44D860"/><path d="M143 41.75c-.16 0-.33-.02-.49-.05a2.52 2.52 0 0 1-.47-.14c-.15-.06-.29-.14-.431-.23-.13-.09-.259-.2-.38-.31-.109-.12-.219-.24-.309-.38s-.17-.28-.231-.43a2.619 2.619 0 0 1-.189-.96c0-.16.02-.33.05-.49.03-.16.08-.31.139-.47.061-.15.141-.29.231-.43.09-.13.2-.26.309-.38.121-.11.25-.22.38-.31.141-.09.281-.17.431-.23.149-.06.31-.11.47-.14.32-.07.65-.07.98 0 .159.03.32.08.47.14.149.06.29.14.43.23.13.09.259.2.38.31.11.12.22.25.31.38.09.14.17.28.23.43.06.16.11.31.14.47.029.16.05.33.05.49 0 .66-.271 1.31-.73 1.77-.121.11-.25.22-.38.31-.14.09-.281.17-.43.23a2.565 2.565 0 0 1-.96.19m20-1.25c-.66 0-1.3-.27-1.771-.73a3.802 3.802 0 0 1-.309-.38c-.09-.14-.17-.28-.231-.43a2.619 2.619 0 0 1-.189-.96c0-.66.27-1.3.729-1.77.121-.11.25-.22.38-.31.141-.09.281-.17.431-.23.149-.06.31-.11.47-.14.32-.07.66-.07.98 0 .159.03.32.08.47.14.149.06.29.14.43.23.13.09.259.2.38.31.459.47.73 1.11.73 1.77 0 .16-.021.33-.05.49-.03.16-.08.32-.14.47-.07.15-.14.29-.23.43-.09.13-.2.26-.31.38-.121.11-.25.22-.38.31-.14.09-.281.17-.43.23a2.565 2.565 0 0 1-.96.19" fill="#000"/></g></svg> \ No newline at end of file diff --git a/static/img/preview.png b/static/img/preview.png new file mode 100644 index 0000000..c8e7653 Binary files /dev/null and b/static/img/preview.png differ diff --git a/static/img/test.svg b/static/img/test.svg deleted file mode 100644 index fc33b41..0000000 --- a/static/img/test.svg +++ /dev/null @@ -1,5 +0,0 @@ -<svg width="6022" height="2624" viewBox="0 0 6022 2624" fill="none" xmlns="http://www.w3.org/2000/svg"> -<rect width="6021" height="2623" transform="translate(0.390625 0.390381)" fill="#FAFAFA"/> -<path fill-rule="evenodd" clip-rule="evenodd" d="M1746.66 1363.49C1746.66 1494.69 1690.66 1613.3 1600.87 1695.8H1492.53C1494.85 1685.2 1489.22 1677.91 1481.93 1672.94C1466.69 1662.34 1457.08 1644.78 1459.4 1626.56C1465.36 1578.52 1494.52 1517.22 1600.87 1460.9C1672.77 1422.46 1686.02 1343.28 1690.99 1331.68C1698.28 1312.46 1696.3 1296.23 1681.05 1280.66C1653.55 1252.49 1623.74 1226.98 1587.62 1210.42C1536.93 1186.56 1485.24 1187.89 1433.89 1207.1C1424.94 1210.42 1426.93 1203.46 1426.27 1200.48C1419.31 1166.68 1407.71 1134.21 1391.15 1103.73C1357.68 1043.43 1310.97 999.033 1241.39 984.123C1231.12 981.804 1220.52 981.141 1209.91 979.816C1204.94 979.153 1202.29 980.479 1203.62 986.442C1212.9 1030.84 1225.82 1073.58 1253.98 1110.03C1266.9 1126.92 1284.46 1138.19 1301.69 1149.78C1319.91 1162.37 1339.13 1173.97 1356.36 1188.22C1372.59 1202.13 1385.85 1218.37 1392.14 1241.56C1389.82 1239.24 1388.83 1238.58 1388.17 1237.58C1335.15 1153.43 1231.45 1116.32 1127.08 1146.8C1117.48 1149.45 1118.8 1152.77 1123.44 1159.72C1153.59 1206.11 1195 1239.24 1244.04 1264.75C1280.49 1283.64 1318.26 1299.21 1359.34 1304.51C1377.89 1306.83 1368.95 1319.42 1371.93 1334.33C1375.91 1357.52 1385.52 1364.81 1382.2 1362.82C1319.25 1337.64 1266.9 1327.7 1223.5 1327.7C1044.25 1327.7 1015.1 1498.67 1016.42 1500.65C1013.77 1499.66 970.699 1483.76 961.091 1526.83C951.151 1570.56 1009.8 1599.06 1009.8 1599.06C1017.42 1547.37 1063.8 1536.11 1069.43 1534.78C1064.79 1537.43 1034.64 1554.99 1025.37 1603.03C1017.42 1645.44 1050.88 1682.88 1063.47 1695.8H989.253C899.796 1613.3 843.803 1494.69 843.803 1363.49C843.803 1114 1045.58 911.895 1295.06 911.895C1544.55 911.895 1746.66 1114 1746.66 1363.49ZM1418.65 1695.8H1370.94C1373.26 1693.48 1374.91 1690.17 1375.58 1686.53C1379.55 1663.33 1359.67 1658.7 1359.67 1658.7H1249.67C1249.67 1658.7 1293.41 1656.71 1333.5 1640.14C1373.26 1623.24 1405.39 1593.76 1411.03 1585.8C1392.47 1629.54 1401.42 1666.32 1409.04 1684.87C1410.7 1689.51 1414.34 1693.48 1418.65 1695.8Z" fill="#FF8B53"/> -<path d="M2112.76 1594.26C2070.23 1594.26 2032.61 1584.85 1999.89 1566.04C1967.59 1546.82 1942.03 1520.65 1923.22 1487.53C1904.82 1453.99 1895.62 1415.55 1895.62 1372.21C1895.62 1328.86 1904.82 1290.63 1923.22 1257.5C1942.03 1223.97 1967.59 1197.8 1999.89 1178.99C2032.61 1159.77 2070.23 1150.16 2112.76 1150.16C2143.84 1150.16 2172.26 1155.68 2198.02 1166.72C2224.19 1177.35 2246.68 1192.48 2265.49 1212.11C2284.71 1231.74 2299.43 1254.44 2309.66 1280.2L2217.03 1311.48C2210.9 1297.17 2202.52 1284.7 2191.88 1274.07C2181.66 1263.43 2169.8 1255.26 2156.31 1249.53C2143.22 1243.81 2128.7 1240.94 2112.76 1240.94C2090.27 1240.94 2070.23 1246.46 2052.64 1257.5C2035.06 1268.55 2021.36 1284.08 2011.55 1304.12C2001.73 1323.75 1996.83 1346.45 1996.83 1372.21C1996.83 1397.97 2001.73 1420.87 2011.55 1440.91C2021.77 1460.54 2035.67 1476.08 2053.26 1487.53C2071.25 1498.57 2091.7 1504.09 2114.6 1504.09C2131.36 1504.09 2146.29 1501.02 2159.37 1494.89C2172.46 1488.75 2183.71 1480.16 2193.11 1469.12C2202.93 1458.08 2211.31 1445.41 2218.26 1431.09L2310.88 1462.38C2301.07 1488.55 2286.55 1511.65 2267.33 1531.69C2248.11 1551.32 2225.42 1566.65 2199.24 1577.69C2173.07 1588.74 2144.24 1594.26 2112.76 1594.26ZM2478.07 1594.26C2445.76 1594.26 2417.34 1587.51 2392.81 1574.01C2368.27 1560.11 2348.85 1541.1 2334.54 1516.97C2320.63 1492.84 2313.68 1465.03 2313.68 1433.55C2313.68 1402.06 2320.43 1374.25 2333.92 1350.13C2347.83 1326 2367.05 1307.19 2391.58 1293.69C2416.53 1279.79 2444.74 1272.84 2476.23 1272.84C2508.53 1272.84 2536.95 1279.79 2561.49 1293.69C2586.43 1307.19 2605.65 1326 2619.15 1350.13C2633.05 1374.25 2640 1402.06 2640 1433.55C2640 1465.03 2633.05 1492.84 2619.15 1516.97C2605.65 1541.1 2586.64 1560.11 2562.1 1574.01C2537.57 1587.51 2509.56 1594.26 2478.07 1594.26ZM2478.07 1505.93C2490.34 1505.93 2501.17 1502.86 2510.58 1496.73C2520.39 1490.59 2527.96 1482.21 2533.27 1471.58C2539 1460.54 2541.86 1447.86 2541.86 1433.55C2541.86 1419.23 2539 1406.76 2533.27 1396.13C2527.96 1385.09 2520.39 1376.5 2510.58 1370.37C2500.76 1364.23 2489.52 1361.17 2476.84 1361.17C2464.17 1361.17 2452.92 1364.23 2443.11 1370.37C2433.29 1376.5 2425.52 1385.09 2419.8 1396.13C2414.48 1406.76 2411.82 1419.23 2411.82 1433.55C2411.82 1447.86 2414.48 1460.54 2419.8 1471.58C2425.52 1482.21 2433.29 1490.59 2443.11 1496.73C2453.33 1502.86 2464.98 1505.93 2478.07 1505.93ZM2876.18 1586.89L2871.88 1529.85V1157.52H2967.57V1586.89H2876.18ZM2784.78 1594.26C2756.16 1594.26 2731.42 1587.92 2710.56 1575.24C2690.12 1562.15 2674.17 1543.55 2662.72 1519.42C2651.68 1495.3 2646.16 1466.67 2646.16 1433.55C2646.16 1400.02 2651.68 1371.39 2662.72 1347.67C2674.17 1323.55 2690.12 1305.14 2710.56 1292.47C2731.42 1279.38 2756.16 1272.84 2784.78 1272.84C2810.14 1272.84 2831.4 1279.38 2848.58 1292.47C2866.16 1305.14 2879.25 1323.55 2887.83 1347.67C2896.42 1371.39 2900.71 1400.02 2900.71 1433.55C2900.71 1466.67 2896.42 1495.3 2887.83 1519.42C2879.25 1543.55 2866.16 1562.15 2848.58 1575.24C2831.4 1587.92 2810.14 1594.26 2784.78 1594.26ZM2809.93 1505.93C2821.79 1505.93 2832.42 1502.86 2841.83 1496.73C2851.23 1490.59 2858.59 1482.21 2863.91 1471.58C2869.23 1460.54 2871.88 1447.86 2871.88 1433.55C2871.88 1419.23 2869.23 1406.76 2863.91 1396.13C2858.59 1385.09 2851.23 1376.5 2841.83 1370.37C2832.42 1364.23 2821.59 1361.17 2809.32 1361.17C2797.05 1361.17 2786.21 1364.23 2776.81 1370.37C2767.4 1376.5 2759.84 1385.09 2754.11 1396.13C2748.8 1406.76 2745.94 1419.23 2745.53 1433.55C2745.94 1447.86 2748.8 1460.54 2754.11 1471.58C2759.84 1482.21 2767.4 1490.59 2776.81 1496.73C2786.62 1502.86 2797.66 1505.93 2809.93 1505.93ZM3152.58 1594.26C3120.68 1594.26 3092.47 1587.51 3067.93 1574.01C3043.39 1560.52 3024.17 1541.71 3010.27 1517.58C2996.37 1493.46 2989.42 1465.44 2989.42 1433.55C2989.42 1401.65 2996.37 1373.64 3010.27 1349.51C3024.17 1325.39 3043.39 1306.58 3067.93 1293.08C3092.87 1279.59 3121.5 1272.84 3153.8 1272.84C3182.84 1272.84 3209.01 1279.79 3232.32 1293.69C3255.63 1307.6 3274.03 1328.45 3287.52 1356.26C3301.43 1383.66 3308.38 1417.6 3308.38 1458.08H3077.74L3088.17 1446.43C3088.17 1460.33 3091.03 1472.6 3096.76 1483.23C3102.48 1493.86 3110.46 1502.04 3120.68 1507.77C3130.9 1513.08 3142.35 1515.74 3155.03 1515.74C3170.16 1515.74 3182.84 1512.47 3193.06 1505.93C3203.28 1498.98 3210.44 1490.39 3214.53 1480.16L3299.79 1508.99C3291.61 1528.62 3279.96 1544.78 3264.83 1557.45C3250.11 1570.13 3233.14 1579.53 3213.92 1585.67C3194.7 1591.39 3174.25 1594.26 3152.58 1594.26ZM3090.63 1407.17L3080.81 1394.29H3218.21L3209.01 1407.17C3209.01 1391.63 3205.94 1379.57 3199.81 1370.98C3193.68 1361.99 3186.11 1355.44 3177.11 1351.35C3168.53 1347.26 3159.73 1345.22 3150.74 1345.22C3141.74 1345.22 3132.54 1347.26 3123.14 1351.35C3114.14 1355.44 3106.37 1361.99 3099.83 1370.98C3093.69 1379.57 3090.63 1391.63 3090.63 1407.17ZM3334.49 1586.89V1157.52H3503.17C3534.25 1157.52 3561.85 1163.66 3585.98 1175.92C3610.11 1187.78 3628.92 1204.55 3642.41 1226.22C3656.32 1247.49 3663.27 1272.02 3663.27 1299.83C3663.27 1327.64 3656.32 1352.38 3642.41 1374.05C3628.51 1395.72 3609.29 1412.69 3584.75 1424.96C3560.63 1436.82 3532.82 1442.75 3501.33 1442.75H3433.25V1586.89H3334.49ZM3567.58 1586.89L3470.66 1416.37L3544.88 1361.78L3680.44 1586.89H3567.58ZM3433.25 1351.97H3500.11C3511.56 1351.97 3521.78 1349.72 3530.78 1345.22C3539.77 1340.72 3546.72 1334.59 3551.63 1326.82C3556.95 1318.64 3559.61 1309.64 3559.61 1299.83C3559.61 1284.7 3553.88 1272.23 3542.43 1262.41C3531.39 1252.6 3516.67 1247.69 3498.27 1247.69H3433.25V1351.97ZM3883.04 1586.89L3879.98 1520.65V1434.16C3879.98 1417.8 3878.55 1403.49 3875.68 1391.22C3873.23 1378.96 3868.12 1369.55 3860.35 1363.01C3852.99 1356.06 3842.15 1352.58 3827.84 1352.58C3816.39 1352.58 3806.37 1355.24 3797.78 1360.55C3789.2 1365.87 3781.84 1373.03 3775.7 1382.02L3691.67 1354.42C3699.03 1339.29 3708.64 1325.59 3720.5 1313.32C3732.76 1301.05 3747.69 1291.24 3765.27 1283.88C3782.86 1276.52 3803.3 1272.84 3826.61 1272.84C3858.51 1272.84 3885.5 1278.77 3907.58 1290.63C3929.66 1302.49 3946.22 1319.05 3957.26 1340.31C3968.31 1361.58 3973.83 1386.73 3973.83 1415.76L3972.6 1586.89H3883.04ZM3799.01 1594.26C3763.02 1594.26 3735.01 1586.28 3714.98 1570.33C3694.94 1553.98 3684.92 1530.67 3684.92 1500.41C3684.92 1468.1 3695.35 1443.97 3716.2 1428.03C3737.06 1412.08 3766.3 1404.1 3803.92 1404.1H3887.95V1466.06H3839.49C3819.46 1466.06 3804.94 1468.92 3795.94 1474.64C3786.95 1479.96 3782.45 1487.73 3782.45 1497.95C3782.45 1505.31 3785.72 1511.24 3792.26 1515.74C3799.21 1519.83 3808.62 1521.88 3820.48 1521.88C3832.34 1521.88 3842.56 1519.42 3851.15 1514.51C3860.14 1509.2 3867.1 1502.25 3872 1493.66C3877.32 1485.07 3879.98 1475.87 3879.98 1466.06H3904.51C3904.51 1506.54 3895.72 1538.03 3878.14 1560.52C3860.96 1583.01 3834.59 1594.26 3799.01 1594.26ZM4007.59 1586.89V1157.52H4103.28V1529.85L4098.37 1586.89H4007.59ZM4190.38 1594.26C4165.02 1594.26 4143.76 1587.92 4126.58 1575.24C4109.41 1562.15 4096.53 1543.55 4087.94 1519.42C4079.35 1495.3 4075.06 1466.67 4075.06 1433.55C4075.06 1400.02 4079.35 1371.39 4087.94 1347.67C4096.53 1323.55 4109.41 1305.14 4126.58 1292.47C4143.76 1279.38 4165.02 1272.84 4190.38 1272.84C4219 1272.84 4243.74 1279.38 4264.6 1292.47C4285.45 1305.14 4301.4 1323.55 4312.44 1347.67C4323.48 1371.39 4329 1400.02 4329 1433.55C4329 1466.67 4323.48 1495.3 4312.44 1519.42C4301.4 1543.55 4285.45 1562.15 4264.6 1575.24C4243.74 1587.92 4219 1594.26 4190.38 1594.26ZM4165.84 1505.93C4178.11 1505.93 4188.95 1502.86 4198.35 1496.73C4207.76 1490.59 4215.32 1482.21 4221.05 1471.58C4226.77 1460.54 4229.63 1447.86 4229.63 1433.55C4229.63 1419.23 4226.98 1406.76 4221.66 1396.13C4216.34 1385.09 4208.78 1376.5 4198.96 1370.37C4189.56 1364.23 4178.72 1361.17 4166.45 1361.17C4154.19 1361.17 4143.15 1364.23 4133.33 1370.37C4123.93 1376.5 4116.57 1385.09 4111.25 1396.13C4105.93 1407.17 4103.28 1419.64 4103.28 1433.55C4103.28 1447.86 4105.93 1460.54 4111.25 1471.58C4116.57 1482.21 4123.93 1490.59 4133.33 1496.73C4142.74 1502.86 4153.57 1505.93 4165.84 1505.93ZM4350.85 1586.89V1157.52H4446.53V1529.85L4441.63 1586.89H4350.85ZM4533.64 1594.26C4508.28 1594.26 4487.02 1587.92 4469.84 1575.24C4452.67 1562.15 4439.79 1543.55 4431.2 1519.42C4422.61 1495.3 4418.32 1466.67 4418.32 1433.55C4418.32 1400.02 4422.61 1371.39 4431.2 1347.67C4439.79 1323.55 4452.67 1305.14 4469.84 1292.47C4487.02 1279.38 4508.28 1272.84 4533.64 1272.84C4562.26 1272.84 4587 1279.38 4607.86 1292.47C4628.71 1305.14 4644.66 1323.55 4655.7 1347.67C4666.74 1371.39 4672.26 1400.02 4672.26 1433.55C4672.26 1466.67 4666.74 1495.3 4655.7 1519.42C4644.66 1543.55 4628.71 1562.15 4607.86 1575.24C4587 1587.92 4562.26 1594.26 4533.64 1594.26ZM4509.1 1505.93C4521.37 1505.93 4532.2 1502.86 4541.61 1496.73C4551.02 1490.59 4558.58 1482.21 4564.31 1471.58C4570.03 1460.54 4572.89 1447.86 4572.89 1433.55C4572.89 1419.23 4570.23 1406.76 4564.92 1396.13C4559.6 1385.09 4552.04 1376.5 4542.22 1370.37C4532.82 1364.23 4521.98 1361.17 4509.71 1361.17C4497.45 1361.17 4486.4 1364.23 4476.59 1370.37C4467.19 1376.5 4459.82 1385.09 4454.51 1396.13C4449.19 1407.17 4446.53 1419.64 4446.53 1433.55C4446.53 1447.86 4449.19 1460.54 4454.51 1471.58C4459.82 1482.21 4467.19 1490.59 4476.59 1496.73C4486 1502.86 4496.83 1505.93 4509.1 1505.93ZM4699.63 1586.89V1280.2H4795.31V1586.89H4699.63ZM4747.47 1240.94C4733.16 1240.94 4720.48 1235.63 4709.44 1224.99C4698.81 1213.95 4693.49 1201.28 4693.49 1186.96C4693.49 1171.83 4698.81 1159.16 4709.44 1148.93C4720.48 1138.3 4733.16 1132.99 4747.47 1132.99C4762.19 1132.99 4774.87 1138.3 4785.5 1148.93C4796.13 1159.16 4801.45 1171.83 4801.45 1186.96C4801.45 1201.28 4796.13 1213.95 4785.5 1224.99C4774.87 1235.63 4762.19 1240.94 4747.47 1240.94ZM4970.97 1594.26C4934.57 1594.26 4907.38 1585.67 4889.39 1568.49C4871.8 1550.91 4863.01 1525.96 4863.01 1493.66V1184.51H4958.7V1469.74C4958.7 1482.01 4960.95 1491 4965.45 1496.73C4969.95 1502.45 4976.9 1505.31 4986.3 1505.31C4989.98 1505.31 4994.28 1504.5 4999.18 1502.86C5004.09 1500.82 5008.59 1498.36 5012.68 1495.5L5045.8 1565.43C5035.99 1573.6 5024.13 1580.56 5010.23 1586.28C4996.73 1591.6 4983.65 1594.26 4970.97 1594.26ZM4815.17 1360.55V1280.2H5028.63V1360.55H4815.17Z" fill="#FF8B53"/> -</svg> diff --git a/static/img/undraw_docusaurus_mountain.svg b/static/img/undraw_docusaurus_mountain.svg deleted file mode 100644 index af961c4..0000000 --- a/static/img/undraw_docusaurus_mountain.svg +++ /dev/null @@ -1,171 +0,0 @@ -<svg xmlns="http://www.w3.org/2000/svg" width="1088" height="687.962" viewBox="0 0 1088 687.962"> - <title>Easy to Use</title> - <g id="Group_12" data-name="Group 12" transform="translate(-57 -56)"> - <g id="Group_11" data-name="Group 11" transform="translate(57 56)"> - <path id="Path_83" data-name="Path 83" d="M1017.81,560.461c-5.27,45.15-16.22,81.4-31.25,110.31-20,38.52-54.21,54.04-84.77,70.28a193.275,193.275,0,0,1-27.46,11.94c-55.61,19.3-117.85,14.18-166.74,3.99a657.282,657.282,0,0,0-104.09-13.16q-14.97-.675-29.97-.67c-15.42.02-293.07,5.29-360.67-131.57-16.69-33.76-28.13-75-32.24-125.27-11.63-142.12,52.29-235.46,134.74-296.47,155.97-115.41,369.76-110.57,523.43,7.88C941.15,276.621,1036.99,396.031,1017.81,560.461Z" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_84" data-name="Path 84" d="M986.56,670.771c-20,38.52-47.21,64.04-77.77,80.28a193.272,193.272,0,0,1-27.46,11.94c-55.61,19.3-117.85,14.18-166.74,3.99a657.3,657.3,0,0,0-104.09-13.16q-14.97-.675-29.97-.67-23.13.03-46.25,1.72c-100.17,7.36-253.82-6.43-321.42-143.29L382,283.981,444.95,445.6l20.09,51.59,55.37-75.98L549,381.981l130.2,149.27,36.8-81.27L970.78,657.9l14.21,11.59Z" transform="translate(-56 -106.019)" fill="#f2f2f2"/> - <path id="Path_85" data-name="Path 85" d="M302,282.962l26-57,36,83-31-60Z" opacity="0.1"/> - <path id="Path_86" data-name="Path 86" d="M610.5,753.821q-14.97-.675-29.97-.67L465.04,497.191Z" transform="translate(-56 -106.019)" opacity="0.1"/> - <path id="Path_87" data-name="Path 87" d="M464.411,315.191,493,292.962l130,150-132-128Z" opacity="0.1"/> - <path id="Path_88" data-name="Path 88" d="M908.79,751.051a193.265,193.265,0,0,1-27.46,11.94L679.2,531.251Z" transform="translate(-56 -106.019)" opacity="0.1"/> - <circle id="Ellipse_11" data-name="Ellipse 11" cx="3" cy="3" r="3" transform="translate(479 98.962)" fill="#f2f2f2"/> - <circle id="Ellipse_12" data-name="Ellipse 12" cx="3" cy="3" r="3" transform="translate(396 201.962)" fill="#f2f2f2"/> - <circle id="Ellipse_13" data-name="Ellipse 13" cx="2" cy="2" r="2" transform="translate(600 220.962)" fill="#f2f2f2"/> - <circle id="Ellipse_14" data-name="Ellipse 14" cx="2" cy="2" r="2" transform="translate(180 265.962)" fill="#f2f2f2"/> - <circle id="Ellipse_15" data-name="Ellipse 15" cx="2" cy="2" r="2" transform="translate(612 96.962)" fill="#f2f2f2"/> - <circle id="Ellipse_16" data-name="Ellipse 16" cx="2" cy="2" r="2" transform="translate(736 192.962)" fill="#f2f2f2"/> - <circle id="Ellipse_17" data-name="Ellipse 17" cx="2" cy="2" r="2" transform="translate(858 344.962)" fill="#f2f2f2"/> - <path id="Path_89" data-name="Path 89" d="M306,121.222h-2.76v-2.76h-1.48v2.76H299V122.7h2.76v2.759h1.48V122.7H306Z" fill="#f2f2f2"/> - <path id="Path_90" data-name="Path 90" d="M848,424.222h-2.76v-2.76h-1.48v2.76H841V425.7h2.76v2.759h1.48V425.7H848Z" fill="#f2f2f2"/> - <path id="Path_91" data-name="Path 91" d="M1144,719.981c0,16.569-243.557,74-544,74s-544-57.431-544-74,243.557,14,544,14S1144,703.413,1144,719.981Z" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_92" data-name="Path 92" d="M1144,719.981c0,16.569-243.557,74-544,74s-544-57.431-544-74,243.557,14,544,14S1144,703.413,1144,719.981Z" transform="translate(-56 -106.019)" opacity="0.1"/> - <ellipse id="Ellipse_18" data-name="Ellipse 18" cx="544" cy="30" rx="544" ry="30" transform="translate(0 583.962)" fill="#3f3d56"/> - <path id="Path_93" data-name="Path 93" d="M624,677.981c0,33.137-14.775,24-33,24s-33,9.137-33-24,33-96,33-96S624,644.844,624,677.981Z" transform="translate(-56 -106.019)" fill="#ff6584"/> - <path id="Path_94" data-name="Path 94" d="M606,690.66c0,15.062-6.716,10.909-15,10.909s-15,4.153-15-10.909,15-43.636,15-43.636S606,675.6,606,690.66Z" transform="translate(-56 -106.019)" opacity="0.1"/> - <rect id="Rectangle_97" data-name="Rectangle 97" width="92" height="18" rx="9" transform="translate(489 604.962)" fill="#2f2e41"/> - <rect id="Rectangle_98" data-name="Rectangle 98" width="92" height="18" rx="9" transform="translate(489 586.962)" fill="#2f2e41"/> - <path id="Path_95" data-name="Path 95" d="M193,596.547c0,55.343,34.719,100.126,77.626,100.126" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_96" data-name="Path 96" d="M270.626,696.673c0-55.965,38.745-101.251,86.626-101.251" transform="translate(-56 -106.019)" fill="#6c63ff"/> - <path id="Path_97" data-name="Path 97" d="M221.125,601.564c0,52.57,22.14,95.109,49.5,95.109" transform="translate(-56 -106.019)" fill="#6c63ff"/> - <path id="Path_98" data-name="Path 98" d="M270.626,696.673c0-71.511,44.783-129.377,100.126-129.377" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_99" data-name="Path 99" d="M254.3,697.379s11.009-.339,14.326-2.7,16.934-5.183,17.757-1.395,16.544,18.844,4.115,18.945-28.879-1.936-32.19-3.953S254.3,697.379,254.3,697.379Z" transform="translate(-56 -106.019)" fill="#a8a8a8"/> - <path id="Path_100" data-name="Path 100" d="M290.716,710.909c-12.429.1-28.879-1.936-32.19-3.953-2.522-1.536-3.527-7.048-3.863-9.591l-.368.014s.7,8.879,4.009,10.9,19.761,4.053,32.19,3.953c3.588-.029,4.827-1.305,4.759-3.2C294.755,710.174,293.386,710.887,290.716,710.909Z" transform="translate(-56 -106.019)" opacity="0.2"/> - <path id="Path_101" data-name="Path 101" d="M777.429,633.081c0,38.029,23.857,68.8,53.341,68.8" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_102" data-name="Path 102" d="M830.769,701.882c0-38.456,26.623-69.575,59.525-69.575" transform="translate(-56 -106.019)" fill="#6c63ff"/> - <path id="Path_103" data-name="Path 103" d="M796.755,636.528c0,36.124,15.213,65.354,34.014,65.354" transform="translate(-56 -106.019)" fill="#6c63ff"/> - <path id="Path_104" data-name="Path 104" d="M830.769,701.882c0-49.139,30.773-88.9,68.8-88.9" transform="translate(-56 -106.019)" fill="#3f3d56"/> - <path id="Path_105" data-name="Path 105" d="M819.548,702.367s7.565-.233,9.844-1.856,11.636-3.562,12.2-.958,11.368,12.949,2.828,13.018-19.844-1.33-22.119-2.716S819.548,702.367,819.548,702.367Z" transform="translate(-56 -106.019)" fill="#a8a8a8"/> - <path id="Path_106" data-name="Path 106" d="M844.574,711.664c-8.54.069-19.844-1.33-22.119-2.716-1.733-1.056-2.423-4.843-2.654-6.59l-.253.01s.479,6.1,2.755,7.487,13.579,2.785,22.119,2.716c2.465-.02,3.317-.9,3.27-2.2C847.349,711.159,846.409,711.649,844.574,711.664Z" transform="translate(-56 -106.019)" opacity="0.2"/> - <path id="Path_107" data-name="Path 107" d="M949.813,724.718s11.36-1.729,14.5-4.591,16.89-7.488,18.217-3.667,19.494,17.447,6.633,19.107-30.153,1.609-33.835-.065S949.813,724.718,949.813,724.718Z" transform="translate(-56 -106.019)" fill="#a8a8a8"/> - <path id="Path_108" data-name="Path 108" d="M989.228,734.173c-12.86,1.659-30.153,1.609-33.835-.065-2.8-1.275-4.535-6.858-5.2-9.45l-.379.061s1.833,9.109,5.516,10.783,20.975,1.725,33.835.065c3.712-.479,4.836-1.956,4.529-3.906C993.319,732.907,991.991,733.817,989.228,734.173Z" transform="translate(-56 -106.019)" opacity="0.2"/> - <path id="Path_109" data-name="Path 109" d="M670.26,723.9s9.587-1.459,12.237-3.875,14.255-6.32,15.374-3.095,16.452,14.725,5.6,16.125-25.448,1.358-28.555-.055S670.26,723.9,670.26,723.9Z" transform="translate(-56 -106.019)" fill="#a8a8a8"/> - <path id="Path_110" data-name="Path 110" d="M703.524,731.875c-10.853,1.4-25.448,1.358-28.555-.055-2.367-1.076-3.827-5.788-4.39-7.976l-.32.051s1.547,7.687,4.655,9.1,17.7,1.456,28.555.055c3.133-.4,4.081-1.651,3.822-3.3C706.977,730.807,705.856,731.575,703.524,731.875Z" transform="translate(-56 -106.019)" opacity="0.2"/> - <path id="Path_111" data-name="Path 111" d="M178.389,719.109s7.463-1.136,9.527-3.016,11.1-4.92,11.969-2.409,12.808,11.463,4.358,12.553-19.811,1.057-22.23-.043S178.389,719.109,178.389,719.109Z" transform="translate(-56 -106.019)" fill="#a8a8a8"/> - <path id="Path_112" data-name="Path 112" d="M204.285,725.321c-8.449,1.09-19.811,1.057-22.23-.043-1.842-.838-2.979-4.506-3.417-6.209l-.249.04s1.2,5.984,3.624,7.085,13.781,1.133,22.23.043c2.439-.315,3.177-1.285,2.976-2.566C206.973,724.489,206.1,725.087,204.285,725.321Z" transform="translate(-56 -106.019)" opacity="0.2"/> - <path id="Path_113" data-name="Path 113" d="M439.7,707.337c0,30.22-42.124,20.873-93.7,20.873s-93.074,9.347-93.074-20.873,42.118-36.793,93.694-36.793S439.7,677.117,439.7,707.337Z" transform="translate(-56 -106.019)" opacity="0.1"/> - <path id="Path_114" data-name="Path 114" d="M439.7,699.9c0,30.22-42.124,20.873-93.7,20.873s-93.074,9.347-93.074-20.873S295.04,663.1,346.616,663.1,439.7,669.676,439.7,699.9Z" transform="translate(-56 -106.019)" fill="#3f3d56"/> - </g> - <g id="docusaurus_keytar" transform="translate(312.271 493.733)"> - <path id="Path_40" data-name="Path 40" d="M99,52h91.791V89.153H99Z" transform="translate(5.904 -14.001)" fill="#fff" fill-rule="evenodd"/> - <path id="Path_41" data-name="Path 41" d="M24.855,163.927A21.828,21.828,0,0,1,5.947,153a21.829,21.829,0,0,0,18.908,32.782H46.71V163.927Z" transform="translate(-3 -4.634)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_42" data-name="Path 42" d="M121.861,61.1l76.514-4.782V45.39A21.854,21.854,0,0,0,176.52,23.535H78.173L75.441,18.8a3.154,3.154,0,0,0-5.464,0l-2.732,4.732L64.513,18.8a3.154,3.154,0,0,0-5.464,0l-2.732,4.732L53.586,18.8a3.154,3.154,0,0,0-5.464,0L45.39,23.535c-.024,0-.046,0-.071,0l-4.526-4.525a3.153,3.153,0,0,0-5.276,1.414l-1.5,5.577-5.674-1.521a3.154,3.154,0,0,0-3.863,3.864L26,34.023l-5.575,1.494a3.155,3.155,0,0,0-1.416,5.278l4.526,4.526c0,.023,0,.046,0,.07L18.8,48.122a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,59.05a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,69.977a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,80.9a3.154,3.154,0,0,0,0,5.464L23.535,89.1,18.8,91.832a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,102.76a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,113.687a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,124.615a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,135.542a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,146.469a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,157.4a3.154,3.154,0,0,0,0,5.464l4.732,2.732L18.8,168.324a3.154,3.154,0,0,0,0,5.464l4.732,2.732A21.854,21.854,0,0,0,45.39,198.375H176.52a21.854,21.854,0,0,0,21.855-21.855V89.1l-76.514-4.782a11.632,11.632,0,0,1,0-23.219" transform="translate(-1.681 -17.226)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_43" data-name="Path 43" d="M143,186.71h32.782V143H143Z" transform="translate(9.984 -5.561)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_44" data-name="Path 44" d="M196.71,159.855a5.438,5.438,0,0,0-.7.07c-.042-.164-.081-.329-.127-.493a5.457,5.457,0,1,0-5.4-9.372q-.181-.185-.366-.367a5.454,5.454,0,1,0-9.384-5.4c-.162-.046-.325-.084-.486-.126a5.467,5.467,0,1,0-10.788,0c-.162.042-.325.08-.486.126a5.457,5.457,0,1,0-9.384,5.4,21.843,21.843,0,1,0,36.421,21.02,5.452,5.452,0,1,0,.7-10.858" transform="translate(10.912 -6.025)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_45" data-name="Path 45" d="M153,124.855h32.782V103H153Z" transform="translate(10.912 -9.271)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_46" data-name="Path 46" d="M194.855,116.765a2.732,2.732,0,1,0,0-5.464,2.811,2.811,0,0,0-.349.035c-.022-.082-.04-.164-.063-.246a2.733,2.733,0,0,0-1.052-5.253,2.7,2.7,0,0,0-1.648.566q-.09-.093-.184-.184a2.7,2.7,0,0,0,.553-1.633,2.732,2.732,0,0,0-5.245-1.07,10.928,10.928,0,1,0,0,21.031,2.732,2.732,0,0,0,5.245-1.07,2.7,2.7,0,0,0-.553-1.633q.093-.09.184-.184a2.7,2.7,0,0,0,1.648.566,2.732,2.732,0,0,0,1.052-5.253c.023-.081.042-.164.063-.246a2.814,2.814,0,0,0,.349.035" transform="translate(12.767 -9.377)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_47" data-name="Path 47" d="M65.087,56.891a2.732,2.732,0,0,1-2.732-2.732,8.2,8.2,0,0,0-16.391,0,2.732,2.732,0,0,1-5.464,0,13.659,13.659,0,0,1,27.319,0,2.732,2.732,0,0,1-2.732,2.732" transform="translate(0.478 -15.068)" fill-rule="evenodd"/> - <path id="Path_48" data-name="Path 48" d="M103,191.347h65.565a21.854,21.854,0,0,0,21.855-21.855V93H124.855A21.854,21.854,0,0,0,103,114.855Z" transform="translate(6.275 -10.199)" fill="#ffff50" fill-rule="evenodd"/> - <path id="Path_49" data-name="Path 49" d="M173.216,129.787H118.535a1.093,1.093,0,1,1,0-2.185h54.681a1.093,1.093,0,0,1,0,2.185m0,21.855H118.535a1.093,1.093,0,1,1,0-2.186h54.681a1.093,1.093,0,0,1,0,2.186m0,21.855H118.535a1.093,1.093,0,1,1,0-2.185h54.681a1.093,1.093,0,0,1,0,2.185m0-54.434H118.535a1.093,1.093,0,1,1,0-2.185h54.681a1.093,1.093,0,0,1,0,2.185m0,21.652H118.535a1.093,1.093,0,1,1,0-2.186h54.681a1.093,1.093,0,0,1,0,2.186m0,21.855H118.535a1.093,1.093,0,1,1,0-2.186h54.681a1.093,1.093,0,0,1,0,2.186M189.585,61.611c-.013,0-.024-.007-.037-.005-3.377.115-4.974,3.492-6.384,6.472-1.471,3.114-2.608,5.139-4.473,5.078-2.064-.074-3.244-2.406-4.494-4.874-1.436-2.835-3.075-6.049-6.516-5.929-3.329.114-4.932,3.053-6.346,5.646-1.5,2.762-2.529,4.442-4.5,4.364-2.106-.076-3.225-1.972-4.52-4.167-1.444-2.443-3.112-5.191-6.487-5.1-3.272.113-4.879,2.606-6.3,4.808-1.5,2.328-2.552,3.746-4.551,3.662-2.156-.076-3.27-1.65-4.558-3.472-1.447-2.047-3.077-4.363-6.442-4.251-3.2.109-4.807,2.153-6.224,3.954-1.346,1.709-2.4,3.062-4.621,2.977a1.093,1.093,0,0,0-.079,2.186c3.3.11,4.967-1.967,6.417-3.81,1.286-1.635,2.4-3.045,4.582-3.12,2.1-.09,3.091,1.218,4.584,3.327,1.417,2,3.026,4.277,6.263,4.394,3.391.114,5.022-2.42,6.467-4.663,1.292-2,2.406-3.734,4.535-3.807,1.959-.073,3.026,1.475,4.529,4.022,1.417,2.4,3.023,5.121,6.324,5.241,3.415.118,5.064-2.863,6.5-5.5,1.245-2.282,2.419-4.437,4.5-4.509,1.959-.046,2.981,1.743,4.492,4.732,1.412,2.79,3.013,5.95,6.365,6.071l.185,0c3.348,0,4.937-3.36,6.343-6.331,1.245-2.634,2.423-5.114,4.444-5.216Z" transform="translate(7.109 -13.11)" fill-rule="evenodd"/> - <path id="Path_50" data-name="Path 50" d="M83,186.71h43.71V143H83Z" transform="translate(4.42 -5.561)" fill="#3ecc5f" fill-rule="evenodd"/> - <g id="Group_8" data-name="Group 8" transform="matrix(0.966, -0.259, 0.259, 0.966, 109.327, 91.085)"> - <rect id="Rectangle_3" data-name="Rectangle 3" width="92.361" height="36.462" rx="2" transform="translate(0 0)" fill="#d8d8d8"/> - <g id="Group_2" data-name="Group 2" transform="translate(1.531 23.03)"> - <rect id="Rectangle_4" data-name="Rectangle 4" width="5.336" height="5.336" rx="1" transform="translate(16.797 0)" fill="#4a4a4a"/> - <rect id="Rectangle_5" data-name="Rectangle 5" width="5.336" height="5.336" rx="1" transform="translate(23.12 0)" fill="#4a4a4a"/> - <rect id="Rectangle_6" data-name="Rectangle 6" width="5.336" height="5.336" rx="1" transform="translate(29.444 0)" fill="#4a4a4a"/> - <rect id="Rectangle_7" data-name="Rectangle 7" width="5.336" height="5.336" rx="1" transform="translate(35.768 0)" fill="#4a4a4a"/> - <rect id="Rectangle_8" data-name="Rectangle 8" width="5.336" height="5.336" rx="1" transform="translate(42.091 0)" fill="#4a4a4a"/> - <rect id="Rectangle_9" data-name="Rectangle 9" width="5.336" height="5.336" rx="1" transform="translate(48.415 0)" fill="#4a4a4a"/> - <rect id="Rectangle_10" data-name="Rectangle 10" width="5.336" height="5.336" rx="1" transform="translate(54.739 0)" fill="#4a4a4a"/> - <rect id="Rectangle_11" data-name="Rectangle 11" width="5.336" height="5.336" rx="1" transform="translate(61.063 0)" fill="#4a4a4a"/> - <rect id="Rectangle_12" data-name="Rectangle 12" width="5.336" height="5.336" rx="1" transform="translate(67.386 0)" fill="#4a4a4a"/> - <path id="Path_51" data-name="Path 51" d="M1.093,0H14.518a1.093,1.093,0,0,1,1.093,1.093V4.243a1.093,1.093,0,0,1-1.093,1.093H1.093A1.093,1.093,0,0,1,0,4.243V1.093A1.093,1.093,0,0,1,1.093,0ZM75,0H88.426a1.093,1.093,0,0,1,1.093,1.093V4.243a1.093,1.093,0,0,1-1.093,1.093H75a1.093,1.093,0,0,1-1.093-1.093V1.093A1.093,1.093,0,0,1,75,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - </g> - <g id="Group_3" data-name="Group 3" transform="translate(1.531 10.261)"> - <path id="Path_52" data-name="Path 52" d="M1.093,0H6.218A1.093,1.093,0,0,1,7.31,1.093V4.242A1.093,1.093,0,0,1,6.218,5.335H1.093A1.093,1.093,0,0,1,0,4.242V1.093A1.093,1.093,0,0,1,1.093,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_13" data-name="Rectangle 13" width="5.336" height="5.336" rx="1" transform="translate(8.299 0)" fill="#4a4a4a"/> - <rect id="Rectangle_14" data-name="Rectangle 14" width="5.336" height="5.336" rx="1" transform="translate(14.623 0)" fill="#4a4a4a"/> - <rect id="Rectangle_15" data-name="Rectangle 15" width="5.336" height="5.336" rx="1" transform="translate(20.947 0)" fill="#4a4a4a"/> - <rect id="Rectangle_16" data-name="Rectangle 16" width="5.336" height="5.336" rx="1" transform="translate(27.271 0)" fill="#4a4a4a"/> - <rect id="Rectangle_17" data-name="Rectangle 17" width="5.336" height="5.336" rx="1" transform="translate(33.594 0)" fill="#4a4a4a"/> - <rect id="Rectangle_18" data-name="Rectangle 18" width="5.336" height="5.336" rx="1" transform="translate(39.918 0)" fill="#4a4a4a"/> - <rect id="Rectangle_19" data-name="Rectangle 19" width="5.336" height="5.336" rx="1" transform="translate(46.242 0)" fill="#4a4a4a"/> - <rect id="Rectangle_20" data-name="Rectangle 20" width="5.336" height="5.336" rx="1" transform="translate(52.565 0)" fill="#4a4a4a"/> - <rect id="Rectangle_21" data-name="Rectangle 21" width="5.336" height="5.336" rx="1" transform="translate(58.888 0)" fill="#4a4a4a"/> - <rect id="Rectangle_22" data-name="Rectangle 22" width="5.336" height="5.336" rx="1" transform="translate(65.212 0)" fill="#4a4a4a"/> - <rect id="Rectangle_23" data-name="Rectangle 23" width="5.336" height="5.336" rx="1" transform="translate(71.536 0)" fill="#4a4a4a"/> - <rect id="Rectangle_24" data-name="Rectangle 24" width="5.336" height="5.336" rx="1" transform="translate(77.859 0)" fill="#4a4a4a"/> - <rect id="Rectangle_25" data-name="Rectangle 25" width="5.336" height="5.336" rx="1" transform="translate(84.183 0)" fill="#4a4a4a"/> - </g> - <g id="Group_4" data-name="Group 4" transform="translate(91.05 9.546) rotate(180)"> - <path id="Path_53" data-name="Path 53" d="M1.093,0H6.219A1.093,1.093,0,0,1,7.312,1.093v3.15A1.093,1.093,0,0,1,6.219,5.336H1.093A1.093,1.093,0,0,1,0,4.243V1.093A1.093,1.093,0,0,1,1.093,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_26" data-name="Rectangle 26" width="5.336" height="5.336" rx="1" transform="translate(8.299 0)" fill="#4a4a4a"/> - <rect id="Rectangle_27" data-name="Rectangle 27" width="5.336" height="5.336" rx="1" transform="translate(14.623 0)" fill="#4a4a4a"/> - <rect id="Rectangle_28" data-name="Rectangle 28" width="5.336" height="5.336" rx="1" transform="translate(20.947 0)" fill="#4a4a4a"/> - <rect id="Rectangle_29" data-name="Rectangle 29" width="5.336" height="5.336" rx="1" transform="translate(27.271 0)" fill="#4a4a4a"/> - <rect id="Rectangle_30" data-name="Rectangle 30" width="5.336" height="5.336" rx="1" transform="translate(33.594 0)" fill="#4a4a4a"/> - <rect id="Rectangle_31" data-name="Rectangle 31" width="5.336" height="5.336" rx="1" transform="translate(39.918 0)" fill="#4a4a4a"/> - <rect id="Rectangle_32" data-name="Rectangle 32" width="5.336" height="5.336" rx="1" transform="translate(46.242 0)" fill="#4a4a4a"/> - <rect id="Rectangle_33" data-name="Rectangle 33" width="5.336" height="5.336" rx="1" transform="translate(52.565 0)" fill="#4a4a4a"/> - <rect id="Rectangle_34" data-name="Rectangle 34" width="5.336" height="5.336" rx="1" transform="translate(58.889 0)" fill="#4a4a4a"/> - <rect id="Rectangle_35" data-name="Rectangle 35" width="5.336" height="5.336" rx="1" transform="translate(65.213 0)" fill="#4a4a4a"/> - <rect id="Rectangle_36" data-name="Rectangle 36" width="5.336" height="5.336" rx="1" transform="translate(71.537 0)" fill="#4a4a4a"/> - <rect id="Rectangle_37" data-name="Rectangle 37" width="5.336" height="5.336" rx="1" transform="translate(77.86 0)" fill="#4a4a4a"/> - <rect id="Rectangle_38" data-name="Rectangle 38" width="5.336" height="5.336" rx="1" transform="translate(84.183 0)" fill="#4a4a4a"/> - <rect id="Rectangle_39" data-name="Rectangle 39" width="5.336" height="5.336" rx="1" transform="translate(8.299 0)" fill="#4a4a4a"/> - <rect id="Rectangle_40" data-name="Rectangle 40" width="5.336" height="5.336" rx="1" transform="translate(14.623 0)" fill="#4a4a4a"/> - <rect id="Rectangle_41" data-name="Rectangle 41" width="5.336" height="5.336" rx="1" transform="translate(20.947 0)" fill="#4a4a4a"/> - <rect id="Rectangle_42" data-name="Rectangle 42" width="5.336" height="5.336" rx="1" transform="translate(27.271 0)" fill="#4a4a4a"/> - <rect id="Rectangle_43" data-name="Rectangle 43" width="5.336" height="5.336" rx="1" transform="translate(33.594 0)" fill="#4a4a4a"/> - <rect id="Rectangle_44" data-name="Rectangle 44" width="5.336" height="5.336" rx="1" transform="translate(39.918 0)" fill="#4a4a4a"/> - <rect id="Rectangle_45" data-name="Rectangle 45" width="5.336" height="5.336" rx="1" transform="translate(46.242 0)" fill="#4a4a4a"/> - <rect id="Rectangle_46" data-name="Rectangle 46" width="5.336" height="5.336" rx="1" transform="translate(52.565 0)" fill="#4a4a4a"/> - <rect id="Rectangle_47" data-name="Rectangle 47" width="5.336" height="5.336" rx="1" transform="translate(58.889 0)" fill="#4a4a4a"/> - <rect id="Rectangle_48" data-name="Rectangle 48" width="5.336" height="5.336" rx="1" transform="translate(65.213 0)" fill="#4a4a4a"/> - <rect id="Rectangle_49" data-name="Rectangle 49" width="5.336" height="5.336" rx="1" transform="translate(71.537 0)" fill="#4a4a4a"/> - <rect id="Rectangle_50" data-name="Rectangle 50" width="5.336" height="5.336" rx="1" transform="translate(77.86 0)" fill="#4a4a4a"/> - <rect id="Rectangle_51" data-name="Rectangle 51" width="5.336" height="5.336" rx="1" transform="translate(84.183 0)" fill="#4a4a4a"/> - </g> - <g id="Group_6" data-name="Group 6" transform="translate(1.531 16.584)"> - <path id="Path_54" data-name="Path 54" d="M1.093,0h7.3A1.093,1.093,0,0,1,9.485,1.093v3.15A1.093,1.093,0,0,1,8.392,5.336h-7.3A1.093,1.093,0,0,1,0,4.243V1.094A1.093,1.093,0,0,1,1.093,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <g id="Group_5" data-name="Group 5" transform="translate(10.671 0)"> - <rect id="Rectangle_52" data-name="Rectangle 52" width="5.336" height="5.336" rx="1" fill="#4a4a4a"/> - <rect id="Rectangle_53" data-name="Rectangle 53" width="5.336" height="5.336" rx="1" transform="translate(6.324 0)" fill="#4a4a4a"/> - <rect id="Rectangle_54" data-name="Rectangle 54" width="5.336" height="5.336" rx="1" transform="translate(12.647 0)" fill="#4a4a4a"/> - <rect id="Rectangle_55" data-name="Rectangle 55" width="5.336" height="5.336" rx="1" transform="translate(18.971 0)" fill="#4a4a4a"/> - <rect id="Rectangle_56" data-name="Rectangle 56" width="5.336" height="5.336" rx="1" transform="translate(25.295 0)" fill="#4a4a4a"/> - <rect id="Rectangle_57" data-name="Rectangle 57" width="5.336" height="5.336" rx="1" transform="translate(31.619 0)" fill="#4a4a4a"/> - <rect id="Rectangle_58" data-name="Rectangle 58" width="5.336" height="5.336" rx="1" transform="translate(37.942 0)" fill="#4a4a4a"/> - <rect id="Rectangle_59" data-name="Rectangle 59" width="5.336" height="5.336" rx="1" transform="translate(44.265 0)" fill="#4a4a4a"/> - <rect id="Rectangle_60" data-name="Rectangle 60" width="5.336" height="5.336" rx="1" transform="translate(50.589 0)" fill="#4a4a4a"/> - <rect id="Rectangle_61" data-name="Rectangle 61" width="5.336" height="5.336" rx="1" transform="translate(56.912 0)" fill="#4a4a4a"/> - <rect id="Rectangle_62" data-name="Rectangle 62" width="5.336" height="5.336" rx="1" transform="translate(63.236 0)" fill="#4a4a4a"/> - </g> - <path id="Path_55" data-name="Path 55" d="M1.094,0H8A1.093,1.093,0,0,1,9.091,1.093v3.15A1.093,1.093,0,0,1,8,5.336H1.093A1.093,1.093,0,0,1,0,4.243V1.094A1.093,1.093,0,0,1,1.093,0Z" transform="translate(80.428 0)" fill="#4a4a4a" fill-rule="evenodd"/> - </g> - <g id="Group_7" data-name="Group 7" transform="translate(1.531 29.627)"> - <rect id="Rectangle_63" data-name="Rectangle 63" width="5.336" height="5.336" rx="1" transform="translate(0 0)" fill="#4a4a4a"/> - <rect id="Rectangle_64" data-name="Rectangle 64" width="5.336" height="5.336" rx="1" transform="translate(6.324 0)" fill="#4a4a4a"/> - <rect id="Rectangle_65" data-name="Rectangle 65" width="5.336" height="5.336" rx="1" transform="translate(12.647 0)" fill="#4a4a4a"/> - <rect id="Rectangle_66" data-name="Rectangle 66" width="5.336" height="5.336" rx="1" transform="translate(18.971 0)" fill="#4a4a4a"/> - <path id="Path_56" data-name="Path 56" d="M1.093,0H31.515a1.093,1.093,0,0,1,1.093,1.093V4.244a1.093,1.093,0,0,1-1.093,1.093H1.093A1.093,1.093,0,0,1,0,4.244V1.093A1.093,1.093,0,0,1,1.093,0ZM34.687,0h3.942a1.093,1.093,0,0,1,1.093,1.093V4.244a1.093,1.093,0,0,1-1.093,1.093H34.687a1.093,1.093,0,0,1-1.093-1.093V1.093A1.093,1.093,0,0,1,34.687,0Z" transform="translate(25.294 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_67" data-name="Rectangle 67" width="5.336" height="5.336" rx="1" transform="translate(66.003 0)" fill="#4a4a4a"/> - <rect id="Rectangle_68" data-name="Rectangle 68" width="5.336" height="5.336" rx="1" transform="translate(72.327 0)" fill="#4a4a4a"/> - <rect id="Rectangle_69" data-name="Rectangle 69" width="5.336" height="5.336" rx="1" transform="translate(84.183 0)" fill="#4a4a4a"/> - <path id="Path_57" data-name="Path 57" d="M5.336,0V1.18A1.093,1.093,0,0,1,4.243,2.273H1.093A1.093,1.093,0,0,1,0,1.18V0Z" transform="translate(83.59 2.273) rotate(180)" fill="#4a4a4a"/> - <path id="Path_58" data-name="Path 58" d="M5.336,0V1.18A1.093,1.093,0,0,1,4.243,2.273H1.093A1.093,1.093,0,0,1,0,1.18V0Z" transform="translate(78.255 3.063)" fill="#4a4a4a"/> - </g> - <rect id="Rectangle_70" data-name="Rectangle 70" width="88.927" height="2.371" rx="1.085" transform="translate(1.925 1.17)" fill="#4a4a4a"/> - <rect id="Rectangle_71" data-name="Rectangle 71" width="4.986" height="1.581" rx="0.723" transform="translate(4.1 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_72" data-name="Rectangle 72" width="4.986" height="1.581" rx="0.723" transform="translate(10.923 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_73" data-name="Rectangle 73" width="4.986" height="1.581" rx="0.723" transform="translate(16.173 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_74" data-name="Rectangle 74" width="4.986" height="1.581" rx="0.723" transform="translate(21.421 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_75" data-name="Rectangle 75" width="4.986" height="1.581" rx="0.723" transform="translate(26.671 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_76" data-name="Rectangle 76" width="4.986" height="1.581" rx="0.723" transform="translate(33.232 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_77" data-name="Rectangle 77" width="4.986" height="1.581" rx="0.723" transform="translate(38.48 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_78" data-name="Rectangle 78" width="4.986" height="1.581" rx="0.723" transform="translate(43.73 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_79" data-name="Rectangle 79" width="4.986" height="1.581" rx="0.723" transform="translate(48.978 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_80" data-name="Rectangle 80" width="4.986" height="1.581" rx="0.723" transform="translate(55.54 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_81" data-name="Rectangle 81" width="4.986" height="1.581" rx="0.723" transform="translate(60.788 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_82" data-name="Rectangle 82" width="4.986" height="1.581" rx="0.723" transform="translate(66.038 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_83" data-name="Rectangle 83" width="4.986" height="1.581" rx="0.723" transform="translate(72.599 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_84" data-name="Rectangle 84" width="4.986" height="1.581" rx="0.723" transform="translate(77.847 1.566)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_85" data-name="Rectangle 85" width="4.986" height="1.581" rx="0.723" transform="translate(83.097 1.566)" fill="#d8d8d8" opacity="0.136"/> - </g> - <path id="Path_59" data-name="Path 59" d="M146.71,159.855a5.439,5.439,0,0,0-.7.07c-.042-.164-.081-.329-.127-.493a5.457,5.457,0,1,0-5.4-9.372q-.181-.185-.366-.367a5.454,5.454,0,1,0-9.384-5.4c-.162-.046-.325-.084-.486-.126a5.467,5.467,0,1,0-10.788,0c-.162.042-.325.08-.486.126a5.457,5.457,0,1,0-9.384,5.4,21.843,21.843,0,1,0,36.421,21.02,5.452,5.452,0,1,0,.7-10.858" transform="translate(6.275 -6.025)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_60" data-name="Path 60" d="M83,124.855h43.71V103H83Z" transform="translate(4.42 -9.271)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_61" data-name="Path 61" d="M134.855,116.765a2.732,2.732,0,1,0,0-5.464,2.811,2.811,0,0,0-.349.035c-.022-.082-.04-.164-.063-.246a2.733,2.733,0,0,0-1.052-5.253,2.7,2.7,0,0,0-1.648.566q-.09-.093-.184-.184a2.7,2.7,0,0,0,.553-1.633,2.732,2.732,0,0,0-5.245-1.07,10.928,10.928,0,1,0,0,21.031,2.732,2.732,0,0,0,5.245-1.07,2.7,2.7,0,0,0-.553-1.633q.093-.09.184-.184a2.7,2.7,0,0,0,1.648.566,2.732,2.732,0,0,0,1.052-5.253c.023-.081.042-.164.063-.246a2.811,2.811,0,0,0,.349.035" transform="translate(7.202 -9.377)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_62" data-name="Path 62" d="M143.232,42.33a2.967,2.967,0,0,1-.535-.055,2.754,2.754,0,0,1-.514-.153,2.838,2.838,0,0,1-.471-.251,4.139,4.139,0,0,1-.415-.339,3.2,3.2,0,0,1-.338-.415A2.7,2.7,0,0,1,140.5,39.6a2.968,2.968,0,0,1,.055-.535,3.152,3.152,0,0,1,.152-.514,2.874,2.874,0,0,1,.252-.47,2.633,2.633,0,0,1,.753-.754,2.837,2.837,0,0,1,.471-.251,2.753,2.753,0,0,1,.514-.153,2.527,2.527,0,0,1,1.071,0,2.654,2.654,0,0,1,.983.4,4.139,4.139,0,0,1,.415.339,4.019,4.019,0,0,1,.339.415,2.786,2.786,0,0,1,.251.47,2.864,2.864,0,0,1,.208,1.049,2.77,2.77,0,0,1-.8,1.934,4.139,4.139,0,0,1-.415.339,2.722,2.722,0,0,1-1.519.459m21.855-1.366a2.789,2.789,0,0,1-1.935-.8,4.162,4.162,0,0,1-.338-.415,2.7,2.7,0,0,1-.459-1.519,2.789,2.789,0,0,1,.8-1.934,4.139,4.139,0,0,1,.415-.339,2.838,2.838,0,0,1,.471-.251,2.752,2.752,0,0,1,.514-.153,2.527,2.527,0,0,1,1.071,0,2.654,2.654,0,0,1,.983.4,4.139,4.139,0,0,1,.415.339,2.79,2.79,0,0,1,.8,1.934,3.069,3.069,0,0,1-.055.535,2.779,2.779,0,0,1-.153.514,3.885,3.885,0,0,1-.251.47,4.02,4.02,0,0,1-.339.415,4.138,4.138,0,0,1-.415.339,2.722,2.722,0,0,1-1.519.459" transform="translate(9.753 -15.532)" fill-rule="evenodd"/> - </g> - </g> -</svg> diff --git a/static/img/undraw_docusaurus_react.svg b/static/img/undraw_docusaurus_react.svg deleted file mode 100644 index 94b5cf0..0000000 --- a/static/img/undraw_docusaurus_react.svg +++ /dev/null @@ -1,170 +0,0 @@ -<svg xmlns="http://www.w3.org/2000/svg" width="1041.277" height="554.141" viewBox="0 0 1041.277 554.141"> - <title>Powered by React</title> - <g id="Group_24" data-name="Group 24" transform="translate(-440 -263)"> - <g id="Group_23" data-name="Group 23" transform="translate(439.989 262.965)"> - <path id="Path_299" data-name="Path 299" d="M1040.82,611.12q-1.74,3.75-3.47,7.4-2.7,5.67-5.33,11.12c-.78,1.61-1.56,3.19-2.32,4.77-8.6,17.57-16.63,33.11-23.45,45.89A73.21,73.21,0,0,1,942.44,719l-151.65,1.65h-1.6l-13,.14-11.12.12-34.1.37h-1.38l-17.36.19h-.53l-107,1.16-95.51,1-11.11.12-69,.75H429l-44.75.48h-.48l-141.5,1.53-42.33.46a87.991,87.991,0,0,1-10.79-.54h0c-1.22-.14-2.44-.3-3.65-.49a87.38,87.38,0,0,1-51.29-27.54C116,678.37,102.75,655,93.85,629.64q-1.93-5.49-3.6-11.12C59.44,514.37,97,380,164.6,290.08q4.25-5.64,8.64-11l.07-.08c20.79-25.52,44.1-46.84,68.93-62,44-26.91,92.75-34.49,140.7-11.9,40.57,19.12,78.45,28.11,115.17,30.55,3.71.24,7.42.42,11.11.53,84.23,2.65,163.17-27.7,255.87-47.29,3.69-.78,7.39-1.55,11.12-2.28,66.13-13.16,139.49-20.1,226.73-5.51a189.089,189.089,0,0,1,26.76,6.4q5.77,1.86,11.12,4c41.64,16.94,64.35,48.24,74,87.46q1.37,5.46,2.37,11.11C1134.3,384.41,1084.19,518.23,1040.82,611.12Z" transform="translate(-79.34 -172.91)" fill="#f2f2f2"/> - <path id="Path_300" data-name="Path 300" d="M576.36,618.52a95.21,95.21,0,0,1-1.87,11.12h93.7V618.52Zm-78.25,62.81,11.11-.09V653.77c-3.81-.17-7.52-.34-11.11-.52ZM265.19,618.52v11.12h198.5V618.52ZM1114.87,279h-74V191.51q-5.35-2.17-11.12-4V279H776.21V186.58c-3.73.73-7.43,1.5-11.12,2.28V279H509.22V236.15c-3.69-.11-7.4-.29-11.11-.53V279H242.24V217c-24.83,15.16-48.14,36.48-68.93,62h-.07v.08q-4.4,5.4-8.64,11h8.64V618.52h-83q1.66,5.63,3.6,11.12h79.39v93.62a87,87,0,0,0,12.2,2.79c1.21.19,2.43.35,3.65.49h0a87.991,87.991,0,0,0,10.79.54l42.33-.46v-97H498.11v94.21l11.11-.12V629.64H765.09V721l11.12-.12V629.64H1029.7v4.77c.76-1.58,1.54-3.16,2.32-4.77q2.63-5.45,5.33-11.12,1.73-3.64,3.47-7.4v-321h76.42Q1116.23,284.43,1114.87,279ZM242.24,618.52V290.08H498.11V618.52Zm267,0V290.08H765.09V618.52Zm520.48,0H776.21V290.08H1029.7Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_301" data-name="Path 301" d="M863.09,533.65v13l-151.92,1.4-1.62.03-57.74.53-1.38.02-17.55.15h-.52l-106.98.99L349.77,551.4h-.15l-44.65.42-.48.01-198.4,1.82v-15l46.65-28,93.6-.78,2-.01.66-.01,2-.03,44.94-.37,2.01-.01.64-.01,2-.01L315,509.3l.38-.01,35.55-.3h.29l277.4-2.34,6.79-.05h.68l5.18-.05,37.65-.31,2-.03,1.85-.02h.96l11.71-.09,2.32-.03,3.11-.02,9.75-.09,15.47-.13,2-.02,3.48-.02h.65l74.71-.64Z" fill="#65617d"/> - <path id="Path_302" data-name="Path 302" d="M863.09,533.65v13l-151.92,1.4-1.62.03-57.74.53-1.38.02-17.55.15h-.52l-106.98.99L349.77,551.4h-.15l-44.65.42-.48.01-198.4,1.82v-15l46.65-28,93.6-.78,2-.01.66-.01,2-.03,44.94-.37,2.01-.01.64-.01,2-.01L315,509.3l.38-.01,35.55-.3h.29l277.4-2.34,6.79-.05h.68l5.18-.05,37.65-.31,2-.03,1.85-.02h.96l11.71-.09,2.32-.03,3.11-.02,9.75-.09,15.47-.13,2-.02,3.48-.02h.65l74.71-.64Z" opacity="0.2"/> - <path id="Path_303" data-name="Path 303" d="M375.44,656.57v24.49a6.13,6.13,0,0,1-3.5,5.54,6,6,0,0,1-2.5.6l-34.9.74a6,6,0,0,1-2.7-.57,6.12,6.12,0,0,1-3.57-5.57V656.57Z" transform="translate(-79.34 -172.91)" fill="#3f3d56"/> - <path id="Path_304" data-name="Path 304" d="M375.44,656.57v24.49a6.13,6.13,0,0,1-3.5,5.54,6,6,0,0,1-2.5.6l-34.9.74a6,6,0,0,1-2.7-.57,6.12,6.12,0,0,1-3.57-5.57V656.57Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_305" data-name="Path 305" d="M377.44,656.57v24.49a6.13,6.13,0,0,1-3.5,5.54,6,6,0,0,1-2.5.6l-34.9.74a6,6,0,0,1-2.7-.57,6.12,6.12,0,0,1-3.57-5.57V656.57Z" transform="translate(-79.34 -172.91)" fill="#3f3d56"/> - <rect id="Rectangle_137" data-name="Rectangle 137" width="47.17" height="31.5" transform="translate(680.92 483.65)" fill="#3f3d56"/> - <rect id="Rectangle_138" data-name="Rectangle 138" width="47.17" height="31.5" transform="translate(680.92 483.65)" opacity="0.1"/> - <rect id="Rectangle_139" data-name="Rectangle 139" width="47.17" height="31.5" transform="translate(678.92 483.65)" fill="#3f3d56"/> - <path id="Path_306" data-name="Path 306" d="M298.09,483.65v4.97l-47.17,1.26v-6.23Z" opacity="0.1"/> - <path id="Path_307" data-name="Path 307" d="M460.69,485.27v168.2a4,4,0,0,1-3.85,3.95l-191.65,5.1h-.05a4,4,0,0,1-3.95-3.95V485.27a4,4,0,0,1,3.95-3.95h191.6a4,4,0,0,1,3.95,3.95Z" transform="translate(-79.34 -172.91)" fill="#65617d"/> - <path id="Path_308" data-name="Path 308" d="M265.19,481.32v181.2h-.05a4,4,0,0,1-3.95-3.95V485.27a4,4,0,0,1,3.95-3.95Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_309" data-name="Path 309" d="M194.59,319.15h177.5V467.4l-177.5,4Z" fill="#39374d"/> - <path id="Path_310" data-name="Path 310" d="M726.09,483.65v6.41l-47.17-1.26v-5.15Z" opacity="0.1"/> - <path id="Path_311" data-name="Path 311" d="M867.69,485.27v173.3a4,4,0,0,1-4,3.95h0L672,657.42a4,4,0,0,1-3.85-3.95V485.27a4,4,0,0,1,3.95-3.95H863.7a4,4,0,0,1,3.99,3.95Z" transform="translate(-79.34 -172.91)" fill="#65617d"/> - <path id="Path_312" data-name="Path 312" d="M867.69,485.27v173.3a4,4,0,0,1-4,3.95h0V481.32h0a4,4,0,0,1,4,3.95Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_313" data-name="Path 313" d="M775.59,319.15H598.09V467.4l177.5,4Z" fill="#39374d"/> - <path id="Path_314" data-name="Path 314" d="M663.19,485.27v168.2a4,4,0,0,1-3.85,3.95l-191.65,5.1h0a4,4,0,0,1-4-3.95V485.27a4,4,0,0,1,3.95-3.95h191.6A4,4,0,0,1,663.19,485.27Z" transform="translate(-79.34 -172.91)" fill="#65617d"/> - <path id="Path_315" data-name="Path 315" d="M397.09,319.15h177.5V467.4l-177.5,4Z" fill="#4267b2"/> - <path id="Path_316" data-name="Path 316" d="M863.09,533.65v13l-151.92,1.4-1.62.03-57.74.53-1.38.02-17.55.15h-.52l-106.98.99L349.77,551.4h-.15l-44.65.42-.48.01-198.4,1.82v-15l202.51-1.33h.48l40.99-.28h.19l283.08-1.87h.29l.17-.01h.47l4.79-.03h1.46l74.49-.5,4.4-.02.98-.01Z" opacity="0.1"/> - <circle id="Ellipse_111" data-name="Ellipse 111" cx="51.33" cy="51.33" r="51.33" transform="translate(435.93 246.82)" fill="#fbbebe"/> - <path id="Path_317" data-name="Path 317" d="M617.94,550.07s-99.5,12-90,0c3.44-4.34,4.39-17.2,4.2-31.85-.06-4.45-.22-9.06-.45-13.65-1.1-22-3.75-43.5-3.75-43.5s87-41,77-8.5c-4,13.13-2.69,31.57.35,48.88.89,5.05,1.92,10,3,14.7a344.66,344.66,0,0,0,9.65,33.92Z" transform="translate(-79.34 -172.91)" fill="#fbbebe"/> - <path id="Path_318" data-name="Path 318" d="M585.47,546c11.51-2.13,23.7-6,34.53-1.54,2.85,1.17,5.47,2.88,8.39,3.86s6.12,1.22,9.16,1.91c10.68,2.42,19.34,10.55,24.9,20s8.44,20.14,11.26,30.72l6.9,25.83c6,22.45,12,45.09,13.39,68.3a2437.506,2437.506,0,0,1-250.84,1.43c5.44-10.34,11-21.31,10.54-33s-7.19-23.22-4.76-34.74c1.55-7.34,6.57-13.39,9.64-20.22,8.75-19.52,1.94-45.79,17.32-60.65,6.92-6.68,17-9.21,26.63-8.89,12.28.41,24.85,4.24,37,6.11C555.09,547.48,569.79,548.88,585.47,546Z" transform="translate(-79.34 -172.91)" fill="#ff6584"/> - <path id="Path_319" data-name="Path 319" d="M716.37,657.17l-.1,1.43v.1l-.17,2.3-1.33,18.51-1.61,22.3-.46,6.28-1,13.44v.17l-107,1-175.59,1.9v.84h-.14v-1.12l.45-14.36.86-28.06.74-23.79.07-2.37a10.53,10.53,0,0,1,11.42-10.17c4.72.4,10.85.89,18.18,1.41l3,.22c42.33,2.94,120.56,6.74,199.5,2,1.66-.09,3.33-.19,5-.31,12.24-.77,24.47-1.76,36.58-3a10.53,10.53,0,0,1,11.6,11.23Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_320" data-name="Path 320" d="M429.08,725.44v-.84l175.62-1.91,107-1h.3v-.17l1-13.44.43-6,1.64-22.61,1.29-17.9v-.44a10.617,10.617,0,0,0-.11-2.47.3.3,0,0,0,0-.1,10.391,10.391,0,0,0-2-4.64,10.54,10.54,0,0,0-9.42-4c-12.11,1.24-24.34,2.23-36.58,3-1.67.12-3.34.22-5,.31-78.94,4.69-157.17.89-199.5-2l-3-.22c-7.33-.52-13.46-1-18.18-1.41a10.54,10.54,0,0,0-11.24,8.53,11,11,0,0,0-.18,1.64l-.68,22.16L429.54,710l-.44,14.36v1.12Z" transform="translate(-79.34 -172.91)" fill="#3f3d56"/> - <path id="Path_321" data-name="Path 321" d="M716.67,664.18l-1.23,15.33-1.83,22.85-.46,5.72-1,12.81-.06.64v.17h0l-.15,1.48.11-1.48h-.29l-107,1-175.65,1.9v-.28l.49-14.36,1-28.06.64-18.65A6.36,6.36,0,0,1,434.3,658a6.25,6.25,0,0,1,3.78-.9c2.1.17,4.68.37,7.69.59,4.89.36,10.92.78,17.94,1.22,13,.82,29.31,1.7,48,2.42,52,2,122.2,2.67,188.88-3.17,3-.26,6.1-.55,9.13-.84a6.26,6.26,0,0,1,3.48.66,5.159,5.159,0,0,1,.86.54,6.14,6.14,0,0,1,2,2.46,3.564,3.564,0,0,1,.25.61A6.279,6.279,0,0,1,716.67,664.18Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_322" data-name="Path 322" d="M377.44,677.87v3.19a6.13,6.13,0,0,1-3.5,5.54l-40.1.77a6.12,6.12,0,0,1-3.57-5.57v-3Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_323" data-name="Path 323" d="M298.59,515.57l-52.25,1V507.9l52.25-1Z" fill="#3f3d56"/> - <path id="Path_324" data-name="Path 324" d="M298.59,515.57l-52.25,1V507.9l52.25-1Z" opacity="0.1"/> - <path id="Path_325" data-name="Path 325" d="M300.59,515.57l-52.25,1V507.9l52.25-1Z" fill="#3f3d56"/> - <path id="Path_326" data-name="Path 326" d="M758.56,679.87v3.19a6.13,6.13,0,0,0,3.5,5.54l40.1.77a6.12,6.12,0,0,0,3.57-5.57v-3Z" transform="translate(-79.34 -172.91)" opacity="0.1"/> - <path id="Path_327" data-name="Path 327" d="M678.72,517.57l52.25,1V509.9l-52.25-1Z" opacity="0.1"/> - <path id="Path_328" data-name="Path 328" d="M676.72,517.57l52.25,1V509.9l-52.25-1Z" fill="#3f3d56"/> - <path id="Path_329" data-name="Path 329" d="M534.13,486.79c.08,7-3.16,13.6-5.91,20.07a163.491,163.491,0,0,0-12.66,74.71c.73,11,2.58,22,.73,32.9s-8.43,21.77-19,24.9c17.53,10.45,41.26,9.35,57.76-2.66,8.79-6.4,15.34-15.33,21.75-24.11a97.86,97.86,0,0,1-13.31,44.75A103.43,103.43,0,0,0,637,616.53c4.31-5.81,8.06-12.19,9.72-19.23,3.09-13-1.22-26.51-4.51-39.5a266.055,266.055,0,0,1-6.17-33c-.43-3.56-.78-7.22.1-10.7,1-4.07,3.67-7.51,5.64-11.22,5.6-10.54,5.73-23.3,2.86-34.88s-8.49-22.26-14.06-32.81c-4.46-8.46-9.3-17.31-17.46-22.28-5.1-3.1-11-4.39-16.88-5.64l-25.37-5.43c-5.55-1.19-11.26-2.38-16.87-1.51-9.47,1.48-16.14,8.32-22,15.34-4.59,5.46-15.81,15.71-16.6,22.86-.72,6.59,5.1,17.63,6.09,24.58,1.3,9,2.22,6,7.3,11.52C532,478.05,534.07,482,534.13,486.79Z" transform="translate(-79.34 -172.91)" fill="#3f3d56"/> - </g> - <g id="docusaurus_keytar" transform="translate(670.271 615.768)"> - <path id="Path_40" data-name="Path 40" d="M99,52h43.635V69.662H99Z" transform="translate(-49.132 -33.936)" fill="#fff" fill-rule="evenodd"/> - <path id="Path_41" data-name="Path 41" d="M13.389,158.195A10.377,10.377,0,0,1,4.4,153a10.377,10.377,0,0,0,8.988,15.584H23.779V158.195Z" transform="translate(-3 -82.47)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_42" data-name="Path 42" d="M66.967,38.083l36.373-2.273V30.615A10.389,10.389,0,0,0,92.95,20.226H46.2l-1.3-2.249a1.5,1.5,0,0,0-2.6,0L41,20.226l-1.3-2.249a1.5,1.5,0,0,0-2.6,0l-1.3,2.249-1.3-2.249a1.5,1.5,0,0,0-2.6,0l-1.3,2.249-.034,0-2.152-2.151a1.5,1.5,0,0,0-2.508.672L25.21,21.4l-2.7-.723a1.5,1.5,0,0,0-1.836,1.837l.722,2.7-2.65.71a1.5,1.5,0,0,0-.673,2.509l2.152,2.152c0,.011,0,.022,0,.033l-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6L20.226,41l-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3-2.249,1.3a1.5,1.5,0,0,0,0,2.6l2.249,1.3A10.389,10.389,0,0,0,30.615,103.34H92.95A10.389,10.389,0,0,0,103.34,92.95V51.393L66.967,49.12a5.53,5.53,0,0,1,0-11.038" transform="translate(-9.836 -17.226)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_43" data-name="Path 43" d="M143,163.779h15.584V143H143Z" transform="translate(-70.275 -77.665)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_44" data-name="Path 44" d="M173.779,148.389a2.582,2.582,0,0,0-.332.033c-.02-.078-.038-.156-.06-.234a2.594,2.594,0,1,0-2.567-4.455q-.086-.088-.174-.175a2.593,2.593,0,1,0-4.461-2.569c-.077-.022-.154-.04-.231-.06a2.6,2.6,0,1,0-5.128,0c-.077.02-.154.038-.231.06a2.594,2.594,0,1,0-4.461,2.569,10.384,10.384,0,1,0,17.314,9.992,2.592,2.592,0,1,0,.332-5.161" transform="translate(-75.08 -75.262)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_45" data-name="Path 45" d="M153,113.389h15.584V103H153Z" transform="translate(-75.08 -58.444)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_46" data-name="Path 46" d="M183.389,108.944a1.3,1.3,0,1,0,0-2.6,1.336,1.336,0,0,0-.166.017c-.01-.039-.019-.078-.03-.117a1.3,1.3,0,0,0-.5-2.5,1.285,1.285,0,0,0-.783.269q-.043-.044-.087-.087a1.285,1.285,0,0,0,.263-.776,1.3,1.3,0,0,0-2.493-.509,5.195,5.195,0,1,0,0,10,1.3,1.3,0,0,0,2.493-.509,1.285,1.285,0,0,0-.263-.776q.044-.043.087-.087a1.285,1.285,0,0,0,.783.269,1.3,1.3,0,0,0,.5-2.5c.011-.038.02-.078.03-.117a1.337,1.337,0,0,0,.166.017" transform="translate(-84.691 -57.894)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_47" data-name="Path 47" d="M52.188,48.292a1.3,1.3,0,0,1-1.3-1.3,3.9,3.9,0,0,0-7.792,0,1.3,1.3,0,1,1-2.6,0,6.493,6.493,0,0,1,12.987,0,1.3,1.3,0,0,1-1.3,1.3" transform="translate(-21.02 -28.41)" fill-rule="evenodd"/> - <path id="Path_48" data-name="Path 48" d="M103,139.752h31.168a10.389,10.389,0,0,0,10.389-10.389V93H113.389A10.389,10.389,0,0,0,103,103.389Z" transform="translate(-51.054 -53.638)" fill="#ffff50" fill-rule="evenodd"/> - <path id="Path_49" data-name="Path 49" d="M141.1,94.017H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m0,10.389H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m0,10.389H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m0-25.877H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m0,10.293H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m0,10.389H115.106a.519.519,0,1,1,0-1.039H141.1a.519.519,0,0,1,0,1.039m7.782-47.993c-.006,0-.011,0-.018,0-1.605.055-2.365,1.66-3.035,3.077-.7,1.48-1.24,2.443-2.126,2.414-.981-.035-1.542-1.144-2.137-2.317-.683-1.347-1.462-2.876-3.1-2.819-1.582.054-2.344,1.451-3.017,2.684-.715,1.313-1.2,2.112-2.141,2.075-1-.036-1.533-.938-2.149-1.981-.686-1.162-1.479-2.467-3.084-2.423-1.555.053-2.319,1.239-2.994,2.286-.713,1.106-1.213,1.781-2.164,1.741-1.025-.036-1.554-.784-2.167-1.65-.688-.973-1.463-2.074-3.062-2.021a3.815,3.815,0,0,0-2.959,1.879c-.64.812-1.14,1.456-2.2,1.415a.52.52,0,0,0-.037,1.039,3.588,3.588,0,0,0,3.05-1.811c.611-.777,1.139-1.448,2.178-1.483,1-.043,1.47.579,2.179,1.582.674.953,1.438,2.033,2.977,2.089,1.612.054,2.387-1.151,3.074-2.217.614-.953,1.144-1.775,2.156-1.81.931-.035,1.438.7,2.153,1.912.674,1.141,1.437,2.434,3.006,2.491,1.623.056,2.407-1.361,3.09-2.616.592-1.085,1.15-2.109,2.14-2.143.931-.022,1.417.829,2.135,2.249.671,1.326,1.432,2.828,3.026,2.886l.088,0c1.592,0,2.347-1.6,3.015-3.01.592-1.252,1.152-2.431,2.113-2.479Z" transform="translate(-55.378 -38.552)" fill-rule="evenodd"/> - <path id="Path_50" data-name="Path 50" d="M83,163.779h20.779V143H83Z" transform="translate(-41.443 -77.665)" fill="#3ecc5f" fill-rule="evenodd"/> - <g id="Group_8" data-name="Group 8" transform="matrix(0.966, -0.259, 0.259, 0.966, 51.971, 43.3)"> - <rect id="Rectangle_3" data-name="Rectangle 3" width="43.906" height="17.333" rx="2" transform="translate(0 0)" fill="#d8d8d8"/> - <g id="Group_2" data-name="Group 2" transform="translate(0.728 10.948)"> - <rect id="Rectangle_4" data-name="Rectangle 4" width="2.537" height="2.537" rx="1" transform="translate(7.985 0)" fill="#4a4a4a"/> - <rect id="Rectangle_5" data-name="Rectangle 5" width="2.537" height="2.537" rx="1" transform="translate(10.991 0)" fill="#4a4a4a"/> - <rect id="Rectangle_6" data-name="Rectangle 6" width="2.537" height="2.537" rx="1" transform="translate(13.997 0)" fill="#4a4a4a"/> - <rect id="Rectangle_7" data-name="Rectangle 7" width="2.537" height="2.537" rx="1" transform="translate(17.003 0)" fill="#4a4a4a"/> - <rect id="Rectangle_8" data-name="Rectangle 8" width="2.537" height="2.537" rx="1" transform="translate(20.009 0)" fill="#4a4a4a"/> - <rect id="Rectangle_9" data-name="Rectangle 9" width="2.537" height="2.537" rx="1" transform="translate(23.015 0)" fill="#4a4a4a"/> - <rect id="Rectangle_10" data-name="Rectangle 10" width="2.537" height="2.537" rx="1" transform="translate(26.021 0)" fill="#4a4a4a"/> - <rect id="Rectangle_11" data-name="Rectangle 11" width="2.537" height="2.537" rx="1" transform="translate(29.028 0)" fill="#4a4a4a"/> - <rect id="Rectangle_12" data-name="Rectangle 12" width="2.537" height="2.537" rx="1" transform="translate(32.034 0)" fill="#4a4a4a"/> - <path id="Path_51" data-name="Path 51" d="M.519,0H6.9A.519.519,0,0,1,7.421.52v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.017V.519A.519.519,0,0,1,.519,0ZM35.653,0h6.383a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H35.652a.519.519,0,0,1-.519-.519V.519A.519.519,0,0,1,35.652,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - </g> - <g id="Group_3" data-name="Group 3" transform="translate(0.728 4.878)"> - <path id="Path_52" data-name="Path 52" d="M.519,0H2.956a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.017V.519A.519.519,0,0,1,.519,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_13" data-name="Rectangle 13" width="2.537" height="2.537" rx="1" transform="translate(3.945 0)" fill="#4a4a4a"/> - <rect id="Rectangle_14" data-name="Rectangle 14" width="2.537" height="2.537" rx="1" transform="translate(6.951 0)" fill="#4a4a4a"/> - <rect id="Rectangle_15" data-name="Rectangle 15" width="2.537" height="2.537" rx="1" transform="translate(9.958 0)" fill="#4a4a4a"/> - <rect id="Rectangle_16" data-name="Rectangle 16" width="2.537" height="2.537" rx="1" transform="translate(12.964 0)" fill="#4a4a4a"/> - <rect id="Rectangle_17" data-name="Rectangle 17" width="2.537" height="2.537" rx="1" transform="translate(15.97 0)" fill="#4a4a4a"/> - <rect id="Rectangle_18" data-name="Rectangle 18" width="2.537" height="2.537" rx="1" transform="translate(18.976 0)" fill="#4a4a4a"/> - <rect id="Rectangle_19" data-name="Rectangle 19" width="2.537" height="2.537" rx="1" transform="translate(21.982 0)" fill="#4a4a4a"/> - <rect id="Rectangle_20" data-name="Rectangle 20" width="2.537" height="2.537" rx="1" transform="translate(24.988 0)" fill="#4a4a4a"/> - <rect id="Rectangle_21" data-name="Rectangle 21" width="2.537" height="2.537" rx="1" transform="translate(27.994 0)" fill="#4a4a4a"/> - <rect id="Rectangle_22" data-name="Rectangle 22" width="2.537" height="2.537" rx="1" transform="translate(31 0)" fill="#4a4a4a"/> - <rect id="Rectangle_23" data-name="Rectangle 23" width="2.537" height="2.537" rx="1" transform="translate(34.006 0)" fill="#4a4a4a"/> - <rect id="Rectangle_24" data-name="Rectangle 24" width="2.537" height="2.537" rx="1" transform="translate(37.012 0)" fill="#4a4a4a"/> - <rect id="Rectangle_25" data-name="Rectangle 25" width="2.537" height="2.537" rx="1" transform="translate(40.018 0)" fill="#4a4a4a"/> - </g> - <g id="Group_4" data-name="Group 4" transform="translate(43.283 4.538) rotate(180)"> - <path id="Path_53" data-name="Path 53" d="M.519,0H2.956a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.017V.519A.519.519,0,0,1,.519,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_26" data-name="Rectangle 26" width="2.537" height="2.537" rx="1" transform="translate(3.945 0)" fill="#4a4a4a"/> - <rect id="Rectangle_27" data-name="Rectangle 27" width="2.537" height="2.537" rx="1" transform="translate(6.951 0)" fill="#4a4a4a"/> - <rect id="Rectangle_28" data-name="Rectangle 28" width="2.537" height="2.537" rx="1" transform="translate(9.958 0)" fill="#4a4a4a"/> - <rect id="Rectangle_29" data-name="Rectangle 29" width="2.537" height="2.537" rx="1" transform="translate(12.964 0)" fill="#4a4a4a"/> - <rect id="Rectangle_30" data-name="Rectangle 30" width="2.537" height="2.537" rx="1" transform="translate(15.97 0)" fill="#4a4a4a"/> - <rect id="Rectangle_31" data-name="Rectangle 31" width="2.537" height="2.537" rx="1" transform="translate(18.976 0)" fill="#4a4a4a"/> - <rect id="Rectangle_32" data-name="Rectangle 32" width="2.537" height="2.537" rx="1" transform="translate(21.982 0)" fill="#4a4a4a"/> - <rect id="Rectangle_33" data-name="Rectangle 33" width="2.537" height="2.537" rx="1" transform="translate(24.988 0)" fill="#4a4a4a"/> - <rect id="Rectangle_34" data-name="Rectangle 34" width="2.537" height="2.537" rx="1" transform="translate(27.994 0)" fill="#4a4a4a"/> - <rect id="Rectangle_35" data-name="Rectangle 35" width="2.537" height="2.537" rx="1" transform="translate(31.001 0)" fill="#4a4a4a"/> - <rect id="Rectangle_36" data-name="Rectangle 36" width="2.537" height="2.537" rx="1" transform="translate(34.007 0)" fill="#4a4a4a"/> - <rect id="Rectangle_37" data-name="Rectangle 37" width="2.537" height="2.537" rx="1" transform="translate(37.013 0)" fill="#4a4a4a"/> - <rect id="Rectangle_38" data-name="Rectangle 38" width="2.537" height="2.537" rx="1" transform="translate(40.018 0)" fill="#4a4a4a"/> - <rect id="Rectangle_39" data-name="Rectangle 39" width="2.537" height="2.537" rx="1" transform="translate(3.945 0)" fill="#4a4a4a"/> - <rect id="Rectangle_40" data-name="Rectangle 40" width="2.537" height="2.537" rx="1" transform="translate(6.951 0)" fill="#4a4a4a"/> - <rect id="Rectangle_41" data-name="Rectangle 41" width="2.537" height="2.537" rx="1" transform="translate(9.958 0)" fill="#4a4a4a"/> - <rect id="Rectangle_42" data-name="Rectangle 42" width="2.537" height="2.537" rx="1" transform="translate(12.964 0)" fill="#4a4a4a"/> - <rect id="Rectangle_43" data-name="Rectangle 43" width="2.537" height="2.537" rx="1" transform="translate(15.97 0)" fill="#4a4a4a"/> - <rect id="Rectangle_44" data-name="Rectangle 44" width="2.537" height="2.537" rx="1" transform="translate(18.976 0)" fill="#4a4a4a"/> - <rect id="Rectangle_45" data-name="Rectangle 45" width="2.537" height="2.537" rx="1" transform="translate(21.982 0)" fill="#4a4a4a"/> - <rect id="Rectangle_46" data-name="Rectangle 46" width="2.537" height="2.537" rx="1" transform="translate(24.988 0)" fill="#4a4a4a"/> - <rect id="Rectangle_47" data-name="Rectangle 47" width="2.537" height="2.537" rx="1" transform="translate(27.994 0)" fill="#4a4a4a"/> - <rect id="Rectangle_48" data-name="Rectangle 48" width="2.537" height="2.537" rx="1" transform="translate(31.001 0)" fill="#4a4a4a"/> - <rect id="Rectangle_49" data-name="Rectangle 49" width="2.537" height="2.537" rx="1" transform="translate(34.007 0)" fill="#4a4a4a"/> - <rect id="Rectangle_50" data-name="Rectangle 50" width="2.537" height="2.537" rx="1" transform="translate(37.013 0)" fill="#4a4a4a"/> - <rect id="Rectangle_51" data-name="Rectangle 51" width="2.537" height="2.537" rx="1" transform="translate(40.018 0)" fill="#4a4a4a"/> - </g> - <g id="Group_6" data-name="Group 6" transform="translate(0.728 7.883)"> - <path id="Path_54" data-name="Path 54" d="M.519,0h3.47a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.017V.52A.519.519,0,0,1,.519,0Z" transform="translate(0 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <g id="Group_5" data-name="Group 5" transform="translate(5.073 0)"> - <rect id="Rectangle_52" data-name="Rectangle 52" width="2.537" height="2.537" rx="1" transform="translate(0 0)" fill="#4a4a4a"/> - <rect id="Rectangle_53" data-name="Rectangle 53" width="2.537" height="2.537" rx="1" transform="translate(3.006 0)" fill="#4a4a4a"/> - <rect id="Rectangle_54" data-name="Rectangle 54" width="2.537" height="2.537" rx="1" transform="translate(6.012 0)" fill="#4a4a4a"/> - <rect id="Rectangle_55" data-name="Rectangle 55" width="2.537" height="2.537" rx="1" transform="translate(9.018 0)" fill="#4a4a4a"/> - <rect id="Rectangle_56" data-name="Rectangle 56" width="2.537" height="2.537" rx="1" transform="translate(12.025 0)" fill="#4a4a4a"/> - <rect id="Rectangle_57" data-name="Rectangle 57" width="2.537" height="2.537" rx="1" transform="translate(15.031 0)" fill="#4a4a4a"/> - <rect id="Rectangle_58" data-name="Rectangle 58" width="2.537" height="2.537" rx="1" transform="translate(18.037 0)" fill="#4a4a4a"/> - <rect id="Rectangle_59" data-name="Rectangle 59" width="2.537" height="2.537" rx="1" transform="translate(21.042 0)" fill="#4a4a4a"/> - <rect id="Rectangle_60" data-name="Rectangle 60" width="2.537" height="2.537" rx="1" transform="translate(24.049 0)" fill="#4a4a4a"/> - <rect id="Rectangle_61" data-name="Rectangle 61" width="2.537" height="2.537" rx="1" transform="translate(27.055 0)" fill="#4a4a4a"/> - <rect id="Rectangle_62" data-name="Rectangle 62" width="2.537" height="2.537" rx="1" transform="translate(30.061 0)" fill="#4a4a4a"/> - </g> - <path id="Path_55" data-name="Path 55" d="M.52,0H3.8a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.017V.52A.519.519,0,0,1,.519,0Z" transform="translate(38.234 0)" fill="#4a4a4a" fill-rule="evenodd"/> - </g> - <g id="Group_7" data-name="Group 7" transform="translate(0.728 14.084)"> - <rect id="Rectangle_63" data-name="Rectangle 63" width="2.537" height="2.537" rx="1" transform="translate(0 0)" fill="#4a4a4a"/> - <rect id="Rectangle_64" data-name="Rectangle 64" width="2.537" height="2.537" rx="1" transform="translate(3.006 0)" fill="#4a4a4a"/> - <rect id="Rectangle_65" data-name="Rectangle 65" width="2.537" height="2.537" rx="1" transform="translate(6.012 0)" fill="#4a4a4a"/> - <rect id="Rectangle_66" data-name="Rectangle 66" width="2.537" height="2.537" rx="1" transform="translate(9.018 0)" fill="#4a4a4a"/> - <path id="Path_56" data-name="Path 56" d="M.519,0H14.981A.519.519,0,0,1,15.5.519v1.5a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,2.018V.519A.519.519,0,0,1,.519,0Zm15.97,0h1.874a.519.519,0,0,1,.519.519v1.5a.519.519,0,0,1-.519.519H16.489a.519.519,0,0,1-.519-.519V.519A.519.519,0,0,1,16.489,0Z" transform="translate(12.024 0)" fill="#4a4a4a" fill-rule="evenodd"/> - <rect id="Rectangle_67" data-name="Rectangle 67" width="2.537" height="2.537" rx="1" transform="translate(31.376 0)" fill="#4a4a4a"/> - <rect id="Rectangle_68" data-name="Rectangle 68" width="2.537" height="2.537" rx="1" transform="translate(34.382 0)" fill="#4a4a4a"/> - <rect id="Rectangle_69" data-name="Rectangle 69" width="2.537" height="2.537" rx="1" transform="translate(40.018 0)" fill="#4a4a4a"/> - <path id="Path_57" data-name="Path 57" d="M2.537,0V.561a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,.561V0Z" transform="translate(39.736 1.08) rotate(180)" fill="#4a4a4a"/> - <path id="Path_58" data-name="Path 58" d="M2.537,0V.561a.519.519,0,0,1-.519.519H.519A.519.519,0,0,1,0,.561V0Z" transform="translate(37.2 1.456)" fill="#4a4a4a"/> - </g> - <rect id="Rectangle_70" data-name="Rectangle 70" width="42.273" height="1.127" rx="0.564" transform="translate(0.915 0.556)" fill="#4a4a4a"/> - <rect id="Rectangle_71" data-name="Rectangle 71" width="2.37" height="0.752" rx="0.376" transform="translate(1.949 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_72" data-name="Rectangle 72" width="2.37" height="0.752" rx="0.376" transform="translate(5.193 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_73" data-name="Rectangle 73" width="2.37" height="0.752" rx="0.376" transform="translate(7.688 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_74" data-name="Rectangle 74" width="2.37" height="0.752" rx="0.376" transform="translate(10.183 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_75" data-name="Rectangle 75" width="2.37" height="0.752" rx="0.376" transform="translate(12.679 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_76" data-name="Rectangle 76" width="2.37" height="0.752" rx="0.376" transform="translate(15.797 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_77" data-name="Rectangle 77" width="2.37" height="0.752" rx="0.376" transform="translate(18.292 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_78" data-name="Rectangle 78" width="2.37" height="0.752" rx="0.376" transform="translate(20.788 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_79" data-name="Rectangle 79" width="2.37" height="0.752" rx="0.376" transform="translate(23.283 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_80" data-name="Rectangle 80" width="2.37" height="0.752" rx="0.376" transform="translate(26.402 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_81" data-name="Rectangle 81" width="2.37" height="0.752" rx="0.376" transform="translate(28.897 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_82" data-name="Rectangle 82" width="2.37" height="0.752" rx="0.376" transform="translate(31.393 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_83" data-name="Rectangle 83" width="2.37" height="0.752" rx="0.376" transform="translate(34.512 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_84" data-name="Rectangle 84" width="2.37" height="0.752" rx="0.376" transform="translate(37.007 0.744)" fill="#d8d8d8" opacity="0.136"/> - <rect id="Rectangle_85" data-name="Rectangle 85" width="2.37" height="0.752" rx="0.376" transform="translate(39.502 0.744)" fill="#d8d8d8" opacity="0.136"/> - </g> - <path id="Path_59" data-name="Path 59" d="M123.779,148.389a2.583,2.583,0,0,0-.332.033c-.02-.078-.038-.156-.06-.234a2.594,2.594,0,1,0-2.567-4.455q-.086-.088-.174-.175a2.593,2.593,0,1,0-4.461-2.569c-.077-.022-.154-.04-.231-.06a2.6,2.6,0,1,0-5.128,0c-.077.02-.154.038-.231.06a2.594,2.594,0,1,0-4.461,2.569,10.384,10.384,0,1,0,17.314,9.992,2.592,2.592,0,1,0,.332-5.161" transform="translate(-51.054 -75.262)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_60" data-name="Path 60" d="M83,113.389h20.779V103H83Z" transform="translate(-41.443 -58.444)" fill="#3ecc5f" fill-rule="evenodd"/> - <path id="Path_61" data-name="Path 61" d="M123.389,108.944a1.3,1.3,0,1,0,0-2.6,1.338,1.338,0,0,0-.166.017c-.01-.039-.019-.078-.03-.117a1.3,1.3,0,0,0-.5-2.5,1.285,1.285,0,0,0-.783.269q-.043-.044-.087-.087a1.285,1.285,0,0,0,.263-.776,1.3,1.3,0,0,0-2.493-.509,5.195,5.195,0,1,0,0,10,1.3,1.3,0,0,0,2.493-.509,1.285,1.285,0,0,0-.263-.776q.044-.043.087-.087a1.285,1.285,0,0,0,.783.269,1.3,1.3,0,0,0,.5-2.5c.011-.038.02-.078.03-.117a1.335,1.335,0,0,0,.166.017" transform="translate(-55.859 -57.894)" fill="#44d860" fill-rule="evenodd"/> - <path id="Path_62" data-name="Path 62" d="M141.8,38.745a1.41,1.41,0,0,1-.255-.026,1.309,1.309,0,0,1-.244-.073,1.349,1.349,0,0,1-.224-.119,1.967,1.967,0,0,1-.2-.161,1.52,1.52,0,0,1-.161-.2,1.282,1.282,0,0,1-.218-.722,1.41,1.41,0,0,1,.026-.255,1.5,1.5,0,0,1,.072-.244,1.364,1.364,0,0,1,.12-.223,1.252,1.252,0,0,1,.358-.358,1.349,1.349,0,0,1,.224-.119,1.309,1.309,0,0,1,.244-.073,1.2,1.2,0,0,1,.509,0,1.262,1.262,0,0,1,.468.192,1.968,1.968,0,0,1,.2.161,1.908,1.908,0,0,1,.161.2,1.322,1.322,0,0,1,.12.223,1.361,1.361,0,0,1,.1.5,1.317,1.317,0,0,1-.379.919,1.968,1.968,0,0,1-.2.161,1.346,1.346,0,0,1-.223.119,1.332,1.332,0,0,1-.5.1m10.389-.649a1.326,1.326,0,0,1-.92-.379,1.979,1.979,0,0,1-.161-.2,1.282,1.282,0,0,1-.218-.722,1.326,1.326,0,0,1,.379-.919,1.967,1.967,0,0,1,.2-.161,1.351,1.351,0,0,1,.224-.119,1.308,1.308,0,0,1,.244-.073,1.2,1.2,0,0,1,.509,0,1.262,1.262,0,0,1,.468.192,1.967,1.967,0,0,1,.2.161,1.326,1.326,0,0,1,.379.919,1.461,1.461,0,0,1-.026.255,1.323,1.323,0,0,1-.073.244,1.847,1.847,0,0,1-.119.223,1.911,1.911,0,0,1-.161.2,1.967,1.967,0,0,1-.2.161,1.294,1.294,0,0,1-.722.218" transform="translate(-69.074 -26.006)" fill-rule="evenodd"/> - </g> - <g id="React-icon" transform="translate(906.3 541.56)"> - <path id="Path_330" data-name="Path 330" d="M263.668,117.179c0-5.827-7.3-11.35-18.487-14.775,2.582-11.4,1.434-20.477-3.622-23.382a7.861,7.861,0,0,0-4.016-1v4a4.152,4.152,0,0,1,2.044.466c2.439,1.4,3.5,6.724,2.672,13.574-.2,1.685-.52,3.461-.914,5.272a86.9,86.9,0,0,0-11.386-1.954,87.469,87.469,0,0,0-7.459-8.965c5.845-5.433,11.332-8.41,15.062-8.41V78h0c-4.931,0-11.386,3.514-17.913,9.611-6.527-6.061-12.982-9.539-17.913-9.539v4c3.712,0,9.216,2.959,15.062,8.356a84.687,84.687,0,0,0-7.405,8.947,83.732,83.732,0,0,0-11.4,1.972c-.412-1.793-.717-3.532-.932-5.2-.843-6.85.2-12.175,2.618-13.592a3.991,3.991,0,0,1,2.062-.466v-4h0a8,8,0,0,0-4.052,1c-5.039,2.9-6.168,11.96-3.568,23.328-11.153,3.443-18.415,8.947-18.415,14.757,0,5.828,7.3,11.35,18.487,14.775-2.582,11.4-1.434,20.477,3.622,23.382a7.882,7.882,0,0,0,4.034,1c4.931,0,11.386-3.514,17.913-9.611,6.527,6.061,12.982,9.539,17.913,9.539a8,8,0,0,0,4.052-1c5.039-2.9,6.168-11.96,3.568-23.328C256.406,128.511,263.668,122.988,263.668,117.179Zm-23.346-11.96c-.663,2.313-1.488,4.7-2.421,7.083-.735-1.434-1.506-2.869-2.349-4.3-.825-1.434-1.7-2.833-2.582-4.2C235.517,104.179,237.974,104.645,240.323,105.219Zm-8.212,19.1c-1.4,2.421-2.833,4.716-4.321,6.85-2.672.233-5.379.359-8.1.359-2.708,0-5.415-.126-8.069-.341q-2.232-3.2-4.339-6.814-2.044-3.523-3.73-7.136c1.112-2.4,2.367-4.805,3.712-7.154,1.4-2.421,2.833-4.716,4.321-6.85,2.672-.233,5.379-.359,8.1-.359,2.708,0,5.415.126,8.069.341q2.232,3.2,4.339,6.814,2.044,3.523,3.73,7.136C234.692,119.564,233.455,121.966,232.11,124.315Zm5.792-2.331c.968,2.4,1.793,4.805,2.474,7.136-2.349.574-4.823,1.058-7.387,1.434.879-1.381,1.757-2.8,2.582-4.25C236.4,124.871,237.167,123.419,237.9,121.984ZM219.72,141.116a73.921,73.921,0,0,1-4.985-5.738c1.614.072,3.263.126,4.931.126,1.685,0,3.353-.036,4.985-.126A69.993,69.993,0,0,1,219.72,141.116ZM206.38,130.555c-2.546-.377-5-.843-7.352-1.417.663-2.313,1.488-4.7,2.421-7.083.735,1.434,1.506,2.869,2.349,4.3S205.5,129.192,206.38,130.555ZM219.63,93.241a73.924,73.924,0,0,1,4.985,5.738c-1.614-.072-3.263-.126-4.931-.126-1.686,0-3.353.036-4.985.126A69.993,69.993,0,0,1,219.63,93.241ZM206.362,103.8c-.879,1.381-1.757,2.8-2.582,4.25-.825,1.434-1.6,2.869-2.331,4.3-.968-2.4-1.793-4.805-2.474-7.136C201.323,104.663,203.8,104.179,206.362,103.8Zm-16.227,22.449c-6.348-2.708-10.454-6.258-10.454-9.073s4.106-6.383,10.454-9.073c1.542-.663,3.228-1.255,4.967-1.811a86.122,86.122,0,0,0,4.034,10.92,84.9,84.9,0,0,0-3.981,10.866C193.38,127.525,191.694,126.915,190.134,126.252Zm9.647,25.623c-2.439-1.4-3.5-6.724-2.672-13.574.2-1.686.52-3.461.914-5.272a86.9,86.9,0,0,0,11.386,1.954,87.465,87.465,0,0,0,7.459,8.965c-5.845,5.433-11.332,8.41-15.062,8.41A4.279,4.279,0,0,1,199.781,151.875Zm42.532-13.663c.843,6.85-.2,12.175-2.618,13.592a3.99,3.99,0,0,1-2.062.466c-3.712,0-9.216-2.959-15.062-8.356a84.689,84.689,0,0,0,7.405-8.947,83.731,83.731,0,0,0,11.4-1.972A50.194,50.194,0,0,1,242.313,138.212Zm6.9-11.96c-1.542.663-3.228,1.255-4.967,1.811a86.12,86.12,0,0,0-4.034-10.92,84.9,84.9,0,0,0,3.981-10.866c1.775.556,3.461,1.165,5.039,1.829,6.348,2.708,10.454,6.258,10.454,9.073C259.67,119.994,255.564,123.562,249.216,126.252Z" fill="#61dafb"/> - <path id="Path_331" data-name="Path 331" d="M320.8,78.4Z" transform="translate(-119.082 -0.328)" fill="#61dafb"/> - <circle id="Ellipse_112" data-name="Ellipse 112" cx="8.194" cy="8.194" r="8.194" transform="translate(211.472 108.984)" fill="#61dafb"/> - <path id="Path_332" data-name="Path 332" d="M520.5,78.1Z" transform="translate(-282.975 -0.082)" fill="#61dafb"/> - </g> - </g> -</svg> diff --git a/static/img/undraw_docusaurus_tree.svg b/static/img/undraw_docusaurus_tree.svg deleted file mode 100644 index d9161d3..0000000 --- a/static/img/undraw_docusaurus_tree.svg +++ /dev/null @@ -1,40 +0,0 @@ -<svg xmlns="http://www.w3.org/2000/svg" width="1129" height="663" viewBox="0 0 1129 663"> - <title>Focus on What Matters</title> - <circle cx="321" cy="321" r="321" fill="#f2f2f2" /> - <ellipse cx="559" cy="635.49998" rx="514" ry="27.50002" fill="#3f3d56" /> - <ellipse cx="558" cy="627" rx="460" ry="22" opacity="0.2" /> - <rect x="131" y="152.5" width="840" height="50" fill="#3f3d56" /> - <path d="M166.5,727.3299A21.67009,21.67009,0,0,0,188.1701,749H984.8299A21.67009,21.67009,0,0,0,1006.5,727.3299V296h-840Z" transform="translate(-35.5 -118.5)" fill="#3f3d56" /> - <path d="M984.8299,236H188.1701A21.67009,21.67009,0,0,0,166.5,257.6701V296h840V257.6701A21.67009,21.67009,0,0,0,984.8299,236Z" transform="translate(-35.5 -118.5)" fill="#3f3d56" /> - <path d="M984.8299,236H188.1701A21.67009,21.67009,0,0,0,166.5,257.6701V296h840V257.6701A21.67009,21.67009,0,0,0,984.8299,236Z" transform="translate(-35.5 -118.5)" opacity="0.2" /> - <circle cx="181" cy="147.5" r="13" fill="#3f3d56" /> - <circle cx="217" cy="147.5" r="13" fill="#3f3d56" /> - <circle cx="253" cy="147.5" r="13" fill="#3f3d56" /> - <rect x="168" y="213.5" width="337" height="386" rx="5.33505" fill="#606060" /> - <rect x="603" y="272.5" width="284" height="22" rx="5.47638" fill="#2e8555" /> - <rect x="537" y="352.5" width="416" height="15" rx="5.47638" fill="#2e8555" /> - <rect x="537" y="396.5" width="416" height="15" rx="5.47638" fill="#2e8555" /> - <rect x="537" y="440.5" width="416" height="15" rx="5.47638" fill="#2e8555" /> - <rect x="537" y="484.5" width="416" height="15" rx="5.47638" fill="#2e8555" /> - <rect x="865" y="552.5" width="88" height="26" rx="7.02756" fill="#3ecc5f" /> - <path d="M1088.60287,624.61594a30.11371,30.11371,0,0,0,3.98291-15.266c0-13.79652-8.54358-24.98081-19.08256-24.98081s-19.08256,11.18429-19.08256,24.98081a30.11411,30.11411,0,0,0,3.98291,15.266,31.248,31.248,0,0,0,0,30.53213,31.248,31.248,0,0,0,0,30.53208,31.248,31.248,0,0,0,0,30.53208,30.11408,30.11408,0,0,0-3.98291,15.266c0,13.79652,8.54353,24.98081,19.08256,24.98081s19.08256-11.18429,19.08256-24.98081a30.11368,30.11368,0,0,0-3.98291-15.266,31.248,31.248,0,0,0,0-30.53208,31.248,31.248,0,0,0,0-30.53208,31.248,31.248,0,0,0,0-30.53213Z" transform="translate(-35.5 -118.5)" fill="#3f3d56" /> - <ellipse cx="1038.00321" cy="460.31783" rx="19.08256" ry="24.9808" fill="#3f3d56" /> - <ellipse cx="1038.00321" cy="429.78574" rx="19.08256" ry="24.9808" fill="#3f3d56" /> - <path d="M1144.93871,339.34489a91.61081,91.61081,0,0,0,7.10658-10.46092l-50.141-8.23491,54.22885.4033a91.566,91.566,0,0,0,1.74556-72.42605l-72.75449,37.74139,67.09658-49.32086a91.41255,91.41255,0,1,0-150.971,102.29805,91.45842,91.45842,0,0,0-10.42451,16.66946l65.0866,33.81447-69.40046-23.292a91.46011,91.46011,0,0,0,14.73837,85.83669,91.40575,91.40575,0,1,0,143.68892,0,91.41808,91.41808,0,0,0,0-113.02862Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M981.6885,395.8592a91.01343,91.01343,0,0,0,19.56129,56.51431,91.40575,91.40575,0,1,0,143.68892,0C1157.18982,436.82067,981.6885,385.60008,981.6885,395.8592Z" transform="translate(-35.5 -118.5)" opacity="0.1" /> - <path d="M365.62,461.43628H477.094v45.12043H365.62Z" transform="translate(-35.5 -118.5)" fill="#fff" fill-rule="evenodd" /> - <path d="M264.76252,608.74122a26.50931,26.50931,0,0,1-22.96231-13.27072,26.50976,26.50976,0,0,0,22.96231,39.81215H291.304V608.74122Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M384.17242,468.57061l92.92155-5.80726V449.49263a26.54091,26.54091,0,0,0-26.54143-26.54143H331.1161l-3.31768-5.74622a3.83043,3.83043,0,0,0-6.63536,0l-3.31768,5.74622-3.31767-5.74622a3.83043,3.83043,0,0,0-6.63536,0l-3.31768,5.74622L301.257,417.205a3.83043,3.83043,0,0,0-6.63536,0L291.304,422.9512c-.02919,0-.05573.004-.08625.004l-5.49674-5.49541a3.8293,3.8293,0,0,0-6.4071,1.71723l-1.81676,6.77338L270.607,424.1031a3.82993,3.82993,0,0,0-4.6912,4.69253l1.84463,6.89148-6.77072,1.81411a3.8315,3.8315,0,0,0-1.71988,6.40975l5.49673,5.49673c0,.02787-.004.05574-.004.08493l-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74621,3.31768L259.0163,466.081a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31767a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31767a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31768a3.83042,3.83042,0,0,0,0,6.63535l5.74622,3.31768-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768L259.0163,558.976a3.83042,3.83042,0,0,0,0,6.63535l5.74622,3.31768-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768-5.74622,3.31768a3.83042,3.83042,0,0,0,0,6.63535l5.74622,3.31768-5.74622,3.31768a3.83043,3.83043,0,0,0,0,6.63536l5.74622,3.31768A26.54091,26.54091,0,0,0,291.304,635.28265H450.55254A26.5409,26.5409,0,0,0,477.094,608.74122V502.5755l-92.92155-5.80727a14.12639,14.12639,0,0,1,0-28.19762" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M424.01111,635.28265h39.81214V582.19979H424.01111Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M490.36468,602.10586a6.60242,6.60242,0,0,0-.848.08493c-.05042-.19906-.09821-.39945-.15393-.59852A6.62668,6.62668,0,1,0,482.80568,590.21q-.2203-.22491-.44457-.44589a6.62391,6.62391,0,1,0-11.39689-6.56369c-.1964-.05575-.39414-.10218-.59056-.15262a6.63957,6.63957,0,1,0-13.10086,0c-.1964.05042-.39414.09687-.59056.15262a6.62767,6.62767,0,1,0-11.39688,6.56369,26.52754,26.52754,0,1,0,44.23127,25.52756,6.6211,6.6211,0,1,0,.848-13.18579" transform="translate(-35.5 -118.5)" fill="#44d860" fill-rule="evenodd" /> - <path d="M437.28182,555.65836H477.094V529.11693H437.28182Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M490.36468,545.70532a3.31768,3.31768,0,0,0,0-6.63536,3.41133,3.41133,0,0,0-.42333.04247c-.02655-.09953-.04911-.19907-.077-.29859a3.319,3.319,0,0,0-1.278-6.37923,3.28174,3.28174,0,0,0-2.00122.68742q-.10947-.11346-.22294-.22295a3.282,3.282,0,0,0,.67149-1.98265,3.31768,3.31768,0,0,0-6.37-1.2992,13.27078,13.27078,0,1,0,0,25.54082,3.31768,3.31768,0,0,0,6.37-1.2992,3.282,3.282,0,0,0-.67149-1.98265q.11347-.10947.22294-.22294a3.28174,3.28174,0,0,0,2.00122.68742,3.31768,3.31768,0,0,0,1.278-6.37923c.02786-.0982.05042-.19907.077-.29859a3.41325,3.41325,0,0,0,.42333.04246" transform="translate(-35.5 -118.5)" fill="#44d860" fill-rule="evenodd" /> - <path d="M317.84538,466.081a3.31768,3.31768,0,0,1-3.31767-3.31768,9.953,9.953,0,1,0-19.90608,0,3.31768,3.31768,0,1,1-6.63535,0,16.58839,16.58839,0,1,1,33.17678,0,3.31768,3.31768,0,0,1-3.31768,3.31768" transform="translate(-35.5 -118.5)" fill-rule="evenodd" /> - <path d="M370.92825,635.28265h79.62429A26.5409,26.5409,0,0,0,477.094,608.74122v-92.895H397.46968a26.54091,26.54091,0,0,0-26.54143,26.54143Z" transform="translate(-35.5 -118.5)" fill="#ffff50" fill-rule="evenodd" /> - <path d="M457.21444,556.98543H390.80778a1.32707,1.32707,0,0,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414m0,26.54143H390.80778a1.32707,1.32707,0,1,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414m0,26.54143H390.80778a1.32707,1.32707,0,1,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414m0-66.10674H390.80778a1.32707,1.32707,0,0,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414m0,26.29459H390.80778a1.32707,1.32707,0,0,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414m0,26.54143H390.80778a1.32707,1.32707,0,0,1,0-2.65414h66.40666a1.32707,1.32707,0,0,1,0,2.65414M477.094,474.19076c-.01592,0-.0292-.008-.04512-.00663-4.10064.13934-6.04083,4.24132-7.75274,7.86024-1.78623,3.78215-3.16771,6.24122-5.43171,6.16691-2.50685-.09024-3.94007-2.92222-5.45825-5.91874-1.74377-3.44243-3.73438-7.34667-7.91333-7.20069-4.04227.138-5.98907,3.70784-7.70631,6.857-1.82738,3.35484-3.07084,5.39455-5.46887,5.30033-2.55727-.09289-3.91619-2.39536-5.48877-5.06013-1.75306-2.96733-3.77951-6.30359-7.8775-6.18946-3.97326.13669-5.92537,3.16507-7.64791,5.83912-1.82207,2.82666-3.09872,4.5492-5.52725,4.447-2.61832-.09289-3.9706-2.00388-5.53522-4.21611-1.757-2.4856-3.737-5.299-7.82308-5.16231-3.88567.13271-5.83779,2.61434-7.559,4.80135-1.635,2.07555-2.9116,3.71846-5.61218,3.615a1.32793,1.32793,0,1,0-.09555,2.65414c4.00377.134,6.03154-2.38873,7.79257-4.6275,1.562-1.9853,2.91027-3.69855,5.56441-3.78879,2.55594-.10882,3.75429,1.47968,5.56707,4.04093,1.7212,2.43385,3.67465,5.19416,7.60545,5.33616,4.11789.138,6.09921-2.93946,7.8536-5.66261,1.56861-2.43385,2.92221-4.53461,5.50734-4.62352,2.37944-.08892,3.67466,1.79154,5.50072,4.885,1.72121,2.91557,3.67069,6.21865,7.67977,6.36463,4.14709.14332,6.14965-3.47693,7.89475-6.68181,1.51155-2.77092,2.93814-5.38791,5.46621-5.4755,2.37944-.05573,3.62025,2.11668,5.45558,5.74622,1.71459,3.388,3.65875,7.22591,7.73019,7.37321l.22429.004c4.06614,0,5.99571-4.08074,7.70364-7.68905,1.51154-3.19825,2.94211-6.21069,5.3972-6.33411Z" transform="translate(-35.5 -118.5)" fill-rule="evenodd" /> - <path d="M344.38682,635.28265h53.08286V582.19979H344.38682Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M424.01111,602.10586a6.60242,6.60242,0,0,0-.848.08493c-.05042-.19906-.09821-.39945-.15394-.59852A6.62667,6.62667,0,1,0,416.45211,590.21q-.2203-.22491-.44458-.44589a6.62391,6.62391,0,1,0-11.39689-6.56369c-.1964-.05575-.39413-.10218-.59054-.15262a6.63957,6.63957,0,1,0-13.10084,0c-.19641.05042-.39414.09687-.59055.15262a6.62767,6.62767,0,1,0-11.39689,6.56369,26.52755,26.52755,0,1,0,44.2313,25.52756,6.6211,6.6211,0,1,0,.848-13.18579" transform="translate(-35.5 -118.5)" fill="#44d860" fill-rule="evenodd" /> - <path d="M344.38682,555.65836h53.08286V529.11693H344.38682Z" transform="translate(-35.5 -118.5)" fill="#3ecc5f" fill-rule="evenodd" /> - <path d="M410.74039,545.70532a3.31768,3.31768,0,1,0,0-6.63536,3.41133,3.41133,0,0,0-.42333.04247c-.02655-.09953-.04911-.19907-.077-.29859a3.319,3.319,0,0,0-1.278-6.37923,3.28174,3.28174,0,0,0-2.00122.68742q-.10947-.11346-.22294-.22295a3.282,3.282,0,0,0,.67149-1.98265,3.31768,3.31768,0,0,0-6.37-1.2992,13.27078,13.27078,0,1,0,0,25.54082,3.31768,3.31768,0,0,0,6.37-1.2992,3.282,3.282,0,0,0-.67149-1.98265q.11347-.10947.22294-.22294a3.28174,3.28174,0,0,0,2.00122.68742,3.31768,3.31768,0,0,0,1.278-6.37923c.02786-.0982.05042-.19907.077-.29859a3.41325,3.41325,0,0,0,.42333.04246" transform="translate(-35.5 -118.5)" fill="#44d860" fill-rule="evenodd" /> - <path d="M424.01111,447.8338a3.60349,3.60349,0,0,1-.65028-.06636,3.34415,3.34415,0,0,1-.62372-.18579,3.44679,3.44679,0,0,1-.572-.30522,5.02708,5.02708,0,0,1-.50429-.4114,3.88726,3.88726,0,0,1-.41007-.50428,3.27532,3.27532,0,0,1-.55737-1.84463,3.60248,3.60248,0,0,1,.06636-.65027,3.82638,3.82638,0,0,1,.18447-.62373,3.48858,3.48858,0,0,1,.30656-.57064,3.197,3.197,0,0,1,.91436-.91568,3.44685,3.44685,0,0,1,.572-.30523,3.344,3.344,0,0,1,.62372-.18578,3.06907,3.06907,0,0,1,1.30053,0,3.22332,3.22332,0,0,1,1.19436.491,5.02835,5.02835,0,0,1,.50429.41139,4.8801,4.8801,0,0,1,.41139.50429,3.38246,3.38246,0,0,1,.30522.57064,3.47806,3.47806,0,0,1,.25215,1.274A3.36394,3.36394,0,0,1,426.36,446.865a5.02708,5.02708,0,0,1-.50429.4114,3.3057,3.3057,0,0,1-1.84463.55737m26.54143-1.65884a3.38754,3.38754,0,0,1-2.35024-.96877,5.04185,5.04185,0,0,1-.41007-.50428,3.27532,3.27532,0,0,1-.55737-1.84463,3.38659,3.38659,0,0,1,.96744-2.34892,5.02559,5.02559,0,0,1,.50429-.41139,3.44685,3.44685,0,0,1,.572-.30523,3.3432,3.3432,0,0,1,.62373-.18579,3.06952,3.06952,0,0,1,1.30052,0,3.22356,3.22356,0,0,1,1.19436.491,5.02559,5.02559,0,0,1,.50429.41139,3.38792,3.38792,0,0,1,.96876,2.34892,3.72635,3.72635,0,0,1-.06636.65026,3.37387,3.37387,0,0,1-.18579.62373,4.71469,4.71469,0,0,1-.30522.57064,4.8801,4.8801,0,0,1-.41139.50429,5.02559,5.02559,0,0,1-.50429.41139,3.30547,3.30547,0,0,1-1.84463.55737" transform="translate(-35.5 -118.5)" fill-rule="evenodd" /> -</svg>