Archive for the ‘en-US’ Category
“All Architects !”: Empowering Every Developer as an Architect
Introduction
In the Devoxx France 2023 quickie “Tous architectes !”, Simon Maurin, Lead Architect at Leboncoin, delivers a compelling case for democratizing software architecture. Drawing from his decade-long experience at France’s leading classified ads platform, Maurin argues that architecture isn’t the sole domain of designated architects but a shared responsibility across development teams. This 15-minute talk explores how Leboncoin evolved its architectural practices to scale with growth, offering practical insights for developers and tech leads navigating large organizations.
Key Insights
Maurin begins by reflecting on Leboncoin’s early days, where small teams naturally collaborated on architecture through organic discussions. As the company grew to serve 30 million monthly users, this informal approach became unsustainable. The introduction of formal architects risked creating bottlenecks and disconnects. Maurin highlights the pivotal shift to empowering all developers as architects, fostering a culture where everyone contributes to design decisions. This approach aligns with Domain-Driven Design principles, which Maurin champions as a tool for maintaining clarity in complex systems.
A key mechanism introduced at Leboncoin was Architecture Decision Records (ADRs). These lightweight documents capture the rationale behind architectural choices, ensuring transparency and continuity. Maurin shares a case study where ADRs helped Leboncoin transition from a monolith to microservices, reducing coupling and enabling faster iterations. The talk also touches on data engineering challenges, such as scaling to handle 10 million daily events, underscoring the need for shared ownership in high-traffic environments.
Lessons Learned
Maurin’s talk offers several takeaways for developers:
-
Shared Responsibility: Architecture thrives when all team members, not just architects, engage in decision-making.
-
ADRs as a Tool: Documenting decisions prevents knowledge silos and aids onboarding.
-
Cultural Shift: Scaling architecture requires fostering a mindset where developers feel empowered to challenge and contribute.
These lessons are particularly relevant for growing tech organizations facing the tension between agility and structure. Maurin’s emphasis on collaboration over hierarchy resonates with modern software engineering trends.
Conclusion
Simon Maurin’s “Tous architectes !” is a rallying cry for developers to embrace their role in shaping software architecture. By sharing Leboncoin’s journey, Maurin provides a roadmap for balancing freedom and formality in large teams. This talk is a must-watch for developers and architects seeking to foster inclusive, scalable practices in their organizations.
[SpringIO2023] Anatomy of a Spring Boot App with Clean Architecture: Steve Pember
In a thought-provoking session at Spring I/O 2023, Steve Pember, a seasoned developer from Boston-based startup Stavi, explored the principles of Clean Architecture and their application within Spring Boot applications. Drawing from Robert Martin’s influential book, Steve demonstrated how Clean Architecture, inspired by patterns like Ports and Adapters and Hexagonal Architecture, fosters readable, flexible, and maintainable codebases. Through a reference application and practical insights, he provided a roadmap for developers to structure Spring Boot apps that remain resilient to change and scalable for large teams.
The Case for Software Architecture
Steve began by addressing the often-misunderstood role of software architecture, challenging the stereotype of architects as mere whiteboard enthusiasts. He likened software architects to their building counterparts, who design every detail from high-level structures to minute specifics. Without proper architecture, Steve warned, systems devolve into unmaintainable “big balls of mud,” slowing development and hindering competitiveness. He highlighted the benefits of well-architected systems—separation of concerns, modularity, testability, and maintainability—arguing that these guardrails enable teams to maintain velocity over time, even if they initially slow development.
Principles of Clean Architecture
Delving into Clean Architecture, Steve outlined its core concepts: SOLID principles, component design, boundaries, and dependency rules. He clarified SOLID principles, such as single responsibility (supporting one user type per class) and dependency inversion (using interfaces), as foundational to clean code. Components, he explained, should be independently developable and loosely coupled, aligning with domain-driven design or microservices. The defining feature of Clean Architecture is its layered structure, where dependencies point inward to a core of business logic, encapsulated by interfaces that shield it from external details like databases or third-party services. This ensures the core remains agnostic, enhancing flexibility and testability.
Implementing Clean Architecture in Spring Boot
Steve demonstrated how to apply Clean Architecture in Spring Boot using a reference shoe store application. He proposed a multi-module structure with three components: core (housing business logic, entities, and services), details (containing database and third-party integrations), and app (where Spring configuration and integration occur). By using interfaces for repositories and gateways, the core remains independent of external systems, allowing seamless swaps, such as replacing a PostgreSQL repository with DynamoDB. Steve emphasized minimal controllers and service classes, advocating for specific, single-responsibility services like CustomerOrderQueryService. He also highlighted the importance of integration tests, using tools like Testcontainers to validate interactions with external systems.
Treating Details as Deferrable
A key takeaway was Steve’s mantra that “everything not in core is a detail.” Databases, environments, input mechanisms, and even Spring itself should be treated as implementation details, deferrable until necessary. He cautioned against premature database schema design, urging developers to prioritize business logic over storage concerns. By encapsulating details behind interfaces, applications become adaptable to changes, such as switching databases or input methods (e.g., HTTP to Kafka). Steve’s demo showcased this flexibility, swapping a PostgreSQL order repository for DynamoDB with minimal code changes, proving the power of Clean Architecture’s plug-in approach.
Links:
[NodeCongress2021] Don’t Try This at Home: Synchronous I/O in Node.js – Anna Henningsen
Node.js’s asynchronous creed—non-blocking I/O as ethos—clashes intriguingly with synchronous imperatives, where immediacy trumps concurrency. Anna Henningsen, erstwhile Node.js TSC member now at MongoDB’s dev tools cadre, probes this tension, cataloging detours from the async path and gleaning internals’ revelations. Pronouns she/her, Anna balances core contributions with family joys, her moniker addaleax echoing across Twitter and GitHub.
Anna queries the aversion: sync ops monopolize threads, stalling event loops—left pane’s stalled fetches versus right’s parallel prowess. Yet, exigencies persist: CLI bootstraps, config reads—fs.readFileSync reigns for startup simplicity.
Navigating Sync Detours and Their Perils
Anna enumerates evasions: worker_threads offloads to pools, yielding promises—fs.promises.readFile in isolates, main-thread yields via Atomics.wait. Threads excel for CPU hogs, but I/O yields context switches, inflating overheads.
Child processes fork interpreters, stdin/stdout pipes async, but spawnSync blocks—IPC for coordination. Anna demos: execSync shells commands, perils in untrusted inputs.
Domains? Deprecated, error silos sans true parallelism. Async_hooks? Context propagation, not computation.
Enter Anna’s brainchild: synchronous workers—native addons spawning interpreters, runUntil blocks main on promises, full API access sans multi-threading. Node 15.5+ requisites, experimental tag.
MongoDB’s Babel transpilation awaits sync-as-call sites, best-effort awaits. Anna’s taxonomy—drawbacks galore—affirms async’s supremacy, yet equips edge cases with informed arsenals.
Experimental Horizons and Practical Caveats
Anna’s holiday hack—runnable on GitHub—invites tinkering, crashes notwithstanding. Her MongoDB pivot underscores sync’s niche: edge functions crave immediacy, transpilation bridges gaps.
Anna’s disquisition, laced with humor, fortifies Node.js fidelity to flux, while charting sync’s shadowed trails.
Links:
[PyConUS 2023] Fixing Legacy Code, One Pull Request at a Time
At PyCon US 2023, Guillaume Dequenne from Sonar presented a compelling workshop on modernizing legacy codebases through incremental improvements. Sponsored by Sonar, this session focused on integrating code quality tools into development workflows to enhance maintainability and sustainability, using a Flask application as a practical example. Guillaume’s approach, dubbed “Clean as You Code,” offers a scalable strategy for tackling technical debt without overwhelming developers.
The Legacy Code Conundrum
Legacy codebases often pose significant challenges, accumulating technical debt that hinders development efficiency and developer morale. Guillaume illustrated this with a vivid metaphor: analyzing a legacy project for the first time can feel like drowning in a sea of issues. Traditional approaches to fixing all issues at once are unscalable, risking functional regressions and requiring substantial resources. Instead, Sonar advocates for a pragmatic methodology that focuses on ensuring new code adheres to high-quality standards, gradually reducing technical debt over time.
Clean as You Code Methodology
The “Clean as You Code” approach hinges on two principles: ownership of new code and incremental improvement. Guillaume explained that developers naturally understand and take responsibility for code they write today, making it easier to enforce quality standards. By ensuring that each pull request introduces clean code, teams can progressively refurbish their codebase. Over time, as new code replaces outdated sections, the overall quality improves without requiring a massive upfront investment. This method aligns with continuous integration and delivery (CI/CD) practices, allowing teams to maintain high standards while delivering features systematically.
Leveraging SonarCloud for Quality Assurance
Guillaume demonstrated the practical application of this methodology using SonarCloud, a cloud-based static analysis tool. By integrating SonarCloud into a Flask application’s CI/CD pipeline, developers can automatically analyze pull requests for issues like bugs, security vulnerabilities, and code smells. He showcased how SonarCloud’s quality gates enforce standards on new code, ensuring that only clean contributions are merged. For instance, Guillaume highlighted a detected SQL injection vulnerability due to unsanitized user input, emphasizing the tool’s ability to provide contextual data flow analysis to pinpoint and resolve issues efficiently.
Enhancing Developer Workflow with SonarLint
To catch issues early, Guillaume introduced SonarLint, an IDE extension for PyCharm and VSCode that performs real-time static analysis. This tool allows developers to address issues before committing code, streamlining the review process. He demonstrated how SonarLint highlights issues like unraised exceptions and offers quick fixes, enhancing productivity. Additionally, the connected mode between SonarLint and SonarCloud synchronizes issue statuses, ensuring consistency across development and review stages. This integration empowers developers to maintain high-quality code from the outset, reducing the burden of post-commit fixes.
Sustaining Codebase Health
The workshop underscored the long-term benefits of the “Clean as You Code” approach, illustrated by a real-world project where issue counts decreased over time as new rules were introduced. By focusing on new code and leveraging tools like SonarCloud and SonarLint, teams can achieve sustainable codebases that are maintainable, reliable, and secure. Guillaume’s presentation offered a roadmap for developers to modernize legacy systems incrementally, fostering a culture of continuous improvement.
Links:
Hashtags: #LegacyCode #CleanCode #StaticAnalysis #SonarCloud #SonarLint #Python #Flask #GuillaumeDequenne #PyConUS2023
[SpringIO2023] Spring is Bootiful but So is Your Domain: Michael Plöd’s Call to Action
At Spring I/O 2023 in Barcelona, Michael Plöd delivered an engaging and unconventional talk that urged developers to step beyond their technical comfort zones and dive into the business domains they serve. Departing from the typical code-heavy sessions of the conference, Michael, a fellow at InnoQ and a long-time Spring user, emphasized the transformative power of understanding business contexts. Through interactive polls, real-world anecdotes, and practical strategies, he inspired attendees to become more valuable developers by aligning their technical expertise with business needs, ultimately enhancing code quality, team collaboration, and product impact.
The Value of Domain Knowledge
Michael opened by challenging the audience to reflect on their motivations for becoming software engineers, humorously acknowledging the allure of financial rewards but quickly pivoting to a deeper point: developers who grasp their business domain become significantly more valuable. He argued that domain knowledge enables better design choices, from writing maintainable code to making informed modularization decisions. By understanding the business, developers can create software that aligns with organizational goals, reducing friction and enhancing agility. Michael’s interactive poll revealed that many attendees had only a partial understanding of their business models, underscoring the need for greater curiosity about customer segments, value propositions, and revenue streams.
Writing Maintainable Code Through Domain Alignment
A standout moment was Michael’s recounting of a formative experience as a young developer at a bank, tasked with building a mortgage loan scoring engine. Initially, he relied on a detailed 50-page specification, structuring the code around assumed rules for points and no-go criteria. However, during acceptance testing, discrepancies emerged, revealing a mismatch between his mental model and the risk managers’ perspective. By directly engaging with the risk managers and refactoring the code to reflect their clustered rule structure, Michael transformed a complex change into a straightforward task. This story highlighted the importance of understanding the business’s mental model, reducing implicit assumptions, and structuring code to mirror domain logic, resulting in more maintainable and adaptable software.
Improving Modularization and Communication
Michael emphasized that domain knowledge informs better modularization decisions, particularly in architectures like microservices or serverless systems. He cited the Accelerate book, which links loosely coupled architectures to high-performing IT organizations, suggesting that aligning modules with business domains enhances team autonomy and delivery speed. Another poll showed strong audience agreement that modularization impacts value propositions, reinforcing the need to consider business goals when defining module boundaries. On communication, Michael cautioned against using technical jargon that alienates business stakeholders, advocating for empathy and clear language. He shared an amusing example of a fashion retailer where database table names leaked into sales floor terminology, illustrating the pitfalls of disconnected communication.
Influencing Product Design
The talk culminated in a call to influence product design through domain expertise. Michael argued that developers who understand business problems can propose solutions that enhance user experiences or create new business models. He referenced Marty Cagan’s research, which identifies direct customer feedback as a top source for product ideas, suggesting developers contribute more than just code. A final poll on digitalization revealed varied interpretations, from paperless processes to business model innovation, prompting Michael to stress that both improving existing models and creating new ones require close collaboration between technology and business teams. By fostering curiosity and asking questions, developers can bridge this gap, driving meaningful digital transformation.
Links:
[NodeCongress2023] Deconstructing the JavaScript Runtime: V8, Libuv, and the Mechanics of Performance
Lecturer: Erick Wendel
Erick Wendel is a highly active member of the JavaScript and Node.js open-source community, serving as a Node.js core committer and international keynote speaker. He is recognized as a professional educator and holds multiple prestigious awards, including Google Developer Expert (GDE), Microsoft Most Valuable Professional (MVP), and GitHub Star. Mr. Wendel has made significant contributions to the Node.js core, specifically in modules like the native test runner and child process, and is known for his work in recreating the Node.js runtime from scratch as an educational exercise. He is the founder of EW Academy, a platform dedicated to advanced JavaScript education, having trained over 100,000 developers globally.
- Institutional Profile/Professional Page: Erick Wendel
- X (Twitter): @erickwendel_
- LinkedIn: in/erickwendel
Abstract
This article provides a scholarly analysis of the fundamental architectural components of modern JavaScript runtimes, such as Node.js, Deno, and Bun, by examining the core technologies that enable their high performance. The focus is on the essential interaction between the V8 JavaScript engine, the Libuv library for asynchronous I/O, and the C++ bindings (Core Modules) that interface with the operating system. The study highlights the methodological challenges involved in bridging JavaScript’s garbage-collected memory model with C++’s direct memory management, which is key to understanding runtime optimization.
Context: The Runtime Landscape
The recent proliferation of new JavaScript runtimes (Bun, Deno) underscores the need for deep optimization and architectural choices that address modern system demands. These runtimes are not monolithic; they are complex systems composed of distinct, specialized components. Understanding these components is crucial to grasping the functional differences and performance advantages between the various environments.
Methodology and Core Components
The construction of a JavaScript runtime hinges on three primary architectural pillars:
- V8 JavaScript Engine: V8 is the foundation, responsible for parsing, compiling (Just-In-Time), and executing JavaScript code. Its primary functions are managing the garbage-collected memory heap and the event loop. It provides an interface (an
isolate) that must be utilized to communicate with the JavaScript environment. - Libuv (Library for Unix/Windows V8): Libuv is a cross-platform asynchronous I/O library that provides the core threading, event loop management, and non-blocking networking capabilities. It abstracts the differences in operating system APIs (e.g., Windows vs. Linux) to ensure a consistent interface for I/O operations.
- Core Modules/Bindings (The Bridge): These are the C++ functions that act as the essential link between the JavaScript environment (managed by V8) and the operating system’s capabilities (often accessed via Libuv). They expose low-level operating system features (like file system access or network sockets) to JavaScript.
Analysis: The Interoperability Challenge
The most critical challenge in runtime design is managing the interaction between V8 and the C++ code. Since V8 manages its own memory (garbage collection) and C++ uses direct memory allocation, a robust, safe interface is required. Any attempt to call a C++ function from JavaScript necessitates crossing this boundary, which requires obtaining a V8 isolate instance. Furthermore, to handle asynchronous operations, C++ functions must receive a callback, execute their blocking I/O on the Libuv thread pool, and then signal V8 to process the result on the main event loop.
Consequences and Implications
The lecture demonstrates that core differences between runtimes often stem from the specific C++ implementations and optimization choices made within the Core Modules/Bindings and how they interact with underlying system calls and Libuv. While V8 and Libuv are largely standardized components, the performance gains and unique features of runtimes like Bun (which uses Zig and JavaScriptCore instead of V8) are realized by optimizing the “glue” layer. The current environment suggests collaboration rather than outright competition, with core contributors and key figures moving between and contributing to the various runtime organizations (Node.js, Deno), fostering a shared advancement of the ecosystem.
Relevant links and hashtags
- Lecture Video: Bun, Deno, Node.js? Recreating a JavaScript runtime from Scratch – Erick Wendel, Node Congress 2023
- Lecturer Professional Links:
- Professional Page: Erick Wendel
- X (Twitter): @erickwendel_
- LinkedIn: in/erickwendel
- Organization: EW Academy
Hashtags: #JSRuntime #V8Engine #Libuv #NodeJS #Deno #Bun #SystemsProgramming #CoreModules #NodeCongress
[PHPForumParis2022] FrankenPHP: Diving into PHP’s Interpreter, Virtual Machines, and More – Kévin Dunglas
Kévin Dunglas, a seasoned developer at Les-Tilleuls.coop and creator of API Platform, presented an innovative exploration of FrankenPHP at PHP Forum Paris 2022. Blending PHP with Go, Kévin introduced a groundbreaking server solution that pushes PHP’s boundaries. His talk delved into the technical intricacies of integrating Go’s threading model with PHP’s interpreter, offering a glimpse into a future where PHP applications achieve unprecedented performance and flexibility.
Introducing FrankenPHP
Kévin opened with the origins of FrankenPHP, a project born from his passion for both PHP and Go. Inspired by Les-Tilleuls’ developer Loris Sorio, who designed its logo, FrankenPHP aims to combine PHP’s ease of use with Go’s performance capabilities. Kévin explained how it leverages Go’s threading to overcome PHP-FPM’s limitations, enabling features like concurrent request handling. This fusion, he argued, unlocks new possibilities for PHP applications, particularly in high-performance scenarios.
Overcoming Technical Challenges
Delving into the technical core, Kévin described the complexities of integrating PHP’s Zend Thread Safe (ZTS) mode with Go’s threading model. He highlighted challenges like signal conflicts and the lack of OPcache support, which required custom modifications to PHP’s source code. By isolating PHP processes within Go threads, Kévin’s team achieved stable communication, though he noted the solution remains experimental. His transparency about these hurdles provided valuable insights for developers exploring similar integrations.
Performance and Future Directions
Kévin showcased FrankenPHP’s performance potential, demonstrating how enabling OPcache by modifying PHP’s SAPI list significantly reduced compilation overhead. He outlined future goals, including support for Laravel Octane and Symfony’s CLI, while acknowledging Windows compatibility challenges. Kévin’s call for community contributions to refine FrankenPHP underscored its open-source ethos, inviting developers to explore its code and report issues to enhance its stability.
Community Engagement and Collaboration
Concluding, Kévin emphasized the collaborative spirit driving FrankenPHP’s development. He encouraged developers to contribute via GitHub, highlighting the project’s experimental nature and potential for growth. By sharing Les-Tilleuls’ vision, Kévin inspired attendees to experiment with FrankenPHP, fostering a community-driven effort to redefine PHP’s role in modern web development.
Links:
[Spring I/O 2023] Do You Really Need Hibernate?
Simon Martinelli’s thought-provoking session at Spring I/O 2023 challenges the default adoption of Hibernate in Java applications. With decades of experience, Simon advocates for jOOQ as a performant, SQL-centric alternative for database-centric projects. Using a track-and-field event management system as a case study, he illustrates how jOOQ simplifies data access, avoids common ORM pitfalls, and complements Hibernate when needed. This presentation is a masterclass in rethinking persistence strategies for modern Java development.
Questioning the ORM Paradigm
Simon begins by questioning the reflexive use of Hibernate and JPA in Java projects. While powerful for complex domain models, ORMs introduce overhead—such as dirty checking or persistence by reachability—that may not suit all applications. For CRUD-heavy systems, like his 25-year-old event management application, a simpler approach is often sufficient. By focusing on database tables rather than object graphs, developers can streamline data operations, avoiding the complexity of managing entity state transitions.
jOOQ: A Database-First Approach
jOOQ’s database-first philosophy is central to Simon’s argument. By generating type-safe Java code from database schemas, jOOQ enables developers to write SQL-like queries using a fluent DSL. This approach, as Simon demonstrates, ensures compile-time safety and eliminates runtime errors from mismatched SQL strings. The tool supports a wide range of databases, including legacy systems with stored procedures, making it versatile for both modern and enterprise environments. Integration with Flyway and Testcontainers further simplifies schema migrations and code generation.
Efficient Data Retrieval with Nested Structures
A highlight of Simon’s talk is jOOQ’s ability to handle nested data structures efficiently. Using the event management system’s ranking list—a tree of competitions, categories, athletes, and results—he showcases jOOQ’s MULTISET feature. This leverages JSON functionality in modern databases to fetch hierarchical data in a single SQL statement, avoiding the redundancy of JPA’s join fetches. This capability is particularly valuable for REST APIs and reporting, where nested data is common, eliminating the need for DTO mapping.
Combining jOOQ and Hibernate for Flexibility
Rather than advocating for jOOQ as a complete replacement, Simon proposes a hybrid approach. jOOQ excels in querying, bulk operations, and legacy database integration, while Hibernate shines in entity state management and cascading operations. By combining both in a single application, developers can leverage their respective strengths. Simon warns against using JPA for raw SQL, as it lacks jOOQ’s type safety, reinforcing the value of choosing the right tool for each task.
Practical Insights and Tooling
Simon’s demo, backed by a GitHub repository, illustrates jOOQ’s integration with Maven, Testcontainers, and a new Testcontainers Flyway plugin. He highlights practical considerations, such as whether to version generated code and jOOQ’s licensing model for commercial databases. The talk also addresses limitations, like MULTISET’s incompatibility with MariaDB, offering candid advice for database selection. These insights ground the presentation in real-world applicability, making it accessible to developers of varying experience levels.
A Call to Rethink Persistence
Simon’s presentation is a compelling call to reassess persistence strategies. By showcasing jOOQ’s performance and flexibility, he encourages developers to align their tools with application needs. His track-and-field application, evolved over decades, serves as a testament to the enduring value of SQL-driven development. For Java developers seeking to optimize data access, this talk offers a clear, actionable path forward, blending modern tooling with pragmatic wisdom.
Links:
Hashtags: #SpringIO2023 #jOOQ #Hibernate #Java #SQL #Database #SimonMartinelli #Testcontainers #Flyway
[Spring I/O 2023] Multitenant Mystery: Only Rockers in the Building by Thomas Vitale
In the vibrant atmosphere of Spring I/O 2023, Thomas Vitale, a seasoned software engineer and cloud architect at Systematic in Denmark, captivated the audience with his exploration of multitenant architectures in Spring Boot applications. Through a compelling narrative involving a stolen guitar in a building inhabited by rock bands, Thomas unraveled the complexities of ensuring data isolation, security, and observability in multi-tenant systems. His presentation, rich with practical insights and live coding, offered a masterclass in building robust SaaS solutions using Java, Spring, and related technologies.
Understanding Multitenancy
Thomas began by defining multitenancy as an architecture where a single application instance serves multiple clients, or tenants, simultaneously. This approach, prevalent in software-as-a-service (SaaS) solutions, optimizes operational costs by sharing infrastructure across customers. He illustrated this with an analogy of a building housing rock bands, where each band (tenant) shares common facilities like staircases but maintains private storage for their instruments. This setup underscores the need for meticulous data isolation to prevent cross-tenant data leakage, a critical concern in industries like healthcare where regulatory compliance is paramount.
Implementing Tenant Resolution
A cornerstone of Thomas’s approach was establishing a tenant context within a Spring Boot application. He demonstrated how to resolve tenant information from HTTP requests using a custom header, X-Tenant-ID. By implementing a tenant resolver and interceptor, Thomas ensured that each request’s tenant identifier is stored in a thread-local context, accessible throughout the request lifecycle. His live coding showcased the integration of Spring MVC’s HandlerInterceptor to seamlessly extract and manage tenant data, setting the stage for further customization. This mechanism allows developers to process requests in a tenant-specific manner, enhancing the application’s flexibility.
Data Isolation Strategies
Data isolation emerged as the most critical aspect of multitenancy. Thomas outlined three strategies: discriminator-based partitioning, separate schemas, and separate databases. He focused on the separate schema approach, leveraging Hibernate and Spring Data JPA to manage tenant-specific schemas within a single PostgreSQL database. By configuring Hibernate’s CurrentTenantIdentifierResolver and MultiTenantConnectionProvider, Thomas ensured that database connections dynamically switch schemas based on the tenant context. His demo highlighted the effectiveness of this strategy, showing how instruments stored for one tenant (e.g., “Dukes”) remained isolated from another (“Beans”), thus safeguarding data integrity.
Security and Observability
Security and observability were pivotal in Thomas’s narrative. He addressed the challenge of dynamic authentication by integrating Keycloak, allowing tenant-specific identity providers to be resolved at runtime. This approach avoids hardcoding configurations, enabling seamless onboarding of new tenants. For observability, Thomas emphasized the importance of tenant-specific logging, metrics, and tracing. Using Micrometer and OpenTelemetry, he enriched logs and traces with tenant identifiers, facilitating debugging and monitoring. A critical lesson emerged during his demo: a caching oversight led to data leakage across tenants, underscoring the need for tenant-specific cache keys. Thomas resolved this by implementing a custom key generator, restoring data isolation.
Solving the Mystery
The stolen guitar mystery served as a metaphor for real-world multitenancy pitfalls. By tracing the issue to a caching flaw, Thomas illustrated how seemingly minor oversights can have significant consequences. His resolution—ensuring tenant-specific caching—reinforced the importance of vigilance in multi-tenant systems. The presentation concluded with a call to prioritize data isolation, offering attendees a blueprint for building scalable, secure SaaS applications with Spring Boot.
Links:
- Thomas Vitale on LinkedIn
- Systematic company website
- Thomas Vitale’s GitHub repository
- Thomas Vitale’s book: Cloud Native Spring in Action
Hashtags: #Multitenancy #SpringBoot #Java #SaaS #DataIsolation #Security #Observability #ThomasVitale #Systematic #Keycloak #Hibernate #SpringIO2023
[KotlinConf2023] Compose Multiplatform on iOS: Sharing UIs Across Ecosystems with Sebastian Aigner and Nikita Lipsky
At KotlinConf’23, Sebastian Aigner (Developer Advocate at JetBrains) and Nikita Lipsky (Software Developer for Kotlin at JetBrains) presented an exciting overview of Compose Multiplatform, focusing on its then-Alpha support for iOS. Their session detailed how this JetBrains initiative enables developers to write their user interface once in Kotlin and deploy it across Android, iOS, desktop, and web, fostering significant code sharing and development efficiency. The official documentation for Compose Multiplatform offers further insights.
The presentation began by recapping the classic Kotlin Multiplatform (KMP) use case, which allows sharing of business logic while retaining access to platform-specific APIs. Compose Multiplatform builds upon this by providing a solution for sharing the UI layer itself, addressing scenarios where building and maintaining separate native UIs for each platform is not feasible due to time, resources, or the desire for rapid market entry. While the talk focused on iOS and Android, the speakers emphasized that Compose Multiplatform also supports desktop (stabilized in late 2021) and web targets.
Architecture and Jetpack Compose Foundations
A key point underscored by Sebastian and Nikita was that Compose Multiplatform is built upon Jetpack Compose, Google’s modern declarative UI toolkit for Android, which is 100% Kotlin. This means developers familiar with Jetpack Compose can leverage their existing knowledge and skills to build UIs for iOS and other platforms. The JetBrains team collaborates closely with Google, regularly upstreaming changes to the Jetpack Compose repositories.
Nikita Lipsky delved into the architecture, explaining that official Jetpack Compose itself is already a Kotlin Multiplatform project at its core, with its lowest levels defining Kotlin Multiplatform sources. The composable function concept is an extension to the Kotlin language requiring compiler support, and the entire Compose system is managed by the Compose Runtime. For iOS, Compose Multiplatform renders UI elements by drawing directly onto a CAPI (Canvas API) provided by Skiko, a graphics library that abstracts over Skia (for Android and desktop) and CoreGraphics (for iOS). This allows for consistent rendering across platforms.
Live Demos and iOS Integration
The session featured live demonstrations showcasing the capabilities of Compose Multiplatform on iOS. Sebastian Aigner walked through a sample application, highlighting how standard Jetpack Compose code for UI elements, state management (using remember), layouts (like Column), and modifiers can be shared and run on iOS simulators and devices. He demonstrated features like text input, button interactions, and even integration with iOS-specific functionalities like the share sheet, emphasizing the goal of seamless interoperability.
The speakers also discussed the importance of providing solid accessibility integrations and ensuring smooth performance, even on high-refresh-rate displays, which is an ongoing area of focus for the Kotlin/Native and Compose Multiplatform teams. Interoperability with existing iOS UI code (SwiftUI and UIKit) was also presented as a key feature, allowing for gradual adoption. Developers can embed Compose Multiplatform views within existing SwiftUI applications or, conversely, embed native iOS views within a Compose Multiplatform UI. This flexibility is crucial for teams looking to integrate Compose into their established projects incrementally.
Getting Started and Future Outlook
Sebastian and Nikita provided clear guidance on how developers can start experimenting with Compose Multiplatform for iOS. They pointed to project templates, sample applications available on the Compose Multiplatform GitHub repository (including to-do list apps and code viewers), and updated KMP production samples that now include branches with Compose-based UI implementations. The new memory manager in Kotlin/Native was also mentioned as a significant improvement, simplifying multi-threaded programming for all Kotlin targets, including iOS.
While acknowledging that the iOS target was in Alpha and some areas were still works in progress, the overall message was one of excitement and a call to action for the community. They encouraged developers to explore the technology, provide feedback, and contribute to its evolution. The vision is a future where developers can agree on a delightful way to write UIs for all their target platforms using Kotlin.