Software System Design
I do not know how the perfect software architectures are build. It is possible that perfect software designs are myth. …
I do not know how the perfect software architectures are build. It is possible that perfect software designs are myth. …
Kotlin supports Higher order functions. In this blog, I will create a higher order function that will use map & fold right for execution. Before diving into higher order functions, let’s go through map & fold right. map is collective transform operation. var numbers = mutableListOf(1, 2, 3) numbers = numbers.map { it*2 }.toMutableList() // elements in numbers: 2,4,6 foldRight accept initial state, apply initial state to all elements and return final state. var numbers = mutableListOf(1, 2, 3) var result = numbers.foldRight(100, {a,b -> test(a,b)}) private fun test(a: Int, b: Any): Int { return a + b as Int } /* First execution: initial 100 a = 3 b = 100 Second Execution a = 2 b = 103 Third Execution a = 1 b = 105 final: result = 106 */ Let’s create a higher order function Middleware that takes an instance StringApp, has inner function next: Type and return Type. ...
It is very connivent to use any DI framework when all the objects required are available in application. For example, I have two classes Logger, Service and class Middleware is dependent on these classes. class Logger() class Service() //this class requires Logger & Service object class Middleware(private val logger:Logger. private val service:Service) // middleware object val middleware = Middleware(Logger(),Service()) Dagger can build objects of Logger and Service classes by indicating @Inject annotation to all three classes internal class Logger @Inject constructor() internal class Service @Inject constructor() //this class requires Logger & Service object internal class Middleware @Inject constructor(private val logger:Logger. private val service:Service) @Component interface MiddlewareComponent { fun buildComponent():Middleware } // middleware object val middleware = DaggerMiddlewareComponent.builder().build().buildComponent() If the project requirements are modified to get Logger with custom implementation, we can write @Module to support dependency injection. // now, Logger is interface interface Logger class Service @Inject constructor() class Middleware @Inject constructor(val logger: Logger, val service: Service) @Module class LoggerModule constructor(val logger: Logger) { @Provides fun providesLogger(): Logger { return logger } } @Component(modules = [LoggerModule::class]) interface MiddlewareComponent { fun buildComponent(): Middleware } //custom implementation class NullLogger : Logger //injecting logger module with interface implementation val middleware = DaggerMiddlewareComponent.builder().loggerModule(LoggerModule(NullLogger())).build().buildComponent()
Below are widely used Dependency Injection frameworks mostly by android & Java application projects. For Android application development, the suggested Framework by Google are Dagger and Hilt. These frameworks help to avoid writing boilerplate code. Guice Guice (pronounced ‘juice’) is a lightweight dependency injection framework for Java 6 and above, brought to you by Google. (github.com) With 10K stars this framework is mostly used by Java developers where Java is used for backend & Application development. For Android, this framework is not suggested as this framework use reflections to scan annotations from code. This requires significant CPU cycles and RAM thus slowdowns application launch. Reflection on the desktop/server JVM is very efficient, and even very large Guice applications don’t have performance problems related to Guice. Manage your app’s memory | Android Developers : Other dependency injection frameworks that use reflection tend to initialize processes by scanning your code for annotations. This process can require significantly more CPU cycles and RAM and can cause a noticeable lag when the app launches. ...
Redis is in-memory data structure store. Redis has a really good documentation to learn and implement framework capabilities. My mentor at Job guided me to learn Redis. My primary focus is to understand how Redis helps for Distributed Caching. Distributed Caching Distributed Caching is cache shared by multiple servers. The miclsroservices or services can keep it’s own cache for data but distributed cache has many advantages as we can scale and manage cache at one place. The caches are used to save time to reduce cost to read database from database. The in memory(RAM cache) data is much more efficient to perform read operations as compared to SQL databases. Redis supports distributed caching by clusters. Twitter has redis instance for every user across data centers. When a tweet comes, the tweet is inserted into redis cache instance of every user who follows the tweet owner Real Time Delivery Twitter. Distributing caching helps twitter to deliver 300k tweets/sec. ...
We can make our code snippets more interesting and readable by sharing code with color formatting. To turn on colors, just add language short name 😉 For C# code, add cs after ```. ```cs write your code here ``` Example: static void Main(string[] args) { Logging logger = new Logging(); logger.Log("login success"); }
Code reviews plays an important role to keep code consistent and readable. Code reviews are conducted to maintain quality and simplicity. The bugs should be taken care by automated tests. Code reviews are the best way to learn coding skills from your team members. In this post, I want to share my opinion on how to write code reviews comments. I read a document Google code review. This document is really helpful to write code reviews comments and how to fix, reply on code review comments. The variable name, function name or class name style formatting This type of comments should be taken care by compile time code validation. For example, Android has checkstyle. Rename class or variable names When we are suggesting someone to rename something in our code, maybe we can express or thoughts by: why to change name? what are the suggested names? ...
Checkstyle is a development tool to help programmers write Java code that adheres to a coding standard. Steps to enable checkstyle for Android Project Create checkstyle.xml Create folder checkstyle inside Android Project app folder. Create file checkstyle.xml Reference <?xml version="1.0"?> <!DOCTYPE module PUBLIC "-//Puppy Crawl//DTD Check Configuration 1.2//EN" "http://www.puppycrawl.com/dtds/configuration_1_2.dtd"> <!-- Checkstyle configuration that checks the sun coding conventions from: - the Java Language Specification at http://java.sun.com/docs/books/jls/second_edition/html/index.html - the Sun Code Conventions at http://java.sun.com/docs/codeconv/ - the Javadoc guidelines at http://java.sun.com/j2se/javadoc/writingdoccomments/index.html - the JDK Api documentation http://java.sun.com/j2se/docs/api/index.html - some best practices Checkstyle is very configurable. Be sure to read the documentation at http://checkstyle.sf.net (or in your downloaded distribution). Most Checks are configurable, be sure to consult the documentation. To completely disable a check, just comment it out or delete it from the file. Finally, it is worth reading the documentation. --> <module name="Checker"> <!-- If you set the basedir property below, then all reported file names will be relative to the specified directory. See http://checkstyle.sourceforge.net/5.x/config.html#Checker <property name="basedir" value="${basedir}"/> --> <!-- Checks that a package-info.java file exists for each package. --> <!-- See http://checkstyle.sf.net/config_javadoc.html#JavadocPackage --> <module name="JavadocPackage"/> <!-- Checks whether files end with a new line. --> <!-- See http://checkstyle.sf.net/config_misc.html#NewlineAtEndOfFile --> <module name="NewlineAtEndOfFile"/> <!-- Checks that property files contain the same keys. --> <!-- See http://checkstyle.sf.net/config_misc.html#Translation --> <module name="Translation"/> <!-- Checks for Size Violations. --> <!-- See http://checkstyle.sf.net/config_sizes.html --> <module name="FileLength"/> <!-- Checks for whitespace --> <!-- See http://checkstyle.sf.net/config_whitespace.html --> <module name="FileTabCharacter"/> <!-- Miscellaneous other checks. --> <!-- See http://checkstyle.sf.net/config_misc.html --> <module name="RegexpSingleline"> <property name="format" value="\s+$"/> <property name="minimum" value="0"/> <property name="maximum" value="0"/> <property name="message" value="Line has trailing spaces."/> </module> <module name="TreeWalker"> <!-- Checks for Javadoc comments. --> <!-- See http://checkstyle.sf.net/config_javadoc.html --> <module name="JavadocMethod"/> <module name="JavadocType"/> <module name="JavadocVariable"/> <module name="JavadocStyle"/> <!-- Checks for Naming Conventions. --> <!-- See http://checkstyle.sf.net/config_naming.html --> <module name="ConstantName"/> <module name="LocalFinalVariableName"/> <module name="LocalVariableName"/> <module name="MemberName"/> <module name="MethodName"/> <module name="PackageName"/> <module name="ParameterName"/> <module name="StaticVariableName"/> <module name="TypeName"/> <!-- Checks for Headers --> <!-- See http://checkstyle.sf.net/config_header.html --> <!-- <module name="Header"> --> <!-- The follow property value demonstrates the ability --> <!-- to have access to ANT properties. In this case it uses --> <!-- the ${basedir} property to allow Checkstyle to be run --> <!-- from any directory within a project. See property --> <!-- expansion, --> <!-- http://checkstyle.sf.net/config.html#properties --> <!-- <property --> <!-- name="headerFile" --> <!-- value="${basedir}/java.header"/> --> <!-- </module> --> <!-- Following interprets the header file as regular expressions. --> <!-- <module name="RegexpHeader"/> --> <!-- Checks for imports --> <!-- See http://checkstyle.sf.net/config_import.html --> <module name="AvoidStarImport"/> <module name="IllegalImport"/> <!-- defaults to sun.* packages --> <module name="RedundantImport"/> <module name="UnusedImports"/> <!-- Checks for Size Violations. --> <!-- See http://checkstyle.sf.net/config_sizes.html --> <module name="LineLength"/> <module name="MethodLength"/> <module name="ParameterNumber"/> <!-- Checks for whitespace --> <!-- See http://checkstyle.sf.net/config_whitespace.html --> <module name="EmptyForIteratorPad"/> <module name="GenericWhitespace"/> <module name="MethodParamPad"/> <module name="NoWhitespaceAfter"/> <module name="NoWhitespaceBefore"/> <module name="OperatorWrap"/> <module name="ParenPad"/> <module name="TypecastParenPad"/> <module name="WhitespaceAfter"/> <module name="WhitespaceAround"/> <!-- Modifier Checks --> <!-- See http://checkstyle.sf.net/config_modifiers.html --> <module name="ModifierOrder"/> <module name="RedundantModifier"/> <module name="AvoidNestedBlocks"/> <module name="EmptyBlock"/> <module name="LeftCurly"/> <module name="NeedBraces"/> <module name="RightCurly"/> <module name="AvoidInlineConditionals"/> <module name="DoubleCheckedLocking"/> <!-- MY FAVOURITE --> <module name="EmptyStatement"/> <module name="EqualsHashCode"/> <module name="HiddenField"/> <module name="IllegalInstantiation"/> <module name="InnerAssignment"/> <module name="MagicNumber"/> <module name="MissingSwitchDefault"/> <module name="RedundantThrows"/> <module name="SimplifyBooleanExpression"/> <module name="SimplifyBooleanReturn"/> <module name="DesignForExtension"/> <module name="FinalClass"/> <module name="HideUtilityClassConstructor"/> <module name="InterfaceIsType"/> <module name="VisibilityModifier"/> </module> </module> Create checkstyle.gradle Create checkstyle.gradle inside app folder (at same level where build.gradle exists) ...
I use online tools to generate sequence diagrams. Recently, my colleague at work guided me about Mermaid to generate sequence diagrams. This is an awesome tool. Mermaid Mermaid has online editor Editor. However, I did not use online editor for confidentiality reasons. I created index.html and opened in browser. <html> <body> <script src="https://cdn.jsdelivr.net/npm/mermaid/dist/mermaid.min.js"></script> <script> mermaid.initialize({ startOnLoad: true }); </script> <div class="mermaid"> sequenceDiagram participant A participant B A->>B:How are you? B-->> A: I am good loop test loop A->>B:How are you? B-->> A: I am good end </div> </body> </html>
Recently, I struggled a bit to figure out a way to access Azure-Pipeline Variables in Node.js JavaScript/TypeScript project. However, it is easy. .yml Pipeline code - task: Npm@1 displayName: "Run project" env: MyVariableName: $(MYVARIABLENAME) // this is pipeline variable name, in Capital letters inputs: commands: 'custom' CustomCommand: 'run test' npm Package install package string-replace-loader TypeScript/JavaScript File Create a file with any name “test.ts” test.ts const test = () => { const myVariable = "My-Variable"; }; Setup webpack.config.js module: { rules: [ { test: /test\.ts$/, loader: 'string-replace-loader', options: { search: 'My-Variable', replace: process.env['MyVariableName'] // from .yml env } } ] } } Finally "scripts" :{ "test": "webpack --config webpack.config.js" }