CINXE.COM

Our Great Migration from MongoDB to PostgreSQL | Product Hunt

<!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1"/><link rel="stylesheet" href="/_next/static/css/a72ac300b2b8aae3.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/1ea9739f23a3b69e.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/8f6f840789d23ad8.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/fa118094cc4cd9f8.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/c99d6c2024146960.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/639ca35bc51610d3.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/1571eeb1adaac6eb.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/da95359741fd339a.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/0a0d922ec8281d19.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/006228bc07977ccd.css" data-precedence="next"/><link rel="stylesheet" href="/_next/static/css/b0e0dd11aa1ac818.css" data-precedence="next"/><link rel="preload" as="script" fetchPriority="low" href="/_next/static/chunks/webpack-d2b397d461e59162.js"/><script src="/_next/static/chunks/fd9d1056-96a9c9a805849b31.js" async=""></script><script src="/_next/static/chunks/8523-44072685e11ad456.js" async=""></script><script src="/_next/static/chunks/main-app-c3ffcc96edcc8029.js" async=""></script><script src="/_next/static/chunks/53877-51c4a285eb192ef0.js" async=""></script><script src="/_next/static/chunks/46403-e33a58cdfbb894e8.js" async=""></script><script src="/_next/static/chunks/58056-751c28e77ae5a19a.js" async=""></script><script src="/_next/static/chunks/87138-0346ed4de56c8f41.js" async=""></script><script src="/_next/static/chunks/48191-5065c49d069bd01c.js" async=""></script><script src="/_next/static/chunks/14604-45e3a9aa74635210.js" async=""></script><script src="/_next/static/chunks/55579-59b56c16d22d5e09.js" async=""></script><script src="/_next/static/chunks/94531-936a58903208c445.js" async=""></script><script src="/_next/static/chunks/7851-391d4a68ffe47521.js" async=""></script><script src="/_next/static/chunks/28051-6c99bb1ef2e7af63.js" async=""></script><script src="/_next/static/chunks/23714-107263d1137b8b64.js" async=""></script><script src="/_next/static/chunks/55151-9f3a96035f27a91c.js" async=""></script><script src="/_next/static/chunks/31158-f57f0197bfdfc676.js" async=""></script><script src="/_next/static/chunks/86111-10b40af0fab64eb1.js" async=""></script><script src="/_next/static/chunks/50570-6a6ca0f37ede1d3b.js" async=""></script><script src="/_next/static/chunks/69558-1b9bff93d908a3d5.js" async=""></script><script src="/_next/static/chunks/63761-17f7fa9792e0fc0c.js" async=""></script><script src="/_next/static/chunks/95903-22bd3ff6f84beadc.js" async=""></script><script src="/_next/static/chunks/app/(main)/layout-d5b344c3d5112f09.js" async=""></script><script src="/_next/static/chunks/74468-913b2d3a1cd26fb3.js" async=""></script><script src="/_next/static/chunks/64417-22df6c507fdbe6ed.js" async=""></script><script src="/_next/static/chunks/app/(main)/not-found-97bc615d259bf592.js" async=""></script><script src="/_next/static/chunks/1997-8c211c482f7f1b80.js" async=""></script><script src="/_next/static/chunks/87620-cdf22e94cf823402.js" async=""></script><script src="/_next/static/chunks/17436-7d847d18b236a58e.js" async=""></script><script src="/_next/static/chunks/app/layout-f3770231938d0d2a.js" async=""></script><script src="/_next/static/chunks/app/(cards)/layout-8f806a8becc1daf9.js" async=""></script><script src="/_next/static/chunks/25058-f2b5f735f386b605.js" async=""></script><script src="/_next/static/chunks/app/global-error-62b3730fa3f51ebe.js" async=""></script><script src="/_next/static/chunks/ee815485-de04c5299c631099.js" async=""></script><script src="/_next/static/chunks/673e98bc-0265ffc690629011.js" async=""></script><script src="/_next/static/chunks/17873-c31f11c5f34602f7.js" async=""></script><script src="/_next/static/chunks/18489-27cb2cd16662f495.js" async=""></script><script src="/_next/static/chunks/86224-d84904eb72b0dfed.js" async=""></script><script src="/_next/static/chunks/63470-3c423fadd5b8d82e.js" async=""></script><script src="/_next/static/chunks/89792-e60b17bdd9ad5353.js" async=""></script><script src="/_next/static/chunks/3638-eb4b9de42bd38a18.js" async=""></script><script src="/_next/static/chunks/48567-5dfdc8e6fb42bbea.js" async=""></script><script src="/_next/static/chunks/59539-d4616fb2727e849e.js" async=""></script><script src="/_next/static/chunks/60732-57a9cb17d418c253.js" async=""></script><script src="/_next/static/chunks/26410-8d54001898f1c180.js" async=""></script><script src="/_next/static/chunks/10775-a9b2f35310c960a8.js" async=""></script><script src="/_next/static/chunks/16977-e4da546af4f18ac4.js" async=""></script><script src="/_next/static/chunks/78221-3b8b0bf117dcfe81.js" async=""></script><script src="/_next/static/chunks/40830-12562fb98330baca.js" async=""></script><script src="/_next/static/chunks/app/(main)/stories/%5Bslug%5D/page-0a1aea86d7645bc2.js" async=""></script><link rel="preload" href="https://www.googletagmanager.com/gtag/js?id=G-WZ46833KH9" as="script"/><link rel="preload" href="https://www.googletagmanager.com/gtm.js?id=G-WZ46833KH9" as="script"/><meta property="fb:app_id" content="1467820943460899"/><link rel="search" type="application/opensearchdescription+xml" title="ProductHunt" href="/osd.xml"/><meta name="theme-color" content="#ffffff"/><title> Our Great Migration from MongoDB to PostgreSQL | Product Hunt</title><meta name="description" content="Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone&#x27;s talking about."/><link rel="author" href="https://www.producthunt.com/@dangtony98"/><meta name="author" content="Tony Dang"/><link rel="manifest" href="/manifest.json" crossorigin="use-credentials"/><meta name="fb:app_id" content="1467820943460899"/><link rel="alternate" type="application/atom+xml" title="Product Hunt - All newest Products" href="https://www.producthunt.com/feed"/><meta property="og:title" content=" Our Great Migration from MongoDB to PostgreSQL | Product Hunt"/><meta property="og:description" content="Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone&#x27;s talking about."/><meta property="og:url" content="https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql"/><meta property="og:site_name" content="Product Hunt"/><meta property="og:locale" content="en_US"/><meta property="og:image" content="https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format&amp;fit=crop&amp;frame=1&amp;h=512&amp;w=1024"/><meta property="og:type" content="article"/><meta name="twitter:card" content="summary_large_image"/><meta name="twitter:site" content="@producthunt"/><meta name="twitter:creator" content="@dangtony98"/><meta name="twitter:title" content=" Our Great Migration from MongoDB to PostgreSQL | Product Hunt"/><meta name="twitter:description" content="Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone&#x27;s talking about."/><meta name="twitter:image" content="https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format&amp;fit=crop&amp;frame=1&amp;h=512&amp;w=1024"/><link rel="icon" href="https://ph-static.imgix.net/ph-favicon-brand-500.ico?auto=format"/><link rel="apple-touch-icon-precomposed" href="https://ph-static.imgix.net/ph-ios-icon.png?auto=format"/><link rel="chrome-webstore-item" href="https://producthunt.app.link/extension"/><script id="injection">window['__ENV__'] = {"NODE_ENV":"production"};</script><script src="/_next/static/chunks/polyfills-42372ed130431b0a.js" noModule=""></script><script>(window[Symbol.for("ApolloSSRDataTransport")] ??= []).push({"rehydrate":{":R1kq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R5kq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R2ccutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R9kcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rhkcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R2kcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R2kcutkqH1:":{"data":undefined,"loading":true,"networkStatus":1,"called":true},":Rbkcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rjkcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rckcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rkkcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rdkcutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rscutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rkutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":Rsutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R14utkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R1kutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R2sutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R34utkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R3cutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R1dkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R1tkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R3scutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R5scutkq:":{"data":{},"complete":false,"missing":"Dangling reference to missing Viewer object"},":R1scutkq:":{"data":{"viewer":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}}},"networkStatus":7},":R1scutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R7scutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rbscutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R37rrqkutkq:":{"data":{"story":{"__typename":"AnthologiesStory","id":"13201","title":"Our Great Migration from MongoDB to PostgreSQL","slug":"our-great-migration-from-mongodb-to-postgresql","description":"","headerImageUuid":"f0a85533-cc7d-43a1-8df6-88c6aae0b886.png","category":{"__typename":"Category","slug":"how_to","name":"How To"},"publishedAt":"2024-07-02T10:00:00-07:00","bodyHtml":"\u003cdiv\u003eHey Product Hunt! \u003c/div\u003e\u003cdiv\u003eI’m excited to share our story for how we recently performed a full database migration from MongoDB to PostgreSQL at\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e Infisical\u003c/a\u003e. This entailed deliberating the initiative, adopting new tech, creating new database schemas, rewiring logic, re-writing queries, to migrating millions (if not billions) of database records over to PostgreSQL.\u003c/div\u003e\u003ch2\u003eWhere we started\u003c/h2\u003e\u003cdiv\u003eWhen we first built\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e Infisical\u003c/a\u003e, we built it with the stack that felt most familiar with the team. As part of that stack, we chose MongoDB + Mongoose ORM because the combination presented least overhead and allowed us to ship quality features quickly. As Donald Knuth states\u003cem\u003e, “premature optimization is the root of all evil,” \u003c/em\u003eand there was certainly no need for further optimization at the time.\u003c/div\u003e\u003cdiv\u003eAt the time, we were also more focused on building Infisical Cloud, the managed SaSS offering, and given this focus, we didn’t anticipate as many users self-hosting the product and hence it wasn’t designed with that use-case in mind.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eNote\u003c/strong\u003e: Looking back, we followed YC’s traditional advice that you should not over-optimize especially when just starting out — Just pick a stack that you can build with most quickly, reduce scope, and hack together the MVP. We continue to follow this principle with optimizations made overtime (e.g. moving from Heroku to DigitalOcean to AWS, revamping features based on feedback, etc.).\u003c/div\u003e\u003ch2\u003eWhy not MongoDB?\u003c/h2\u003e\u003cdiv\u003eWhile MongoDB served \u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eInfisical\u003c/a\u003ewell in the early days, it started showing signs of shortcoming when the use-case of our product evolved beyond the managed service. As time passed, we found that many organizations, especially ones operating at the intersection of compliance and security, preferred self-hosting Infisical as opposed to using Infisical Cloud; others had on-prem requirements that needed to be met.\u003c/div\u003e\u003cdiv\u003eWith demand growing for self-hosting Infisical, we found ourselves shipping many features catered to reducing the learning curve needed to self-host Infisical and, as part of that, we ended up leaving MongoDB in favor of PostgreSQL.\u003c/div\u003e\u003cdiv\u003eIn practice, we and our customers often ran into constraints around the capabilities and usability of MongoDB like the lack of support for \u003ca href=\"https://en.wikipedia.org/wiki/Database_transaction\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003etransactions\u003c/a\u003e, clean-up, inconsistent versioning across managed offerings by cloud providers, not to mention issues associated with schema-less database design structure.\u003c/div\u003e\u003cdiv\u003eAmongst a dozen more reasons, we came to the realization that a full database migration to something more universal was the ultimate feature needed to make Infisical more accessible to teams and organizations around the world.\u003c/div\u003e\u003ch2\u003eWhy PostgreSQL?\u003c/h2\u003e\u003cdiv\u003eWhen searching for a new database, we began by listing out what aspects mattered most to us: ease of management (i.e. configuration, deployment, and scaling included), built-in support for\u003ca href=\"https://en.wikipedia.org/wiki/Database_transaction\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e transactions\u003c/a\u003e, and relational capabilities. As part of the deliberation, we also contemplated whether or not we should build our own integrated storage or pursue an external storage solution.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eHere’s what that meant for each option:\u003c/strong\u003e\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eIntegrated storage:\u003c/strong\u003e We could package in a database system like \u003ca href=\"https://www.sqlite.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eSQLite\u003c/a\u003e directly into Infisical and pursue a horizontal replication strategy to reduce latency by avoiding extra network hops. In this model, scaling the system would mean deploying multiple instances of Infisical and have them communicate with each other via some \u003ca href=\"https://en.wikipedia.org/wiki/Consensus_(computer_science)\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econsensus algorithm\u003c/a\u003e like \u003ca href=\"https://en.wikipedia.org/wiki/Raft_(algorithm)\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eRaft\u003c/a\u003e. While this seemed like an excellent solution since customer’s wouldn’t need to connect any dependencies to run Infisical, the tooling ecosystem to execute this vision felt immature and the engineering effort required for it felt nothing short of overwhelming.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eExternal storage\u003c/strong\u003e: We could simply replace MongoDB with another database(s) like PostgreSQL or MySQL and use its built-in scaling capabilities. Although this solution didn’t fully eliminate friction associated with needing external dependencies to use Infisical, we felt that it already delivered significant benefits by virtue of not being MongoDB. When it came to supporting one or multiple databases, we felt that supporting multiple would mean missing out on the unique advantages of each solution; it would also add to our engineering overhead.\u003c/div\u003e\u003cdiv\u003eAfter careful consideration, we chose PostgreSQL. Beyond having a vibrant community, extensive documentation, and a myriad of solutions and extensions available, we appreciated most its open source nature and how the vast majority of cloud providers offered managed services of PostgreSQL.\u003c/div\u003e\u003cdiv\u003eAbove all, this meant that users of Infisical could more easily self-host our platform on any cloud provider and pair it with its corresponding managed PostgreSQL service. Moreover, given how widely-adopted the database has become, we were confident that users would have less trouble operating it when using Infisical.\u003c/div\u003e\u003ch2\u003eWhat about the ORM?\u003c/h2\u003e\u003cdiv\u003eAfter settling on PostgreSQL, we needed to figure out how our application would interact with the database. Right off the bat, we wanted something comparable to our experience with MongoDB where we used Mongoose ORM. So, we began evaluating candidates on the basis of maturity, visualization and migration support, and appropriate level of abstraction; we primarily considered \u003ca href=\"https://orm.drizzle.team/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eDrizzle ORM\u003c/a\u003e, \u003ca href=\"https://www.prisma.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ePrisma ORM\u003c/a\u003e, \u003ca href=\"https://typeorm.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eTypeORM\u003c/a\u003e, and \u003ca href=\"https://knexjs.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eKnex.js\u003c/a\u003e, a query builder.\u003c/div\u003e\u003cdiv\u003eAt the end, we decided to use Knex.js, a query builder, instead of a ORM to maintain better control over the database. While admittedly, going with raw SQL would be most versatile with least abstraction in place, we felt the approach would be far too error-prone and frankly cumbersome to maintain, especially without proper TypeScript support. Moreover, beyond being close to bare SQL, Knex.js came with its own toolkit for seeding and migration, had a mature ecosystem with excellent documentation and answers for almost any possible query. Coupled with some custom Zod integration work, we managed to get it to a satisfactory level for TypeScript support.\u003c/div\u003e\u003cdiv\u003eHaving decided on the database and ORM, we kicked off a process that would ultimately result in a re-write of dozens of data structures and hundreds of queries across the application.\u003c/div\u003e\u003ch2\u003eHow did we plan the migration?\u003c/h2\u003e\u003cdiv\u003eToward the end of the code-rewrite, we started to think about how we would conduct the migration operation to map our MongoDB data to PostgreSQL with minimal disruption to the Infisical Cloud platform.\u003c/div\u003e\u003cdiv\u003eGiven Infisical’s critical role in customers infrastructure, we immediately ruled out the possibility of having any absolute downtime. The part where we had to make a compromise was in disallowing write operations during the brief migration window (i.e. customers would not be able to create or update application configuration) in exchange for higher guarantee of data integrity. This tradeoff seemed acceptable given that customers primarily fetched back secrets from Infisical and, to a much lesser extent, updated their application configuration on a second-by-second basis.\u003c/div\u003e\u003cdiv\u003eNext, regarding the actual migration operation, we needed to dump data from MongoDB, transform it carefully, and insert it back into PostgreSQL. As we audited the migration sequence, we grappled through challenges like making sure that various tree-like structures from NoSQL were correctly transformed to their relational counterparts; this was particularly sensitive for data structures like folders that had recursive considerations. We also found that we needed a persistent way to store and map identifiers in MongoDB to those in PostgreSQL; doing so in-memory would not work considering how much data we were dealing with. In the end, we settled for using the \u003ca href=\"https://leveljs.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eLevelDB\u003c/a\u003e key-value store to assist with identifier storage and lookup operations. With it, we would move data table-by-table into PostgreSQL.\u003c/div\u003e\u003ch2\u003eThe Great Migration\u003c/h2\u003e\u003cdiv\u003eFinally, we were ready to conduct the migration. At this point, folks not directly involved in the codebase re-write had spent a much-needed quarter improving other aspects of Infisical including making frontend changes, performing maintenance patches, extending client functionality, and writing up better documentation. We now all reconvened to prepare for the migration itself that is replacing the application codebase with the new one and transferring data over from MongoDB to PostgreSQL.\u003c/div\u003e\u003cdiv\u003eAs part of the preparation, we drafted a detailed migration checklist with an expected timeline.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eOn a high-level, the plan looked something like this:\u003c/strong\u003e\u003c/div\u003e\u003cul\u003e\u003cli\u003eIn the weeks building up to the migration, we would communicate in advance via both email and in-app banner to let users know about the impending database upgrade. We would conduct thorough testing of every feature flow on the platform and perform trial runs for the migration.\u003c/li\u003e\u003cli\u003eThe migration itself would occur within a six-hour window where only read operations would be allowed to the platform. During this window, we would run the migration script to move data from MongoDB to PostgreSQL, check that no data was lost, and if successful switch the DNS to the new instance. There were of course backup plans in place in case things went south.\u003c/li\u003e\u003cli\u003eFinally, after the migration, we would iron out any residual issues and start rolling out new documentation for working with Infisical and PostgreSQL.\u003c/li\u003e\u003c/ul\u003e\u003cdiv\u003eFortunately, the migration turned out to be smooth with zero data loss and only a few non-essential incidents of feature malfunction; we ironed out these bugs out in the following 36 hours with minimal impact to customers. Overall, we considered the initiative to be a success given the objective at hand, the scope of the task, and the resulting execution of it.\u003c/div\u003e\u003ch2\u003eClosing Thoughts\u003c/h2\u003e\u003cdiv\u003eThe decision to move from MongoDB to PostgreSQL was not an easy one from the get-go. All in all, the initiative took us 3–4 months to perform with careful planning and discussion around why we needed to perform it, how we were going to do it; and then to execute it all with care. For those of you who are still with me, I’d highly recommend thinking through the use-case and implementation deeply before attempting such a big endeavor.\u003c/div\u003e\u003cdiv\u003eOverall, I’m extremely happy that everything went according to plan and we were able to deliver such a huge update that will make a large difference to users of \u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eInfisical\u003c/a\u003e moving forward!\u003c/div\u003e\u003cdiv\u003e\u003ca href=\"https://www.producthunt.com/@dangtony98\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e\u003cem\u003eTony\u003c/em\u003e\u003c/a\u003e\u003cem\u003e is a co-founder of \u003c/em\u003e\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e\u003cem\u003eInfisical\u003c/em\u003e\u003c/a\u003e\u003cem\u003e where he works on all things Engineering and Product; he's a YC alum and Cornell grad where he studied CS.\u003c/em\u003e\u003c/div\u003e","canManage":false,"minsToRead":9,"structuredData":{"@context":"https://schema.org","@type":"NewsArticle","mainEntityOfPage":{"@type":"WebPage","@id":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql"},"headline":"Our Great Migration from MongoDB to PostgreSQL","image":["https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024"],"author":{"@type":"Person","name":"Tony Dang","image":"https://ph-avatars.imgix.net/3999558/original.jpeg?auto=format\u0026fit=crop\u0026crop=faces\u0026w=100\u0026h=100","url":"https://www.producthunt.com/@dangtony98"},"publisher":{"@type":"Organization","name":"Product Hunt","logo":{"@type":"ImageObject","url":"https://ph-static.imgix.net/ph-publisher-logo.png","width":220,"height":60}},"description":"","datePublished":"2024-07-02T10:00:00.000-07:00","dateModified":"2024-11-19T08:16:50.072-08:00"},"meta":{"__typename":"MetaTags","title":"Our Great Migration from MongoDB to PostgreSQL","description":"","creator":"@dangtony98","canonicalUrl":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql","image":"https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024","type":"article"},"moreStories":[{"__typename":"AnthologiesStory","id":"13663","title":"How to Detect AI Content with Keystroke Tracking","slug":"how-to-detect-ai-content-with-keystroke-tracking","headerImageUuid":"3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png","minsToRead":3,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"5149485","name":"matt hardy","username":"mdahardy"},"authorName":"Mathew Hardy","authorUrl":""},{"__typename":"AnthologiesStory","id":"13630","title":"An Initially Failed PH Launch Turned Around to Get Us 850+ Paid Subscribers","slug":"initially-failed-ph-launch-turned-around-to-get-us-850-paid-subscribers","headerImageUuid":"3c43ae0c-75e2-45b7-8e83-977c67ab4c92.webp","minsToRead":3,"category":{"__typename":"Category","name":"Makers","slug":"makers"},"author":{"__typename":"User","id":"2713059","name":"Anton Osika","username":"antonosika"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13597","title":"The Case for Supabase","slug":"the-case-for-supabase","headerImageUuid":"a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png","minsToRead":9,"category":{"__typename":"Category","name":"Opinions","slug":"opinions"},"author":{"__typename":"User","id":"7512242","name":"Sanjana Friedman","username":"sanjanaf"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13564","title":"3.5 Years, 12 Hard Pivots, Still Not Dead","slug":"3-5-years-12-hard-pivots-still-not-dead","headerImageUuid":"d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png","minsToRead":10,"category":{"__typename":"Category","name":"Opinions","slug":"opinions"},"author":{"__typename":"User","id":"3896127","name":"Vaibhav Gupta","username":"hellovai"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13465","title":"Cofounder Mode: A Tactical Guide to Finding a Cofounder","slug":"cofounder-mode-a-tactical-guide-to-finding-a-cofounder","headerImageUuid":"d406b3ba-2d4d-4d08-a966-5610980e802d.webp","minsToRead":10,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"13382","name":"Rob Balian","username":"robbalian"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13432","title":"A Founder’s Guide to AI Fine-Tuning","slug":"a-founder-s-guide-to-ai-fine-tuning","headerImageUuid":"2cd80df4-e3ff-43dd-8885-ad4a6b499b80.webp","minsToRead":5,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"970351","name":"Kyle Corbitt","username":"corbt"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13366","title":"A Better Way to Get Your First 10 B2B Customers","slug":"a-better-way-to-get-your-first-10-b2b-customers","headerImageUuid":"3850ebe3-c944-4989-9513-96bd2d5c8574.png","minsToRead":6,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"3090719","name":"Chris Bakke","username":"chrisbakke"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13399","title":"The Cold Email Template that Got Me an 8% Reply Rate","slug":"the-cold-email-template-that-got-me-an-8-reply-rate","headerImageUuid":"618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png","minsToRead":4,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"5187421","name":"Xiaohan Shen","username":"shen_xh"},"authorName":"","authorUrl":""}],"authorName":"","authorUrl":"","author":{"__typename":"User","id":"3999558","name":"Tony Dang","username":"dangtony98","avatarUrl":"https://ph-avatars.imgix.net/3999558/original.jpeg"},"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql","hasVoted":false,"votesCount":13,"name":"Our Great Migration from MongoDB to PostgreSQL","canComment":false,"commentsCount":7,"threads":{"__typename":"CommentConnection","totalCount":7,"edges":[{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3632591","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"I'm also advocating a move from MongoDB to PostgreSQL in our org, I will use this post as a supporting argument 🫡 \nBtw, we're launching soon on ProductHunt and would love your support! \u003ca href=\"https://www.producthunt.com/products/supergpt\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ehttps://www.producthunt.com/prod...\u003c/a\u003e","bodyHtml":"I'm also advocating a move from MongoDB to PostgreSQL in our org, I will use this post as a supporting argument 🫡 \nBtw, we're launching soon on ProductHunt and would love your support! \u003ca href=\"https://www.producthunt.com/products/supergpt\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ehttps://www.producthunt.com/prod...\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"4002294","name":"Kabir Singh Shekhawat","username":"kabir_singh_shekhawat","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":{"__typename":"Product","id":"592052","name":"Superjoin","logoUuid":"76852a3a-ded0-494c-84d1-6b56d507dba7.png","isNoLongerOnline":false},"avatarUrl":"https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg","karmaBadge":{"__typename":"KarmaBadge","kind":"BRONZE","score":150}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3632591","createdAt":"2024-07-08T23:36:51-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3632591","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"4141093","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"It's nice seeing this informative content. \u003ca href=\"https://premierconcretesanantonio.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econcrete patio\u003c/a\u003e","bodyHtml":"It's nice seeing this informative content. \u003ca href=\"https://premierconcretesanantonio.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econcrete patio\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"6873315","name":"Oli Seo","username":"oli_seo","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/6873315/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=4141093","createdAt":"2024-11-19T08:16:50-08:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=4141093","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3630185","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Switching from MongoDB to PostgreSQL is a big move, especially considering the shift from a flexible schema to a structured one. How do you think this transition will affect the way you handle future scalability and feature development? The migration seems well-planned and executed, but I'm curious about the most unexpected challenge you faced during the process.","bodyHtml":"Switching from MongoDB to PostgreSQL is a big move, especially considering the shift from a flexible schema to a structured one. How do you think this transition will affect the way you handle future scalability and feature development? The migration seems well-planned and executed, but I'm curious about the most unexpected challenge you faced during the process.","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7261259","name":"Naomi | Beeyond AI","username":"naomigarcia","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg","karmaBadge":{"__typename":"KarmaBadge","kind":"BRONZE","score":455}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3630185","createdAt":"2024-07-08T09:33:08-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3630185","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3785701","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Playing games is getting a lot of attention from young people, especially students. So when these ages use it, do they have to pay any fees to download the game? That is worrying and today I will introduce to you the game \u003ca href=\"https://slopeball.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eslope ball\u003c/a\u003e which is extremely free and also helps brain thinking. Using it for free like that helps all ages to use it without having to pay complicated fees. The game is a great experience if you are really passionate and find a suitable game. Not only does it help with thinking but it also helps you reduce work stress. We should need to release and not be constrained that playing games will be negative and lead to social evils. Many people think that this opinion is wrong, but this is not one of the things that makes you worry. So believe in the game and choose the right game as we introduce to experience it in the most correct way.","bodyHtml":"Playing games is getting a lot of attention from young people, especially students. So when these ages use it, do they have to pay any fees to download the game? That is worrying and today I will introduce to you the game \u003ca href=\"https://slopeball.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eslope ball\u003c/a\u003e which is extremely free and also helps brain thinking. Using it for free like that helps all ages to use it without having to pay complicated fees. The game is a great experience if you are really passionate and find a suitable game. Not only does it help with thinking but it also helps you reduce work stress. We should need to release and not be constrained that playing games will be negative and lead to social evils. Many people think that this opinion is wrong, but this is not one of the things that makes you worry. So believe in the game and choose the right game as we introduce to experience it in the most correct way.","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7473971","name":"Carter Schinner","username":"carter_schinner","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7473971/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3785701","createdAt":"2024-08-15T18:50:36-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3785701","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3892615","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Looking forward for more post. \u003ca href=\"https://seattle-waterheaterrepair.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ewater heater repair seattle wa\u003c/a\u003e","bodyHtml":"Looking forward for more post. \u003ca href=\"https://seattle-waterheaterrepair.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ewater heater repair seattle wa\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7579058","name":"Angel Brown","username":"angel_brown2","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7579058/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3892615","createdAt":"2024-09-11T04:11:35-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3892615","hasVoted":false,"votesCount":0}}],"pageInfo":{"__typename":"PageInfo","endCursor":"NQ","hasNextPage":true}}}},"networkStatus":7},":R37rrqkutkqH1:":{"data":{"viewer":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}}},"networkStatus":7},":R1kr7rrqkutkq:":{"data":undefined,"loading":true,"networkStatus":1,"called":true},":Rlr7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rlr7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R2lr7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R2lr7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rlqq9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rlqq9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R2u9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1iu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rb5iu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5iu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5iu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5iu9r7rrqkutkqH2:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5iu9r7rrqkutkqH3:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5iu9r7rrqkutkqH4:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5iu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5iu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R4u9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1ku9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rb5ku9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ku9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ku9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ku9r7rrqkutkqH2:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ku9r7rrqkutkqH3:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ku9r7rrqkutkqH4:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5ku9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5ku9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R6u9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1mu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rb5mu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5mu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5mu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5mu9r7rrqkutkqH2:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5mu9r7rrqkutkqH3:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5mu9r7rrqkutkqH4:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5mu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5mu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R8u9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1ou9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rb5ou9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ou9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ou9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ou9r7rrqkutkqH2:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ou9r7rrqkutkqH3:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5ou9r7rrqkutkqH4:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5ou9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5ou9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rau9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1qu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rb5qu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5qu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5qu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5qu9r7rrqkutkqH2:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5qu9r7rrqkutkqH3:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rt5qu9r7rrqkutkqH4:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5qu9r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmt5qu9r7rrqkutkqH1:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R136r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra36r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R156r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rm56r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra56r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R176r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rm76r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra76r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R196r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rm96r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Ra96r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1b6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmb6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rab6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1d6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmd6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rad6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1f6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmf6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Raf6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":R1h6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rmh6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined},":Rah6r7rrqkutkq:":{"data":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}},"complete":true,"missing":undefined}},"events":[{"type":"started","options":{"skip":false,"fetchPolicy":"cache-first","query":"query Context{viewer{...UseCurrentUserFragment}}fragment ViewerNoticeFragment on Notice{type invite{id product{id slug}}makerSuggestion{id post{id slug}}dismissable{id isDismissed dismissableKey dismissableGroup}}fragment AbTestFragment on AbTestAssignment{name variant}fragment LaunchTipsFragment on Post{id canComment commentsCount featuredAt makerInviteUrl name url slug createdAt isMaker isHunter launchState shoutouts{id}}fragment UseCurrentUserFragment on Viewer{id email emailVerified isImpersonated analyticsIdentifyJson deviceType showCookiePolicy showCommentWarning showCaptcha showPhoneVerification isAdmin features notificationFeedItemsUnreadCount flashAlert notice{...ViewerNoticeFragment}otpRequiredFrom user{id avatarUrl isMaker name username}abTestActiveParticipations{...AbTestFragment}visitStreak{id emoji duration}recentLaunch{id ...LaunchTipsFragment}intercomUserHash ifVisitedFromMobile newsletterSettings{hasNewsletterSubscription}}","notifyOnNetworkStatusChange":false,"nextFetchPolicy":undefined},"id":"2"},{"type":"started","options":{"variables":{"slug":"our-great-migration-from-mongodb-to-postgresql","includeThreadForCommentId":null,"commentsListSubjectFilter":null,"order":null,"excludeThreadForCommentId":null,"commentsListSubjectThreadsCursor":null},"skip":false,"fetchPolicy":"cache-first","query":"query StoryShowPage($slug:String!$commentsListSubjectThreadsCursor:String=\"\"$commentsListSubjectThreadsLimit:Int=5$commentsThreadRepliesCursor:String=\"\"$commentsListSubjectFilter:ThreadFilter$includeThreadForCommentId:ID$excludeThreadForCommentId:ID$order:ThreadOrder){story(slug:$slug){id title slug description headerImageUuid category{slug name}publishedAt bodyHtml canManage minsToRead structuredData meta{title description creator canonicalUrl image type}moreStories(limit:8){id ...StoryItem}...StoryAuthor ...FacebookShareButtonFragment ...StoryVoteButtonFragment ...StoryComments}}fragment UserImage on User{id name username avatarUrl}fragment ComingSoonUserBadgeFragment on User{id promotableUpcomingEvent{id}}fragment ProductThumbnailFragment on Product{id name logoUuid isNoLongerOnline}fragment TopProductBadgeFragment on User{id topProductBadge{id product{id ...ProductThumbnailFragment}}}fragment PostStatusIconFragment on Post{id productState}fragment PostThumbnailFragment on Post{id name thumbnailImageUuid ...PostStatusIconFragment}fragment TopLaunchBadgeFragment on User{id topLaunchBadge{id post{id ...PostThumbnailFragment product{id name}}}}fragment SelectedBylineProductFragment on User{id selectedBylineProduct{id ...ProductThumbnailFragment}}fragment KarmaBadgeItemFragment on KarmaBadge{kind score}fragment KarmaBadgeFragment on User{id karmaBadge{...KarmaBadgeItemFragment}}fragment PollOptionFragment on PollOption{id text imageUuid answersCount answersPercent hasAnswered}fragment PollFragment on Poll{id answersCount hasAnswered options{id ...PollOptionFragment}}fragment CommentActionBarDestroyButtonFragment on Comment{id}fragment CommentVoteButtonFragment on Comment{id ...on Votable{id hasVoted votesCount}}fragment FacebookShareButtonFragment on Shareable{id url}fragment CommentActionBarFragment on Comment{id approvalStatus isHidden isPinned isSticky canAward canViewReplyBtn isFlaggedByViewer path createdAt canEdit canDestroy poll{id answersCount}user{id name}score inputInfo{id typingSpeed pastedIndex pastedValue}awardOptions{id option}...CommentActionBarDestroyButtonFragment ...CommentVoteButtonFragment ...FacebookShareButtonFragment}fragment CommentFragment on Comment{id award isHidden approvalStatus badges isSticky body bodyHtml subject{id}user{id name username ...ComingSoonUserBadgeFragment ...TopProductBadgeFragment ...TopLaunchBadgeFragment ...SelectedBylineProductFragment ...UserImage ...KarmaBadgeFragment}poll{id ...PollFragment}...CommentActionBarFragment}fragment CommentsThreadFragment on Comment{id isSticky visibleRepliesCount repliesCount canAward replies(first:5 after:$commentsThreadRepliesCursor focusCommentId:$includeThreadForCommentId){edges{node{id ...CommentFragment}}pageInfo{endCursor hasNextPage}}...CommentFragment}fragment CommentsListSubjectFragment on Commentable{id threads(first:$commentsListSubjectThreadsLimit after:$commentsListSubjectThreadsCursor filter:$commentsListSubjectFilter order:$order includeCommentId:$includeThreadForCommentId excludeCommentId:$excludeThreadForCommentId){totalCount edges{node{id ...CommentsThreadFragment}}pageInfo{endCursor hasNextPage}}}fragment CommentsSubjectFragment on Commentable{id commentsCount ...CommentsListSubjectFragment}fragment StoryItem on AnthologiesStory{id title slug headerImageUuid minsToRead category{name slug}author{id name username}authorName authorUrl}fragment StoryAuthor on AnthologiesStory{id authorName authorUrl author{id name username ...UserImage}}fragment StoryVoteButtonFragment on AnthologiesStory{id hasVoted votesCount}fragment StoryComments on AnthologiesStory{id name:title canComment commentsCount ...CommentsSubjectFragment}","notifyOnNetworkStatusChange":false,"nextFetchPolicy":undefined},"id":"3"},{"type":"data","id":"2","result":{"data":{"viewer":{"__typename":"Viewer","id":null,"email":null,"emailVerified":false,"isImpersonated":false,"analyticsIdentifyJson":{},"deviceType":"desktop","showCookiePolicy":false,"showCommentWarning":false,"showCaptcha":false,"showPhoneVerification":false,"isAdmin":false,"features":["ph_top_product_badge","ph_hub_top_badges","ph_phone_verification","ph_unfurl_unfeatured_posts","ph_verify_usa_phone_number","ph_verify_with_targeted_friction","ph_score_events_enabled","ph_mega_ads"],"notificationFeedItemsUnreadCount":0,"flashAlert":null,"notice":null,"otpRequiredFrom":null,"user":null,"abTestActiveParticipations":[],"visitStreak":{"__typename":"VisitStreak","id":"273bf9dc-f6d0-4275-b0b7-febd16c3872d","emoji":null,"duration":1},"recentLaunch":null,"intercomUserHash":null,"ifVisitedFromMobile":false,"newsletterSettings":{"__typename":"ViewerNewsletterSettings","hasNewsletterSubscription":false}}}}},{"type":"complete","id":"2"},{"type":"data","id":"3","result":{"data":{"story":{"__typename":"AnthologiesStory","id":"13201","title":"Our Great Migration from MongoDB to PostgreSQL","slug":"our-great-migration-from-mongodb-to-postgresql","description":"","headerImageUuid":"f0a85533-cc7d-43a1-8df6-88c6aae0b886.png","category":{"__typename":"Category","slug":"how_to","name":"How To"},"publishedAt":"2024-07-02T10:00:00-07:00","bodyHtml":"\u003cdiv\u003eHey Product Hunt! \u003c/div\u003e\u003cdiv\u003eI’m excited to share our story for how we recently performed a full database migration from MongoDB to PostgreSQL at\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e Infisical\u003c/a\u003e. This entailed deliberating the initiative, adopting new tech, creating new database schemas, rewiring logic, re-writing queries, to migrating millions (if not billions) of database records over to PostgreSQL.\u003c/div\u003e\u003ch2\u003eWhere we started\u003c/h2\u003e\u003cdiv\u003eWhen we first built\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e Infisical\u003c/a\u003e, we built it with the stack that felt most familiar with the team. As part of that stack, we chose MongoDB + Mongoose ORM because the combination presented least overhead and allowed us to ship quality features quickly. As Donald Knuth states\u003cem\u003e, “premature optimization is the root of all evil,” \u003c/em\u003eand there was certainly no need for further optimization at the time.\u003c/div\u003e\u003cdiv\u003eAt the time, we were also more focused on building Infisical Cloud, the managed SaSS offering, and given this focus, we didn’t anticipate as many users self-hosting the product and hence it wasn’t designed with that use-case in mind.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eNote\u003c/strong\u003e: Looking back, we followed YC’s traditional advice that you should not over-optimize especially when just starting out — Just pick a stack that you can build with most quickly, reduce scope, and hack together the MVP. We continue to follow this principle with optimizations made overtime (e.g. moving from Heroku to DigitalOcean to AWS, revamping features based on feedback, etc.).\u003c/div\u003e\u003ch2\u003eWhy not MongoDB?\u003c/h2\u003e\u003cdiv\u003eWhile MongoDB served \u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eInfisical\u003c/a\u003ewell in the early days, it started showing signs of shortcoming when the use-case of our product evolved beyond the managed service. As time passed, we found that many organizations, especially ones operating at the intersection of compliance and security, preferred self-hosting Infisical as opposed to using Infisical Cloud; others had on-prem requirements that needed to be met.\u003c/div\u003e\u003cdiv\u003eWith demand growing for self-hosting Infisical, we found ourselves shipping many features catered to reducing the learning curve needed to self-host Infisical and, as part of that, we ended up leaving MongoDB in favor of PostgreSQL.\u003c/div\u003e\u003cdiv\u003eIn practice, we and our customers often ran into constraints around the capabilities and usability of MongoDB like the lack of support for \u003ca href=\"https://en.wikipedia.org/wiki/Database_transaction\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003etransactions\u003c/a\u003e, clean-up, inconsistent versioning across managed offerings by cloud providers, not to mention issues associated with schema-less database design structure.\u003c/div\u003e\u003cdiv\u003eAmongst a dozen more reasons, we came to the realization that a full database migration to something more universal was the ultimate feature needed to make Infisical more accessible to teams and organizations around the world.\u003c/div\u003e\u003ch2\u003eWhy PostgreSQL?\u003c/h2\u003e\u003cdiv\u003eWhen searching for a new database, we began by listing out what aspects mattered most to us: ease of management (i.e. configuration, deployment, and scaling included), built-in support for\u003ca href=\"https://en.wikipedia.org/wiki/Database_transaction\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e transactions\u003c/a\u003e, and relational capabilities. As part of the deliberation, we also contemplated whether or not we should build our own integrated storage or pursue an external storage solution.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eHere’s what that meant for each option:\u003c/strong\u003e\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eIntegrated storage:\u003c/strong\u003e We could package in a database system like \u003ca href=\"https://www.sqlite.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eSQLite\u003c/a\u003e directly into Infisical and pursue a horizontal replication strategy to reduce latency by avoiding extra network hops. In this model, scaling the system would mean deploying multiple instances of Infisical and have them communicate with each other via some \u003ca href=\"https://en.wikipedia.org/wiki/Consensus_(computer_science)\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econsensus algorithm\u003c/a\u003e like \u003ca href=\"https://en.wikipedia.org/wiki/Raft_(algorithm)\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eRaft\u003c/a\u003e. While this seemed like an excellent solution since customer’s wouldn’t need to connect any dependencies to run Infisical, the tooling ecosystem to execute this vision felt immature and the engineering effort required for it felt nothing short of overwhelming.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eExternal storage\u003c/strong\u003e: We could simply replace MongoDB with another database(s) like PostgreSQL or MySQL and use its built-in scaling capabilities. Although this solution didn’t fully eliminate friction associated with needing external dependencies to use Infisical, we felt that it already delivered significant benefits by virtue of not being MongoDB. When it came to supporting one or multiple databases, we felt that supporting multiple would mean missing out on the unique advantages of each solution; it would also add to our engineering overhead.\u003c/div\u003e\u003cdiv\u003eAfter careful consideration, we chose PostgreSQL. Beyond having a vibrant community, extensive documentation, and a myriad of solutions and extensions available, we appreciated most its open source nature and how the vast majority of cloud providers offered managed services of PostgreSQL.\u003c/div\u003e\u003cdiv\u003eAbove all, this meant that users of Infisical could more easily self-host our platform on any cloud provider and pair it with its corresponding managed PostgreSQL service. Moreover, given how widely-adopted the database has become, we were confident that users would have less trouble operating it when using Infisical.\u003c/div\u003e\u003ch2\u003eWhat about the ORM?\u003c/h2\u003e\u003cdiv\u003eAfter settling on PostgreSQL, we needed to figure out how our application would interact with the database. Right off the bat, we wanted something comparable to our experience with MongoDB where we used Mongoose ORM. So, we began evaluating candidates on the basis of maturity, visualization and migration support, and appropriate level of abstraction; we primarily considered \u003ca href=\"https://orm.drizzle.team/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eDrizzle ORM\u003c/a\u003e, \u003ca href=\"https://www.prisma.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ePrisma ORM\u003c/a\u003e, \u003ca href=\"https://typeorm.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eTypeORM\u003c/a\u003e, and \u003ca href=\"https://knexjs.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eKnex.js\u003c/a\u003e, a query builder.\u003c/div\u003e\u003cdiv\u003eAt the end, we decided to use Knex.js, a query builder, instead of a ORM to maintain better control over the database. While admittedly, going with raw SQL would be most versatile with least abstraction in place, we felt the approach would be far too error-prone and frankly cumbersome to maintain, especially without proper TypeScript support. Moreover, beyond being close to bare SQL, Knex.js came with its own toolkit for seeding and migration, had a mature ecosystem with excellent documentation and answers for almost any possible query. Coupled with some custom Zod integration work, we managed to get it to a satisfactory level for TypeScript support.\u003c/div\u003e\u003cdiv\u003eHaving decided on the database and ORM, we kicked off a process that would ultimately result in a re-write of dozens of data structures and hundreds of queries across the application.\u003c/div\u003e\u003ch2\u003eHow did we plan the migration?\u003c/h2\u003e\u003cdiv\u003eToward the end of the code-rewrite, we started to think about how we would conduct the migration operation to map our MongoDB data to PostgreSQL with minimal disruption to the Infisical Cloud platform.\u003c/div\u003e\u003cdiv\u003eGiven Infisical’s critical role in customers infrastructure, we immediately ruled out the possibility of having any absolute downtime. The part where we had to make a compromise was in disallowing write operations during the brief migration window (i.e. customers would not be able to create or update application configuration) in exchange for higher guarantee of data integrity. This tradeoff seemed acceptable given that customers primarily fetched back secrets from Infisical and, to a much lesser extent, updated their application configuration on a second-by-second basis.\u003c/div\u003e\u003cdiv\u003eNext, regarding the actual migration operation, we needed to dump data from MongoDB, transform it carefully, and insert it back into PostgreSQL. As we audited the migration sequence, we grappled through challenges like making sure that various tree-like structures from NoSQL were correctly transformed to their relational counterparts; this was particularly sensitive for data structures like folders that had recursive considerations. We also found that we needed a persistent way to store and map identifiers in MongoDB to those in PostgreSQL; doing so in-memory would not work considering how much data we were dealing with. In the end, we settled for using the \u003ca href=\"https://leveljs.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eLevelDB\u003c/a\u003e key-value store to assist with identifier storage and lookup operations. With it, we would move data table-by-table into PostgreSQL.\u003c/div\u003e\u003ch2\u003eThe Great Migration\u003c/h2\u003e\u003cdiv\u003eFinally, we were ready to conduct the migration. At this point, folks not directly involved in the codebase re-write had spent a much-needed quarter improving other aspects of Infisical including making frontend changes, performing maintenance patches, extending client functionality, and writing up better documentation. We now all reconvened to prepare for the migration itself that is replacing the application codebase with the new one and transferring data over from MongoDB to PostgreSQL.\u003c/div\u003e\u003cdiv\u003eAs part of the preparation, we drafted a detailed migration checklist with an expected timeline.\u003c/div\u003e\u003cdiv\u003e\u003cstrong\u003eOn a high-level, the plan looked something like this:\u003c/strong\u003e\u003c/div\u003e\u003cul\u003e\u003cli\u003eIn the weeks building up to the migration, we would communicate in advance via both email and in-app banner to let users know about the impending database upgrade. We would conduct thorough testing of every feature flow on the platform and perform trial runs for the migration.\u003c/li\u003e\u003cli\u003eThe migration itself would occur within a six-hour window where only read operations would be allowed to the platform. During this window, we would run the migration script to move data from MongoDB to PostgreSQL, check that no data was lost, and if successful switch the DNS to the new instance. There were of course backup plans in place in case things went south.\u003c/li\u003e\u003cli\u003eFinally, after the migration, we would iron out any residual issues and start rolling out new documentation for working with Infisical and PostgreSQL.\u003c/li\u003e\u003c/ul\u003e\u003cdiv\u003eFortunately, the migration turned out to be smooth with zero data loss and only a few non-essential incidents of feature malfunction; we ironed out these bugs out in the following 36 hours with minimal impact to customers. Overall, we considered the initiative to be a success given the objective at hand, the scope of the task, and the resulting execution of it.\u003c/div\u003e\u003ch2\u003eClosing Thoughts\u003c/h2\u003e\u003cdiv\u003eThe decision to move from MongoDB to PostgreSQL was not an easy one from the get-go. All in all, the initiative took us 3–4 months to perform with careful planning and discussion around why we needed to perform it, how we were going to do it; and then to execute it all with care. For those of you who are still with me, I’d highly recommend thinking through the use-case and implementation deeply before attempting such a big endeavor.\u003c/div\u003e\u003cdiv\u003eOverall, I’m extremely happy that everything went according to plan and we were able to deliver such a huge update that will make a large difference to users of \u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eInfisical\u003c/a\u003e moving forward!\u003c/div\u003e\u003cdiv\u003e\u003ca href=\"https://www.producthunt.com/@dangtony98\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e\u003cem\u003eTony\u003c/em\u003e\u003c/a\u003e\u003cem\u003e is a co-founder of \u003c/em\u003e\u003ca href=\"https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003e\u003cem\u003eInfisical\u003c/em\u003e\u003c/a\u003e\u003cem\u003e where he works on all things Engineering and Product; he's a YC alum and Cornell grad where he studied CS.\u003c/em\u003e\u003c/div\u003e","canManage":false,"minsToRead":9,"structuredData":{"@context":"https://schema.org","@type":"NewsArticle","mainEntityOfPage":{"@type":"WebPage","@id":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql"},"headline":"Our Great Migration from MongoDB to PostgreSQL","image":["https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024"],"author":{"@type":"Person","name":"Tony Dang","image":"https://ph-avatars.imgix.net/3999558/original.jpeg?auto=format\u0026fit=crop\u0026crop=faces\u0026w=100\u0026h=100","url":"https://www.producthunt.com/@dangtony98"},"publisher":{"@type":"Organization","name":"Product Hunt","logo":{"@type":"ImageObject","url":"https://ph-static.imgix.net/ph-publisher-logo.png","width":220,"height":60}},"description":"","datePublished":"2024-07-02T10:00:00.000-07:00","dateModified":"2024-11-19T08:16:50.072-08:00"},"meta":{"__typename":"MetaTags","title":"Our Great Migration from MongoDB to PostgreSQL","description":"","creator":"@dangtony98","canonicalUrl":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql","image":"https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024","type":"article"},"moreStories":[{"__typename":"AnthologiesStory","id":"13663","title":"How to Detect AI Content with Keystroke Tracking","slug":"how-to-detect-ai-content-with-keystroke-tracking","headerImageUuid":"3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png","minsToRead":3,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"5149485","name":"matt hardy","username":"mdahardy"},"authorName":"Mathew Hardy","authorUrl":""},{"__typename":"AnthologiesStory","id":"13630","title":"An Initially Failed PH Launch Turned Around to Get Us 850+ Paid Subscribers","slug":"initially-failed-ph-launch-turned-around-to-get-us-850-paid-subscribers","headerImageUuid":"3c43ae0c-75e2-45b7-8e83-977c67ab4c92.webp","minsToRead":3,"category":{"__typename":"Category","name":"Makers","slug":"makers"},"author":{"__typename":"User","id":"2713059","name":"Anton Osika","username":"antonosika"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13597","title":"The Case for Supabase","slug":"the-case-for-supabase","headerImageUuid":"a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png","minsToRead":9,"category":{"__typename":"Category","name":"Opinions","slug":"opinions"},"author":{"__typename":"User","id":"7512242","name":"Sanjana Friedman","username":"sanjanaf"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13564","title":"3.5 Years, 12 Hard Pivots, Still Not Dead","slug":"3-5-years-12-hard-pivots-still-not-dead","headerImageUuid":"d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png","minsToRead":10,"category":{"__typename":"Category","name":"Opinions","slug":"opinions"},"author":{"__typename":"User","id":"3896127","name":"Vaibhav Gupta","username":"hellovai"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13465","title":"Cofounder Mode: A Tactical Guide to Finding a Cofounder","slug":"cofounder-mode-a-tactical-guide-to-finding-a-cofounder","headerImageUuid":"d406b3ba-2d4d-4d08-a966-5610980e802d.webp","minsToRead":10,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"13382","name":"Rob Balian","username":"robbalian"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13432","title":"A Founder’s Guide to AI Fine-Tuning","slug":"a-founder-s-guide-to-ai-fine-tuning","headerImageUuid":"2cd80df4-e3ff-43dd-8885-ad4a6b499b80.webp","minsToRead":5,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"970351","name":"Kyle Corbitt","username":"corbt"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13366","title":"A Better Way to Get Your First 10 B2B Customers","slug":"a-better-way-to-get-your-first-10-b2b-customers","headerImageUuid":"3850ebe3-c944-4989-9513-96bd2d5c8574.png","minsToRead":6,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"3090719","name":"Chris Bakke","username":"chrisbakke"},"authorName":"","authorUrl":""},{"__typename":"AnthologiesStory","id":"13399","title":"The Cold Email Template that Got Me an 8% Reply Rate","slug":"the-cold-email-template-that-got-me-an-8-reply-rate","headerImageUuid":"618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png","minsToRead":4,"category":{"__typename":"Category","name":"How To","slug":"how_to"},"author":{"__typename":"User","id":"5187421","name":"Xiaohan Shen","username":"shen_xh"},"authorName":"","authorUrl":""}],"authorName":"","authorUrl":"","author":{"__typename":"User","id":"3999558","name":"Tony Dang","username":"dangtony98","avatarUrl":"https://ph-avatars.imgix.net/3999558/original.jpeg"},"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql","hasVoted":false,"votesCount":13,"name":"Our Great Migration from MongoDB to PostgreSQL","canComment":false,"commentsCount":7,"threads":{"__typename":"CommentConnection","totalCount":7,"edges":[{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3632591","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"I'm also advocating a move from MongoDB to PostgreSQL in our org, I will use this post as a supporting argument 🫡 \nBtw, we're launching soon on ProductHunt and would love your support! \u003ca href=\"https://www.producthunt.com/products/supergpt\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ehttps://www.producthunt.com/prod...\u003c/a\u003e","bodyHtml":"I'm also advocating a move from MongoDB to PostgreSQL in our org, I will use this post as a supporting argument 🫡 \nBtw, we're launching soon on ProductHunt and would love your support! \u003ca href=\"https://www.producthunt.com/products/supergpt\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ehttps://www.producthunt.com/prod...\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"4002294","name":"Kabir Singh Shekhawat","username":"kabir_singh_shekhawat","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":{"__typename":"Product","id":"592052","name":"Superjoin","logoUuid":"76852a3a-ded0-494c-84d1-6b56d507dba7.png","isNoLongerOnline":false},"avatarUrl":"https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg","karmaBadge":{"__typename":"KarmaBadge","kind":"BRONZE","score":150}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3632591","createdAt":"2024-07-08T23:36:51-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3632591","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"4141093","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"It's nice seeing this informative content. \u003ca href=\"https://premierconcretesanantonio.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econcrete patio\u003c/a\u003e","bodyHtml":"It's nice seeing this informative content. \u003ca href=\"https://premierconcretesanantonio.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003econcrete patio\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"6873315","name":"Oli Seo","username":"oli_seo","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/6873315/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=4141093","createdAt":"2024-11-19T08:16:50-08:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=4141093","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3630185","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Switching from MongoDB to PostgreSQL is a big move, especially considering the shift from a flexible schema to a structured one. How do you think this transition will affect the way you handle future scalability and feature development? The migration seems well-planned and executed, but I'm curious about the most unexpected challenge you faced during the process.","bodyHtml":"Switching from MongoDB to PostgreSQL is a big move, especially considering the shift from a flexible schema to a structured one. How do you think this transition will affect the way you handle future scalability and feature development? The migration seems well-planned and executed, but I'm curious about the most unexpected challenge you faced during the process.","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7261259","name":"Naomi | Beeyond AI","username":"naomigarcia","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg","karmaBadge":{"__typename":"KarmaBadge","kind":"BRONZE","score":455}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3630185","createdAt":"2024-07-08T09:33:08-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3630185","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3785701","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Playing games is getting a lot of attention from young people, especially students. So when these ages use it, do they have to pay any fees to download the game? That is worrying and today I will introduce to you the game \u003ca href=\"https://slopeball.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eslope ball\u003c/a\u003e which is extremely free and also helps brain thinking. Using it for free like that helps all ages to use it without having to pay complicated fees. The game is a great experience if you are really passionate and find a suitable game. Not only does it help with thinking but it also helps you reduce work stress. We should need to release and not be constrained that playing games will be negative and lead to social evils. Many people think that this opinion is wrong, but this is not one of the things that makes you worry. So believe in the game and choose the right game as we introduce to experience it in the most correct way.","bodyHtml":"Playing games is getting a lot of attention from young people, especially students. So when these ages use it, do they have to pay any fees to download the game? That is worrying and today I will introduce to you the game \u003ca href=\"https://slopeball.io/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003eslope ball\u003c/a\u003e which is extremely free and also helps brain thinking. Using it for free like that helps all ages to use it without having to pay complicated fees. The game is a great experience if you are really passionate and find a suitable game. Not only does it help with thinking but it also helps you reduce work stress. We should need to release and not be constrained that playing games will be negative and lead to social evils. Many people think that this opinion is wrong, but this is not one of the things that makes you worry. So believe in the game and choose the right game as we introduce to experience it in the most correct way.","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7473971","name":"Carter Schinner","username":"carter_schinner","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7473971/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3785701","createdAt":"2024-08-15T18:50:36-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3785701","hasVoted":false,"votesCount":0}},{"__typename":"CommentEdge","node":{"__typename":"Comment","id":"3892615","isSticky":false,"visibleRepliesCount":0,"repliesCount":0,"canAward":false,"replies":{"__typename":"CommentConnection","edges":[],"pageInfo":{"__typename":"PageInfo","endCursor":"","hasNextPage":false}},"award":null,"isHidden":false,"approvalStatus":"pending_visible","badges":[],"body":"Looking forward for more post. \u003ca href=\"https://seattle-waterheaterrepair.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ewater heater repair seattle wa\u003c/a\u003e","bodyHtml":"Looking forward for more post. \u003ca href=\"https://seattle-waterheaterrepair.com/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\"\u003ewater heater repair seattle wa\u003c/a\u003e","subject":{"__typename":"AnthologiesStory","id":"13201"},"user":{"__typename":"User","id":"7579058","name":"Angel Brown","username":"angel_brown2","promotableUpcomingEvent":null,"topProductBadge":null,"topLaunchBadge":null,"selectedBylineProduct":null,"avatarUrl":"https://ph-avatars.imgix.net/7579058/original.png","karmaBadge":{"__typename":"KarmaBadge","kind":"PLAIN","score":0}},"poll":null,"isPinned":false,"canViewReplyBtn":false,"isFlaggedByViewer":false,"path":"/stories/our-great-migration-from-mongodb-to-postgresql?comment=3892615","createdAt":"2024-09-11T04:11:35-07:00","canEdit":false,"canDestroy":false,"score":null,"inputInfo":null,"awardOptions":[{"__typename":"CommentAward","id":"design","option":"design"},{"__typename":"CommentAward","id":"idea","option":"idea"},{"__typename":"CommentAward","id":"intro","option":"intro"},{"__typename":"CommentAward","id":"bug","option":"bug"},{"__typename":"CommentAward","id":"funny","option":"funny"}],"url":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql?comment=3892615","hasVoted":false,"votesCount":0}}],"pageInfo":{"__typename":"PageInfo","endCursor":"NQ","hasNextPage":true}}}}}},{"type":"complete","id":"3"}]})</script></head><body><div id="root-container"><header class="w-full bg-white sticky top-0 z-20 border-b-[0.5px] border-light-sky"><div class="grid grid-cols-[1fr_2fr_1fr] items-center bg-white px-6 sm:grid-cols-[auto_1fr_auto] max-h-[64px] min-h-[64px]"><div class="flex flex-row items-center gap-6 md:gap-8"><a aria-label="Product Hunt Logo" href="/"><svg xmlns="http://www.w3.org/2000/svg" width="40" height="40" viewBox="0 0 40 40" class="size-8"><g fill="none" fill-rule="evenodd"><path fill="#FF6154" d="M40 20c0 11.046-8.954 20-20 20S0 31.046 0 20 8.954 0 20 0s20 8.954 20 20"></path><path fill="#FFF" d="M22.667 20H17v-6h5.667a3 3 0 0 1 0 6m0-10H13v20h4v-6h5.667a7 7 0 1 0 0-14"></path></g></svg></a><div class="text-14 font-normal text-dark-gray relative"><svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16" class="absolute left-4 top-2 size-4"><path fill="#4B587C" d="M7 14c-3.86 0-7-3.14-7-7s3.14-7 7-7 7 3.14 7 7-3.14 7-7 7M7 2C4.243 2 2 4.243 2 7s2.243 5 5 5 5-2.243 5-5-2.243-5-5-5m8.707 12.293L13.314 11.9a8 8 0 0 1-1.414 1.414l2.393 2.393a.997.997 0 0 0 1.414 0 1 1 0 0 0 0-1.414" opacity="0.5"></path></svg><input data-hj-allow="true" data-test="header-search-input" autoComplete="off" class="input box-border w-full min-w-[164px] max-w-full appearance-none rounded-full border-0 border-white px-10 pl-[40px] text-light-gray focus:outline-none sm:w-full sm:max-w-[216px] sm:text-base h-8 bg-indigo-25" placeholder="Search" title="Search" name="q"/></div></div><nav aria-label="Main Navigation"><ul class="flex flex-row items-center justify-center gap-6 md:gap-7 lg:gap-8"><li class="group relative list-none" data-test="header-nav-link-launches"><a class="cursor-pointer text-16 text-light-gray" href="/leaderboard/daily/2024/11/23?ref=header_nav">Launches</a><div class="styles_dropdown__6p8ZV hidden group-hover:block group-hover:translate-y-0 group-hover:opacity-100 styles_left__zme_r"><div class="bg-white styles_shadow__RlOHG"><div class="z-100 px-4 py-2"><a href="/coming-soon?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(213, 243, 221, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#d5f3dd" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#599D6B" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#ComingSoon_svg__a)"><path d="M12 21.25a8.25 8.25 0 1 0 0-16.5 8.25 8.25 0 0 0 0 16.5m-6.75-18-3 3m16.5-3 3 3"></path><path d="M12 7.75V13h5.25"></path></g><defs><clipPath id="ComingSoon_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Coming soon</div><div class="text-12 font-normal text-light-gray">Upcoming launches to watch</div></div></div></a><a href="/leaderboard/daily/2024/11/23?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(255, 230, 228, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#ffe6e4" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#F86C60" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#LaunchArchive_svg__a)"><path d="M9 17.25s-.75 3-5.25 3c0-4.5 3-5.25 3-5.25m11.167-4.416c2.25-2.25 2.39-4.927 2.32-6.12a.75.75 0 0 0-.7-.7c-1.194-.071-3.869.068-6.12 2.32L7.5 12l4.5 4.5zM12.75 6.75H6.97a.75.75 0 0 0-.53.22l-3.22 3.22a.75.75 0 0 0 .425 1.272L7.5 12"></path><path d="M17.25 11.25v5.78a.75.75 0 0 1-.22.53l-3.22 3.22a.75.75 0 0 1-1.272-.425L12 16.5"></path></g><defs><clipPath id="LaunchArchive_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Launch archive</div><div class="text-12 font-normal text-light-gray">Most-loved launches by the community</div></div></div></a><a href="/launch?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(229, 239, 255, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#e5efff" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#3979E3" stroke-width="1.5" clip-path="url(#LaunchGuide_svg__a)"><path stroke-miterlimit="10" d="M12 21a9 9 0 1 0 0-18 9 9 0 0 0 0 18Z"></path><path stroke-linecap="round" stroke-linejoin="round" d="m16.5 7.5-6 3-3 6 6-3z"></path></g><defs><clipPath id="LaunchGuide_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Launch Guide</div><div class="text-12 font-normal text-light-gray">Checklists and pro tips for launching</div></div></div></a></div></div></div></li><li class="group relative"><a class="text-16 group-hover:text-brand-500 text-light-gray" href="/categories?ref=header_nav">Products</a></li><li class="group relative list-none" data-test="header-nav-link-news"><a class="cursor-pointer text-16 text-light-gray" href="/newsletters?ref=header_nav">News</a><div class="styles_dropdown__6p8ZV hidden group-hover:block group-hover:translate-y-0 group-hover:opacity-100 styles_left__zme_r"><div class="bg-white styles_shadow__RlOHG"><div class="z-100 px-4 py-2"><a href="/newsletters?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(234, 233, 255, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#eae9ff" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#6D68D4" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Newsletter_svg__a)"><path d="M3 5.25h18V18a.75.75 0 0 1-.75.75H3.75A.75.75 0 0 1 3 18z"></path><path d="m21 5.25-9 8.25-9-8.25"></path></g><defs><clipPath id="Newsletter_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Newsletter</div><div class="text-12 font-normal text-light-gray">The best of Product Hunt, every day</div></div></div></a><a href="/stories?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(255, 233, 244, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#ffe9f4" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#F468AC" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Stories_svg__a)"><path d="M12 8.25a3 3 0 0 1 3-3h6a.75.75 0 0 1 .75.75v12a.75.75 0 0 1-.75.75h-6a3 3 0 0 0-3 3M2.25 18a.75.75 0 0 0 .75.75h6a3 3 0 0 1 3 3V8.25a3 3 0 0 0-3-3H3a.75.75 0 0 0-.75.75zM15 9h3.75M15 12h3.75M15 15h3.75"></path></g><defs><clipPath id="Stories_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Stories</div><div class="text-12 font-normal text-light-gray">Tech news, interviews, and tips from makers</div></div></div></a><a href="/changes?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(207, 252, 219, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#cffcdb" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#579167" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Changelog_svg__a)"><path d="M10.5 10.5h6m-6 3h6m3-9.75h-15a.75.75 0 0 0-.75.75v15c0 .414.336.75.75.75h15a.75.75 0 0 0 .75-.75v-15a.75.75 0 0 0-.75-.75m-12 0v16.5"></path></g><defs><clipPath id="Changelog_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Changelog</div><div class="text-12 font-normal text-light-gray">New Product Hunt features and releases</div></div></div></a></div></div></div></li><li class="group relative list-none" data-test="header-nav-link-community"><a class="cursor-pointer text-16 text-light-gray" href="/discussions?ref=header_nav">Community</a><div class="styles_dropdown__6p8ZV hidden group-hover:block group-hover:translate-y-0 group-hover:opacity-100 styles_left__zme_r"><div class="bg-white styles_shadow__RlOHG"><div class="z-100 px-4 py-2"><a href="/discussions?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(255, 233, 248, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#ffe9f8" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#DE62B6" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Discussions_svg__a)"><path d="M6.71 13.5 3 16.5v-12a.75.75 0 0 1 .75-.75h12a.75.75 0 0 1 .75.75v8.25a.75.75 0 0 1-.75.75z"></path><path d="M7.5 13.5v3.75a.75.75 0 0 0 .75.75h9.04L21 21V9a.75.75 0 0 0-.75-.75H16.5"></path></g><defs><clipPath id="Discussions_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Discussions</div><div class="text-12 font-normal text-light-gray">Ask questions, find support, and connect</div></div></div></a><a href="/visit-streaks?ref=header_nav"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(255, 228, 228, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#ffe4e4" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#F10202" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Streaks_svg__a)"><path d="M12.75 18c1.875-.316 3.432-1.875 3.75-3.75"></path><path d="m10.5 9 2.463-6.75C14.987 3.93 19.5 8.264 19.5 13.5a7.5 7.5 0 0 1-15 0c0-2.866 1.352-5.462 2.906-7.5z"></path></g><defs><clipPath id="Streaks_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Streaks</div><div class="text-12 font-normal text-light-gray">The most active community members</div></div></div></a><a href="https://lu.ma/producthunt" target="_blank"><div class="my-2 flex flex-row gap-4 styles_container__K6Yj1" style="background:linear-gradient(to right, rgba(207, 242, 216, 0.25) 50%, rgba(255, 255, 255, 0.3) 50%)"><div style="background-color:#cff2d8" class="styles_container__T4TJj"><svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none"><g stroke="#3F9E58" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" clip-path="url(#Event_svg__a)"><path d="M19.5 3.75h-15a.75.75 0 0 0-.75.75v15c0 .414.336.75.75.75h15a.75.75 0 0 0 .75-.75v-15a.75.75 0 0 0-.75-.75m-3-1.5v3m-9-3v3m-3.75 3h16.5"></path><path d="m8.625 14.25 2.25 2.25 4.5-4.5"></path></g><defs><clipPath id="Event_svg__a"><path fill="#fff" d="M0 0h24v24H0z"></path></clipPath></defs></svg></div><div class="flex flex-1 flex-col"><div class="text-14 font-normal text-dark-gray">Events</div><div class="text-12 font-normal text-light-gray">Meet others online and in-person</div></div></div></a></div></div></div></li><li class="group relative list-none" data-test="header-nav-link-advertise"><a class="cursor-pointer text-16 text-light-gray" href="/sponsor?ref=header_nav">Advertise</a></li></ul></nav><!--$--><div class="flex flex-row items-center justify-end gap-4"><a class="text-16 font-normal text-coral rounded bg-barely-orange !py-[6px] px-4 text-brand-700" data-test="header-nav-link-subscribe" href="/newsletters?ref=header_nav&amp;campaign=weekly_newsletter&amp;source=header_nav">Subscribe</a><div class="text-16 font-normal text-white cursor-pointer rounded bg-brand-500 !py-[6px] px-4" data-test="header-nav-link-sign-in">Sign in</div></div><!--/$--></div></header><div class="styles_contentContainer__FsFxr"><div class="mt-5 styles_container__eS_WB"><header class="flex-1"><div class="flex"><ol class="flex list-none flex-row flex-wrap gap-2"><li class="flex flex-row items-center gap-2"><a class="text-14 font-normal text-dark-gray hover:text-blue opacity-70" href="/stories">Stories</a></li><li class="flex flex-row items-center gap-2"><svg xmlns="http://www.w3.org/2000/svg" width="7" height="11" viewBox="0 0 7 11" class="mt-0.5 h-2 fill-light-gray"><path fill-rule="evenodd" d="M6.744 5.502a1 1 0 0 1-.292.703l-4.247 4.247a1.003 1.003 0 0 1-1.412-.002.996.996 0 0 1-.003-1.412L4.33 5.5.79 1.962A1.004 1.004 0 0 1 .794.55a.995.995 0 0 1 1.41-.002l4.248 4.247c.192.192.29.447.29.702z"></path></svg><a class="text-14 font-normal text-dark-gray hover:text-blue pointer-events-none" href="/stories/our-great-migration-from-mongodb-to-postgresql">Our Great Migration from MongoDB to PostgreSQL</a></li></ol></div><div class="styles_grid__clDr5 styles_grid--gap-5__jGmDi styles_grid--grid__IBRR7 items-center"><div class="styles_item__rz7L2 styles_widescreen-6__f7_BY styles_desktop-6__pXLL8 undefined styles_mobile-6___6mkX"><h1 class="text-24 sm:text-32 md:text-32 font-bold text-dark-gray sm:mb-6">Our Great Migration from MongoDB to PostgreSQL</h1><div class="styles_grid__clDr5"><div class="styles_item__rz7L2"><div class="text-12 font-normal text-light-gray">Published on</div><div class="text-12 font-medium text-dark-gray">July 2nd, 2024</div></div><div class="styles_item__rz7L2"><div class="text-12 font-normal text-light-gray">Author</div><div class=""><a class="text-12 font-medium text-dark-gray" href="/@dangtony98">Tony Dang</a></div></div><div class="styles_item__rz7L2"><div class="text-12 font-normal text-light-gray">Category</div><a class="text-12 font-medium text-dark-gray" href="/stories/category/how_to">How To</a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-6__f7_BY styles_desktop-6__pXLL8 undefined styles_mobile-6___6mkX"><img loading="lazy" srcSet="https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;fit=max&amp;dpr=1 1x, https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;fit=max&amp;dpr=2 2x, https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;fit=max&amp;dpr=3 3x" src="https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;fit=max" style="width:100%;height:auto" class="styles_headerImage__Y54V8"/></div></div></header></div><div class="mb-16 mt-10 bg-light-sky styles_separator__lbyIi"></div><div class="styles_container__eS_WB"><div class="styles_grid__clDr5 styles_grid--gap-0__nuGY1 styles_grid--grid__IBRR7"><div class="styles_item__rz7L2 styles_widescreen-2__9dgMX styles_desktop-2__cv0m8 styles_sticky__BhECt"><button type="button" data-test="stories-vote-button" class="styles_reset__0clCw styles_feed__QkQvW"><div class="flex flex-col items-center"><div class="styles_icon__kJG98 styles_lightGray__wsqtZ"></div><div class="text-12 font-semibold text-light-gray styles_voteCountItem__zwuqk">13</div></div></button><div class="text-12 font-semibold text-light-gray uppercase my-6">Share On</div><div class="flex flex-col gap-2"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral text-12 font-semibold styles_twitterButton__jSbbW">Twitter</button><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral text-12 font-semibold styles_facebookButton__aTubP">Facebook</button><button type="button" class="text-left text-12 font-semibold text-light-gray">Copy link</button></div></div><div class="styles_item__rz7L2 styles_widescreen-7__xSnLa styles_desktop-8__EF8GW undefined styles_mobile-6___6mkX"><div class="text-light-gray styles_storyBody__vozi8"><div>Hey Product Hunt! </div><div>I’m excited to share our story for how we recently performed a full database migration from MongoDB to PostgreSQL at<a href="https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F" target="_blank" rel="noopener"> Infisical</a>. This entailed deliberating the initiative, adopting new tech, creating new database schemas, rewiring logic, re-writing queries, to migrating millions (if not billions) of database records over to PostgreSQL.</div><h2>Where we started</h2><div>When we first built<a href="https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F" target="_blank" rel="noopener"> Infisical</a>, we built it with the stack that felt most familiar with the team. As part of that stack, we chose MongoDB + Mongoose ORM because the combination presented least overhead and allowed us to ship quality features quickly. As Donald Knuth states<em>, “premature optimization is the root of all evil,” </em>and there was certainly no need for further optimization at the time.</div><div>At the time, we were also more focused on building Infisical Cloud, the managed SaSS offering, and given this focus, we didn’t anticipate as many users self-hosting the product and hence it wasn’t designed with that use-case in mind.</div><div><strong>Note</strong>: Looking back, we followed YC’s traditional advice that you should not over-optimize especially when just starting out — Just pick a stack that you can build with most quickly, reduce scope, and hack together the MVP. We continue to follow this principle with optimizations made overtime (e.g. moving from Heroku to DigitalOcean to AWS, revamping features based on feedback, etc.).</div><h2>Why not MongoDB?</h2><div>While MongoDB served <a href="https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F" target="_blank" rel="noopener">Infisical</a>well in the early days, it started showing signs of shortcoming when the use-case of our product evolved beyond the managed service. As time passed, we found that many organizations, especially ones operating at the intersection of compliance and security, preferred self-hosting Infisical as opposed to using Infisical Cloud; others had on-prem requirements that needed to be met.</div><div>With demand growing for self-hosting Infisical, we found ourselves shipping many features catered to reducing the learning curve needed to self-host Infisical and, as part of that, we ended up leaving MongoDB in favor of PostgreSQL.</div><div>In practice, we and our customers often ran into constraints around the capabilities and usability of MongoDB like the lack of support for <a href="https://en.wikipedia.org/wiki/Database_transaction" target="_blank" rel="noopener">transactions</a>, clean-up, inconsistent versioning across managed offerings by cloud providers, not to mention issues associated with schema-less database design structure.</div><div>Amongst a dozen more reasons, we came to the realization that a full database migration to something more universal was the ultimate feature needed to make Infisical more accessible to teams and organizations around the world.</div><h2>Why PostgreSQL?</h2><div>When searching for a new database, we began by listing out what aspects mattered most to us: ease of management (i.e. configuration, deployment, and scaling included), built-in support for<a href="https://en.wikipedia.org/wiki/Database_transaction" target="_blank" rel="noopener"> transactions</a>, and relational capabilities. As part of the deliberation, we also contemplated whether or not we should build our own integrated storage or pursue an external storage solution.</div><div><strong>Here’s what that meant for each option:</strong></div><div><strong>Integrated storage:</strong> We could package in a database system like <a href="https://www.sqlite.org/" target="_blank" rel="noopener">SQLite</a> directly into Infisical and pursue a horizontal replication strategy to reduce latency by avoiding extra network hops. In this model, scaling the system would mean deploying multiple instances of Infisical and have them communicate with each other via some <a href="https://en.wikipedia.org/wiki/Consensus_(computer_science)" target="_blank" rel="noopener">consensus algorithm</a> like <a href="https://en.wikipedia.org/wiki/Raft_(algorithm)" target="_blank" rel="noopener">Raft</a>. While this seemed like an excellent solution since customer’s wouldn’t need to connect any dependencies to run Infisical, the tooling ecosystem to execute this vision felt immature and the engineering effort required for it felt nothing short of overwhelming.</div><div><strong>External storage</strong>: We could simply replace MongoDB with another database(s) like PostgreSQL or MySQL and use its built-in scaling capabilities. Although this solution didn’t fully eliminate friction associated with needing external dependencies to use Infisical, we felt that it already delivered significant benefits by virtue of not being MongoDB. When it came to supporting one or multiple databases, we felt that supporting multiple would mean missing out on the unique advantages of each solution; it would also add to our engineering overhead.</div><div>After careful consideration, we chose PostgreSQL. Beyond having a vibrant community, extensive documentation, and a myriad of solutions and extensions available, we appreciated most its open source nature and how the vast majority of cloud providers offered managed services of PostgreSQL.</div><div>Above all, this meant that users of Infisical could more easily self-host our platform on any cloud provider and pair it with its corresponding managed PostgreSQL service. Moreover, given how widely-adopted the database has become, we were confident that users would have less trouble operating it when using Infisical.</div><h2>What about the ORM?</h2><div>After settling on PostgreSQL, we needed to figure out how our application would interact with the database. Right off the bat, we wanted something comparable to our experience with MongoDB where we used Mongoose ORM. So, we began evaluating candidates on the basis of maturity, visualization and migration support, and appropriate level of abstraction; we primarily considered <a href="https://orm.drizzle.team/" target="_blank" rel="noopener">Drizzle ORM</a>, <a href="https://www.prisma.io/" target="_blank" rel="noopener">Prisma ORM</a>, <a href="https://typeorm.io/" target="_blank" rel="noopener">TypeORM</a>, and <a href="https://knexjs.org/" target="_blank" rel="noopener">Knex.js</a>, a query builder.</div><div>At the end, we decided to use Knex.js, a query builder, instead of a ORM to maintain better control over the database. While admittedly, going with raw SQL would be most versatile with least abstraction in place, we felt the approach would be far too error-prone and frankly cumbersome to maintain, especially without proper TypeScript support. Moreover, beyond being close to bare SQL, Knex.js came with its own toolkit for seeding and migration, had a mature ecosystem with excellent documentation and answers for almost any possible query. Coupled with some custom Zod integration work, we managed to get it to a satisfactory level for TypeScript support.</div><div>Having decided on the database and ORM, we kicked off a process that would ultimately result in a re-write of dozens of data structures and hundreds of queries across the application.</div><h2>How did we plan the migration?</h2><div>Toward the end of the code-rewrite, we started to think about how we would conduct the migration operation to map our MongoDB data to PostgreSQL with minimal disruption to the Infisical Cloud platform.</div><div>Given Infisical’s critical role in customers infrastructure, we immediately ruled out the possibility of having any absolute downtime. The part where we had to make a compromise was in disallowing write operations during the brief migration window (i.e. customers would not be able to create or update application configuration) in exchange for higher guarantee of data integrity. This tradeoff seemed acceptable given that customers primarily fetched back secrets from Infisical and, to a much lesser extent, updated their application configuration on a second-by-second basis.</div><div>Next, regarding the actual migration operation, we needed to dump data from MongoDB, transform it carefully, and insert it back into PostgreSQL. As we audited the migration sequence, we grappled through challenges like making sure that various tree-like structures from NoSQL were correctly transformed to their relational counterparts; this was particularly sensitive for data structures like folders that had recursive considerations. We also found that we needed a persistent way to store and map identifiers in MongoDB to those in PostgreSQL; doing so in-memory would not work considering how much data we were dealing with. In the end, we settled for using the <a href="https://leveljs.org/" target="_blank" rel="noopener">LevelDB</a> key-value store to assist with identifier storage and lookup operations. With it, we would move data table-by-table into PostgreSQL.</div><h2>The Great Migration</h2><div>Finally, we were ready to conduct the migration. At this point, folks not directly involved in the codebase re-write had spent a much-needed quarter improving other aspects of Infisical including making frontend changes, performing maintenance patches, extending client functionality, and writing up better documentation. We now all reconvened to prepare for the migration itself that is replacing the application codebase with the new one and transferring data over from MongoDB to PostgreSQL.</div><div>As part of the preparation, we drafted a detailed migration checklist with an expected timeline.</div><div><strong>On a high-level, the plan looked something like this:</strong></div><ul><li>In the weeks building up to the migration, we would communicate in advance via both email and in-app banner to let users know about the impending database upgrade. We would conduct thorough testing of every feature flow on the platform and perform trial runs for the migration.</li><li>The migration itself would occur within a six-hour window where only read operations would be allowed to the platform. During this window, we would run the migration script to move data from MongoDB to PostgreSQL, check that no data was lost, and if successful switch the DNS to the new instance. There were of course backup plans in place in case things went south.</li><li>Finally, after the migration, we would iron out any residual issues and start rolling out new documentation for working with Infisical and PostgreSQL.</li></ul><div>Fortunately, the migration turned out to be smooth with zero data loss and only a few non-essential incidents of feature malfunction; we ironed out these bugs out in the following 36 hours with minimal impact to customers. Overall, we considered the initiative to be a success given the objective at hand, the scope of the task, and the resulting execution of it.</div><h2>Closing Thoughts</h2><div>The decision to move from MongoDB to PostgreSQL was not an easy one from the get-go. All in all, the initiative took us 3–4 months to perform with careful planning and discussion around why we needed to perform it, how we were going to do it; and then to execute it all with care. For those of you who are still with me, I’d highly recommend thinking through the use-case and implementation deeply before attempting such a big endeavor.</div><div>Overall, I’m extremely happy that everything went according to plan and we were able to deliver such a huge update that will make a large difference to users of <a href="https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F" target="_blank" rel="noopener">Infisical</a> moving forward!</div><div><a href="https://www.producthunt.com/@dangtony98" target="_blank" rel="noopener"><em>Tony</em></a><em> is a co-founder of </em><a href="https://streaklinks.com/CByMYcoJCfHsT9ZKyAWVJjE2/https%3A%2F%2Finfisical.com%2F" target="_blank" rel="noopener"><em>Infisical</em></a><em> where he works on all things Engineering and Product; he&#x27;s a YC alum and Cornell grad where he studied CS.</em></div></div><div class="text-12 font-semibold text-light-gray uppercase mb-5 md:mb-6">Comments <!-- -->(7)</div><form data-test="comment-form" autoComplete="off"><div class="flex flex-row gap-3 border-y border-light-blue pt-3 pb-5"><img loading="lazy" srcSet="https://ph-static.imgix.net/guest-user-avatar.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-static.imgix.net/guest-user-avatar.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-static.imgix.net/guest-user-avatar.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-static.imgix.net/guest-user-avatar.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="" class="rounded-full"/><div class="flex flex-1 flex-col"><div class="relative"><div style="position:relative;overflow-y:visible"><div style="background-color:#fff;font-size:14px;font-weight:normal;color:#21293c;min-height:24px"><div style="position:relative;box-sizing:border-box;width:100%;color:transparent;overflow:hidden;white-space:pre-wrap;word-wrap:break-word;border:1px solid transparent;text-align:start;padding:8px;border-radius:8px"> </div><textarea placeholder="Write a comment" style="display:block;width:100%;position:absolute;margin:0;top:0;left:0;box-sizing:border-box;background-color:transparent;font-family:inherit;font-size:inherit;letter-spacing:inherit;height:100%;bottom:0;overflow:hidden;resize:none;padding:8px;border:1px solid transparent;outline:none"></textarea></div></div></div><div class="mt-3 flex flex-row items-center justify-between"><div class="flex flex-row items-center gap-6 sm:gap-4"><div><div class="cursor-default"><svg xmlns="http://www.w3.org/2000/svg" width="18" height="19"><g fill="#4B587C" fill-rule="evenodd"><path fill-rule="nonzero" d="M12.515 4.325v7.012q0 .923.857.989l.137.005h3.967v2.006h-4.96q-1.684 0-1.98-1.81l-.027-.196q-.103.993-.68 1.5-.576.506-1.664.506-1.275 0-2.465-1.167-1.105-1.084-1.185-2.608l-.006-.237V8.337q0-1.66 1.19-2.836 1.1-1.086 2.574-1.17l.249-.006zM10.487 6.33H8.499l-.18.007a1.92 1.92 0 0 0-1.235.583q-.525.525-.584 1.236l-.007.18v1.988l.007.18q.058.71.58 1.235.585.59 1.42.59.814 0 1.401-.59.52-.525.579-1.235l.007-.18z"></path><path d="M7.357.5h3.286c1.084 0 1.958 0 2.666.058.729.06 1.369.185 1.961.487a5 5 0 0 1 2.185 2.185c.302.592.428 1.233.487 1.961C18 5.9 18 6.773 18 7.857v3.286c0 1.084 0 1.958-.058 2.666-.06.729-.185 1.369-.487 1.961a5 5 0 0 1-2.185 2.185c-.592.302-1.232.428-1.961.487-.708.058-1.582.058-2.666.058H7.357c-1.084 0-1.958 0-2.666-.058-.728-.06-1.369-.185-1.96-.487A5 5 0 0 1 .544 15.77c-.302-.592-.428-1.232-.487-1.961C0 13.1 0 12.227 0 11.143V7.857C0 6.773 0 5.9.058 5.191c.06-.728.185-1.369.487-1.96A5 5 0 0 1 2.73 1.044C3.322.743 3.963.617 4.691.558 5.4.5 6.273.5 7.357.5M4.854 2.551c-.605.05-.953.142-1.216.276a3 3 0 0 0-1.311 1.311c-.134.263-.226.611-.276 1.216C2.001 5.971 2 6.764 2 7.9v3.2c0 1.137 0 1.929.051 2.546.05.605.142.953.276 1.216a3 3 0 0 0 1.311 1.311c.263.134.611.226 1.216.276.617.05 1.41.051 2.546.051h3.2c1.137 0 1.929 0 2.546-.051.605-.05.953-.142 1.216-.276a3 3 0 0 0 1.311-1.311c.134-.263.226-.611.276-1.216.05-.617.051-1.41.051-2.546V7.9c0-1.137 0-1.929-.051-2.546-.05-.605-.142-.953-.276-1.216a3 3 0 0 0-1.311-1.311c-.263-.134-.611-.226-1.216-.276-.617-.05-1.41-.051-2.546-.051H7.4c-1.137 0-1.929 0-2.546.051"></path></g></svg></div></div><div><div class="cursor-default"><svg xmlns="http://www.w3.org/2000/svg" width="18" height="19"><g fill="#4B587C" fill-rule="evenodd"><path d="M7.357.5h3.286c1.084 0 1.958 0 2.666.058.729.06 1.369.185 1.961.487a5 5 0 0 1 2.185 2.185c.302.592.428 1.233.487 1.961C18 5.9 18 6.773 18 7.857v3.286c0 1.084 0 1.958-.058 2.666-.06.729-.185 1.369-.487 1.961a5 5 0 0 1-2.185 2.185c-.592.302-1.232.428-1.961.487-.708.058-1.582.058-2.666.058H7.357c-1.084 0-1.958 0-2.666-.058-.728-.06-1.369-.185-1.96-.487A5 5 0 0 1 .544 15.77c-.302-.592-.428-1.232-.487-1.961C0 13.1 0 12.227 0 11.143V7.857C0 6.773 0 5.9.058 5.191c.06-.728.185-1.369.487-1.96A5 5 0 0 1 2.73 1.044C3.322.743 3.963.617 4.691.558 5.4.5 6.273.5 7.357.5M4.854 2.551c-.605.05-.953.142-1.216.276a3 3 0 0 0-1.311 1.311c-.134.263-.226.611-.276 1.216C2.001 5.971 2 6.764 2 7.9v3.2c0 1.137 0 1.929.051 2.546.05.605.142.953.276 1.216a3 3 0 0 0 1.311 1.311c.263.134.611.226 1.216.276.617.05 1.41.051 2.546.051h3.2c1.137 0 1.929 0 2.546-.051.605-.05.953-.142 1.216-.276a3 3 0 0 0 1.311-1.311c.134-.263.226-.611.276-1.216.05-.617.051-1.41.051-2.546V7.9c0-1.137 0-1.929-.051-2.546-.05-.605-.142-.953-.276-1.216a3 3 0 0 0-1.311-1.311c-.263-.134-.611-.226-1.216-.276-.617-.05-1.41-.051-2.546-.051H7.4c-1.137 0-1.929 0-2.546.051"></path><path d="M9 5a1 1 0 0 1 1 1v5a1 1 0 0 1-2 0V6a1 1 0 0 1 1-1m0 8a1 1 0 1 1 0 2 1 1 0 0 1 0-2"></path></g></svg></div></div></div><div class="flex flex-row items-center gap-3"><button type="submit" data-test="form-submit-button" class="styles_reset__0clCw styles_button__BmLM4 styles_primary__o9u3f leading-none sm:leading-normal">Login to comment</button></div></div></div></div></form><div class="my-5"><div class="flex flex-col"><div data-test="thread-3632591"><div id="comment-3632591" data-test="comment-3632591" class="flex flex-row gap-2 md:mb-6"><div class=""><a data-test="user-image-link-4002294" aria-label="Kabir Singh Shekhawat" class="relative" href="/@kabir_singh_shekhawat"><img loading="lazy" srcSet="https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-avatars.imgix.net/4002294/9e6fe2fc-2e9a-4068-8f5c-9322891deb54.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="Kabir Singh Shekhawat" class="rounded-full"/></a></div><div class="flex flex-1 flex-col gap-2 pb-6 md:pb-0 md:pl-0"><div class="flex flex-row items-center justify-between gap-1"><div class="flex flex-row items-center"><div class=""><a class="text-14 font-semibold text-dark-gray" href="/@kabir_singh_shekhawat">Kabir Singh Shekhawat</a><a class="text-12 font-normal text-light-gray ml-1" href="/@kabir_singh_shekhawat">@<!-- -->kabir_singh_shekhawat</a></div><div class="flex flex-row items-center gap-2"><div class="sm:ml-2"><div class="flex items-center gap-2"><div class=""><div class="flex items-center gap-1"><img loading="lazy" srcSet="https://ph-files.imgix.net/76852a3a-ded0-494c-84d1-6b56d507dba7.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=15&amp;h=15&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/76852a3a-ded0-494c-84d1-6b56d507dba7.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=15&amp;h=15&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/76852a3a-ded0-494c-84d1-6b56d507dba7.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=15&amp;h=15&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/76852a3a-ded0-494c-84d1-6b56d507dba7.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=15&amp;h=15&amp;fit=crop" style="width:15px;height:15px" alt="Superjoin" class="rounded" data-test="Superjoin-thumbnail"/><div class="text-12 font-normal text-light-gray mt-[2px]">Superjoin</div></div></div></div></div></div></div></div><div class="flex flex-col gap-1"><div class="styles_htmlText__eYPgj text-16 font-normal text-light-gray styles_format__8NeQe styles_commentBody__PMsJ2">I'm also advocating a move from MongoDB to PostgreSQL in our org, I will use this post as a supporting argument 🫡 Btw, we're launching soon on ProductHunt and would love your support! <a href="https://www.producthunt.com/products/supergpt" target="_blank" rel="nofollow noopener noreferrer">https://www.producthunt.com/prod...</a></div><div class="flex flex-col"><div class="mt-3 flex flex-row flex-wrap items-center gap-5"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral" data-test="comment-vote-button"><div data-test="comment-upvote-info" class="flex flex-row items-center gap-1"><div class="text-12 font-semibold text-light-gray hover:text-coral">Upvote</div><div class="text-12 font-semibold text-light-gray"></div></div></button><a href="#"><div class="text-12 font-semibold text-light-gray hover:text-coral">Share</div></a><a class="text-12 font-semibold text-light-gray" href="/stories/our-great-migration-from-mongodb-to-postgresql?comment=3632591"><time dateTime="2024-07-08T23:36:51-07:00" title="Tuesday, July 9th 2024, 6:36:51 AM">Jul 9</time></a></div><div class="mt-3 flex flex-row items-center gap-5"></div></div></div></div></div><div class="styles_mobileContainer__atI9L"></div></div><div data-test="thread-4141093"><div id="comment-4141093" data-test="comment-4141093" class="flex flex-row gap-2 md:mb-6"><div class=""><a data-test="user-image-link-6873315" aria-label="Oli Seo" class="relative" href="/@oli_seo"><img loading="lazy" srcSet="https://ph-avatars.imgix.net/6873315/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-avatars.imgix.net/6873315/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-avatars.imgix.net/6873315/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-avatars.imgix.net/6873315/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="Oli Seo" class="rounded-full"/></a></div><div class="flex flex-1 flex-col gap-2 pb-6 md:pb-0 md:pl-0"><div class="flex flex-row items-center justify-between gap-1"><div class="flex flex-row items-center"><div class=""><a class="text-14 font-semibold text-dark-gray" href="/@oli_seo">Oli Seo</a><a class="text-12 font-normal text-light-gray ml-1" href="/@oli_seo">@<!-- -->oli_seo</a></div><div class="flex flex-row items-center gap-2"><div class="sm:ml-2"></div></div></div></div><div class="flex flex-col gap-1"><div class="styles_htmlText__eYPgj text-16 font-normal text-light-gray styles_format__8NeQe styles_commentBody__PMsJ2">It's nice seeing this informative content. <a href="https://premierconcretesanantonio.com/" target="_blank" rel="nofollow noopener noreferrer">concrete patio</a></div><div class="flex flex-col"><div class="mt-3 flex flex-row flex-wrap items-center gap-5"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral" data-test="comment-vote-button"><div data-test="comment-upvote-info" class="flex flex-row items-center gap-1"><div class="text-12 font-semibold text-light-gray hover:text-coral">Upvote</div><div class="text-12 font-semibold text-light-gray"></div></div></button><a href="#"><div class="text-12 font-semibold text-light-gray hover:text-coral">Share</div></a><a class="text-12 font-semibold text-light-gray" href="/stories/our-great-migration-from-mongodb-to-postgresql?comment=4141093"><time dateTime="2024-11-19T08:16:50-08:00" title="Tuesday, November 19th 2024, 4:16:50 PM">Nov 19</time></a></div><div class="mt-3 flex flex-row items-center gap-5"></div></div></div></div></div><div class="styles_mobileContainer__atI9L"></div></div><div data-test="thread-3630185"><div id="comment-3630185" data-test="comment-3630185" class="flex flex-row gap-2 md:mb-6"><div class=""><a data-test="user-image-link-7261259" aria-label="Naomi | Beeyond AI" class="relative" href="/@naomigarcia"><img loading="lazy" srcSet="https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-avatars.imgix.net/7261259/3f15c46d-0859-443e-adbc-b56ac89f695c.jpeg?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="Naomi | Beeyond AI" class="rounded-full"/></a></div><div class="flex flex-1 flex-col gap-2 pb-6 md:pb-0 md:pl-0"><div class="flex flex-row items-center justify-between gap-1"><div class="flex flex-row items-center"><div class=""><a class="text-14 font-semibold text-dark-gray" href="/@naomigarcia">Naomi | Beeyond AI</a><a class="text-12 font-normal text-light-gray ml-1" href="/@naomigarcia">@<!-- -->naomigarcia</a></div><div class="flex flex-row items-center gap-2"><div class="sm:ml-2"></div></div></div></div><div class="flex flex-col gap-1"><div class="styles_htmlText__eYPgj text-16 font-normal text-light-gray styles_format__8NeQe styles_commentBody__PMsJ2">Switching from MongoDB to PostgreSQL is a big move, especially considering the shift from a flexible schema to a structured one. How do you think this transition will affect the way you handle future scalability and feature development? The migration seems well-planned and executed, but I'm curious about the most unexpected challenge you faced during the process.</div><div class="flex flex-col"><div class="mt-3 flex flex-row flex-wrap items-center gap-5"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral" data-test="comment-vote-button"><div data-test="comment-upvote-info" class="flex flex-row items-center gap-1"><div class="text-12 font-semibold text-light-gray hover:text-coral">Upvote</div><div class="text-12 font-semibold text-light-gray"></div></div></button><a href="#"><div class="text-12 font-semibold text-light-gray hover:text-coral">Share</div></a><a class="text-12 font-semibold text-light-gray" href="/stories/our-great-migration-from-mongodb-to-postgresql?comment=3630185"><time dateTime="2024-07-08T09:33:08-07:00" title="Monday, July 8th 2024, 4:33:08 PM">Jul 8</time></a></div><div class="mt-3 flex flex-row items-center gap-5"></div></div></div></div></div><div class="styles_mobileContainer__atI9L"></div></div><div data-test="thread-3785701"><div id="comment-3785701" data-test="comment-3785701" class="flex flex-row gap-2 md:mb-6"><div class=""><a data-test="user-image-link-7473971" aria-label="Carter Schinner" class="relative" href="/@carter_schinner"><img loading="lazy" srcSet="https://ph-avatars.imgix.net/7473971/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-avatars.imgix.net/7473971/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-avatars.imgix.net/7473971/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-avatars.imgix.net/7473971/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="Carter Schinner" class="rounded-full"/></a></div><div class="flex flex-1 flex-col gap-2 pb-6 md:pb-0 md:pl-0"><div class="flex flex-row items-center justify-between gap-1"><div class="flex flex-row items-center"><div class=""><a class="text-14 font-semibold text-dark-gray" href="/@carter_schinner">Carter Schinner</a><a class="text-12 font-normal text-light-gray ml-1" href="/@carter_schinner">@<!-- -->carter_schinner</a></div><div class="flex flex-row items-center gap-2"><div class="sm:ml-2"></div></div></div></div><div class="flex flex-col gap-1"><div class="styles_htmlText__eYPgj text-16 font-normal text-light-gray styles_format__8NeQe styles_commentBody__PMsJ2">Playing games is getting a lot of attention from young people, especially students. So when these ages use it, do they have to pay any fees to download the game? That is worrying and today I will introduce to you the game <a href="https://slopeball.io/" target="_blank" rel="nofollow noopener noreferrer">slope ball</a> which is extremely free and also helps brain thinking. Using it for free like that helps all ages to use it without having to pay complicated fees. The game is a great experience if you are really passionate and find a suitable game. Not only does it help with thinking but it also helps you reduce work stress. We should need to release and not be constrained that playing games will be negative and lead to social evils. Many people think that this opinion is wrong, but this is not one of the things that makes you worry. So believe in the game and choose the right game as we introduce to experience it in the most correct way.</div><div class="flex flex-col"><div class="mt-3 flex flex-row flex-wrap items-center gap-5"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral" data-test="comment-vote-button"><div data-test="comment-upvote-info" class="flex flex-row items-center gap-1"><div class="text-12 font-semibold text-light-gray hover:text-coral">Upvote</div><div class="text-12 font-semibold text-light-gray"></div></div></button><a href="#"><div class="text-12 font-semibold text-light-gray hover:text-coral">Share</div></a><a class="text-12 font-semibold text-light-gray" href="/stories/our-great-migration-from-mongodb-to-postgresql?comment=3785701"><time dateTime="2024-08-15T18:50:36-07:00" title="Friday, August 16th 2024, 1:50:36 AM">Aug 16</time></a></div><div class="mt-3 flex flex-row items-center gap-5"></div></div></div></div></div><div class="styles_mobileContainer__atI9L"></div></div><div data-test="thread-3892615"><div id="comment-3892615" data-test="comment-3892615" class="flex flex-row gap-2 md:mb-6"><div class=""><a data-test="user-image-link-7579058" aria-label="Angel Brown" class="relative" href="/@angel_brown2"><img loading="lazy" srcSet="https://ph-avatars.imgix.net/7579058/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=1 1x, https://ph-avatars.imgix.net/7579058/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=2 2x, https://ph-avatars.imgix.net/7579058/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop&amp;dpr=3 3x" src="https://ph-avatars.imgix.net/7579058/original.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=36&amp;h=36&amp;fit=crop" style="width:36px;height:36px" alt="Angel Brown" class="rounded-full"/></a></div><div class="flex flex-1 flex-col gap-2 pb-6 md:pb-0 md:pl-0"><div class="flex flex-row items-center justify-between gap-1"><div class="flex flex-row items-center"><div class=""><a class="text-14 font-semibold text-dark-gray" href="/@angel_brown2">Angel Brown</a><a class="text-12 font-normal text-light-gray ml-1" href="/@angel_brown2">@<!-- -->angel_brown2</a></div><div class="flex flex-row items-center gap-2"><div class="sm:ml-2"></div></div></div></div><div class="flex flex-col gap-1"><div class="styles_htmlText__eYPgj text-16 font-normal text-light-gray styles_format__8NeQe styles_commentBody__PMsJ2">Looking forward for more post. <a href="https://seattle-waterheaterrepair.com/" target="_blank" rel="nofollow noopener noreferrer">water heater repair seattle wa</a></div><div class="flex flex-col"><div class="mt-3 flex flex-row flex-wrap items-center gap-5"><button type="button" class="text-left text-12 font-semibold text-light-gray hover:text-coral" data-test="comment-vote-button"><div data-test="comment-upvote-info" class="flex flex-row items-center gap-1"><div class="text-12 font-semibold text-light-gray hover:text-coral">Upvote</div><div class="text-12 font-semibold text-light-gray"></div></div></button><a href="#"><div class="text-12 font-semibold text-light-gray hover:text-coral">Share</div></a><a class="text-12 font-semibold text-light-gray" href="/stories/our-great-migration-from-mongodb-to-postgresql?comment=3892615"><time dateTime="2024-09-11T04:11:35-07:00" title="Wednesday, September 11th 2024, 11:11:35 AM">Sep 11</time></a></div><div class="mt-3 flex flex-row items-center gap-5"></div></div></div></div></div><div class="styles_mobileContainer__atI9L"></div></div><div><div class="styles_container__lNjYm"><div class="styles_loader__IcPYn" style="width:30px;height:30px"></div></div></div></div></div></div></div></div><div class="mb-16 mt-10 bg-light-sky styles_separator__lbyIi"></div><div class="mb-16 sm:mb-6 md:mb-5 lg:mb-8 styles_container__eS_WB"><header class="flex-1"><div class="text-24 font-bold text-dark-gray mb-8">More stories</div><div class="styles_grid__clDr5 styles_grid--gap-10__f4icO styles_grid--grid__IBRR7 mb-10"><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13663"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/how-to-detect-ai-content-with-keystroke-tracking"><img loading="lazy" srcSet="https://ph-files.imgix.net/3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/3bc04edd-4ce9-4ae3-8ce1-f7a795fb326d.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop" style="width:100%;height:auto" alt="How to Detect AI Content with Keystroke Tracking header image" class="styles_headerImage__FJQKQ"/></a><div><div class="text-12 font-normal text-light-gray"><span>Mathew Hardy</span> <!-- -->· <a href="/stories/category/how_to">How To</a> · <!-- -->3<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/how-to-detect-ai-content-with-keystroke-tracking"><div class="text-18 font-bold text-dark-gray">How to Detect AI Content with Keystroke Tracking</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13630"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/initially-failed-ph-launch-turned-around-to-get-us-850-paid-subscribers"><video style="width:100%;height:auto" class="styles_headerImage__FJQKQ styles_video__b8SeA" aria-label="An Initially Failed PH Launch Turned Around to Get Us 850+ Paid Subscribers header image" width="384" height="226" poster="https://ph-files.imgix.net/3c43ae0c-75e2-45b7-8e83-977c67ab4c92.webp?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;fm=webp&amp;w=384&amp;h=226&amp;fit=max&amp;frame=1&amp;dpr=2" muted="" loop="" disableRemotePlayback="" disablePictureInPicture="" playsInline="" preload="none"><source src="https://ph-files.imgix.net/3c43ae0c-75e2-45b7-8e83-977c67ab4c92.webp?fm=mp4&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/mp4"/><source src="https://ph-files.imgix.net/3c43ae0c-75e2-45b7-8e83-977c67ab4c92.webp?fm=webm&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/webm"/></video></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@antonosika">Anton Osika</a> <!-- -->· <a href="/stories/category/makers">Makers</a> · <!-- -->3<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/initially-failed-ph-launch-turned-around-to-get-us-850-paid-subscribers"><div class="text-18 font-bold text-dark-gray">An Initially Failed PH Launch Turned Around to Get Us 850+ Paid Subscribers</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13597"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/the-case-for-supabase"><img loading="lazy" srcSet="https://ph-files.imgix.net/a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/a9dcc38d-0921-4fe7-9f56-6ea150f3144e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop" style="width:100%;height:auto" alt="The Case for Supabase header image" class="styles_headerImage__FJQKQ"/></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@sanjanaf">Sanjana Friedman</a> <!-- -->· <a href="/stories/category/opinions">Opinions</a> · <!-- -->9<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/the-case-for-supabase"><div class="text-18 font-bold text-dark-gray">The Case for Supabase</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13564"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/3-5-years-12-hard-pivots-still-not-dead"><img loading="lazy" srcSet="https://ph-files.imgix.net/d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/d6b22c0a-c044-4fa1-9362-cb0cffe7626e.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop" style="width:100%;height:auto" alt="3.5 Years, 12 Hard Pivots, Still Not Dead header image" class="styles_headerImage__FJQKQ"/></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@hellovai">Vaibhav Gupta</a> <!-- -->· <a href="/stories/category/opinions">Opinions</a> · <!-- -->10<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/3-5-years-12-hard-pivots-still-not-dead"><div class="text-18 font-bold text-dark-gray">3.5 Years, 12 Hard Pivots, Still Not Dead</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13465"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/cofounder-mode-a-tactical-guide-to-finding-a-cofounder"><video style="width:100%;height:auto" class="styles_headerImage__FJQKQ styles_video__b8SeA" aria-label="Cofounder Mode: A Tactical Guide to Finding a Cofounder header image" width="384" height="226" poster="https://ph-files.imgix.net/d406b3ba-2d4d-4d08-a966-5610980e802d.webp?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;fm=webp&amp;w=384&amp;h=226&amp;fit=max&amp;frame=1&amp;dpr=2" muted="" loop="" disableRemotePlayback="" disablePictureInPicture="" playsInline="" preload="none"><source src="https://ph-files.imgix.net/d406b3ba-2d4d-4d08-a966-5610980e802d.webp?fm=mp4&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/mp4"/><source src="https://ph-files.imgix.net/d406b3ba-2d4d-4d08-a966-5610980e802d.webp?fm=webm&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/webm"/></video></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@robbalian">Rob Balian</a> <!-- -->· <a href="/stories/category/how_to">How To</a> · <!-- -->10<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/cofounder-mode-a-tactical-guide-to-finding-a-cofounder"><div class="text-18 font-bold text-dark-gray">Cofounder Mode: A Tactical Guide to Finding a Cofounder</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13432"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/a-founder-s-guide-to-ai-fine-tuning"><video style="width:100%;height:auto" class="styles_headerImage__FJQKQ styles_video__b8SeA" aria-label="A Founder’s Guide to AI Fine-Tuning header image" width="384" height="226" poster="https://ph-files.imgix.net/2cd80df4-e3ff-43dd-8885-ad4a6b499b80.webp?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;fm=webp&amp;w=384&amp;h=226&amp;fit=max&amp;frame=1&amp;dpr=2" muted="" loop="" disableRemotePlayback="" disablePictureInPicture="" playsInline="" preload="none"><source src="https://ph-files.imgix.net/2cd80df4-e3ff-43dd-8885-ad4a6b499b80.webp?fm=mp4&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/mp4"/><source src="https://ph-files.imgix.net/2cd80df4-e3ff-43dd-8885-ad4a6b499b80.webp?fm=webm&amp;crop=max&amp;w=384&amp;h=226&amp;dpr=2#t=0.001" type="video/webm"/></video></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@corbt">Kyle Corbitt</a> <!-- -->· <a href="/stories/category/how_to">How To</a> · <!-- -->5<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/a-founder-s-guide-to-ai-fine-tuning"><div class="text-18 font-bold text-dark-gray">A Founder’s Guide to AI Fine-Tuning</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13366"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/a-better-way-to-get-your-first-10-b2b-customers"><img loading="lazy" srcSet="https://ph-files.imgix.net/3850ebe3-c944-4989-9513-96bd2d5c8574.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/3850ebe3-c944-4989-9513-96bd2d5c8574.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/3850ebe3-c944-4989-9513-96bd2d5c8574.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/3850ebe3-c944-4989-9513-96bd2d5c8574.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop" style="width:100%;height:auto" alt="A Better Way to Get Your First 10 B2B Customers header image" class="styles_headerImage__FJQKQ"/></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@chrisbakke">Chris Bakke</a> <!-- -->· <a href="/stories/category/how_to">How To</a> · <!-- -->6<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/a-better-way-to-get-your-first-10-b2b-customers"><div class="text-18 font-bold text-dark-gray">A Better Way to Get Your First 10 B2B Customers</div></a></div></div></div><div class="styles_item__rz7L2 styles_widescreen-3__XIvvF styles_desktop-3__gO0fF" data-test="story-item-13399"><div class="styles_grid__clDr5 styles_grid--gap-4___DRbO styles_grid--column__Rcu66"><a class="text-16 font-normal text-dark-gray" href="/stories/the-cold-email-template-that-got-me-an-8-reply-rate"><img loading="lazy" srcSet="https://ph-files.imgix.net/618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=1 1x, https://ph-files.imgix.net/618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=2 2x, https://ph-files.imgix.net/618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop&amp;dpr=3 3x" src="https://ph-files.imgix.net/618ce5ca-71f8-4c26-b8e7-4be58a81ef6f.png?auto=compress&amp;codec=mozjpeg&amp;cs=strip&amp;auto=format&amp;w=384&amp;h=226&amp;fit=crop" style="width:100%;height:auto" alt="The Cold Email Template that Got Me an 8% Reply Rate header image" class="styles_headerImage__FJQKQ"/></a><div><div class="text-12 font-normal text-light-gray"><a class="text-12 font-normal text-light-gray" href="/@shen_xh">Xiaohan Shen</a> <!-- -->· <a href="/stories/category/how_to">How To</a> · <!-- -->4<!-- --> min read</div><a class="text-16 font-normal text-dark-gray" href="/stories/the-cold-email-template-that-got-me-an-8-reply-rate"><div class="text-18 font-bold text-dark-gray">The Cold Email Template that Got Me an 8% Reply Rate</div></a></div></div></div></div></header></div></div><script type="application/ld+json">[{"@context":"https://schema.org","@type":"NewsArticle","mainEntityOfPage":{"@type":"WebPage","@id":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql"},"headline":"Our Great Migration from MongoDB to PostgreSQL","image":["https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format&fit=crop&frame=1&h=512&w=1024"],"author":{"@type":"Person","name":"Tony Dang","image":"https://ph-avatars.imgix.net/3999558/original.jpeg?auto=format&fit=crop&crop=faces&w=100&h=100","url":"https://www.producthunt.com/@dangtony98"},"publisher":{"@type":"Organization","name":"Product Hunt","logo":{"@type":"ImageObject","url":"https://ph-static.imgix.net/ph-publisher-logo.png","width":220,"height":60}},"description":"","datePublished":"2024-07-02T10:00:00.000-07:00","dateModified":"2024-11-19T08:16:50.072-08:00"},{"@context":"http://schema.org","@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"name":"Stories","item":"https://www.producthunt.com/stories"},{"@type":"ListItem","position":2,"name":"Our Great Migration from MongoDB to PostgreSQL","item":"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql"}]}]</script><!--$--><!--/$--></div><div id="root-portal"></div><script>(self.__next_s=self.__next_s||[]).push([0,{"children":"\n !function(){var analytics=window.analytics=window.analytics||[];if(!analytics.initialize)if(analytics.invoked)window.console&&console.error&&console.error(\"Segment snippet included twice.\");else{analytics.invoked=!0;analytics.methods=[\"trackSubmit\",\"trackClick\",\"trackLink\",\"trackForm\",\"pageview\",\"identify\",\"reset\",\"group\",\"track\",\"ready\",\"alias\",\"debug\",\"page\",\"once\",\"off\",\"on\",\"addSourceMiddleware\",\"addIntegrationMiddleware\",\"setAnonymousId\",\"addDestinationMiddleware\"];analytics.factory=function(e){return function(){var t=Array.prototype.slice.call(arguments);t.unshift(e);analytics.push(t);return analytics}};for(var e=0;e<analytics.methods.length;e++){var key=analytics.methods[e];analytics[key]=analytics.factory(key)}analytics.load=function(key,e){var t=document.createElement(\"script\");t.type=\"text/javascript\";t.defer=!0;t.src=\"https://segment-cdn.producthunt.com/\";var n=document.getElementsByTagName(\"script\")[0];n.parentNode.insertBefore(t,n);analytics._loadOptions=e};analytics._writeKey=\"dtyjquswuq\";analytics.SNIPPET_VERSION=\"4.15.2\";\n analytics.load(\"dtyjquswuq\");\n }}();\n","id":"segment"}])</script><script src="/_next/static/chunks/webpack-d2b397d461e59162.js" async=""></script><script>(self.__next_f=self.__next_f||[]).push([0]);self.__next_f.push([2,null])</script><script>self.__next_f.push([1,"1:HL[\"/_next/static/css/a72ac300b2b8aae3.css\",\"style\"]\n2:HL[\"/_next/static/css/1ea9739f23a3b69e.css\",\"style\"]\n3:HL[\"/_next/static/css/8f6f840789d23ad8.css\",\"style\"]\n4:HL[\"/_next/static/css/fa118094cc4cd9f8.css\",\"style\"]\n5:HL[\"/_next/static/css/c99d6c2024146960.css\",\"style\"]\n6:HL[\"/_next/static/css/639ca35bc51610d3.css\",\"style\"]\n7:HL[\"/_next/static/css/1571eeb1adaac6eb.css\",\"style\"]\n8:HL[\"/_next/static/css/da95359741fd339a.css\",\"style\"]\n9:HL[\"/_next/static/css/0a0d922ec8281d19.css\",\"style\"]\na:HL[\"/_next/static/css/006228bc07977ccd.css\",\"style\"]\nb:HL[\"/_next/static/css/b0e0dd11aa1ac818.css\",\"style\"]\n"])</script><script>self.__next_f.push([1,"c:I[95751,[],\"\"]\nf:I[39275,[],\"\"]\n11:I[61343,[],\"\"]\n12:I[49620,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"94531\",\"static/chunks/94531-936a58903208c445.js\",\"7851\",\"static/chunks/7851-391d4a68ffe47521.js\",\"28051\",\"static/chunks/28051-6c99bb1ef2e7af63.js\",\"23714\",\"static/chunks/23714-107263d1137b8b64.js\",\"55151\",\"static/chunks/55151-9f3a96035f27a91c.js\",\"31158\",\"static/chunks/31158-f57f0197bfdfc676.js\",\"86111\",\"static/chunks/86111-10b40af0fab64eb1.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"63761\",\"static/chunks/63761-17f7fa9792e0fc0c.js\",\"95903\",\"static/chunks/95903-22bd3ff6f84beadc.js\",\"4095\",\"static/chunks/app/(main)/layout-d5b344c3d5112f09.js\"],\"default\",1]\n13:I[64417,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"74468\",\"static/chunks/74468-913b2d3a1cd26fb3.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"86883\",\"static/chunks/app/(main)/not-found-97bc615d259bf592.js\"],\"default\"]\n14:I[66914,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"sta"])</script><script>self.__next_f.push([1,"tic/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"AppRouter\"]\n15:I[76236,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"UserAgentProvider\"]\n16:I[39342,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"NavigationProgressProvider\"]\n17:I[3374,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.j"])</script><script>self.__next_f.push([1,"s\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"default\"]\n18:I[79395,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"31462\",\"static/chunks/app/(cards)/layout-8f806a8becc1daf9.js\"],\"default\"]\n19:I[75299,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"ErrorBoundary\"]\n1a:I[84080,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"6"])</script><script>self.__next_f.push([1,"9558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"\"]\n1c:I[64404,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"GoogleAnalytics\"]\n1d:I[27640,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"87620\",\"static/chunks/87620-cdf22e94cf823402.js\",\"17436\",\"static/chunks/17436-7d847d18b236a58e.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"63185\",\"static/chunks/app/layout-f3770231938d0d2a.js\"],\"GoogleTagManager\"]\n1f:I[96314,[\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"25058\",\"static/chunks/25058-f2b5f735f386b605.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"69558\""])</script><script>self.__next_f.push([1,",\"static/chunks/69558-1b9bff93d908a3d5.js\",\"64417\",\"static/chunks/64417-22df6c507fdbe6ed.js\",\"16470\",\"static/chunks/app/global-error-62b3730fa3f51ebe.js\"],\"default\"]\n10:[\"slug\",\"our-great-migration-from-mongodb-to-postgresql\",\"d\"]\n1b:T449,\n !function(){var analytics=window.analytics=window.analytics||[];if(!analytics.initialize)if(analytics.invoked)window.console\u0026\u0026console.error\u0026\u0026console.error(\"Segment snippet included twice.\");else{analytics.invoked=!0;analytics.methods=[\"trackSubmit\",\"trackClick\",\"trackLink\",\"trackForm\",\"pageview\",\"identify\",\"reset\",\"group\",\"track\",\"ready\",\"alias\",\"debug\",\"page\",\"once\",\"off\",\"on\",\"addSourceMiddleware\",\"addIntegrationMiddleware\",\"setAnonymousId\",\"addDestinationMiddleware\"];analytics.factory=function(e){return function(){var t=Array.prototype.slice.call(arguments);t.unshift(e);analytics.push(t);return analytics}};for(var e=0;e\u003canalytics.methods.length;e++){var key=analytics.methods[e];analytics[key]=analytics.factory(key)}analytics.load=function(key,e){var t=document.createElement(\"script\");t.type=\"text/javascript\";t.defer=!0;t.src=\"https://segment-cdn.producthunt.com/\";var n=document.getElementsByTagName(\"script\")[0];n.parentNode.insertBefore(t,n);analytics._loadOptions=e};analytics._writeKey=\"dtyjquswuq\";analytics.SNIPPET_VERSION=\"4.15.2\";\n analytics.load(\"dtyjquswuq\");\n }}();\n20:[]\n"])</script><script>self.__next_f.push([1,"0:[\"$\",\"$Lc\",null,{\"buildId\":\"BDohOcX48oWS9QbMlK-wt\",\"assetPrefix\":\"\",\"urlParts\":[\"\",\"stories\",\"our-great-migration-from-mongodb-to-postgresql\"],\"initialTree\":[\"\",{\"children\":[\"(main)\",{\"children\":[\"stories\",{\"children\":[[\"slug\",\"our-great-migration-from-mongodb-to-postgresql\",\"d\"],{\"children\":[\"__PAGE__\",{}]}]}]}]},\"$undefined\",\"$undefined\",true],\"initialSeedData\":[\"\",{\"children\":[\"(main)\",{\"children\":[\"stories\",{\"children\":[[\"slug\",\"our-great-migration-from-mongodb-to-postgresql\",\"d\"],{\"children\":[\"__PAGE__\",{},[[\"$Ld\",\"$Le\",[[\"$\",\"link\",\"0\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/0a0d922ec8281d19.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"1\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/006228bc07977ccd.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"2\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/b0e0dd11aa1ac818.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}]]],null],null]},[null,[\"$\",\"$Lf\",null,{\"parallelRouterKey\":\"children\",\"segmentPath\":[\"children\",\"(main)\",\"children\",\"stories\",\"children\",\"$10\",\"children\"],\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L11\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":\"$undefined\",\"notFoundStyles\":\"$undefined\"}]],null]},[null,[\"$\",\"$Lf\",null,{\"parallelRouterKey\":\"children\",\"segmentPath\":[\"children\",\"(main)\",\"children\",\"stories\",\"children\"],\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L11\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":\"$undefined\",\"notFoundStyles\":\"$undefined\"}]],null]},[[[[\"$\",\"link\",\"0\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/639ca35bc51610d3.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"1\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/1571eeb1adaac6eb.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"2\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/da95359741fd339a.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}]],[\"$\",\"$L12\",null,{\"children\":[\"$\",\"$Lf\",null,{\"parallelRouterKey\":\"children\",\"segmentPath\":[\"children\",\"(main)\",\"children\"],\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L11\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":[\"$\",\"$L13\",null,{\"code\":404}],\"notFoundStyles\":[]}],\"params\":{}}]],null],null]},[[[[\"$\",\"link\",\"0\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/a72ac300b2b8aae3.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"1\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/1ea9739f23a3b69e.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"2\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/8f6f840789d23ad8.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"3\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/fa118094cc4cd9f8.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}],[\"$\",\"link\",\"4\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/css/c99d6c2024146960.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\"}]],[\"$\",\"html\",null,{\"lang\":\"en\",\"children\":[[\"$\",\"head\",null,{\"children\":[[\"$\",\"meta\",null,{\"property\":\"fb:app_id\",\"content\":\"1467820943460899\"}],[\"$\",\"script\",null,{\"id\":\"injection\",\"dangerouslySetInnerHTML\":{\"__html\":\"window['__ENV__'] = {\\\"NODE_ENV\\\":\\\"production\\\"};\"}}],[\"$\",\"link\",null,{\"rel\":\"search\",\"type\":\"application/opensearchdescription+xml\",\"title\":\"ProductHunt\",\"href\":\"/osd.xml\"}]]}],[\"$\",\"body\",null,{\"className\":\"$undefined\",\"children\":[[\"$\",\"div\",null,{\"id\":\"root-container\",\"children\":[\"$\",\"$L14\",null,{\"children\":[\"$\",\"$L15\",null,{\"userAgent\":\"$undefined\",\"children\":[\"$\",\"$L16\",null,{\"children\":[\"$\",\"$L17\",null,{\"ApolloWrapper\":\"$18\",\"serverSideRendered\":true,\"children\":[\"$\",\"$L19\",null,{\"children\":[\"$\",\"$Lf\",null,{\"parallelRouterKey\":\"children\",\"segmentPath\":[\"children\"],\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L11\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":[[\"$\",\"title\",null,{\"children\":\"404: This page could not be found.\"}],[\"$\",\"div\",null,{\"style\":{\"fontFamily\":\"system-ui,\\\"Segoe UI\\\",Roboto,Helvetica,Arial,sans-serif,\\\"Apple Color Emoji\\\",\\\"Segoe UI Emoji\\\"\",\"height\":\"100vh\",\"textAlign\":\"center\",\"display\":\"flex\",\"flexDirection\":\"column\",\"alignItems\":\"center\",\"justifyContent\":\"center\"},\"children\":[\"$\",\"div\",null,{\"children\":[[\"$\",\"style\",null,{\"dangerouslySetInnerHTML\":{\"__html\":\"body{color:#000;background:#fff;margin:0}.next-error-h1{border-right:1px solid rgba(0,0,0,.3)}@media (prefers-color-scheme:dark){body{color:#fff;background:#000}.next-error-h1{border-right:1px solid rgba(255,255,255,.3)}}\"}}],[\"$\",\"h1\",null,{\"className\":\"next-error-h1\",\"style\":{\"display\":\"inline-block\",\"margin\":\"0 20px 0 0\",\"padding\":\"0 23px 0 0\",\"fontSize\":24,\"fontWeight\":500,\"verticalAlign\":\"top\",\"lineHeight\":\"49px\"},\"children\":\"404\"}],[\"$\",\"div\",null,{\"style\":{\"display\":\"inline-block\"},\"children\":[\"$\",\"h2\",null,{\"style\":{\"fontSize\":14,\"fontWeight\":400,\"lineHeight\":\"49px\",\"margin\":0},\"children\":\"This page could not be found.\"}]}]]}]}]],\"notFoundStyles\":[]}]}]}]}]}]}]}],[\"$\",\"div\",null,{\"id\":\"root-portal\"}],[[\"$\",\"$L1a\",null,{\"id\":\"intercom\",\"strategy\":\"afterInteractive\",\"dangerouslySetInnerHTML\":{\"__html\":\"\\n (function() {\\n if (window.innerWidth \u003c= 576) {\\n return;\\n }\\n window.intercomSettings = {\\n app_id: \\\"fe4ce68d4a8352909f553b276994db414d33a55c\\\"\\n };\\n (function(){var w=window;var ic=w.Intercom;if(typeof ic===\\\"function\\\"){ic('reattach_activator');ic('update',w.intercomSettings);}else{var d=document;var i=function(){i.c(arguments);};i.q=[];i.c=function(args){i.q.push(args);};w.Intercom=i;var l=function(){setTimeout(function(){var s=d.createElement('script');s.type='text/javascript';s.defer=true;s.src='https://widget.intercom.io/widget/fe4ce68d4a8352909f553b276994db414d33a55c';var x=d.getElementsByTagName('script')[0];x.parentNode.insertBefore(s,x);}, 4000);};if(w.attachEvent){w.attachEvent('onload',l);}else{w.addEventListener('load',l,false);}}})();\\n })()\\n\"}}],[\"$\",\"$L1a\",null,{\"id\":\"segment\",\"strategy\":\"beforeInteractive\",\"dangerouslySetInnerHTML\":{\"__html\":\"$1b\"}}],false,[[\"$\",\"$L1c\",null,{\"gaId\":\"G-WZ46833KH9\"}],[\"$\",\"$L1d\",null,{\"gtmId\":\"G-WZ46833KH9\"}]]]]}]]}]],null],null],\"couldBeIntercepted\":false,\"initialHead\":[null,\"$L1e\"],\"globalErrorComponent\":\"$1f\",\"missingSlots\":\"$W20\"}]\n"])</script><script>self.__next_f.push([1,"21:I[89136,[\"50155\",\"static/chunks/ee815485-de04c5299c631099.js\",\"54354\",\"static/chunks/673e98bc-0265ffc690629011.js\",\"53877\",\"static/chunks/53877-51c4a285eb192ef0.js\",\"46403\",\"static/chunks/46403-e33a58cdfbb894e8.js\",\"58056\",\"static/chunks/58056-751c28e77ae5a19a.js\",\"87138\",\"static/chunks/87138-0346ed4de56c8f41.js\",\"48191\",\"static/chunks/48191-5065c49d069bd01c.js\",\"14604\",\"static/chunks/14604-45e3a9aa74635210.js\",\"55579\",\"static/chunks/55579-59b56c16d22d5e09.js\",\"94531\",\"static/chunks/94531-936a58903208c445.js\",\"7851\",\"static/chunks/7851-391d4a68ffe47521.js\",\"28051\",\"static/chunks/28051-6c99bb1ef2e7af63.js\",\"23714\",\"static/chunks/23714-107263d1137b8b64.js\",\"17873\",\"static/chunks/17873-c31f11c5f34602f7.js\",\"1997\",\"static/chunks/1997-8c211c482f7f1b80.js\",\"18489\",\"static/chunks/18489-27cb2cd16662f495.js\",\"86224\",\"static/chunks/86224-d84904eb72b0dfed.js\",\"63470\",\"static/chunks/63470-3c423fadd5b8d82e.js\",\"89792\",\"static/chunks/89792-e60b17bdd9ad5353.js\",\"3638\",\"static/chunks/3638-eb4b9de42bd38a18.js\",\"50570\",\"static/chunks/50570-6a6ca0f37ede1d3b.js\",\"48567\",\"static/chunks/48567-5dfdc8e6fb42bbea.js\",\"59539\",\"static/chunks/59539-d4616fb2727e849e.js\",\"60732\",\"static/chunks/60732-57a9cb17d418c253.js\",\"26410\",\"static/chunks/26410-8d54001898f1c180.js\",\"10775\",\"static/chunks/10775-a9b2f35310c960a8.js\",\"16977\",\"static/chunks/16977-e4da546af4f18ac4.js\",\"78221\",\"static/chunks/78221-3b8b0bf117dcfe81.js\",\"40830\",\"static/chunks/40830-12562fb98330baca.js\",\"11611\",\"static/chunks/app/(main)/stories/%5Bslug%5D/page-0a1aea86d7645bc2.js\"],\"default\"]\n22:T4b9,[{\"@context\":\"https://schema.org\",\"@type\":\"NewsArticle\",\"mainEntityOfPage\":{\"@type\":\"WebPage\",\"@id\":\"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql\"},\"headline\":\"Our Great Migration from MongoDB to PostgreSQL\",\"image\":[\"https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024\"],\"author\":{\"@type\":\"Person\",\"name\":\"Tony Dang\",\"image\":\"https://ph-avatars.imgix.net/3999558/original.jpeg?auto=format\u0026f"])</script><script>self.__next_f.push([1,"it=crop\u0026crop=faces\u0026w=100\u0026h=100\",\"url\":\"https://www.producthunt.com/@dangtony98\"},\"publisher\":{\"@type\":\"Organization\",\"name\":\"Product Hunt\",\"logo\":{\"@type\":\"ImageObject\",\"url\":\"https://ph-static.imgix.net/ph-publisher-logo.png\",\"width\":220,\"height\":60}},\"description\":\"\",\"datePublished\":\"2024-07-02T10:00:00.000-07:00\",\"dateModified\":\"2024-11-19T08:16:50.072-08:00\"},{\"@context\":\"http://schema.org\",\"@type\":\"BreadcrumbList\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Stories\",\"item\":\"https://www.producthunt.com/stories\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Our Great Migration from MongoDB to PostgreSQL\",\"item\":\"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql\"}]}]e:[[\"$\",\"$L21\",null,{}],[\"$\",\"script\",null,{\"type\":\"application/ld+json\",\"dangerouslySetInnerHTML\":{\"__html\":\"$22\"}}]]\n"])</script><script>self.__next_f.push([1,"1e:[[\"$\",\"meta\",\"0\",{\"name\":\"viewport\",\"content\":\"width=device-width, initial-scale=1, minimum-scale=1\"}],[\"$\",\"meta\",\"1\",{\"name\":\"theme-color\",\"content\":\"#ffffff\"}],[\"$\",\"meta\",\"2\",{\"charSet\":\"utf-8\"}],[\"$\",\"title\",\"3\",{\"children\":\" Our Great Migration from MongoDB to PostgreSQL | Product Hunt\"}],[\"$\",\"meta\",\"4\",{\"name\":\"description\",\"content\":\"Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone's talking about.\"}],[\"$\",\"link\",\"5\",{\"rel\":\"author\",\"href\":\"https://www.producthunt.com/@dangtony98\"}],[\"$\",\"meta\",\"6\",{\"name\":\"author\",\"content\":\"Tony Dang\"}],[\"$\",\"link\",\"7\",{\"rel\":\"manifest\",\"href\":\"/manifest.json\",\"crossOrigin\":\"use-credentials\"}],[\"$\",\"meta\",\"8\",{\"name\":\"fb:app_id\",\"content\":\"1467820943460899\"}],[\"$\",\"link\",\"9\",{\"rel\":\"alternate\",\"type\":\"application/atom+xml\",\"title\":\"Product Hunt - All newest Products\",\"href\":\"https://www.producthunt.com/feed\"}],[\"$\",\"meta\",\"10\",{\"property\":\"og:title\",\"content\":\" Our Great Migration from MongoDB to PostgreSQL | Product Hunt\"}],[\"$\",\"meta\",\"11\",{\"property\":\"og:description\",\"content\":\"Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone's talking about.\"}],[\"$\",\"meta\",\"12\",{\"property\":\"og:url\",\"content\":\"https://www.producthunt.com/stories/our-great-migration-from-mongodb-to-postgresql\"}],[\"$\",\"meta\",\"13\",{\"property\":\"og:site_name\",\"content\":\"Product Hunt\"}],[\"$\",\"meta\",\"14\",{\"property\":\"og:locale\",\"content\":\"en_US\"}],[\"$\",\"meta\",\"15\",{\"property\":\"og:image\",\"content\":\"https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024\"}],[\"$\",\"meta\",\"16\",{\"property\":\"og:type\",\"content\":\"article\"}],[\"$\",\"meta\",\"17\",{\"name\":\"twitter:card\",\"content\":\"summary_large_image\"}],[\"$\",\"meta\",\"18\",{\"name\":\"twitter:site\",\"content\":\"@producthunt\"}],[\"$\",\"meta\",\"19\",{\"name\":\"twitter:creator\",\"content\":\"@dangtony98\"}],[\"$\",\"meta\",\"20\",{\"name\":\"twitter:title\",\"content\":\" Our Great Migration from MongoDB to PostgreSQL | Product Hunt\"}],[\"$\",\"meta\",\"21\",{\"name\":\"twitter:description\",\"content\":\"Product Hunt is a curation of the best new products, every day. Discover the latest mobile apps, websites, and technology products that everyone's talking about.\"}],[\"$\",\"meta\",\"22\",{\"name\":\"twitter:image\",\"content\":\"https://ph-files.imgix.net/f0a85533-cc7d-43a1-8df6-88c6aae0b886.png?auto=format\u0026fit=crop\u0026frame=1\u0026h=512\u0026w=1024\"}],[\"$\",\"link\",\"23\",{\"rel\":\"icon\",\"href\":\"https://ph-static.imgix.net/ph-favicon-brand-500.ico?auto=format\"}],[\"$\",\"link\",\"24\",{\"rel\":\"apple-touch-icon-precomposed\",\"href\":\"https://ph-static.imgix.net/ph-ios-icon.png?auto=format\"}],[\"$\",\"link\",\"25\",{\"rel\":\"chrome-webstore-item\",\"href\":\"https://producthunt.app.link/extension\"}]]\n"])</script><script>self.__next_f.push([1,"d:null\n"])</script></body></html>

Pages: 1 2 3 4 5 6 7 8 9 10